Jump to content

Photo

Jumpman levels with custom code


31 replies to this topic

#1 playermissile OFFLINE  

playermissile

    Chopper Commander

  • 218 posts

Posted Tue Nov 22, 2016 5:15 PM

There's a new release of Omnivore that includes a built-in MAC/65 compatible assembler:

 

https://github.com/r...ases/tag/0.14.0

 

There's an overview of creating custom levels here: https://playermissil...ith-custom-code

 

and I'm including my level Clockwise as an example.

 

atari042.png

Attached Files



#2 tschak909 OFFLINE  

tschak909

    Stargunner

  • 1,749 posts
  • Location:USA

Posted Tue Nov 22, 2016 5:22 PM

AWESOME! :)

 

-Thom



#3 Goochman OFFLINE  

Goochman

    Quadrunner

  • 6,788 posts
  • Moongates to the Past

Posted Fri Dec 23, 2016 7:41 PM

Question on the designer.  Im working on a level which has alot of girder erasing.  After a certain point I am getting an error trying to create more triggers for erasing - or actual building for that matter.  Is there a limit?



#4 playermissile OFFLINE  

playermissile

    Chopper Commander

  • Topic Starter
  • 218 posts

Posted Fri Dec 23, 2016 11:11 PM

Yeah, looking at the routine in the code at $4b00 it looks like there is a 256 byte limit for the harvest table. Each harvest table entry is 6 bytes long, so that means there's a limit of 42 triggers.

 

I'll have to add a check for than into Omnivore.



#5 Mclaneinc OFFLINE  

Mclaneinc

    River Patroller

  • 4,848 posts
  • Location:Northolt, UK

Posted Sat Dec 24, 2016 3:58 AM

Bloody hell, I missed this post...PM that is an awesome bit of coding, its a level that would have shone on the game when released..

 

Of course I'm loving all these new levels so a MASSIVE thank you to Goochman, Kevin, yourself and anyone else who made some, wish the contest had gone better but I guess its been a tough old year all around so people were lost for time.

 

Still, it makes the ones that did get made even more special...

 

Thank you all..



#6 Goochman OFFLINE  

Goochman

    Quadrunner

  • 6,788 posts
  • Moongates to the Past

Posted Sat Dec 24, 2016 9:56 PM

Yeah, looking at the routine in the code at $4b00 it looks like there is a 256 byte limit for the harvest table. Each harvest table entry is 6 bytes long, so that means there's a limit of 42 triggers.

 

I'll have to add a check for than into Omnivore.

 

Well I hit it :) - I had a pretty cool idea to pretty much wipe a map.....maybe I can still do it with fewer triggers :)



#7 playermissile OFFLINE  

playermissile

    Chopper Commander

  • Topic Starter
  • 218 posts

Posted Sat Dec 24, 2016 11:52 PM

 

Well I hit it :) - I had a pretty cool idea to pretty much wipe a map.....maybe I can still do it with fewer triggers :)

 

It's not supported in Omnivore because it's not something that is very useful in general, but it's possible to design your own drawing elements. I haven't experimented with it, but Kevin and I noted the possibility in our reverse engineering notes:

 

http://playermissile...#h.wtrim2a10znr

 

I don't know what the limits are, so I'm not sure how wide or tall the elements can be, but for your purposes, maybe you could create a large erasable element that could wipe out a bigger area.



#8 Savetz OFFLINE  

Savetz

    Dragonstomper

  • 795 posts
  • Location:Portland OR

Posted Tue Jan 17, 2017 3:15 PM

I've published my custom code for three new levels (Score Eater, Lasers, and Jetpack) here: 

 

http://atariage.com/...test/?p=3674126



#9 Goochman OFFLINE  

Goochman

    Quadrunner

  • 6,788 posts
  • Moongates to the Past

Posted Wed Jan 18, 2017 12:37 PM

Ok seeing some of the samples Im trying to add some custom code (or should I say steal and reuse :) ) - In the editor I dont see a way to add custom code the way its documented on your website:

 

You will need to edit the assembly source with your favorite text editor and then use the Jumpman -> Custom Code... to add the source file to your level. After that it will remember the file when you load the level again. Be sure the source code is in the same directory as the .atr image. If you move the .atr file to a new place, be sure to copy your assembly file as well.

 

At this point Im taking some custom code and trying to change the sprite definitions for my use.



#10 playermissile OFFLINE  

playermissile

    Chopper Commander

  • Topic Starter
  • 218 posts

Posted Wed Jan 18, 2017 1:38 PM

Are you using the latest Omnivore, 0.14.1? You also need to be in the jumpman level editor mode, otherwise you won't get that menu item. It doesn't work in the hex edit view.



#11 Mclaneinc OFFLINE  

Mclaneinc

    River Patroller

  • 4,848 posts
  • Location:Northolt, UK

Posted Wed Jan 18, 2017 2:18 PM

You may want to update the site to show 14.1 as the latest, still says 13.0, downloads does give you 14.1 tho...



#12 playermissile OFFLINE  

playermissile

    Chopper Commander

  • Topic Starter
  • 218 posts

Posted Wed Jan 18, 2017 2:54 PM

You may want to update the site to show 14.1 as the latest, still says 13.0, downloads does give you 14.1 tho...

 

I can see how that would be confusing.  :) I don't update the website as much now that I'm on a podcasting break, so I'm just going to remove the latest version number and point everyone at the download page.



#13 Goochman OFFLINE  

Goochman

    Quadrunner

  • 6,788 posts
  • Moongates to the Past

Posted Wed Jan 18, 2017 3:15 PM

Ok that does explain the issue :) - I have the latest Omnivore and have the menu item.

 

One last question before I sorta give up.  I copied the scoreeater.s file from this entry: http://atariage.com/forums/topic/255262-jumpman-level-design-contest/page-4#entry3674126 

 

I renamed it to x.s

I created a new level in the same folder called x.atr

 

When I tried to add the custom code file I got an error stating:

 

In file x.s line 4-- Error:  Illegal label name, must start with '@', '?', or a letter

 

Here are the first couple of lines of the file:

 

