Files
alttpr-baserom/inventory.asm
cassidoxa 788cceaab9 Continue labeling and documentation in ram.asm, main rando block
Deleted several unused modules and some commented code
Reorganized some routines to clean up modules
Moved some memory into mirrored WRAM
Refactored NMI hook aux routine
Removed old fake flipper fix
2022-11-16 21:38:28 -05:00

1078 lines
33 KiB
NASM

;================================================================================
; Inventory Updates
;================================================================================
; InventoryTracking
; brmpnskf ------oq
; b = blue boomerang | -
; r = red boomerang | -
; m = mushroom current | -
; p = magic powder | -
; n = mushroom past | -
; s = shovel | -
; k = fake flute | o = any bomb acquired from item location
; f = working flute | q = quickswap locked
;--------------------------------------------------------------------------------
; BowTracking
; Item Tracking Slot #2
; bsp-----
; b = bow
; s = silver arrow bow
; p = 2nd progressive bow
; -
; -
; -
; -
; -
;--------------------------------------------------------------------------------
; ProcessMenuButtons:
; out: Carry - 0 = No Button, 1 = Yes Button
;--------------------------------------------------------------------------------
ProcessMenuButtons:
LDA.b $F4 : BIT.b #$40 : BNE .y_pressed ; check for P1 Y-button
BIT #$20 : BNE .sel_pressed ; check for P1 Select button
LDA.b $F0 : BIT.b #$20 : BNE .sel_held
.sel_unheld
LDA.l HudFlag : AND.b #$20 : BEQ +
LDA.l HudFlag : AND.b #$DF : STA.l HudFlag ; select is released, unset hud flag
LDA.b $1B : BEQ + ; skip if outdoors
LDA.b #$20 : STA.w $012F ; menu select sound
+
JSL.l ResetEquipment
+
.sel_held
CLC ; no buttons
RTL
.sel_pressed
LDA.l HudFlag : ORA.b #$20 : STA.l HudFlag ; set hud flag
LDA.b #$20 : STA.w $012F ; menu select sound
JSL.l ResetEquipment
RTL
.y_pressed ; Note: used as entry point by quickswap code. Must preserve X.
LDA.b #$10 : STA.w $0207
LDA.w $0202 ; check selected item
CMP.b #$02 : BNE + ; boomerang
LDA.l InventoryTracking : AND.b #$C0 : CMP.b #$C0 : BNE .errorJump ; make sure we have both boomerangs
LDA.l BoomerangEquipment : EOR.b #$03 : STA.l BoomerangEquipment ; swap blue & red boomerang
LDA.b #$20 : STA.w $012F ; menu select sound
JMP .captured
+ CMP #$01 : BNE + ; bow
LDA.l BowTracking : AND.b #$C0 : CMP.b #$C0 : BNE .errorJump ; make sure we have both bows
PHX : LDX.b #$00 ; scan ancilla table for arrows
-- : CPX.b #$0A : !BGE ++
LDA.w $0C4A, X : CMP.b #$09 : BNE +++
PLX : BRA .errorJump2 ; found an arrow, don't allow the swap
+++
INX : BRA -- : ++
PLX
LDA.l SilverArrowsUseRestriction : BEQ ++
LDA.b RoomIndex : ORA.b RoomIndex+1 : BEQ ++ ; not in ganon's room in restricted mode
LDA.l BowEquipment : CMP.b #$03 : !BLT .errorJump : !SUB #$02 : STA.l BowEquipment
BRA .errorJump2
++
LDA.l BowEquipment : !SUB #$01 : EOR.b #$02 : !ADD #$01 : STA.l BowEquipment ; swap bows
LDA.b #$20 : STA.w $012F ; menu select sound
JMP .captured
+ BRA +
.errorJump
BRA .errorJump2
+ CMP #$05 : BNE + ; powder
LDA.l InventoryTracking : AND.b #$30 : CMP.b #$30 : BNE .errorJump ; make sure we have mushroom & magic powder
LDA.l PowderEquipment : EOR.b #$03 : STA.l PowderEquipment ; swap mushroom & magic powder
LDA.b #$20 : STA.w $012F ; menu select sound
JMP .captured
+ BRA +
.errorJump2
BRA .error
+ CMP #$0D : BNE + ; flute
LDA.w $037A : CMP.b #$01 : BEQ .midShovel ; inside a shovel animation, force the shovel & make error sound
LDA.l InventoryTracking : BIT.b #$04 : BEQ .error ; make sure we have shovel
AND.b #$03 : BEQ .error ; make sure we have one of the flutes
LDA.l FluteEquipment : CMP.b #01 : BNE .toShovel ; not shovel
LDA.l InventoryTracking : AND.b #$01 : BEQ .toFakeFlute ; check for real flute
LDA.b #$03 ; set real flute
BRA .fluteSuccess
.toFakeFlute
LDA.b #$02 ; set fake flute
BRA .fluteSuccess
.toShovel
LDA.b #$01 ; set shovel
.fluteSuccess
STA.l FluteEquipment ; store set item
LDA.b #$20 : STA.w $012F ; menu select sound
BRA .captured
+
CMP.b #$10 : BNE .error : JSL.l ProcessBottleMenu : BRA .captured : +
CLC
RTL
.midShovel
.error
LDA.b #$3C : STA.w $012E ; error sound
.captured
SEC
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
;ProcessBottleMenu:
;--------------------------------------------------------------------------------
ProcessBottleMenu:
LDA.l BottleIndex ; check bottle state
BEQ .no_bottles ; skip if we have no bottles
PHX
INC : CMP.b #$05 : !BLT + : LDA.b #$01 : + ;increment and wrap 1-4
TAX : LDA.l BottleContents-1, X ; check bottle
BNE + : LDX.b #$01 : + ; wrap if we reached the last bottle
TXA : STA.l BottleIndex ; set bottle index
LDA.b #$20 : STA.w $012F ; menu select sound
PLX
.no_bottles
LDA.b #$00 ; pretend like the controller state was 0 from the overridden load
RTL
; .y_not_pressed
; LDA.b $F4 : AND.b #$0C ; thing we wrote over - load controller state
;RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
;OpenBottleMenu:
;--------------------------------------------------------------------------------
OpenBottleMenu:
LDA.b $F6 : AND.b #$40 : BEQ .x_not_pressed ; skip if X is not down
LDA.b #$10 : STA.w $0207 ; set 16 frame cool off
LDA.b #$20 : STA.w $012F ; make menu sound
LDA.b #$07 : STA.w $0200 ; thing we wrote over - opens bottle menu
.x_not_pressed
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
;CloseBottleMenu:
;--------------------------------------------------------------------------------
CloseBottleMenu:
LDA.b $F6 : AND.b #$40 : BEQ .x_not_pressed ; skip if X is not down
LDA.b #$10 : STA.w $0207 ; set 16 frame cool off
LDA.b #$20 : STA.w $012F ; make menu sound
INC.w $0200 ; return to normal menu
STZ.w $0205
LDA.b #$00
RTL
.x_not_pressed
LDA.b $F4 : AND.b #$0C ; thing we wrote over (probably)
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; AddInventory:
;--------------------------------------------------------------------------------
macro TopHalf(address)
LDA.l <address> : !ADD #$10 : STA.l <address>
endmacro
macro BottomHalf(address)
PHA : PHX
LDA.l <address> : INC : AND.b #$0F : TAX
LDA.l <address> : AND.b #$F0 : STA.l <address>
TXA : ORA.l <address> : STA.l <address>
PLX : PLA
endmacro
;--------------------------------------------------------------------------------
FullInventoryExternal:
LDA.l StatsLocked : BEQ + : RTL : +
PHA : PHX : PHP : JMP AddInventory_incrementCounts
;--------------------------------------------------------------------------------
AddInventory:
PHA : PHX : PHP
CPY.b #$0C : BNE + ; Blue Boomerang
LDA.l InventoryTracking : ORA.b #$80 : STA.l InventoryTracking
JMP .incrementCounts
+ CPY.b #$2A : BNE + ; Red Boomerang
LDA.l InventoryTracking : ORA.b #$40 : STA.l InventoryTracking
JMP .incrementCounts
+ CPY.b #$29 : BNE + ; Mushroom
LDA.l InventoryTracking : ORA.b #$28 : STA.l InventoryTracking
JMP .incrementCounts
+ CPY.b #$0D : BNE + ; Magic Powder
LDA.l InventoryTracking : ORA.b #$10 : STA.l InventoryTracking
JMP .incrementCounts
+ CPY.b #$13 : BNE + ; Shovel
LDA.l InventoryTracking : ORA.b #$04 : STA.l InventoryTracking
JMP .incrementCounts
+ CPY.b #$14 : BNE + ; Flute (Inactive)
LDA.l InventoryTracking : ORA.b #$02 : STA.l InventoryTracking
JMP .incrementCounts
+ CPY.b #$4A : BNE + ; Flute (Active)
LDA.l InventoryTracking : ORA.b #$01 : STA.l InventoryTracking
JMP .incrementCounts
+ CPY.b #$0B : BNE + ; Bow
LDA.l ArrowMode : BNE +++
LDA.l BowTracking : ORA.b #$80 : STA.l BowTracking
+++
JMP .incrementCounts
+ CPY.b #$3A : BNE + ; Bow & Arrows
LDA.l BowTracking : ORA.b #$80 : STA.l BowTracking
JMP .incrementCounts
+ CPY.b #$3B : BNE + ; Bow & Silver Arrows
LDA.l BowTracking : ORA.b #$40 : STA.l BowTracking
LDA.l ArrowMode : BNE +++
LDA.l BowTracking : ORA.b #$80 : STA.l BowTracking ; activate wood arrows when not in rupee bow
+++
JMP .incrementCounts
+ CPY.b #$43 : BNE + ; Single arrow
LDA.l ArrowMode : BEQ +++
LDA.l BowTracking : ORA.b #$80 : STA.l BowTracking ; activate wood arrows in quick-swap
+++
JMP .incrementCounts
+ CPY.b #$58 : BNE + ; Upgrade-Only Silver Arrows
LDA.l BowTracking : ORA.b #$40 : STA.l BowTracking
+
.incrementCounts
LDA.l StatsLocked : BEQ + : JMP .done : +
; don't count any of this stuff
CPY.b #$20 : BNE + : JMP .itemCounts : + ; Crystal
CPY.b #$26 : BNE + : JMP .itemCounts : + ; Heart Piece Completion Heart
CPY.b #$2E : BNE + : JMP .itemCounts : + ; Red Potion (Refill)
CPY.b #$2F : BNE + : JMP .itemCounts : + ; Green Potion (Refill)
CPY.b #$30 : BNE + : JMP .itemCounts : + ; Blue Potion (Refill)
CPY.b #$37 : BNE + : JMP .itemCounts : + ; Pendant
CPY.b #$38 : BNE + : JMP .itemCounts : + ; Pendant
CPY.b #$39 : BNE + : JMP .itemCounts : + ; Pendant
CPY.b #$04 : !BLT .isSword ; Swords - Skip Shop/Fairy Check for Swords
CPY.b #$49 : BEQ .isSword
CPY.b #$50 : BEQ .isSword
CPY.b #$5E : BEQ .isSword
BRA +
.isSword
JMP .dungeonCounts
+
CPY.b #$3B : BNE + : JMP .dungeonCounts : + ; Silver Arrow Bow - Skip Shop/Fairy Check for Silver Arrow Bow
LDA.b $1B : BEQ ++ ; skip shop check if outdoors
LDA.w $02E9 : CMP.b #$01 : BEQ ++ ; skip shop check for chests
PHP : REP #$20 ; set 16-bit accumulator
LDA.w $048E
CMP.w #274 : BNE + : JMP .shop : + ; dark world death mountain shop, ornamental shield shop
CMP.w #271 : BNE + : JMP .shop : + ; villiage of outcasts shop, lumberjack shop, lake hylia shop, dark world magic shop
CMP.w #272 : BNE + : JMP .shop : + ; red shield shop
CMP.w #284 : BNE + : JMP .shop : + ; bomb shop
;CMP.w #265 : BNE + : JMP .shop : + ; potion shop - commented this out because it's easier to just block potion refills because this one interferes with the powder item being counted
;CMP.w #271 : BNE + : JMP .shop : + ; lake hylia shop
CMP.w #287 : BNE + : JMP .shop : + ; kakariko shop
CMP.w #255 : BNE + : JMP .shop : + ; light world death mountain shop
CMP.w #276 : BNE + : JMP .shop : + ; waterfall fairy
CMP.w #277 : BNE + : JMP .shop : + ; upgrade fairy (shop)
CMP.w #278 : BNE + : JMP .shop : + ; pyramid fairy
PLP : BRA ++
.shop
PLP : JMP .done
++
.dungeonCounts
LDA.b $1B : BNE + : JMP .fullItemCounts : +
SEP #$20 ; Set 8-bit Accumulator
LDA.w $040C ; get dungeon id
CMP.b #$FF : BEQ .fullItemCounts
CMP.l BallNChainDungeon : BNE +
CPY.b #$32 : BNE +
JMP .done
+
CMP.b #$04 : BCS +
LDA.l SewersLocations : INC : STA.l SewersLocations
LDA.l HCLocations : INC : STA.l HCLocations
BRA .fullItemCounts
+ LSR : TAX : LDA.l DungeonLocationsChecked, X : INC : STA.l DungeonLocationsChecked, X
++ CPX.b #$0D : BNE +
LDA.l BigKeyField : AND.b #$04 : BNE ++
JSR .incrementGTowerPreBigKey
++
+
; == END INDOOR-ONLY SECTION
.fullItemCounts
LDA.l BootsEquipment : BNE + ; Check for Boots
LDA.l PreBootsLocations : INC : STA.l PreBootsLocations ; Increment Pre Boots Counter
+
LDA.l MirrorEquipment : BNE + ; Check for Mirror
LDA.l PreMirrorLocations : INC : STA.l PreMirrorLocations ; Increment Pre Mirror Counter
+
LDA.l FluteEquipment : BNE + ; Check for Flute
LDA.l PreFluteLocations : INC : STA.l PreFluteLocations ; Increment Pre Mirror Counter
+
REP #$20
LDA.l TotalItemCounter : INC : STA.l TotalItemCounter ; Increment Item Total
SEP #$20
.itemCounts
CPY.b #$00 : BNE + ; Fighter's Sword & Fighter's Shield
LDX.b #$01
JSR .incrementSword
JSR .incrementShield
JMP .done
+ CPY.b #$01 : BNE + ; Master Sword
LDX.b #$02
JSR .incrementSword
JMP .done
+ CPY.b #$02 : BNE + ; Tempered Sword
LDX.b #$03
JSR .incrementSword
JMP .done
+ CPY.b #$03 : BNE + ; Golden Sword
LDX.b #$04
JSR .incrementSword
JMP .done
+ CPY.b #$04 : BNE + ; Fighter's Shield
LDX.b #$01
JSR .incrementShield
JMP .done
+ CPY.b #$05 : BNE + ; Red Shield
LDX.b #$02
JSR .incrementShield
JMP .done
+ CPY.b #$06 : BNE + ; Mirror Shield
LDX.b #$03
JSR .incrementShield
JMP .done
+ CPY.b #$07 : !BLT + ; Items $07 - $0D
CPY.b #$0E : !BGE +
JSR .incrementY
JMP .done
+ CPY.b #$14 : BNE + ; Flute (Inactive) - LEAVE THIS ABOVE THE 0F-16 CONDITION - kkat
JSR .stampFlute
JSR .incrementY
JMP .done
+ CPY.b #$0F : !BLT + ; Items $0F - $16
CPY.b #$17 : !BGE +
JSR .incrementY
JMP .done
+ CPY.b #$17 : BNE + ; Heart Piece
JSR .incrementHeartPiece
JMP .done
+ CPY.b #$18 : !BLT + ; Items $18 - $19
CPY.b #$1A : !BGE +
JSR .incrementY
JMP .done
+ CPY.b #$1A : BNE + ; Magic Mirror
JSR .stampMirror
JSR .incrementY
JMP .done
+ CPY.b #$1D : BNE + ; Book of Mudora - LEAVE THIS ABOVE THE 1B-1F CONDITION - kkat
JSR .incrementY
JMP .done
+ CPY.b #$1B : !BLT + ; Items $1B - $1F
CPY.b #$20 : !BGE +
JSR .incrementA
JMP .done
+ CPY.b #$20 : BNE + ; Crystal
JSR .incrementCrystal
JSR .setDungeonCompletion
JMP .done
+ CPY.b #$21 : BNE + ; Bug Net
JSR .incrementY
JMP .done
+ CPY.b #$22 : BNE + ; Blue Mail
LDX.b #$01
JSR .incrementMail
+ CPY.b #$23 : BNE + ; Red Mail
LDX.b #$02
JSR .incrementMail
+ CPY.b #$24 : BNE + ; Small Key
JSR .incrementKey
JMP .done
+ CPY.b #$25 : BNE + ; Compass
JSL MaybeFlagCompassTotalPickup
JSR .incrementCompass
JMP .done
+ CPY.b #$26 : BNE + ; Liar Heart (Container)
;JSR .incrementHeartContainer
JMP .done
+ CPY.b #$27 : BNE + ; 1 Bomb
JSR .maybeIncrementBombs
JMP .done
+ CPY.b #$28 : BNE + ; 3 Bombs
JSR .maybeIncrementBombs
JMP .done
+ CPY.b #$29 : BNE + ; Mushroom
JSR .incrementY
JMP .done
+ CPY.b #$2A : !BLT + ; Items $2A - $2D
CPY.b #$2E : !BGE +
JSR .incrementY
JMP .done
+ CPY.b #$31 : BNE + ; 10 Bombs
JSR .maybeIncrementBombs
JMP .done
+ CPY.b #$32 : BNE + ; Big Key
JSR .incrementBigKey
JMP .done
+ CPY.b #$33 : BNE + ; Map
JSR .incrementMap
JMP .done
+ CPY.b #$37 : !BLT + ; Items $37 - $39 - Pendants
CPY.b #$3A : !BGE +
JSR .incrementPendant
JSR .setDungeonCompletion
JMP .done
+ CPY.b #$3A : !BLT + ; Items $3A - $3B - Bow & Silver Arrows
CPY.b #$3C : !BGE +
JSR .incrementBow
JMP .done
+ CPY.b #$3C : BNE + ; Bottle w/Bee
JSR .incrementY
JMP .done
+ CPY.b #$3D : BNE + ; Bottle w/Fairy
JSR .incrementY
JMP .done
+ CPY.b #$3E : !BLT + ; Items $3E - $3F - Heart Containers
CPY.b #$40 : !BGE +
JSR .incrementHeartContainer
JMP .done
+ CPY.b #$48 : BNE + ; Bottle w/Gold Bee
JSR .incrementY
JMP .done
+ CPY.b #$49 : BNE + ; Fighter's Sword
LDX #$01
JSR .incrementSword
JMP .done
+ CPY.b #$4A : BNE + ; Flute (Active)
JSR .stampFlute
JSR .incrementY
JMP .done
+ CPY.b #$4B : BNE + ; Pegasus Boots
JSR .stampBoots
JSR .incrementA
JMP .done
+ CPY.b #$4C : BNE + ; 50 Bomb Capacity Upgrade
JSR .incrementCapacity
JSR .maybeIncrementBombs
JMP .done
+ CPY.b #$4D : !BLT + ; Items $4D - $4F - Capacity Upgrades
CPY.b #$50 : !BGE +
JSR .incrementCapacity
JMP .done
+ CPY.b #$50 : BNE + ; Master Sword (Safe)
LDX #$02
JSR .incrementSword
JMP .done
+ CPY.b #$51 : BNE + ; 5 Bomb Capacity Upgrade
LDX #$02
JSR .maybeIncrementBombs
JMP .done
+ CPY.b #$52 : BNE + ; 10 Bomb Capacity Upgrade
LDX #$02
JSR .maybeIncrementBombs
JMP .done
+ CPY.b #$51 : !BLT + ; Items $51 - $54 - Capacity Upgrades
CPY.b #$55 : !BGE +
JSR .incrementCapacity
JMP .done
+ CPY.b #$58 : BNE + ; Upgrade-Only Silver Arrows
JSR .incrementBow
JMP .done
+ CPY.b #$5E : BNE + ; Progressive Sword
LDA.l SwordEquipment : INC : TAX
JSR .incrementSword
JMP .done
+ CPY.b #$5F : BNE + ; Progressive Shield
LDA.l ShieldEquipment : INC : TAX
JSR .incrementShield
JMP .done
+ CPY.b #$60 : BNE + ; Progressive Armor
LDA.l ArmorEquipment : INC : TAX
JSR .incrementMail
JMP .done
+ CPY.b #$61 : BNE + ; Progressive Lifting Glove
JSR .incrementA
JMP .done
+ CPY.b #$64 : !BLT + ; Items $64 & $65 - Progressive Bow
CPY.b #$66 : !BGE +
JSR .incrementBow
JMP .done
+ CPY.b #$70 : !BLT + ; Items $70 - $7F - Free Maps
CPY.b #$80 : !BGE +
JSR .incrementMap
JMP .done
+ CPY.b #$80 : !BLT + ; Items $80 - $8F - Free Compasses
CPY.b #$90 : !BGE +
JSL MaybeFlagCompassTotalPickup
JSR .incrementCompass
JMP .done
+ CPY.b #$90 : !BLT + ; Items $90 - $9F - Free Big Keys
CPY.b #$A0 : !BGE +
JSR .incrementBigKey
JMP .done
+ CPY.b #$A0 : !BLT + ; Items $A0 - $AF - Free Small Keys
CPY.b #$B0 : !BGE +
JSR .incrementKey
JMP .done
+
.done
PLP : PLX : PLA
RTL
; WHICH BEE IS BOTTLED?
; MAKE SURE FAIRY FOUNTAINS DON'T FUCK THE COUNTS UP
.stampSword
REP #$20 ; set 16-bit accumulator
LDA.l SwordTime : BNE +
LDA.l SwordTime+2 : BNE +
LDA.l NMIFrames : STA.l SwordTime
LDA.l NMIFrames+2 : STA.l SwordTime+2
+
SEP #$20 ; set 8-bit accumulator
RTS
.stampBoots
REP #$20 ; set 16-bit accumulator
LDA.l BootsTime : BNE +
LDA.l BootsTime+2 : BNE +
LDA.l NMIFrames : STA.l BootsTime
LDA.l NMIFrames+2 : STA.l BootsTime+2
+
SEP #$20 ; set 8-bit accumulator
RTS
.stampFlute
REP #$20 ; set 16-bit accumulator
LDA.l FluteTime : BNE +
LDA.l FluteTime+2 : BNE +
LDA.l NMIFrames : STA.l FluteTime
LDA.l NMIFrames+2 : STA.l FluteTime+2
+
SEP #$20 ; set 8-bit accumulator
RTS
.stampMirror
REP #$20 ; set 16-bit accumulator
LDA.l MirrorTime : BNE +
LDA.l MirrorTime+2 : BNE +
LDA.l NMIFrames : STA.l MirrorTime
LDA.l NMIFrames+2 : STA.l MirrorTime+2
+
SEP #$20 ; set 8-bit accumulator
RTS
.incrementSword
JSR .stampSword
LDA.l HighestSword
INC : STA.b Scrap04 : CPX.b Scrap04 : !BLT + ; don't increment unless we're getting a better sword
TXA : STA.l HighestSword
+
RTS
.incrementShield
LDA.l HighestShield
INC : STA.b Scrap04 : CPX.b Scrap04 : !BLT + ; don't increment unless we're getting a better shield
TXA : STA.l HighestShield
+
RTS
.incrementBow
LDA.l BowEquipment : BNE .dontCount ; Don't increment Y item count for extra bows
.incrementY
LDA.l YAItemCounter : !ADD #$08 : STA.l YAItemCounter
.dontCount
RTS
.incrementA
LDA.l YAItemCounter : INC : AND.b #$07 : TAX
LDA.l YAItemCounter : AND.b #$F8 : STA.l YAItemCounter
TXA : ORA.l YAItemCounter : STA.l YAItemCounter
RTS
.incrementPendant
LDA.l PendantCounter : INC : STA.l PendantCounter
RTS
.incrementCapacity
LDA.l CapacityUpgrades : INC : STA.l CapacityUpgrades
RTS
.incrementHeartPiece
LDA.l HeartPieceCounter : INC : STA.l HeartPieceCounter
RTS
.incrementHeartContainer
LDA.l HeartContainerCounter : INC : STA.l HeartContainerCounter
RTS
.incrementCrystal
LDA.l CrystalCounter : INC : STA.l CrystalCounter
RTS
.incrementMail
LDA.l HighestMail
INC : STA.b Scrap04 : CPX.b Scrap04 : !BLT + ; don't increment unless we're getting a better mail
TXA : STA.l HighestMail
+
RTS
.incrementKeyLong
JSR .incrementKey
RTL
.incrementKey
LDA.l SmallKeyCounter : INC : STA.l SmallKeyCounter
RTS
.incrementCompass
%BottomHalf(MapsCompasses)
RTS
.incrementBigKey
%TopHalf(BigKeysBigChests)
RTS
.incrementGTowerPreBigKey
LDA.l PreGTBKLocations : INC : STA.l PreGTBKLocations
RTS
.maybeIncrementBombs
LDA.l InventoryTracking+1 : AND.b #$02 : BNE +
LDA.l InventoryTracking+1 : ORA.b #$02 : STA.l InventoryTracking+1
JSR .incrementY
+
RTS
.incrementMap
%TopHalf(MapsCompasses)
RTS
.incrementBossSwordLong
JSR .incrementBossSword
RTL
.incrementBossSword
LDA.l SwordEquipment
BNE + : -
LDA.l SwordlessBossKills : INC : STA.l SwordlessBossKills
RTS
+ CMP.b #$FF : BEQ -
+ CMP.b #$01 : BNE +
%TopHalf(SwordBossKills) : RTS
+ CMP.b #$02 : BNE +
%BottomHalf(SwordBossKills) : RTS
+ CMP.b #$03 : BNE +
%TopHalf(SwordBossKills+1) : RTS
+ CMP.b #$04 : BNE +
%BottomHalf(SwordBossKills+1)
+
RTS
.setDungeonCompletion
LDX $040C : BMI +
REP #$20 ; 16 bit
LDA.l DungeonMask, X
ORA.l DungeonsCompleted : STA.l DungeonsCompleted
SEP #$20 ; 8 bit
+
RTS
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; Link_ReceiveItem_HUDRefresh:
;--------------------------------------------------------------------------------
Link_ReceiveItem_HUDRefresh:
LDA.l BombsEquipment : BNE + ; skip if we have bombs
LDA.l BombCapacity : BEQ + ; skip if we can't have bombs
LDA.l BombsFiller : BEQ + ; skip if we are filling no bombs
DEC : STA.l BombsFiller ; decrease bomb fill count
LDA.b #$01 : STA.l BombsEquipment ; increase actual bomb count
+
JSL.l HUD_RefreshIconLong ; thing we wrote over
JSL.l PostItemGet
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; HandleBombAbsorbtion:
;--------------------------------------------------------------------------------
HandleBombAbsorbtion:
STA.l BombsFiller ; thing we wrote over
LDA.w $0303 : BNE + ; skip if we already have some item selected
LDA.l BombCapacity : BEQ + ; skip if we can't have bombs
LDA.b #$04 : STA.w $0202 ; set selected item to bombs
LDA.b #$01 : STA.w $0303 ; set selected item to bombs
JSL.l HUD_RebuildLong
+
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; AddYMarker:
;--------------------------------------------------------------------------------
AddYMarker:
LDA.w $0202 : AND.w #$FF ; load item value
CMP.w #$02 : BNE + ; boomerang
LDA.l InventoryTracking : AND.w #$C0 : CMP.w #$C0 : BEQ .drawYBubble : BRA .drawNormal
+ CMP.w #$01 : BNE + ; bow
LDA.l BowTracking : AND.w #$C0 : CMP.w #$C0 : BEQ .drawYBubble : BRA .drawNormal
+ CMP.w #$05 : BNE + ; powder
LDA.l InventoryTracking : AND.w #$30 : CMP.w #$30 : BEQ .drawYBubble : BRA .drawNormal
+ CMP.w #$0D : BNE + ; flute
LDA.l InventoryTracking : BIT.w #$04 : BEQ .drawNormal ; make sure we have shovel
AND.w #$03 : BNE .drawYBubble ; make sure we have one of the flutes
BRA .drawNormal
+ CMP.w #$10 : BEQ .drawJarMarker
.drawNormal
LDA.w #$7C60
BRA .drawTile
.drawJarMarker
LDA.w $0207 : AND.w #$0020 : BNE .drawXBubble
.drawYBubble
LDA.w #$3D4F
BRA .drawTile
.drawXBubble
JSR MakeCircleBlue
LDA.w #$2D3E
.drawTile
STA.w $FFC4, Y
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; MakeCircleBlue
; this is horrible, make it better
;--------------------------------------------------------------------------------
MakeCircleBlue:
LDA.w $FFC0, Y : AND.w #$EFFF : STA.w $FFC0, Y
LDA.w $FFC2, Y : AND.w #$EFFF : STA.w $FFC2, Y
LDA.w $FFFE, Y : AND.w #$EFFF : STA.w $FFFE, Y
LDA.w $0004, Y : AND.w #$EFFF : STA.w $0004, Y
LDA.w $003E, Y : AND.w #$EFFF : STA.w $003E, Y
LDA.w $0044, Y : AND.w #$EFFF : STA.w $0044, Y
LDA.w $0080, Y : AND.w #$EFFF : STA.w $0080, Y
LDA.w $0082, Y : AND.w #$EFFF : STA.w $0082, Y
LDA.w $FFBE, Y : AND.w #$EFFF : STA.w $FFBE, Y
LDA.w $FFC4, Y : AND.w #$EFFF : STA.w $FFC4, Y
LDA.w $0084, Y : AND.w #$EFFF : STA.w $0084, Y
LDA.w $007E, Y : AND.w #$EFFF : STA.w $007E, Y
RTS
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; UpgradeFlute:
;--------------------------------------------------------------------------------
UpgradeFlute:
LDA.l InventoryTracking : AND.b #$FC : ORA.b #$01 : STA.l InventoryTracking ; switch to the working flute
LDA.b #$03 : STA.l FluteEquipment ; upgrade primary inventory
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; CheckKeys:
;--------------------------------------------------------------------------------
CheckKeys:
LDA.l GenericKeys : BEQ + : RTL : +
LDA.w $040C : CMP.b #$FF
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; DrawKeyIcon:
;--------------------------------------------------------------------------------
DrawKeyIcon:
LDA.b Scrap04 : AND.w #$00FF : CMP.w #$0090 : BNE + : LDA.w #$007F : + : ORA.w #$2400 : STA.l $7EC764
LDA.b Scrap05 : AND.w #$00FF : ORA.w #$2400 : STA.l $7EC766
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; LoadKeys:
;--------------------------------------------------------------------------------
LoadKeys:
LDA.l GenericKeys : BEQ +
LDA.l CurrentGenericKeys
RTL
+
LDA.l DungeonKeys, X
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; SaveKeys:
;--------------------------------------------------------------------------------
SaveKeys:
PHA
LDA.l GenericKeys : BEQ +
PLA : STA.l CurrentGenericKeys
RTL
+
PLA : STA.l DungeonKeys, X
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; ClearOWKeys:
;--------------------------------------------------------------------------------
ClearOWKeys:
PHA
JSL.l TurtleRockEntranceFix
JSL.l FakeWorldFix
JSR.w FixBunnyOnExitToLightWorld
LDA.l GenericKeys : BEQ +
PLA : LDA.l CurrentGenericKeys : STA.l CurrentSmallKeys
RTL
+
PLA : STA.l CurrentSmallKeys
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; PrepItemScreenBigKey:
;--------------------------------------------------------------------------------
PrepItemScreenBigKey:
STZ.b Scrap02
STZ.b Scrap03
REP #$30 ; thing we wrote over - set 16-bit accumulator
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; LoadPowder:
;--------------------------------------------------------------------------------
LoadPowder:
JSL.l Sprite_SpawnDynamically ; thing we wrote over
%GetPossiblyEncryptedItem(WitchItem, SpriteItemValues)
STA.w $0DA0, Y ; Store item type
JSL.l PrepDynamicTile
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; InitializeBottles:
;--------------------------------------------------------------------------------
InitializeBottles:
STA.l BottleContents, X ; thing we wrote over
PHA
LDA.l BottleIndex : BNE +
TXA : INC : STA.l BottleIndex ; write bottle index to menu properly
+
PLA
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; DrawPowder:
;--------------------------------------------------------------------------------
DrawPowder:
LDA.w $02DA : BNE .defer ; defer if link is buying a potion
LDA.l RedrawFlag : BEQ +
LDA.w $0DA0, X ; Retrieve stored item type
JSL.l PrepDynamicTile
LDA.b #$00 : STA.l RedrawFlag ; reset redraw flag
BRA .defer
+
LDA.w $0DA0, X ; Retrieve stored item type
JSL.l DrawDynamicTile
.defer
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; LoadMushroom:
;--------------------------------------------------------------------------------
LoadMushroom:
LDA.b #$00 : STA.w $0DC0, X ; thing we wrote over
.justGFX
PHA
LDA.b #$01 : STA.l RedrawFlag
LDA.b $5D : CMP.b #$14 : BEQ .skip ; skip if we're mid-mirror
LDA.b #$00 : STA.l RedrawFlag
%GetPossiblyEncryptedItem(MushroomItem, SpriteItemValues)
STA.w $0E80, X ; Store item type
JSL.l PrepDynamicTile
.skip
PLA
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; DrawMushroom:
;--------------------------------------------------------------------------------
DrawMushroom:
PHA : PHY
LDA.l RedrawFlag : BEQ .skipInit ; skip init if already ready
JSL.l LoadMushroom_justGFX
BRA .done ; don't draw on the init frame
.skipInit
LDA.w $0E80, X ; Retrieve stored item type
JSL.l DrawDynamicTile
.done
PLY : PLA
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; CollectPowder:
;--------------------------------------------------------------------------------
CollectPowder:
LDY $0DA0, X ; Retrieve stored item type
BNE +
; if for any reason the item value is 0 reload it, just in case
%GetPossiblyEncryptedItem(WitchItem, SpriteItemValues) : TAY
+
STZ $02E9 ; item from NPC
JSL.l Link_ReceiveItem
;JSL.l FullInventoryExternal
JSL.l ItemSet_Powder
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; RemoveMushroom:
;--------------------------------------------------------------------------------
RemoveMushroom:
LDA.l InventoryTracking : AND.b #$DF : STA.l InventoryTracking ; remove the mushroom
AND.b #$10 : BEQ .empty ; check if we have powder
LDA.b #$02 : STA.l PowderEquipment ; give powder if we have it
RTL
.empty
LDA.b #$00 : STA.l PowderEquipment ; clear the inventory slot if we don't have powder
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; DrawMagicHeader:
;--------------------------------------------------------------------------------
DrawMagicHeader:
LDA.l MagicConsumption : AND.w #$00FF : CMP.w #$0002 : BEQ .quarterMagic
.halfMagic
LDA.w #$28F7 : STA.l $7EC704
LDA.w #$2851 : STA.l $7EC706
LDA.w #$28FA : STA.l $7EC708
RTL
.quarterMagic
LDA.w #$28F7 : STA.l $7EC704
LDA.w #$2800 : STA.l $7EC706
LDA.w #$2801 : STA.l $7EC708
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; SpawnShovelGamePrizeSFX:
;--------------------------------------------------------------------------------
SpawnShovelGamePrizeSFX:
STA.l $7FFE00 ; thing we wrote over
PHA
LDA.b #$1B : STA.w $012F ; play puzzle sound
PLA
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; SpawnChestGamePrizeSFX:
;--------------------------------------------------------------------------------
SpawnChestGamePrizeSFX:
CPX.b #$07 : BNE .normal
LDA.b RoomIndex : CMP.b #$06 : BNE .normal
.prize
LDA.b #$1B : STA.w $012F : RTL ; play puzzle sound
.normal
LDA.b #$0E : STA.w $012F ; play chest sound
RTL
;--------------------------------------------------------------------------------
;--------------------------------------------------------------------------------
; SpawnShovelItem:
;--------------------------------------------------------------------------------
SpawnShovelItem:
LDA.b #$01 : STA.l RedrawFlag
LDA.w $03FC : BEQ +
JSL DiggingGameGuy_AttemptPrizeSpawn
JMP .skip
+
LDA.w $035B : AND.b #$01 : BNE + : JMP .skip : + ; corner dig fix
PHY : PHP
PHB : PHK : PLB
SEP #$30 ; set 8-bit accumulator and index registers
LDA.b $1B : BEQ + : JMP .no_drop : + ; skip if indoors
LDA.b $8A : CMP.b #$2A : BEQ .no_drop ; don't drop in the haunted grove
CMP.b #$68 : BEQ .no_drop ; don't drop in the digging game area
JSL GetRandomInt : BIT.b #$03 : BNE .no_drop ; drop with 1/4 chance
LSR #2 : TAX ; clobber lower 2 bis - we have 64 slots now
LDA.l ShovelSpawnTable, X ; look up the drop on the table
;most of this part below is copied from the digging game
STA.l $7FFE00
JSL Sprite_SpawnDynamically
LDX.b #$00
LDA.b $2F : CMP.b #$04 : BEQ + : INX : +
LDA.l .x_speeds, X : STA.w $0D50, Y
LDA.b #$00 : STA.w $0D40, Y
LDA.b #$18 : STA.w $0F80, Y
LDA.b #$FF : STA.w $0B58, Y
LDA.b #$30 : STA.w $0F10, Y
LDA.b $22 : !ADD.l .x_offsets, X
AND.b #$F0 : STA.w $0D10, Y
LDA.b $23 : ADC.b #$00 : STA.w $0D30, Y
LDA.b $20 : !ADD.b #$16 : AND.b #$F0 : STA.w $0D00, Y
LDA.b $21 : ADC.b #$00 : STA.w $0D20, Y
LDA.b #$00 : STA.w $0F20, Y
TYX
LDA.b #$30 : JSL Sound_SetSfx3PanLong
.no_drop
PLB
PLP : PLY
.skip
RTL
;DATA - Shovel Spawn Information
{
.x_speeds
db $F0
db $10
.x_offsets
db $00
db $13
}
;--------------------------------------------------------------------------------