00001. ; Super Mario Bros. 3 Full Disassembly by Southbird 2012 
00002. ; For more info, see http://www.sonicepoch.com/sm3mix/ 
00003. ; 
00004. ; PLEASE INCLUDE A CREDIT TO THE SOUTHBIRD DISASSEMBLY 
00005. ; AND THE ABOVE LINK SOMEWHERE IN YOUR WORKS :) 
00006. ; 
00007. ; Original disassembler source generated by DCC6502 version v1.4 
00008. ; (With labels, comments, and some syntax corrections for nesasm by Southbird) 
00009. ; For more info about DCC6502, e-mail veilleux@ameth.org 
00010. ; 
00011. ; This source file last updated: 2012-01-29 13:49:44.499306754 -0600 
00012. ; Distribution package date: Fri Apr 6 23:46:16 UTC 2012 
00013. ;---------------------------------------------------------------------------
 
00014. ; Indexed per top 2 bits of tile ($00, $40, $80, $C0)
 
00015. ; Defines the shape of a slope tile for slope levels (Hills style and underground)
 
00016. ; Values used for Player_Slopes:
 
00017. ; 1) A tile is retrieved in Player_GetTileAndAttr
 
00018. ; 2) Pick the proper table start by tile "quadrant" ($00, $40, $80, $C0)
 
00019. ; 3) The relevant value from Tile_AttrTable (a series of values-per-quad
 
00020. ; loaded by tileset) is grabbed; the tile retrieved in #1 is used as
 
00021. ; a base value. Hills/Underground style attr table: $25, $5F, $99, $E2
 
00022. ; 4) If the tile is beneath the base this data is not used
 
00023. ; (e.g. using the above Hills example, if we got tile $16 -- this is
 
00024. ; quad $00, and the quad $00 base tile is $25, so this is not valid)
 
00025. ; 5) If tile is in range, it is subtracted, so using the Hills example:
 
00026. ; Tile $25 -- first table, index 0. Tile $26 -- first table, index 1.
 
00027. ; Tile $5F -- second table, index 0. Etc...
 
00028. Level_SlopeSetByQuad:
 
00029. .word Level_SlopeQuad00 ; Tile quad $00
 
00030. .word Level_SlopeQuad40 ; Tile quad $40
 
00031. .word Level_SlopeQuad80 ; Tile quad $80
 
00032. .word Level_SlopeQuadC0 ; Tile quad $C0
 
00033.  
00034. ; These tables are rooted by the base value for each tile quad by the only two
 
00035. ; tilesets to support slopes, 3 (Hills) and 14 (Underground)
 
00036. ; For reference, that attribute set is: $25, $5F, $99, $E2
 
00037. ;
 
00038. ; The value in the next four LUTs reference a "slope shape" as defined in the
 
00039. ; Slope_LUT table that follows...
 
00040.  
00041. Level_SlopeQuad00:
 
00042. ; Tile $25+
 
00043. .byte $01, $07, $02, $0C, $0D, $0E, $0F, $07, $03, $03, $03, $03, $03, $03, $07, $04
 
00044. .byte $07, $04, $04, $03, $03, $03, $03, $03, $07, $04, $07, $04, $04, $04, $04, $04
 
00045.  
00046. Level_SlopeQuad40:
 
00047. ; Tile $5F+
 
00048. .byte $03, $03, $03, $03, $03, $03, $03, $03, $03, $03, $03, $03, $03, $03, $03, $03
 
00049. .byte $03, $03, $03, $03, $03, $03, $03, $03, $03, $03, $03, $03, $03
 
00050.  
00051. Level_SlopeQuad80:
 
00052. ; Tile $99+
 
00053. .byte $01, $07, $02, $0C, $0D, $0E, $0F, $05, $06, $11, $12, $13, $14, $08, $07, $04
 
00054. .byte $07, $04, $04, $08, $03, $03, $03, $03, $03, $03, $03, $03, $03, $03, $03, $03
 
00055. .byte $03, $03, $03, $03, $03, $03, $08
 
00056.  
00057. Level_SlopeQuadC0:
 
00058. ; Tile $E2+
 
00059. .byte $01, $07, $02, $0C, $0D, $0E, $0F, $05, $06, $11, $12, $13, $14, $07, $03, $03
 
00060. .byte $03, $03, $08, $07, $04, $07, $04, $04, $08, $08, $04
 
00061.  
00062. Slope_LUT:
 
00063. ; Lower 4 bits are the ground slope height
 
00064. ; Upper 4 bits are the ceiling slope height
 
00065.  
00066. ; 16 entries for each pixel across the 16x16 tile
 
00067. ; <--- --- X --- -->
 
00068. .byte $10, $10, $10, $10, $10, $10, $10, $10, $10, $10, $10, $10, $10, $10, $10, $10 ; $00 (used as "no slope", i.e. BG tile)
 
00069. .byte $0F, $0E, $0D, $0C, $0B, $0A, $09, $08, $07, $06, $05, $04, $03, $02, $01, $00 ; $01
 
00070. .byte $00, $01, $02, $03, $04, $05, $06, $07, $08, $09, $0A, $0B, $0C, $0D, $0E, $0F ; $02
 
00071. .byte $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0 ; $03 (all solid square tiles)
 
00072. .byte $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00 ; $04 (wall, see PRG008_B9F4)
 
00073. .byte $00, $10, $20, $30, $40, $50, $60, $70, $80, $90, $A0, $B0, $C0, $D0, $E0, $F0 ; $05
 
00074. .byte $F0, $E0, $D0, $C0, $B0, $A0, $90, $80, $70, $60, $50, $40, $30, $20, $10, $00 ; $06
 
00075. .byte $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00 ; $07 (unsloped ground, see PRG008_B9F4)
 
00076. .byte $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0 ; $08 (unsloped ceiling, see PRG008_B9F4)
 
00077. .byte $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0 ; $09
 
00078. .byte $02, $02, $02, $02, $03, $03, $03, $03, $04, $04, $04, $04, $03, $03, $03, $02 ; $0A
 
00079. .byte $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0, $F0 ; $0B
 
00080. .byte $0F, $0E, $0E, $0D, $0D, $0D, $0C, $0C, $0B, $0B, $0A, $0A, $09, $09, $08, $08 ; $0C
 
00081. .byte $07, $06, $06, $05, $05, $05, $04, $04, $03, $03, $02, $02, $01, $01, $00, $00 ; $0D
 
00082. .byte $00, $00, $01, $01, $02, $02, $03, $03, $04, $04, $05, $05, $05, $06, $06, $07 ; $0E
 
00083. .byte $08, $08, $09, $09, $0A, $0A, $0B, $0B, $0C, $0C, $0D, $0D, $0D, $0E, $0E, $0F ; $0F
 
00084. .byte $0E, $0D, $0B, $0A, $09, $09, $08, $08, $08, $08, $08, $09, $09, $0A, $0B, $0D ; $10
 
00085. .byte $00, $00, $10, $10, $20, $20, $30, $30, $40, $40, $50, $50, $50, $60, $60, $70 ; $11
 
00086. .byte $80, $80, $90, $90, $A0, $A0, $B0, $B0, $C0, $C0, $D0, $D0, $D0, $E0, $E0, $F0 ; $12
 
00087. .byte $F0, $E0, $E0, $D0, $D0, $D0, $C0, $C0, $B0, $B0, $A0, $A0, $90, $90, $80, $80 ; $13
 
00088. .byte $70, $60, $60, $50, $50, $50, $40, $40, $30, $30, $20, $20, $10, $10, $00, $00 ; $14
 
00089.  
00090. ; Effect on Player's velocity per slope "shape" index (Slope_LUT above)
 
00091. Slope_PlayerVel_Effect:
 
00092. .byte $00, -$03, $03, $00, $00, $00, $00, $00 ; $00-$07
 
00093. .byte $00, $00, $00, $00, -$02, -$02, $02, $02 ; $08-$0F
 
00094. .byte $00, $00, $00, $00, $00 ; $10-$14
 
00095.  
00096. ; Effect on Object's velocity per slope "shape" index (Slope_LUT above)
 
00097. ; NOTE: Incomplete -- probably avoids concering with certain ceiling slopes
 
00098. Slope_ObjectVel_Effect:
 
00099. ; $80 disables response to this slope
 
00100. .byte $00, -$02, $02, $00, $00, $80, $80, $00 ; $00-$07
 
00101. .byte $00, $80, $00, $80, -$01, -$01, $01, $01 ; $08-$0F
 
00102. ; Incomplete, missing $10-$14
 
00103. ; RAS: Slopes $10-$14 are ceiling slopes, which enemies have pretty much
 
00104. ; no proper involvement with in native SMB3. Also due to a "lazy" calculation
 
00105. ; found after the label PRG000_C5EC, these would be inaccessible anyway!
 
00106.  
00107.  
00108. ; Default address for Level_GndLUT_L/H in a non-slope level; note that this
 
00109. ; doesn't make sense (the address for Level_LayPtrOrig_AddrH would just give
 
00110. ; you the original layout pointer, not slope data) so this is probably dead
 
00111. ; code. Level_GndLUT_L/H isn't used in non-slope levels anyway...
 
00112. NonSlope_LUT_Addr: .word Level_LayPtrOrig_AddrH
 
00113.  
00114. ; Default address for Level_GndLUT_L/H in a sloped level
 
00115. Slope_LUT_Addr: .word Slope_LUT
 
00116.  
00117. ; This defines 4 values per Level_Tileset, with each of those values
 
00118. ; belonging to a tile "quadrant" (i.e. tiles beginning at $00, $40,
 
00119. ; $80, and $C0), and defines the beginning tile which should be
 
00120. ; classified as "underwater" (Minimum Tile Under Water By Quad)
 
00121. ; A value of $FF is used to indicate that no tile in that quadrant
 
00122. ; is underwater (and for the first three quads is unreachable!)
 
00123. Level_MinTileUWByQuad:
 
00124. ; 4 values per Level_TilesetIdx, which is basically (Level_Tileset - 1)
 
00125. ; Listing by valid Level_Tileset values for consistency...
 
00126. .byte $FF, $FF, $FF, $DA ; 1 Plains style
 
00127. .byte $FF, $FF, $FF, $DA ; 2 Mini Fortress style
 
00128. .byte $FF, $FF, $FF, $C1 ; 3 Hills style
 
00129. .byte $FF, $FF, $FF, $DA ; 4 High-Up style
 
00130. .byte $FF, $FF, $FF, $DA ; 5 pipe world plant infestation
 
00131. .byte $02, $3F, $8A, $C0 ; 6 water world
 
00132. .byte $FF, $FF, $FF, $DA ; 7 Toad House
 
00133. .byte $FF, $FF, $8A, $DA ; 8 Vertical pipe maze
 
00134. .byte $FF, $FF, $FF, $DA ; 9 desert levels
 
00135. .byte $FF, $FF, $FF, $DA ; 10 Airship
 
00136. .byte $FF, $FF, $FF, $DA ; 11 Giant World
 
00137. .byte $FF, $FF, $FF, $DA ; 12 Ice level
 
00138. .byte $FF, $FF, $FF, $DA ; 13 Sky level
 
00139. .byte $FF, $FF, $FF, $C1 ; 14 Underground
 
00140.  
00141.
 
00142. ToadItem_PalPerItem:
 
00143. .byte $30 ; 0: INVALID
 
00144. .byte $16 ; 1: Mushroom
 
00145. .byte $2A ; 2: Fire flower
 
00146. .byte $2A ; 3: Leaf
 
00147. .byte $2A ; 4: Frog
 
00148. .byte $17 ; 5: Tanooki
 
00149. .byte $27 ; 6: Hammer
 
00150. .byte $36 ; 7: Judgems
 
00151. .byte $27 ; 8: P-Wing
 
00152. .byte $30 ; 9: Star
 
00153. .byte $07 ; A: Anchor
 
00154. .byte $36 ; B: Hammer
 
00155. .byte $27 ; C: Whistle
 
00156. .byte $27 ; D: Music Box
 
00157.  
00158. ; Objects detect using a specific offset from this list
 
00159. ; Which "group" they use is specified by the respective value in ObjectGroup_Attributes2
 
00160. Object_TileDetectOffsets:
 
00161.  
00162. ; Y/X offset pairs
 
00163.  
00164. ; For groups:
 
00165. ; Row 1: Object Y Velocity >= 0 (on ground or moving downward)
 
00166. ; Row 2: Object Y Velocity < 0 (moving upward)
 
00167. ; Row 3: Object X velocity < 0 (moving leftward)
 
00168. ; Row 4: Object X velocity >= 0 (moving rightward)
 
00169.  
00170. ; Group 0
 
00171. ; Y X
 
00172. .byte $10, $03 ; At feet
 
00173. .byte $00, $03 ; At head
 
00174. .byte $0A, $01 ; Wall to left
 
00175. .byte $0A, $07 ; Wall to right
 
00176.  
00177. ; Group 1
 
00178. ; NOTE! See "ONLY HAPPENS WITH GROUP 1 ROW 1 AND SLOPES ENABLED"
 
00179. ; In a sloped level using this group, alternate offsets (below
 
00180. ; Group 12) are used for left/right wall detection!
 
00181. ; Y X
 
00182. OTDO_G1R1: .byte $10, $08 ; At feet
 
00183. .byte $00, $08 ; At head
 
00184. .byte $09, $00 ; Wall to left
 
00185. .byte $09, $0F ; Wall to right
 
00186.  
00187. ; Group 2
 
00188. ; Y X
 
00189. .byte $20, $08 ; At feet
 
00190. .byte $0C, $08 ; At head
 
00191. .byte $15, $00 ; Wall to left
 
00192. .byte $15, $0F ; Wall to right
 
00193.  
00194. ; Group 3
 
00195. ; Y X
 
00196. .byte $00, $00 ; At feet
 
00197. .byte $00, $00 ; At head
 
00198. .byte $00, $00 ; Wall to left
 
00199. .byte $00, $00 ; Wall to right
 
00200.  
00201. ; Group 4
 
00202. ; Y X
 
00203. .byte $10, $08 ; At feet
 
00204. .byte $00, $08 ; At head
 
00205. .byte $08, $01 ; Wall to left
 
00206. .byte $08, $0E ; Wall to right
 
00207.  
00208. ; Group 5
 
00209. ; Y X
 
00210. .byte $10, $0C ; At feet
 
00211. .byte $00, $0C ; At head
 
00212. .byte $0A, $01 ; Wall to left
 
00213. .byte $0A, $17 ; Wall to right
 
00214.  
00215. ; Group 6
 
00216. ; Y X
 
00217. .byte $20, $0C ; At feet
 
00218. .byte $00, $0C ; At head
 
00219. .byte $11, $01 ; Wall to left
 
00220. .byte $11, $17 ; Wall to right
 
00221.  
00222. ; Group 7
 
00223. ; Y X
 
00224. .byte $10, $08 ; At feet
 
00225. .byte $00, $08 ; At head
 
00226. .byte $08, $08 ; Wall to left
 
00227. .byte $08, $08 ; Wall to right
 
00228.  
00229. ; Group 8
 
00230. ; Y X
 
00231. .byte $20, $08 ; At feet
 
00232. .byte $10, $08 ; At head
 
00233. .byte $18, $01 ; Wall to left
 
00234. .byte $18, $0E ; Wall to right
 
00235.  
00236. ; Group 9
 
00237. ; Y X
 
00238. .byte $04, $14 ; At feet
 
00239. .byte $04, $1C ; At head
 
00240. .byte $0C, $14 ; Wall to left
 
00241. .byte $0C, $1C ; Wall to right
 
00242.  
00243. ; Group 10
 
00244. ; Y X
 
00245. .byte $10, $08 ; At feet
 
00246. .byte $00, $08 ; At head
 
00247. .byte $0A, $00 ; Wall to left
 
00248. .byte $0A, $1F ; Wall to right
 
00249.  
00250. ; Group 11
 
00251. ; Y X
 
00252. .byte $30, $08 ; At feet
 
00253. .byte $00, $08 ; At head
 
00254. .byte $10, $01 ; Wall to left
 
00255. .byte $10, $0E ; Wall to right
 
00256.  
00257. ; Group 12
 
00258. ; Y X
 
00259. .byte $30, $08 ; At feet
 
00260. .byte $00, $08 ; At head
 
00261. .byte $23, $01 ; Wall to left
 
00262. .byte $23, $0E ; Wall to right
 
00263.  
00264. ; Alternate offsets used when object utilizes "Group 1" in sloped levels
 
00265. ; See "ONLY HAPPENS WITH GROUP 1 ROW 1 AND SLOPES ENABLED"
 
00266. ; Y X
 
00267. OTDO_G1Alt: .byte $02, $01 ; Wall to left
 
00268. .byte $02, $0E ; Wall to right
 
00269.  
00270. ; Offsets used for detection of water tiles
 
00271. ; Y X
 
00272. OTDO_Water: .byte $04, $08
 
00273.  
00274.  
00275. ; Defines the "bounding box"
 
00276. ; Selected by Object_AttrFlags lower 4 bits
 
00277. Object_BoundBox:
 
00278. ; Left Right Bot Top - offsets applied to sprite X/Y
 
00279. .byte 2, 4, 2, 8 ; 0
 
00280. .byte 1, 13, 2, 8 ; 1
 
00281. .byte 2, 12, 2, 24 ; 2
 
00282. .byte 10, 27, -2, 18 ; 3
 
00283. .byte 1, 14, 2, 26 ; 4 (UNUSED)
 
00284. .byte 5, 14, 10, 18 ; 5 (UNUSED)
 
00285. .byte 2, 27, -2, 34 ; 6
 
00286. .byte 2, 20, 2, 12 ; 7
 
00287. .byte 2, 43, -2, 18 ; 8
 
00288. .byte 2, 20, 2, 28 ; 9
 
00289. .byte 2, 12, 2, 20 ; A
 
00290. .byte 0, 31, -1, 14 ; B
 
00291. .byte 1, 14, -2, 13 ; C
 
00292. .byte 4, 17, 10, 19 ; D
 
00293. .byte 4, 8, 5, 40 ; E
 
00294. .byte 2, 43, 2, 12 ; F
 
00295.  
00296. Object_AttrFlags:
 
00297. ; Defines flags which set attributes of objects
 
00298. .byte OAT_BOUNDBOX00 ; Object $00
 
00299. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $01
 
00300. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $02
 
00301. .byte OAT_BOUNDBOX00 ; Object $03
 
00302. .byte OAT_BOUNDBOX02 ; Object $04
 
00303. .byte OAT_BOUNDBOX01 ; Object $05
 
00304. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $06 - OBJ_BOUNCEDOWNUP
 
00305. .byte OAT_BOUNDBOX02 | OAT_WEAPONIMMUNITY | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $07 - OBJ_WARPHIDE
 
00306. .byte OAT_BOUNDBOX00 | OAT_WEAPONIMMUNITY | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $08 - OBJ_PSWITCHDOOR
 
00307. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $09 - OBJ_AIRSHIPANCHOR
 
00308. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $0A
 
00309. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $0B - OBJ_POWERUP_1UP
 
00310. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $0C - OBJ_POWERUP_STARMAN
 
00311. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $0D - OBJ_POWERUP_MUSHROOM
 
00312. .byte OAT_BOUNDBOX09 | OAT_HITNOTKILL ; Object $0E - OBJ_BOSS_KOOPALING
 
00313. .byte OAT_BOUNDBOX00 ; Object $0F
 
00314. .byte OAT_BOUNDBOX00 ; Object $10
 
00315. .byte OAT_BOUNDBOX00 ; Object $11
 
00316. .byte OAT_BOUNDBOX00 ; Object $12
 
00317. .byte OAT_BOUNDBOX00 ; Object $13
 
00318. .byte OAT_BOUNDBOX00 ; Object $14
 
00319. .byte OAT_BOUNDBOX00 ; Object $15
 
00320. .byte OAT_BOUNDBOX00 ; Object $16
 
00321. .byte OAT_BOUNDBOX01 ; Object $17 - OBJ_SPINYCHEEP
 
00322. .byte OAT_BOUNDBOX13 ; Object $18 - OBJ_BOSS_BOWSER
 
00323. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $19 - OBJ_POWERUP_FIREFLOWER
 
00324. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $1A
 
00325. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $1B - OBJ_BOUNCELEFTRIGHT
 
00326. .byte OAT_BOUNDBOX01 ; Object $1C
 
00327. .byte OAT_BOUNDBOX00 ; Object $1D
 
00328. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $1E - OBJ_POWERUP_SUPERLEAF
 
00329. .byte OAT_BOUNDBOX00 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $1F - OBJ_GROWINGVINE
 
00330. .byte OAT_BOUNDBOX00 ; Object $20
 
00331. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $21 - OBJ_POWERUP_MUSHCARD
 
00332. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $22 - OBJ_POWERUP_FIRECARD
 
00333. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $23 - OBJ_POWERUP_STARCARD
 
00334. .byte OAT_BOUNDBOX08 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $24 - OBJ_CLOUDPLATFORM_FAST
 
00335. .byte OAT_BOUNDBOX00 | OAT_WEAPONIMMUNITY | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $25
 
00336. .byte OAT_BOUNDBOX08 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $26 - OBJ_WOODENPLAT_RIDER
 
00337. .byte OAT_BOUNDBOX08 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $27 - OBJ_OSCILLATING_H
 
00338. .byte OAT_BOUNDBOX08 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $28 - OBJ_OSCILLATING_V
 
00339. .byte OAT_BOUNDBOX01 ; Object $29 - OBJ_SPIKE
 
00340. .byte OAT_BOUNDBOX02 ; Object $2A - OBJ_PATOOIE
 
00341. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY ; Object $2B - OBJ_GOOMBAINSHOE
 
00342. .byte OAT_BOUNDBOX08 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $2C - OBJ_CLOUDPLATFORM
 
00343. .byte OAT_BOUNDBOX07 ; Object $2D - OBJ_BIGBERTHA
 
00344. .byte OAT_BOUNDBOX11 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $2E - OBJ_INVISIBLELIFT
 
00345. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY ; Object $2F - OBJ_BOO
 
00346. .byte OAT_BOUNDBOX00 | OAT_FIREIMMUNITY ; Object $30 - OBJ_HOTFOOT_SHY
 
00347. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY ; Object $31 - OBJ_BOOSTRETCH
 
00348. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY ; Object $32 - OBJ_BOOSTRETCH_FLIP
 
00349. .byte OAT_BOUNDBOX01 ; Object $33 - OBJ_NIPPER
 
00350. .byte OAT_BOUNDBOX02 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $34 - OBJ_TOAD
 
00351. .byte OAT_BOUNDBOX00 ; Object $35 - OBJ_TOADHOUSEITEM
 
00352. .byte OAT_BOUNDBOX08 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $36 - OBJ_WOODENPLATFORM
 
00353. .byte OAT_BOUNDBOX08 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $37 - OBJ_OSCILLATING_HS
 
00354. .byte OAT_BOUNDBOX08 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $38 - OBJ_OSCILLATING_VS
 
00355. .byte OAT_BOUNDBOX01 ; Object $39 - OBJ_NIPPERHOPPING
 
00356. .byte OAT_BOUNDBOX03 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $3A - OBJ_FALLINGPLATFORM
 
00357. .byte OAT_BOUNDBOX01 ; Object $3B - OBJ_CHARGINGCHEEPCHEEP
 
00358. .byte OAT_BOUNDBOX08 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $3C - OBJ_WOODENPLATFORMFALL
 
00359. .byte OAT_BOUNDBOX01 ; Object $3D - OBJ_NIPPERFIREBREATHER
 
00360. .byte OAT_BOUNDBOX08 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $3E - OBJ_WOODENPLATFORMFLOAT
 
00361. .byte OAT_BOUNDBOX01 | OAT_BOUNCEOFFOTHERS | OAT_FIREIMMUNITY ; Object $3F - OBJ_DRYBONES
 
00362. .byte OAT_BOUNDBOX01 ; Object $40 - OBJ_BUSTERBEATLE
 
00363. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $41 - OBJ_ENDLEVELCARD
 
00364. .byte OAT_BOUNDBOX01 ; Object $42 - OBJ_CHEEPCHEEPPOOL2POOL
 
00365. .byte OAT_BOUNDBOX01 ; Object $43 - OBJ_CHEEPCHEEPPOOL2POOL2
 
00366. .byte OAT_BOUNDBOX08 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $44 - OBJ_WOODENPLATUNSTABLE
 
00367. .byte OAT_BOUNDBOX00 | OAT_FIREIMMUNITY ; Object $45 - OBJ_HOTFOOT
 
00368. .byte OAT_BOUNDBOX02 ; Object $46 - OBJ_PIRANHASPIKEBALL
 
00369. .byte OAT_BOUNDBOX06 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $47 - OBJ_GIANTBLOCKCTL
 
00370. .byte OAT_BOUNDBOX01 ; Object $48 - OBJ_TINYCHEEPCHEEP
 
00371. .byte OAT_BOUNDBOX01 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $49 - OBJ_FLOATINGBGCLOUD
 
00372. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $4A - OBJ_BOOMBOOMQBALL
 
00373. .byte OAT_BOUNDBOX13 ; Object $4B - OBJ_BOOMBOOMJUMP
 
00374. .byte OAT_BOUNDBOX13 ; Object $4C - OBJ_BOOMBOOMFLY
 
00375. .byte OAT_BOUNDBOX00 ; Object $4D
 
00376. .byte OAT_BOUNDBOX00 ; Object $4E
 
00377. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY ; Object $4F - OBJ_CHAINCHOMPFREE
 
00378. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY ; Object $50 - OBJ_BOBOMBEXPLODE
 
00379. .byte OAT_BOUNDBOX01 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $51 - OBJ_ROTODISCDUAL
 
00380. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $52 - OBJ_TREASUREBOX
 
00381. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY ; Object $53 - OBJ_PODOBOOCEILING
 
00382. .byte OAT_BOUNDBOX12 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $54
 
00383. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY ; Object $55 - OBJ_BOBOMB
 
00384. .byte OAT_BOUNDBOX07 ; Object $56 - OBJ_PIRANHASIDEWAYSLEFT
 
00385. .byte OAT_BOUNDBOX07 ; Object $57 - OBJ_PIRANHASIDEWAYSRIGHT
 
00386. .byte OAT_BOUNDBOX01 ; Object $58 - OBJ_FIRECHOMP
 
00387. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY ; Object $59 - OBJ_FIRESNAKE
 
00388. .byte OAT_BOUNDBOX01 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $5A - OBJ_ROTODISCCLOCKWISE
 
00389. .byte OAT_BOUNDBOX01 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $5B - OBJ_ROTODISCCCLOCKWISE
 
00390. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $5C - OBJ_ICEBLOCK
 
00391. .byte OAT_BOUNDBOX01 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $5D - OBJ_TORNADO
 
00392. .byte OAT_BOUNDBOX01 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $5E - OBJ_ROTODISCDUALOPPOSE
 
00393. .byte OAT_BOUNDBOX01 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $5F - OBJ_ROTODISCDUALOPPOSE2
 
00394. .byte OAT_BOUNDBOX01 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $60 - OBJ_ROTODISCDUALCCLOCK
 
00395. .byte OAT_BOUNDBOX01 ; Object $61 - OBJ_BLOOPERWITHKIDS
 
00396. .byte OAT_BOUNDBOX01 ; Object $62 - OBJ_BLOOPER
 
00397. .byte OAT_BOUNDBOX13 ; Object $63 - OBJ_BIGBERTHABIRTHER
 
00398. .byte OAT_BOUNDBOX01 ; Object $64 - OBJ_CHEEPCHEEPHOPPER
 
00399. .byte OAT_BOUNDBOX00 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $65 - OBJ_WATERCURRENTUPWARD
 
00400. .byte OAT_BOUNDBOX00 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $66 - OBJ_WATERCURRENTDOWNARD
 
00401. .byte OAT_BOUNDBOX13 | OAT_FIREIMMUNITY ; Object $67 - OBJ_LAVALOTUS
 
00402. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY ; Object $68 - OBJ_TWIRLINGBUZZY
 
00403. .byte OAT_BOUNDBOX01 ; Object $69 - OBJ_TWIRLINGSPINY
 
00404. .byte OAT_BOUNDBOX01 ; Object $6A - OBJ_BLOOPERCHILDSHOOT
 
00405. .byte OAT_BOUNDBOX12 | OAT_FIREIMMUNITY ; Object $6B - OBJ_PILEDRIVER
 
00406. .byte OAT_BOUNDBOX01 | OAT_BOUNCEOFFOTHERS ; Object $6C - OBJ_GREENTROOPA
 
00407. .byte OAT_BOUNDBOX01 | OAT_BOUNCEOFFOTHERS ; Object $6D - OBJ_REDTROOPA
 
00408. .byte OAT_BOUNDBOX01 | OAT_BOUNCEOFFOTHERS ; Object $6E - OBJ_PARATROOPAGREENHOP
 
00409. .byte OAT_BOUNDBOX01 | OAT_BOUNCEOFFOTHERS ; Object $6F - OBJ_FLYINGREDPARATROOPA
 
00410. .byte OAT_BOUNDBOX01 | OAT_BOUNCEOFFOTHERS | OAT_FIREIMMUNITY ; Object $70 - OBJ_BUZZYBEATLE
 
00411. .byte OAT_BOUNDBOX01 | OAT_BOUNCEOFFOTHERS ; Object $71 - OBJ_SPINY
 
00412. .byte OAT_BOUNDBOX01 | OAT_BOUNCEOFFOTHERS ; Object $72 - OBJ_GOOMBA
 
00413. .byte OAT_BOUNDBOX01 ; Object $73 - OBJ_PARAGOOMBA
 
00414. .byte OAT_BOUNDBOX01 ; Object $74 - OBJ_PARAGOOMBAWITHMICROS
 
00415. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $75 - OBJ_BOSSATTACK
 
00416. .byte OAT_BOUNDBOX01 ; Object $76 - OBJ_JUMPINGCHEEPCHEEP
 
00417. .byte OAT_BOUNDBOX01 ; Object $77 - OBJ_GREENCHEEP
 
00418. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY ; Object $78 - OBJ_BULLETBILL
 
00419. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY ; Object $79 - OBJ_BULLETBILLHOMING
 
00420. .byte OAT_BOUNDBOX13 | OAT_BOUNCEOFFOTHERS ; Object $7A - OBJ_BIGGREENTROOPA
 
00421. .byte OAT_BOUNDBOX13 | OAT_BOUNCEOFFOTHERS ; Object $7B - OBJ_BIGREDTROOPA
 
00422. .byte OAT_BOUNDBOX13 | OAT_BOUNCEOFFOTHERS ; Object $7C - OBJ_BIGGOOMBA
 
00423. .byte OAT_BOUNDBOX13 ; Object $7D - OBJ_BIGGREENPIRANHA
 
00424. .byte OAT_BOUNDBOX13 | OAT_BOUNCEOFFOTHERS ; Object $7E - OBJ_BIGGREENHOPPER
 
00425. .byte OAT_BOUNDBOX13 ; Object $7F - OBJ_BIGREDPIRANHA
 
00426. .byte OAT_BOUNDBOX01 | OAT_BOUNCEOFFOTHERS ; Object $80 - OBJ_FLYINGGREENPARATROOPA
 
00427. .byte OAT_BOUNDBOX02 ; Object $81 - OBJ_HAMMERBRO
 
00428. .byte OAT_BOUNDBOX02 ; Object $82 - OBJ_BOOMERANGBRO
 
00429. .byte OAT_BOUNDBOX01 ; Object $83 - OBJ_LAKITU
 
00430. .byte OAT_BOUNDBOX01 ; Object $84 - OBJ_SPINYEGG
 
00431. .byte OAT_BOUNDBOX01 | OAT_BOUNCEOFFOTHERS ; Object $85 - OBJ_SPINYEGGDUD
 
00432. .byte OAT_BOUNDBOX13 ; Object $86 - OBJ_HEAVYBRO
 
00433. .byte OAT_BOUNDBOX02 ; Object $87 - OBJ_FIREBRO
 
00434. .byte OAT_BOUNDBOX01 ; Object $88 - OBJ_ORANGECHEEP
 
00435. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY ; Object $89 - OBJ_CHAINCHOMP
 
00436. .byte OAT_BOUNDBOX13 | OAT_FIREIMMUNITY ; Object $8A - OBJ_THWOMP
 
00437. .byte OAT_BOUNDBOX13 | OAT_FIREIMMUNITY ; Object $8B - OBJ_THWOMPLEFTSLIDE
 
00438. .byte OAT_BOUNDBOX13 | OAT_FIREIMMUNITY ; Object $8C - OBJ_THWOMPRIGHTSLIDE
 
00439. .byte OAT_BOUNDBOX13 | OAT_FIREIMMUNITY ; Object $8D - OBJ_THWOMPUPDOWN
 
00440. .byte OAT_BOUNDBOX13 | OAT_FIREIMMUNITY ; Object $8E - OBJ_THWOMPDIAGONALUL
 
00441. .byte OAT_BOUNDBOX13 | OAT_FIREIMMUNITY ; Object $8F - OBJ_THWOMPDIAGONALDL
 
00442. .byte OAT_BOUNDBOX01 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $90 - OBJ_TILTINGPLATFORM
 
00443. .byte OAT_BOUNDBOX01 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $91 - OBJ_TWIRLINGPLATCWNS
 
00444. .byte OAT_BOUNDBOX01 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $92 - OBJ_TWIRLINGPLATCW
 
00445. .byte OAT_BOUNDBOX01 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $93 - OBJ_TWIRLINGPERIODIC
 
00446. .byte OAT_BOUNDBOX06 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $94 - OBJ_BIGQBLOCK_3UP
 
00447. .byte OAT_BOUNDBOX06 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $95 - OBJ_BIGQBLOCK_MUSHROOM
 
00448. .byte OAT_BOUNDBOX06 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $96 - OBJ_BIGQBLOCK_FIREFLOWER
 
00449. .byte OAT_BOUNDBOX06 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $97 - OBJ_BIGQBLOCK_SUPERLEAF
 
00450. .byte OAT_BOUNDBOX06 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $98 - OBJ_BIGQBLOCK_TANOOKI
 
00451. .byte OAT_BOUNDBOX06 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $99 - OBJ_BIGQBLOCK_FROG
 
00452. .byte OAT_BOUNDBOX06 | OAT_FIREIMMUNITY | OAT_HITNOTKILL ; Object $9A - OBJ_BIGQBLOCK_HAMMER
 
00453. .byte OAT_BOUNDBOX00 ; Object $9B
 
00454. .byte OAT_BOUNDBOX00 ; Object $9C
 
00455. .byte OAT_BOUNDBOX14 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $9D - OBJ_FIREJET_UPWARD
 
00456. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY ; Object $9E - OBJ_PODOBOO
 
00457. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY ; Object $9F - OBJ_PARABEETLE
 
00458. .byte OAT_BOUNDBOX02 ; Object $A0 - OBJ_GREENPIRANHA
 
00459. .byte OAT_BOUNDBOX02 ; Object $A1 - OBJ_GREENPIRANHA_FLIPPED
 
00460. .byte OAT_BOUNDBOX10 ; Object $A2 - OBJ_REDPIRANHA
 
00461. .byte OAT_BOUNDBOX10 ; Object $A3 - OBJ_REDPIRANHA_FLIPPED
 
00462. .byte OAT_BOUNDBOX02 ; Object $A4 - OBJ_GREENPIRANHA_FIRE
 
00463. .byte OAT_BOUNDBOX02 ; Object $A5 - OBJ_GREENPIRANHA_FIREC
 
00464. .byte OAT_BOUNDBOX10 ; Object $A6 - OBJ_VENUSFIRETRAP
 
00465. .byte OAT_BOUNDBOX10 ; Object $A7 - OBJ_VENUSFIRETRAP_CEIL
 
00466. .byte OAT_BOUNDBOX11 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $A8 - OBJ_UPARROW
 
00467. .byte OAT_BOUNDBOX11 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $A9 - OBJ_MANYARROW
 
00468. .byte OAT_BOUNDBOX00 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $AA - OBJ_AIRSHIPPROP
 
00469. .byte OAT_BOUNDBOX00 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $AB
 
00470. .byte OAT_BOUNDBOX15 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $AC - OBJ_FIREJET_LEFT
 
00471. .byte OAT_BOUNDBOX12 ; Object $AD - OBJ_ROCKYWRENCH
 
00472. .byte OAT_BOUNDBOX11 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $AE - OBJ_BOLTLIFT
 
00473. .byte OAT_BOUNDBOX01 | OAT_FIREIMMUNITY ; Object $AF - OBJ_ENEMYSUN
 
00474. .byte OAT_BOUNDBOX13 | OAT_FIREIMMUNITY ; Object $B0 - OBJ_BIGCANNONBALL
 
00475. .byte OAT_BOUNDBOX15 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $B1 - OBJ_FIREJET_RIGHT
 
00476. .byte OAT_BOUNDBOX14 | OAT_WEAPONIMMUNITY | OAT_HITNOTKILL ; Object $B2 - OBJ_FIREJET_UPSIDEDOWN
 
00477. .byte OAT_BOUNDBOX01 ; Object $B3
 
00478.  
00479. ; Brick by tileset; anyone use this?
 
00480. ; $C3A8
 
00481. .byte TILEA_BRICK ; 0 Plains style
 
00482. .byte TILEA_BRICK ; 1 Mini Fortress style
 
00483. .byte TILEA_BRICK ; 2 Hills style
 
00484. .byte TILEA_BRICK ; 3 High-Up style
 
00485. .byte TILEA_BRICK ; 4 pipe world plant infestation
 
00486. .byte TILEA_BRICK ; 5 water world
 
00487. .byte TILEA_BRICK ; 6 Toad House
 
00488. .byte TILEA_BRICK ; 7 Vertical pipe maze
 
00489. .byte TILEA_BRICK ; 8 desert levels
 
00490. .byte TILEA_BRICK ; 9 Airship
 
00491. .byte TILEA_BRICK ; 10 Giant World
 
00492. .byte TILEA_BRICK ; 11 Ice level
 
00493. .byte TILEA_BRICK ; 12 Sky level
 
00494. .byte TILEA_BRICK ; 13 Underground
 
00495.  
00496. ; Index by Level_TilesetIdx
 
00497. ; Enables spike tiles where available (this tile and tile before it)
 
00498. SpikesEnable:
 
00499. .byte $FF ; 0 Plains style
 
00500. .byte TILE2_SPIKEDOWN ; 1 Mini Fortress style
 
00501. .byte $FF ; 2 Hills style
 
00502. .byte $FF ; 3 High-Up style
 
00503. .byte $FF ; 4 pipe world plant infestation
 
00504. .byte $FF ; 5 water world
 
00505. .byte $FF ; 6 Toad House
 
00506. .byte TILE8_SPIKE_UP ; 7 Vertical pipe maze
 
00507. .byte TILE9_SPIKEUP ; 8 desert levels
 
00508. .byte $FF ; 9 Airship
 
00509. .byte $FF ; 10 Giant World
 
00510. .byte $FF ; 11 Ice level
 
00511. .byte $FF ; 12 Sky level
 
00512. .byte $FF ; 13 Underground
 
00513.  
00514. ; Index by Level_TilesetIdx
 
00515. ; Enables conveyor tiles where available (this tile and tile before it)
 
00516. ConveyorEnable:
 
00517. .byte $00 ; 0 Plains style
 
00518. .byte TILE2_CONVEYORR ; 1 Mini Fortress style
 
00519. .byte $00 ; 2 Hills style
 
00520. .byte TILE2_CONVEYORR ; 3 High-Up style
 
00521. .byte TILE2_CONVEYORR ; 4 pipe world plant infestation
 
00522. .byte $00 ; 5 water world
 
00523. .byte $00 ; 6 Toad House
 
00524. .byte $00 ; 7 Vertical pipe maze
 
00525. .byte $00 ; 8 desert levels
 
00526. .byte $00 ; 9 Airship
 
00527. .byte $00 ; 10 Giant World
 
00528. .byte $00 ; 11 Ice level
 
00529. .byte $00 ; 12 Sky level
 
00530. .byte $00 ; 13 Underground
 
00531.  
00532. ; Index by Level_TilesetIdx
 
00533. ; Sets the tile which is a pain in the ass (typically muncher, sometimes jelectro)
 
00534. ; Although TILEA_MUNCHER is always considered anyway for Kuribo's shoe...
 
00535. ; (see after PRG008_BD96) which is probably a bug/mistake! (Although to their
 
00536. ; credit, you can never normally have Kuribo's shoe in a Jelectro level)
 
00537. MuncherJelectroSet:
 
00538. .byte TILEA_MUNCHER ; 0 Plains style
 
00539. .byte TILEA_MUNCHER ; 1 Mini Fortress style
 
00540. .byte TILEA_MUNCHER ; 2 Hills style
 
00541. .byte TILEA_MUNCHER ; 3 High-Up style
 
00542. .byte TILEA_MUNCHER ; 4 pipe world plant infestation
 
00543. .byte TILE4_JELECTRO ; 5 water world
 
00544. .byte TILEA_MUNCHER ; 6 Toad House
 
00545. .byte TILEA_MUNCHER ; 7 Vertical pipe maze
 
00546. .byte TILEA_MUNCHER ; 8 desert levels
 
00547. .byte TILEA_MUNCHER ; 9 Airship
 
00548. .byte TILEA_MUNCHER ; 10 Giant World
 
00549. .byte TILE4_JELECTRO ; 11 Ice level
 
00550. .byte TILEA_MUNCHER ; 12 Sky level
 
00551. .byte TILEA_MUNCHER ; 13 Underground
 
00552.  
00553.  
00554. ; This table grants a couple (dis)abilities to certain
 
00555. ; power-ups; specifically:
 
00556. ; Bit 0 (1) = Able to fly and flutter (Raccoon tail wagging)
 
00557. ; Bit 1 (2) = NOT able to slide on slopes
 
00558. PowerUp_Ability:
 
00559. ; Small, Big, Fire, Leaf, Frog, Tanooki, Hammer
 
00560. .byte $00, $00, $00, $01, $02, $01, $02
 
00561.  
00562. ; Velocities set to X/Y directly to Player for what might be a now-unused debug routine of sorts
 
00563. PRG000_C3E7:
 
00564. .byte $00, $30, -$30
 
00565.  
00566. ; FIXME: Anybody want to claim this?
 
00567. ; Looks like maybe a leftover debug routine for some kind of "float around" mode maybe!!
 
00568. ; $C3EA
 
00569. LDA <Pad_Holding
 
00570. AND #(PAD_LEFT | PAD_RIGHT)
 
00571. TAY ; Y = 1 or 2
 
00572.  
00573. ; Set Player X velocity directly??
 
00574. LDA PRG000_C3E7,Y
 
00575. STA <Player_XVel
 
00576.  
00577. LDA <Pad_Holding
 
00578. LSR A
 
00579. LSR A
 
00580. AND #((PAD_UP | PAD_DOWN) >> 2)
 
00581. TAY ; Y = 1 or 2
 
00582.  
00583. ; Set Player Y velocity directly??
 
00584. LDA PRG000_C3E7,Y
 
00585. STA <Player_YVel
 
00586.  
00587. RTS ; Return
 
00588.  
00589. ; Offsets into Sprite_RAM used by objects
 
00590. SprRamOffsets:
 
00591. ; The specified Sprite_RAM offset is calculated by object's index
 
00592. ; added to Counter_7to0 (i.e. a value 0 to 7) so as to evenly
 
00593. ; distribute the drawing of objects over available sprites and
 
00594. ; help cope with the sprites-per-scanline drawing limits.
 
00595. ;
 
00596. ; Basically, on different frames, different objects will have
 
00597. ; different sprite priority, so while there may be flicker, at
 
00598. ; least everything is somewhat visible
 
00599. .byte $40, $E8, $58, $D0, $70, $B8, $88, $A0, $40, $E8, $58, $D0, $70, $B8, $88
 
00600.  
00601.  
00602. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
00603. ; DoTimeBonus
 
00604. ;
 
00605. ; Converts your time remaining to score bonus, but only if there
 
00606. ; is no BGM playing! Also resets 'X' to object slot index.
 
00607. ; "BEQ" branches after this function if the clock is at 000.
 
00608. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
00609. TimeBonus_Score:
 
00610. .byte 50, 5 ; 500 and 50
 
00611.  
00612. ; $C412
 
00613. DoTimeBonus:
 
00614. LDA SndCur_Music1
 
00615. BNE PRG000_C446 ; If any music playing, jump to PRG000_C446 (RTS)
 
00616.  
00617. LDY #$01 ; Y = 1 (most significant or middle digit of time is non-zero)
 
00618.  
00619. LDA Level_TimerMSD
 
00620. ORA Level_TimerMid
 
00621. BNE PRG000_C422 ; If most significant or middle digit of time is non-zero, jump to PRG000_C422
 
00622.  
00623. INY ; Y = 2 (most significant and middle digit of time are zero)
 
00624.  
00625. PRG000_C422:
 
00626. ORA Level_TimerLSD
 
00627. BEQ PRG000_C446 ; If all time digits are zero, jump to PRG000_C446 (RTS)
 
00628.  
00629. TYA ; A = Y
 
00630. TAX ; X = A = 1 or 2
 
00631.  
00632. LDA (TimeBonus_Score - 1),X ; Get appropriate score bonus
 
00633. STA Score_Earned ; Push into score buffer
 
00634.  
00635. PRG000_C42F:
 
00636. DEC Level_TimerMSD,X ; Decrement off middle or least significant digit
 
00637. BPL PRG000_C43C ; If digit is >= 0, jump to PRG000_C43C
 
00638.  
00639. LDA #$09
 
00640. STA Level_TimerMSD,X ; Otherwise, reload it with 9
 
00641.  
00642. DEX ; X--
 
00643. BPL PRG000_C42F ; While X >= 0, loop!
 
00644.  
00645. PRG000_C43C:
 
00646. LDX <SlotIndexBackup ; Restore 'X' as object slot index
 
00647.  
00648. ; Play tick sound
 
00649. LDA Sound_QLevel1
 
00650. ORA #SND_LEVELBLIP
 
00651. STA Sound_QLevel1
 
00652.  
00653. PRG000_C446:
 
00654. RTS ; Return
 
00655.  
00656.  
00657. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
00658. ; SpecialObj_FindEmptyAbort
 
00659. ; SpecialObj_FindEmptyAbortY
 
00660. ;
 
00661. ; Finds an empty special object slot (returned in 'Y') or "aborts"
 
00662. ; if no slot is open OR if the object has any horizontal sprite visibility
 
00663. ; "abort" = will not return to caller...
 
00664. ;
 
00665. ; SpecialObj_FindEmptyAbortY just allows a specified range
 
00666. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
00667. ; $C447
 
00668. SpecialObj_FindEmptyAbort:
 
00669. LDY #$05
 
00670. SpecialObj_FindEmptyAbortY:
 
00671. LDA SpecialObj_ID,Y
 
00672. BEQ PRG000_C454 ; If object slot is dead/empty, jump to PRG000_C454
 
00673. DEY ; Y--
 
00674. BPL SpecialObj_FindEmptyAbortY ; While Y >= 0, loop!
 
00675.  
00676. PRG000_C451:
 
00677. ; Do not return to caller!!
 
00678. PLA
 
00679. PLA
 
00680. RTS
 
00681.  
00682. PRG000_C454:
 
00683. JSR Object_AnySprOffscreen
 
00684.  
00685. BNE PRG000_C451 ; If any sprites are off-screen, jump to PRG000_C451
 
00686.  
00687. RTS ; Return
 
00688.  
00689.  
00690. ; Goes into Score_Get100PlusPts, but object index is stored in 'Y'
 
00691. ; NOTE: Overwrites 'X' anyway, so be careful!
 
00692. Score_Get100PlusPtsY:
 
00693. PHA ; Save 'A'
 
00694. TYA
 
00695. TAX ; 'X' = 'Y'
 
00696. PLA ; Restore 'A'
 
00697.  
00698. ; Get at least 100 pts based on value in 'A'
 
00699. Score_Get100PlusPts:
 
00700. ADD #$05 ; Base at 100 points
 
00701. JSR Score_PopUp
 
00702. LDX <SlotIndexBackup ; X = object slot index
 
00703. RTS ; Return
 
00704.  
00705.  
00706. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
00707. ; Score_PopUp
 
00708. ;
 
00709. ; Pops up a score value (e.g. from a killed enemy)
 
00710. ;
 
00711. ; A = score value
 
00712. ; X = index of on-screen object
 
00713. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
00714. Score_PopUp:
 
00715. ; $C467
 
00716. PHA ; Save input value
 
00717. STY <Temp_Var15 ; Backup 'Y' -> Temp_Var15
 
00718.  
00719. JSR Score_FindFreeSlot ; Get free Scores_Value slot
 
00720. PLA ; Restore input value
 
00721. STA Scores_Value,Y ; Store input value
 
00722.  
00723. LDA Objects_SpriteY,X
 
00724. SUB #16
 
00725. CMP #192
 
00726. BLT PRG000_C47D ; If (sprite's Y - 16) < 192, jump to PRG000_C47D
 
00727.  
00728. LDA #$05 ; A = 5
 
00729.  
00730. PRG000_C47D:
 
00731. STA Scores_Y,Y ; Set score Y
 
00732.  
00733. ; Set score X to spawning object
 
00734. LDA Objects_SpriteX,X
 
00735. STA Scores_X,Y
 
00736.  
00737. ; Set score counter to $30
 
00738. LDA #$30
 
00739. STA Scores_Counter,Y
 
00740.  
00741. LDY <Temp_Var15 ; Restore 'Y'
 
00742.  
00743. RTS ; Return
 
00744.  
00745.  
00746. ; Find a free slot to display the score in
 
00747. Score_FindFreeSlot:
 
00748. LDY #$04 ; Y = 4
 
00749. PRG000_C490:
 
00750. LDA Scores_Value,Y
 
00751. BEQ PRG000_C49A ; If Scores_Value[Y] = 0, jump to PRG000_C49A (RTS)
 
00752.  
00753. DEY ; Y--
 
00754. BPL PRG000_C490 ; While Y >= 0, loop
 
00755.  
00756. LDY #$04 ; Y = 4
 
00757.  
00758. PRG000_C49A:
 
00759. RTS ; Return
 
00760.  
00761. PRG000_C49B:
 
00762.  
00763. ; Common init point for "power up" coins (coins that emerge from bricks and blocks)
 
00764.  
00765. ; Temp_Var1 = Y Lo
 
00766. ; Temp_Var2 = X lo
 
00767.  
00768. LDY #$03 ; Y = 3
 
00769.  
00770. PRG000_C49D:
 
00771. LDA CoinPUp_State,Y
 
00772. BEQ PRG000_C4A7 ; If this coin slot state = 0, it's free, go use it!
 
00773. DEY ; Y--
 
00774. BPL PRG000_C49D ; While Y >= 0, loop!
 
00775.  
00776. ; If all else fails, just overwrite the oldest slot!
 
00777. LDY #$03 ; Y = 3
 
00778.  
00779. PRG000_C4A7:
 
00780.  
00781. ; Play coin sound
 
00782. LDA Sound_QLevel1
 
00783. ORA #SND_LEVELCOIN
 
00784. STA Sound_QLevel1
 
00785.  
00786. LDA #$01
 
00787. STA CoinPUp_State,Y ; Set coin state to 1
 
00788.  
00789. LDA <Temp_Var1 ; Get input Y
 
00790. SUB Level_VertScroll ; Make relative to vertical scroll
 
00791. SBC #24 ; Subtract 24
 
00792. STA CoinPUp_Y,Y ; Store as coin's Y
 
00793.  
00794. LDA <Temp_Var2 ; Get input X
 
00795. SUB <Horz_Scroll ; Make relative to horizontal scroll
 
00796. STA CoinPUp_X,Y ; Store as coin's X
 
00797.  
00798. LDA #-5
 
00799. STA CoinPUp_YVel,Y ; Set Y Vel = -5
 
00800.  
00801. LDA #$01
 
00802. STA CoinPUp_Counter,Y ; Set counter to 1
 
00803.  
00804. RTS ; Return
 
00805.  
00806.  
00807. Conveyor_CarryX: .byte -$01, $01 ; Left, Right
 
00808. Conveyor_CarryXHi: .byte $FF, $00 ; 16-bit sign extension
 
00809.  
00810. ; Checks for and handles object touching conveyor belt by carrying object
 
00811. ; $C4D6
 
00812. Object_HandleConveyorCarry:
 
00813. LDA <Objects_DetStat,X
 
00814. AND #$03
 
00815. BNE PRG000_C4F5 ; If object has hit a wall, jump to PRG000_C4F5 (RTS)
 
00816.  
00817. LDA Object_TileFeet2
 
00818. SUB #TILE2_CONVEYORL
 
00819. CMP #$02
 
00820. BGE PRG000_C4F5 ; If object is not standing on a conveyor belt, jump to PRG000_C4F5 (RTS)
 
00821.  
00822. TAY ; Conveyor tile relative index -> 'Y'
 
00823.  
00824. LDA <Objects_X,X
 
00825. ADC Conveyor_CarryX,Y
 
00826. STA <Objects_X,X
 
00827.  
00828. LDA <Objects_XHi,X
 
00829. ADC Conveyor_CarryXHi,Y
 
00830. STA <Objects_XHi,X
 
00831.  
00832. PRG000_C4F5:
 
00833. RTS ; Return
 
00834.  
00835.  
00836. ; Checks for and handles object touching conveyor belt, storing result into LRBounce_Vel
 
00837. ; $CF46
 
00838. Object_HandleConveyorBounceVel:
 
00839. LDA Level_PSwitchCnt
 
00840. BNE PRG000_C4F5 ; If P-Switch is active, jump to PRG000_C4F5
 
00841.  
00842. LDA Object_TileFeet2
 
00843. SUB #TILE2_CONVEYORL
 
00844. CMP #$02
 
00845. BGE PRG000_C4F5 ; If object is not standing on a conveyor belt, jump to PRG000_C4F5 (RTS)
 
00846.  
00847. TAY ; Conveyor tile relative index -> 'Y'
 
00848.  
00849. LDA Conveyor_CarryX,Y
 
00850.  
00851. LDY #-$01 ; Y = -$01
 
00852.  
00853. EOR <Objects_XVel,X ; Check if object is not going with conveyor
 
00854. BMI PRG000_C511 ; If the signs differ (going against conveyor), jump to PRG000_C511
 
00855.  
00856. LDY #$01 ; Y = $01
 
00857.  
00858. PRG000_C511:
 
00859. STY LRBounce_Vel ; -> LRBounce_Vel
 
00860.  
00861. RTS ; Return
 
00862.  
00863.  
00864. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
00865. ; Object_HitGround
 
00866. ;
 
00867. ; When object hits the ground, this aligns it properly to a tile
 
00868. ;
 
00869. ; X = index of on-screen object
 
00870. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
00871. ; $C515
 
00872. Object_HitGround:
 
00873. LDA <Objects_DetStat,X
 
00874. BPL PRG000_C533 ; If object is NOT touching the "32 pixel partition" floor, jump to PRG000_C533
 
00875.  
00876. ; Object is touching the "32 pixel partition" floor...
 
00877.  
00878. LDA <Objects_Y,X
 
00879. SUB Level_VertScroll
 
00880. AND #$f0
 
00881. ADD #$01
 
00882. ADD Level_VertScroll
 
00883. STA <Objects_Y,X ; Aligns to grid and adds 1
 
00884.  
00885. LDA #$00
 
00886. ADC #$00
 
00887. STA <Objects_YHi,X ; Apply carry
 
00888.  
00889. JMP PRG000_C53D ; Jump to PRG000_C53D
 
00890.  
00891. PRG000_C533:
 
00892. LDA <Objects_Y,X
 
00893. AND #$f0
 
00894. ADD Object_SlopeHeight
 
00895. STA <Objects_Y,X ; Align to tile and apply slope
 
00896.  
00897. PRG000_C53D:
 
00898. LDA #$00
 
00899. STA <Objects_YVel,X ; Halt vertical movement
 
00900.  
00901. RTS ; Return
 
00902.  
00903.  
00904. ; The only difference amongst the Object_WorldDetect[x] entries
 
00905. ; are the input value, which specifies the limit that an object
 
00906. ; should acknowledge a floor tile. E.g., Object_WorldDetect4
 
00907. ; means the object will not detect a floor if it is more than
 
00908. ; 4 pixels vertically down in to it. "N1" (Negative one) is
 
00909. ; thus basically to never use that limit because the object
 
00910. ; can't be at a depth of "-1 pixels into the tile"
 
00911.  
00912. ; $C542
 
00913. Object_WorldDetectN1:
 
00914. LDA #$ff ; Use A = $FF
 
00915. BNE PRG000_C54C ; Jump (technically always) to PRG000_C54C
 
00916.  
00917. ; $C546
 
00918. Object_WorldDetect8:
 
00919. LDA #$08 ; Use A = 8
 
00920. BNE PRG000_C54C ; Jump (technically always) to PRG000_C54C
 
00921.  
00922. ; $C54A
 
00923. Object_WorldDetect4:
 
00924. LDA #$04 ; Use A = 4
 
00925.  
00926. PRG000_C54C:
 
00927. PHA ; Save input value (not used until PRG000_C649)
 
00928.  
00929. CPX #$05
 
00930. BNE PRG000_C559 ; If object slot is NOT 5, jump to PRG000_C559
 
00931.  
00932. LDA ObjSplash_DisTimer,X
 
00933. BEQ PRG000_C559 ; If ObjSplash_DisTimer = 0, jump to PRG000_C559
 
00934.  
00935. DEC ObjSplash_DisTimer,X ; ObjSplash_DisTimer --
 
00936.  
00937. PRG000_C559:
 
00938. LDA <Objects_DetStat,X
 
00939. STA Temp_VarNP0 ; Object's detection status -> Temp_VarNP0
 
00940.  
00941. LDA #$00
 
00942. STA <Objects_DetStat,X ; Clear Object's detection status
 
00943. STA Object_SlopeHeight ; Clear Object's slope height
 
00944. STA LRBounce_Vel ; Clear left/right bounce power
 
00945.  
00946. JSR Object_GetAttrAndMoveTiles ; Fill in values for Object_TileFeet/Quad and Object_TileWall/Quad
 
00947.  
00948. PLA ; Restore input value
 
00949. STA <Temp_Var1 ; Store into Temp_Var1
 
00950.  
00951. LDY Object_AttrWall ; Y = detected quadrant of potential wall tile
 
00952. LDA Object_TileWall ; A = detected tile index
 
00953. CMP Tile_AttrTable+4,Y
 
00954. BLT PRG000_C584 ; If the tile's index < the beginning wall/ceiling solid tile for this quad, jump to PRG000_C584
 
00955.  
00956. ; Object is touching solid wall tile
 
00957.  
00958. LDA #$01 ; A = 1
 
00959.  
00960. LDY <Objects_XVel,X
 
00961. BPL PRG000_C580 ; If object's X velocity >= 0 (still or moving rightward), jump to PRG000_C580
 
00962.  
00963. ; Negative X vel...
 
00964. ASL A ; A = 2
 
00965.  
00966. PRG000_C580:
 
00967. ORA <Objects_DetStat,X ; Set bit 0 or 1
 
00968. STA <Objects_DetStat,X ; Update Objects_DetStat
 
00969.  
00970. PRG000_C584:
 
00971. LDY Object_AttrFeet ; Y = detected quadrant of tile
 
00972.  
00973. LDA <Objects_YVel,X
 
00974. BPL PRG000_C5A9 ; If object's Y velocity >= 0 (still or moving downward), jump to PRG000_C5A9
 
00975.  
00976. ; Object moving upwards... (ceiling detection)
 
00977.  
00978. LDA Level_SlopeEn
 
00979. BEQ PRG000_C59A ; If slopes are not enabled here, jump to PRG000_C59A
 
00980.  
00981. ; Slope detection (not specific)
 
00982.
 
00983. LDA Object_TileFeet
 
00984. CMP Tile_AttrTable,Y
 
00985. BLT PRG000_C5A8 ; If tile is not within range of tiles solid at ceiling, jump to PRG000_C5A8 (RTS)
 
00986. BGE PRG000_C5A2 ; Otherwise, jump to PRG000_C5A2
 
00987.  
00988. PRG000_C59A:
 
00989.  
00990. ; Non-slope detection
 
00991.  
00992. LDA Object_TileFeet
 
00993. CMP Tile_AttrTable+4,Y
 
00994. BLT PRG000_C5A8 ; If tile is not within range of tiles solid at ceiling, jump to PRG000_C5A8 (RTS)
 
00995.  
00996. PRG000_C5A2:
 
00997. ; Flag ceiling impact
 
00998. LDA <Objects_DetStat,X
 
00999. ORA #$08
 
01000. STA <Objects_DetStat,X
 
01001.  
01002. PRG000_C5A8:
 
01003. RTS ; Return
 
01004.  
01005. PRG000_C5A9:
 
01006.  
01007. ; Object moving downwards (floor detection)
 
01008.  
01009. LDA Object_TileFeet
 
01010. CMP Tile_AttrTable,Y
 
01011. BGE PRG000_C5B4 ; If tile is within range of the starting solid tile, jump to PRG000_C5B4
 
01012. JMP PRG000_C65D ; Otherwise, jump to PRG000_C65D
 
01013.  
01014. PRG000_C5B4:
 
01015. LDY Level_SlopeEn
 
01016. BNE PRG000_C5BC ; If slopes are enabled, jump to PRG000_C5BC
 
01017. JMP PRG000_C649 ; Jump to PRG000_C649
 
01018.  
01019. PRG000_C5BC:
 
01020.  
01021. ; Slopes...
 
01022.  
01023. ; Any of the following tiles, jump to PRG000_C67F
 
01024. CMP #TILE3_VERTGROUNDL
 
01025. BEQ PRG000_C5D0
 
01026.  
01027. CMP #TILE3_VERTGROUNDR
 
01028. BEQ PRG000_C5D0
 
01029.  
01030. CMP #TILE14_ABOVE_MIDGROUND
 
01031. BEQ PRG000_C5D0
 
01032.  
01033. CMP #TILE3_MIDGROUND
 
01034. BEQ PRG000_C5D0
 
01035.  
01036. CMP #TILE3_WMIDGROUND
 
01037. BNE PRG000_C5D3
 
01038.  
01039. PRG000_C5D0:
 
01040. JMP PRG000_C67F ; Jump to PRG000_C67F
 
01041.  
01042. PRG000_C5D3:
 
01043.  
01044. ; Slopes enabled, not touching one of the flat solids
 
01045.  
01046. LDA <Objects_Y,X
 
01047. AND #$0f
 
01048. STA <Temp_Var1 ; Temp_Var1 = object's tile-relative vertical position
 
01049.  
01050. LDA <Temp_Var16 ; Temp_Var16 right now is ObjTile_DetXLo
 
01051. AND #$0f
 
01052. STA <Temp_Var16 ; Temp_Var16 = object's tile-relative horizontal position
 
01053.  
01054. LDY Level_Tile_Slope ; Y = object's detected slope
 
01055. LDA Slope_ObjectVel_Effect,Y ; Get value by slope
 
01056. CMP #$80
 
01057. BNE PRG000_C5EC ; If value <> $80, jump to PRG000_C5EC
 
01058. JMP PRG000_C65D ; Otherwise, jump to PRG000_C65D
 
01059.  
01060. PRG000_C5EC:
 
01061. ; Slope response
 
01062.  
01063. ; Calculate the offset into Slope_LUT
 
01064. ; NOTE: This fails to accomodate slope shape index values of $10+...
 
01065. ; The most significant bit will be lost due to the 8-bit register!
 
01066. ; But those are ceiling slopes which enemies generally don't care about
 
01067. ; (Not even the upside-down Buzzy / Spiny enemies have proper ceiling slope coding!!)
 
01068. TYA
 
01069. ASL A
 
01070. ASL A
 
01071. ASL A
 
01072. ASL A ; A = slope value << 4 (16 bytes per slope "shape" index)
 
01073. ADD <Temp_Var16 ; Add the tile-relative horizontal position (offset to pixel specific height on this slope)
 
01074. TAY ; -> 'Y'
 
01075.  
01076. LDA Slope_LUT,Y
 
01077. AND #$0f
 
01078. STA <Temp_Var2 ; Lower 4 bits of slope (the "floor" slope height) -> Temp_Var2
 
01079.  
01080. LDA <Temp_Var1
 
01081. CMP #12
 
01082. BGE PRG000_C606 ; If object's tile-relative Y position >= 12, jump to PRG000_C606
 
01083.  
01084.  
01085. CMP <Temp_Var2
 
01086. BLT PRG000_C65D ; If object's tile-relative Y position < calculated slope height, jump to PRG000_C65D
 
01087.  
01088. PRG000_C606:
 
01089. LDA <Temp_Var2
 
01090. STA Object_SlopeHeight ; Store Object_SlopeHeight
 
01091.  
01092. ; Set "hit ground" flag
 
01093. LDA <Objects_DetStat,X
 
01094. ORA #$04
 
01095. STA <Objects_DetStat,X
 
01096.  
01097. LDY Level_Tile_Slope ; Y = object's detected slope
 
01098.  
01099. LDA <Objects_XVel,X
 
01100. LSR A
 
01101. LSR A
 
01102. LSR A
 
01103. LSR A ; A = "whole" part of Object's X Velocity
 
01104. BNE PRG000_C61E ; If not zero, jump to PRG000_C61E
 
01105.  
01106. LDA #$01 ; Otherwise, use A = 1
 
01107.  
01108. PRG000_C61E:
 
01109. CMP #$08
 
01110. BLT PRG000_C624 ; If object's X velocity < 8, jump to PRG000_C624
 
01111.  
01112. ORA #$f0 ; Sign extend
 
01113.  
01114. PRG000_C624:
 
01115. LDX Slope_ObjectVel_Effect,Y ; X = value from Slope_ObjectVel_Effect
 
01116. CPX #$00
 
01117. BNE PRG000_C62E ; If value <> 0, jump to PRG000_C62E
 
01118.  
01119. ; Otherwise...
 
01120. LDX #$00 ; X = 0
 
01121. TXA ; A = 0
 
01122.  
01123. PRG000_C62E:
 
01124. CPX #$00
 
01125. BPL PRG000_C635 ; If X is not negative, jump to PRG000_C635
 
01126.  
01127. JSR Negate ; Otherwise, negate (absolute value)
 
01128.  
01129. PRG000_C635:
 
01130. STX <Temp_Var1 ; -> Temp_Var1
 
01131.  
01132. LDX <SlotIndexBackup ; X = object slot index
 
01133. STA Objects_Slope,X ; Absolute value slope
 
01134.  
01135. LDA <Temp_Var1 ; A = value from Slope_ObjectVel_Effect
 
01136.  
01137. LDY <Objects_XVel,X
 
01138. BPL PRG000_C645 ; If X Velocity >= 0, jump to PRG000_C645
 
01139.  
01140. ; X velocity < 0 ...
 
01141. JSR Negate ; Negate value
 
01142.  
01143. PRG000_C645:
 
01144. STA LRBounce_Vel ; Store the "power" of the left/right bouncer
 
01145.  
01146. RTS ; Return
 
01147.  
01148.  
01149. PRG000_C649:
 
01150. LDA Player_PartDetEn
 
01151. BNE PRG000_C656 ; If Player_PartDetEn is set (the object hit the visual ground), jump to PRG000_C656
 
01152.  
01153. ; The original input value finally winds up here. This limits when an object will actually
 
01154. ; acknowledge "hitting ground." Basically, if the object is more than [input value] pixels
 
01155. ; down in to the tile, it will not count as having hit the floor.
 
01156.  
01157. LDA <Objects_Y,X
 
01158. AND #$0f ; Object's tile-relative vertical position
 
01159. CMP <Temp_Var1
 
01160. BGE PRG000_C65C ; If object is too far down in to the tile, jump to PRG000_C65C (RTS)
 
01161.  
01162. PRG000_C656:
 
01163.  
01164. ; Flag object as "hit ground"
 
01165. LDA <Objects_DetStat,X
 
01166. ORA #$04
 
01167. STA <Objects_DetStat,X
 
01168.  
01169. PRG000_C65C:
 
01170. RTS ; Return
 
01171.  
01172.  
01173. PRG000_C65D:
 
01174. LDA Level_SlopeEn
 
01175. BEQ PRG000_C67E ; If slopes are not enabled in this level, jump to PRG000_C67E
 
01176.  
01177. ; This is a correction applied for when an enemy steps over the edge of a slope:
 
01178. ; ___
 
01179. ; / \ <-- like when he walks across the top, down the side
 
01180. ; Helps keep the enemy following the curve downward, especially enemies like red
 
01181. ; shell koopa troopas that otherwise turn away at an edge...
 
01182.  
01183. LDY #$00 ; Y = 0
 
01184.  
01185. LDA Objects_Slope,X
 
01186. BEQ PRG000_C67E ; If slope value = 0, jump to PRG000_C67E
 
01187. BPL PRG000_C66C ; If slope is positive, jump to PRG000_C66C
 
01188.  
01189. DEY ; Otherwise, Y = $FF
 
01190.  
01191. PRG000_C66C:
 
01192. ADD <Objects_Y,X
 
01193. STA <Objects_Y,X ; Update Y
 
01194.  
01195. TYA ; A = $00/$FF, sign extension
 
01196.  
01197. ADC <Objects_YHi,X
 
01198. STA <Objects_YHi,X ; Apply to Y Hi
 
01199.  
01200. LDA #$00
 
01201. STA Objects_Slope,X ; Clear slope value
 
01202.  
01203. JMP Object_WorldDetectN1 ; Jump to Object_WorldDetectN1
 
01204.  
01205. PRG000_C67E:
 
01206. RTS ; Return
 
01207.  
01208. PRG000_C67F:
 
01209.  
01210. ; Flat ground tiles in a sloped world
 
01211.  
01212. LDA Objects_State,X
 
01213. CMP #OBJSTATE_KILLED
 
01214. BEQ PRG000_C69C ; If object is killed, jump to PRG000_C69C (RTS)
 
01215.  
01216. CMP #OBJSTATE_HELD
 
01217. BEQ PRG000_C69C ; If object is being held, jump to PRG000_C69C (RTS)
 
01218.  
01219. LDA <Objects_Y,X
 
01220. AND #$f0
 
01221. SUB #$01
 
01222. STA <Objects_Y,X ; Align object to one pixel above the tile
 
01223.  
01224. LDA <Objects_YHi,X
 
01225. SBC #$00
 
01226. STA <Objects_YHi,X ; Set the Y Hi
 
01227.  
01228. JMP Object_WorldDetectN1 ; Jump to Object_WorldDetectN1
 
01229.  
01230. PRG000_C69C:
 
01231. RTS ; Return
 
01232.  
01233.  
01234. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
01235. ; Object_GetAttrAndMoveTiles
 
01236. ;
 
01237. ; Gets tiles for an object based on its attribute settings and
 
01238. ; current state of movement. Handles entering/leaving water.
 
01239. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
01240. Object_GetAttrAndMoveTiles:
 
01241. LDY #(OTDO_Water - Object_TileDetectOffsets) ; Special offsets used for checking for water tiles
 
01242. JSR Object_DetectTile ; Get tile here
 
01243.  
01244. ASL A
 
01245. ROL A
 
01246. ROL A ; Upper 2 bits shift right 6, effectively
 
01247. AND #%00000011 ; Keep these bits, i.e. "tile quadrant"
 
01248. STA <Temp_Var1 ; -> Temp_Var1
 
01249. TAY ; -> 'Y'
 
01250.  
01251. LDA <Level_Tile
 
01252. CMP Tile_AttrTable,Y
 
01253. BGE PRG000_C6FD ; If this tile >= this attribute tile, jump to PRG000_C6FD (may be solid)
 
01254.  
01255. LDX #$00 ; X = 0 (object is NOT underwater)
 
01256.  
01257. ; If this tile is TILEA_PSWITCH_PRESSED, TILE1_WFALLTOP, or PRG000_C6D0, jump to PRG000_C6D0
 
01258. ; Object's apparently aren't in-water in a waterfall?
 
01259. CMP #TILEA_PSWITCH_PRESSED
 
01260. BEQ PRG000_C6D0
 
01261. CMP #TILE1_WFALLTOP
 
01262. BEQ PRG000_C6D0
 
01263. CMP #TILE1_WFALLMID
 
01264. BEQ PRG000_C6D0
 
01265.  
01266. LDA Level_TilesetIdx
 
01267. ASL A
 
01268. ASL A ; Offset to beginning of underwater-by-quad table
 
01269. ADD <Temp_Var1 ; Add quadrant offset
 
01270. TAY ; -> 'Y'
 
01271. LDA Level_MinTileUWByQuad,Y ; Get the starting underwater tile
 
01272. CMP <Level_Tile
 
01273. BGE PRG000_C6D0 ; If starting underwater tile is >= the detected tile, jump to PRG000_C6D0
 
01274.  
01275. INX ; X = 1 (object is underwater)
 
01276.  
01277. PRG000_C6D0:
 
01278. TXA ; X -> A
 
01279.  
01280. LDX <SlotIndexBackup ; Restore 'X' as object slot index
 
01281.  
01282. CMP Objects_InWater,X
 
01283. BEQ PRG000_C6FA ; If object is either still in water / out of water (hasn't changed), jump to PRG000_C6FA
 
01284.  
01285. PHA ; Save underwater flag
 
01286.  
01287. LDA <Level_Tile ; A = tile index
 
01288. LDY <Temp_Var1 ; Y = tile quadrant
 
01289. CMP Tile_AttrTable,Y
 
01290.  
01291. PLA ; Restore underwater flag
 
01292.  
01293. BGE PRG000_C6FA ; If tile index >= the attribute tile, solid tile, jump to PRG000_C6FA
 
01294.  
01295. PHA ; Save underwater flag
 
01296.  
01297. LDA Objects_LastTile,X
 
01298. PHA ; Save Objects_LastTile
 
01299.  
01300. ASL A
 
01301. ROL A
 
01302. ROL A ; Upper 2 bits shift right 6, effectively
 
01303. AND #%00000011 ; Keep these bits, i.e. "tile quadrant"
 
01304. TAY ; Y = quadrant of last detected tile
 
01305.  
01306. PLA ; Restore the last detected tile
 
01307.  
01308. CMP Tile_AttrTable,Y
 
01309.  
01310. PLA ; Restore the underwater flag
 
01311.  
01312. BGE PRG000_C6FA ; If last detected tile >= the starting underwater tile, jump to PRG000_C6FA
 
01313.  
01314. PHA ; Save underwater flag
 
01315.  
01316. JSR Object_WaterSplash ; Hit water; splash!
 
01317.  
01318. PLA ; Restore underwater flag
 
01319.  
01320. PRG000_C6FA:
 
01321. STA Objects_InWater,X ; Set object's in-water flag
 
01322.  
01323. PRG000_C6FD:
 
01324. LDA <Level_Tile
 
01325. STA Objects_LastTile,X ; Set last tile this object detected
 
01326.  
01327. LDY ObjGroupRel_Idx ; Y = object's group-relative index
 
01328.  
01329. LDA ObjectGroup_Attributes2,Y ; Get attributes set 2 for this object
 
01330. AND #OA2_TDOGRPMASK
 
01331. LSR A ; Upper 4 bits of attributes set 2 shifted right 1 (value * 8)
 
01332. PHA ; Save it
 
01333. TAY ; -> 'Y' (use respective Object_TileDetectOffsets group Row 1)
 
01334.  
01335. LDA <Objects_YVel,X
 
01336. BPL PRG000_C713 ; If object Y velocity is >= 0 (stopped or moving downward), jump to PRG000_C713
 
01337.  
01338. INY
 
01339. INY ; If object moving upward, Y += 2 (use respective Object_TileDetectOffsets group Row 2)
 
01340.  
01341. PRG000_C713:
 
01342. JSR Object_DetectTile ; Get tile
 
01343.  
01344. ; Store into tile index holders
 
01345. STA Object_TileFeet2
 
01346. STA Object_TileFeet
 
01347.  
01348. PHA ; Save tile
 
01349.  
01350. LDA Level_TilesetIdx
 
01351. CMP #$02
 
01352. BNE PRG000_C736 ; If Level_TilesetIdx <> 2 (not a Hills style level), jump to PRG000_C736
 
01353.  
01354. ; If enemy is touching quicksand, jump to PRG000_C72E; otherwise, jump to PRG000_C736
 
01355. LDA <Level_Tile
 
01356. CMP #TILE3_QUICKSAND_TOP
 
01357. BEQ PRG000_C72E
 
01358. CMP #TILE3_QUICKSAND_MID
 
01359. BNE PRG000_C736
 
01360.  
01361. PRG000_C72E:
 
01362. INC Objects_QSandCtr,X ; Increment the quicksand counter
 
01363.  
01364. LDA #OBJSTATE_KILLED
 
01365. STA Objects_State,X ; killed by quicksand
 
01366.  
01367. PRG000_C736:
 
01368. PLA ; Restore tile
 
01369.  
01370. ASL A
 
01371. ROL A
 
01372. ROL A ; Upper 2 bits shift right 6, effectively
 
01373. AND #%00000011 ; Keep these bits, i.e. "tile quadrant"
 
01374. STA Object_AttrFeet ; Store quadrant value
 
01375. TAY ; -> 'Y'
 
01376.  
01377. LDA ObjTile_DetXLo
 
01378. STA <Temp_Var16 ; Temp_Var16 = ObjTile_DetXLo
 
01379.  
01380. LDA Level_SlopeEn
 
01381. BEQ PRG000_C76C ; If slopes are not enabled here, jump to PRG000_C76C
 
01382.  
01383. LDA <Level_Tile
 
01384. CMP Tile_AttrTable,Y
 
01385. BLT PRG000_C76C ; If detected tile < starting solidity tile, jump to PRG000_C76C
 
01386.  
01387. PHA ; Save tile
 
01388.  
01389. TYA ; Quadrant value -> 'A'
 
01390. ASL A ; Shifted left 1 (2 byte index)
 
01391. TAX ; -> 'X'
 
01392.  
01393. ; Temp_Var3/4 point to array of slope values for this quadrant
 
01394. LDA Level_SlopeSetByQuad,X
 
01395. STA <Temp_Var3
 
01396. LDA Level_SlopeSetByQuad+1,X
 
01397. STA <Temp_Var4
 
01398.  
01399. PLA ; Restore tile
 
01400.  
01401. SUB Tile_AttrTable,Y ; Subtract the root tile value
 
01402. TAY ; -> 'Y'
 
01403. LDA [Temp_Var3],Y ; Get slope value
 
01404. STA Level_Tile_Slope ; -> Level_Tile_Slope
 
01405.  
01406. LDX <SlotIndexBackup ; Restore X as object slot index
 
01407.  
01408. PRG000_C76C:
 
01409. LDA #$00
 
01410. STA Object_TileWall2 ; Object_TileWall2 = 0
 
01411.  
01412. PLA ; Restore Object_TileDetectOffsets index
 
01413.  
01414. CMP #(OTDO_G1R1 - Object_TileDetectOffsets)
 
01415. BNE PRG000_C78C ; If not using Group 1 Row 1, jump to PRG000_C78C
 
01416.  
01417. LDY Level_SlopeEn
 
01418. BEQ PRG000_C78C ; If slopes are not enabled, jump to PRG000_C78C
 
01419.  
01420. ;;;;;;;;;;;;;;;;;; ONLY HAPPENS WITH GROUP 1 ROW 1 AND SLOPES ENABLED
 
01421.  
01422. PHA ; Save Object_TileDetectOffsets index
 
01423.  
01424. LDA Temp_VarNP0 ; Retrieve object's in-air status
 
01425. AND #$04 ; Bit 2 is set to indicate object is "on solid ground"
 
01426. TAY ; -> 'Y' (0 or 4)
 
01427.  
01428. PLA ; Restore Object_TileDetectOffsets index
 
01429.  
01430. CPY #$00
 
01431. BEQ PRG000_C78C ; If Y = 0 (object not on solid ground), jump to PRG000_C78C
 
01432.  
01433. LDY #(OTDO_G1Alt - Object_TileDetectOffsets) ; Otherwise, use alternate wall detection offsets
 
01434. JMP PRG000_C791 ; Jump to PRG000_C791
 
01435.  
01436. ;;;;;;;;;;;;;;;;;; END
 
01437.  
01438. PRG000_C78C:
 
01439. TAY ; Object_TileDetectOffsets index -> 'Y'
 
01440.  
01441. INY
 
01442. INY
 
01443. INY
 
01444. INY ; Y += 4 (move down two Rows in Object_TileDetectOffsets)
 
01445.  
01446. PRG000_C791:
 
01447. LDA <Objects_XVel,X
 
01448. BMI PRG000_C797 ; If object's X velocity < 0 (moving leftward), jump to PRG000_C797
 
01449.  
01450. INY
 
01451. INY ; Y += 2 (move down one Rows in Object_TileDetectOffsets)
 
01452.  
01453. PRG000_C797:
 
01454. JSR Object_DetectTile ; Get tile here
 
01455.  
01456. ; Store into tile index holders
 
01457. STA Object_TileWall2
 
01458. STA Object_TileWall
 
01459.  
01460. ASL A
 
01461. ROL A
 
01462. ROL A ; Upper 2 bits shift right 6, effectively
 
01463. AND #%00000011 ; Keep these bits, i.e. "tile quadrant"
 
01464. STA Object_AttrWall ; Store quadrant value
 
01465.  
01466. RTS ; Return
 
01467.  
01468.  
01469.  
01470.  
01471. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
01472. ; Object_DetectTile
 
01473. ;
 
01474. ; Gets tile based on offset of object; the offset is set by the
 
01475. ; 'Y' register which indexes Object_TileDetectOffsets for the
 
01476. ; Y/X offset pair. Seems kind of a limited way to go, but hey..
 
01477. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
01478. ; $C7A9
 
01479. Object_DetectTile:
 
01480. LDA Level_7Vertical
 
01481. BEQ PRG000_C7B1 ; If level is NOT vertical, jump to PRG000_C7B1
 
01482.  
01483. JMP PRG000_C85C ; Jump to PRG000_C85C
 
01484.  
01485. PRG000_C7B1:
 
01486. LDA Player_PartDetEn
 
01487. BEQ PRG000_C7D9 ; If Player_PartDetEn is not set, jump to PRG000_C7D9
 
01488.  
01489. ; The 32 pixel partition floor is enabled
 
01490. ; Any object Y >= 160 must detect the bottom two tile rows instead!
 
01491.  
01492. LDA <Objects_Y,X
 
01493. ADD Object_TileDetectOffsets,Y ; Adding tile detection offset to Object's Y
 
01494. SUB Level_VertScroll ; Make relative to scroll
 
01495. CMP #160
 
01496. BLT PRG000_C7D9 ; If Y < 160, jump to PRG000_C7D9
 
01497.  
01498. ; Object is low enough to the visual floor...
 
01499.  
01500. SBC #16 ; Subtract 16
 
01501. AND #$f0 ; Align to grid
 
01502. STA ObjTile_DetYLo ; -> ObjTile_DetYLo
 
01503.  
01504. ; Flag object as touching "32 pixel partition" floor
 
01505. LDA <Objects_DetStat,X
 
01506. ORA #$80
 
01507. STA <Objects_DetStat,X
 
01508.  
01509. LDA #$01
 
01510. STA ObjTile_DetYHi ; ObjTile_DetYHi = 1
 
01511.  
01512. JMP PRG000_C7F1 ; Jump to PRG000_C7F1
 
01513.  
01514. PRG000_C7D9:
 
01515. LDA <Objects_Y,X
 
01516. ADD Object_TileDetectOffsets,Y ; Adding tile detection Y offset to Object's Y
 
01517. AND #$f0 ; Align to grid
 
01518. STA ObjTile_DetYLo ; -> ObjTile_DetYLo (low)
 
01519.  
01520. LDA <Objects_YHi,X
 
01521. ADC #$00 ; Apply carry
 
01522. STA ObjTile_DetYHi ; -> ObjTile_DetYHi (high)
 
01523.  
01524. BEQ PRG000_C7FA ; If no carry, jump to PRG000_C7FA
 
01525.  
01526. ; In a non-vertical level, a high value of 2 or greater is way beyond the bottom
 
01527. CMP #$02
 
01528. BGE PRG000_C832 ; If the Y Hi >= 2, jump to PRG000_C832
 
01529.  
01530. PRG000_C7F1:
 
01531. PHA ; Save high part
 
01532.  
01533. LDA ObjTile_DetYLo
 
01534. CMP #$b0
 
01535.  
01536. PLA ; Restore high part
 
01537.  
01538. BGE PRG000_C832 ; If the Y lo part is greater than $B0 (the bottom of the screen), jump to PRG000_C832
 
01539.  
01540. PRG000_C7FA:
 
01541. AND #$01
 
01542. STA <Temp_Var3 ; Temp_Var3 = 0 or 1, depending if Y lo is on odd line or not
 
01543.  
01544. LDA <Objects_X,X
 
01545. ADC Object_TileDetectOffsets+1,Y ; Adding tile detection X offset to Object's X
 
01546. STA ObjTile_DetXLo ; -> ObjTile_DetXLo (low)
 
01547.  
01548. LDA <Objects_XHi,X
 
01549. ADC #$00 ; Apply carry
 
01550. STA ObjTile_DetXHi ; -> ObjTile_DetXHi (high)
 
01551.  
01552. CMP #$10
 
01553. BGE PRG000_C832 ; If the high part is more than $10 (biggest possible within other limits), jump to PRG000_C832
 
01554.  
01555. ASL A ; Change high part into 2 byte index to select the screen
 
01556. TAY ; -> 'Y'
 
01557.  
01558. ; Calculate Temp_Var2/1 (tile address)
 
01559. LDA Tile_Mem_Addr,Y
 
01560. STA <Temp_Var1
 
01561. LDA Tile_Mem_Addr+1,Y
 
01562. ADC <Temp_Var3
 
01563. STA <Temp_Var2
 
01564.  
01565. ; Calculate tile offset within screen
 
01566. LDA ObjTile_DetXLo
 
01567. LSR A
 
01568. LSR A
 
01569. LSR A
 
01570. LSR A
 
01571. ORA ObjTile_DetYLo
 
01572.  
01573. TAY ; -> 'Y'
 
01574.  
01575. PRG000_C82A:
 
01576. LDA [Temp_Var1],Y ; Get tile
 
01577.  
01578. JSR PSwitch_SubstTileAndAttr ; Substitute tile if P-Switch is active
 
01579.  
01580. JMP PRG000_C834 ; Jump to PRG000_C834
 
01581.  
01582. PRG000_C832:
 
01583. LDA #$00 ; No tile detected
 
01584.  
01585. PRG000_C834:
 
01586. STA <Level_Tile ; Store tile index detected
 
01587.  
01588. RTS ; Return
 
01589.  
01590.  
01591. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
01592. ; PSwitch_SubstTileAndAttr
 
01593. ;
 
01594. ; P-Switch substitution function for tiles which it effects
 
01595. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
01596. ; Parallel arrays which for a given tile in the accumulator,
 
01597. ; if it matches one of the ones in PrePSwitchTile is replaced
 
01598. ; with the attribute and tile from the other arrays...
 
01599. PrePSwitchTile: .byte $40, $67, $66, $05
 
01600. PostPSwitchTile: .byte $67, $40, $40, $40
 
01601. PostPSwitchAttr: .byte $03, $00, $00, $00
 
01602.  
01603. PSwitch_SubstTileAndAttr:
 
01604. LDY Level_PSwitchCnt ; Y = Level_PSwitchCnt
 
01605. BEQ PRG000_C85B ; If P-Switch not active, jump to PRG000_C85B (RTS)
 
01606.  
01607. LDY #(PostPSwitchTile - PrePSwitchTile - 1)
 
01608. PRG000_C84A:
 
01609. CMP PrePSwitchTile,Y
 
01610. BNE PRG000_C858 ; If this is not a match, jump to PRG000_C858
 
01611.  
01612. LDA PostPSwitchAttr,Y ; Get replacement attribute
 
01613. STA <Player_Slopes ; Store into Player_Slopes
 
01614.  
01615. LDA PostPSwitchTile,Y ; Get replacement tile
 
01616. RTS ; Return
 
01617.  
01618. PRG000_C858:
 
01619. DEY ; Y--
 
01620. BPL PRG000_C84A ; While Y >= 0, loop!
 
01621.  
01622. PRG000_C85B:
 
01623. RTS ; Return
 
01624.  
01625.  
01626. PRG000_C85C:
 
01627.  
01628. ; Vertical level object detect tile
 
01629.  
01630. LDA <Objects_Y,X
 
01631. ADD Object_TileDetectOffsets,Y ; Adding tile detection Y offset to Object's Y
 
01632. AND #$f0 ; Align to grid
 
01633. STA ObjTile_DetYLo ; -> ObjTile_DetYLo (low)
 
01634. STA <Temp_Var3 ; -> Temp_Var3
 
01635.  
01636. LDA <Objects_YHi,X
 
01637. ADC #$00 ; Apply carry
 
01638. STA ObjTile_DetYHi ; -> ObjTile_DetYHi (high)
 
01639.  
01640. CMP #$10
 
01641. BGE PRG000_C832 ; If object is detecting way too low (out of range), jump to PRG000_C832 (no tile detected)
 
01642.  
01643. ADC #$60 ; +$60
 
01644. STA <Temp_Var2 ; -> Temp_Var2
 
01645.  
01646. ; ObjTile_DetXHi = Objects_XHi (should be zero)
 
01647. LDA <Objects_XHi,X
 
01648. STA ObjTile_DetXHi
 
01649.  
01650. LDA <Objects_X,X
 
01651. ADD Object_TileDetectOffsets+1,Y ; Adding tile detection X offset to Object's X
 
01652. STA ObjTile_DetXLo ; -> ObjTile_DetXLo (low)
 
01653.  
01654. ; Calculate tile offset within screen
 
01655. LSR A
 
01656. LSR A
 
01657. LSR A
 
01658. LSR A
 
01659. ORA <Temp_Var3
 
01660. STA <Temp_Var1 ; -> Temp_Var1
 
01661.  
01662. LDY #$00 ; Y = 0 (additional offset not used)
 
01663.  
01664. JMP PRG000_C82A ; Jump to PRG000_C82A
 
01665.  
01666. ; FIXME: Anybody want to claim this?
 
01667. ; $C893
 
01668. .byte $FC, $04, $01, $02
 
01669.  
01670.  
01671. ; When Object hits water, splash!
 
01672. Object_WaterSplash:
 
01673. LDA #$02
 
01674.  
01675. Podoboo_Splash:
 
01676. STA <Temp_Var1 ; Temp_Var1 = 2
 
01677.  
01678. LDA ObjSplash_DisTimer,X
 
01679. BNE PRG000_C914 ; If splashes are disabled, jump to PRG000_C914 (RTS)
 
01680.  
01681. LDA Level_ObjectID,X
 
01682. CMP #OBJ_GROWINGVINE
 
01683. BEQ PRG000_C914 ; If object is a growing vine, jump to PRG000_C914 (RTS)
 
01684.  
01685. LDA <Objects_YVel,X
 
01686. BMI PRG000_C8BE ; If Object's Y velocity is negative (moving upward), jump to PRG000_C8BE
 
01687.  
01688. ; If object is some kind of blooper, jump to PRG000_C914 (RTS)
 
01689. LDA Level_ObjectID,X
 
01690. CMP #OBJ_BLOOPER
 
01691. BEQ PRG000_C914
 
01692. CMP #OBJ_BLOOPERCHILDSHOOT
 
01693. BEQ PRG000_C914
 
01694. CMP #OBJ_BLOOPERWITHKIDS
 
01695. BEQ PRG000_C914
 
01696.  
01697. LDA #$00
 
01698. STA <Objects_YVel,X ; Object's Y velocity is zeroed at impact of water
 
01699.  
01700. PRG000_C8BE:
 
01701.  
01702. ; Basically looking not to do a splash effect if object is falling off-screen
 
01703.  
01704. JSR Object_AnySprOffscreen
 
01705. BNE PRG000_C914 ; If any sprites are off-screen, jump to PRG000_C914 (RTS)
 
01706.  
01707. LDY #$02 ; Y = 2 (this is immediately overwritten and thus not used)
 
01708.  
01709. ; Alternate between splash slot 1 and 2
 
01710. INC Object_SplashAlt ; Object_SplashAlt++
 
01711. LDA Object_SplashAlt
 
01712. AND #$01 ; Keep just bit 0
 
01713. TAY ; -> 'Y'
 
01714.  
01715. INY ; Y = 1 or 2
 
01716.  
01717. LDA #$01
 
01718. STA Splash_Counter,Y ; Splash counter = 1 (begin splash)
 
01719.  
01720. LSR A
 
01721. STA Splash_NoScrollY,Y ; Splash_NoScrollY = 0 (splash is relative to vertical scroll)
 
01722.  
01723. ; Set appropriate splash Y
 
01724. LDA <Objects_Y,X
 
01725. SUB #$04
 
01726. AND #$f0
 
01727. ADD <Temp_Var1
 
01728. STA Splash_Y,Y
 
01729.  
01730. ; Set appropriate splash X
 
01731. LDA <Objects_X,X
 
01732. STA Splash_X,Y
 
01733.  
01734. LDA <Objects_YVel,X
 
01735. BMI PRG000_C914 ; If object's Y velocity is negative (moving upwards), jump to PRG000_C914 (RTS)
 
01736.  
01737. ; NOTE: The following is probably old debug code; it basically catches the coordinates
 
01738. ; of the very first splash any object makes... and then will never update again because
 
01739. ; nothing clears the WatrHit_IsSetFlag value... may also be an unused feature where an
 
01740. ; object could respond somehow to having splashed down?
 
01741.  
01742. LDA WatrHit_IsSetFlag
 
01743. BNE PRG000_C914 ; If WatrHit_IsSetFlag is set, jump to PRG000_C914 (RTS)
 
01744.  
01745. LDA #$80
 
01746. STA WatrHit_IsSetFlag ; WatrHit_IsSetFlag = $80
 
01747.  
01748. ; Store Object_WatrHit vars
 
01749. LDA <Objects_Y,X
 
01750. ADC #$06
 
01751. STA Object_WatrHitY
 
01752.  
01753. LDA <Objects_YHi,X
 
01754. ADC #$00
 
01755. STA Object_WatrHitYHi
 
01756.  
01757. LDA <Objects_X,X
 
01758. ADC #$04
 
01759. STA Object_WatrHitX
 
01760.  
01761. LDA <Objects_XHi,X
 
01762. ADC #$00
 
01763. STA Object_WatrHitXHi
 
01764.  
01765. PRG000_C914:
 
01766. RTS ; Return
 
01767.  
01768. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
01769. ; Objects_HandleScrollAndUpdate
 
01770. ;
 
01771. ; THE function which spawns objects as they appear on screen and
 
01772. ; calls updates on all objects based on their state etc. Also
 
01773. ; updates the timers.
 
01774. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
01775. Objects_HandleScrollAndUpdate:
 
01776. JMP PRG000_C927 ; Jump to PRG000_C927
 
01777.  
01778. PRG000_C918:
 
01779. .byte $35, $F0, $0C
 
01780.  
01781. ; FIXME: Anybody want to claim this?
 
01782. ; Appears to be a debug routine that would toggle the Player to be invincible by pressing SELECT
 
01783. ; $C91B
 
01784. LDA <Pad_Input
 
01785. AND #PAD_SELECT
 
01786. BEQ PRG000_C927 ; If Player is NOT pressing SELECT, jump to PRG000_C927
 
01787.  
01788. ; Toggle invincibility flag
 
01789. EOR Player_DebugNoHitFlag
 
01790. STA Player_DebugNoHitFlag
 
01791.  
01792. PRG000_C927:
 
01793. LDA Splash_DisTimer
 
01794. BEQ PRG000_C92F ; If Splash_DisTimer > 0, jump to PRG000_C92F
 
01795.  
01796. DEC Splash_DisTimer ; Splash_DisTimer--
 
01797.  
01798. PRG000_C92F:
 
01799. LDA <Player_Suit
 
01800. CMP #PLAYERSUIT_HAMMER
 
01801. BNE PRG000_C93A ; If Player suit is NOT hammer suit, jump to PRG000_C93A
 
01802.  
01803. ; Otherwise...
 
01804. LDA #$4f
 
01805. STA PatTable_BankSel+5 ; Sixth pattern table bank = $4F
 
01806.  
01807. PRG000_C93A:
 
01808. LDA <Player_IsDying
 
01809. CMP #$03
 
01810. BNE PRG000_C948 ; If Player is NOT dying due to TIME UP, jump to PRG000_C948
 
01811.  
01812. ; Otherwise...
 
01813. LDA PatTable_BankSel+2
 
01814. CMP #$52
 
01815. BNE PRG000_C948 ; If third pattern table bank has not been set to $52, jump to PRG000_C948
 
01816. RTS ; Return
 
01817.  
01818. PRG000_C948:
 
01819. LDA Player_IsHolding
 
01820. STA Player_ISHolding_OLD ; Player_ISHolding_OLD = Player_ISHolding
 
01821.  
01822. LDA #$00
 
01823. STA Player_IsHolding ; Clear Player_IsHolding
 
01824. STA ArrowPlat_IsActive ; Clear ArrowPlat_IsActive
 
01825.  
01826. LDA #$ff
 
01827. STA LRBounce_Y ; LRBounce_Y = $FF
 
01828.  
01829. ; Set page @ A000 to 5
 
01830. LDA #$05
 
01831. STA PAGE_A000
 
01832. JSR PRGROM_Change_A000
 
01833.  
01834. JSR LevelEvent_Do ; Perform event as set by Level_Event
 
01835. JSR Level_SpawnObjsAndBounce ; Handle if Player bounced off block and spawn new objects as screen scrolls
 
01836.  
01837. DEC Counter_7to0 ; Counter_7to0--
 
01838. BPL PRG000_C973 ; If Counter_7to0 >= 0, jump to PRG000_C973
 
01839.  
01840. LDA #$07
 
01841. STA Counter_7to0 ; Otherwise, reset Counter_7to0 to 7
 
01842.  
01843. PRG000_C973:
 
01844. LDX #$07
 
01845.  
01846. PRG000_C975:
 
01847. STX <SlotIndexBackup ; Backup current object index -> SlotIndexBackup
 
01848.  
01849. LDA <Player_HaltGame
 
01850. BNE PRG000_C9B6 ; If gameplay is halted, jump to PRG000_C9B6
 
01851.  
01852. LDA Objects_Timer,X
 
01853. BEQ PRG000_C983 ; If this timer is already at zero, jump to PRG000_C983
 
01854.  
01855. DEC Objects_Timer,X ; Otherwise, decrement it
 
01856.  
01857. PRG000_C983:
 
01858.  
01859. LDA Objects_Timer2,X
 
01860. BEQ PRG000_C98B ; If this timer is already at zero, jump to PRG000_C98B
 
01861.  
01862. DEC Objects_Timer2,X ; Otherwise, decrement it
 
01863.  
01864. PRG000_C98B:
 
01865.  
01866. CPX #$05
 
01867. BGE PRG000_C9B6 ; If object slot index >= 5, jump to PRG000_C9B6
 
01868.  
01869. ; Non-special objects in slots 0 to 4...
 
01870.  
01871. LDA Objects_Timer4,X
 
01872. BEQ PRG000_C997 ; If this timer is already at zero, jump to PRG000_C997
 
01873.  
01874. DEC Objects_Timer4,X ; Otherwise, decrement it
 
01875.  
01876. PRG000_C997:
 
01877. LDA Objects_Timer3,X
 
01878. BEQ PRG000_C9B6 ; If timer is zero, jump to PRG000_C9B6
 
01879.  
01880. CMP #$60
 
01881. BLT PRG000_C9B3 ; If timer value is < $60, jump to PRG000_C9B3
 
01882.  
01883. LDA #$01 ; A = 1
 
01884.  
01885. LDY Objects_State,X
 
01886. CPY #OBJSTATE_NORMAL
 
01887. BEQ PRG000_C9B3 ; If object's state is Normal, jump to PRG000_C9B3
 
01888.  
01889. CPY #$04
 
01890. BNE PRG000_C9AF ; If object's state is NOT 4 (being held), jump to PRG000_C9AF
 
01891.  
01892. ; Object being held...
 
01893.  
01894. LDA #$03 ; A = 3
 
01895. PRG000_C9AF:
 
01896. AND <Counter_1
 
01897. BNE PRG000_C9B6 ; Every A:A+1 ticks, jump to PRG000_C9B6
 
01898.  
01899. PRG000_C9B3:
 
01900. DEC Objects_Timer3,X ; Every 4 ticks, decrement Objects_Timer3
 
01901.  
01902. PRG000_C9B6:
 
01903. TXA ; Object index -> 'A'
 
01904. ADD Counter_7to0 ; Add current value of Counter_7to0
 
01905. TAY ; -> 'Y' (anywhere from 0 to 14)
 
01906.  
01907. LDA SprRamOffsets,Y
 
01908. STA Object_SprRAM,X ; Store this object's Sprite_RAM offset
 
01909.  
01910. JSR Object_DoStateAction ; Do whatever's required by this object by its current state
 
01911. JSR Object_HitByTailOrBouncer ; Test and respond if object was hit by Player tail attack or left/right bouncer
 
01912.  
01913. LDA Objects_State,X
 
01914. BNE PRG000_C9D2 ; If object's state is not 0 (dead/empty), jump to PRG000_C9D2
 
01915.  
01916. ; Remove object's associated spawn index
 
01917. LDA #$ff
 
01918. STA Objects_SpawnIdx,X
 
01919.  
01920. PRG000_C9D2:
 
01921. DEX ; X--
 
01922. BPL PRG000_C975 ; While X >= 0, loop!
 
01923.  
01924. LDA Cine_ToadKing
 
01925. BEQ PRG000_C9E5 ; If Toad & King Cinematic is NOT going on, jump to PRG000_C9E5
 
01926.  
01927. ; Set page @ A000 to 24
 
01928. LDA #24
 
01929. STA PAGE_A000
 
01930. JSR PRGROM_Change_A000
 
01931.  
01932. JSR Cinematic_ToadAndKing ; Do the Toad & King Cinematic logic
 
01933.  
01934. PRG000_C9E5:
 
01935. LDA Player_Flip
 
01936. BEQ PRG000_C9FB ; If Player is NOT somersaulting, jump to PRG000_C9FB
 
01937.  
01938. LDA Player_InWater
 
01939. ORA Player_SandSink
 
01940. BNE PRG000_C9F6 ; If Player is in water or sinking in sand, jump to PRG000_C9F6
 
01941.  
01942. LDA <Player_InAir
 
01943. BNE PRG000_C9FB ; If Player is mid-air, jump to PRG000_C9FB
 
01944.  
01945. PRG000_C9F6:
 
01946. ; A would-be somersaulting Player is either in water or sand,
 
01947. ; or is not mid-air; disable it!
 
01948. LDA #$00
 
01949. STA Player_Flip
 
01950.  
01951. PRG000_C9FB:
 
01952. LDA Level_ChgTileEvent
 
01953. BNE PRG000_CA33 ; If a change tile event is called for, jump to PRG000_CA33
 
01954.  
01955. ; Check each block bump slot to see if it needs to occur
 
01956. LDY #$00
 
01957. LDA Level_BlkBump,Y
 
01958. BNE PRG000_CA13
 
01959.  
01960. INY
 
01961. LDA Level_BlkBump,Y
 
01962. BNE PRG000_CA13
 
01963.  
01964. INY
 
01965. LDA Level_BlkBump,Y
 
01966. BEQ PRG000_CA33
 
01967.  
01968. PRG000_CA13:
 
01969. STA Level_ChgTileEvent ; Set the block bump change event
 
01970.  
01971. ; Set relevant parameters
 
01972. LDA Level_BlkBump_XHi,Y
 
01973. STA Level_BlockChgXHi
 
01974.  
01975. LDA Level_BlkBump_XLo,Y
 
01976. STA Level_BlockChgXLo
 
01977.  
01978. LDA Level_BlkBump_YHi,Y
 
01979. STA Level_BlockChgYHi
 
01980.  
01981. LDA Level_BlkBump_YLo,Y
 
01982. STA Level_BlockChgYLo
 
01983.  
01984. ; Clear this block bump!
 
01985. LDA #$00
 
01986. STA Level_BlkBump,Y
 
01987.  
01988. PRG000_CA33:
 
01989. LDA Level_JctCtl
 
01990. BEQ PRG000_CA40 ; If no level junction is occurring, jump to PRG000_CA40
 
01991.  
01992. STA LevelPartialInit ; Flag that we need a level partial initialization
 
01993.  
01994. ; Clear the "Get Wand" cinematic state
 
01995. LDA #$00
 
01996. STA Level_GetWandState
 
01997.  
01998. PRG000_CA40:
 
01999. RTS ; Return
 
02000.  
02001. ; Breaks up every 36 object IDs to make smaller jump tables
 
02002. ObjectID_BaseVals:
 
02003. .byte $00, $24, $48, $6C, $90
 
02004.  
02005.  
02006. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
02007. ; Object_DoStateAction
 
02008. ;
 
02009. ; Do whatever is required by the current Objects_State value
 
02010. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
02011. Object_DoStateAction:
 
02012. LDA Objects_State,X
 
02013. BEQ PRG000_CA40 ; If this object is "dead/empty", jump to PRG000_CA40
 
02014.  
02015. CMP #$08
 
02016. BEQ PRG000_CA81 ; If this object's state = 8 ("Poof" Dying), jump to PRG000_CA81
 
02017.  
02018. LDY #$04 ; Y = 4
 
02019.  
02020. ; Try to locate the group that this object ID belongs to
 
02021. ; Groups are defined by ObjectID_BaseVals, every 36 values.
 
02022. PRG000_CA51:
 
02023. LDA Level_ObjectID,X ; Get object ID
 
02024. CMP ObjectID_BaseVals,Y ; Compare to this base value
 
02025. BGE PRG000_CA5C ; If this object ID >= the base value, jump to PRG000_CA5C
 
02026.  
02027. ; Object ID is smaller, thus not this group...
 
02028.  
02029. DEY ; Y--
 
02030. BNE PRG000_CA51 ; If Y > 0, loop!
 
02031.  
02032. PRG000_CA5C:
 
02033.  
02034. ; Y contains index to the base value for this group of object IDs
 
02035. ; A contains the object's ID
 
02036.  
02037. INY ; Y++
 
02038. SUB ObjectID_BaseVals-1,Y ; Subtract next group's ID to make this object's ID relative to group
 
02039.  
02040. STA ObjGroupRel_Idx ; Set ObjGroupRel_Idx to this group-relative index value
 
02041.  
02042. ; Y is now a value of 1 to 5, and that value dictates the page
 
02043. ; where this object's code can be found...
 
02044. STY PAGE_A000 ; Set new page
 
02045. TAY ; Object group-relative index -> 'Y'
 
02046.
 
02047. JSR PRGROM_Change_A000 ; Set page @ A000 to appropriate object page...
 
02048.  
02049. LDA Objects_DisPatChng,X
 
02050. BNE PRG000_CA81 ; If pattern bank enforcement is disabled, jump to PRG000_CA81
 
02051.  
02052. ; Object's can request a particular pattern set to be available to them.
 
02053. ; They may set either the fifth or sixth bank of CHRROM, which is specified
 
02054. ; by bit 7.
 
02055.  
02056. LDX #$00 ; X = 0 (fifth CHRROM bank)
 
02057. LDA ObjectGroup_PatTableSel,Y ; Load CHRROM bank request for this object, if any
 
02058. BEQ PRG000_CA7F ; If CHRROM bank request is zero, no change, jump to PRG000_CA7F
 
02059. BPL PRG000_CA7A ; If CHRROM bank request does not have bit 7 set, jump to PRG000_CA7A
 
02060. INX ; Otherwise, X = 1 (sixth CHRROM bank)
 
02061.  
02062. PRG000_CA7A:
 
02063. AND #$7f ; Bit 7 is used to specify which bank, so filter it here
 
02064. STA PatTable_BankSel+4,X ; Store pattern bank
 
02065.  
02066. PRG000_CA7F:
 
02067. LDX <SlotIndexBackup ; Restore X as the object slot index
 
02068.  
02069. PRG000_CA81:
 
02070. JSR AScrlURDiag_CheckWrapping ; Handle diagonal autoscroll's scroll wrappping
 
02071. JSR Object_DetermineVertVis ; Set flags based on which sprites of this object are vertically visible
 
02072. JSR Object_DetermineHorzVis ; Set flags based on which sprites of this object are horizontally visible
 
02073.  
02074. LDA Objects_State,X ; Get object state...
 
02075.  
02076. JSR DynJump
 
02077.  
02078. ; THESE MUST FOLLOW DynJump FOR THE DYNAMIC JUMP TO WORK!!
 
02079. .word ObjState_DeadEmpty ; 0 - Dead/Empty
 
02080. .word ObjState_Initializing ; 1 - Initializing
 
02081. .word ObjState_Normal ; 2 - Normal operation
 
02082. .word ObjState_Shelled ; 3 - Shelled
 
02083. .word ObjState_Held ; 4 - Held by Player
 
02084. .word ObjState_Kicked ; 5 - Kicked
 
02085. .word ObjState_Killed ; 6 - Killed
 
02086. .word ObjState_Squashed ; 7 - Object was squashed (NOTE: Really only intended for Goomba/Giant Goomba)
 
02087. .word ObjState_PoofDying ; 8 - "Poof" Dying
 
02088.  
02089. ; Patterns selected by "poof" death frame
 
02090. PoofDeath_Pats:
 
02091. .byte $47, $45, $41, $43
 
02092.  
02093. ObjState_PoofDying:
 
02094. LDA Objects_Timer,X
 
02095. BNE PRG000_CAAE ; If object timer is not expired, jump to PRG000_CAAE
 
02096.  
02097. JMP PRG000_D068 ; Jump to PRG000_D068 (Object_SetDeadEmpty)
 
02098.  
02099. PRG000_CAAE:
 
02100. JSR Object_AnySprOffscreen
 
02101. BNE PRG000_CAF0 ; If any sprite is off-screen, jump to PRG000_CAF0 (RTS)
 
02102.  
02103. ; Set the "poof" pixel positions
 
02104. JSR Object_CalcSpriteXY_NoHi
 
02105. LDY Object_SprRAM,X
 
02106. LDA <Objects_SpriteY,X
 
02107. STA Sprite_RAM+$00,Y
 
02108. STA Sprite_RAM+$04,Y
 
02109. LDA <Objects_SpriteX,X
 
02110. STA Sprite_RAM+$03,Y
 
02111. ADD #$08
 
02112. STA Sprite_RAM+$07,Y
 
02113.  
02114. LDA Objects_Timer,X
 
02115. LSR A
 
02116. LSR A
 
02117. LSR A
 
02118. TAX ; X = "poof" frame
 
02119.  
02120. ; Set "poof" death patterns
 
02121. LDA PoofDeath_Pats,X
 
02122. STA Sprite_RAM+$01,Y
 
02123. STA Sprite_RAM+$05,Y
 
02124.  
02125. ; Set the attributes
 
02126. LDA Level_NoStopCnt
 
02127. LSR A
 
02128. LSR A
 
02129. ROR A
 
02130. AND #$80
 
02131. ORA #$01
 
02132. STA Sprite_RAM+$02,Y
 
02133.  
02134. EOR #$c0
 
02135. STA Sprite_RAM+$06,Y
 
02136.  
02137. LDX <SlotIndexBackup ; X = object slot index
 
02138.  
02139. PRG000_CAF0:
 
02140. RTS ; Return
 
02141.  
02142. ; In units of $10 ticks by timer 3...
 
02143. PRG000_CAF1:
 
02144. .byte %00000010, %00000010, %00000100, %00001000, %00010000, %00010000
 
02145.  
02146. ; Some objects have "feet" when they are waking up,
 
02147. ; this offsets their Y depending on whether v-flipped
 
02148. ObjWakeUp_FeetYOff: .byte 10, -10
 
02149.  
02150. ; Called for an object in state 3 to do its "shelled" routine
 
02151. ObjState_Shelled:
 
02152. LDY ObjGroupRel_Idx ; Y = object's group-relative index
 
02153.  
02154. LDA ObjectGroup_Attributes3,Y
 
02155. AND #OA3_SQUASH
 
02156. BEQ PRG000_CB10 ; If OA3_SQUASH is NOT set (stomp does not "shell" this object), jump to PRG000_CB10
 
02157.  
02158. ; Attribute set 3 bit 4 is set...
 
02159.  
02160. ; Go to "stomped" state
 
02161.  
02162. ; Timer 3 = $10
 
02163. LDA #$10
 
02164. STA Objects_Timer3,X
 
02165.  
02166. ; Set object state to Squashed
 
02167. LDA #OBJSTATE_SQUASHED
 
02168. STA Objects_State,X
 
02169.  
02170. JMP Object_ShakeAndDraw ; Draw object and don't come back...
 
02171.  
02172. PRG000_CB10:
 
02173.  
02174. ; Attribute set 3 bit 4 is NOT set... (object is "shelled" when stomped)
 
02175.  
02176. LDA <Player_HaltGame
 
02177. BNE PRG000_CB5B ; If gameplay is halted, jump to PRG000_CB5B
 
02178.  
02179. JSR Object_ShellDoWakeUp ; Handle waking up (MAY not return here, if object "wakes up"!)
 
02180. JSR Object_Move ; Perform standard object movements
 
02181.  
02182. LDA <Objects_DetStat,X
 
02183. AND #$04
 
02184. BEQ PRG000_CB45 ; If object hit floor, jump to PRG000_CB45
 
02185.  
02186. LDA <Objects_YVel,X
 
02187. BMI PRG000_CB45 ; If object is moving upward, jump to PRG000_CB45
 
02188.  
02189. ; Object has NOT hit floor and is NOT moving upward...
 
02190.  
02191. PHA ; Save Y velocity
 
02192.  
02193. JSR Object_HitGround ; Align with ground
 
02194.  
02195. LDA <Objects_XVel,X ; Get X velocity
 
02196.  
02197. PHP ; Save CPU state
 
02198.  
02199. ; Get absolute value of X velocity
 
02200. BPL PRG000_CB30
 
02201. JSR Negate
 
02202. PRG000_CB30:
 
02203.  
02204. LSR A ; Divide by 2
 
02205. PLP ; Restore CPU state
 
02206.  
02207. ; If needed to negate before, negate again
 
02208. BPL PRG000_CB37
 
02209. JSR Negate
 
02210. PRG000_CB37:
 
02211. STA <Objects_XVel,X ; Set as X velocity
 
02212.  
02213. PLA ; Restore Y velocity
 
02214.  
02215. ; Divide by 4
 
02216. LSR A
 
02217. LSR A
 
02218. JSR Negate ; Negate it
 
02219. CMP #-$02
 
02220. BGE PRG000_CB45 ; If object only lightly moving upward, jump to PRG000_CB45
 
02221.  
02222. STA <Objects_YVel,X ; Set object Y velocity
 
02223.  
02224. PRG000_CB45:
 
02225. LDA <Objects_DetStat,X
 
02226. AND #$08
 
02227. BEQ PRG000_CB4F ; If object has NOT hit ceiling, jump to PRG000_CB4F
 
02228.  
02229. ; Set object Y velocity to $10 (rebound off ceiling)
 
02230. LDA #$10
 
02231. STA <Objects_YVel,X
 
02232.  
02233. PRG000_CB4F:
 
02234. LDA <Objects_DetStat,X
 
02235. AND #$03
 
02236. BEQ PRG000_CB58 ; If object has NOT hit wall, jump to PRG000_CB58
 
02237.  
02238. JSR Object_AboutFace ; Turn around...
 
02239.  
02240. PRG000_CB58:
 
02241. JSR Object_HandleBumpUnderneath ; Handle object getting hit from underside
 
02242.  
02243. PRG000_CB5B:
 
02244. JSR Object_BumpOffOthers ; Bump off and turn away from other objects
 
02245.  
02246. PRG000_CB5E:
 
02247. JSR Object_DeleteOffScreen ; Delete object if it goes off-screen
 
02248.  
02249.  
02250. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
02251. ; Object_DrawShelled
 
02252. ;
 
02253. ; Draw object in "shelled" state
 
02254. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
02255. ; $CB61
 
02256. Object_DrawShelled:
 
02257. ; Set object frame to 2
 
02258. LDA #$02
 
02259. STA Objects_Frame,X
 
02260.  
02261. LDA Objects_IsGiant,X
 
02262. BEQ PRG000_CB7B ; If object is NOT giant, jump to PRG000_CB7B
 
02263.  
02264. ; Call special "giant" object draw routine (giant objects assume a JMP instruction @ ObjectGroup_PatternSets)
 
02265. JSR ObjectGroup_PatternSets
 
02266.  
02267. Object_SetShakeAwakeTimer:
 
02268.  
02269. ; Set timer for object to wake up from
 
02270.  
02271. LDA Objects_Timer3,X
 
02272. CMP #$60
 
02273. BGE PRG000_CB7A ; If timer 3 >= $60, jump to PRG000_CB7A
 
02274.  
02275. AND #$07
 
02276. STA Objects_Timer4,X ; Timer 4 = 0-7, based on timer3
 
02277.  
02278. PRG000_CB7A:
 
02279. RTS ; Return
 
02280.  
02281.  
02282. PRG000_CB7B:
 
02283.  
02284. LDA Level_ObjectID,X
 
02285.  
02286. CMP #OBJ_BOBOMBEXPLODE
 
02287. BEQ PRG000_CB86 ; If this is a Bob-omb exploding, jump to PRG000_CB86
 
02288.  
02289. CMP #OBJ_BOBOMB
 
02290. BNE PRG000_CB8E ; If this is not a Bob-omb of any sort, jump to PRG000_CB8E
 
02291.  
02292. PRG000_CB86:
 
02293.  
02294. ; Have object flip same way as Player
 
02295. LDA <Player_FlipBits
 
02296. STA Objects_FlipBits,X
 
02297.  
02298. JMP Object_ShakeAndDraw ; Draw object and never come back!
 
02299.  
02300. PRG000_CB8E:
 
02301. JSR Object_ShakeAndDrawMirrored ; Draw mirrored sprite
 
02302.  
02303. LDY Level_ObjectID,X
 
02304. CPY #OBJ_ICEBLOCK
 
02305. BEQ PRG000_CBB3 ; If object is an Iceblock, jump to PRG000_CBB3 (RTS)
 
02306.  
02307. JSR Object_SetShakeAwakeTimer ; Set the "shake awake" timers
 
02308.  
02309. CPY #OBJ_BUZZYBEATLE
 
02310. BNE PRG000_CBB4 ; If object is NOT a Buzzy Beatle, jump to PRG000_CBB4
 
02311.  
02312. ; Buzzy Beatle
 
02313.  
02314. LDY Objects_FlipBits,X
 
02315. BMI PRG000_CBB3 ; If Buzzy is vertically flipped, jump to PRG000_CBB3 (RTS)
 
02316.  
02317. LDY Object_SprRAM,X ; Y = object's Sprite_RAM offset
 
02318.  
02319. ; +1 to Y to sprite if not flipped
 
02320. LDA Sprite_RAM+$00,Y
 
02321. ADD #$01
 
02322. STA Sprite_RAM+$00,Y
 
02323. STA Sprite_RAM+$04,Y
 
02324.  
02325. PRG000_CBB3:
 
02326. RTS ; Return
 
02327.  
02328. PRG000_CBB4:
 
02329.  
02330. ; NOT a Buzzy Beatle
 
02331.  
02332. CPY #OBJ_SPINY
 
02333. BEQ PRG000_CBB3 ; If Object is a Spiny, jump to PRG000_CBB3
 
02334.  
02335. ; "Shake awake" speed
 
02336.  
02337. LDA Objects_Timer3,X
 
02338. CMP #$50
 
02339. BGE PRG000_CC23 ; If timer 3 >= $50, jump to PRG000_CC23
 
02340.  
02341. LSR A
 
02342. LSR A
 
02343. LSR A
 
02344. LSR A
 
02345. TAY ; Y = index into PRG000_CAF1 (proper bit mask for shaking speed)
 
02346.  
02347. ; Various speed shake by timer 3
 
02348. LDA Objects_Timer3,X
 
02349. AND PRG000_CAF1,Y
 
02350. BEQ PRG000_CC23 ; If not shaking on this bit, jump to PRG000_CC23
 
02351.  
02352. LDA #$01 ; A = 1 (object not vertically flipped)
 
02353.  
02354. LDY Objects_FlipBits,X
 
02355. BMI PRG000_CBD4 ; If object is vertically flipped, jump to PRG000_CBD4
 
02356.  
02357. LSR A ; A = 0 (object vertically flipped)
 
02358.  
02359. PRG000_CBD4:
 
02360. LDY Object_SprRAM,X ; Y = object's Sprite_RAM offset
 
02361.  
02362. TAX ; X = 0 or 1 (proper Y offset for foot)
 
02363.  
02364. ; One foot
 
02365. LDA Sprite_RAM+$00,Y
 
02366. CMP #$f8
 
02367. BEQ PRG000_CBEA ; If sprite Y = $F8, jump to PRG000_CBEA
 
02368.  
02369. ADD ObjWakeUp_FeetYOff,X ; Add the foot offset
 
02370. CMP #$c5
 
02371. BGE PRG000_CBF8 ; If the offset >= $C5, jump to PRG000_CBF8
 
02372.  
02373. STA Sprite_RAM+$08,Y ; Foot Y
 
02374.  
02375. PRG000_CBEA:
 
02376.  
02377. ; Other foot
 
02378. LDA Sprite_RAM+$04,Y
 
02379. CMP #$f8
 
02380. BEQ PRG000_CBF8 ; If sprite Y = $F8, jump to PRG000_CBF8
 
02381.  
02382. ADD ObjWakeUp_FeetYOff,X ; Add the foot offset
 
02383. STA Sprite_RAM+$0C,Y ; Other foot Y
 
02384.  
02385. PRG000_CBF8:
 
02386.  
02387. ; Foot Xs
 
02388. LDA Sprite_RAM+$03,Y
 
02389. SUB #$03
 
02390. STA Sprite_RAM+$0B,Y
 
02391.  
02392. LDA Sprite_RAM+$07,Y
 
02393. ADD #$03
 
02394. STA Sprite_RAM+$0F,Y
 
02395.  
02396. ; Foot attributes
 
02397. LDA Sprite_RAM+$02,Y
 
02398. AND #$80
 
02399. ORA #$03
 
02400. STA Sprite_RAM+$0A,Y
 
02401.  
02402. ; Flip the other foot
 
02403. ORA #$40
 
02404. STA Sprite_RAM+$0E,Y
 
02405.  
02406. ; Feet pattern
 
02407. LDA #$f9
 
02408. STA Sprite_RAM+$09,Y
 
02409. STA Sprite_RAM+$0D,Y
 
02410.  
02411. LDX <SlotIndexBackup ; Restore 'X' as object index
 
02412.  
02413. PRG000_CC23:
 
02414. RTS ; Return
 
02415.  
02416.  
02417. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
02418. ; Object_BumpOffOthers
 
02419. ;
 
02420. ; Detects all objects "prior" to this one and determines if the
 
02421. ; objects have collided, at which point they "bump off eachother"
 
02422. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
02423. Object_BumpOffOthers:
 
02424. TXA ; A = object slot index
 
02425. ADD <Counter_1
 
02426. LSR A
 
02427. BCS PRG000_CC6B ; Semi-randomly jump to PRG000_CC6B (RTS)
 
02428.  
02429. JSR Object_AnySprOffscreen
 
02430. BNE PRG000_CC6B ; If any sprite is off-screen, jump to PRG000_CC6B (RTS)
 
02431.  
02432. JSR Object_CalcBoundBox2
 
02433. TXA
 
02434. BEQ PRG000_CC6B ; If object slot is zero, jump to PRG000_CC6B (RTS)
 
02435.  
02436. DEX ; X-- (consider the previous object)
 
02437.  
02438. PRG000_CC37:
 
02439. LDY Level_ObjectID,X ; Y = Object ID
 
02440.  
02441. LDA Object_AttrFlags,Y
 
02442. AND #OAT_BOUNCEOFFOTHERS
 
02443. BEQ PRG000_CC66 ; If OAT_BOUNCEOFFOTHERS is NOT set, jump to PRG000_CC66
 
02444.  
02445. LDA Objects_State,X
 
02446. CMP #OBJSTATE_NORMAL
 
02447. BNE PRG000_CC66 ; If Object state is NOT Normal, jump to PRG000_CC66
 
02448.  
02449. JSR Object_AnySprOffscreen
 
02450. BNE PRG000_CC66 ; If any sprite of object is off-screen, jump to PRG000_CC66
 
02451.  
02452. JSR Object_CalcBoundBox
 
02453. JSR ObjectObject_Intersect
 
02454. BCC PRG000_CC66 ; If object did not intersect with prior object, jump to PRG000_CC66
 
02455.  
02456. LDY <SlotIndexBackup ; Y = object slot index
 
02457.  
02458. LDA <Objects_SpriteX,X
 
02459. CMP Objects_SpriteX,Y
 
02460. LDY #$00 ; Y = 0
 
02461. BLT PRG000_CC62 ; If this object's sprite X < the OTHER object's sprite X, jump to PRG000_CC62
 
02462. LDY #$40 ; Otherwise, Y = $40
 
02463.  
02464. PRG000_CC62:
 
02465. TYA
 
02466. STA Objects_FlipBits,X ; Object turns around if it hit another object
 
02467.  
02468. PRG000_CC66:
 
02469. DEX ; X--
 
02470. BPL PRG000_CC37 ; While X >= 0, loop!
 
02471.  
02472. LDX <SlotIndexBackup ; X = object slot index
 
02473.  
02474. PRG000_CC6B:
 
02475. RTS ; Return
 
02476.  
02477.  
02478. ObjKickXvel: .byte $18, -$18
 
02479.  
02480. ObjState_Kicked:
 
02481. LDA <Player_HaltGame
 
02482. BEQ PRG000_CC75 ; If gameplay is NOT halted, jump to PRG000_CC75
 
02483.  
02484. JMP PRG000_CD46 ; Jump to PRG000_CD46
 
02485.  
02486. PRG000_CC75:
 
02487. JSR Object_Move ; Perform standard object movements
 
02488. JSR Object_DetermineHorzVis ; Determine horizontally visible sprites
 
02489.  
02490. LDA <Objects_DetStat,X
 
02491. AND #$04
 
02492. BEQ PRG000_CC94 ; If object has hit ground, jump to PRG000_CC94
 
02493.  
02494. LDA <Objects_XVel,X
 
02495. BNE PRG000_CC8D ; If object is moving horizontally, jump to PRG000_CC8D
 
02496.  
02497. ; Object not moving horizontally...
 
02498. JSR Level_ObjCalcXDiffs
 
02499. LDA ObjKickXvel,Y
 
02500. STA <Objects_XVel,X ; Set X velocity based on which side of Player the object is on
 
02501.  
02502. PRG000_CC8D:
 
02503. JSR Object_HitGround ; Align to floor
 
02504.  
02505. ; Y Velocity = $0C (begin drop)
 
02506. LDA #$0c
 
02507. STA <Objects_YVel,X
 
02508.  
02509. PRG000_CC94:
 
02510. LDA <Objects_DetStat,X
 
02511. AND #$03
 
02512. BNE PRG000_CC9D ; If object has hit a wall, jump to PRG000_CC9D
 
02513.  
02514. JMP PRG000_CCF7 ; Otherwise, jump to PRG000_CCF7
 
02515.  
02516. PRG000_CC9D:
 
02517. LDA Objects_SpriteX,X
 
02518.  
02519. LDY <Objects_XVel,X
 
02520. BPL PRG000_CCAA ; If object is not moving to the left, jump to PRG000_CCAA
 
02521.  
02522. CMP #$06
 
02523. BLT PRG000_CCE2 ; If object's sprite X < 6, jump to PRG000_CCAA
 
02524. BGE PRG000_CCAE ; Otherwise, jump to PRG000_CCAE
 
02525.  
02526. PRG000_CCAA:
 
02527. CMP #228
 
02528. BGE PRG000_CCE2 ; If object's sprite X < 228, jump to PRG000_CCE2
 
02529.  
02530. PRG000_CCAE:
 
02531. JSR Object_AnySprOffscreen
 
02532. BNE PRG000_CCE2 ; If any sprite is off-screen, jump to PRG000_CCE2
 
02533.  
02534. LDA PAGE_A000
 
02535. PHA ; Save current PAGE_A000 page
 
02536.  
02537. ; Set page @ A000 to 8
 
02538. LDA #$08
 
02539. STA PAGE_A000
 
02540. JSR PRGROM_Change_A000
 
02541.  
02542. ; Temp_Var13 = Object tile detect Y Hi
 
02543. LDA ObjTile_DetYHi
 
02544. STA <Temp_Var13
 
02545.  
02546. ; Temp_Var13 = Object tile detect Y Hi
 
02547. LDA ObjTile_DetYLo
 
02548. STA <Temp_Var14
 
02549.  
02550. ; Temp_Var15 = Object tile detect X Hi
 
02551. LDA ObjTile_DetXHi
 
02552. STA <Temp_Var15
 
02553.  
02554. ; Temp_Var16 = Object tile detect X Lo
 
02555. LDA ObjTile_DetXLo
 
02556. STA <Temp_Var16
 
02557.  
02558. ; Handle object bouncing off blocks
 
02559. LDA Object_TileWall2
 
02560. JSR Object_BumpOffBlocks
 
02561.  
02562. LDX <SlotIndexBackup ; X = object slot index
 
02563.  
02564. ; Restore page @ A000 to previous value
 
02565. PLA
 
02566. STA PAGE_A000
 
02567. JSR PRGROM_Change_A000
 
02568.  
02569. PRG000_CCE2:
 
02570.  
02571. ; Play bump sound
 
02572. LDA Sound_QPlayer
 
02573. ORA #SND_PLAYERBUMP
 
02574. STA Sound_QPlayer
 
02575.  
02576. LDA Level_ObjectID,X
 
02577. CMP #OBJ_ICEBLOCK
 
02578. BNE PRG000_CCF4 ; If this object is NOT an Ice Block, jump to PRG000_CCF4
 
02579.  
02580. JMP PRG000_D295 ; Jump to PRG000_D295 (set Ice Block to "killed" state)
 
02581.  
02582. PRG000_CCF4:
 
02583. JSR Object_AboutFace ; Bounced off block, turn around
 
02584.  
02585. PRG000_CCF7:
 
02586. JSR Object_HandleBumpUnderneath ; Handle the kicked shelled object getting hit from underneath
 
02587.  
02588. TXA
 
02589. ADD <Counter_1
 
02590. LSR A
 
02591. BCC PRG000_CD46 ; Semi-randomly jump to PRG000_CD46
 
02592.  
02593. JSR ObjectToObject_HitTest
 
02594. BCC PRG000_CD46 ; If object has not hit another object, jump to PRG000_CD46
 
02595.  
02596. ; Play object-to-object collision sound
 
02597. LDA Sound_QPlayer
 
02598. ORA #SND_PLAYERKICK
 
02599. STA Sound_QPlayer
 
02600.  
02601. ; Knock object in same general direction as the kicked shell object
 
02602. LDA <Objects_XVel,X
 
02603. ASL A
 
02604. LDA #$10 ; A = $10
 
02605. BCC PRG000_CD17
 
02606. LDA #-$10 ; A = -$10
 
02607. PRG000_CD17:
 
02608. STA Objects_XVel,Y
 
02609.  
02610. LDA Objects_State,Y
 
02611. CMP #OBJSTATE_KICKED
 
02612. BNE PRG000_CD36 ; If the impacted object's state is not Kicked, jump to PRG000_CD36
 
02613.  
02614. ; Another kicked object on the way... (slam and kill eachother)
 
02615.  
02616. LDA Objects_KillTally,Y
 
02617. JSR Score_Get100PlusPts ; Get the total score this OTHER kicked shell object earned
 
02618. JSR ObjectKill_SetShellKillVars ; Kill our kicked object and set ShellKill variables
 
02619.  
02620. ; Set X Velocity of our kicked object in the direction of the impacted object
 
02621. LDA Objects_XVel,Y
 
02622. ASL A
 
02623. LDA #$10
 
02624. BCS PRG000_CD34
 
02625. LDA #-$10
 
02626. PRG000_CD34:
 
02627. STA <Objects_XVel,X
 
02628.  
02629. PRG000_CD36:
 
02630. TYA
 
02631. TAX ; X = the other object we just hit
 
02632. JSR ObjectKill_SetShellKillVars ; Kill the impacted object and set ShellKill variables
 
02633.  
02634. LDX <SlotIndexBackup ; X = object slot index (our kicked object)
 
02635. LDA Objects_KillTally,X
 
02636. INC Objects_KillTally,X ; Increase our kicked object's kill tally...
 
02637. JSR Score_Get100PlusPtsY ; Get points by the kill tally! (Incidentally, Score_Get100PlusPts would work too)
 
02638.  
02639. PRG000_CD46:
 
02640. JSR Object_DeleteOffScreen ; Delete the kicked shell object if it goes off-screen
 
02641.  
02642. LDA Level_ObjectID,X
 
02643. CMP #OBJ_ICEBLOCK
 
02644. BEQ PRG000_CD77 ; If the kicked object is an ice block, jump to PRG000_CD77
 
02645.  
02646. ; Object is NOT an ice block...
 
02647.  
02648. ; NOTE: I really, really wish Nintendo used a consistent check here!
 
02649. ; Other code checks Objects_IsGiant before taking this route...
 
02650. CMP #OBJ_BIGGREENTROOPA
 
02651. BGE PRG000_CD80 ; If the object ID >= OBJ_BIGGREENTROOPA (why not use Objects_IsGiant?!), jump to PRG000_CD80
 
02652.  
02653. LDA Level_NoStopCnt
 
02654. LSR A
 
02655. AND #$03
 
02656. TAY ; Y = 0 to 3, by counter
 
02657.  
02658. LDA Objects_FlipBits,X
 
02659. AND #~SPR_HFLIP ; Keep all FlipBits except horizontal flips
 
02660. ORA ObjShell_AnimFlipBits,Y
 
02661. STA Objects_FlipBits,X ; Apply flip as appropriate
 
02662.  
02663. ; Set animation frame as appropriate
 
02664. LDA ObjShell_AnimFrame,Y
 
02665. STA Objects_Frame,X
 
02666.  
02667. TYA
 
02668. AND #$01
 
02669. BNE PRG000_CD74 ; Every other tick, jump to PRG000_CD74
 
02670.  
02671. JMP Object_ShakeAndDrawMirrored ; Draw sprite and don't come back
 
02672.  
02673. PRG000_CD74:
 
02674. JMP Object_ShakeAndDraw ; Update sprite data, draw sprite, and don't come back
 
02675.  
02676. PRG000_CD77:
 
02677.  
02678. ; Ice block only...
 
02679.  
02680. LDA <Counter_1
 
02681. LSR A
 
02682. STA Objects_ColorCycle,X ; Cycle colors
 
02683. JMP Object_ShakeAndDrawMirrored ; Draw sprite and don't come back!
 
02684.  
02685. PRG000_CD80:
 
02686. JMP ObjectGroup_PatternSets ; Jump to ObjectGroup_PatternSets (giant object special shelled draw routine)
 
02687.  
02688.  
02689. ObjectKill_SetShellKillVars:
 
02690. ; Set object state to Killed
 
02691. LDA #OBJSTATE_KILLED
 
02692. STA Objects_State,X
 
02693.  
02694. ; Bounce up a bit
 
02695. LDA #-$30
 
02696. STA <Objects_YVel,X
 
02697.  
02698. ; Set ShellKillFlash vars
 
02699. LDA <Objects_Y,X
 
02700. STA ShellKillFlash_Y
 
02701. LDA <Objects_X,X
 
02702. STA ShellKillFlash_X
 
02703. LDA #$0a
 
02704. STA ShellKillFlash_Cnt
 
02705.  
02706. RTS ; Return
 
02707.
 
02708. ; Kicked shell object animation frames and flips
 
02709. ObjShell_AnimFlipBits: .byte $00, $00, $00, $40
 
02710. ObjShell_AnimFrame: .byte $04, $06, $05, $06
 
02711.  
02712. ; Copies all brick bust data over to the second bust slots
 
02713. ; (So up to 2 bricks may be scattering debris at once)
 
02714. BrickBust_MoveOver:
 
02715. LDA BrickBust_En
 
02716. STA BrickBust_En+1
 
02717.  
02718. LDA BrickBust_YUpr
 
02719. STA BrickBust_YUpr+1
 
02720.  
02721. LDA BrickBust_YLwr
 
02722. STA BrickBust_YLwr+1
 
02723.  
02724. LDA BrickBust_X
 
02725. STA BrickBust_X+1
 
02726.  
02727. LDA BrickBust_YVel
 
02728. STA BrickBust_YVel+1
 
02729.  
02730. LDA BrickBust_XDist
 
02731. STA BrickBust_XDist+1
 
02732.  
02733. LDA BrickBust_HEn
 
02734. STA BrickBust_HEn+1
 
02735.  
02736. RTS ; Return
 
02737.  
02738.  
02739. ; FIXME: Anybody want to claim this?
 
02740. ; Appears to override what goes in to Object_BumpBlocks
 
02741. ; $CDCF
 
02742. LDA Object_TileWall2
 
02743.  
02744. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
02745. ; Object_BumpBlocks
 
02746. ;
 
02747. ; Provides an arbitrary object with the ability to hit objects
 
02748. ; with its "head"; used by Boom Boom, though Boom Boom never
 
02749. ; gets a chance to employ that in the game...
 
02750. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
02751. ; $CDD2
 
02752. Object_BumpBlocks:
 
02753. STA <Temp_Var8 ; Store detected tile -> Temp_Var8
 
02754.  
02755. ; Backup current PAGE_A000 bank
 
02756. LDA PAGE_A000
 
02757. PHA
 
02758.  
02759. ; Change page @ A000 to 8
 
02760. LDA #$08
 
02761. STA PAGE_A000
 
02762. JSR PRGROM_Change_A000
 
02763.  
02764. ; Transfer tile detection
 
02765.  
02766. LDA ObjTile_DetYHi
 
02767. STA <Temp_Var13
 
02768.  
02769. LDA ObjTile_DetYLo
 
02770. STA <Temp_Var14
 
02771.  
02772. LDA ObjTile_DetXHi
 
02773. STA <Temp_Var15
 
02774.  
02775. LDA ObjTile_DetXLo
 
02776. STA <Temp_Var16
 
02777.  
02778. ; Send detected tile over to check if object has hit any blocks
 
02779. ; that respond to being hit with head
 
02780. LDA <Temp_Var8
 
02781. JSR Object_BumpOffBlocks
 
02782.  
02783. LDX <SlotIndexBackup ; X = object slot index
 
02784.  
02785. ; Restore page @ A000 to previous page
 
02786. PLA
 
02787. STA PAGE_A000
 
02788. JSR PRGROM_Change_A000
 
02789.  
02790. RTS ; Return
 
02791.  
02792.  
02793. ; X velocities depending on kick direction, added to by half of Player's X velocity
 
02794. ObjectKickXVelMoving: .byte -$30, $30
 
02795.  
02796. ; Set appropriate flip bits based on object's relative position to Player
 
02797. PlayerKickFlipBits: .byte $00, $40
 
02798.  
02799. ; X velocities depending on kick direction
 
02800. BobombKickXVel: .byte -$28, $28
 
02801.  
02802. ; Different X and X Hi offsets applied to object being held by Player
 
02803. ; Changes whether not doing anything special, in pipe, etc.
 
02804. ObjectHoldXOff: .byte $0B, -$0B, $04, -$04, $04, $0B, -$13, $04, -$08, $04, $00
 
02805. ObjectHoldXHiOff: .byte $00, $FF, $00, $FF, $00, $00, $FF, $00, $FF, $00, $00
 
02806.  
02807. ; Object-to-object hit resultant X velocity
 
02808. ObjectToObject_HitXVel: .byte -$08, $08
 
02809.  
02810. ObjState_Held:
 
02811. LDA <Player_IsDying
 
02812. BEQ PRG000_CE28 ; If Player is NOT dying, jump to PRG000_CE28
 
02813.  
02814. JMP PRG000_CF98 ; Jump to PRG000_CF98 (just draw held object)
 
02815.  
02816. PRG000_CE28:
 
02817. JSR Object_ShellDoWakeUp ; Wake up while Player is holding object...
 
02818. BIT <Pad_Holding
 
02819. BVC Player_KickObject ; If Player is NOT holding B button, jump to Player_KickObject
 
02820.  
02821. PRG000_CE2F:
 
02822. JMP PRG000_CEEF ; Jump to PRG000_CEEF
 
02823.  
02824.  
02825. Player_KickObject:
 
02826. LDA Level_PipeMove
 
02827. BNE PRG000_CE2F ; If Player is moving through pipes, jump to PRG000_CE2F (PRG000_CEEF)
 
02828.  
02829. ; Play kick sound
 
02830. LDA Sound_QPlayer
 
02831. ORA #SND_PLAYERKICK
 
02832. STA Sound_QPlayer
 
02833.  
02834. ; Have Player do kick frame
 
02835. LDA #$0c
 
02836. STA Player_Kick
 
02837.  
02838. ; Set object timer 2 to $10
 
02839. LDA #$10
 
02840. STA Objects_Timer2,X
 
02841.  
02842. LDA Level_ObjectID,X
 
02843.  
02844. CMP #OBJ_BOBOMBEXPLODE
 
02845. BEQ PRG000_CE54 ; If this is a Bob-omb ready to explode, jump to PRG000_CE54
 
02846.  
02847. CMP #OBJ_BOBOMB
 
02848. BNE PRG000_CE79 ; If this is NOT a Bob-omb, jump to PRG000_CE79
 
02849.  
02850. PRG000_CE54:
 
02851.  
02852. ; Bob-ombs only...
 
02853.  
02854. ; State remains "normal"
 
02855. LDA #OBJSTATE_NORMAL
 
02856. STA Objects_State,X
 
02857.  
02858. ; Set Y vel to -$20 (bounce up)
 
02859. LDA #-$20
 
02860. STA <Objects_YVel,X
 
02861.  
02862. ; Set X Velocity appropriately based on kick direction
 
02863. JSR Level_ObjCalcXDiffs
 
02864. LDA BobombKickXVel,Y
 
02865. STA <Objects_XVel,X
 
02866.  
02867. EOR <Player_XVel
 
02868. BMI PRG000_CE76 ; If the Bob-omb's X velocity is the opposite sign of the Player's, jump to PRG000_CE76
 
02869.  
02870. LDA <Player_XVel
 
02871. STA <Temp_Var1 ; -> Temp_Var1 (yyyy xxxx)
 
02872. ASL <Temp_Var1 ; Shift 1 bit left (bit 7 into carry) (y yyyx xxx0)
 
02873. ROR A ; A is now arithmatically shifted to the right (yyyyy xxx) (signed division by 2)
 
02874. ADD ObjectKickXVelMoving,Y ; Add base "moving" X velocity of Bob-omb
 
02875. STA <Objects_XVel,X ; Set this as Bob-omb's X Velocity
 
02876.  
02877. PRG000_CE76:
 
02878. JMP Object_ShakeAndDraw ; Draw Bob-omb and don't come back!
 
02879.  
02880. PRG000_CE79:
 
02881.  
02882. ; Anything besides a Bob-omb...
 
02883.  
02884. ; Clear Objects_KillTally
 
02885. LDA #$00
 
02886. STA Objects_KillTally,X
 
02887.  
02888. LDA Objects_State,X
 
02889. CMP #OBJSTATE_HELD
 
02890. BNE PRG000_CEBE ; If object's state is not Held, jump to PRG000_CEBE
 
02891.  
02892. ; This object is being held by Player...
 
02893.  
02894. LDA Level_ObjectID,X
 
02895. CMP #OBJ_ICEBLOCK
 
02896. BEQ PRG000_CEB4 ; If this is an ice block, jump to PRG000_CEB4
 
02897.  
02898. LDY #1 ; Y = 1
 
02899.  
02900. LDA <Player_FlipBits
 
02901. BNE PRG000_CE94 ; If Player is not turned around, jump to PRG000_CE94
 
02902.  
02903. LDY #-1 ; Y = -1
 
02904.  
02905. PRG000_CE94:
 
02906. STY <Objects_XVel,X ; Set minimum X velocity on object (to enable wall hit detection)
 
02907.  
02908. JSR Object_WorldDetectN1 ; Detect against world
 
02909.  
02910. LDA <Objects_DetStat,X
 
02911. AND #$03
 
02912. BEQ PRG000_CEB4 ; If object has not hit a wall, jump to PRG000_CEB4
 
02913.  
02914. ; KICK OBJECT INTO WALL LOGIC
 
02915.  
02916. ; Flat 100 points
 
02917. LDA #$05
 
02918. JSR Score_PopUp
 
02919.  
02920. ; Object state is Killed
 
02921. LDA #OBJSTATE_KILLED
 
02922. STA Objects_State,X
 
02923.  
02924. ; Set object Y velocity to -$40 (fly up a bit)
 
02925. LDA #-$40
 
02926. STA <Objects_YVel,X
 
02927.  
02928. ; Remove that minimum X velocity
 
02929. LDA #$00
 
02930. STA <Objects_XVel,X
 
02931.  
02932. JMP PRG000_CF98 ; Jump to PRG000_CF98
 
02933.  
02934. PRG000_CEB4:
 
02935.  
02936. ; Object kicked not against wall...
 
02937.  
02938. LDY #0 ; Y = 0
 
02939.  
02940. LDA <Player_FlipBits
 
02941. BEQ PRG000_CEBB ; If Player has not turned around, jump to PRG000_CEBB
 
02942.  
02943. INY ; Y = 1
 
02944.  
02945. PRG000_CEBB:
 
02946. JMP PRG000_CEC6 ; Jump to PRG000_CEC6
 
02947.  
02948. PRG000_CEBE:
 
02949.  
02950. ; Object kicked, was not held
 
02951.  
02952. ; Make sure Player is facing object he's kicking
 
02953. JSR Level_ObjCalcXDiffs
 
02954. LDA PlayerKickFlipBits,Y
 
02955. STA <Player_FlipBits
 
02956.  
02957. PRG000_CEC6:
 
02958. LDA ObjectKickXVelMoving,Y ; Get appropriate base X velocity for kick
 
02959. STA <Objects_XVel,X ; -> Object's X velocity
 
02960.  
02961. EOR <Player_XVel
 
02962. BMI PRG000_CEDC ; If the object's X velocity is the opposite sign of the Player's, jump to PRG000_CEDC
 
02963.  
02964. LDA <Player_XVel ; Get the Player's X velocity
 
02965. STA <Temp_Var1 ; -> Temp_Var1 (yyyy xxxx)
 
02966. ASL <Temp_Var1 ; Shift 1 bit left (bit 7 into carry) (y yyyx xxx0)
 
02967. ROR A ; A is now arithmatically shifted to the right (yyyyy xxx) (signed division by 2)
 
02968. ADD ObjectKickXVelMoving,Y ; Add base "moving" X velocity of object
 
02969. STA <Objects_XVel,X ; Set as object's X velocity
 
02970.  
02971. PRG000_CEDC:
 
02972. ; If object's state is not Killed, jump to PRG000_CEE8
 
02973. LDA Objects_State,X
 
02974. CMP #OBJSTATE_KILLED
 
02975. BEQ PRG000_CEE8
 
02976.  
02977. ; Set object state to 5 (Kicked)
 
02978. LDA #OBJSTATE_KICKED
 
02979. STA Objects_State,X
 
02980.  
02981. PRG000_CEE8:
 
02982.  
02983. ; Set object's Y velocity to zero
 
02984. LDA #$00
 
02985. STA <Objects_YVel,X
 
02986.  
02987. JMP PRG000_CF98 ; Jump to PRG000_CF98
 
02988.  
02989. PRG000_CEEF:
 
02990.  
02991. ; Player moving through pipes...
 
02992.  
02993. ; Player keeps on holding through the pipes!!
 
02994. LDA #$01
 
02995. STA Player_IsHolding
 
02996.  
02997. LDA Level_PipeMove
 
02998. BEQ PRG000_CEFD ; If Player is NOT moving through pipes, jump to PRG000_CEFD
 
02999.  
03000. LDY #$0a ; Y = 10
 
03001. BNE PRG000_CF1A ; Jump (technically always) to PRG000_CF1A
 
03002.  
03003. PRG000_CEFD:
 
03004. LDY #$00 ; Y = 0
 
03005.  
03006. LDA <Player_FlipBits
 
03007. BNE PRG000_CF04 ; If Player is turned around, jump to PRG000_CF04
 
03008.  
03009. INY ; Y = 1
 
03010.  
03011. PRG000_CF04:
 
03012. LDA Objects_IsGiant,X
 
03013. BEQ PRG000_CF0E ; If object is not giant, jump to PRG000_CF0E
 
03014.  
03015. ; Y += 5
 
03016. INY
 
03017. INY
 
03018. INY
 
03019. INY
 
03020. INY
 
03021.  
03022. PRG000_CF0E:
 
03023. LDA Player_PipeFace
 
03024. BEQ PRG000_CF1F ; If Player is NOT "pipe facing" (facing forward in pipe), jump to PRG000_CF1F
 
03025.  
03026. ; Y += 2
 
03027. INY
 
03028. INY
 
03029.  
03030. CMP #$05
 
03031. BLT PRG000_CF1A ; If less than 5 ticks remaining on the "pipe face", jump to PRG000_CF1A
 
03032.  
03033. INY ; Otherwise, Y++
 
03034.  
03035. PRG000_CF1A:
 
03036.  
03037. ; Set object to occupy Sprite_RAM offset $10
 
03038. LDA #$10
 
03039. STA Object_SprRAM,X
 
03040.  
03041. PRG000_CF1F:
 
03042.  
03043. ; Set held object's proper X position
 
03044. LDA <Player_X
 
03045. ADD ObjectHoldXOff,Y
 
03046. STA <Objects_X,X
 
03047.  
03048. LDA <Player_XHi
 
03049. ADC ObjectHoldXHiOff,Y
 
03050. STA <Objects_XHi,X
 
03051.  
03052. LDA #-$02 ; A = -$02
 
03053.  
03054. LDY Objects_IsGiant,X
 
03055. BNE PRG000_CF3D ; If object is giant, jump to PRG000_CF3D
 
03056.  
03057. LDA #$0d ; A = $0D
 
03058.  
03059. LDY <Player_Suit
 
03060. BNE PRG000_CF3D ; If Player is not small, jump to PRG000_CF3D
 
03061.  
03062. LDA #$0f ; Otherwise, A = $0F
 
03063.  
03064. PRG000_CF3D:
 
03065. PHA ; Save 'A'
 
03066.  
03067. ; Set Y offset to object being held
 
03068. ADD <Player_Y
 
03069. STA <Objects_Y,X
 
03070.  
03071. LDY #$00 ; Y = 0
 
03072.  
03073. PLA ; Restore 'A'
 
03074.  
03075. BPL PRG000_CF49 ; If A >= 0 (negative when object was giant), jump to PRG000_CF49
 
03076.  
03077. DEY ; Y = -1
 
03078.  
03079. PRG000_CF49:
 
03080. TYA ; A = 0 or -1
 
03081.  
03082. ; Apply carry
 
03083. ADC <Player_YHi
 
03084. STA <Objects_YHi,X
 
03085.  
03086. ; While held, object's velocities match Player's
 
03087. LDA <Player_XVel
 
03088. STA <Objects_XVel,X
 
03089. LDA <Player_YVel
 
03090. STA <Objects_YVel,X
 
03091.  
03092. JSR Object_WorldDetectN1 ; Detect against world
 
03093. JSR Object_CalcSpriteXY_NoHi ; Calculate low parts of sprite X/Y (never off-screen when held by Player!)
 
03094. JSR ObjectToObject_HitTest ; Test if this object has collided with another object
 
03095. BCC PRG000_CF98 ; If this object did not collide with any other objects, jump to PRG000_CF98
 
03096.  
03097. LDA Objects_Timer2,X
 
03098. ORA Level_PipeMove
 
03099. BNE PRG000_CF98 ; If timer 2 is not expired or Player is moving through pipes, jump to PRG000_CF98
 
03100.  
03101. ; Object colliding sound!
 
03102. LDA Sound_QPlayer
 
03103. ORA #SND_PLAYERKICK
 
03104. STA Sound_QPlayer
 
03105.  
03106. ; Object which was held is dead!
 
03107. LDA #OBJSTATE_KILLED
 
03108. STA Objects_State,X
 
03109.  
03110. ; Y velocity = -$30 (fly up a bit)
 
03111. LDA #-$30
 
03112. STA <Objects_YVel,X
 
03113.  
03114. ; Object that got hit is dead!
 
03115. LDA #OBJSTATE_KILLED
 
03116. STA Objects_State,Y
 
03117.  
03118. ; Y velocity = -$30 (fly up a bit)
 
03119. LDA #-$30
 
03120. STA Objects_YVel,Y
 
03121.  
03122. ; Get 100 pts for the hit!
 
03123. LDA #$00
 
03124. JSR Score_Get100PlusPts
 
03125.  
03126. ; Object will not collide again for 16 ticks (dampener I guess)
 
03127. LDA #16
 
03128. STA Objects_Timer2,X
 
03129.  
03130. TYA
 
03131. TAX
 
03132. JSR Level_ObjCalcXDiffs ; Determine which side the OTHER object is on
 
03133.  
03134. ; Set the OTHER object's X velocity appropriately
 
03135. LDA ObjectToObject_HitXVel,Y
 
03136. STA <Objects_XVel,X
 
03137.  
03138. PRG000_CF98:
 
03139. LDX <SlotIndexBackup ; Restore 'X' to the object slot index
 
03140.  
03141. LDA <Player_IsDying
 
03142. BNE PRG000_CFA5 ; If Player is dying, jump to PRG000_CFA5
 
03143.  
03144. ; Player is NOT dying...
 
03145.  
03146. LDA Sprite_RAM+$28
 
03147. CMP #$f8
 
03148. BEQ PRG000_CFA8 ; ?? If Sprite_RAM+$28 (10th sprite) Y coordinate = $F8 (unused), jump to PRG000_CFA8 ??
 
03149.  
03150. PRG000_CFA5:
 
03151. JSR Object_DrawShelled ; Draw shelled object
 
03152.  
03153. PRG000_CFA8:
 
03154. RTS ; Return
 
03155.  
03156.  
03157. ; Unused space... deleted code?
 
03158. NOP
 
03159. NOP
 
03160. NOP
 
03161. NOP
 
03162. NOP
 
03163. NOP
 
03164. NOP
 
03165. NOP
 
03166.  
03167. ObjState_Killed:
 
03168. JSR Object_FallAndDelete ; Have object fall and delete if it gets too low (at which point we don't return)
 
03169.  
03170. LDY ObjGroupRel_Idx ; Y = object's group relative index
 
03171.  
03172. LDA ObjectGroup_KillAction,Y
 
03173. AND #%00001111
 
03174. BEQ Object_DoKillAction ; If kill action is zero, jump to Object_DoKillAction (i.e. do NOT set frame 2)
 
03175.  
03176. CPX #$05
 
03177. BGE Object_DoKillAction ; If object slot >= 5 (i.e. not a "general" objects), jump to Object_DoKillAction (i.e. do NOT set frame 2)
 
03178.  
03179. PHA ; Save kill action
 
03180.  
03181. LDA #$02
 
03182. STA Objects_Frame,X ; Set frame to 2
 
03183.  
03184. PLA ; Restore kill action
 
03185.  
03186. ; Do the kill action
 
03187. Object_DoKillAction:
 
03188. JSR DynJump
 
03189.  
03190. ; THESE MUST FOLLOW DynJump FOR THE DYNAMIC JUMP TO WORK!!
 
03191. .word Object_StandardKill ; 0: Standard kill (does not set frame 2)
 
03192. .word Object_CalcAndDrawKilled ; 1: Standard sprite draw and kill
 
03193. .word Object_DrawMirroredKilled ; 2: Draw mirrored sprite
 
03194. .word Object_Draw16x32Killed ; 3: Draw tall sprite
 
03195. .word Object_DrawTallHFlipped ; 4: Draw tall object horizontally flipped
 
03196. .word Object_NormalAndKilled ; 5: Do "Normal" state and killed action (sinking/vert flip)
 
03197. .word Object_GiantKilled ; 6: Giant enemy death
 
03198. .word Object_PoofDie ; 7: Do "poof" dying state while killed
 
03199. .word Object_DrawAndMoveNotHalt ; 8: Draw and do movements unless gameplay halted
 
03200. .word Object_NormalWhileKilled ; 9: Just do "Normal" state while killed
 
03201.  
03202. Object_StandardKill:
 
03203. JSR Object_DoHaltedAction
 
03204. JMP Object_DoKilledAction
 
03205.  
03206. Object_NormalAndKilled:
 
03207. JSR Object_DoNormal
 
03208. JMP Object_DoKilledAction
 
03209.  
03210. Object_NormalWhileKilled:
 
03211. JMP Object_DoNormal
 
03212.  
03213. Object_GiantKilled:
 
03214. JSR ObjectGroup_PatternSets ; Do special draw routine used by "giant" enemies
 
03215. JMP Object_DoKilledAction
 
03216.  
03217. Object_PoofDie:
 
03218. ; Set object state to 8 ("Poof" Dying)
 
03219. LDA #OBJSTATE_POOFDEATH
 
03220. STA Objects_State,X
 
03221.  
03222. ; Set timer to $1F
 
03223. LDA #$1f
 
03224. STA Objects_Timer,X
 
03225.  
03226. RTS ; Return
 
03227.  
03228. Object_DrawAndMoveNotHalt:
 
03229. JSR Object_ShakeAndDraw
 
03230. JMP Object_MoveNotHalted
 
03231.  
03232. Object_DrawTallHFlipped:
 
03233. JSR Object_DrawTallAndHFlip
 
03234. JMP Object_DoKilledAction
 
03235.  
03236. Object_Draw16x32Killed:
 
03237. JSR Object_Draw16x32Sprite
 
03238. JMP Object_DoKilledAction
 
03239.  
03240. Object_DrawMirroredKilled:
 
03241. JSR Object_ShakeAndDrawMirrored
 
03242. JMP Object_DoKilledAction
 
03243.  
03244. Object_CalcAndDrawKilled:
 
03245. JSR Object_ShakeAndDraw
 
03246.  
03247. ; If object was killed by sinking in quicksand or just killed, do this...
 
03248. Object_DoKilledAction:
 
03249. LDA <Player_HaltGame
 
03250. BNE PRG000_D054 ; If gameplay is halted, jump to PRG000_D054
 
03251.  
03252. LDA Objects_QSandCtr,X
 
03253. BEQ PRG000_D045 ; If object is not sinking in quicksand, jump to PRG000_D045
 
03254.  
03255. INC Objects_QSandCtr,X ; Objects_QSandCtr++
 
03256.  
03257. CMP #$90
 
03258. BNE PRG000_D02E ; If Objects_QSandCtr <> $90, jump to PRG000_D02E
 
03259.  
03260. ; Otherwise, object has sunk long enough; delete it...
 
03261. JMP Object_Delete ; Jump to Object_Delete
 
03262.  
03263. PRG000_D02E:
 
03264.  
03265. ; Slow object descent
 
03266. LDA #$04
 
03267. STA <Objects_YVel,X
 
03268.  
03269. JSR Object_ApplyYVel_NoLimit ; Apply Y velocity
 
03270.  
03271. ; Set sprite priority
 
03272. LDA Objects_FlipBits,X
 
03273. ORA #SPR_BEHINDBG
 
03274. STA Objects_FlipBits,X
 
03275.  
03276. CPX #$05
 
03277. BLT PRG000_D044 ; If object index < 5 (object is a "general" object), jump to PRG000_D044 (RTS)
 
03278.  
03279. JMP Object_HitTestRespond ; Special object, do hit test/respond
 
03280.  
03281. PRG000_D044:
 
03282. RTS ; Return
 
03283.  
03284. PRG000_D045:
 
03285.  
03286. ; Dead object, not sinking in quicksand
 
03287.  
03288. ; Vertically flip
 
03289. LDA Objects_FlipBits,X
 
03290. ORA #SPR_VFLIP
 
03291. STA Objects_FlipBits,X
 
03292.  
03293. Object_MoveNotHalted:
 
03294. LDA <Player_HaltGame
 
03295. BNE PRG000_D054 ; If gameplay halted, jump to PRG000_D054 (RTS)
 
03296.  
03297. JSR Object_Move ; Perform standard object movements
 
03298.  
03299. PRG000_D054:
 
03300. RTS ; Return
 
03301.  
03302.  
03303. ; If killed object falls too low, delete it
 
03304. Object_FallAndDelete:
 
03305. LDA Level_7Vertical
 
03306. BEQ PRG000_D060 ; If level is NOT vertical, jump to PRG000_D060
 
03307.  
03308. ; In vertical level...
 
03309.  
03310. LDA <Objects_SpriteY,X
 
03311. CMP #200
 
03312. BLT PRG000_D054 ; If object Y < 200, jump to PRG000_D054 (RTS)
 
03313.  
03314. PRG000_D060:
 
03315. LDA <Objects_YHi,X
 
03316. CMP #$02
 
03317. BLS PRG000_D054 ; If object Y Hi < 2 (way low), jump to PRG000_D054
 
03318.  
03319. ; Do NOT return to caller!
 
03320. PLA
 
03321. PLA
 
03322.  
03323. PRG000_D068:
 
03324. JMP Object_SetDeadEmpty ; Jump to Object_SetDeadEmpty
 
03325.  
03326. ObjState_Squashed:
 
03327. LDA Objects_Timer3,X
 
03328. BEQ PRG000_D090 ; If timer 3 is expired, jump to PRG000_D090
 
03329.  
03330. JSR Object_Move ; Perform standard object movements
 
03331.  
03332. LDA <Objects_DetStat,X
 
03333. AND #$04
 
03334. BEQ PRG000_D07E ; If object did NOT hit ground, jump to PRG000_D07E
 
03335.  
03336. JSR Object_HitGround ; Align to ground
 
03337. STA <Objects_XVel,X ; Clear X velocity
 
03338.  
03339. PRG000_D07E:
 
03340.  
03341. ; Set object frame to 3
 
03342. LDA #$03
 
03343. STA Objects_Frame,X
 
03344.  
03345. LDA Level_ObjectID,X
 
03346. CMP #OBJ_GOOMBA
 
03347. BNE PRG000_D08D ; If object is not a goomba, jump to PRG000_D08D (ObjectGroup_PatternSets, i.e. the "giant" enemy alternative)
 
03348.  
03349. JMP Object_ShakeAndDrawMirrored ; Draw goomba as mirrored sprite and don't come back
 
03350.  
03351. PRG000_D08D:
 
03352. JMP ObjectGroup_PatternSets ; Do the giant enemy draw routine and don't come back
 
03353.  
03354. PRG000_D090:
 
03355. JMP Object_SetDeadEmpty ; Jump to Object_SetDeadEmpty (mark object as dead/empty)
 
03356.  
03357. Object_MaxFalls:
 
03358. .byte OBJECT_MAXFALL, OBJECT_MAXFALLINWATER
 
03359.  
03360. ; Gravity of object
 
03361. Object_Gravity:
 
03362. .byte OBJECT_FALLRATE, OBJECT_FALLRATEINWATER
 
03363.  
03364. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
03365. ; Object_Move
 
03366. ;
 
03367. ; Links all code together to move an object with velocity
 
03368. ; including intersecting with the world etc.
 
03369. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
03370. ; $D097
 
03371. Object_Move:
 
03372. LDA <Objects_XVel,X ; Get Object's X velocity
 
03373. PHA ; Save it
 
03374.  
03375. LDY Objects_InWater,X
 
03376. BEQ PRG000_D0A9 ; If object is not in water, jump to PRG000_D0A9
 
03377.  
03378. LDY Objects_State,X
 
03379. CPY #OBJSTATE_NORMAL
 
03380. BEQ PRG000_D0A9 ; If object's state is Normal, jump to PRG000_D0A9
 
03381.  
03382. ; This is basically an pseudo-ASR, a right shift preserving the sign
 
03383. ASL A ; Bit 7 pushed into carry
 
03384. ROR <Objects_XVel,X ; X velocity rotated right (divided by 2) and proper sign of bit 7 in place
 
03385.  
03386. PRG000_D0A9:
 
03387. JSR Object_ApplyXVel ; Applies object's X velocity
 
03388.  
03389. PLA ; Restore Object's X velocity
 
03390.  
03391. STA <Objects_XVel,X ; Undoes Object_ApplyXVel
 
03392.  
03393. JSR Object_ApplyYVel_NoLimit ; Apply Y velocity without limit
 
03394.  
03395. JSR Object_WorldDetect4 ; Detect against the world
 
03396.  
03397. LDY Objects_InWater,X ; Y = whether in-water
 
03398.  
03399. LDA <Objects_YVel,X
 
03400. BPL PRG000_D0CA ; If object is object is still or moving downward, jump to PRG000_D0CA
 
03401.  
03402. ; Object is moving upward...
 
03403.  
03404. CPY #$00
 
03405. BEQ PRG000_D0CA ; If object is NOT in water, jump to PRG000_D0CA
 
03406.  
03407. CMP #OBJECT_MAXWATERUPWARD
 
03408. BGE PRG000_D0CA ; If object's Y velocity is between OBJECT_MAXWATERUPWARD and 0, jump to PRG000_D0CA
 
03409.  
03410. LDA #OBJECT_MAXWATERUPWARD
 
03411. STA <Objects_YVel,X ; Otherwise, cut off velocity at OBJECT_MAXWATERUPWARD
 
03412.  
03413. BNE PRG000_D0CA ; Jump (technically always) to PRG000_D0CA (uhh... pointless, heh)
 
03414.  
03415. PRG000_D0CA:
 
03416. LDA <Objects_YVel,X
 
03417. ADD Object_Gravity,Y
 
03418. STA <Objects_YVel,X ; Apply gravity to object
 
03419.  
03420. BMI PRG000_D0DE ; If Y velocity is negative, jump to PRG000_D0DE (RTS)
 
03421.  
03422. CMP Object_MaxFalls,Y
 
03423. BLT PRG000_D0DE ; If object is not falling at the max rate, jump to PRG000_D0DE (RTS)
 
03424.  
03425. LDA Object_MaxFalls,Y
 
03426. STA <Objects_YVel,X ; Cap fall at max rate
 
03427.  
03428. PRG000_D0DE:
 
03429. RTS ; Return
 
03430.  
03431. ObjectHeld_WakeUpDir: .byte $40, $00
 
03432.  
03433. ; Handle shelled object "waking up" from a shelled state, if timer 3 expired...
 
03434. Object_ShellDoWakeUp:
 
03435.  
03436. ; If object is a Bob-omb, jump to PRG000_D0EC, otherwise jump to PRG000_D101
 
03437. LDA Level_ObjectID,X
 
03438. CMP #OBJ_BOBOMBEXPLODE
 
03439. BEQ PRG000_D0EC
 
03440. CMP #OBJ_BOBOMB
 
03441. BNE PRG000_D101
 
03442.  
03443. PRG000_D0EC:
 
03444.  
03445. ; A Bob-omb only...
 
03446.  
03447. LDA Objects_Timer,X
 
03448. BNE PRG000_D0F9 ; If timer is not expired, jump to PRG000_D0F9
 
03449.  
03450. ; Timer expired, change to state 2 (Normal)
 
03451. LDA #OBJSTATE_NORMAL
 
03452. STA Objects_State,X
 
03453. JMP BobOmb_Explode ; Jump to BobOmb_Explode and don't come back!
 
03454.  
03455. PRG000_D0F9:
 
03456. CMP #$40
 
03457. BGE PRG000_D100 ; If timer ticks >= $40, jump to PRG000_D100 (RTS)
 
03458.  
03459. STA Objects_ColorCycle,X ; In the last timer ticks, flash colors!
 
03460.  
03461. PRG000_D100:
 
03462. RTS ; Return
 
03463.  
03464. PRG000_D101:
 
03465.  
03466. ; Anything besides a Bob-omb...
 
03467.  
03468. CMP #OBJ_ICEBLOCK
 
03469. BNE PRG000_D120 ; If object is NOT an Ice Block, jump to PRG000_D120
 
03470.  
03471. ; Object is an ice block...
 
03472.  
03473. LDA Objects_Timer3,X
 
03474. BNE PRG000_D10D ; If timer 3 is not expired, jump to PRG000_D10D
 
03475.  
03476. ; Timer 3 expired...
 
03477.  
03478. JMP Object_PoofDie ; Jump to Object_PoofDie (Set state to 8 ["Poof" Dying] and set timer)
 
03479.  
03480.  
03481. ; Basically from here to the RTS, color cycle the ice block as it begins to "melt"
 
03482. ; at different rates depending on where the timer is exactly...
 
03483. PRG000_D10D:
 
03484. CMP #$60
 
03485. BGE PRG000_D11C ; If timer 3 ticks >= $60, jump to PRG000_D11C
 
03486.  
03487. CMP #$30
 
03488. BGE PRG000_D11B ; If timer 3 ticks >= $30, jump to PRG000_D11B
 
03489.  
03490. CMP #$10
 
03491. BGE PRG000_D11A ; If timer 3 ticks >= $10, jump to PRG000_D11A
 
03492.  
03493. LSR A
 
03494.  
03495. PRG000_D11A:
 
03496. LSR A
 
03497.  
03498. PRG000_D11B:
 
03499. LSR A
 
03500.  
03501. PRG000_D11C:
 
03502. STA Objects_ColorCycle,X ; Set color cycle value
 
03503.  
03504. RTS ; Return
 
03505.  
03506.  
03507. PRG000_D120:
 
03508.  
03509. ; Object is not a Bob-omb and not an Ice Block...
 
03510.  
03511. LDA Objects_Timer3,X
 
03512. BNE PRG000_D15A ; If timer 3 is not expired, jump to PRG000_D15A (RTS)
 
03513.  
03514. LDA Objects_State,X
 
03515. CMP #OBJSTATE_HELD
 
03516. BNE PRG000_D147 ; If object is not currently being held, jump to PRG000_D147
 
03517.  
03518. ; Object is being held...
 
03519.  
03520. JSR Object_WorldDetectN1
 
03521. LDA <Objects_DetStat,X
 
03522. BEQ PRG000_D147 ; If held object did not impact anything, jump to PRG000_D147
 
03523.  
03524. ; Held object impacted...
 
03525.  
03526. ; Get 100 points
 
03527. LDA #$05
 
03528. JSR Score_PopUp
 
03529.  
03530. ; Set object state to Killed
 
03531. LDA #OBJSTATE_KILLED
 
03532. STA Objects_State,X
 
03533.  
03534. ; Set object Y velocity to -$40 (fly up after death)
 
03535. LDA #-$40
 
03536. STA <Objects_YVel,X
 
03537.  
03538. ; Halt horizontal movement
 
03539. LDA #$00
 
03540. STA <Objects_XVel,X
 
03541.  
03542. BEQ PRG000_D155 ; Jump (technically always) to PRG000_D155
 
03543.  
03544. PRG000_D147:
 
03545.  
03546. ; Held object did NOT impact... (time to wake up!)
 
03547.  
03548. ; Set object state to Normal
 
03549. LDA #OBJSTATE_NORMAL
 
03550. STA Objects_State,X
 
03551.  
03552. ; Have object "wake up" towards Player!
 
03553. JSR Level_ObjCalcXDiffs
 
03554. LDA ObjectHeld_WakeUpDir,Y
 
03555. STA Objects_FlipBits,X
 
03556.  
03557. PRG000_D155:
 
03558.  
03559. ; Do NOT return to caller!
 
03560. PLA
 
03561. PLA
 
03562.  
03563. JMP PRG000_CB5E ; Jump to PRG000_CB5E (essentially JSR Object_DeleteOffScreen)
 
03564.  
03565. PRG000_D15A:
 
03566. RTS ; Return
 
03567.  
03568.  
03569. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
03570. ; Object_AboutFace
 
03571. ;
 
03572. ; Object reverses travel and facing direction
 
03573. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
03574. ; $D15B
 
03575. Object_AboutFace:
 
03576. LDA <Objects_XVel,X
 
03577. JSR Negate
 
03578. STA <Objects_XVel,X ; Negate object's X velocity
 
03579.  
03580. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
03581. ; Object_FlipFace
 
03582. ;
 
03583. ; Object reverses facing direction
 
03584. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
03585. ; $D162
 
03586. Object_FlipFace:
 
03587. LDA Objects_FlipBits,X
 
03588. EOR #SPR_HFLIP
 
03589. STA Objects_FlipBits,X ; Flip left/right flag
 
03590.  
03591. RTS ; Return
 
03592.  
03593. PRG000_D16B: .byte -$08, $08
 
03594.  
03595.  
03596. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
03597. ; Object_HandleBumpUnderneath
 
03598. ;
 
03599. ; Handles an object getting killed or shelled when hit from under
 
03600. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
03601. ; $D16D
 
03602. Object_HandleBumpUnderneath:
 
03603. JSR Object_AnySprOffscreen
 
03604. BNE PRG000_D1C4 ; If any sprite is off-screen, jump to PRG000_D1C4 (RTS)
 
03605.  
03606. LDA Object_TileFeet2
 
03607. CMP #TILEA_BLOCKBUMP_CLEAR
 
03608. BNE Player_HitEnemy ; If object did not detect a block bump clear tile, jump to Player_HitEnemy
 
03609.  
03610. ; Object detected a block bump tile (object got bumped)
 
03611.  
03612. ; Set Y Vel to -$30 (bounce dead)
 
03613. LDA #-$30
 
03614. STA <Objects_YVel,X
 
03615.  
03616. JSR Level_ObjCalcXDiffs ; Detect which side object is on versus Player
 
03617.  
03618. ; Store proper X velocity
 
03619. LDA PRG000_D16B,Y
 
03620. STA <Objects_XVel,X
 
03621.  
03622. ; Vertically flip object
 
03623. LDA #SPR_VFLIP
 
03624. STA Objects_FlipBits,X
 
03625.  
03626. LDY ObjGroupRel_Idx
 
03627. LDA ObjectGroup_Attributes3,Y
 
03628. AND #OA3_DIESHELLED
 
03629. BNE PRG000_D19E ; If OA3_DIESHELLED is SET (object may use special routine), jump to PRG000_D19E
 
03630.  
03631. ; Object killed, get 100 pts
 
03632.  
03633. LDA #OBJSTATE_KILLED
 
03634. STA Objects_State,X
 
03635.  
03636. LDA #$00
 
03637. JMP Score_Get100PlusPts ; Jump to Score_Get100PlusPts and don't come back!
 
03638.  
03639. PRG000_D19E:
 
03640. LDA ObjGroupRel_Idx
 
03641. ASL A
 
03642. TAY ; Y = 2-byte index into CollideJumpTable
 
03643.  
03644.  
03645. LDA ObjectGroup_CollideJumpTable+1,Y ; Get the CollideJumpTable upper byte
 
03646. AND #%11111000
 
03647. CMP #%00001000
 
03648. BNE PRG000_D1B7 ; If the upper byte is not ($08xx - $0Fxx), jump to PRG000_D1B7
 
03649.  
03650. ; SPECIAL JUMP TABLE VALUE ($08xx - $0Fxx): Change to alternate object
 
03651.  
03652. ; Change to alternate ObjectID in low byte
 
03653. LDA ObjectGroup_CollideJumpTable,Y
 
03654. STA Level_ObjectID,X
 
03655.  
03656. ; Get 100 pts
 
03657. LDA #$00
 
03658. JSR Score_Get100PlusPts
 
03659.  
03660. PRG000_D1B7:
 
03661. JMP Object_SetShellState ; Jump to Object_SetShellState ("dies" into shelled state)
 
03662.  
03663. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
03664. ; Player_HitEnemy
 
03665. ;
 
03666. ; General routine for how the object responds to a Player
 
03667. ; colliding with it (good and bad)
 
03668. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
03669. ; $D1BA
 
03670. Player_HitEnemy:
 
03671. JSR Object_HitTest ; Check for collision
 
03672.  
03673. ; Clear hit status bits
 
03674. LDA #$00
 
03675. STA Objects_PlayerHitStat,X
 
03676.  
03677. BCS PRG000_D1C5 ; If collision occurred, jump to PRG000_D1C5
 
03678.  
03679. PRG000_D1C4:
 
03680. RTS ; Return
 
03681.  
03682. PRG000_D1C5:
 
03683. LDA Objects_Timer2,X
 
03684. BNE PRG000_D1C4 ; If timer 2 hasn't expired, jump to PRG000_D1C4 (RTS)
 
03685.  
03686. ; Timer 2 has expired...
 
03687.  
03688. LDA Player_Slide
 
03689. BNE PRG000_D1DB ; If Player is sliding, jump to PRG000_D1DB
 
03690.  
03691. ; Player is not sliding...
 
03692.  
03693. LDY ObjGroupRel_Idx ; Y = object group relative index
 
03694. LDA ObjectGroup_Attributes2,Y ; Get attributes set 2
 
03695. AND #OA2_GNDPLAYERMOD
 
03696. BEQ PRG000_D218 ; If OA2_GNDPLAYERMOD not set, jump to PRG000_D218
 
03697. BNE PRG000_D205 ; Otherwise, jump to PRG000_D205
 
03698.  
03699. PRG000_D1DB:
 
03700.  
03701. ; Player is sliding...
 
03702.  
03703. JSR PRG000_D218 ; Also include code like attribute set 2 bit 1 is set
 
03704.  
03705. LDA Objects_State,X
 
03706. CMP #OBJSTATE_NORMAL
 
03707. BEQ PRG000_D204 ; If object state is Normal, jump to PRG000_D204 (RTS)
 
03708.  
03709. STA <Temp_Var4 ; Otherwise, store current state into Temp_Var4
 
03710.  
03711. JSR Enemy_Kill ; Kill enemy
 
03712.  
03713. LDA RandomN,X
 
03714. AND #$1f ; Cap 0-31
 
03715. ADC #-$4C
 
03716. STA <Objects_YVel,X ; Object Y Vel = -$2D to -$4C
 
03717.  
03718. ; Set object state to Killed
 
03719. LDA #OBJSTATE_KILLED
 
03720. STA Objects_State,X
 
03721.  
03722. LDA <Player_XVel ; Get Player X velocity
 
03723. STA <Temp_Var1 ; -> Temp_Var1 (yyyy xxxx)
 
03724. ASL <Temp_Var1 ; Shift 1 bit left (bit 7 into carry) (y yyyx xxx0)
 
03725. ROR A ; A is now arithmatically shifted to the right (yyyyy xxx) (signed division by 2)
 
03726. ADD <Objects_XVel,X ; Add the existing velocity to this (so object velocity is influenced by half Player velocity)
 
03727. STA <Objects_XVel,X ; -> Object's X velocity
 
03728.  
03729. PRG000_D204:
 
03730. RTS ; Return
 
03731.  
03732.  
03733. PRG000_D205:
 
03734.  
03735. ; Object attribute set 2 bit 1 is set...
 
03736.  
03737. ; What does this do?
 
03738. ; First off, Player must be on solid ground
 
03739. ; Then, either the object is falling faster than $0A OR the object is on the ground
 
03740. ; In those cases, we jump to Object_HoldKickOrHurtPlayer
 
03741.  
03742. ; The only real apparent function here is that a fast-falling or grounded object
 
03743. ; will force into the "Hold, Kick, or Hurt Player" routine without doing the
 
03744. ; the other checks, but with the Player being on the ground, it's hard for him
 
03745. ; not to get hit anyway. As such, I can't really for sure tell what the
 
03746. ; intention of this code was really supposed to be??
 
03747.  
03748. ; Otherwise it is PRG000_D218
 
03749.  
03750. LDA <Player_InAir
 
03751. BNE PRG000_D218 ; If Player is mid air, jump to PRG000_D218
 
03752.  
03753. ; Player is on solid ground...
 
03754.  
03755. LDA <Objects_YVel,X
 
03756. CMP #$0a
 
03757. BLS PRG000_D212 ; If Object's Y velocity < $0A, jump to PRG000_D212
 
03758. PRG000_D20F:
 
03759. JMP Object_HoldKickOrHurtPlayer ; Otherwise, jump to Object_HoldKickOrHurtPlayer
 
03760.  
03761. PRG000_D212:
 
03762.  
03763. ; Object's Y velocity < $0A ...
 
03764.  
03765. LDA <Objects_DetStat,X
 
03766. AND #$04
 
03767. BNE PRG000_D20F ; If object has hit ground, jump to PRG000_D20F (to Object_HoldKickOrHurtPlayer)
 
03768.  
03769. PRG000_D218:
 
03770.  
03771. ; Object attribute set 2 bit 1 not set...
 
03772. ; OR Player is mid-air...
 
03773. ; OR Player is sliding...
 
03774.  
03775. ; Remember, this is after the bounding boxes have already been used
 
03776. ; to determine there's some kind of collision; we're just find tuning
 
03777. ; if this is a successful "stomp" or not...
 
03778. ;
 
03779. ; 'Y' represents the "height" of the object for collision detection
 
03780. ; The way to think about this is we're going to reference Objects_Y
 
03781. ; which in SMB3 is generally the "top" of the enemy, or in any case
 
03782. ; point at which "stomp" should occur. (Of note, Koopa Troopa's
 
03783. ; "top" is their shell; the head is drawn as a negative coordinate
 
03784. ; from that point.) The judgement is based on Player_Y, which is the
 
03785. ; "top" of the Player (note for "Super" Mario, that's near the hat,
 
03786. ; but for "small" Mario, that's roughly 16 pixels above.)
 
03787. ;
 
03788. ; G = Goomba (for example)
 
03789. ;
 
03790. ; . <-- This would be 19 (for this example) pixels above
 
03791. ; |
 
03792. ; G <-- top of 'Goomba' is Objects_Y
 
03793. ;
 
03794. ; . m <-- Top of Player must be beneath the 19 pixel offset
 
03795. ; | M
 
03796. ; G
 
03797. ;
 
03798. ; ... if the above is true, that's considered "stompable" range.
 
03799.  
03800. LDY #17 ; Y = 17 (the following two objects)
 
03801.  
03802. LDA Level_ObjectID,X
 
03803. CMP #OBJ_PILEDRIVER
 
03804. BEQ PRG000_D22E ; If object is a pile driver microgoomba, jump to PRG000_D22E
 
03805.  
03806. CMP #OBJ_CHEEPCHEEPHOPPER
 
03807. BEQ PRG000_D22E ; If object is a hopping Cheep Cheep jump to PRG000_D22E
 
03808.  
03809. LDY #19 ; Y = 19 (anything else, unless object is giant)
 
03810.  
03811. LDA Objects_IsGiant,X
 
03812. BEQ PRG000_D22E ; If object is not giant, jump to PRG000_D22E
 
03813.  
03814. LDY #8 ; Y = 8 (not the first two, if object is giant set)
 
03815.  
03816. PRG000_D22E:
 
03817. STY <Temp_Var2 ; -> Temp_Var2 (height above object considered "stompable" range)
 
03818.  
03819. LDA <Objects_Y,X ; Get object's Y
 
03820. SUB <Temp_Var2 ; Subtract Temp_Var2 (height above object considered "stompable" range)
 
03821. ROL <Temp_Var1 ; Stores the carry bit into Temp_Var1 bit 0
 
03822. CMP <Player_Y
 
03823.  
03824. PHP ; Save CPU state (the comparison)
 
03825.  
03826. LSR <Temp_Var1 ; Restore the carry bit
 
03827. LDA <Objects_YHi,X
 
03828. SBC #$00 ; Apply the carry bit to the Objects_YHi as needed for the height subtraction
 
03829.  
03830. PLP ; Restore CPU state (the comparison)
 
03831.  
03832. SBC <Player_YHi ; Get the difference against the Player_YHi
 
03833. BMI PRG000_D20F ; If negative (Player_YHi > Objects_YHi, Player is lower), jump to PRG000_D20F (Object_HoldKickOrHurtPlayer)
 
03834.  
03835. LDA <Player_YVel
 
03836. BPL PRG000_D253 ; If Player's Y Velocity >= 0 (stationary or moving downward), jump to PRG000_D253
 
03837.  
03838. ; Player is moving upward...
 
03839.  
03840. LDA Player_FlyTime
 
03841. BNE PRG000_D253 ; If Player is flying, jump to PRG000_D253
 
03842.  
03843. ; Player moving upward, not flying...
 
03844.  
03845. LDA Kill_Tally
 
03846. BEQ PRG000_D20F ; If Player hasn't killed anything yet, jump to PRG000_D20F (Object_HoldKickOrHurtPlayer)
 
03847.  
03848. PRG000_D253:
 
03849.  
03850. ; Player hit from top bit
 
03851. LDA #$01
 
03852. STA Objects_PlayerHitStat,X
 
03853.  
03854. LDA Player_InWater
 
03855. BNE PRG000_D267 ; If Player is in water, jump to PRG000_D267
 
03856.  
03857. LDY ObjGroupRel_Idx ; Y = group relative index
 
03858. LDA ObjectGroup_Attributes3,Y ; Get object's attribute 3 setting
 
03859. AND #OA3_NOTSTOMPABLE
 
03860. BEQ PRG000_D272 ; If OA3_NOTSTOMPABLE NOT set (Object is stompable), jump to PRG000_D272
 
03861.  
03862. PRG000_D267:
 
03863.  
03864. ; Player is in water (can't stomp in water) OR attribute 3 bit 5 is set (can't stomp anyway)...
 
03865.  
03866. LDA Player_Kuribo
 
03867. ORA Player_Statue
 
03868. BNE PRG000_D272 ; If in Kuribo's shoe or transformed into statue, ignore this and jump to PRG000_D272
 
03869.  
03870. JMP PRG000_D355 ; Jump to PRG000_D355 (hurt Player!)
 
03871.  
03872. PRG000_D272:
 
03873.  
03874. ; Enemy got stomped!
 
03875.  
03876. LDY ObjGroupRel_Idx ; Y = group relative index
 
03877. LDA ObjectGroup_Attributes2,Y ; Get object attribute set 2
 
03878. AND #OA2_STOMPDONTCARE
 
03879. BNE PRG000_D2B3 ; If OA2_STOMPDONTCARE is set (object is indifferent about stomping), jump to PRG000_D2B3 (RTS)
 
03880.  
03881. ; Attribute set 2 bit 2 NOT set... (object cares about being stomped)
 
03882.  
03883. LDA Player_Statue
 
03884. ORA Player_Kuribo
 
03885. BEQ PRG000_D29B ; If Player is NOT a statue and NOT in a Kuribo's shoe, jump to PRG000_D29B
 
03886.  
03887. ; Player is a statue or in a Kuribo's shoe...
 
03888.  
03889. JSR PRG000_D2B4 ; Handle stomp!
 
03890.  
03891. LDY ObjGroupRel_Idx ; Y = object group relative index
 
03892. LDA ObjectGroup_Attributes3,Y ; Get attribute set 3
 
03893. AND #OA3_SQUASH
 
03894. BEQ PRG000_D295 ; If OA3_SQUASH NOT set, jump to PRG000_D295 (kill it)
 
03895.  
03896. ; When stomped by statue/Kuribo, if the enemy was going to get squashed anyway
 
03897. ; then go ahead into "shelled" state which redirects to "stomped" state.
 
03898.  
03899. LDA #OBJSTATE_SHELLED ; Otherwise, state is Shelled
 
03900. BNE PRG000_D297 ; Jump (technically always) to PRG000_D297
 
03901.  
03902. PRG000_D295:
 
03903.  
03904. ; When stomped by statue/Kuribo, if the enemy was going to actually going to
 
03905. ; become shelled, kill it instead...
 
03906.  
03907. LDA #OBJSTATE_KILLED ; State is Killed
 
03908.  
03909. PRG000_D297:
 
03910. STA Objects_State,X ; Set appropriate object state
 
03911.  
03912. RTS ; Return
 
03913.  
03914.  
03915. PRG000_D29B:
 
03916.  
03917. ; Player NOT a statue and NOT in a Kuribo's shoe stomp code
 
03918.  
03919. LDA Objects_State,X
 
03920. CMP #OBJSTATE_SHELLED
 
03921. BNE PRG000_D2B4 ; If object state is not shelled, jump to PRG000_D2B4 (typical stomp)
 
03922.  
03923. PRG000_D2A2:
 
03924.  
03925. ; Enemy is in a shell...
 
03926.  
03927. LDA Kill_Tally
 
03928. INC Kill_Tally ; Use Kill_Tally +1
 
03929. JSR Score_Get100PlusPts ; Get points for the kick
 
03930. JSR Player_KickObject ; Player kicks the enemy!
 
03931.  
03932. ; Clear Player kick
 
03933. LDA #$00
 
03934. STA Player_Kick
 
03935.  
03936. PRG000_D2B3:
 
03937. RTS ; Return
 
03938.  
03939.  
03940. PRG000_D2B4:
 
03941.  
03942. ; Set timer 2 to 8
 
03943. LDA #$08
 
03944. STA Objects_Timer2,X
 
03945.  
03946. ; Set Player's Y velocity to -$40 (bounce!)
 
03947. LDA #-$40
 
03948. STA <Player_YVel
 
03949.  
03950. ; Play squish sound
 
03951. LDA Sound_QPlayer
 
03952. ORA #SND_PLAYERSWIM
 
03953. STA Sound_QPlayer
 
03954.  
03955. DEC Objects_HitCount,X ; HitCount--
 
03956. BPL PRG000_D2B3 ; If hits remain, jump to PRG000_D2B3 (RTS)
 
03957.  
03958. LDA ObjGroupRel_Idx ; A = object group relative index
 
03959. ASL A ; Shift left 1 (2 byte index)
 
03960. PHA ; Save this
 
03961.  
03962. TAY ; -> 'Y'
 
03963. LDA ObjectGroup_CollideJumpTable+1,Y ; Get the CollideJumpTable upper byte
 
03964.  
03965. AND #%11110100
 
03966. CMP #%00000100
 
03967. BNE PRG000_D2E1 ; If the upper byte is not ($04xx - $07xx), jump to PRG000_D2E1
 
03968.  
03969. ; SPECIAL JUMP TABLE VALUE ($04xx - $07xx): High scoring
 
03970.  
03971. ; In this case, Kill_Tally will be boosted by 4 (+1) instead of just +1
 
03972. LDA Kill_Tally
 
03973. ADD #$04
 
03974. BNE PRG000_D2E4
 
03975.  
03976. PRG000_D2E1:
 
03977. LDA Kill_Tally ; Otherwise, just get Kill_Tally
 
03978.  
03979. PRG000_D2E4:
 
03980. INC Kill_Tally ; Kill_Tally++
 
03981. JSR Score_Get100PlusPts ; Get proper score award
 
03982.  
03983. PLA ; Restore index into CollideJumpTable
 
03984. TAY ; -> 'Y'
 
03985.  
03986. LDA ObjectGroup_CollideJumpTable+1,Y ; Get the CollideJumpTable upper byte
 
03987. AND #%11111000
 
03988. CMP #%00001000
 
03989. BNE PRG000_D301 ; If the upper byte is not ($08xx - $0Fxx), jump to PRG000_D301
 
03990.  
03991. ; SPECIAL JUMP TABLE VALUE ($08xx - $0Fxx): Change to alternate object
 
03992.  
03993. ; Change to alternate ObjectID in low byte
 
03994. LDA ObjectGroup_CollideJumpTable,Y
 
03995. STA Level_ObjectID,X
 
03996.  
03997. INC Objects_HitCount,X ; Give hit back (restore to zero)
 
03998. JMP PRG000_D31E ; Jump to PRG000_D31E
 
03999.  
04000. PRG000_D301:
 
04001. LDY ObjGroupRel_Idx ; Y = object group relative index
 
04002. LDA ObjectGroup_Attributes2,Y ; Get object attributes set 2
 
04003. AND #OA2_NOSHELLORSQUASH
 
04004. BEQ PRG000_D323 ; If OA2_NOSHELLORSQUASH is NOT set (shelled enemy), jump to PRG000_D323
 
04005.  
04006. ; Cancel the "Squish" sound, use the "kick" sound instead!
 
04007. LDA Sound_QPlayer
 
04008. AND #~SND_PLAYERSWIM
 
04009. ORA #SND_PLAYERKICK
 
04010. STA Sound_QPlayer
 
04011.  
04012. ; Set object state to 6 (killed)
 
04013. LDA #OBJSTATE_KILLED
 
04014. STA Objects_State,X
 
04015.  
04016. ; Halt horizontal movement
 
04017. LDA #$00
 
04018. STA <Objects_XVel,X
 
04019.  
04020. PRG000_D31E:
 
04021. ; Halt vertical movement
 
04022. LDA #$00
 
04023. STA <Objects_YVel,X
 
04024.  
04025. RTS ; Return
 
04026.  
04027. PRG000_D323:
 
04028. INC Objects_HitCount,X ; Give hit back (restore to zero)
 
04029.  
04030. Object_SetShellState:
 
04031. ; Set Objects_State to Shelled
 
04032. LDA #OBJSTATE_SHELLED
 
04033. STA Objects_State,X
 
04034.  
04035. ; Set timer 3 = $FF (wake up timer)
 
04036. LDA #$ff
 
04037. STA Objects_Timer3,X
 
04038.  
04039. RTS ; Return
 
04040.  
04041.  
04042. Object_HoldKickOrHurtPlayer:
 
04043.  
04044. LDA Objects_State,X
 
04045. CMP #OBJSTATE_SHELLED
 
04046. BNE PRG000_D355 ; If object state is not Shelled, jump to PRG000_D355 (hurt Player!)
 
04047.  
04048. LDA Player_Kuribo
 
04049. ORA Player_Statue
 
04050. BEQ PRG000_D343 ; If Player is NOT in Kuribo's shoe and NOT in a statue, jump to PRG000_D343
 
04051. JMP PRG000_D2A2 ; Otherwise, jump to PRG000_D2A2
 
04052.  
04053. PRG000_D343:
 
04054. LDA Player_ISHolding_OLD
 
04055. BNE PRG000_D39F ; If Player WAS holding something, jump to PRG000_D39F (RTS)
 
04056.  
04057. BIT <Pad_Holding
 
04058. BVS PRG000_D34F ; If Player is holding B, jump to PRG000_D34F
 
04059. JMP Player_KickObject ; Kick away the object and don't come back!
 
04060.  
04061. PRG000_D34F:
 
04062.  
04063. ; Keep held object in state 4 (Held)
 
04064. LDA #OBJSTATE_HELD
 
04065. STA Objects_State,X
 
04066.  
04067. RTS ; Return
 
04068.  
04069.  
04070. PRG000_D355:
 
04071.  
04072. ; Player potentially gonna get hurt!
 
04073.  
04074. LDA Player_FlashInv ; If Player is flashing from getting hit recently...
 
04075. ORA Player_Statue ; ... or Player is a statue ...
 
04076. ORA Objects_Timer2,X ; ... or this object's timer2 is not expired ...
 
04077. ORA Player_StarInv ; ... or Player is invincible by Star Man ...
 
04078. BNE PRG000_D39F ; ... then jump to PRG000_D39F (RTS)
 
04079.  
04080. LDA Objects_State,X
 
04081. CMP #OBJSTATE_KICKED
 
04082. BNE PRG000_D382 ; If object's state is not Kicked, jump to PRG000_D382
 
04083.  
04084. LDY #$00 ; Y = 0
 
04085.  
04086. LDA <Player_XVel
 
04087. BEQ PRG000_D382 ; If Player is not moving horizontally, jump to PRG000_D382
 
04088. BPL PRG000_D373 ; If Player is moving to the right, jump to PRG000_D373
 
04089.  
04090. INY ; Otherwise, Y = 1
 
04091.  
04092. PRG000_D373:
 
04093. STY <Temp_Var1 ; Temp_Var1 = 0 (Player moving left) or 1 (Player moving right)
 
04094.  
04095. EOR <Objects_XVel,X ; Check for X velocity sign difference between Player and object
 
04096. BMI PRG000_D382 ; If there's a difference in sign, jump to PRG000_D382
 
04097.  
04098. ; Object and Player are moving in the same horizontal direction...
 
04099.  
04100. JSR Level_ObjCalcXDiffs
 
04101. CPY <Temp_Var1
 
04102. BNE PRG000_D39F ; If Player is moving away from object, jump to PRG000_D39F
 
04103. BEQ PRG000_D39C ; Otherwise, jump to PRG000_D39C
 
04104.  
04105. PRG000_D382:
 
04106. LDY Level_ObjectID,X ; Y = object's ID
 
04107.  
04108. LDA Object_AttrFlags,Y
 
04109. AND #OAT_BOUNCEOFFOTHERS
 
04110. BEQ PRG000_D39C ; If OAT_BOUNCEOFFOTHERS is NOT set (turn around when hit), jump to PRG000_D39C
 
04111.  
04112. JSR Level_ObjCalcXDiffs
 
04113.  
04114. LDA Objects_FlipBits,X
 
04115. AND #~SPR_HFLIP ; Clear horizontal flip
 
04116. DEY
 
04117. BEQ PRG000_D399
 
04118. ORA #SPR_HFLIP ; Set horizontal flip
 
04119. PRG000_D399:
 
04120. STA Objects_FlipBits,X ; Update object flip bits as necessary
 
04121.  
04122. PRG000_D39C:
 
04123. JMP Player_GetHurt ; Hurt Player and don't come back!
 
04124.  
04125. PRG000_D39F:
 
04126. RTS ; Return
 
04127.  
04128. ; A very popular RTS @ $D3A0
 
04129. ObjState_DeadEmpty:
 
04130. ObjInit_DoNothing:
 
04131. ObjNorm_DoNothing:
 
04132. ObjHit_DoNothing:
 
04133. ObjHalt_DoNothing:
 
04134. LevelEvent_DoNothing:
 
04135. RTS ; Return
 
04136.  
04137. ; Called for an object in state 1 to perform initialization logic
 
04138. ObjState_Initializing:
 
04139. JSR Level_PrepareNewObject ; Prepare the object
 
04140.  
04141. INC Objects_State,X ; Set object state to 2 (Normal run)
 
04142. JSR Object_SetPaletteFromAttr ; Set object's palette
 
04143.  
04144. LDA ObjGroupRel_Idx ; Get object's group relative index
 
04145. ASL A ; Shift left 1 (2 byte index)
 
04146. TAY ; -> Y
 
04147.  
04148. ; Get jump address specific to this object
 
04149. LDA ObjectGroup_InitJumpTable,Y
 
04150. STA <Temp_Var1
 
04151. LDA ObjectGroup_InitJumpTable+1,Y
 
04152. STA <Temp_Var2
 
04153. JMP [Temp_Var1] ; Dynamically jump to object's init routine
 
04154.  
04155. ; Set object's palette value
 
04156. ; $D3BC
 
04157. Object_SetPaletteFromAttr:
 
04158. LDY ObjGroupRel_Idx ; Y = object's relative group index
 
04159. LDA ObjectGroup_Attributes,Y ; Get attributes
 
04160. AND #OA1_PALMASK ; Keep only bits 0 and 1 (palette)
 
04161. STA Objects_SprAttr,X ; Set this object's palette
 
04162. RTS ; Return
 
04163.  
04164.  
04165. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04166. ; Object_DeleteOffScreen
 
04167. ;
 
04168. ; The routine that removes objects if they go off-screen
 
04169. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04170. ; Vertical level
 
04171. PRG000_D3C8: .byte $40, $B0 ; Lo
 
04172. PRG000_D3CA: .byte $01, $FF ; Hi
 
04173.  
04174. ; Non-vertical level -- selectable remove sizes
 
04175. PRG000_D3CC: .byte $20, $D0, $80, $80, $40, $B0 ; Lo
 
04176. PRG000_D3D2: .byte $01, $FF, $01, $FF, $01, $FF ; Hi
 
04177.  
04178. ; The different "N" varieties specify how wide before the deletion occurs
 
04179.  
04180. ; $D3D8
 
04181. Object_DeleteOffScreen_N4:
 
04182. LDA #$04 ; A = 4
 
04183. BNE PRG000_D3EF ; Jump (technically always) to PRG000_D3EF
 
04184.  
04185. ; $D3DC
 
04186. Object_DeleteOffScreen_N2:
 
04187. LDA #$02 ; A = 2
 
04188. BNE PRG000_D3EF ; Jump (technically always) to PRG000_D3EF
 
04189.  
04190. ; $D3E0
 
04191. Object_DeleteOffScreen:
 
04192. LDA Objects_UseShortHTest,X
 
04193. BEQ PRG000_D3ED ; If object wants to use "short" horizontal test, jump to PRG000_D3ED
 
04194.  
04195. LDA Objects_SprHVis,X
 
04196. BNE Object_DeleteOffScreen_N2 ; If any sprites are horizontally off-screen, jump to Object_DeleteOffScreen_N2
 
04197.  
04198. STA Objects_UseShortHTest,X ; Clear Objects_UseShortHTest
 
04199.  
04200. PRG000_D3ED:
 
04201. LDA #$00 ; A = 0
 
04202.  
04203. PRG000_D3EF:
 
04204. STA <Temp_Var1 ; Temp_Var1 = 0, 2, or 4
 
04205.  
04206. JSR Object_AnySprOffscreen
 
04207. BEQ PRG000_D463 ; If any sprites are off-screen, jump to PRG000_D463
 
04208.  
04209. LDA Level_7Vertical
 
04210. BNE PRG000_D464 ; If level is vertical, jump to PRG000_D464
 
04211.  
04212.  
04213. ; LEVEL NOT VERTICAL
 
04214.  
04215. LDA <Objects_YHi,X
 
04216. CMP #$02
 
04217. BPL Object_Delete ; If object Y Hi >= 2 (way off screen), jump to Object_Delete
 
04218.  
04219. ; Semi-randomly jump to PRG000_D463 (RTS)
 
04220. ; That is, only occasionally actually do the off-screen check
 
04221. ; Keeps down on CPU cycles spent wondering about the object
 
04222. TXA
 
04223. ADD <Counter_1
 
04224. LSR A ; A = (object index + Counter_1) >> 1
 
04225. BCS PRG000_D463 ; If carry set, jump to PRG000_D463 (RTS)
 
04226.  
04227. AND #$01
 
04228. STA <Temp_Var2 ; Temp_Var2 stores bit 0 from above; thus 0 or 1
 
04229.  
04230. ADC <Temp_Var1 ; So value is now 0-5
 
04231. TAY ; -> 'Y'
 
04232.  
04233. LDA <Horz_Scroll
 
04234. ADD PRG000_D3CC,Y ; Horizontal scroll plus offset
 
04235.  
04236. ROL <Temp_Var1 ; Temp_Var1 is 0/1, 4/5
 
04237.  
04238. CMP <Objects_X,X ; Compare to object X
 
04239. PHP ; Save CPU state
 
04240.  
04241. LDA <Horz_Scroll_Hi
 
04242. LSR <Temp_Var1
 
04243. ADC PRG000_D3D2,Y ; Add high part of offset
 
04244.  
04245. PLP ; Restore CPU state
 
04246.  
04247. SBC <Objects_XHi,X
 
04248. STA <Temp_Var1 ; Temp_Var1 is X Hi difference
 
04249.  
04250. LDY <Temp_Var2 ; Y = Temp_Var2
 
04251. BEQ PRG000_D42E ; If zero, jump to PRG000_D42E
 
04252.  
04253. EOR #$80
 
04254. STA <Temp_Var1 ; Temp_Var1 ^= $80
 
04255.  
04256. PRG000_D42E:
 
04257. LDA <Temp_Var1
 
04258. BPL PRG000_D463 ; If positive, jump to PRG000_D463 (RTS)
 
04259.  
04260. ; Deletes object, marks it so it will reappear next time it comes on-screen
 
04261. Object_Delete:
 
04262. LDA Level_ObjectID,X
 
04263.  
04264. ; If object ID is OBJ_FIRECHOMP, OBJ_CHAINCHOMPFREE, OBJ_BLOOPERCHILDSHOOT,
 
04265. ; OBJ_BLOOPERWITHKIDS, or OBJ_FIRESNAKE, jump to PRG000_D449
 
04266. ; These objects are hardcoded to release their X/Y Buffer allocations!
 
04267. CMP #OBJ_FIRECHOMP
 
04268. BEQ PRG000_D449
 
04269.  
04270. CMP #OBJ_CHAINCHOMPFREE
 
04271. BEQ PRG000_D449
 
04272.  
04273. CMP #OBJ_BLOOPERCHILDSHOOT
 
04274. BEQ PRG000_D449
 
04275.  
04276. CMP #OBJ_BLOOPERWITHKIDS
 
04277. BEQ PRG000_D449
 
04278.  
04279. CMP #OBJ_FIRESNAKE
 
04280. BNE Object_SetDeadAndNotSpawned
 
04281.  
04282. PRG000_D449:
 
04283.  
04284. ; One of the above five objects ONLY!
 
04285.  
04286. LDY Objects_Var6,X ; Y = Var6 (should be 0 or 1, the buffer slot the object occupies)
 
04287.  
04288. ; Clear the occupation of the X/Y Buffer
 
04289. LDA #$00
 
04290. STA Buffer_Occupied,Y
 
04291.  
04292. Object_SetDeadAndNotSpawned:
 
04293. LDY Objects_SpawnIdx,X ; Get the spawn index of this object
 
04294. BMI Object_SetDeadEmpty ; If object is spawned, jump to Object_SetDeadEmpty
 
04295.  
04296. ; Clear object spawn flag
 
04297. LDA Level_ObjectsSpawned,Y
 
04298. AND #$7f
 
04299. STA Level_ObjectsSpawned,Y
 
04300.  
04301. Object_SetDeadEmpty:
 
04302. ; Mark object as dead/empty
 
04303. LDA #OBJSTATE_DEADEMPTY
 
04304. STA Objects_State,X
 
04305.  
04306. PRG000_D463:
 
04307. RTS ; Return
 
04308.  
04309.  
04310. PRG000_D464:
 
04311. ; LEVEL IS VERTICAL
 
04312.  
04313. LDA <Counter_1
 
04314. LSR A
 
04315. BCS PRG000_D463 ; Every other tick, jump to PRG000_D463 (RTS)
 
04316.  
04317. AND #$01
 
04318. STA <Temp_Var2 ; Temp_Var2 = 0 or 1
 
04319. TAY ; -> 'Y'
 
04320.  
04321. LDA Level_VertScroll
 
04322. ADD PRG000_D3C8,Y
 
04323. ROL <Temp_Var1 ; 0/1 or 4/5
 
04324.  
04325. CMP <Objects_Y,X ; Compare to object Y
 
04326.  
04327. PRG000_D479:
 
04328. PHP ; Save CPU state
 
04329.  
04330. LDA Level_VertScrollH
 
04331. LSR <Temp_Var1
 
04332. ADC PRG000_D3CA,Y
 
04333.  
04334. PLP ; Restore CPU state
 
04335.  
04336. SBC <Objects_YHi,X
 
04337. STA <Temp_Var1
 
04338. LDY <Temp_Var2
 
04339. BEQ PRG000_D48F
 
04340.  
04341. EOR #$80
 
04342. STA <Temp_Var1
 
04343.  
04344. PRG000_D48F:
 
04345. LDA <Temp_Var1
 
04346. BPL PRG000_D463
 
04347. BMI Object_Delete
 
04348. BPL PRG000_D497
 
04349.  
04350. PRG000_D497:
 
04351. BEQ PRG000_D479
 
04352.  
04353.  
04354. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04355. ; Level_PrepareNewObject
 
04356. ;
 
04357. ; Prepares a new object by initializing all of the many object
 
04358. ; variables to zero...
 
04359. ;
 
04360. ; X = index of on-screen object
 
04361. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04362. ; $D499
 
04363. Level_PrepareNewObject:
 
04364.  
04365. ; Clear various object variables
 
04366. LDA #$00
 
04367. STA Objects_Var1,X
 
04368. STA Objects_Var2,X
 
04369. STA <Objects_SpriteX,X
 
04370. STA Objects_Timer,X
 
04371. STA Objects_Timer2,X
 
04372. STA <Objects_XVel,X
 
04373. STA <Objects_YVel,X
 
04374. STA Objects_FlipBits,X
 
04375. STA Objects_Frame,X
 
04376. STA Objects_ColorCycle,X
 
04377. STA <Objects_DetStat,X
 
04378.  
04379. CPX #$06
 
04380. BGE PRG000_D4C8 ; If using slot index >= 6, jump to PRG000_D4C8 (skip variables available only to slots 0 to 5)
 
04381.  
04382. ; Clear some more variables (object slots 0 to 5 ONLY)
 
04383. STA Objects_DisPatChng,X
 
04384. STA ObjSplash_DisTimer,X
 
04385. STA Objects_QSandCtr,X
 
04386. STA Objects_InWater,X
 
04387.  
04388. PRG000_D4C8:
 
04389. CPX #$05
 
04390. BGE PRG000_D506 ; If using slot index >= 5, jump to PRG000_D506 (skip variables available only to slots 0 to 4)
 
04391.  
04392. ; Clear even more variables (object slots 0 to 4 [major objects] ONLY!!)
 
04393. STA Objects_PlayerHitStat,X
 
04394. STA Objects_Timer4,X
 
04395. STA Objects_Timer3,X
 
04396. STA Objects_Slope,X
 
04397. STA Objects_Var7,X
 
04398. STA <Objects_Var5,X
 
04399. STA <Objects_Var4,X
 
04400. STA Objects_Var3,X
 
04401. STA Objects_Var6,X
 
04402. STA Objects_TargetingXVal,X
 
04403. STA Objects_TargetingYVal,X
 
04404. STA Objects_IsGiant,X
 
04405. STA Objects_UseShortHTest,X
 
04406. STA Objects_HitCount,X
 
04407. STA Objects_DisPatChng,X
 
04408. STA Objects_Var10,X
 
04409. STA Objects_Var11,X
 
04410. STA Objects_Var12,X
 
04411. STA Objects_Var13,X
 
04412. STA Objects_Var14,X
 
04413.  
04414. PRG000_D506:
 
04415. RTS ; Return
 
04416.  
04417.  
04418. ; Called for an object in state 2 to do its "normal" routine
 
04419. ObjState_Normal:
 
04420. LDA <Player_HaltGame
 
04421. BEQ Object_DoNormal ; If gameplay is NOT halted by the Player, jump to Object_DoNormal
 
04422.  
04423. JMP Object_DoHaltedAction ; Jump to Object_DoHaltedAction
 
04424.  
04425. Object_DoNormal:
 
04426. LDA ObjGroupRel_Idx
 
04427. ASL A
 
04428. TAY ; Y = object's group relative index * 2 (2 byte index for jump table)
 
04429.  
04430. ; Get jump address specific to this object
 
04431. LDA ObjectGroup_NormalJumpTable,Y
 
04432. STA <Temp_Var1
 
04433. LDA ObjectGroup_NormalJumpTable+1,Y
 
04434. STA <Temp_Var2
 
04435. JMP [Temp_Var1] ; Dynamically jump to object's "normal" routine
 
04436.  
04437.  
04438. Object_DoHaltedAction:
 
04439.  
04440. ; Gameplay is halted, determine what needs to happen with this object...
 
04441.  
04442. LDY ObjGroupRel_Idx ; Y = group relative index
 
04443.  
04444. LDA ObjectGroup_Attributes3,Y ; Get attribute set 3 bits
 
04445. AND #OA3_HALT_MASK ; Keep only the lowest 4
 
04446. JSR DynJump
 
04447.  
04448. ; WARNING: Read comment; some of these are specific to object banks!
 
04449.  
04450. ; THESE MUST FOLLOW DynJump FOR THE DYNAMIC JUMP TO WORK!!
 
04451. .word Bank2_HotFootHaltAction ; 0: Bank2/Hotfoot ONLY
 
04452. .word Object_ShakeAndDraw ; 1: Standard draw
 
04453. .word Object_Draw16x32Sprite ; 2: Draw tall sprite
 
04454. .word Bank2_SpikeHaltAction ; 3: Bank2/Spike ONLY
 
04455. .word ObjHalt_DoNothing ; 4: Do nothing
 
04456. .word ObjHalt_DoNothingNotNormal ; 5: If object is in "normal" state, do its normal routine, otherwise do nothing (COMMON)
 
04457. .word Object_DrawWide ; 6: Draw wide sprite
 
04458. .word ObjHalt_DoNothing ; 7: Do nothing
 
04459. .word Shoe_DrawGoomba ; 8: Bank2/Kuribo's Shoe ONLY
 
04460. .word ObjHalt_DoNothing ; 9: Do nothing
 
04461. .word Object_ShakeAndDrawMirrored ; 10: Draw mirrored sprite
 
04462. .word EndLevelCard_Draw ; 11: Bank2/End Level Card ONLY
 
04463. .word ObjHalt_DoNothing ; 12: Do nothing
 
04464. .word Buster_DrawHoldingIceBrick ; 13: Bank2/Buster Beatle ONLY
 
04465. .word Bank2_PiranhaSpikeHaltAction ; 14: Bank2/Piranha Spike Ball ONLY
 
04466.  
04467. ObjHalt_DoNothingNotNormal:
 
04468. LDA Objects_State,X
 
04469. CMP #OBJSTATE_NORMAL
 
04470. BNE PRG000_D553 ; If object's state is not Normal, jump to PRG000_D553
 
04471.  
04472. JMP Object_DoNormal ; Otherwise, jump to Object_DoNormal (jump into object's "Normal" routine)
 
04473.  
04474. PRG000_D553:
 
04475. RTS ; Return
 
04476.  
04477.  
04478. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04479. ; Object_CalcSpriteXY_NoHi
 
04480. ;
 
04481. ; Calculate SpriteX/Y without considering the "High" parts
 
04482. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04483. ; $D554
 
04484. Object_CalcSpriteXY_NoHi:
 
04485. LDA <Objects_Y,X
 
04486. SUB Level_VertScroll
 
04487. STA <Objects_SpriteY,X
 
04488.  
04489. LDA <Objects_X,X
 
04490. SUB <Horz_Scroll
 
04491. STA <Objects_SpriteX,X
 
04492.  
04493. RTS ; Return
 
04494.  
04495.  
04496. ; $D564
 
04497. Fish_FixedY_ExceptHitFloor:
 
04498. LDA <Objects_DetStat,X
 
04499. AND #$04
 
04500. BNE PRG000_D588 ; If object has hit floor, jump to PRG000_D588
 
04501.  
04502. ; $D56A
 
04503. Fish_FixedYIfAppro:
 
04504. LDA Level_AScrlConfig
 
04505. BEQ PRG000_D588 ; If no auto scroll effect active (assuming fixed height water level), jump to PRG000_D588 (RTS)
 
04506.  
04507. LDA Level_FreeVertScroll
 
04508. CMP #$01
 
04509. BEQ PRG000_D588 ; If this level has free vertical scrolling, jump to PRG000_D588
 
04510.  
04511. LDY #$00 ; Y = 0 (16-bit carry)
 
04512.  
04513. LDA Level_ScrollDiffV
 
04514. BPL PRG000_D57E ; If desired vertical scroll is not negative, jump to PRG000_D57E
 
04515.  
04516. DEY ; Y = $FF (16-bit carry)
 
04517.  
04518. PRG000_D57E:
 
04519.  
04520. ; In fixed-height, locked scrolling water levels, Big Bertha's
 
04521. ; Object_Y position offsets from the scroll position
 
04522. ADD <Objects_Y,X
 
04523. STA <Objects_Y,X
 
04524. TYA
 
04525. ADC <Objects_YHi,X
 
04526. STA <Objects_YHi,X
 
04527.  
04528. PRG000_D588:
 
04529. RTS ; Return
 
04530.  
04531.  
04532. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04533. ; Object_ShakeAndCalcSprite
 
04534. ;
 
04535. ; The routine for a held object to "shake awake" (shelled enemies)
 
04536. ; and calculates sprite related info
 
04537. ;
 
04538. ; X = index of on-screen object
 
04539. ;
 
04540. ; Returns lots of stuff:
 
04541. ; Temp_Var1 = Object sprite Y
 
04542. ; Temp_Var2 = Object sprite X
 
04543. ; Temp_Var3 = Object's LR flag
 
04544. ; Temp_Var4 = Object's attributes
 
04545. ; Temp_Var5 = Objects_SprVVis
 
04546. ; Temp_Var6 = Object's starting tiles index (and -> 'X')
 
04547. ; Temp_Var7 = Object's Sprite_RAM offset (and -> 'Y')
 
04548. ; Temp_Var8 = Objects_SprHVis
 
04549. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04550. ; $D589
 
04551. Object_ShakeAndCalcSprite:
 
04552. LDA <Objects_Y,X ; Get object's Y
 
04553. SUB Level_VertScroll ; Make relative
 
04554. STA <Objects_SpriteY,X ; Store as sprite Y
 
04555. STA <Temp_Var1 ; Also -> Temp_Var1
 
04556.  
04557. ; This is the object "shakin' awake" routine! (Enemies in shell etc.)
 
04558.  
04559. SEC ; Set carry (remember, this is the default for not applying carry to subtraction)
 
04560.  
04561. LDA Objects_Timer4,X
 
04562. BEQ PRG000_D5A0 ; If Timer4 = 0, jump to PRG000_D5A0
 
04563.  
04564. CMP #$40
 
04565. BLT PRG000_D59F ; If Timer4 < $40, jump to PRG000_D59F
 
04566.  
04567. LSR A
 
04568. LSR A
 
04569.  
04570. PRG000_D59F:
 
04571. LSR A ; Shift right 1 (if Timer4 < $40) or 3 (basically applies a carry sort of sporadically for "shakin' awake")
 
04572.  
04573. PRG000_D5A0:
 
04574. LDA <Objects_X,X ; Get object's X
 
04575. SBC <Horz_Scroll ; Make relative
 
04576. STA <Objects_SpriteX,X ; Store as sprite X
 
04577. STA <Temp_Var2 ; Also -> Temp_Var2
 
04578.  
04579. LDA Objects_FlipBits,X
 
04580. STA <Temp_Var3 ; Temp_Var3 = object's LR flag
 
04581.  
04582. LDY ObjGroupRel_Idx ; Y = object's group relative index
 
04583.  
04584. LDA Objects_ColorCycle,X
 
04585. BEQ PRG000_D5BC ; If Objects_ColorCycle = 0, jump to PRG000_D5BC
 
04586.  
04587. DEC Objects_ColorCycle,X ; Objects_ColorCycle--
 
04588. AND #$03
 
04589. BPL PRG000_D5BF ; Jump (technically always) to PRG000_D5BF
 
04590.  
04591. PRG000_D5BC:
 
04592. LDA Objects_SprAttr,X ; Otherwise, just get the normal attributes
 
04593.  
04594. PRG000_D5BF:
 
04595. STA <Temp_Var4 ; Decided attributes -> Temp_Var4
 
04596.  
04597. LDA Objects_SprVVis,X
 
04598. STA <Temp_Var5 ; Temp_Var5 = Objects_SprVVis
 
04599.  
04600. LDA Objects_SprHVis,X
 
04601. STA <Temp_Var8 ; Temp_Var8 = Objects_SprVVis
 
04602.  
04603. ; Each "frame" value moves up two bytes to the next pair
 
04604. LDA Objects_Frame,X
 
04605. ASL A
 
04606. STA <Temp_Var6 ; Temp_Var6 = Objects_Frame << 1
 
04607.  
04608. LDA ObjectGroup_PatternStarts,Y
 
04609. ADD <Temp_Var6
 
04610. STA <Temp_Var6 ; Temp_Var6 += ObjectGroup_PatternStarts[Y] (set base tile index)
 
04611.  
04612. TAX ; -> 'X'
 
04613.  
04614. LDY <SlotIndexBackup ; Y = object slot index
 
04615.  
04616. LDA Object_SprRAM,Y
 
04617. STA <Temp_Var7 ; Temp_Var7 = Object_SprRAM[Y]
 
04618.  
04619. TAY ; -> 'Y'
 
04620.  
04621. RTS ; Return
 
04622.  
04623. PRG000_D5E3:
 
04624. .byte $08, $04, $02, $01
 
04625.  
04626. ; Object "shaking awake" and draw its sprite
 
04627. ; $D5E7
 
04628. Object_ShakeAndDraw:
 
04629. JSR Object_ShakeAndCalcSprite
 
04630. JSR Object_Draw16x16Sprite
 
04631.  
04632. LDX <SlotIndexBackup
 
04633. RTS ; Return
 
04634.  
04635. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04636. ; Object_ShakeAndDrawMirrored
 
04637. ;
 
04638. ; Used to draw 16x16 mirrored object sprites.
 
04639. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04640. ; $D5F0
 
04641. Object_ShakeAndDrawMirrored:
 
04642. JSR Object_ShakeAndDraw ; Draw object and "shake awake"
 
04643.  
04644. ; Keep all attributes except horizontal flip
 
04645. LDA Sprite_RAM+$02,Y
 
04646. AND #%10111111
 
04647. STA Sprite_RAM+$02,Y
 
04648.  
04649. ; Flip opposite sprite
 
04650. ORA #$40
 
04651. STA Sprite_RAM+$06,Y
 
04652.  
04653. RTS ; Return
 
04654.  
04655. ; $D601
 
04656. Object_DrawTallAndHFlip:
 
04657. JSR Object_Draw16x32Sprite ; Draw tall sprite
 
04658.  
04659. ; Reverse sprites
 
04660. LDA Sprite_RAM-$06,Y
 
04661. AND #%10111111
 
04662. STA Sprite_RAM-$06,Y
 
04663.  
04664. STA Sprite_RAM+$02,Y
 
04665. ORA #$40
 
04666. STA Sprite_RAM-$02,Y
 
04667.  
04668. STA Sprite_RAM+$06,Y
 
04669.  
04670. RTS ; Return
 
04671.  
04672.  
04673. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04674. ; Object_Draw16x32Sprite
 
04675. ;
 
04676. ; Used to draw 16x32 object sprites.
 
04677. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04678. ; $D618
 
04679. Object_Draw16x32Sprite:
 
04680. JSR Object_ShakeAndCalcSprite
 
04681.  
04682. LDX <SlotIndexBackup ; X = object slot index
 
04683.  
04684. LDA Objects_Frame,X
 
04685. ASL A
 
04686. ADD <Temp_Var6
 
04687. STA <Temp_Var6 ; Temp_Var6 += object's frame
 
04688. TAX ; -> 'X'
 
04689.  
04690. LDA <Temp_Var3 ; Objects_FlipBits
 
04691. BPL PRG000_D62D ; If Objects_FlipBits bit 7 is NOT set, jump to PRG000_D62D
 
04692.  
04693. ; Otherwise...
 
04694. INX
 
04695. INX ; X += 2
 
04696.  
04697. PRG000_D62D:
 
04698. JSR Object_Draw16x16Sprite ; Draw sprite
 
04699.  
04700. LSR <Temp_Var5 ; Objects_SprVVis
 
04701.  
04702. ; 'Y' += 8 (Sprite RAM 2 sprites over)
 
04703. TYA
 
04704. ADD #$08
 
04705. TAY
 
04706.  
04707. LDX <Temp_Var6 ; X = Temp_Var6 (starting tile)
 
04708.  
04709. LDA <Temp_Var3 ; Objects_FlipBits
 
04710. BMI PRG000_D63F ; If Objects_FlipBits bit 7 set, jump to PRG000_D63F
 
04711.  
04712. ; Otherwise...
 
04713. INX
 
04714. INX ; X += 2
 
04715.  
04716. PRG000_D63F:
 
04717. LDA #16
 
04718. ADD <Temp_Var1 ; Sprite Y
 
04719. STA <Temp_Var1 ; Temp_Var1 += 16
 
04720.  
04721. JSR Object_Draw16x16Sprite ; Draw sprite
 
04722.  
04723. LDX <SlotIndexBackup ; X = object slot index
 
04724.  
04725. RTS ; Return
 
04726.  
04727.  
04728. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04729. ; Object_DrawWide
 
04730. ;
 
04731. ; Draws a wide 48x16 object
 
04732. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04733. Object_DrawWide:
 
04734. JSR Object_ShakeAndCalcSprite
 
04735.  
04736. LDX <SlotIndexBackup ; X = object's slot index
 
04737.  
04738. ; Calculate offset into the ObjectGroup_PatternSets table
 
04739. LDA Objects_Frame,X
 
04740. ADD <Temp_Var6
 
04741. STA <Temp_Var6 ; Temp_Var6 += object's frame
 
04742. TAX ; -> 'X'
 
04743. JSR Object_Draw48x16Sprite ; Draw wide sprite
 
04744.  
04745. LDX <SlotIndexBackup ; X = object's slot index
 
04746. RTS ; Return
 
04747.  
04748. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04749. ; Object_ToggleFrameBySpd
 
04750. ;
 
04751. ; Sets object's frame alternating 0 or 1 at a rate which
 
04752. ; increases in speed (X velocity)
 
04753. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04754. ; $D660
 
04755. Object_ToggleFrameBySpd:
 
04756. LDA <Objects_XVel,X
 
04757. BNE PRG000_D665 ; If object is moving horizontally, jump to PRG000_D665
 
04758.  
04759. ; Otherwise, do nothing
 
04760. RTS ; Return
 
04761.  
04762. PRG000_D665:
 
04763.  
04764. ; Absolute value of X Velocity
 
04765. BPL PRG000_D66A
 
04766. JSR Negate
 
04767. PRG000_D66A:
 
04768.  
04769. AND #$f0
 
04770. LSR A
 
04771. LSR A
 
04772. LSR A
 
04773. LSR A
 
04774. TAY ; Y = "whole" part of X Velocity only
 
04775.  
04776. LDA PRG000_D5E3,Y ; Get masking value
 
04777.  
04778. LDY #$00 ; Y = 0
 
04779.  
04780. AND <Counter_1
 
04781. BEQ PRG000_D67B ; If Counter_1 masked by value is zero, jump to PRG000_D67B
 
04782.  
04783. INY ; Otherwise, Y = 1
 
04784.  
04785. PRG000_D67B:
 
04786. TYA
 
04787. STA Objects_Frame,X ; Set as frame 0 or 1
 
04788. RTS ; Return
 
04789.  
04790.  
04791. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04792. ; Object_Draw16x16Sprite
 
04793. ;
 
04794. ; Used to draw 16x16 object sprites.
 
04795. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04796. ; $D680
 
04797. Object_Draw16x16Sprite:
 
04798. ; Temp_Var1 = Object sprite Y
 
04799. ; Temp_Var2 = Object sprite X
 
04800. ; Temp_Var3 = Object's LR flag
 
04801. ; Temp_Var4 = Object's attributes
 
04802. ; Temp_Var5 = Objects_SprVVis
 
04803. ; Temp_Var6 = Object's starting tiles index (and -> 'X')
 
04804. ; Temp_Var7 = Object's Sprite_RAM offset (and -> 'Y')
 
04805. ; Temp_Var8 = Objects_SprHVis
 
04806.  
04807. LDA <Temp_Var5 ; Check sprite vertical visibility
 
04808. LSR A ; Shift right (checking lowest bit)
 
04809. BCS PRG000_D6C6 ; If this bit is set, this sprite piece is invisible, jump to PRG000_D6C6 (RTS)
 
04810.  
04811. LDA <Temp_Var1 ; Get sprite Y
 
04812.  
04813. BIT <Temp_Var8 ; Testing bit 7 of horizontal sprite visibility
 
04814. BMI PRG000_D68E ; If bit 7 is set (this sprite is horizontally off-screen), jump to PRG000_D68E
 
04815.  
04816. STA Sprite_RAM+$00,Y ; Otherwise, OK to set sprite Y
 
04817.  
04818. PRG000_D68E:
 
04819. BVS PRG000_D693 ; If bit 6 is set, jump to PRG000_D693
 
04820.  
04821. STA Sprite_RAM+$04,Y ; Otherwise, OK set second sprite Y
 
04822.  
04823. PRG000_D693:
 
04824. LDA <Temp_Var2 ; Get sprite X
 
04825. STA Sprite_RAM+$03,Y ; Store into Sprite RAM
 
04826.  
04827. ADD #$08 ; +8 for next sprite over
 
04828. STA Sprite_RAM+$07,Y ; Store into second sprite
 
04829.  
04830. LDA ObjectGroup_PatternSets,X ; Get first sprite pattern index
 
04831. STA Sprite_RAM+$01,Y ; -> Sprite RAM
 
04832.  
04833. LDA ObjectGroup_PatternSets+1,X ; Get second sprite pattern index
 
04834. STA Sprite_RAM+$05,Y ; -> Sprite RAM
 
04835.  
04836. LDA <Temp_Var3
 
04837. ORA <Temp_Var4 ; Joins base attributes to H-flip flag
 
04838. STA Sprite_RAM+$02,Y ; Store into both sprite's attributes
 
04839. STA Sprite_RAM+$06,Y ; Store into both sprite's attributes
 
04840.  
04841. BIT <Temp_Var3
 
04842. BVC PRG000_D6C6 ; If sprite is not horizontally flipped, jump to PRG000_D6C6 (RTS)
 
04843.  
04844. ; If flipped, swap sprite attributes
 
04845. LDA Sprite_RAM+$01,Y
 
04846. PHA
 
04847. LDA Sprite_RAM+$05,Y
 
04848. STA Sprite_RAM+$01,Y
 
04849. PLA
 
04850. STA Sprite_RAM+$05,Y
 
04851.  
04852. PRG000_D6C6:
 
04853. RTS ; Return
 
04854.  
04855.  
04856. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04857. ; Object_Draw48x16Sprite
 
04858. ;
 
04859. ; Used to draw 48x16 object sprites.
 
04860. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04861. ; $D6C7
 
04862. Object_Draw48x16Sprite:
 
04863. LDA <Temp_Var5 ; Check sprite vertical visibility
 
04864. LSR A
 
04865. BCS PRG000_D726 ; If this sprite is off-screen, jump to PRG000_D726 (RTS)
 
04866.  
04867. LDA <Temp_Var8 ; Checking horizontal sprite visibility
 
04868. ASL A ; Left shift flags value
 
04869. STA <Temp_Var10 ; -> Temp_Var10
 
04870.  
04871. LDA <Temp_Var1 ; Sprite Y
 
04872. BCS PRG000_D6D8 ; If sprite is horizontally off-screen, jump to PRG000_D6D8
 
04873.  
04874. STA Sprite_RAM+$00,Y ; Set sprite Y in RAM
 
04875.  
04876. PRG000_D6D8:
 
04877. BIT <Temp_Var10
 
04878. BMI PRG000_D6DF ; If this sprite is off-screen, jump to PRG000_D6DF
 
04879.  
04880. STA Sprite_RAM+$04,Y ; Set sprite Y in RAM
 
04881.  
04882. PRG000_D6DF:
 
04883. BVS PRG000_D6E4 ; If this sprite is off-screen, jump to PRG000_D6E4
 
04884.  
04885. STA Sprite_RAM+$08,Y ; Set sprite Y in RAM
 
04886.  
04887. PRG000_D6E4:
 
04888. LDA <Temp_Var2
 
04889. STA Sprite_RAM+$03,Y ; Set sprite X in RAM
 
04890. ADD #$08
 
04891. STA Sprite_RAM+$07,Y ; Set sprite X in RAM (+8)
 
04892. ADD #$08
 
04893. STA Sprite_RAM+$0B,Y ; Set sprite X in RAM (+16)
 
04894.  
04895. ; Set each of the sprite's patterns
 
04896. LDA ObjectGroup_PatternSets,X
 
04897. STA Sprite_RAM+$01,Y
 
04898. LDA ObjectGroup_PatternSets+1,X
 
04899. STA Sprite_RAM+$05,Y
 
04900. LDA ObjectGroup_PatternSets+2,X
 
04901. STA Sprite_RAM+$09,Y
 
04902.  
04903. ; Set each sprite's attributes
 
04904. LDA <Temp_Var3
 
04905. ORA <Temp_Var4 ; Combine attributes
 
04906. STA Sprite_RAM+$02,Y
 
04907. STA Sprite_RAM+$06,Y
 
04908. STA Sprite_RAM+$0A,Y
 
04909.  
04910. BIT <Temp_Var3
 
04911. BVC PRG000_D6C6 ; If sprite is not horizontally flipped, jump to PRG000_D6C6 (RTS)
 
04912.  
04913. ; Swap end sprites patterns
 
04914. LDA Sprite_RAM+$01,Y
 
04915. PHA
 
04916. LDA Sprite_RAM+$09,Y
 
04917. STA Sprite_RAM+$01,Y
 
04918. PLA
 
04919. STA Sprite_RAM+$09,Y
 
04920.  
04921. PRG000_D726:
 
04922. RTS ; Return
 
04923.
 
04924.  
04925. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04926. ; Object_GetRandNearUnusedSpr
 
04927. ;
 
04928. ; Gets a semi-random "near by" sprite as appropriate for an
 
04929. ; object; it's a "friendly" way of getting an additional sprite
 
04930. ; for an object that's going over the normal limit.
 
04931. ;
 
04932. ; X = index of on-screen object
 
04933. ;
 
04934. ; Returns:
 
04935. ; Temp_Var7 = offset to the blank sprite (also in 'Y')
 
04936. ; Temp_Var8 = 5 or 1
 
04937. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
04938.  
04939. ; Selection table for the 5/1... doesn't seem like the
 
04940. ; values actually mean anything, it just checks > 5?
 
04941. ; Kept in Temp_Var9 anyway...
 
04942. PRG000_D727:
 
04943. .byte $00, $01, $02, $03, $04, $05, $03, $07, $00, $01, $02, $03, $04, $05, $02
 
04944.  
04945. ; $D736
 
04946. Object_GetRandNearUnusedSpr:
 
04947. TXA
 
04948. PHA ; Save object index
 
04949.  
04950. LDY #$07 ; Y = 7
 
04951. PRG000_D73A:
 
04952. STY <Temp_Var7 ; Update Temp_Var7
 
04953.  
04954. LDX <SlotIndexBackup ; X = object slot index
 
04955.  
04956. LDA RandomN,X
 
04957. AND #$07
 
04958. ADD <Temp_Var7
 
04959. TAY ; Y = (Random 0-7) + Temp_Var7
 
04960.  
04961. LDA PRG000_D727,Y
 
04962. TAY
 
04963. STY <Temp_Var9 ; Temp_Var9 = PRG000_D727[Y]
 
04964.  
04965. LDA Objects_State,Y
 
04966. BEQ PRG000_D763 ; If object state = 0 (dead/empty), jump to PRG000_D763
 
04967.  
04968. PRG000_D752:
 
04969. LDY <Temp_Var7 ; Y = Temp_Var7
 
04970. DEY ; Y--
 
04971. BPL PRG000_D73A ; While Y > 0, loop!
 
04972.  
04973. LDX #$20 ; X = $20
 
04974.  
04975. LDA RandomN
 
04976. BPL PRG000_D760 ; 50/50, jump to PRG000_D760
 
04977.  
04978. LDX #$24 ; Otherwise, X = $24
 
04979.  
04980. PRG000_D760:
 
04981. JMP PRG000_D789 ; Jump to PRG000_D789
 
04982.  
04983. PRG000_D763:
 
04984.  
04985. ; Object slot is dead/empty...
 
04986.  
04987. TYA
 
04988. ADD Counter_7to0
 
04989. TAY ; Y = object slot + (0-7)
 
04990.  
04991. LDX SprRamOffsets,Y ; X = Sprite_RAM offset
 
04992.  
04993. LDY #$05 ; Y = 5
 
04994.  
04995. LDA <Temp_Var9
 
04996. CMP #$05
 
04997. BLT PRG000_D776 ; If Temp_Var9 < 5, jump to PRG000_D776
 
04998.  
04999. LDY #$01 ; Y = 1
 
05000.  
05001. PRG000_D776:
 
05002. STY <Temp_Var8 ; Temp_Var8 = 5 or 1
 
05003.  
05004. LDA Sprite_RAM+$00,X
 
05005. CMP #$f8
 
05006. BEQ PRG000_D789 ; If this sprite Y is impossibly low (blank sprite), jump to PRG000_D789
 
05007.  
05008. INX
 
05009. INX
 
05010. INX
 
05011. INX ; X += 4 (next sprite)
 
05012.  
05013. DEY ; Y--
 
05014. BPL PRG000_D776 ; While Y >= 0, loop!
 
05015.  
05016. JMP PRG000_D752 ; Jump to PRG000_D752
 
05017.  
05018. PRG000_D789:
 
05019. STX <Temp_Var7 ; Temp_Var7 = offset to blank sprite
 
05020.  
05021. TXA
 
05022. TAY ; Y = same offset
 
05023.  
05024. PLA
 
05025. TAX ; Restore 'X'
 
05026.  
05027. LDA <Temp_Var8 ; A = 5 or 1
 
05028.  
05029. RTS ; Return
 
05030.  
05031.  
05032. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
05033. ; Object_DetermineHorzVis
 
05034. ; Object_DetermineHorzVisY
 
05035. ;
 
05036. ; Determines how many of each horizontal sprite of an object are
 
05037. ; invisible (off-screen), based on size of object
 
05038. ;
 
05039. ; X = index of on-screen object
 
05040. ; Y = width of object; 0-5 or 8, 16, 24, 32, 40, 48 respectively (Object_DetermineHorzVisY only)
 
05041. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
05042. ; Pixel width minus 8 of objects
 
05043. Object_Widths:
 
05044. .byte 0 ; 0
 
05045. .byte 8 ; 1
 
05046. .byte 16 ; 2
 
05047. .byte 24 ; 3
 
05048. .byte 32 ; 4
 
05049. .byte 40 ; 5
 
05050.  
05051. ; Respective bit to set per width checked
 
05052. Object_WidthFlags:
 
05053. .byte %10000000 ; 0
 
05054. .byte %01000000 ; 1
 
05055. .byte %00100000 ; 2
 
05056. .byte %00010000 ; 3
 
05057. .byte %00001000 ; 4
 
05058. .byte %00000100 ; 5
 
05059.  
05060. ; $D79E
 
05061. Object_DetermineHorzVis:
 
05062. LDY ObjGroupRel_Idx ; Y = object group relative index
 
05063. LDA ObjectGroup_Attributes,Y ; Get object's attributes
 
05064. AND #OA1_WIDTHMASK ; Keep only bits 4-6
 
05065. LSR A
 
05066. LSR A
 
05067. LSR A
 
05068. LSR A ; shift right 4
 
05069. TAY ; Y = Width of object (0-5 or 0, 8, 16, 24, 32, or 40, -8)
 
05070.  
05071. Object_DetermineHorzVisY:
 
05072. LDA Objects_State,X
 
05073. CMP #OBJSTATE_NORMAL
 
05074. BGS PRG000_D7B8 ; If this object's state >= OBJSTATE_NORMAL (not dead or initializing), jump to PRG000_D7B8
 
05075.  
05076. ; If object is dead/empty or initializing, mark all sprites as invisible
 
05077. LDA #%11111100
 
05078. STA Objects_SprHVis,X
 
05079.  
05080. RTS ; Return
 
05081.  
05082. PRG000_D7B8:
 
05083. LDA #$00
 
05084. STA Objects_SprHVis,X ; Clear until determined
 
05085.  
05086. PRG000_D7BD:
 
05087. LDA <Objects_X,X
 
05088. ADD Object_Widths,Y
 
05089. STA <Temp_Var15 ; Temp_Var15 = object's X + ??
 
05090.  
05091. LDA <Objects_XHi,X
 
05092. ADC #$00
 
05093. STA <Temp_Var16 ; Temp_Var16 = Object's X Hi with carry applied
 
05094.  
05095. LDA <Temp_Var15
 
05096. CMP <Horz_Scroll
 
05097. LDA <Temp_Var16
 
05098. SBC <Horz_Scroll_Hi
 
05099. BEQ PRG000_D7DE ; If sprite is not horizontally off-screen, jump to PRG000_D7DE
 
05100.  
05101. ; This sprite is off left/right of screen...
 
05102. LDA Objects_SprHVis,X ; Get appropriate invisibility bit
 
05103. ORA Object_WidthFlags,Y ; OR it
 
05104. STA Objects_SprHVis,X ; Store it
 
05105.  
05106. PRG000_D7DE:
 
05107. DEY ; Y--
 
05108. BPL PRG000_D7BD ; While Y >= 0, loop
 
05109.  
05110. RTS ; Return
 
05111.  
05112.  
05113. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
05114. ; Object_DetermineVertVis
 
05115. ; Object_DetermineVertVisY
 
05116. ;
 
05117. ; Determines how many of each vertical sprite of an object are
 
05118. ; invisible (off-screen), based on size of object
 
05119. ;
 
05120. ; X = index of on-screen object
 
05121. ; Y = height of object; 0-3 or 16, 32, 48, 64 respectively (Object_DetermineVertVisY only)
 
05122. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
05123. ; $D7E2
 
05124. Object_DetermineVertVis:
 
05125. LDY ObjGroupRel_Idx ; Y = object group relative index
 
05126. LDA ObjectGroup_Attributes,Y ; Get object's attributes
 
05127. AND #OA1_HEIGHTMASK ; keep only bits 2 and 3
 
05128. LSR A
 
05129. LSR A ; shift right 2
 
05130. TAY ; Y = size of object (0-3 or 16, 32, 48, 64)
 
05131.  
05132. Object_DetermineVertVisY:
 
05133. LDA #$01
 
05134. STA <Temp_Var3 ; Temp_Var3 = 1
 
05135.  
05136. LDA #$00
 
05137. STA Objects_SprVVis,X ; Clear until determined
 
05138.  
05139. ; Copy object's Y Hi/Lo -> Temp_Var1/2
 
05140. LDA <Objects_YHi,X
 
05141. STA <Temp_Var1
 
05142. LDA <Objects_Y,X
 
05143. STA <Temp_Var2
 
05144.  
05145. PRG000_D7FE:
 
05146.  
05147. ; Add 16 to copy of object's Y (bottom of this sprite)
 
05148. LDA <Temp_Var2
 
05149. ADD #16
 
05150. STA <Temp_Var2
 
05151.  
05152. BCC PRG000_D809 ; If no carry, jump to Objects_SprVVis
 
05153.  
05154. INC <Temp_Var1 ; Otherwise, apply carry
 
05155.  
05156. PRG000_D809:
 
05157. LDA <Temp_Var2
 
05158. SUB Level_VertScroll
 
05159. STA <Temp_Var4 ; Temp_Var4 = screen-relative Y
 
05160.  
05161. LDA <Temp_Var1
 
05162. SBC Level_VertScrollH
 
05163. BNE PRG000_D81E ; If relative position is off-screen, jump to PRG000_D81E
 
05164.  
05165. ; Otherwise...
 
05166. LDA <Temp_Var4
 
05167. CMP #240
 
05168. BLT PRG000_D826 ; If object sprite is higher than 240 (not off bottom of screen), jump to PRG000_D826
 
05169.  
05170. PRG000_D81E:
 
05171.  
05172. ; This sprite is off top/bottom of screen...
 
05173. LDA <Temp_Var3 ; Get current set bit
 
05174. ORA Objects_SprVVis,X
 
05175. STA Objects_SprVVis,X ; Mark this part as invisible
 
05176.  
05177. PRG000_D826:
 
05178. ASL <Temp_Var3 ; Temp_Var3 <<= 1
 
05179. DEY ; Y--
 
05180. BPL PRG000_D7FE ; While Y >= 0, loop!
 
05181.  
05182. PRG000_D82B:
 
05183. RTS ; Return
 
05184.  
05185. ; Defines the "bounding box" around the Player
 
05186. ; Temp_Var1 - upper left of bounding box
 
05187. ; Temp_Var2 - offset to right bounding box (width)
 
05188. ; Temp_Var5 - top of bounding box
 
05189. ; Temp_Var6 - offset to bottom bounding box (height)
 
05190. Player_BoundBox:
 
05191. ; Left Right Bot Top - offsets applied to sprite X/Y
 
05192. .byte 4, 8, 17, 13 ; small/ducking
 
05193. .byte 3, 10, 5, 25 ; otherwise
 
05194.  
05195.  
05196. PRG000_D834:
 
05197. .byte -8, 8
 
05198.
 
05199.  
05200.  
05201. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
05202. ; Object_HitTest
 
05203. ; Object_HitTestRespond
 
05204. ;
 
05205. ; Tests if Player has collided with another object
 
05206. ; If using "Object_HitTestRespond", then if the Player has touched
 
05207. ; the object, it will call appropriate ObjectGroup_CollideJumpTable
 
05208. ; routine after a successful intersection.
 
05209. ;
 
05210. ; In any case, carry is set if there was a collision, or clear
 
05211. ; if the Player did not collide with the object!
 
05212. ;
 
05213. ; X is object's slot
 
05214. ; Y is group relative object index
 
05215. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
05216. ; $D836
 
05217. Object_HitTest:
 
05218. LDA #$01 ; Test only, do NOT perform "collide" routine
 
05219. JMP PRG000_D83D ; Jump to PRG000_D83D
 
05220.  
05221. ; $D83B
 
05222. Object_HitTestRespond:
 
05223. LDA #$00 ; Test and do "collide" routine
 
05224.  
05225. PRG000_D83D:
 
05226. STA <Temp_Var16 ; Temp_Var16 = 0 or 1, depending on entry point
 
05227.  
05228. ; Clear the Player hit status bits
 
05229. LDA Objects_PlayerHitStat,X
 
05230. AND #%11111100
 
05231. STA Objects_PlayerHitStat,X
 
05232.  
05233. CLC ; Carry flag will be used as a result
 
05234.  
05235. LDA <Player_IsDying ; If Player is dying...
 
05236. ORA Player_OffScreen ; ... off-screen ...
 
05237. ORA Player_Behind_En ; ... or behind the scenes ...
 
05238. BNE PRG000_D82B ; ... jump to PRG000_D82B (RTS)
 
05239.  
05240. JSR Object_CalcBoundBox ; Calculate object's bounding box
 
05241.  
05242. LDA <Player_Suit
 
05243. BEQ PRG000_D862 ; If Player is small, jump to PRG000_D862
 
05244.  
05245. LDA #$00 ; A = 0 when small or ducking
 
05246.  
05247. LDY Player_IsDucking
 
05248. BNE PRG000_D862 ; If Player is ducking, jump to PRG000_D862
 
05249.  
05250. LDA #$01 ; A = 1 otherwise
 
05251.  
05252. PRG000_D862:
 
05253. ASL A
 
05254. ASL A ; Multiply by 4
 
05255. TAY ; Y = 0 (small/ducking) or 4 (otherwise)
 
05256.  
05257. ; Calculate upper left of bounding box and lower right offsets of Player
 
05258. LDA <Player_SpriteX
 
05259. ADD Player_BoundBox,Y
 
05260. STA <Temp_Var3
 
05261.  
05262. LDA <Player_SpriteY
 
05263. ADD Player_BoundBox+2,Y
 
05264. STA <Temp_Var7
 
05265.  
05266. LDA Player_BoundBox+1,Y
 
05267. STA <Temp_Var4
 
05268.  
05269. LDA Player_BoundBox+3,Y
 
05270. STA <Temp_Var8
 
05271.  
05272. JSR ObjectObject_Intersect ; Returns carry SET if object and Player intersected
 
05273. BCC PRG000_D82B ; If carry clear, object and Player did not intersect, jump to PRG000_D82B (RTS)
 
05274.  
05275. ; Intersection occurred by 8-bit values that represent "screen relative" positions,
 
05276. ; but this is not a complete check as Player or object may be at different "High/Low"
 
05277. ; positions (full 16-bit coordinate check)
 
05278.  
05279. STA <Temp_Var1 ; Store Player's bounding box top offset -> Temp_Var1
 
05280.  
05281. LDA Level_7Vertical
 
05282. BNE PRG000_D8B1 ; If level is vertical, jump to PRG000_D8B1
 
05283.  
05284. ; Calculate full 16-bit X difference of object -> Temp_Var14/15
 
05285. LDA <Player_X
 
05286. SUB <Objects_X,X
 
05287. STA <Temp_Var15
 
05288.  
05289. LDA <Player_XHi
 
05290. SBC <Objects_XHi,X
 
05291.  
05292. STA <Temp_Var14
 
05293.  
05294. BPL PRG000_D8A9 ; If overall result is positive, jump to PRG000_D8A9
 
05295.  
05296. ; Otherwise, 16-bit negate Temp_Var14/15
 
05297. LDA <Temp_Var15
 
05298. JSR Negate
 
05299. STA <Temp_Var15
 
05300.  
05301. LDA <Temp_Var14
 
05302. EOR #$ff
 
05303. ADC #$00
 
05304. STA <Temp_Var14
 
05305.  
05306. PRG000_D8A9:
 
05307. LDA <Temp_Var14
 
05308. BNE PRG000_D920 ; If Temp_Var14 is not zero, there's a difference in the "High" component of the Player/Object, so no intersect! Jump to PRG000_D920
 
05309.  
05310. LDA <Temp_Var15
 
05311. BMI PRG000_D920 ; If Temp_Var15 is negative, no intersect, jump to PRG000_D920
 
05312.  
05313. PRG000_D8B1:
 
05314.  
05315. ; The above check is not needed on a vertical level...
 
05316. ; no chance of being on horizontally different screens!
 
05317.  
05318. ; Calculate full 16-bit Y difference of object -> Temp_Var14/15
 
05319. LDA <Player_Y
 
05320. SUB <Objects_Y,X
 
05321. STA <Temp_Var15
 
05322.  
05323. LDA <Player_YHi
 
05324. SBC <Objects_YHi,X
 
05325. STA <Temp_Var14
 
05326.  
05327. BPL PRG000_D8CF ; If overall result is positive, jump to PRG000_D8CF
 
05328.  
05329. ; Otherwise, 16-bit negate Temp_Var14/15
 
05330. LDA <Temp_Var15
 
05331. JSR Negate
 
05332. STA <Temp_Var15
 
05333.  
05334. LDA <Temp_Var14
 
05335. EOR #$ff
 
05336. ADC #$00
 
05337. STA <Temp_Var14
 
05338.  
05339. PRG000_D8CF:
 
05340. LDA <Temp_Var14
 
05341. BNE PRG000_D920 ; If Temp_Var14 is not zero, there's a difference in the "High" component of the Player/Object, so no intersect! Jump to PRG000_D920
 
05342.  
05343. LDA <Temp_Var15
 
05344. BMI PRG000_D920 ; If Temp_Var15 is negative, no intersect, jump to PRG000_D920
 
05345.  
05346. ; Temp_Var12 holds specific info:
 
05347. ; Bit 0 - Set if Player's bbox bottom is HIGHER than object's bbox bottom
 
05348. ; Bit 1 - Set if Player's bbox left edge is to the LEFT of object's bbox left edge
 
05349.  
05350. LDA <Temp_Var12
 
05351. LSR A
 
05352. BCC PRG000_D8EB ; If Player's bbox bottom is NOT higher than object's, jump to PRG000_D8EB
 
05353.  
05354. LDA <Temp_Var1 ; Get Player's bounding box top offset
 
05355. SUB <Temp_Var11 ; Get vertical difference between Player and Object's bounding box bottoms
 
05356. CMP #$08
 
05357. BLS PRG000_D8EB ; If the result < 8, jump to PRG000_D8EB
 
05358.  
05359. ; Otherwise, flip the remaining bit of Temp_Var12
 
05360. LDA <Temp_Var12
 
05361. EOR #$01
 
05362. STA <Temp_Var12
 
05363.  
05364. PRG000_D8EB:
 
05365.  
05366. ; Set into status bits for this objcet
 
05367. LDA <Temp_Var12
 
05368. ORA Objects_PlayerHitStat,X
 
05369. STA Objects_PlayerHitStat,X
 
05370.  
05371. LDA Player_StarInv
 
05372. BEQ PRG000_D922 ; If Player is NOT invincible, jump to PRG000_D922
 
05373.  
05374. ; Player is invincible...
 
05375.  
05376. LDY Level_ObjectID,X ; Get object's ID -> Y
 
05377. LDA Object_AttrFlags,Y ; Get this object's attribute flags
 
05378. AND #OAT_HITNOTKILL
 
05379. BNE PRG000_D922 ; If OAT_HITNOTKILL is set, jump to PRG000_D922
 
05380.  
05381. ; For all objects where bit 7 is not set in their attributes...
 
05382.  
05383. LDA #OBJSTATE_KILLED
 
05384. STA Objects_State,X ; Set object state to Killed
 
05385.  
05386. LDA #-$38
 
05387. STA <Objects_YVel,X ; Set Y Velocity to -$38
 
05388.  
05389. ; "Kick" sound
 
05390. LDA Sound_QPlayer
 
05391. ORA #SND_PLAYERKICK
 
05392. STA Sound_QPlayer
 
05393.  
05394. ; 100 points pop up
 
05395. LDA #$05
 
05396. JSR Score_PopUp
 
05397.  
05398. JSR Level_ObjCalcXDiffs ; 'Y' is set to 0 if Player is to the right of object, 1 if to the left
 
05399.  
05400. LDA PRG000_D834,Y
 
05401. STA <Objects_XVel,X ; Set X velocity
 
05402.  
05403. PRG000_D920:
 
05404. CLC ; Clear carry
 
05405. RTS ; Return
 
05406.  
05407.  
05408. PRG000_D922:
 
05409.  
05410. ; For all objects where bit 7 is set in their attributes...
 
05411.  
05412. LDA <Temp_Var16 ; Returns 0 or 1, depending on original entry point
 
05413. BNE PRG000_D929 ; If it was 1 (do not respond to hit), jump to PRG000_D929
 
05414.  
05415. ; Do hit routine
 
05416. JSR Object_DoCollision ; Otherwise...
 
05417.  
05418. PRG000_D929:
 
05419. SEC ; Set carry
 
05420. RTS ; Return
 
05421.  
05422.  
05423. ; FIXME: Anybody want to claim this?
 
05424. ; $D92B
 
05425. .byte $F0, $00, $10, $20
 
05426.  
05427.  
05428. ; Calculates the upper-left and returns the lower-right offsets
 
05429. ; of this object's bounding box...
 
05430. ; Temp_Var1 - upper left of bounding box
 
05431. ; Temp_Var2 - offset to right bounding box
 
05432. ; Temp_Var5 - bottom of bounding box
 
05433. ; Temp_Var6 - offset to top bounding box
 
05434. ; $D92F
 
05435. Object_CalcBoundBox:
 
05436. ; X is object's slot
 
05437. ; Y is group relative object index
 
05438.  
05439. LDY Level_ObjectID,X ; Get this object's ID -> Y
 
05440. LDA Object_AttrFlags,Y ; Get this object's attribute flags
 
05441. AND #OAT_BOUNDBOXMASK ; Mask off the bounding box
 
05442. ASL A
 
05443. ASL A ; Shift left 2
 
05444. TAY ; -> Y (selected bounding box for this object)
 
05445.  
05446. ; Calculate upper left of bounding box and lower right offsets
 
05447. LDA <Objects_SpriteX,X
 
05448. ADD Object_BoundBox,Y
 
05449. STA <Temp_Var1 ; Temp_Var1 object's sprite X with offset
 
05450.  
05451. LDA <Objects_SpriteY,X
 
05452. ADD Object_BoundBox+2,Y
 
05453. STA <Temp_Var5 ; Temp_Var5 object's sprite Y with offset
 
05454.  
05455. LDA Object_BoundBox+1,Y
 
05456. STA <Temp_Var2 ; Temp_Var2 has the right offset
 
05457.  
05458. LDA Object_BoundBox+3,Y
 
05459. STA <Temp_Var6 ; Temp_Var6 has the bottom offset
 
05460.  
05461. RTS ; Return
 
05462.  
05463.  
05464. ; Calculates the upper-left and returns the lower-right offsets
 
05465. ; of this object's bounding box...
 
05466. ; Temp_Var3 - upper left of bounding box
 
05467. ; Temp_Var4 - offset to right bounding box
 
05468. ; Temp_Var7 - bottom of bounding box
 
05469. ; Temp_Var8 - offset to top bounding box
 
05470. ; $D955
 
05471. Object_CalcBoundBox2: ; Same as Object_CalcBoundBox in spirit, just different outputs, used for object-to-object collision
 
05472. ; X is object's slot
 
05473. ; Y is group relative object index
 
05474.  
05475. LDY Level_ObjectID,X ; Get this object's ID -> Y
 
05476. LDA Object_AttrFlags,Y ; Get this object's attribute flags
 
05477. AND #OAT_BOUNDBOXMASK ; Mask off the bounding box
 
05478. ASL A
 
05479. ASL A ; Shift left 2
 
05480. TAY ; -> Y (selected bounding box for this object)
 
05481.  
05482. ; Calculate upper left of bounding box and lower right offsets
 
05483. LDA <Objects_SpriteX,X
 
05484. ADD Object_BoundBox,Y
 
05485. STA <Temp_Var3 ; Temp_Var3 object's sprite X with offset
 
05486.  
05487. LDA <Objects_SpriteY,X
 
05488. ADD Object_BoundBox+2,Y
 
05489. STA <Temp_Var7 ; Temp_Var7 object's sprite Y with offset
 
05490.  
05491. LDA Object_BoundBox+1,Y
 
05492. STA <Temp_Var4 ; Temp_Var4 has the right offset
 
05493.  
05494. LDA Object_BoundBox+3,Y
 
05495. STA <Temp_Var8 ; Temp_Var8 has the bottom offset
 
05496.  
05497. RTS ; Return
 
05498.  
05499.  
05500. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
05501. ; ObjectObject_Intersect
 
05502. ;
 
05503. ; Determines if the Player/Object and the OTHER Object indexed
 
05504. ; by 'X' have intersected according to the bounding box data
 
05505. ;
 
05506. ; X = index of on-screen object
 
05507. ;
 
05508. ; Returns carry SET if Player/Object and Object intersected
 
05509. ; Temp_Var12 holds specific info:
 
05510. ; Bit 0 - Set if Player/Object's bbox bottom is HIGHER than
 
05511. ; object's bbox bottom
 
05512. ; Bit 1 - Set if Player/Object's bbox left edge is to the LEFT of
 
05513. ; object's bbox left edge
 
05514. ;
 
05515. ; Note that this is performed by the "sprite" (or screen-relative)
 
05516. ; positions of the Player/Object and the OTHER Object, and may not
 
05517. ; be accurate (because it's not a full 16-bit coordinate check) and
 
05518. ; more logic is needed after this to determine completely if there
 
05519. ; should be an actual collision. See use of ObjectObject_Intersect
 
05520. ; to get an idea what else needs to be done...
 
05521. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
05522. ; $D97B
 
05523. ObjectObject_Intersect:
 
05524. LDY #$00 ; Y = 0
 
05525. STY <Temp_Var12 ; Temp_Var12 = 0 (Player's bbox is to the RIGHT of the object's left edge, until determined otherwise)
 
05526.  
05527.  
05528. ; Right now we're considering the left edges of the Player and Object
 
05529. ; we're detecting against
 
05530.  
05531. LDA <Temp_Var3 ; Left of Player's bounding box
 
05532. SUB <Temp_Var1 ; Left of object's bound box
 
05533. STA <Temp_Var11 ; Difference between the two -> Temp_Var11
 
05534.  
05535. ASL A ; Sets carry if it was a negative result
 
05536.  
05537. LDA <Temp_Var2 ; Get the object's right edge bounding box offset
 
05538.  
05539. BCC PRG000_D997 ; If the calculated difference was NOT negative (Player's bbox left edge is to the RIGHT of object's bbox left edge), jump to PRG000_D997
 
05540.  
05541. ; Player's box left edge is to the LEFT of the object's left edge
 
05542.  
05543. ; Negate Temp_Var11 (the difference), making it positive
 
05544. LDA <Temp_Var11
 
05545. EOR #$ff
 
05546. STA <Temp_Var11
 
05547. INC <Temp_Var11
 
05548.  
05549. INC <Temp_Var12 ; Temp_Var12 = 1 (Player's bbox is to the LEFT of object's left edge)
 
05550.  
05551. LDA <Temp_Var4 ; Get the Player's right edge bounding box offset
 
05552.  
05553. PRG000_D997:
 
05554. CMP <Temp_Var11
 
05555. BLT PRG000_D9B7 ; If the left edge offset is less than the right edge offset (CARRY CLEAR), jump to PRG000_D9B7 (RTS)
 
05556.  
05557.  
05558. ; That didn't happen...
 
05559.  
05560. ASL <Temp_Var12 ; Push result bit up
 
05561.  
05562. LDA <Temp_Var7 ; Player's bounding box bottom
 
05563. SUB <Temp_Var5 ; Object's bouncing box bottom
 
05564. STA <Temp_Var11 ; Store difference -> Temp_Var11
 
05565.  
05566. ASL A ; Sets carry if it was a negative result
 
05567.  
05568. LDA <Temp_Var6 ; Get object's bounding box top edge offset
 
05569.  
05570. BCC PRG000_D9B5 ; If the calculated difference was NOT negative (Player's bbox bottom is LOWER than object's bbox bottom), jump to PRG000_D9B5
 
05571.  
05572. ; Negate Temp_Var11 (the difference), making it positive
 
05573. LDA <Temp_Var11
 
05574. EOR #$ff
 
05575. STA <Temp_Var11
 
05576. INC <Temp_Var11
 
05577.  
05578. INC <Temp_Var12 ; Set bit 0 of Temp_Var12
 
05579.  
05580. LDA <Temp_Var8 ; Get Player's bounding box top edge offset
 
05581.  
05582. PRG000_D9B5:
 
05583. CMP <Temp_Var11 ; Set final carry bit to determine if we intersected or not
 
05584.  
05585. PRG000_D9B7:
 
05586.  
05587. ; Most importantly, status of the carry flag is returned
 
05588. ; If carry is CLEAR, we did not intersect Player to Object
 
05589.  
05590. ; Temp_Var12 holds specific info:
 
05591. ; Bit 0 - Set if Player's bbox bottom is HIGHER than object's bbox bottom
 
05592. ; Bit 1 - Set if Player's bbox left edge is to the LEFT of object's bbox left edge
 
05593.  
05594. RTS ; Return
 
05595.  
05596.  
05597. ; Proper Collision routine for this object
 
05598. ; $D9BB
 
05599. Object_DoCollision:
 
05600. LDX <SlotIndexBackup ; X = the current object slot
 
05601.  
05602.  
05603. LDA ObjGroupRel_Idx ; Get the object's group relative index
 
05604. ASL A ; Shift left 1 (2 byte index)
 
05605. TAY ; -> Y
 
05606.  
05607. ; Get address from ObjectGroup_CollideJumpTable...
 
05608. LDA ObjectGroup_CollideJumpTable,Y
 
05609. STA <Temp_Var1
 
05610. LDA ObjectGroup_CollideJumpTable+1,Y
 
05611. STA <Temp_Var2
 
05612. JMP [Temp_Var1] ; Jump to the acquired address!
 
05613.  
05614. ; RAS: Dead data: Specified frame of "suit lost" object
 
05615. ; to display when the cooresponding suit was lost (not
 
05616. ; used for any of the "regular" power ups)
 
05617. SMB3J_SuitLossFrame: .byte $00, $00, $00, $00, $01, $02, $03
 
05618.  
05619. ; $D9D3
 
05620. Player_GetHurt:
 
05621. ; If Player is...
 
05622. LDA Player_FlashInv ; ... flashing invincible ...
 
05623. ORA Player_Statue ; ... a statue ...
 
05624. ORA Player_StarInv ; ... invincible by star ...
 
05625. ORA Player_SuitLost ; ... just lost a power-up suit ...
 
05626. ORA <Player_HaltGame ; ... gameplay halted ...
 
05627. ORA Player_HaltTick ; ... Player halted ...
 
05628. ORA Player_DebugNoHitFlag ; ... debug invincibility flag is set (unused) ...
 
05629. BNE PRG000_D9B7 ; ... then jump to PRG000_D9B7 (RTS)
 
05630.  
05631. JMP PRG000_DA15 ; Jump to PRG000_DA15 (skips lost/dead Japanese version code)
 
05632.  
05633. ;;;;;;;;;;;;;; Begin SMB3-J Only Code ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
05634.  
05635. ; RAS: Lost/Dead Code -- This was the Japanese version suit loss code
 
05636. ; For detail why it was removed, see PRG007 LostShoe_Pattern
 
05637. ; $D9EC
 
05638. LDA Player_Kuribo
 
05639. BNE PRG000_D9F7 ; If Player is in Kuribo's Shoe, jump to PRG000_D9F7
 
05640.  
05641. ; Player is NOT in Kuribo's Shoe...
 
05642.  
05643. LDA <Player_Suit
 
05644. CMP #PLAYERSUIT_SUPERSUITBEGIN
 
05645. BLS PRG000_DA4E ; If Player is not in one of the Super Suits, jump to PRG000_DA4E
 
05646.  
05647. PRG000_D9F7:
 
05648.  
05649. ; Player was in a Kuribo's Shoe or one of the Super Suits
 
05650.  
05651. ; Play "shoe lost" sound
 
05652. LDA Sound_QLevel1
 
05653. ORA #SND_LEVELSHOE
 
05654. STA Sound_QLevel1
 
05655.  
05656. LDY <Player_Suit ; Y = Player's power up
 
05657. LDA SMB3J_SuitLossFrame,Y ; Get correct "loss" frame
 
05658. STA <Temp_Var1 ; -> Temp_Var1
 
05659. JSR Player_LoseKuribo ; Suit pops off
 
05660.  
05661. ; Switch back to just Big
 
05662. LDA #$01
 
05663. STA Player_QueueSuit
 
05664.  
05665. ; You no longer have the Kuribo's Shoe
 
05666. LDA #$00
 
05667. STA Player_Kuribo
 
05668.  
05669. BEQ PRG000_DA6D ; Jump (technically always) to PRG000_DA6D
 
05670.  
05671. ;;;;;;;;;;;;;; End SMB3-J Only Code ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
05672.  
05673. PRG000_DA15:
 
05674. LDA Player_Kuribo
 
05675. BNE PRG000_DA32 ; If Player is in Kuribo's shoe, jump to PRG000_DA32
 
05676.  
05677. LDA <Player_Suit
 
05678. CMP #PLAYERSUIT_FIRE ; RAS: Change this to "PLAYERSUIT_SUPERSUITBEGIN" and you restore Japanese version's "always shrink" code!!
 
05679. BLS PRG000_DA4E ; If Player is Big or small, jump to PRG000_DA4E
 
05680.  
05681. ; Higher level power-up suits...
 
05682. LDA #$17
 
05683. STA Player_SuitLost ; Player_SuitLost = $17
 
05684.  
05685. ; Play Power up lost sound
 
05686. LDA Sound_QLevel1
 
05687. ORA #SND_LEVELPOOF
 
05688. STA Sound_QLevel1
 
05689.  
05690. LDA #$02 ; Return to Big (RAS: Would be small in Japanese version!!)
 
05691. JMP PRG000_DA44 ; Jump to PRG000_DA44
 
05692.  
05693. PRG000_DA32:
 
05694.  
05695. ; Play "shoe lost" sound
 
05696. LDA Sound_QLevel1
 
05697. ORA #SND_LEVELSHOE
 
05698. STA Sound_QLevel1
 
05699.  
05700. ; RAS: This lost its meaning, but it marks you to lose the Kuribo's
 
05701. ; shoe specifically; see above for lost/dead SMB3-J code where
 
05702. ; alternate Temp_Var1 values would be used...
 
05703. ; (The other index values display as garbage now instead of the suit,
 
05704. ; see details at PRG007 LostShoe_Pattern)
 
05705. LDA #$00
 
05706. STA <Temp_Var1 ; Temp_Var1 = 0
 
05707.  
05708. JSR Player_LoseKuribo ; Setup effect of Kuribo's shoe "flying off"
 
05709. JMP PRG000_DA47 ; Jump to PRG000_DA47
 
05710.  
05711. PRG000_DA44:
 
05712. STA Player_QueueSuit ; Queue power-up change
 
05713.  
05714. PRG000_DA47:
 
05715. LDA #$00
 
05716. STA Player_Kuribo ; Player no longer has Kuribo's shoe (if he even did a moment ago)
 
05717. BEQ PRG000_DA6D ; Jump (technically always) to PRG000_DA6D
 
05718.  
05719. PRG000_DA4E:
 
05720.  
05721. ; Player is only big or small...
 
05722.  
05723. LDA <Player_Suit
 
05724. BEQ PRG000_DA7A ; If Player is small, jump to PRG000_DA7A (gonna die!!)
 
05725.  
05726. LDA #$02
 
05727. STA Player_QueueSuit ; Return to Big
 
05728.  
05729. ; RAS: NOTE: Deprecated logic! We won't get here in SMB3-US at this
 
05730. ; high of a power level anymore...
 
05731. LDA <Player_Suit
 
05732. CMP #PLAYERSUIT_SUPERSUITBEGIN
 
05733. BGS PRG000_DA6D ; If Player's current power-up is a Super Suit, jump to PRG000_DA6D
 
05734.  
05735. ; Play shrinking sound!!
 
05736. LDA Sound_QPlayer
 
05737. ORA #SND_PLAYERPIPE
 
05738. STA Sound_QPlayer
 
05739.  
05740. LDA #$2f
 
05741. STA Player_Grow ; Player_Grow = $2f (shrinking!)
 
05742. DEC Player_QueueSuit ; Get small!
 
05743.  
05744. PRG000_DA6D:
 
05745. LDA #$71
 
05746. STA Player_FlashInv ; Player_FlashInv = $71
 
05747.  
05748. LDA #$00
 
05749. STA Player_Flip ; Player not somersaulting
 
05750.  
05751. BEQ PRG000_DAAE ; Jump (technically always) to PRG000_DAAE (cosmetic bugfix?)
 
05752.  
05753. RTS ; Return
 
05754.  
05755. PRG000_DA7A:
 
05756. LDX <SlotIndexBackup ; X = SlotIndexBackup
 
05757.  
05758.  
05759. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
05760. ; Player_Die
 
05761. ;
 
05762. ; Simple and to the point: Starts the death song,
 
05763. ; resets a bunch of variables that get in the way,
 
05764. ; changes to small, etc.
 
05765. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
05766. Player_Die:
 
05767. ; Queue death song
 
05768. LDA Sound_QMusic1
 
05769. ORA #MUS1_PLAYERDEATH
 
05770. STA Sound_QMusic1
 
05771.  
05772. ; Clear a bunch of stuff at time of death
 
05773. LDA #$00
 
05774. STA <Player_XVel
 
05775. STA <Obj01_Flag
 
05776. STA Player_Flip
 
05777. STA Player_FlashInv
 
05778. STA Player_Kuribo
 
05779. STA Player_StarInv
 
05780. STA Player_Statue
 
05781. STA Level_PSwitchCnt
 
05782.  
05783. LDA #$01
 
05784. STA Player_QueueSuit ; Queue change to "small"
 
05785.  
05786. LDA #-64
 
05787. STA <Player_YVel ; Player_YVel = -64
 
05788.  
05789. LDA #$30
 
05790. STA Event_Countdown ; Event_Countdown = $30 (ticks until dropped back to map)
 
05791.  
05792. LDA #$01
 
05793. STA <Player_IsDying ; Player_IsDying = 1
 
05794.  
05795. PRG000_DAAE:
 
05796. ; Ensure Player_FlipBits is correct?
 
05797. ; RAS: May be a cosmetic bugfix for player coming out of a somersault
 
05798. ; (see jump to PRG000_DAAE) and getting hit, but I'm not really sure...
 
05799. LDA <Player_FlipBits
 
05800. AND #$7f
 
05801. STA <Player_FlipBits
 
05802.  
05803. RTS ; Return
 
05804.  
05805. ; Set display effect for Player losing Kuribo's shoe
 
05806. ; RAS: This also USED to setup for losing other power-ups in
 
05807. ; the Japanese version, but that is removed and broken in US.
 
05808. ; See notes at PRG007 "LostShoe_Pattern" for details...
 
05809. Player_LoseKuribo:
 
05810. LDY #$05 ; Y = 5
 
05811.  
05812. PRG000_DAB7:
 
05813. LDA SpecialObj_ID,Y
 
05814. BEQ PRG000_DAC0 ; If this slot is open, jump to PRG000_DAC0
 
05815.  
05816. DEY ; Y--
 
05817. BPL PRG000_DAB7 ; While Y >= 0, loop!
 
05818.  
05819. RTS ; Return
 
05820.  
05821. PRG000_DAC0:
 
05822. LDA #SOBJ_KURIBOSHOE
 
05823. STA SpecialObj_ID,Y ; Lost Kuribo's shoe!
 
05824.  
05825. ; Set object at Player
 
05826. LDA <Player_Y
 
05827. STA SpecialObj_YLo,Y
 
05828.  
05829. LDA <Player_YHi
 
05830. STA SpecialObj_YHi,Y
 
05831.  
05832. LDA <Player_X
 
05833. STA SpecialObj_XLo,Y
 
05834.  
05835. LDA #-$30
 
05836. STA SpecialObj_YVel,Y ; Y velocity = -$30
 
05837.  
05838. ; Decide proper X velocity based on Player's facing direction
 
05839. LDA #$00
 
05840. CMP <Player_FlipBits
 
05841.  
05842. LDA #16
 
05843. BGE PRG000_DAE3
 
05844.  
05845. LDA #-16
 
05846.  
05847. PRG000_DAE3:
 
05848. STA SpecialObj_XVel,Y ; Set appropriate X velocity
 
05849.  
05850. ; RAS: This is always zero in SMB3-US, but would have
 
05851. ; been set to other values in the Japanese original
 
05852. LDA <Temp_Var1
 
05853. STA SpecialObj_Data,Y
 
05854.  
05855. RTS ; Return
 
05856.  
05857. ; X velocities as appropriate based on which direction
 
05858. ; Player was when he killed the enemy
 
05859. EnemyKill_XVels: .byte -$08, $08
 
05860.  
05861. ; Tail attack X offset, based on Player's facing direction
 
05862. Player_TailAttackXOff: .byte $11, -$0A
 
05863.  
05864. PRG000_DAF0:
 
05865. .byte -$0A, $11
 
05866.  
05867.  
05868. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
05869. ; Object_HitByTailOrBouncer
 
05870. ;
 
05871. ; Test if object is getting hit by Player's tail attack
 
05872. ; or a left/right bouncing block
 
05873. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
05874. Object_HitByTailOrBouncer:
 
05875. ; Clear the "Tail Attacked" bit
 
05876. LDA Objects_PlayerHitStat,X
 
05877. AND #%11110111
 
05878. STA Objects_PlayerHitStat,X
 
05879.  
05880. JSR Object_RespondToTailAttack ; Get hit by tail attack if appropriate
 
05881.  
05882. ; Handle a left/right bouncer if it impacts an object
 
05883. LDA LRBounce_Y
 
05884. CMP #$ff
 
05885. BEQ PRG000_DB16 ; If LRBounce_Y = $FF, jump to PRG000_DB16 (RTS)
 
05886. STA <Temp_Var7 ; Temp_Var7 = LRBounce_Y
 
05887.  
05888. LDA #$0f
 
05889. STA <Temp_Var8 ; Temp_Var8 = $0F
 
05890.  
05891. LDA LRBounce_X
 
05892. STA <Temp_Var3 ; Temp_Var3 = LRBounce_X
 
05893.  
05894. LDA #$0f
 
05895. STA <Temp_Var4 ; Temp_Var4 = $0F
 
05896.  
05897. JSR Player_TailAttackDo ; Perform tail attack type action
 
05898.  
05899. PRG000_DB16:
 
05900. RTS ; Return
 
05901.  
05902.  
05903. PRG000_DB17: .byte $10, -$10
 
05904.  
05905.  
05906. Object_RespondToTailAttack:
 
05907. LDA Player_TailAttack
 
05908. BEQ PRG000_DB16 ; If Player is not tail attacking, jump to PRG000_DB16 (RTS)
 
05909.  
05910. ; Tail attack only kicks at counter values $09 and $0C
 
05911. CMP #$0c
 
05912. BEQ PRG000_DB26 ; If tail attack counter = $0C, jump to PRG000_DB26
 
05913. CMP #$09
 
05914. BNE PRG000_DB16 ; If tail attack counter <> $09, jump to PRG000_DB16 (RTS)
 
05915.  
05916. PRG000_DB26:
 
05917. LDA <Player_FlipBits
 
05918. AND #$40
 
05919. TAY ; Y = $00 or $40, whether Player is flipped
 
05920. BEQ PRG000_DB2F ; If 'Y' = 0, jump to PRG000_DB2F
 
05921.  
05922. LDY #$01 ; Y = 1
 
05923.  
05924. PRG000_DB2F:
 
05925. LDA Player_TailAttackXOff,Y
 
05926. ADD <Player_SpriteX
 
05927. STA <Temp_Var3 ; Temp_Var3 = appropriate X offset for tail attack
 
05928.  
05929. LDA #$0a
 
05930. STA <Temp_Var4 ; Temp_Var4 = $0A
 
05931.  
05932. LDA <Player_SpriteY
 
05933. ADD #$10
 
05934. STA <Temp_Var7 ; Temp_Var7 = tail attack offset
 
05935.  
05936. LDA #$0f
 
05937. STA <Temp_Var8 ; Temp_Var8 = $0F
 
05938.  
05939. Player_TailAttackDo:
 
05940. LDY Objects_State,X ; Y = object's current state
 
05941.  
05942. LDA Obj2Obj_EnByState,Y
 
05943. BNE PRG000_DB16 ; If object is not hit tested in this state, jump to PRG000_DB16 (RTS)
 
05944.  
05945. JSR Object_AnySprOffscreen
 
05946. BNE PRG000_DB16 ; If any sprite of the object is off-screen, jump to PRG000_DB16 (RTS)
 
05947.  
05948. JSR Object_CalcBoundBox
 
05949. JSR ObjectObject_Intersect
 
05950. BCC PRG000_DB16 ; If Player and object are not intersecting, jump to PRG000_DB16 (RTS)
 
05951.  
05952. ; Set "Tail Attacked" bit
 
05953. LDA Objects_PlayerHitStat,X
 
05954. ORA #%00001000
 
05955. STA Objects_PlayerHitStat,X
 
05956.  
05957. LDY ObjGroupRel_Idx ; Y = object's group-relative index
 
05958.  
05959. LDA ObjectGroup_Attributes3,Y
 
05960. AND #OA3_TAILATKIMMUNE
 
05961. BNE PRG000_DB16 ; If OA3_TAILATKIMMUNE is SET (Object cannot be tail-attacked), jump to PRG000_DB16 (RTS)
 
05962.  
05963. LDA <Temp_Var4
 
05964. CMP #$0f
 
05965. BEQ Enemy_Kill
 
05966.  
05967. LDY #$00 ; Y = 0
 
05968.  
05969. LDA <Player_FlipBits
 
05970. BEQ PRG000_DB7A ; If Player is not turned around, jump to PRG000_DB7A
 
05971.  
05972. INY ; Y = 1
 
05973.  
05974. PRG000_DB7A:
 
05975.  
05976. ; Set ShellKillFlash vars
 
05977. LDA PRG000_DB17,Y
 
05978. ADD <Player_X
 
05979. STA ShellKillFlash_X
 
05980.  
05981. LDA <Player_Y
 
05982. ADD #$10
 
05983. STA ShellKillFlash_Y
 
05984.  
05985. LDA #$0a
 
05986. STA ShellKillFlash_Cnt
 
05987.  
05988.  
05989. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
05990. ; Enemy_Kill
 
05991. ;
 
05992. ; Kills an enemy; flips them over, plays the "kick" sound
 
05993. ; If attribute 3, bit 6 is SET, there's some special
 
05994. ; behavior described below (using CollideJumpTable as a
 
05995. ; value rather than address, alternate dead state 3, etc.)
 
05996. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
05997. Enemy_Kill:
 
05998.  
05999. ; Set timer 2 to 12
 
06000. LDA #12
 
06001. STA Objects_Timer2,X
 
06002.  
06003. ; "Kick" sound
 
06004. LDA Sound_QPlayer
 
06005. ORA #SND_PLAYERKICK
 
06006. STA Sound_QPlayer
 
06007.  
06008. LDY ObjGroupRel_Idx ; Y = object group relative index
 
06009. LDA ObjectGroup_Attributes3,Y ; Get this object's attribute set 3
 
06010. AND #OA3_DIESHELLED
 
06011. BNE PRG000_DBB6 ; If OA3_DIESHELLED is set, jump to PRG000_DBB6
 
06012.  
06013. ; OA3_DIESHELLED is not set...
 
06014.  
06015. LDA Player_Slide
 
06016. BNE PRG000_DBB2 ; If Player is sliding, jump to PRG000_DBB2
 
06017.  
06018. LDA Kill_Tally ; Get current kill tally
 
06019. JSR Score_Get100PlusPts ; Get appropriate score based on kill tally
 
06020.  
06021. PRG000_DBB2:
 
06022. LDA #$06 ; A = 6 (object state 6, killed)
 
06023. BNE PRG000_DBCF ; Jump (technically always) to PRG000_DBCF
 
06024.  
06025.  
06026. PRG000_DBB6:
 
06027.  
06028. ; Attribute set 3 bit 6 is set...
 
06029.  
06030. ; Y *= 2 (2 byte index)
 
06031. TYA
 
06032. ASL A
 
06033. TAY
 
06034.  
06035. LDA ObjectGroup_CollideJumpTable+1,Y ; Get upper byte of collision jump entry
 
06036. AND #%11111000
 
06037. CMP #%00001000 ; If only bit 3 is set and 4-7 are clear, this is a new object ID to change to
 
06038. BNE PRG000_DBC8 ; If the above is not the case, jump to PRG000_DBC8
 
06039.  
06040. ; SPECIAL CASE: Collide Jump table lower byte specifies a new object ID
 
06041.  
06042. LDA ObjectGroup_CollideJumpTable,Y ; Get the new ID
 
06043. STA Level_ObjectID,X ; Set the new ID
 
06044.  
06045. PRG000_DBC8:
 
06046. ; Timer 3 set to $FF
 
06047. LDA #$ff
 
06048. STA Objects_Timer3,X
 
06049.  
06050. LDA #OBJSTATE_SHELLED ; A = Shelled
 
06051.  
06052. PRG000_DBCF:
 
06053. STA Objects_State,X ; Set new object state
 
06054.  
06055. LDA #-$30 ; A = -$30
 
06056.  
06057. LDY <Temp_Var4
 
06058.  
06059. CPY #$0f
 
06060. BEQ PRG000_DBDC ; If Temp_Var4 = $0F, jump to PRG000_DBDC
 
06061.  
06062. LDA #-$50 ; A = -$50
 
06063.  
06064. PRG000_DBDC:
 
06065. STA <Objects_YVel,X ; Set Y velocity appropriately
 
06066.  
06067. ; Set appropriate X Velocity based on facing direction of
 
06068. ; Player when he killed the enemy
 
06069. JSR Level_ObjCalcXDiffs
 
06070. LDA EnemyKill_XVels,Y
 
06071. STA <Objects_XVel,X
 
06072.  
06073. ; Set vertical flip on the object
 
06074. LDA Objects_FlipBits,X
 
06075. ORA #SPR_VFLIP
 
06076. STA Objects_FlipBits,X
 
06077.  
06078. RTS ; Return
 
06079.  
06080.  
06081. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06082. ; ObjectToObject_HitTest
 
06083. ;
 
06084. ; Determines if the object specified in 'X' has collided
 
06085. ; with any of the other active objects not including
 
06086. ; Player (see Object_HitTest/Object_HitTestRespond)
 
06087. ;
 
06088. ; If the object has collided with another object:
 
06089. ; Carry flag is SET
 
06090. ; 'Y' = index of the collided-with object
 
06091. ; 'A' = ObjectID of the collided-with object
 
06092. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06093. ; Enable object-to-object by state (0 = Enabled, 1 = Disabled)
 
06094. Obj2Obj_EnByState:
 
06095. .byte $01 ; State 0: Dead/Empty
 
06096. .byte $01 ; State 1: Initializing
 
06097. .byte $00 ; State 2: Normal
 
06098. .byte $00 ; State 3: Shelled
 
06099. .byte $00 ; State 4: Held
 
06100. .byte $00 ; State 5: Kicked
 
06101. .byte $01 ; State 6: Killed
 
06102. .byte $01 ; State 7: Squashed
 
06103. .byte $01 ; State 8: Dying
 
06104.  
06105. ; $DBF8
 
06106. ObjectToObject_HitTest:
 
06107. LDA Objects_SprVVis,X
 
06108. BNE PRG000_DC54 ; If any sprites are vertically off-screen, jump to PRG000_DC54
 
06109.  
06110. ; No sprites are vertically off-screen...
 
06111.  
06112. LDA Objects_SprHVis,X
 
06113. AND #%11000000
 
06114. CMP #%11000000
 
06115. BEQ PRG000_DC54 ; If both of the end sprite are horizontally off-screen, jump to PRG000_DC54
 
06116.  
06117. JSR Object_CalcBoundBox2 ; Calculate THIS object's bounding box
 
06118.  
06119. PRG000_DC09:
 
06120. LDX #$04 ; X = 4
 
06121. PRG000_DC0B:
 
06122. CPX <SlotIndexBackup
 
06123. BEQ PRG000_DC51 ; If this object slot is the current object, jump to PRG000_DC51 (don't do anything to self)
 
06124.  
06125. LDY Objects_State,X
 
06126. LDA Obj2Obj_EnByState,Y
 
06127. BNE PRG000_DC51 ; If the state this object is in does not do object-to-object detection, jump to PRG000_DC51 (do nothing)
 
06128.  
06129. LDA Objects_SprVVis,X
 
06130. BNE PRG000_DC51 ; If sprites are vertically off-screen, jump to PRG000_DC51 (do nothing)
 
06131.  
06132. LDA Objects_SprHVis,X
 
06133. AND #%11000000
 
06134. CMP #%11000000
 
06135. BEQ PRG000_DC51 ; If two sprites are horizontally off-screen, jump to PRG000_DC51 (do nothing)
 
06136.  
06137. JSR Object_CalcBoundBox ; Calculate OTHER object's bounding box
 
06138. JSR ObjectObject_Intersect ; Returns carry SET if object and OTHER object intersected
 
06139. BCC PRG000_DC51 ; If object did NOT intersect the OTHER object, jump to PRG000_DC51 (do nothing)
 
06140.  
06141. ; These two objects have collided...!
 
06142.  
06143. LDY <SlotIndexBackup ; Y = object slot index
 
06144.  
06145. LDA <Objects_X,X
 
06146. SUB Objects_X,Y ; Difference between the object and the OTHER object's X
 
06147. PHA ; Save the difference
 
06148.  
06149. LDA <Objects_XHi,X
 
06150. SBC Objects_XHi,Y ; Difference between the object and the OTHER object's X Hi
 
06151. STA <Temp_Var1 ; -> Temp_Var1
 
06152.  
06153. PLA ; Restore the lower X difference
 
06154.  
06155. ; Don't quite understand the logic, but this determines if the
 
06156. ; objects are actually on the same screen instead of just
 
06157. ; seeming to due to the low accuracy of sprite coordinates
 
06158. ADC #$80
 
06159. LDA <Temp_Var1
 
06160. ADC #$00
 
06161. BNE PRG000_DC51 ; If the objects did not actually collide, jump to PRG000_DC51 (do nothing)
 
06162.  
06163. SEC ; Object's collided! Set carry!
 
06164.  
06165. LDY Level_ObjectID,X ; Y = OTHER object's ID
 
06166.  
06167. LDA Object_AttrFlags,Y
 
06168. AND #OAT_HITNOTKILL
 
06169. BEQ PRG000_DC57 ; If this object is NOT a "Hit-Not-Kill" type, jump to PRG000_DC57
 
06170.  
06171. PRG000_DC51:
 
06172. DEX ; X--
 
06173. BPL PRG000_DC0B ; While X >= 0, loop!
 
06174.  
06175. PRG000_DC54:
 
06176. CLC ; Clear carry (collided with no other object)
 
06177. BCC PRG000_DC5C ; Jump (technically always) to PRG000_DC5C
 
06178.  
06179. PRG000_DC57:
 
06180. TXA
 
06181. TAY ; Index of the OTHER object that this object collided with -> 'Y'
 
06182. LDA Level_ObjectID,Y ; A = the ID of the OTHER object
 
06183.  
06184. PRG000_DC5C:
 
06185. LDX <SlotIndexBackup ; Restore 'X' as the object slot index
 
06186. RTS ; Return
 
06187.  
06188.  
06189. ; This changes a tile based on Temp_Var13-16 coordinates:
 
06190. ; Temp_Var13 / Temp_Var14 -- Y Hi and Lo
 
06191. ; Temp_Var15 / Temp_Var16 -- X Hi and Lo
 
06192. Level_ChangeTile_ByTempVars:
 
06193.  
06194. PHA ; Save 'A'
 
06195. LDA Level_7Vertical
 
06196. BEQ PRG000_DC7B ; If level is NOT vertical, jump to PRG000_DC7B
 
06197.  
06198. LDY <Temp_Var13
 
06199. LDA <Temp_Var14
 
06200. JSR LevelJct_GetVScreenH ; Adjust coordinates for vertical
 
06201.  
06202. PHA ; Save 'A' (Y Lo)
 
06203.  
06204. ; Set tile grid modify address
 
06205. LDA Tile_Mem_AddrVL,Y
 
06206. STA <Temp_Var1
 
06207. LDA Tile_Mem_AddrVH,Y
 
06208. STA <Temp_Var2
 
06209.  
06210. PLA ; Restore 'A' (Y Lo)
 
06211.  
06212. JMP PRG000_DC91 ; Jump to PRG000_DC91
 
06213.  
06214. PRG000_DC7B:
 
06215. LDA <Temp_Var15
 
06216. ASL A
 
06217. TAY ; Y = Temp_Var15 (X Hi) shifted left 1 (2 bytes index per screen for Tile_Mem_Addr)
 
06218.  
06219. ; Set tile grid modify address
 
06220. LDA Tile_Mem_Addr,Y
 
06221. STA <Temp_Var1
 
06222. LDA Tile_Mem_Addr+1,Y
 
06223. STA <Temp_Var2
 
06224.  
06225. LDA <Temp_Var13
 
06226. BEQ PRG000_DC8F ; If Y Hi = 0, jump to PRG000_DC8F
 
06227.  
06228. INC <Temp_Var2 ; Otherwise, offset to lower screen area
 
06229.  
06230. PRG000_DC8F:
 
06231. LDA <Temp_Var14 ; A = Y lo
 
06232.  
06233. PRG000_DC91:
 
06234. AND #$f0
 
06235. STA <Temp_Var3 ; Tile aligned "low" (makes row)
 
06236.  
06237. LDA <Temp_Var16
 
06238. LSR A
 
06239. LSR A
 
06240. LSR A
 
06241. LSR A
 
06242. ORA <Temp_Var3 ; Makes column
 
06243.  
06244. TAY ; Y = offset to specific tile
 
06245.  
06246. PLA ; Restore 'A' (tile index)
 
06247.  
06248. STA [Temp_Var1],Y ; Change tile as appropriate
 
06249.  
06250. RTS ; Return
 
06251.  
06252.  
06253. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06254. ; Object_CalcCoarseXDiff
 
06255. ;
 
06256. ; Calculates a "coarse" X difference with the Player,
 
06257. ; returning a one byte value that determines the
 
06258. ; difference in X/XHi coordinates in units of 4 pixels
 
06259. ; in Temp_Var15. Temp_Var16 is set to $40 and the
 
06260. ; carry flag is set if the difference was negative.
 
06261. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06262. ; $DCA2
 
06263. Object_CalcCoarseXDiff:
 
06264. LDA <Objects_X,X
 
06265. SUB <Player_X
 
06266. STA <Temp_Var15 ; Temp_Var15 = difference between Object and Player X
 
06267.  
06268. LDA <Objects_XHi,X
 
06269. SBC <Player_XHi ; Calc diff between X His
 
06270.  
06271. LSR A ; Push low bit of "hi" difference -> carry
 
06272. ROR <Temp_Var15 ; Cycle carry into Temp_Var15 at high bit; will be discarding low bit
 
06273. LSR A ; Push low bit of "hi" difference -> carry
 
06274. ROR <Temp_Var15 ; Cycle carry into Temp_Var15 at high bit; will be discarding low bit
 
06275.  
06276. ; Temp_Var15 now holds a difference between the Object and Player
 
06277. ; X coordinates in units of 4 pixels (works up to two screen
 
06278. ; widths; anything greater and object was probably removed anyway)
 
06279.  
06280. ; Note the following only works because there is no way that bit 5 and 7
 
06281. ; could be a part of the actual difference, just the sign factor, since
 
06282. ; a level cannot be more than 10 screens in width.
 
06283. ASL A ; Shift remaining difference left 1; carry set means negative difference
 
06284. AND #$40
 
06285. STA <Temp_Var16 ; Temp_Var16 being $40 also means negative difference
 
06286.  
06287. RTS ; Return
 
06288.  
06289.  
06290. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06291. ; Object_CalcCoarseYDiff
 
06292. ;
 
06293. ; Calculates a "coarse" Y difference with the Player,
 
06294. ; returning a one byte value that determines the
 
06295. ; difference in Y/YHi coordinates in units of 8 pixels.
 
06296. ; Returns Temp_Var15 in the format of a crude signed
 
06297. ; value for Y Hi in bit 6 and 7
 
06298. ; [00 -> Y Hi = 0, 01 -> Y Hi = 1, 11 -> Y Hi = negative]
 
06299. ; and the base Y difference in the bits 0 - 5 (so units
 
06300. ; of 8 pixels.)
 
06301. ; Temp_Var16 holds the raw difference in "Y Hi"
 
06302. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06303. ; $DCB9
 
06304. Object_CalcCoarseYDiff
 
06305. LDA <Objects_Y,X
 
06306. SUB <Player_Y
 
06307. STA <Temp_Var15 ; Temp_Var15 = difference between object's Y and Player's Y
 
06308.  
06309. LDA <Objects_YHi,X
 
06310. SBC <Player_YHi
 
06311. STA <Temp_Var16 ; Temp_Var16 = difference between object's Y Hi and Player's Y Hi
 
06312.  
06313. LSR A ; least significant bit of Y Hi -> carry
 
06314.  
06315. ROR <Temp_Var15 ; Temp_Var15 takes on the "Hi" value in its most significant bit
 
06316.  
06317. LSR A ; next least significant bit of Y Hi -> carry
 
06318. ROR <Temp_Var15 ; The new Temp_Var15's least significant bit is pushed into its bit 7
 
06319.  
06320. ; So now Temp_Var15 holds the main Y difference in its first 5 bits
 
06321. ; Bit 6 and 7 form a signed portion of the "hi" value -- 00 -> Y Hi = 0, 01 -> Y Hi = 1, 11 -> Y Hi = negative
 
06322.  
06323. RTS ; Return
 
06324.  
06325.  
06326. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06327. ; Object_ApplyYVel
 
06328. ; Object_ApplyYVel_NoLimit
 
06329. ;
 
06330. ; Adds the 4.4FP Y velocity to object and prevents object
 
06331. ; from falling faster than OBJECT_MAXFALL (unless using
 
06332. ; Object_ApplyYVel_NoLimit which does not enforce this)
 
06333. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06334. ; $DCCD
 
06335. Object_ApplyYVel:
 
06336. LDA <Objects_YVel,X
 
06337. BMI Object_ApplyYVel_NoLimit ; If Object's Y Vel < 0 (moving upward), jump to Object_ApplyYVel_NoLimit
 
06338.  
06339. CMP #OBJECT_MAXFALL
 
06340. BLS Object_ApplyYVel_NoLimit ; If Object's Y Vel < OBJECT_MAXFALL, jump to Object_ApplyYVel_NoLimit
 
06341.  
06342. LDA #OBJECT_MAXFALL
 
06343. STA <Objects_YVel,X ; Cap Y Velocity to OBJECT_MAXFALL
 
06344.  
06345. ; $DCD9
 
06346. Object_ApplyYVel_NoLimit:
 
06347. TXA
 
06348. ADD #(Objects_YVel - Objects_XVel)
 
06349. TAX ; Offset to Y velocities
 
06350.  
06351. JSR Object_AddVelFrac ; Apply the velocity to the object's position
 
06352.  
06353. LDX <SlotIndexBackup ; Restore X as Object slot index
 
06354.  
06355. RTS ; Return
 
06356.  
06357.  
06358. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06359. ; Object_ApplyXVel
 
06360. ;
 
06361. ; Adds the 4.4FP X velocity to object and will disable
 
06362. ; X Hi's application if the object wants it that way..
 
06363. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06364. ; $DCE4
 
06365. Object_ApplyXVel:
 
06366. JSR Object_AddVelFrac
 
06367.  
06368. LDY Level_7Vertical
 
06369. BEQ PRG000_DCFA ; If Level is NOT vertical, jump to PRG000_DCFA
 
06370.  
06371. ; Non-vertical levels...
 
06372.  
06373. PHA ; Save rollover value
 
06374.  
06375. LDY ObjGroupRel_Idx ; Get object's relative index
 
06376. LDA ObjectGroup_Attributes2,Y ; Get object's 2nd attribute
 
06377. AND #OA2_USE16BITX
 
06378. BNE PRG000_DCF9 ; If OA2_USE16BITX is set, jump to PRG000_DCF9
 
06379.  
06380. STA <Objects_XHi,X ; Otherwise, Object's X Hi is zeroed
 
06381.  
06382. PRG000_DCF9:
 
06383. PLA ; Restore rollover value
 
06384.  
06385. PRG000_DCFA:
 
06386. RTS ; Return
 
06387.  
06388. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06389. ; Object_AddVelFrac
 
06390. ;
 
06391. ; Adds the 4.4FP velocity to X or Y of object
 
06392. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06393. Object_AddVelFrac:
 
06394. LDA <Objects_XVel,X ; Get Velocity
 
06395. ASL A
 
06396. ASL A
 
06397. ASL A
 
06398. ASL A ; Fractional part shifted up
 
06399. ADD Objects_XVelFrac,X
 
06400. STA Objects_XVelFrac,X ; Add to object's vel fractional accumulator
 
06401.  
06402. PHP ; Save CPU state
 
06403. PHP ; Save CPU state
 
06404.  
06405. LDY #$00 ; Y = 0 (positive high part)
 
06406.  
06407. LDA <Objects_XVel,X ; Get Velocity
 
06408. LSR A
 
06409. LSR A
 
06410. LSR A
 
06411. LSR A ; Whole part shifted down (integer)
 
06412. CMP #%00001000 ; Check the sign bit
 
06413. BLT PRG000_DD19 ; If the value was not negatively signed, jump to PRG000_DD19
 
06414. ORA #%11110000 ; Otherwise, apply a sign extension
 
06415. DEY ; Y = $FF (negative high part)
 
06416. PRG000_DD19:
 
06417. PLP ; Restore CPU state
 
06418.  
06419. PHA ; Save integer of velocity
 
06420.  
06421. ADC <Objects_X,X
 
06422. STA <Objects_X,X ; Add with carry
 
06423.  
06424. TYA ; A = $00 or $FF as appropriate
 
06425.  
06426. ADC <Objects_XHi,X
 
06427. STA <Objects_XHi,X ; Add to the high part
 
06428.  
06429. PLA ; Restore integer of Velocity
 
06430.  
06431. PLP ; Restore CPU state
 
06432.  
06433. ADC #$00
 
06434. STA Object_VelCarry ; Set to '1' if fractional part rolled over
 
06435.  
06436. RTS ; Return
 
06437.  
06438.  
06439. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06440. ; Level_ObjCalcXDiffs
 
06441. ;
 
06442. ; For a given object slot in 'X'...
 
06443. ; Returns: Temp_Var16 as pixel difference between Player and object X coordinates
 
06444. ; And 'Y' is set to 0 if Player is to the right of object, 1 if to the left
 
06445. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06446. ; $DD2C
 
06447. Level_ObjCalcXDiffs:
 
06448. LDA <Player_X
 
06449. SUB <Objects_X,X
 
06450. STA <Temp_Var16 ; Temp_Var16 = difference between Player's X and object's X
 
06451.  
06452. LDY #$00 ; Y = 0
 
06453. LDA <Player_XHi
 
06454. SBC <Objects_XHi,X
 
06455. BPL PRG000_DD3C ; If Player's X Hi >= Object's X Hi, jump to PRG000_DD3C (RTS)
 
06456.  
06457. INY ; Otherwise Y = 1
 
06458.  
06459. PRG000_DD3C:
 
06460. RTS ; Return
 
06461.  
06462.  
06463. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06464. ; Level_ObjCalcYDiffs
 
06465. ;
 
06466. ; For a given object slot in 'X'...
 
06467. ; Returns: Temp_Var16 as pixel difference between Player and object Y coordinates
 
06468. ; And 'Y' is set to 0 if Player is lower than object, 1 if higher
 
06469. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06470. ; $DD3D
 
06471. Level_ObjCalcYDiffs:
 
06472. LDA <Player_Y
 
06473. SUB <Objects_Y,X
 
06474. STA <Temp_Var16 ; Temp_Var16 = difference between Player's Y and object's Y
 
06475.  
06476. LDY #$00 ; Y = 0
 
06477. LDA <Player_YHi
 
06478. SBC <Objects_YHi,X
 
06479. BPL PRG000_DD4D ; If Player's Y Hi >= Object's Y Hi, jump to PRG000_DD4D (RTS)
 
06480.  
06481. INY ; Ohterwise Y = 1
 
06482.  
06483. PRG000_DD4D:
 
06484. RTS ; Return
 
06485.  
06486.  
06487. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06488. ; Negate
 
06489. ;
 
06490. ; "NEG" is not REALLY an opcode of its own
 
06491. ; This makes it a subroutine, though...
 
06492. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06493. ; $DD4E
 
06494. Negate:
 
06495. NEG
 
06496. RTS ; Return
 
06497.  
06498.  
06499. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06500. ; Object_AnySprOffscreen
 
06501. ;
 
06502. ; Returns non-zero if any flags are set on Objects_SprHVis or Objects_SprVVis
 
06503. ; (i.e. if any sprites are off-screen)
 
06504. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
06505. ; $DD54
 
06506. Object_AnySprOffscreen:
 
06507. LDA Objects_SprHVis,X
 
06508. ORA Objects_SprVVis,X
 
06509. RTS ; Return
 
06510.  
06511.  
06512. ; FIXME: Anybody want to claim this?
 
06513. ; Appears it would return a free object slot
 
06514. ; $DD5B
 
06515. LDY #$04 ; Y = 4
 
06516. PRG000_DD5D:
 
06517. LDA Objects_State,Y
 
06518. BEQ PRG000_DD65 ; If this object slot is dead/empty, jump to PRG000_DD65
 
06519.  
06520. DEY ; Y--
 
06521. BPL PRG000_DD5D ; While Y >= 0, loop
 
06522.  
06523. PRG000_DD65:
 
06524. RTS ; Return
 
06525.  
06526.  
06527. ; FIXME: Anybody want to claim this?
 
06528. ; Appears to apply offsets to Player X/Y (Temp_Var11/Temp_Var10) and get a tile there
 
06529. ; $DD66
 
06530.  
06531. ; Temp_Var13 = Player_YHi
 
06532. LDA <Player_YHi
 
06533. STA <Temp_Var13
 
06534.  
06535. ; Temp_Var14 = Temp_Var10 (? input var?) + Player_Y
 
06536. LDA <Temp_Var10
 
06537. ADD <Player_Y
 
06538. STA <Temp_Var14
 
06539.  
06540. BCC PRG000_DD75 ; If no carry, jump to PRG000_DD75
 
06541.  
06542. INC <Temp_Var13 ; Apply carry
 
06543.  
06544. PRG000_DD75:
 
06545. LDA <Temp_Var13
 
06546. BNE PRG000_DD84 ; If Temp_Var13 <> 0 (Player is on lower screen), jump to PRG000_DD84
 
06547.  
06548. ; Temp_Var14 -= 16
 
06549. LDA <Temp_Var14
 
06550. SUB #16
 
06551. STA <Temp_Var14
 
06552. BCS PRG000_DD84 ; If carry set, jump to PRG000_DD84
 
06553.  
06554. DEC <Temp_Var13 ; Apply carry
 
06555.  
06556. PRG000_DD84:
 
06557.  
06558. ; Temp_Var15 = Player_XHi
 
06559. LDA <Player_XHi
 
06560. STA <Temp_Var15
 
06561.  
06562. LDA <Temp_Var11
 
06563. BPL PRG000_DD8E ; If Temp_Var11 (? input var?) >= 0, jump to PRG000_DD8E
 
06564.  
06565. DEC <Temp_Var15 ; Otherwise, Temp_Var15--
 
06566.  
06567. PRG000_DD8E:
 
06568.  
06569. ; Temp_Var16 = Player_X + Temp_Var11 (? input var)
 
06570. LDA <Player_X
 
06571. ADD <Temp_Var11
 
06572. STA <Temp_Var16
 
06573. BCC PRG000_DD99 ; If no carry, jump to PRG000_DD99
 
06574.  
06575. INC <Temp_Var15 ; Apply carry
 
06576.  
06577. PRG000_DD99:
 
06578. ; Backup X/Y
 
06579. STY <Temp_Var10
 
06580. STX <Temp_Var11
 
06581.  
06582. JSR Player_GetTileAndSlope_Normal
 
06583.  
06584. ; Restore X/Y
 
06585. LDY <Temp_Var10
 
06586. LDX <Temp_Var11
 
06587. RTS ; Return
 
06588.  
06589.  
06590.  
06591. ; Initializes a "block bump" effect, if one of the 2 slots is open...
 
06592. BlockBump_Init:
 
06593. LDY #$00 ; Y = 0
 
06594. LDA Level_BlkBump,Y
 
06595. BEQ PRG000_DDB2 ; If block bump slot 1 is empty, jump to PRG000_DDB2
 
06596.  
06597. INY ; Y = 1
 
06598. LDA Level_BlkBump,Y
 
06599. BNE PRG000_DDCB ; If block bump slot 2 is not empty, jump to PRG000_DDCB (RTS)
 
06600.  
06601. PRG000_DDB2:
 
06602. LDA <Temp_Var12
 
06603. STA Level_BlkBump,Y ; Store tile-behind effect
 
06604.  
06605. ; Temp_Var13 / Temp_Var14 -- Y Hi and Lo
 
06606. ; Temp_Var15 / Temp_Var16 -- X Hi and Lo
 
06607.  
06608. LDA <Temp_Var15
 
06609. STA Level_BlkBump_XHi,Y
 
06610.  
06611.  
06612. LDA <Temp_Var16
 
06613. STA Level_BlkBump_XLo,Y
 
06614.  
06615. LDA <Temp_Var13
 
06616. STA Level_BlkBump_YHi,Y
 
06617.  
06618. LDA <Temp_Var14
 
06619. STA Level_BlkBump_YLo,Y
 
06620.  
06621. PRG000_DDCB:
 
06622. RTS ; Return
 
06623.  
06624. InventoryRow_BaseIndex:
 
06625. ; Base index in inventory, per row
 
06626. .byte $15, $0E, $07, $00
 
06627.  
06628. Inventory_DestX:
 
06629. ; Destination X coordinate per inventory slot
 
06630. .byte $48, $60, $78, $90, $A8, $C0, $D8
 
06631.  
06632.  
06633. ; This sets up the "pop out" item you get when you open a treasure box
 
06634. ToadHouse_GiveItem:
 
06635.  
06636. ; X = Inventory item index you are getting from Toad
 
06637. ; A = X position of box
 
06638.  
06639. STX Objects_Frame ; Store item you are getting
 
06640. STA <Objects_X ; X position of box that was opened
 
06641.  
06642. LSR A
 
06643. LSR A
 
06644. STA <Temp_Var1 ; Temp_Var1 = X position / 4
 
06645.  
06646. LDY Player_Current
 
06647. BEQ PRG000_DDE7 ; If Player is Mario, jump to PRG000_DDE7
 
06648.  
06649. LDY #(Inventory_Items2 - Inventory_Items) ; Y = offset to Luigi's items
 
06650.  
06651. PRG000_DDE7:
 
06652. LDX #$00 ; X = 0
 
06653.  
06654. PRG000_DDE9:
 
06655. LDA Inventory_Items,Y ; Get item currently in slot
 
06656. BEQ PRG000_DDF4 ; If slot is empty, jump to PRG000_DDF4
 
06657.  
06658. INY ; Y++ (next item slot)
 
06659. INX ; X++ (counter)
 
06660. CPX #(Inventory_Cards - Inventory_Items - 1)
 
06661. BLT PRG000_DDE9 ; While potential item slots remain, loop!
 
06662.  
06663. PRG000_DDF4:
 
06664. STY Objects_Var1 ; Obj var 1 stores target inventory index
 
06665.  
06666. ; The following basically does a MOD 7 against the non-offsetted inventory index
 
06667. TXA ; non-offset inventory index -> 'A'
 
06668. LDY #$03 ; Y = 3 (up to four rows of inventory)
 
06669. PRG000_DDFA:
 
06670. CMP #$07
 
06671. BLT PRG000_DE03 ; If index has arrived in a inventory row-relative spot, jump to PRG000_DE03
 
06672. SBC #$07 ; Otherwise subtract 7...
 
06673. DEY ; Y-- (go one row higher!)
 
06674. BNE PRG000_DDFA ; If not out of rows, loop!
 
06675. PRG000_DE03:
 
06676.  
06677. TAX ; Mod value -> 'X'
 
06678.  
06679. LDA InventoryRow_BaseIndex,Y ; Get base inventory index for this row
 
06680. STA Objects_Var2 ; -> Objects_Var2
 
06681.  
06682. ; Configure the treasure box item to pop out!
 
06683. LDA #OBJSTATE_NORMAL
 
06684. STA Objects_State
 
06685.  
06686. LDA #OBJ_TOADHOUSEITEM
 
06687. STA Level_ObjectID
 
06688.  
06689. LDA #$90
 
06690. STA <Objects_Y
 
06691.  
06692. ; Calculates a good fly rate so item lands in the inventory slot
 
06693. LDA Inventory_DestX,X ; Get target X coordinate for object
 
06694. LSR A
 
06695. LSR A
 
06696. SUB <Temp_Var1 ; was object X / 4
 
06697. STA <Objects_XVel ; Set as X velocity
 
06698.  
06699. LDA #-$30
 
06700. STA <Objects_YVel ; Object's Y velocity = -$30
 
06701.  
06702. LDA #$00
 
06703. STA Objects_XVelFrac ; Objects_XVelFrac = 0
 
06704. STA THouse_UnusedFlag ; THouse_UnusedFlag = 0 (set here, never used otherwise)
 
06705.  
06706. LDA #$ff
 
06707. STA Objects_Timer ; Objects_Timer = $FF
 
06708. STA <Objects_Var4 ; Objects_Var4 = $FF
 
06709.  
06710. ; Play Inventory flip noise
 
06711. LDA Sound_QMap
 
06712. ORA #SND_MAPINVENTORYFLIP
 
06713. STA Sound_QMap
 
06714.  
06715. RTS ; Return
 
06716.  
06717.  
06718. AScrlURDiag_HandleWrap:
 
06719. LDA AScrlURDiag_WrapState
 
06720. STA AScrlURDiag_WrapState_Copy ; AScrlURDiag_WrapState_Copy = AScrlURDiag_WrapState
 
06721. JSR AScrlURDiag_NoWrapAbort ; Will not return here if AScrlURDiag_WrapState_Copy not set or gameplay halted!
 
06722.  
06723. LDY #$00 ; Y = 0
 
06724.  
06725. LDA Level_AScrlVVelCarry
 
06726. LSR A
 
06727. BCC PRG000_DE53 ; If Level_AScrlVVelCarry = 0, jump to PRG000_DE53
 
06728.  
06729. INY ; Y = 1
 
06730. DEC Level_ScrollDiffH ; Level_ScrollDiffH--
 
06731.  
06732. PRG000_DE53:
 
06733. LDA Level_ScrollDiffH
 
06734. STA AScrlURDiag_OffsetX ; AScrlURDiag_OffsetX = Level_ScrollDiffH
 
06735.  
06736. STY Level_ScrollDiffH ; Level_ScrollDiffH = 0 or 1
 
06737.  
06738. ADD <Player_X
 
06739. STA <Player_X ; Player_X += Level_ScrollDiffH
 
06740. BCC PRG000_DE65 ; If no carry, jump to PRG000_DE65
 
06741.  
06742. INC <Player_XHi ; Otherwise, apply carry
 
06743.  
06744. PRG000_DE65:
 
06745. LDY #$00 ; Y = 0
 
06746.  
06747. LDA Level_AScrlVVelCarry
 
06748. LSR A
 
06749. BCC PRG000_DE71 ; If no autoscroll vertical velocity carry, jump to PRG000_DE71
 
06750.  
06751. DEY ; Y = -1
 
06752. INC Level_ScrollDiffV
 
06753.  
06754. PRG000_DE71:
 
06755. LDA Level_ScrollDiffV
 
06756. STA AScrlURDiag_OffsetY ; AScrlURDiag_OffsetY = Level_ScrollDiffV
 
06757.  
06758. STY Level_ScrollDiffV ; Level_ScrollDiffV = 0 or -1
 
06759.  
06760. LDY <Player_InAir
 
06761. BEQ PRG000_DE89 ; If Player is not mid air, jump to PRG000_DE89
 
06762.  
06763. LDY #$00 ; Y = 0
 
06764.  
06765. ADD Level_ScrollDiffV ; Level_ScrollDiffV is 0 or -1 right now
 
06766. CMP #$ff
 
06767. BNE PRG000_DE89
 
06768. DEY ; Y = -1
 
06769.  
06770. PRG000_DE89:
 
06771. ADD <Player_Y
 
06772. STA <Player_Y
 
06773. TYA
 
06774. ADC <Player_YHi
 
06775. STA <Player_YHi
 
06776.  
06777. RTS ; Return
 
06778.  
06779. AScrlURDiag_CheckWrapping:
 
06780. JSR AScrlURDiag_NoWrapAbort ; Will not return here if AScrlURDiag_WrapState_Copy is not set or gameplay halted!
 
06781.  
06782. LDA <Objects_X,X
 
06783. ADD AScrlURDiag_OffsetX
 
06784. STA <Objects_X,X
 
06785. BCC PRG000_DEA3 ; If no carry, jump to PRG000_DEA3
 
06786. INC <Objects_XHi,X ; Otherwise, apply carry
 
06787. PRG000_DEA3:
 
06788.  
06789. LDA <Objects_Y,X
 
06790. ADD AScrlURDiag_OffsetY
 
06791. STA <Objects_Y,X
 
06792. BCC PRG000_DEAF ; If no carry, jump to PRG000_DEAF
 
06793. INC <Objects_YHi,X ; Otherwise, apply carry
 
06794.  
06795. PRG000_DEAF:
 
06796. RTS ; Return
 
06797.  
06798.  
06799. AScrlURDiag_NoWrapAbort:
 
06800. LDA AScrlURDiag_WrapState_Copy
 
06801. BEQ PRG000_DEB9 ; If diagonal autoscroller is not wrapping, jump to PRG000_DEB9
 
06802.  
06803. LDA <Player_HaltGame
 
06804. BEQ PRG000_DEBB ; If gameplay is not halted, jump to PRG000_DEBB (RTS)
 
06805.  
06806. PRG000_DEB9:
 
06807. ; If NOT AScrlURDiag_WrapState_Copy or if gameplay is halted, do not return to caller!!
 
06808. PLA
 
06809. PLA ; Pull return address
 
06810.  
06811. PRG000_DEBB:
 
06812. RTS ; Return
 
06813.  
06814.  
06815. ASHIM .func \1-AScroll_Movement-1
 
06816. ; This is the initial movement table for horizontal auto scroll levels, minus 1
 
06817. ; Level_AScrlLimitSel selects which entry to use, which sets Level_AScrlVar (the actual index value)
 
06818. AScroll_HorizontalInitMove:
 
06819. .byte ASHIM(ASM_World_36_14) ; 0 World 3-6 / 1-4
 
06820. .byte ASHIM(ASM_W3_Airship) ; 1 World 3 Airship
 
06821. .byte ASHIM(ASM_World_62) ; 2 World 6-2
 
06822. .byte ASHIM(ASM_W5_Airship) ; 3 World 5 Airship
 
06823. .byte ASHIM(ASM_UNK4) ; 4
 
06824. .byte ASHIM(ASM_W4Airship) ; 5 World 4 Airship
 
06825. .byte ASHIM(ASM_W6Airship) ; 6 World 6 Airship
 
06826. .byte ASHIM(ASM_World_56) ; 7 World 5-6
 
06827. .byte ASHIM(ASM_UNK8) ; 8
 
06828. .byte ASHIM(ASM_UNK9) ; 9
 
06829. .byte ASHIM(ASM_World_67) ; A World 6-7
 
06830. .byte ASHIM(ASM_W1Airship) ; B World 1 Airship
 
06831. .byte ASHIM(ASM_W7Airship) ; C World 7 Airship
 
06832. .byte ASHIM(ASM_W8Airship) ; D World 8 Airship
 
06833. .byte ASHIM(ASM_W8Battleship) ; E World 8 Battleship
 
06834. .byte ASHIM(ASM_World_74) ; F World 7-4
 
06835. .byte ASHIM(ASM_W1CoinHeaven) ; 10
 
06836. .byte ASHIM(ASM_CoinShip) ; 11 Coin Ship
 
06837. .byte ASHIM(ASM_UNK12) ; 12
 
06838. .byte ASHIM(ASM_World8Tank1) ; 13 World 8 Tank 1
 
06839. .byte ASHIM(ASM_World8Tank2) ; 14 World 8 Tank 2
 
06840. .byte ASHIM(ASM_Terminator) ; 15 ** Terminator Only (because it seeks ahead to see the terminating movement index)
 
06841.  
06842. Video_3CMMushTop:
 
06843. vaddr $208D
 
06844. .byte VU_REPEAT | $06, $A9
 
06845. vaddr $20AB
 
06846. .byte VU_REPEAT | $04, $A9
 
06847. vaddr $20B1
 
06848. .byte VU_REPEAT | $04, $A9
 
06849. vaddr $20CA
 
06850. .byte VU_REPEAT | $05, $A9
 
06851. vaddr $20D1
 
06852. .byte VU_REPEAT | $05, $A9
 
06853. vaddr $214A
 
06854. .byte VU_VERT | VU_REPEAT | $03, $A9
 
06855. .byte $00 ; Terminator
 
06856.  
06857. Video_3CMMushLeft:
 
06858. vaddr $20E9
 
06859. .byte $05, $A9, $A9, $FC, $A9, $A9
 
06860. vaddr $20F2
 
06861. .byte $05, $A9, $A9, $FC, $A9, $A9
 
06862. vaddr $2128
 
06863. .byte VU_VERT | VU_REPEAT | $07, $A9
 
06864. vaddr $2109
 
06865. .byte VU_VERT | VU_REPEAT | $06, $A9
 
06866. vaddr $214D
 
06867. .byte VU_VERT | VU_REPEAT | $03, $A9
 
06868. .byte $00 ; Terminator
 
06869.  
06870. Video_3CMMushMid:
 
06871. vaddr $212E
 
06872. .byte VU_VERT | VU_REPEAT | $08, $A9
 
06873. vaddr $212F
 
06874. .byte VU_VERT | VU_REPEAT | $05, $A9
 
06875. vaddr $2130
 
06876. .byte VU_VERT | VU_REPEAT | $05, $A9
 
06877. vaddr $2131
 
06878. .byte VU_VERT | VU_REPEAT | $08, $A9
 
06879. vaddr $2152
 
06880. .byte VU_VERT | VU_REPEAT | $03, $A9
 
06881. .byte $00 ; Terminator
 
06882.  
06883. Video_3CMMushRight:
 
06884. vaddr $2155
 
06885. .byte VU_VERT | VU_REPEAT | $03, $A9
 
06886. vaddr $2116
 
06887. .byte VU_VERT | VU_REPEAT | $06, $A9
 
06888. vaddr $2137
 
06889. .byte VU_VERT | VU_REPEAT | $07, $A9
 
06890. vaddr $21CB
 
06891. .byte VU_REPEAT | $0A, $A9
 
06892. vaddr $21E9
 
06893. .byte VU_VERT | VU_REPEAT | $02, $A9
 
06894. .byte $00 ; Terminator
 
06895.  
06896. Video_3CMMushBot:
 
06897. vaddr $21EA
 
06898. .byte VU_VERT | VU_REPEAT | $04, $A9
 
06899. vaddr $21EB
 
06900. .byte VU_VERT | $04, $A9, $FC, $FC, $A9
 
06901. vaddr $21F4
 
06902. .byte VU_VERT | $04, $A9, $FC, $FC, $A9
 
06903. vaddr $21F5
 
06904. .byte VU_VERT | VU_REPEAT | $04, $A9
 
06905. vaddr $21F6
 
06906. .byte VU_VERT | VU_REPEAT | $02, $A9
 
06907. vaddr $226B
 
06908. .byte VU_REPEAT | $0A, $A9
 
06909. .byte $00 ; Terminator
 
06910.  
06911. Video_3CMFlowTop:
 
06912. vaddr $208B
 
06913. .byte VU_REPEAT | $0A, $A9
 
06914. vaddr $20A9
 
06915. .byte VU_REPEAT | $03, $A9
 
06916. vaddr $20B4
 
06917. .byte VU_REPEAT | $03, $A9
 
06918. vaddr $20C8
 
06919. .byte VU_REPEAT | $02, $A9
 
06920. vaddr $20D6
 
06921. .byte VU_REPEAT | $02, $A9
 
06922. vaddr $20E8
 
06923. .byte VU_VERT | VU_REPEAT | $03, $A9
 
06924. vaddr $20EB
 
06925. .byte VU_REPEAT | $03, $A9
 
06926. vaddr $210B
 
06927. .byte $01, $A9
 
06928. .byte $00 ; Terminator
 
06929.  
06930. Video_3CMFlowDiag:
 
06931. vaddr $2148
 
06932. .byte VU_REPEAT | $02, $A9
 
06933. vaddr $20CD
 
06934. .byte VU_REPEAT | $06, $A9
 
06935. vaddr $20F2
 
06936. .byte VU_REPEAT | $03, $A9
 
06937. vaddr $20F7
 
06938. .byte VU_VERT | VU_REPEAT | $03, $A9
 
06939. vaddr $214D
 
06940. .byte VU_REPEAT | $06, $A9
 
06941. vaddr $212B
 
06942. .byte VU_REPEAT | $03, $A9
 
06943. vaddr $2156
 
06944. .byte VU_REPEAT | $02, $A9
 
06945. vaddr $21A9
 
06946. .byte VU_REPEAT | $02, $A9
 
06947. .byte $00 ; Terminator
 
06948.  
06949. Video_3CMFlowMid:
 
06950. vaddr $2114
 
06951. .byte $01, $A9
 
06952. vaddr $210E
 
06953. .byte VU_REPEAT | $04, $A9
 
06954. vaddr $2132
 
06955. .byte VU_REPEAT | $03, $A9
 
06956. vaddr $2169
 
06957. .byte VU_REPEAT | $03, $A9
 
06958. vaddr $2174
 
06959. .byte VU_REPEAT | $03, $A9
 
06960. vaddr $218B
 
06961. .byte VU_REPEAT | $0A, $A9
 
06962. vaddr $21B5
 
06963. .byte VU_REPEAT | $02, $A9
 
06964. vaddr $21D7
 
06965. .byte VU_VERT | VU_REPEAT | $03, $A9
 
06966. .byte $00 ; Terminator
 
06967.  
06968. Video_3CMFlowStem:
 
06969. vaddr $21AE
 
06970. .byte VU_VERT | VU_REPEAT | $06, $A9
 
06971. vaddr $21B1
 
06972. .byte VU_VERT | VU_REPEAT | $06, $A9
 
06973. vaddr $21C8
 
06974. .byte VU_VERT | VU_REPEAT | $03, $A9
 
06975. vaddr $21CB
 
06976. .byte VU_REPEAT | $02, $A9
 
06977. vaddr $21D3
 
06978. .byte VU_REPEAT | $02, $A9
 
06979. vaddr $21EA
 
06980. .byte $04, $A9, $FC, $FC, $A9
 
06981. vaddr $21F2
 
06982. .byte $04, $A9, $FC, $FC, $A9
 
06983. .byte $00 ; Terminator
 
06984.  
06985. Video_3CMFlowBot
 
06986. vaddr $220B
 
06987. .byte $01, $A9
 
06988. vaddr $2214
 
06989. .byte $01, $A9
 
06990. vaddr $2229
 
06991. .byte $04, $A9, $FC, $FC, $A9
 
06992. vaddr $2233
 
06993. .byte $04, $A9, $FC, $FC, $A9
 
06994. vaddr $224A
 
06995. .byte $04, $A9, $A9, $FC, $A9
 
06996. vaddr $2252
 
06997. .byte $04, $A9, $FC, $A9, $A9
 
06998. vaddr $226C
 
06999. .byte VU_REPEAT | $08, $A9
 
07000. .byte $00 ; Terminator
 
07001.  
07002.