;score eater, a jumpman level
;by Kevin Savetz, October 26-27 2016
 
.org $2900
 
vbi1:
 
 
It seems it doesnt like .org $900????


#14 Savetz OFFLINE  

Savetz

    Dragonstomper

  • 795 posts
  • Location:Portland OR

Posted Wed Jan 18, 2017 3:20 PM

You're right — it doesn't work. This is my fault, but really @playermissile's fault :)

 

He changed Omnivore's source code syntax from cc65 to Mac/65. So — while score eater and jetpack compiled fine when I wrote them, Omnivore's required syntax changed out from under me since then. I need to update the code to the new syntax.  In the mean time, lasers.s is already in Mac/65 syntax so it should work.

 

—Kevin

 

 

 

Ok that does explain the issue :) - I have the latest Omnivore and have the menu item.

 

One last question before I sorta give up.  I copied the scoreeater.s file from this entry: http://atariage.com/forums/topic/255262-jumpman-level-design-contest/page-4#entry3674126 

 

I renamed it to x.s

I created a new level in the same folder called x.atr

 

When I tried to add the custom code file I got an error stating:

 

In file x.s line 4-- Error:  Illegal label name, must start with '@', '?', or a letter

 

Here are the first couple of lines of the file:

 

;score eater, a jumpman level
;by Kevin Savetz, October 26-27 2016
 
.org $2900
 
vbi1:
 
 
It seems it doesnt like .org $900????

 



#15 Savetz OFFLINE  

Savetz

    Dragonstomper

  • 795 posts
  • Location:Portland OR

Posted Wed Jan 18, 2017 7:37 PM

I have corrected the code format for jetpack and scoreeater.

 

—Kevin

Attached File  scoreeater.s   6.17KB   38 downloads

Attached File  jetpack.s   4.87KB   21 downloads

 



#16 Goochman OFFLINE  

Goochman

    Quadrunner

  • 6,788 posts
  • Moongates to the Past

Posted Wed Jan 18, 2017 8:04 PM

Excellent - thanks!  :)



#17 Goochman OFFLINE  

Goochman

    Quadrunner

  • 6,788 posts
  • Moongates to the Past

Posted Wed Jan 18, 2017 8:08 PM

One last question - is there some easy to use editor on the PC which would give me the sprite strings for the data (is it in hex?)

 

$00,$00,$24,$18,$18,$24,$00,$00



#18 Savetz OFFLINE  

Savetz

    Dragonstomper

  • 795 posts
  • Location:Portland OR

Posted Wed Jan 18, 2017 8:46 PM

I don't know. I don't use a PC, and anyway I like to design graphics on graph paper.

 

On a Mac, you can the the calculator app: in binary mode, enter the image data for that line (e.g. 10010101 then convert to hex (95). I'm sure something is similar on a PC.

 

-Kevin

 

One last question - is there some easy to use editor on the PC which would give me the sprite strings for the data (is it in hex?)

 

$00,$00,$24,$18,$18,$24,$00,$00



#19 playermissile OFFLINE  

playermissile

    Chopper Commander

  • Topic Starter
  • 218 posts

Posted Wed Jan 18, 2017 11:49 PM

You're right — it doesn't work. This is my fault, but really @playermissile's fault :)

 

He changed Omnivore's source code syntax from cc65 to Mac/65. So — while score eater and jetpack compiled fine when I wrote them, Omnivore's required syntax changed out from under me since then. I need to update the code to the new syntax.  In the mean time, lasers.s is already in Mac/65 syntax so it should work.

 

The previous system (unpublished, Kevin was testing it) used the assembler & linker from cc65, but it was Makefile based and not integrated into Omnivore. Linking on cc65 is a particular pain, because you have to set up all these strange segments in a separate file and there's precious little documentation. And I don't know how it would have ever worked under Windows.

 

So, wanting to make life much, much easier for everybody except Kevin, I found this great standalone assembler, ATasm, that uses MAC/65 source. I hacked around with it and created a python wrapper, then embedded this into Omnivore. It is much simpler and easier to use, plus all the vectors and triggers are automatically plugged into the level. Kevin is welcome to go back to the cc65 approach if he wants to.  :)



#20 playermissile OFFLINE  

playermissile

    Chopper Commander

  • Topic Starter
  • 218 posts

Posted Wed Jan 18, 2017 11:58 PM

One last question - is there some easy to use editor on the PC which would give me the sprite strings for the data (is it in hex?)

 

$00,$00,$24,$18,$18,$24,$00,$00

 

There's a flash-based player you can use from your browser at http://www.playsoft.co.uk/aplayed.html

 

You can save the data in a binary format to reload in the browser, or LIST it to a file and you'll get the text output you want. It can do animation, too.



#21 Goochman OFFLINE  

Goochman

    Quadrunner

  • 6,788 posts
  • Moongates to the Past

Posted Thu Jan 19, 2017 6:34 AM

 

There's a flash-based player you can use from your browser at http://www.playsoft.co.uk/aplayed.html

 

You can save the data in a binary format to reload in the browser, or LIST it to a file and you'll get the text output you want. It can do animation, too.

 

That worked perfectly - expect a few updates to some of my older levels :) 



#22 Savetz OFFLINE  

Savetz

    Dragonstomper

  • 795 posts
  • Location:Portland OR

Posted Fri Apr 7, 2017 7:56 PM

It's been too long, but I will start to post the source code to Randy Glover's custom-code Jumpman levels, with my comments. By studying the code and my comments, you can learn to make custom-coded levels, too!

 

There's no custom code on level 1.

Here's level 2, Robots II.

Attached File  02: robots I.s   12.19KB   21 downloads

 

; Commented code for ROBOTS II Jumpman level

; Comments by Kevin Savetz, 2017
 
        *= $2880
L2880   JSR $49d0             ; Standard main game loop
L2883   JSR $4b00
        LDA L283E
        CMP #$00
        BEQ L289E
        LDA $30be
        CMP #$08
        BCC L2883
        LDA $30f0
        CMP #$ff
        BNE L2880
        JMP L283F
L289e   JMP (L2844)
 
        *= $2900
        LDA $30bd             ; VBI entry point. 
        CMP #$02              ; if Jumpman is super dead,
        BNE L2912
L2907   JMP $311b             ; exit
L290a   LDA #$00              ; after the 2x loop
        STA L284F+1           ; Set no peanut has been taken
        JMP $311b             ; exit
L2912   LDA L2A5C             ; $2a5c is Are Players initialized?
        CMP #$00
        BNE L291C
        JMP L2A0C             ; Go initialize Players.
L291c   JSR $41e0             ; Players are already initialized. 41e0 gets a number that's
 ; 1 just 1/4 of the time 
        BNE L2907             ; exit 1/4 of the time. Slows things down.
        INC L2A65
        LDA L2A65             ; alternates between 0 and 1 for animation frames
        AND #$01
        STA L2A65             ; alternate it
        LDX #$ff
L292e   INX                   ; this loop is done twice, as 0 and 1
        CPX #$02
        BEQ L290A             ; exit the loop
        LDA L2A5A,X           ; is robot already on the move to a destination?
        CMP #$00
        BNE L2990             ; If so, JMP away
        LDA L284F+1           ; Robot is not on the move. 
        CMP #$00              ; Has a peanut just been taken?
        BNE L2955             ; If so, JMP away
        LDA L2A66,X           ; Nope. No robots are not moving, so just animate in place.
         ; 2a66 Counts 1-4
        AND #$03              ; set the image for each robot
        STA L2A66,X           ; to one of the first 4 graphics
        INC L2A66,X           ; rotating in order
        LDA L2A66,X           ; their graphics move in unison
        STA $3076,X           ; Set image data for Player 2&3
        JMP L292E             ; next loop
L2955   JSR L29DA             ; Oh boy a peanut has been taken
        LDA #$01              ; reminder: we're in a loop where X will be 0 or 1
        STA L2A5A,X           ; Set this robot is on the move
        LDA L2A61,X           ; get pointer to next 3-tuple of movement data, LB
        STA $cb               ; cb-d1 are scratch 0-page addresses
        LDA L2A63,X           ; starts by loading cb-cc with 2e00 when X=0 and 2f00 when X=1
        STA $cc
        LDY #$00
        LDA ($cb),Y           ; load 2e00, e.g. This is the robot's X change.
        STA L2A5D,X           ; remember robot's X change
        INY
        LDA ($cb),Y           ; load 2e01, e.g.
        STA L2A5F,X           ; remember robot's Y change
        INY
        LDA ($cb),Y           ; load 2e02, e.g.
        STA L2A68,X           ; remember robot move counter
        LDA L2A61,X           ; pointer to next 3-tuple of movement data
        CLC
        ADC #$03              ; set up pointer to read next set
        STA L2A61,X
        LDA L2A68,X           ; get robot move counter
        CMP #$00
        BNE L292E             ; if >0, iterate X to next robot
        STA L2A5A,X           ; robot's not to its destination yet. Store counter in the On The Move? byte
        JMP L292E             ; iterate X to next robot
L2990   DEC L2A68,X           ; Robot is not to its destination. Move a step. Decrement robot move countdown.
        BEQ L2955             ; if its 0, jump to oh boy a peanut has been taken
        LDA $306c,X           ; get Horizontal position of robot
        CLC
        ADC L2A5D,X           ; add robot X change
        STA $306c,X           ; change robot's X
        CLC
        LDA $3071,X           ; get Vertical position of robot
        ADC L2A5F,X           ; add robot Y change
        STA $3071,X           ; change robot's Y
        LDA L2A5D,X           ; get robot X change again
        CMP #$02              ; Show graphic for robot facing the right way, and animate. is it going 02 (right)?
        BEQ L29B9
        CMP #$fe              ; is it fe (left)?
        BEQ L29BE
        LDA #$05              ; robot's X is not changing (so it's on a ladder)
        JMP L29C3
L29b9   LDA #$01              ; it's 02 right, so use image 1 (or 2)
        JMP L29C3
L29be   LDA #$03              ; its fe left, so use image 3 (or 4)
        JMP L29C3             ; this JMP is silly.
L29c3   CLC                   ; A is loaded with a pointer to a different image based on X movement
        ADC L2A65             ; add 0 or 1 to animate movement
        STA $3076,X           ; Set image data for robot
        JMP L292E             ; end of loop; NEXT X
        LDA #$00              ; THIS CODE IS UNREACHABLE
        STA L2A5A,X           ; UNREACHABLE:Store that robot has reached its destination, no longer moving
        LDA #$01              ; UNREACHABLE:
        STA L2A66,X           ; UNREACHABLE:reset 1-4 counter back to 1 for standing still animation
        JMP L292E             ; UNREACHABLE:iterate loop; NEXT X
L29da   LDA #$f1              ; sound subroutine
        STA $3040
        LDA #$29              ; load address of sound
        STA $3041
        STX L29F0             ; temp. storage of X register. Basically, a PHX
        LDA #$07
        JSR $32b0             ; submit the sound list to the player for robot sound
        LDX L29F0             ; reset X register after JSR. PLX
        RTS                   ; end sound subrouine
L29f0   BRK                   ; Temporary stortage of X in the sound routine.
        .byte $01, $a2, $14, $01; Robot sound data
        .byte $f0, $01, $3c, $01
        .byte $c8, $01, $64, $01
        .byte $a0, $01, $8c, $01
        .byte $78, $01, $7d, $01
        .byte $73, $01, $82, $01
        .byte $6e, $01, $00
L2a0c   LDA #$00              ; PM Initialization
        STA $3080             ; old Y position of Player 2
        STA $3081             ; old Y position of Player 3
        LDA #$6a
        STA $305d             ; image data LB for Player 2
        STA $305e             ; image data LB for Player 3
        LDA #$2a
        STA $3062             ; image data HB for Player 3
        STA $3063             ; image data HB for Player 3
        LDA #$0c
        STA $3067             ; image data bytes per image for Player 2
        STA $3068             ; image data bytes per image for Player 3
        LDA #$01
        STA $3076             ; Set image data for Player 2
        STA $3077             ; Set image data for Player 3
        LDA L2A5D
        STA $306c             ; Horizontal position of player 2
        LDA L2A5E
        STA $306d             ; Horizontal position of player 3
        LDA L2A5F
        STA $3071             ; Y position of Player 2
        LDA L2A60
        STA $3072             ; Y position of Player 3
        LDA #$01
        STA $3058             ; P2 active
        STA $3059             ; P3 active
        INC L2A5C             ; Mark players as initialized
        JMP $311b             ; exit
L2a5a   .byte $00             ; Player 2 on the move?  0=reached destination
        .byte $00             ; Player 3 on the move?  0=reached destination
L2a5c   .byte $00             ; Are Players initialized? 1=yes
L2a5d   .byte $98             ; Player 2 robot X change
L2a5e   .byte $44             ; Player 3 robot X change
L2a5f   .byte $be             ; Player 2 robot Y change
L2a60   .byte $32             ; Player 3 robot Y change
L2a61   .byte $00             ; Player 2 pointer to next 3-tuple of movement data, LB
        .byte $00             ; Player 3 pointer to next 3-tuple of movement data, LB
L2a63   .byte $2e             ; Player 2 pointer to 3-tuples of movement data, HB (this never changes)
        .byte $2f             ; Player 3 pointer to 3-tuples of movement data, HB (this never changes)
L2a65   .byte $00             ; alternates between 0 and 1 (for animation)
L2a66   .byte $01             ; Counts 1-4 for Player 2 robot animation
        .byte $01             ; Counts 1-4 for Player 3 robot animation
L2a68   .byte $00             ; Player 2 robot move countdown
        .byte $00             ; Player 3 robot move countdown
        .byte $18, $3c, $70, $70; UNUSED DATA
        .byte $3c, $18, $18, $24
        .byte $42, $81, $81, $81
        .byte $18, $3c, $70, $70
        .byte $3c, $18, $18, $24
        .byte $42, $81, $42, $24
        .byte $18, $3c, $0e, $0e
        .byte $3c, $18, $18, $18
        .byte $24, $42, $42, $42
        .byte $18, $3c, $0e, $0e
        .byte $3c, $18, $18, $18
        .byte $24, $42, $24, $18
        .byte $18, $3c, $66, $66
        .byte $3c, $18, $18, $18
        .byte $18, $24, $42, $81
        .byte $18, $3c, $66, $66
        .byte $3c, $18, $18, $18
        .byte $18, $18, $24, $42
 
What follows is a lot of mystery code that should not be there, which is duplicated in Roll Me Over.
Then some graphic data from The Roost. Skipping all that mess.
 
        *= $2dff
        BRK                   ; movement data for Player 2 bot (orange)
        .byte $02             ; 3-tuples: X change - +2 pixels is right
        .byte $00             ; Y change is 0
        .byte $05             ; ...for 5 cycles
        .byte $00             ; step 2 of move 1: moving up so X change is 0
        .byte $fe             ; Y change is -2.
        .byte $21             ; for 21 cycles
        .byte $02, $00        ; step 3: move right again
        .byte $07             ; for 7 cycles
        .byte $00, $00, $00, $02; 000000 means end of data for that move
        .byte $00, $0d, $00, $fe
        .byte $28, $fe, $00, $08
        .byte $00, $00, $00, $fe
        .byte $01, $10, $fe, $00
        .byte $0f, $00, $fe, $11
        .byte $fe, $00, $09, $00
        .byte $00, $00, $02, $00
        .byte $09, $00, $02, $11
        .byte $fe, $00, $0b, $00
        .byte $02, $11, $fe, $00
        .byte $09, $00, $00, $00
        .byte $fe, $00, $07, $00
        .byte $02, $11, $fe, $00
        .byte $0d, $00, $02, $11
        .byte $02, $00, $09, $00
        .byte $00, $00, $02, $00
        .byte $05, $02, $01, $22
        .byte $02, $00, $06, $00
        .byte $00, $00, $02, $00
        .byte $05, $00, $fe, $21
        .byte $02, $00, $07, $00
        .byte $00, $00, $02, $00
        .byte $0d, $00, $fe, $28
        .byte $fe, $00, $08, $00
        .byte $00, $00, $fe, $01
        .byte $10, $fe, $00, $0f
        .byte $00, $fe, $11, $fe
        .byte $00, $09, $00, $00
        .byte $00, $02, $00, $09
        .byte $00, $02, $11, $fe
        .byte $00, $0b, $00, $02
        .byte $11, $fe, $00, $09
        .byte $00, $00, $00, $fe
        .byte $00, $07, $00, $02
        .byte $11, $fe, $00, $0d
        .byte $00, $02, $11, $02
        .byte $00, $09, $00, $00
        .byte $00, $02, $00, $05
        .byte $02, $01, $22, $02
        .byte $00, $06, $00, $00
        .byte $00
        *= $2f00
        .byte $02, $01, $0f, $02; movement data for Player 3 bot (green)
        .byte $00, $05, $00, $02
        .byte $11, $02, $00, $0d
        .byte $00, $00, $00, $fe
        .byte $00, $1b, $00, $02
        .byte $11, $02, $00, $0b
        .byte $00, $00, $00, $fe
        .byte $00, $17, $00, $02
        .byte $21, $02, $00, $07
        .byte $00, $00, $00, $fe
        .byte $00, $07, $00, $fe
        .byte $11, $02, $00, $09
        .byte $00, $00, $00, $fe
        .byte $00, $09, $00, $fe
        .byte $11, $02, $00, $0d
        .byte $00, $fe, $11, $02
        .byte $00, $23, $00, $00
        .byte $00, $00, $fe, $11
        .byte $fe, $00, $19, $fe
        .byte $ff, $0f, $00, $00
        .byte $00, $02, $01, $0f
        .byte $02, $00, $05, $00
        .byte $02, $11, $02, $00
        .byte $0d, $00, $00, $00
        .byte $fe, $00, $1b, $00
        .byte $02, $11, $02, $00
        .byte $0b, $00, $00, $00
        .byte $fe, $00, $17, $00
        .byte $02, $21, $02, $00
        .byte $07, $00, $00, $00
        .byte $fe, $00, $07, $00
        .byte $fe, $11, $02, $00
        .byte $09, $00, $00, $00
        .byte $fe, $00, $09, $00
        .byte $fe, $11, $02, $00
        .byte $0d, $00, $fe, $11
        .byte $02, $00, $23, $00
        .byte $00, $00, $00, $fe
        .byte $11, $fe, $00, $19
        .byte $fe, $ff, $0f, $00
        .byte $00, $00
 


#23 Savetz OFFLINE  

Savetz

    Dragonstomper

  • 795 posts
  • Location:Portland OR

Posted Fri Apr 7, 2017 8:12 PM

Commented code for BOMBS AWAY.

Attached File  03: bombs away.s   10.82KB   17 downloads

 

        *= $2860
L2860   JSR $49d0             ; Main loop (standard)
L2863   JSR $4b00
        LDA L283E
        CMP #$00
        BEQ L287E
        LDA $30be
        CMP #$08
        BCC L2863
        LDA $30f0
        CMP #$ff
        BNE L2860
        JMP L283F
L287e   JMP (L2844)
 
         *= $2900
        LDA $30bd             ; VBI entry point #1
        CMP #$02              ; is Jumpman super dead?
        BNE L2916
        LDA $3034             ; Yes, he's dead. Is a sound playing on voice 2? (Explosion noise)
        CMP #$00
        BNE L2913             ; There's a sound, exit. (Wait for the explosion sound to end)
        LDA #$00              ; Explosion sound is over, so quiet and falling sound, which happens on audio channel 3
        STA $d205             ; Quiet AUDC3
L2913   JMP $311b
L2916   JSR $41e0             ; Jumpman is alive
        BNE L2913             ; Exit 1/4 of the time. Keeps the bombs from falling too fast
L291b   LDA $d20a             ; get a random number
        AND #$07              ; only want 3 bits - make the number from 0-7
        BNE L2960             ; if it's >0 JMP to make bombs fall and explode
        LDA $d20a             ; get another random number
        AND #$07              ; make it 0-7 too
        CMP #$05              ; this is a second chance for bombdrop
        BCS L2960             ; if it's >= 5, JMP to make bombs fall and explode
        TAX
        LDA L29C3,X           ; check the table of available Players to see if a Player is available as a new bomb
        CMP #$00
        BNE L2960             ; if that table entry>0, Player not available as a new bomb, so, JMP away
        LDA #$01              ; Start a new bomb
        STA $3055,X           ; Turn Player on
        LDA #$c9
        STA $305a,X           ; image data LB
        LDA #$29
        STA $305f,X           ; image data HB. We're using the first group of bombs in the image series.
        LDA #$08
        STA $3064,X           ; image data bytes per image
L2947   LDA $d20a             ; random number
        CMP #$30
        BCC L2947             ; if < $30 go get another random # (too far left)
        CMP #$c8
        BCS L2947             ; >= #c8 is also unacceptable (too far right), get another # 
        STA $3069,X           ; that's the player X
        LDA #$01
        STA $306e,X           ; Player Y = top of screen
        STA $3073,X           ; Use graphic 1
        STA L29C3,X           ; Set player is in use as a bomb
L2960   INC L29C8             ; The following happens whether a new bomb was made or not.
        LDA L29C8
        AND #$03
L2968   STA L29C8             ; 29c8 iterates 0-3 for animation frames
        LDX #$ff
L296d   INX                   ; FOR X = 0 TO 4
        CPX #$05
        BEQ L29AA             ; if X=5 end the loop
        LDA L29C3,X           ; 29c3 is "is this player usable as a bomb?" 0=available, 1=in use, 5-0a=exploding, ff=don't use
        CMP #$ff
        BEQ L296D             ; this player is not available as a bomb, iterate to next player
        CMP #$05
        BCS L296D             ; if its >=5 (exploding), iterate to next player
        CMP #$00
        BEQ L296D             ; if its 0, iterate to next player
        LDA $306e,X           ; So it must be 1. Make it fall. Get Y position
        CLC
        ADC #$03              ; move it down
        CMP #$c5              ; if it at the bottom, 'splode it
        BCS L29A2
        STA $306e,X           ; if it's not too low, save new Y position
        STA $d204             ; falling sound on AUDF3
        LDA #$a2
        STA $d205             ; AUDC3
        LDA L29C8             ; the 0-3 counter
        CLC
        ADC #$01
        STA $3073,X           ; Set Player to next animation frame
        JMP L296D             ; NEXT X
L29a2   LDA #$05              ; Bomb reached the floor
        STA L29C3,X           ; Mark it as ready to explode.
        JMP L296D             ; NEXT X
L29aa   LDA L29C6             ; done iterating thru players
        ORA L29C6             ; if both bombs are "availilable" (not falling or exploding) then quiet AUD3
        ORA L29C7             ; Notice how 29c6 is used twice. I bet one of those was originally 29c3 to support the combined-missile Player bomb
        CMP #$00
        BEQ L29BA
        JMP $311b
L29ba   STA $d204             ; quiet AUDF3
        STA $d205             ; quiet AUDC3
        JMP $311b
L29c3   .byte $ff             ; Table of Players. Don't use Combined Missile Player as a bomb. (But you can! try it by changing it to 0)
 ; I ended up doing that in my Smart Bombs Away level
        .byte $ff             ; don't use Player 0 as a bomb - that's jumpman!
        .byte $ff             ; don't use player 1 as a bomb - that's the shadow!
L29c6   BRK                   ; Do use Player 2 for a bomb
L29c7   BRK                   ; Do use Player 3 as a bomb
L29c8   BRK                   ; iterates 0-3 for animation frames
        .byte $66, $3c, $18, $18; Images start here
        .byte $3c, $2c, $3c, $18
        .byte $34, $3c, $18, $18
        .byte $3c, $34, $3c, $18
        .byte $18, $18, $18, $18
        .byte $3c, $3c, $3c, $18
        .byte $2c, $3c, $18, $18
        .byte $3c, $3c, $3c, $18
        .byte $00, $00, $00, $00
        .byte $00, $24, $18, $18
        .byte $00, $00, $00, $24
        .byte $3c, $18, $7e, $18
        .byte $10, $4a, $52, $5a
        .byte $2c, $bd, $7e, $18
        .byte $00, $00, $08, $52
        .byte $3c, $99, $7e, $18
        .byte $00, $00, $00, $08
        .byte $10, $4a, $3c, $18
        .byte $4c, $1b, $31, $00
        .byte $ff, $ff, $00, $00
        .byte $00
        .byte $66, $3c, $18, $18; Here's a second copy of the bomb graphics, not used.
        .byte $3c, $2c, $3c, $18
        .byte $34, $3c, $18, $18
        .byte $3c, $34, $3c, $18
        .byte $18, $18, $18, $18
        .byte $3c, $3c, $3c, $18
        .byte $2c, $3c, $18, $18
        .byte $3c, $3c, $3c, $18
        .byte $00, $00, $00, $00
        .byte $00, $24, $18, $18
        .byte $00, $00, $00, $24
        .byte $3c, $18, $7e, $18
        .byte $10, $4a, $52, $5a
        .byte $2c, $bd, $7e, $18
        .byte $00, $00, $08, $52
        .byte $3c, $99, $7e, $18
        .byte $00, $00, $00, $08
        .byte $10, $4a, $3c, $18
 
        *= $2ac0
        ORA ($8e,X)           ; Sound data for explosion
        .byte $14
        .byte $03
        ORA ($8b,X)
        ASL $0103,X
        DEY
        PLP
        .byte $03
        ORA ($85,X)
        .byte $32
        .byte $03
        ORA ($81,X)
        .byte $3c
        .byte $03
 
        *= $2b00
        INC L2B9E             ; VBI entry point #2 - handles explosions
        LDA L2B9E
        AND #$01
        STA L2B9E             ; 2b9e switches between 0 and 1
        BEQ L2B10
L2b0d   JMP $311b             ; if it's 1 - half the time - exit
L2b10   LDX #$ff
L2b12   INX                   ; FOR X=0 to 4
        CPX #$05
        BEQ L2B0D             ; after the looping, exit
        LDA L29C3,X
        CMP #$0a              ; Has this bomb finished explosion sequence? (05-0a)
        BEQ L2B6C             ; Yes: JMP away for cleanup
        BCS L2B12             ; if status>$0a (that is, $ff, iterate to next player)
        CMP #$05              ; if it is not about to explode or already exploding, iterate to next bomb
        BCC L2B12             ; NEXT X
        INC L29C3,X           ; This bomb is exploding. Increment explosion counter (5-0a) there are 4 animation frames, 6-9. 5 is ready to explode, 0a is done and ready for cleanup Note: we've incremented it for NEXT time, but A is still the lower number.
        STA $3073,X           ; choose image for bomb. conveniently, explosion images are numbers 6-9 in the graphics list.
        CMP #$05              ; if this is the first image in the explosion sequence
        BEQ L2B41             ; JMP away to cycle back to 1st frame
L2b2e   LDA $3073,X           ; get current animation image in use for bomb
        TAY                   ; which goes in Y
        LDA L2B94,Y           ; It looks up the animation frame number in this table to get the color for this part of the explosion. The first 5 cells of the table are unused; only the data in the 5th-0Ath cells are used.
        PHA                   ; That color number goes on the stack
        LDA L2B8A,X           ; offset table for Player colors
        TAY                   ; which goes in Y
        PLA                   ; fetch the color the stack
        STA $02c0,Y           ; change Player color for pretty, colorful explosion
        JMP L2B12             ; NEXT X
L2b41   LDA $3069,X           ; cycle back to 1st image of 4 in a series
        SEC
        SBC #$04
        STA $3069,X           ; revert to 1st image in animation set
        LDA L2B8F,X           ; get offset for adjusting Player width from table
        TAY
        LDA #$55              ; $55 is an interesting choice here for doube width. References I found say to use 0 for std, 1 for dbl, 2 for quad. There's no $55. But the LSB makes it double width.
        STA $d008,Y           ; adjust Player width
        STX L2B6B             ; PHX: Store X register (our offset from the table) for a sec, sound routine at 32b0's gonna clobber it
        LDA #$c0
        STA $3040             ; LB of sound data
        LDA #$2a
        STA $3041             ; HB of sound data
        LDA #$04              ; A is the duration or speed? for the music driver
        JSR $32b0             ; music driver: start playing a tune pointed to by $3040
        LDX L2B6B             ; PLX: I want my X back
        JMP L2B2E             ; Loop back
L2b6b   BRK                   ; Temp storage for X register. 6502 doesn't have PHX. Sad!
L2b6c   LDA L2B8F,X           ; Bomb explosion sequence is done, clean up
        TAY                   ; 2b8f-2b93 is table of offets from d008 for resetting Player widths
        LDA #$00
        STA $d008,Y           ; reset Player width to single
        LDA L2B8A,X           ; 2b8a-e is table of offets for reseting Player colors, from 02c0
        TAY
        LDA L282A,Y           ; get startup color for that Player
        STA $02c0,Y           ; reset player colors after splosion
        LDA #$00
        STA L29C3,X           ; reset Player: available for new bomb
        STA $3069,X           ; set player X offscreen
        JMP L2B12             ; NEXT X
L2b8a   .byte $07, $00, $01, $02; offset table - reset Player colors from $$02c0
        .byte $03
L2b8f   .byte $04, $00, $01, $02; offset table - resetting player widths from $d008
        .byte $03
L2b94   .byte $00, $00, $00, $00; Table of colors for explosion. The first 5 bytes are unused, the real colors are in the 5th thru 0a spaces
        .byte $00, $54, $1a, $0f
        .byte $28, $54
L2b9e   BRK                   ; switches between 0 and 1
 
 
; later in the level there's some garbage data

 

 


#24 Savetz OFFLINE  

Savetz

    Dragonstomper

  • 795 posts
  • Location:Portland OR

Posted Fri Apr 7, 2017 8:20 PM

Jumping Blocks.

Attached File  04: jumping blocks.s   2.93KB   17 downloads

 

; Commented code for JUMPING BLOCKS Jumpman level

; Comments by Kevin Savetz, 2017
 
        *= $2860
        LDA #$04
        STA $30b6             ; Missiles are 2 pixels high
        LDA #$55              ; Wide missiles
        STA $d00c
        JMP L2880
 
        *= $2880
L2880   JSR $49d0
L2883   JSR $4b00
        LDA L283E
        CMP #$00
L288b   BEQ L289E
L288d   LDA $30be
        CMP #$08
        BCC L2883
        LDA $30f0
        CMP #$ff
        BNE L2880
        JMP L28A6
L289e   LDA #$02
        STA $30b6
        JMP (L2844)
L28a6   LDA #$02
        STA $30b6             ; put Missile height back to normal
        JMP L283E+1
 
        *= $28f9
        BRK                   ; This level is interesting, programatically very simple.
        BRK                   ; It uses the Jumpman engine's regular bullet logic
        BRK                   ; But changes the size and color of the bullets. 
        BRK                   ; Instead of the usual "bullet hit means death" code at 49a0,
        BRK                   ; the level's custom hit detection routine tricks the engine
        BRK                   ; into thinking the trigger was pressed and the joystick was
        BRK  ; moved to jump in one of three directions.
        LDA $3098             ; VBI entry point
        ORA $3099
L2906   ORA $309a
        ORA $309b
        AND #$01              ; Did any of the Missiles hit Jumpman? (In some other levels Glover uses $30a0 to do the exact same thing. I wonder if this was written before he wrote that.)
        CMP #$00
        BNE L2915
        JMP L2943             ; if not, jump away
L2915   LDA #$10              ; A missile hit Jumpman
        STA $302c             ; Fake pressing the trigger
        LDA $d20a
        AND #$03              ; Random # 0-3
        CMP #$00              ; Fake joystick push in a direction based on the random #
        BEQ L292B
        CMP #$01
        BEQ L2933
        CMP #$02
        BEQ L293B
L292b   LDA #$e0              ; Joystick up
        STA $3028
        JMP L2953
L2933   LDA #$70              ; Joystick right
        STA $3028             ; STA here makes the game engine think the stick is pushed
        JMP L2953
L293b   LDA #$b0              ; Joystick left
        STA $3028
        JMP L2953
L2943   LDA $3028             ; No missile hit Jumpman
        AND #$0f              ; ?force the joystick to 0-127. Hm, why not just STA 0?
        STA $3028
        LDA $302c
        AND #$0f              ; ?Same thing with the trigger result. What information is saved in those 4 bits?
        STA $302c
L2953   LDA $30b8             ; This continues whether or not a missile hit JM
        STA $02c7             ; Change the misiles to a random(ish) color.
        JMP $311b             ; And we're done
        ORA ($9d,X)           ; The rest of the level code is junk/unused code.
        ORA L2C30+1           ; Some seems to be assembly source from Builder level. See Reverse Engineering Notes.
 


#25 Savetz OFFLINE  

Savetz

    Dragonstomper

  • 795 posts
  • Location:Portland OR

Posted Fri Apr 7, 2017 8:34 PM

Vampire. 

 

Attached File  05: vampire.s   8.48KB   17 downloads

 

        *= $2900

        LDA $30be             ; VBI vector. If Jumpman status
        CMP #$08              ; is super dead
        BCS L290E             ; exit this routine. Allows the death song to play with out bats flying around
        LDA $30bd             ; Check the other Jumpman alive flag.
        CMP #$02              ; if JM is Dead With Birdies
        BNE L2911
L290e   JMP $311b             ; ...also exit this routine
L2911   LDA L2A73             ; check Are Players initialized? byte
        CMP #$00
        BNE L291B
        JMP L29C8             ; Not initialized, JMP away to initialize them
L291b   INC L2A5E             ; 2a5e increments 0-7
        LDA L2A5E             ; only continue if it==7
        CMP #$07              ; otherwise exit
        BNE L290E             ; this gives the bats their relatively slow pace
        LDA #$00
        STA L2A5E             ; reset counter to 0
        LDX #$ff
L292c   INX                   ; FOR X=0 TO 4
        CPX #$05              ; Iterating through the Players, where 0=Combined Missile Player, 3 and 4=the other available Players. These are the bats.
        BEQ L290E             ; after the loop, exit
        CPX #$01
        BEQ L292C             ; if X=1, NEXT X
        CPX #$02
        BEQ L292C             ; if X=2, NEXT X
        LDA L2A5F,X           ; Check Bat Asleep/Awake Table
        CMP #$02
        BEQ L2943
        JMP L292C             ; If it's not 2 (awake), NEXT X
L2943   INC $3073,X           ; Move bat to next animation frame
        LDA $3073,X
        CMP #$08              ; But if its 8...
        BNE L2952
        LDA #$02              ; move it back to 2. The flying animation is frames 2-7
        STA $3073,X
L2952   LDA $306a             ; Get Jumpman X
        CMP $3069,X           ; Compare with Bat X
        BEQ L298B             ; if they're equal, JMP away
        LDA $306f             ; But they're not equal, so get Jumpman Y
        CMP $306e,X           ; compare with Bat Y
        BEQ L29A8             ; If the Ys are equal, JMP away
        CLC                   ; Neither Xs or Ys are equal. Sad bat.
L2963   LDA $3069,X           ; Get Bat X again
        ADC L2A64,X           ; Add X to this bat's entry in Bat X Change Table
        STA $3069,X           ; New Bat X
        CLC
        LDA $306e,X           ; Get Bat Y
        CLC
        ADC L2A68+1,X         ; Add Y to this bat's entry in Bat Y change table
        CMP #$c2
        BCS L297E             ; If the Y would be >=$c2, JMP to fix that
        STA $306e,X           ; New Bat Y
        JMP L292C             ; NEXT X
L297e   LDA #$00              ; Bat Y is >=C2, at bottom of screen, move it back to top
        STA $306e,X
        LDA #$02
        STA L2A68+1,X         ; Adjust Bat Y Change Table: This bat will continue moving downward
        JMP L292C             ; NEXT X
L298b   LDA #$00              ; JMP dest when Bat X = JM X
        STA L2A64,X           ; Store 0 in this Bat's X Change Table entry
        LDA $306f             ; Get JM Y
        CMP $306e,X           ; Compare to Bat's Y
        BCS L29A0             ; JMP away if JM Y >= Bat Y (JM is below bat)
        LDA #$fe              ; Bat is below JM, so
        STA L2A68+1,X         ; modify Bat Change Table entry to move it up
        JMP L2A0E
L29a0   LDA #$02              ; Bat is above JM, so...
        STA L2A68+1,X         ; Modify Bat Y Change table to move it down
        JMP L2A0E
L29a8   LDA #$00              ; JMP dest when Bat Y = JM Y
        STA L2A68+1,X         ; Modify Bat's Y change table entry to 0
        LDA $306a             ; Get Jumpman's X
        CMP $3069,X           ; compare to bat's X
        BCS L29BD             ; If JM X >= Bat's (bat is to the left of JM) JMP away
        LDA #$fe              ; Bat wants to move left
        STA L2A64,X           ; store that in X change table
        JMP L2A0E
L29bd   LDA #$02              ; Bat is to JM's left
        STA L2A64,X           ; Modify Bat X Table to start Bat moving right
        JMP L2A0E
L29c5   JMP $311b
L29c8   LDX #$ff              ; Player initialization
        STX L2A73             ; Set Are Players Initialized? byte
L29cd   INX                   ; FOR X=0 to 4
        CPX #$05
        BEQ L29C5             ; after this loop, exit
        CPX #$01
        BEQ L29CD             ; IF X=1 NEXT X cuz this player is for JM
        CPX #$02
        BEQ L29CD             ; IF X=2 NEXT X cuz this player is for the shadow
        LDA #$26
        STA $305a,X           ; Player Image Data LB
        LDA #$2a
        STA $305f,X           ; Player Image Data Table HB
        LDA #$08
        STA $3064,X           ; there are 8 data bytes per image
        STA $3082,X           ; just stuff anything other than the startup image in the "old" image data table 
        LDA L2A64,X           ; Get Bat Starting X from Bat X Change Table
        STA $3069,X           ; Save Bat X
        LDA L2A68+1,X         ; Get Bat starting Y from table
        STA $306e,X           ; Save Bat Y
        LDA #$01
        STA $3073,X           ; Start all bats with Image 1 (sleeping)
        STA $3055,X           ; Activate that Player
        LDA #$00
        STA L2A64,X           ; From now on the Bat X table is change (X movement direction) so store 0. Bats always start traveling down
        LDA #$02
        STA L2A68+1,X         ; Same thing for the Y change table. Bats will head down when they wake
        JMP L29CD             ; NEXT X
L2a0d   BRK                   ; temp storage for X
L2a0e   STX L2A0D             ; If bat changed X or Y direction, it wants to talk about it. PHX
        LDA #$74
        STA $3040             ; Sound data LB
        LDA #$2a
        STA $3041             ; Sound data HB
        LDA #$07              ; This is speed or duration or something for the sound routine
        JSR $32b0             ; start playing bat sound
        LDX L2A0D             ; PLX
        JMP L2963             ; JMP to actually move the bat based on new X and Y change choices
L2a26   .byte $24, $18, $18, $3c; Image Data
        .byte $7e, $18, $18, $00
        .byte $81, $42, $42, $3c
        .byte $18, $00, $00, $00
        .byte $00, $00, $81, $7e
        .byte $18, $00, $00, $00
        .byte $00, $00, $00, $7e
        .byte $99, $00, $00, $00
        .byte $00, $00, $00, $3c
        .byte $5a, $42, $81, $00
        .byte $00, $00, $00, $5a
        .byte $bd, $00, $00, $00
        .byte $00, $00, $81, $db
        .byte $3c, $00, $00, $00
L2a5e   .byte $00             ; Counts 0-7
L2a5f   .byte $01, $00, $00, $01; Bat asleep(01)/wake(02) Table
L2a63   .byte $01
L2a64   .byte $74, $00, $00, $7c; Bat X Change Table
        .byte $84
L2a69   .byte $2a, $00, $00, $28; Bat Y Change Table
        .byte $2a
        .byte $01, $00, $00, $01; This looks like a "use this Player as a bat?" table but is unused
        .byte $01
L2a73   .byte $00             ; Are Players Initialized? byte 0=no
        .byte $01, $a6, $05, $01; Sound data
        .byte $0f, $01, $0a, $01
        .byte $00, $a0, $cc, $ae
        .byte $a0, $c7, $cc, $cf
        .byte $d6, $c5, $d2, $20
        .byte $a0, $cc, $ae, $a0
        .byte $c7, $cc, $cf, $d6
        .byte $c5, $d2, $20
 
 
        *= $2aff
        BRK                   ; This VBI vector runs with every peanut collection
L2b00   LDA L283E             ; # of peanuts left to take? Level starts with 14. 
        CMP #$0c              ; If >=12, exit
        BCS L2B13
        CMP #$09
        BCS L2B14             ; if 9, wake 1st bat
        CMP #$06
        BCS L2B21             ; if 6, wake second bat
        CMP #$03
        BCS L2B2E             ; if 3, wake 3rd bat
L2b13   RTS                   ; otherwise exit
L2b14   LDA L2A5F             ; Is bat 1 (CMP) sleeping?
        CMP #$01              ; he really should be at this juncture
        BNE L2B13             ; but if not, exit
        LDA #$02
        STA L2A5F             ; mark him as awake
        RTS                   ; exit
L2b21   LDA L2A62             ; Is bat 2 (Player 2) asleep
        CMP #$01              ; again, he really should be when we get here
        BNE L2B13             ; if not, exit
        LDA #$02
        STA L2A62             ; mark him as awake
        RTS                   ; exit
L2b2e   LDA L2A62+1           ; and Bat 3 (Player 3)
        CMP #$01
        BNE L2B13
        LDA #$02
        STA L2A62+1           ; same deal
        RTS
 
; The rest of the stuff on this level is unused/junk, including
; image data from The Roost
 





0 user(s) are browsing this forum

0 members, 0 guests, 0 anonymous users