diff options
Diffstat (limited to 'engine/items')
-rw-r--r-- | engine/items/get_bag_item_quantity.asm | 18 | ||||
-rw-r--r-- | engine/items/inventory.asm | 8 | ||||
-rwxr-xr-x | engine/items/item_effects.asm (renamed from engine/items/items.asm) | 479 | ||||
-rw-r--r-- | engine/items/subtract_paid_money.asm | 17 | ||||
-rwxr-xr-x | engine/items/tm_prices.asm | 14 | ||||
-rwxr-xr-x | engine/items/tmhm.asm | 4 | ||||
-rwxr-xr-x | engine/items/tms.asm | 2 | ||||
-rwxr-xr-x | engine/items/town_map.asm | 629 |
8 files changed, 893 insertions, 278 deletions
diff --git a/engine/items/get_bag_item_quantity.asm b/engine/items/get_bag_item_quantity.asm new file mode 100644 index 00000000..f10df1a0 --- /dev/null +++ b/engine/items/get_bag_item_quantity.asm @@ -0,0 +1,18 @@ +GetQuantityOfItemInBag: +; In: b = item ID +; Out: b = how many of that item are in the bag + call GetPredefRegisters + ld hl, wNumBagItems +.loop + inc hl + ld a, [hli] + cp $ff + jr z, .notInBag + cp b + jr nz, .loop + ld a, [hl] + ld b, a + ret +.notInBag + ld b, 0 + ret diff --git a/engine/items/inventory.asm b/engine/items/inventory.asm index 58bcf7e9..c2e0b2b4 100644 --- a/engine/items/inventory.asm +++ b/engine/items/inventory.asm @@ -4,7 +4,7 @@ ; [wcf91] = item ID ; [wItemQuantity] = item quantity ; sets carry flag if successful, unsets carry flag if unsuccessful -AddItemToInventory_: +AddItemToInventory_:: ld a, [wItemQuantity] ; a = item quantity push af push bc @@ -12,10 +12,10 @@ AddItemToInventory_: push hl push hl ld d, PC_ITEM_CAPACITY ; how many items the PC can hold - ld a, wNumBagItems & $FF + ld a, LOW(wNumBagItems) cp l jr nz, .checkIfInventoryFull - ld a, wNumBagItems >> 8 + ld a, HIGH(wNumBagItems) cp h jr nz, .checkIfInventoryFull ; if the destination is the bag @@ -98,7 +98,7 @@ AddItemToInventory_: ; hl = address of inventory (either wNumBagItems or wNumBoxItems) ; [wWhichPokemon] = index (within the inventory) of the item to remove ; [wItemQuantity] = quantity to remove -RemoveItemFromInventory_: +RemoveItemFromInventory_:: push hl inc hl ld a, [wWhichPokemon] ; index (within the inventory) of the item being removed diff --git a/engine/items/items.asm b/engine/items/item_effects.asm index e935f292..b1b458ab 100755 --- a/engine/items/items.asm +++ b/engine/items/item_effects.asm @@ -1,8 +1,8 @@ -UseItem_: +UseItem_:: ld a, 1 ld [wActionResultOrTookBattleTurn], a ; initialise to success value ld a, [wcf91] ;contains item_ID - cp HM_01 + cp HM01 jp nc, ItemUseTMHM ld hl, ItemUsePtrTable dec a @@ -16,6 +16,7 @@ UseItem_: jp hl ItemUsePtrTable: +; entries correspond to item ids dw ItemUseBall ; MASTER_BALL dw ItemUseBall ; ULTRA_BALL dw ItemUseBall ; GREAT_BALL @@ -149,7 +150,7 @@ ItemUseBall: ; If the player is fighting an unidentified ghost, set the value that indicates ; the Pokémon can't be caught and skip the capture calculations. - callab IsGhostBattle + callfar IsGhostBattle ld b, $10 ; can't be caught value jp z, .setAnimData @@ -167,12 +168,12 @@ ItemUseBall: call CopyData ; save the player's name in the Wild Monster data (part of the Cinnabar Island Missingno. glitch) ld a, [wBattleType] cp BATTLE_TYPE_OLD_MAN - jp nz,.captured - ld a,$1 + jp nz, .captured + ld a, $1 ld [wCapturedMonSpecies], a CheckEvent EVENT_02F ld b, $63 - jp nz,.setAnimData + jp nz, .setAnimData jp .captured .notOldManBattle ; If the player is fighting the ghost Marowak, set the value that indicates the @@ -251,14 +252,14 @@ ItemUseBall: ; Calculate MaxHP * 255. xor a - ld [H_MULTIPLICAND], a + ldh [hMultiplicand], a ld hl, wEnemyMonMaxHP ld a, [hli] - ld [H_MULTIPLICAND + 1], a + ldh [hMultiplicand + 1], a ld a, [hl] - ld [H_MULTIPLICAND + 2], a + ldh [hMultiplicand + 2], a ld a, 255 - ld [H_MULTIPLIER], a + ldh [hMultiplier], a call Multiply ; Determine BallFactor. It's 8 for Great Balls and 12 for the others. @@ -272,7 +273,7 @@ ItemUseBall: ; Note that the results of all division operations are floored. ; Calculate (MaxHP * 255) / BallFactor. - ld [H_DIVISOR], a + ldh [hDivisor], a ld b, 4 ; number of bytes in dividend call Divide @@ -294,17 +295,17 @@ ItemUseBall: .skip2 ; Let W = ((MaxHP * 255) / BallFactor) / max(HP / 4, 1). Calculate W. - ld [H_DIVISOR], a + ldh [hDivisor], a ld b, 4 call Divide -; If W > 255, store 255 in [H_QUOTIENT + 3]. -; Let X = min(W, 255) = [H_QUOTIENT + 3]. - ld a, [H_QUOTIENT + 2] +; If W > 255, store 255 in [hQuotient + 3]. +; Let X = min(W, 255) = [hQuotient + 3]. + ldh a, [hQuotient + 2] and a jr z, .skip3 ld a, 255 - ld [H_QUOTIENT + 3], a + ldh [hQuotient + 3], a .skip3 pop bc ; b = Rand1 - Status @@ -315,7 +316,7 @@ ItemUseBall: jr c, .failedToCapture ; If W > 255, the ball captures the Pokémon. - ld a, [H_QUOTIENT + 2] + ldh a, [hQuotient + 2] and a jr nz, .captured @@ -323,7 +324,7 @@ ItemUseBall: ; If Rand2 > X, the ball fails to capture the Pokémon. ld b, a - ld a, [H_QUOTIENT + 3] + ldh a, [hQuotient + 3] cp b jr c, .failedToCapture @@ -331,17 +332,17 @@ ItemUseBall: jr .skipShakeCalculations .failedToCapture - ld a, [H_QUOTIENT + 3] + ldh a, [hQuotient + 3] ld [wPokeBallCaptureCalcTemp], a ; Save X. ; Calculate CatchRate * 100. xor a - ld [H_MULTIPLICAND], a - ld [H_MULTIPLICAND + 1], a + ldh [hMultiplicand], a + ldh [hMultiplicand + 1], a ld a, [wEnemyMonActualCatchRate] - ld [H_MULTIPLICAND + 2], a + ldh [hMultiplicand + 2], a ld a, 100 - ld [H_MULTIPLIER], a + ldh [hMultiplier], a call Multiply ; Determine BallFactor2. @@ -363,26 +364,26 @@ ItemUseBall: ; Let Y = (CatchRate * 100) / BallFactor2. Calculate Y. ld a, b - ld [H_DIVISOR], a + ldh [hDivisor], a ld b, 4 call Divide ; If Y > 255, there are 3 shakes. ; Note that this shouldn't be possible. ; The maximum value of Y is (255 * 100) / 150 = 170. - ld a, [H_QUOTIENT + 2] + ldh a, [hQuotient + 2] and a ld b, $63 ; 3 shakes jr nz, .setAnimData ; Calculate X * Y. ld a, [wPokeBallCaptureCalcTemp] - ld [H_MULTIPLIER], a + ldh [hMultiplier], a call Multiply ; Calculate (X * Y) / 255. ld a, 255 - ld [H_DIVISOR], a + ldh [hDivisor], a ld b, 4 call Divide @@ -400,19 +401,19 @@ ItemUseBall: .addAilmentValue ; If the Pokémon has a status ailment, add Status2. - ld a, [H_QUOTIENT + 3] + ldh a, [hQuotient + 3] add b - ld [H_QUOTIENT + 3], a + ldh [hQuotient + 3], a .skip5 ; Finally determine the number of shakes. -; Let Z = ((X * Y) / 255) + Status2 = [H_QUOTIENT + 3]. +; Let Z = ((X * Y) / 255) + Status2 = [hQuotient + 3]. ; The number of shakes depend on the range Z is in. ; 0 ≤ Z < 10: 0 shakes (the ball misses) ; 10 ≤ Z < 30: 1 shake ; 30 ≤ Z < 70: 2 shakes ; 70 ≤ Z: 3 shakes - ld a, [H_QUOTIENT + 3] + ldh a, [hQuotient + 3] cp 10 ld b, $20 jr c, .setAnimData @@ -436,7 +437,7 @@ ItemUseBall: ld a, TOSS_ANIM ld [wAnimationID], a xor a - ld [H_WHOSETURN], a + ldh [hWhoseTurn], a ld [wAnimationType], a ld [wDamageMultipliers], a ld a, [wWhichPokemon] @@ -509,7 +510,7 @@ ItemUseBall: ld [wcf91], a ld a, [wEnemyMonLevel] ld [wCurEnemyLVL], a - callab LoadEnemyMonData + callfar LoadEnemyMonData pop af ld [wcf91], a pop hl @@ -610,53 +611,53 @@ ItemUseBall: ItemUseBallText00: ;"It dodged the thrown ball!" ;"This pokemon can't be caught" - TX_FAR _ItemUseBallText00 - db "@" + text_far _ItemUseBallText00 + text_end ItemUseBallText01: ;"You missed the pokemon!" - TX_FAR _ItemUseBallText01 - db "@" + text_far _ItemUseBallText01 + text_end ItemUseBallText02: ;"Darn! The pokemon broke free!" - TX_FAR _ItemUseBallText02 - db "@" + text_far _ItemUseBallText02 + text_end ItemUseBallText03: ;"Aww! It appeared to be caught!" - TX_FAR _ItemUseBallText03 - db "@" + text_far _ItemUseBallText03 + text_end ItemUseBallText04: ;"Shoot! It was so close too!" - TX_FAR _ItemUseBallText04 - db "@" + text_far _ItemUseBallText04 + text_end ItemUseBallText05: ;"All right! {MonName} was caught!" ;play sound - TX_FAR _ItemUseBallText05 - TX_SFX_CAUGHT_MON - TX_BLINK - db "@" + text_far _ItemUseBallText05 + sound_caught_mon + text_promptbutton + text_end ItemUseBallText07: ;"X was transferred to Bill's PC" - TX_FAR _ItemUseBallText07 - db "@" + text_far _ItemUseBallText07 + text_end ItemUseBallText08: ;"X was transferred to someone's PC" - TX_FAR _ItemUseBallText08 - db "@" + text_far _ItemUseBallText08 + text_end ItemUseBallText06: ;"New DEX data will be added..." ;play sound - TX_FAR _ItemUseBallText06 - TX_SFX_DEX_PAGE_ADDED - TX_BLINK - db "@" + text_far _ItemUseBallText06 + sound_dex_page_added + text_promptbutton + text_end ItemUseTownMap: ld a, [wIsInBattle] and a jp nz, ItemUseNotTime - jpba DisplayTownMap + farjp DisplayTownMap ItemUseBicycle: ld a, [wIsInBattle] @@ -683,7 +684,7 @@ ItemUseBicycle: jp nc, NoCyclingAllowedHere call ItemUseReloadOverworldData xor a ; no keys pressed - ld [hJoyHeld], a ; current joypad state + ldh [hJoyHeld], a ; current joypad state ld a, $1 ld [wWalkBikeSurfState], a ; change player state to bicycling call PlayDefaultMusic ; play bike riding music @@ -719,11 +720,11 @@ ItemUseSurfboard: .tryToStopSurfing xor a - ld [hSpriteIndexOrTextID], a + ldh [hSpriteIndexOrTextID], a ld d, 16 ; talking range in pixels (normal range) call IsSpriteInFrontOfPlayer2 res 7, [hl] - ld a, [hSpriteIndexOrTextID] + ldh a, [hSpriteIndexOrTextID] and a ; is there a sprite in the way? jr nz, .cannotStopSurfing ld hl, TilePairCollisionsWater @@ -776,12 +777,12 @@ ItemUseSurfboard: ret SurfingGotOnText: - TX_FAR _SurfingGotOnText - db "@" + text_far _SurfingGotOnText + text_end SurfingNoPlaceToGetOffText: - TX_FAR _SurfingNoPlaceToGetOffText - db "@" + text_far _SurfingNoPlaceToGetOffText + text_end ItemUsePokedex: predef_jump ShowPokedexMenu @@ -808,10 +809,10 @@ ItemUseEvoStone: ld [wcf91], a call Func_d85d jr nc, .noEffect - callab IsThisPartymonStarterPikachu_Party + callfar IsThisPartymonStarterPikachu_Party jr nc, .notPlayerPikachu ld e, $1b - callab PlayPikachuSoundClip + callfar PlayPikachuSoundClip ld a, [wWhichPokemon] ld hl, wPartyMonNicks call GetPartyMonName @@ -829,7 +830,7 @@ ItemUseEvoStone: call WaitForSoundToFinish ld a, $01 ld [wForceEvolution], a - callab TryEvolvingMon ; try to evolve pokemon + callfar TryEvolvingMon ; try to evolve pokemon pop af ld [wWhichPokemon], a ld hl, wNumBagItems @@ -891,8 +892,8 @@ Func_d85d: ret RefusingText: - TX_FAR _RefusingText - db "@" + text_far _RefusingText + text_end ItemUseVitamin: ld a, [wIsInBattle] @@ -1036,7 +1037,7 @@ ItemUseMedicine: push hl push de push bc - callab Func_2fd6a + callfar Func_2fd6a pop bc pop de pop hl @@ -1135,18 +1136,18 @@ ItemUseMedicine: call AddNTimes ld a, [hli] ld [wHPBarMaxHP + 1], a - ld [H_DIVIDEND], a + ldh [hDividend], a ld a, [hl] ld [wHPBarMaxHP], a - ld [H_DIVIDEND + 1], a + ldh [hDividend + 1], a ld a, 5 - ld [H_DIVISOR], a + ldh [hDivisor], a ld b, 2 ; number of bytes call Divide ; get 1/5 of max HP of pokemon that used Softboiled ld bc, (wPartyMon1HP + 1) - (wPartyMon1MaxHP + 1) add hl, bc ; hl now points to LSB of current HP of pokemon that used Softboiled ; subtract 1/5 of max HP from current HP of pokemon that used Softboiled - ld a, [H_QUOTIENT + 3] + ldh a, [hQuotient + 3] push af ld b, a ld a, [hl] @@ -1154,28 +1155,28 @@ ItemUseMedicine: sub b ld [hld], a ld [wHPBarNewHP], a - ld a, [H_QUOTIENT + 2] + ldh a, [hQuotient + 2] ld b, a ld a, [hl] ld [wHPBarOldHP+1], a sbc b ld [hl], a ld [wHPBarNewHP+1], a - coord hl, 4, 1 + hlcoord 4, 1 ld a, [wWhichPokemon] ld bc, 2 * SCREEN_WIDTH call AddNTimes ; calculate coordinates of HP bar of pokemon that used Softboiled ld a, SFX_HEAL_HP call PlaySoundWaitForCurrent - ld a, [hFlags_0xFFFA] + ldh a, [hFlagsFFFA] set 0, a - ld [hFlags_0xFFFA], a + ldh [hFlagsFFFA], a ld a, $02 ld [wHPBarType], a predef UpdateHPBar2 ; animate HP bar decrease of pokemon that used Softboiled - ld a, [hFlags_0xFFFA] + ldh a, [hFlagsFFFA] res 0, a - ld [hFlags_0xFFFA], a + ldh [hFlagsFFFA], a pop af ld b, a ; store heal amount (1/5 of max HP) ld hl, wHPBarOldHP + 1 @@ -1322,15 +1323,15 @@ ItemUseMedicine: jr z, .playStatusAilmentCuringSound ld a, SFX_HEAL_HP call PlaySoundWaitForCurrent - ld a, [hFlags_0xFFFA] + ldh a, [hFlagsFFFA] set 0, a - ld [hFlags_0xFFFA], a + ldh [hFlagsFFFA], a ld a, $02 ld [wHPBarType], a predef UpdateHPBar2 ; animate the HP bar lengthening - ld a, [hFlags_0xFFFA] + ldh a, [hFlagsFFFA] res 0, a - ld [hFlags_0xFFFA], a + ldh [hFlagsFFFA], a ld a, REVIVE_MSG ld [wPartyMenuTypeOrMessageID], a ld a, [wcf91] @@ -1347,13 +1348,13 @@ ItemUseMedicine: call PlaySoundWaitForCurrent .showHealingItemMessage xor a - ld [H_AUTOBGTRANSFERENABLED], a + ldh [hAutoBGTransferEnabled], a call ClearScreen dec a ld [wUpdateSpritesEnabled], a call RedrawPartyMenu ; redraws the party menu and displays the message ld a, 1 - ld [H_AUTOBGTRANSFERENABLED], a + ldh [hAutoBGTransferEnabled], a ld c, 50 call DelayFrames call WaitForTextScrollButtonPress @@ -1469,17 +1470,17 @@ ItemUseMedicine: push hl push de ld d, a - callab CalcExperience ; calculate experience for next level and store it at $ff96 + callfar CalcExperience ; calculate experience for next level and store it at hExperience pop de pop hl ld bc, wPartyMon1Exp - wPartyMon1Level add hl, bc ; hl now points to MSB of experience ; update experience to minimum for new level - ld a, [hExperience] + ldh a, [hExperience] ld [hli], a - ld a, [hExperience + 1] + ldh a, [hExperience + 1] ld [hli], a - ld a, [hExperience + 2] + ldh a, [hExperience + 2] ld [hl], a pop hl ld a, [wWhichPokemon] @@ -1528,7 +1529,7 @@ ItemUseMedicine: ld [wMonDataLocation], a call LoadMonData ld d, $01 - callab PrintStatsBox ; display new stats text box + callfar PrintStatsBox ; display new stats text box call WaitForTextScrollButtonPress ; wait for button press xor a ; PLAYER_PARTY_DATA ld [wMonDataLocation], a @@ -1541,11 +1542,11 @@ ItemUseMedicine: push af ld a, [wUsedItemOnWhichPokemon] ld [wWhichPokemon], a - callab Func_2fd6a ; evolve pokemon, if appropriate + callfar Func_2fd6a ; evolve pokemon, if appropriate pop af ld [wWhichPokemon], a - callab TryEvolvingMon + callfar TryEvolvingMon ld a, $01 ld [wUpdateSpritesEnabled], a pop af @@ -1555,12 +1556,12 @@ ItemUseMedicine: jp RemoveUsedItem VitaminStatRoseText: - TX_FAR _VitaminStatRoseText - db "@" + text_far _VitaminStatRoseText + text_end VitaminNoEffectText: - TX_FAR _VitaminNoEffectText - db "@" + text_far _VitaminNoEffectText + text_end VitaminText: db "HEALTH@" @@ -1597,7 +1598,7 @@ BaitRockCommon: ld [wAnimationID], a xor a ld [wAnimationType], a - ld [H_WHOSETURN], a + ldh [hWhoseTurn], a ld [de], a ; zero escape factor (for bait), zero bait factor (for rock) .randomLoop ; loop until a random number less than 5 is generated call Random @@ -1617,12 +1618,12 @@ BaitRockCommon: jp DelayFrames ThrewBaitText: - TX_FAR _ThrewBaitText - db "@" + text_far _ThrewBaitText + text_end ThrewRockText: - TX_FAR _ThrewRockText - db "@" + text_far _ThrewRockText + text_end ; also used for Dig out-of-battle effect ItemUseEscapeRope: @@ -1669,9 +1670,7 @@ ItemUseEscapeRope: .notUsable jp ItemUseNotTime -EscapeRopeTilesets: - db FOREST, CEMETERY, CAVERN, FACILITY, INTERIOR - db $ff ; terminator +INCLUDE "data/tilesets/escape_rope_tilesets.asm" ItemUseRepel: ld b, 100 @@ -1721,7 +1720,7 @@ ItemUseCardKey: ld b, a .loop ld a, [hli] - cp $ff + cp -1 jp z, ItemUseNotTime cp b jr nz, .nextEntry1 @@ -1750,46 +1749,7 @@ ItemUseCardKey: set 7, [hl] ret -; These tables are probably supposed to be door locations in Silph Co., -; but they are unused. -; The reason there are 3 tables is unknown. - -; Format: -; 00: Map ID -; 01: Y -; 02: X -; 03: ID? - -CardKeyTable1: - db SILPH_CO_2F, $04, $04, $00 - db SILPH_CO_2F, $04, $05, $01 - db SILPH_CO_4F, $0C, $04, $02 - db SILPH_CO_4F, $0C, $05, $03 - db SILPH_CO_7F, $06, $0A, $04 - db SILPH_CO_7F, $06, $0B, $05 - db SILPH_CO_9F, $04, $12, $06 - db SILPH_CO_9F, $04, $13, $07 - db SILPH_CO_10F, $08, $0A, $08 - db SILPH_CO_10F, $08, $0B, $09 - db $ff - -CardKeyTable2: - db SILPH_CO_3F, $08, $09, $0A - db SILPH_CO_3F, $09, $09, $0B - db SILPH_CO_5F, $04, $07, $0C - db SILPH_CO_5F, $05, $07, $0D - db SILPH_CO_6F, $0C, $05, $0E - db SILPH_CO_6F, $0D, $05, $0F - db SILPH_CO_8F, $08, $07, $10 - db SILPH_CO_8F, $09, $07, $11 - db SILPH_CO_9F, $08, $03, $12 - db SILPH_CO_9F, $09, $03, $13 - db $ff - -CardKeyTable3: - db SILPH_CO_11F, $08, $09, $14 - db SILPH_CO_11F, $09, $09, $15 - db $ff +INCLUDE "data/events/card_key_coords.asm" ItemUsePokedoll: ld a, [wIsInBattle] @@ -1866,8 +1826,8 @@ ItemUseXStat: call LoadScreenTilesFromBuffer1 ; restore saved screen call Delay3 xor a - ld [H_WHOSETURN], a ; set turn to player's turn - callba StatModifierUpEffect ; do stat increase move + ldh [hWhoseTurn], a ; set turn to player's turn + farcall StatModifierUpEffect ; do stat increase move ld a, [wWhichPokemon] push af @@ -1923,13 +1883,13 @@ ItemUsePokeflute: jr nz, .noSnorlaxOrPikachuToWakeUp call CheckPikachuFollowingPlayer jr z, .noSnorlaxOrPikachuToWakeUp - callab IsPikachuRightNextToPlayer + callfar IsPikachuRightNextToPlayer jr nc, .noSnorlaxOrPikachuToWakeUp ld hl, PlayedFluteHadEffectText call PrintText call ItemUseReloadOverworldData ldpikaemotion e, PikachuEmotion26 - callab PlaySpecificPikachuEmotion + callfar PlaySpecificPikachuEmotion ret .noSnorlaxOrPikachuToWakeUp @@ -1976,7 +1936,7 @@ ItemUsePokeflute: and $80 jr nz, .skipMusic call WaitForSoundToFinish ; wait for sound to end - callba Music_PokeFluteInBattle ; play in-battle pokeflute music + farcall Music_PokeFluteInBattle ; play in-battle pokeflute music .musicWaitLoop ; wait for music to finish playing ld a, [wChannelSoundIDs + Ch7] and a ; music off? @@ -2011,41 +1971,35 @@ WakeUpEntireParty: jr nz, .loop ret -; Format: -; 00: Y -; 01: X Route12SnorlaxFluteCoords: - db 62, 9 ; one space West of Snorlax - db 61, 10 ; one space North of Snorlax - db 63, 10 ; one space South of Snorlax - db 62, 11 ; one space East of Snorlax - db $ff ; terminator + dbmapcoord 9, 62 ; one space West of Snorlax + dbmapcoord 10, 61 ; one space North of Snorlax + dbmapcoord 10, 63 ; one space South of Snorlax + dbmapcoord 11, 62 ; one space East of Snorlax + db -1 ; end -; Format: -; 00: Y -; 01: X Route16SnorlaxFluteCoords: - db 10, 27 ; one space East of Snorlax - db 10, 25 ; one space West of Snorlax - db $ff ; terminator + dbmapcoord 27, 10 ; one space East of Snorlax + dbmapcoord 25, 10 ; one space West of Snorlax + db -1 ; end PlayedFluteNoEffectText: - TX_FAR _PlayedFluteNoEffectText - db "@" + text_far _PlayedFluteNoEffectText + text_end FluteWokeUpText: - TX_FAR _FluteWokeUpText - db "@" + text_far _FluteWokeUpText + text_end PlayedFluteHadEffectText: - TX_FAR _PlayedFluteHadEffectText - TX_BLINK - TX_ASM + text_far _PlayedFluteHadEffectText + text_promptbutton + text_asm ld a, [wIsInBattle] and a jr nz, .done ; play out-of-battle pokeflute music - call StopAllMusic ; turn off music + call StopAllMusic ld a, SFX_POKEFLUTE ld c, BANK(SFX_Pokeflute) call PlayMusic @@ -2065,8 +2019,8 @@ ItemUseCoinCase: jp PrintText CoinCaseNumCoinsText: - TX_FAR _CoinCaseNumCoinsText - db "@" + text_far _CoinCaseNumCoinsText + text_end ItemUseOldRod: call FishingInit @@ -2101,12 +2055,12 @@ ItemUseGoodRod: xor 1 jr RodResponse -INCLUDE "data/good_rod.asm" +INCLUDE "data/wild/good_rod.asm" ItemUseSuperRod: call FishingInit jp c, ItemUseNotTime - callab ReadSuperRodData + callfar ReadSuperRodData ld c, e ld b, d ld a, $2 @@ -2142,7 +2096,7 @@ DoNotGenerateFishingEncounter: push af push hl ld [hl], 0 - callba FishingAnim + farcall FishingAnim pop hl pop af ld [hl], a @@ -2189,7 +2143,7 @@ ItemUseItemfinder: and a jp nz, ItemUseNotTime call ItemUseReloadOverworldData - callba HiddenItemNear ; check for hidden items + farcall HiddenItemNear ; check for hidden items ld hl, ItemfinderFoundNothingText jr nc, .printText ; if no hidden items ld c, 4 @@ -2205,12 +2159,12 @@ ItemUseItemfinder: jp PrintText ItemfinderFoundItemText: - TX_FAR _ItemfinderFoundItemText - db "@" + text_far _ItemfinderFoundItemText + text_end ItemfinderFoundNothingText: - TX_FAR _ItemfinderFoundNothingText - db "@" + text_far _ItemfinderFoundNothingText + text_end ItemUsePPUp: ld a, [wIsInBattle] @@ -2261,7 +2215,7 @@ ItemUsePPRestore: call PrintText xor a ld [wPlayerMoveListIndex], a - callab MoveSelectionMenu ; move selection menu + callfar MoveSelectionMenu ; move selection menu ld a, 0 ld [wPlayerMoveListIndex], a jr nz, .chooseMon @@ -2418,24 +2372,24 @@ ItemUsePPRestore: ret RaisePPWhichTechniqueText: - TX_FAR _RaisePPWhichTechniqueText - db "@" + text_far _RaisePPWhichTechniqueText + text_end RestorePPWhichTechniqueText: - TX_FAR _RestorePPWhichTechniqueText - db "@" + text_far _RestorePPWhichTechniqueText + text_end PPMaxedOutText: - TX_FAR _PPMaxedOutText - db "@" + text_far _PPMaxedOutText + text_end PPIncreasedText: - TX_FAR _PPIncreasedText - db "@" + text_far _PPIncreasedText + text_end PPRestoredText: - TX_FAR _PPRestoredText - db "@" + text_far _PPRestoredText + text_end ; for items that can't be used from the Item menu UnusableItem: @@ -2446,10 +2400,10 @@ ItemUseTMHM: and a jp nz, ItemUseNotTime ld a, [wcf91] - sub TM_01 + sub TM01 ; underflows below 0 for HM items (before TM items) push af jr nc, .skipAdding - add 55 ; if item is an HM, add 55 + add NUM_TMS + NUM_HMS ; adjust HM IDs to come after TM IDs .skipAdding inc a ld [wd11e], a @@ -2466,7 +2420,7 @@ ItemUseTMHM: call PrintText ld hl, TeachMachineMoveText call PrintText - coord hl, 14, 7 + hlcoord 14, 7 lb bc, 8, 15 ld a, TWO_OPTION_MENU ld [wTextBoxID], a @@ -2525,7 +2479,7 @@ ItemUseTMHM: jr .chooseMon .checkIfAlreadyLearnedMove - callab CheckIfMoveIsKnown ; check if the pokemon already knows the move + callfar CheckIfMoveIsKnown ; check if the pokemon already knows the move jr c, .chooseMon predef LearnMove ; teach move ld a, [wWhichPokemon] @@ -2543,12 +2497,12 @@ ItemUseTMHM: ld a, d ld [wWhichPokemon], a callabd_ModifyPikachuHappiness PIKAHAPPY_USEDTMHM - callab IsThisPartymonStarterPikachu_Party + callfar IsThisPartymonStarterPikachu_Party jr nc, .notTeachingThunderboltOrThunderToPikachu ld a, [wcf91] - cp TM_24 ; are we teaching thunderbolt to the player pikachu? + cp TM_THUNDERBOLT ; are we teaching thunderbolt to the player pikachu? jr z, .teachingThunderboltOrThunderToPlayerPikachu - cp TM_25 ; are we teaching thunder then? + cp TM_THUNDER ; are we teaching thunder then? jr nz, .notTeachingThunderboltOrThunderToPikachu .teachingThunderboltOrThunderToPlayerPikachu ld a, $5 @@ -2565,20 +2519,20 @@ ItemUseTMHM: jp RemoveUsedItem BootedUpTMText: - TX_FAR _BootedUpTMText - db "@" + text_far _BootedUpTMText + text_end BootedUpHMText: - TX_FAR _BootedUpHMText - db "@" + text_far _BootedUpHMText + text_end TeachMachineMoveText: - TX_FAR _TeachMachineMoveText - db "@" + text_far _TeachMachineMoveText + text_end MonCannotLearnMachineMoveText: - TX_FAR _MonCannotLearnMachineMoveText - db "@" + text_far _MonCannotLearnMachineMoveText + text_end PrintItemUseTextAndRemoveItem: ld hl, ItemUseText00 @@ -2641,58 +2595,58 @@ ItemUseFailed: jp PrintText ItemUseNotTimeText: - TX_FAR _ItemUseNotTimeText - db "@" + text_far _ItemUseNotTimeText + text_end ItemUseNotYoursToUseText: - TX_FAR _ItemUseNotYoursToUseText - db "@" + text_far _ItemUseNotYoursToUseText + text_end ItemUseNoEffectText: - TX_FAR _ItemUseNoEffectText - db "@" + text_far _ItemUseNoEffectText + text_end ThrowBallAtTrainerMonText1: - TX_FAR _ThrowBallAtTrainerMonText1 - db "@" + text_far _ThrowBallAtTrainerMonText1 + text_end ThrowBallAtTrainerMonText2: - TX_FAR _ThrowBallAtTrainerMonText2 - db "@" + text_far _ThrowBallAtTrainerMonText2 + text_end NoCyclingAllowedHereText: - TX_FAR _NoCyclingAllowedHereText - db "@" + text_far _NoCyclingAllowedHereText + text_end NoSurfingHereText: - TX_FAR _NoSurfingHereText - db "@" + text_far _NoSurfingHereText + text_end BoxFullCannotThrowBallText: - TX_FAR _BoxFullCannotThrowBallText - db "@" + text_far _BoxFullCannotThrowBallText + text_end DontHavePokemonText: - TX_FAR _DontHavePokemonText - db "@" + text_far _DontHavePokemonText + text_end ItemUseText00: - TX_FAR _ItemUseText001 - TX_LINE - TX_FAR _ItemUseText002 - db "@" + text_far _ItemUseText001 + text_low + text_far _ItemUseText002 + text_end GotOnBicycleText: - TX_FAR _GotOnBicycleText1 - TX_LINE - TX_FAR _GotOnBicycleText2 - db "@" + text_far _GotOnBicycleText1 + text_low + text_far _GotOnBicycleText2 + text_end GotOffBicycleText: - TX_FAR _GotOffBicycleText1 - TX_LINE - TX_FAR _GotOffBicycleText2 - db "@" + text_far _GotOffBicycleText1 + text_low + text_far _GotOffBicycleText2 + text_end ; restores bonus PP (from PP Ups) when healing at a pokemon center ; also, when a PP Up is used, it increases the current PP by one PP Up bonus @@ -2744,13 +2698,13 @@ RestoreBonusPP: AddBonusPP: push bc ld a, [de] ; normal max PP of move - ld [H_DIVIDEND + 3], a + ldh [hDividend + 3], a xor a - ld [H_DIVIDEND], a - ld [H_DIVIDEND + 1], a - ld [H_DIVIDEND + 2], a + ldh [hDividend], a + ldh [hDividend + 1], a + ldh [hDividend + 2], a ld a, 5 - ld [H_DIVISOR], a + ldh [hDivisor], a ld b, 4 call Divide ld a, [hl] ; move PP @@ -2761,7 +2715,7 @@ AddBonusPP: srl a ld c, a ; c = number of PP Ups used .loop - ld a, [H_QUOTIENT + 3] + ldh a, [hQuotient + 3] cp 8 ; is the amount greater than or equal to 8? jr c, .addAmount ld a, 7 ; cap the amount at 7 @@ -2870,7 +2824,7 @@ GetSelectedMoveOffset2: ; [wItemQuantity] = quantity to toss ; OUTPUT: ; clears carry flag if the item is tossed, sets carry flag if not -TossItem_: +TossItem_:: push hl ld a, [wcf91] call IsItemHM @@ -2889,7 +2843,7 @@ TossItem_: call CopyStringToCF4B ; copy name to wcf4b ld hl, IsItOKToTossItemText call PrintText - coord hl, 14, 7 + hlcoord 14, 7 lb bc, 8, 15 ld a, TWO_OPTION_MENU ld [wTextBoxID], a @@ -2922,16 +2876,16 @@ TossItem_: ret ThrewAwayItemText: - TX_FAR _ThrewAwayItemText - db "@" + text_far _ThrewAwayItemText + text_end IsItOKToTossItemText: - TX_FAR _IsItOKToTossItemText - db "@" + text_far _IsItOKToTossItemText + text_end TooImportantToTossText: - TX_FAR _TooImportantToTossText - db "@" + text_far _TooImportantToTossText + text_end ; checks if an item is a key item ; INPUT: @@ -2940,11 +2894,11 @@ TooImportantToTossText: ; [wIsKeyItem] = result ; 00: item is not key item ; 01: item is key item -IsKeyItem_: +IsKeyItem_:: ld a, $01 ld [wIsKeyItem], a ld a, [wcf91] - cp HM_01 ; is the item an HM or TM? + cp HM01 ; is the item an HM or TM? jr nc, .checkIfItemIsHM ; if the item is not an HM or TM push af @@ -2969,7 +2923,7 @@ IsKeyItem_: ld [wIsKeyItem], a ret -INCLUDE "data/key_items.asm" +INCLUDE "data/items/key_items.asm" SendNewMonToBox: ld de, wNumInBox @@ -3103,15 +3057,15 @@ SendNewMonToBox: push de ld a, [wCurEnemyLVL] ld d, a - callab CalcExperience + callfar CalcExperience pop de - ld a, [hExperience] + ldh a, [hExperience] ld [de], a inc de - ld a, [hExperience + 1] + ldh a, [hExperience + 1] ld [de], a inc de - ld a, [hExperience + 2] + ldh a, [hExperience + 2] ld [de], a inc de xor a @@ -3146,7 +3100,7 @@ SendNewMonToBox: ; checks if the tile in front of the player is a shore or water tile ; used for surfing and fishing ; unsets carry if it is, sets carry if not -IsNextTileShoreOrWater: +IsNextTileShoreOrWater:: ld a, [wCurMapTileset] ld hl, WaterTilesets ld de, 1 @@ -3167,10 +3121,7 @@ IsNextTileShoreOrWater: call IsInArray ret -; tilesets with water -WaterTilesets: - db OVERWORLD, FOREST, DOJO, GYM, SHIP, SHIP_PORT, CAVERN, FACILITY, PLATEAU - db $ff ; terminator +INCLUDE "data/tilesets/water_tilesets.asm" ; shore tiles ShoreTiles: diff --git a/engine/items/subtract_paid_money.asm b/engine/items/subtract_paid_money.asm new file mode 100644 index 00000000..fdefe3d6 --- /dev/null +++ b/engine/items/subtract_paid_money.asm @@ -0,0 +1,17 @@ +; subtracts the amount the player paid from their money +; OUTPUT: carry = 0(success) or 1(fail because there is not enough money) +SubtractAmountPaidFromMoney_:: + ld de, wPlayerMoney + ld hl, hMoney ; total price of items + ld c, 3 ; length of money in bytes + call StringCmp + ret c + ld de, wPlayerMoney + 2 + ld hl, hMoney + 2 ; total price of items + ld c, 3 ; length of money in bytes + predef SubBCDPredef ; subtract total price from money + ld a, MONEY_BOX + ld [wTextBoxID], a + call DisplayTextBoxID ; redraw money text box + and a + ret diff --git a/engine/items/tm_prices.asm b/engine/items/tm_prices.asm index 80e6bf3c..df9761bd 100755 --- a/engine/items/tm_prices.asm +++ b/engine/items/tm_prices.asm @@ -1,9 +1,9 @@ -GetMachinePrice: +GetMachinePrice:: ; Input: [wcf91] = Item Id of a TM ; Output: Stores the TM price at hItemPrice ld a, [wcf91] ; a contains TM item id - sub TM_01 - ret c + sub TM01 ; underflows below 0 for HM items (before TM items) + ret c ; HMs are priceless ld d, a ld hl, TechnicalMachinePrices srl a @@ -16,10 +16,10 @@ GetMachinePrice: swap a .highNybbleIsPrice and $f0 - ld [hItemPrice + 1], a + ldh [hItemPrice + 1], a xor a - ld [hItemPrice], a - ld [hItemPrice + 2], a + ldh [hItemPrice], a + ldh [hItemPrice + 2], a ret -INCLUDE "data/tm_prices.asm" +INCLUDE "data/items/tm_prices.asm" diff --git a/engine/items/tmhm.asm b/engine/items/tmhm.asm index 7ccaa232..a11cd736 100755 --- a/engine/items/tmhm.asm +++ b/engine/items/tmhm.asm @@ -22,5 +22,5 @@ CheckIfMoveIsKnown: ret AlreadyKnowsText: - TX_FAR _AlreadyKnowsText - db "@" + text_far _AlreadyKnowsText + text_end diff --git a/engine/items/tms.asm b/engine/items/tms.asm index 84770747..dcf2665d 100755 --- a/engine/items/tms.asm +++ b/engine/items/tms.asm @@ -39,4 +39,4 @@ TMToMove: ld [wd11e], a ret -INCLUDE "data/tms.asm" +INCLUDE "data/moves/tmhm_moves.asm" diff --git a/engine/items/town_map.asm b/engine/items/town_map.asm new file mode 100755 index 00000000..c401d1c1 --- /dev/null +++ b/engine/items/town_map.asm @@ -0,0 +1,629 @@ +NOT_VISITED EQU $fe + +DisplayTownMap: + call LoadTownMap + ld hl, wUpdateSpritesEnabled + ld a, [hl] + push af + ld [hl], $ff + push hl + ld a, $1 + ldh [hJoy7], a + ld a, [wCurMap] + push af + ld b, $0 + call DrawPlayerOrBirdSprite ; player sprite + hlcoord 1, 0 + ld de, wcd6d + call PlaceString + ld hl, wOAMBuffer + ld de, wTileMapBackup + ld bc, $10 + call CopyData + ld hl, vSprites tile $04 + ld de, TownMapCursor + lb bc, BANK(TownMapCursor), (TownMapCursorEnd - TownMapCursor) / $8 + call CopyVideoDataDouble + xor a + ld [wWhichTownMapLocation], a + pop af + jr .enterLoop + +.townMapLoop + hlcoord 0, 0 + lb bc, 1, 20 + call ClearScreenArea + ld hl, TownMapOrder + ld a, [wWhichTownMapLocation] + ld c, a + ld b, 0 + add hl, bc + ld a, [hl] +.enterLoop + ld de, wTownMapCoords + call LoadTownMapEntry + ld a, [de] + push hl + call TownMapCoordsToOAMCoords + ld a, $4 + ld [wOAMBaseTile], a + ld hl, wOAMBuffer + $10 + call WriteTownMapSpriteOAM ; town map cursor sprite + pop hl + ld de, wcd6d +.copyMapName + ld a, [hli] + ld [de], a + inc de + cp $50 + jr nz, .copyMapName + hlcoord 1, 0 + ld de, wcd6d + call PlaceString + ld hl, wOAMBuffer + $10 + ld de, wTileMapBackup + 16 + ld bc, $10 + call CopyData +.inputLoop + call TownMapSpriteBlinkingAnimation + call JoypadLowSensitivity + ldh a, [hJoy5] + ld b, a + and A_BUTTON | B_BUTTON | D_UP | D_DOWN + jr z, .inputLoop + ld a, SFX_TINK + call PlaySound + bit 6, b + jr nz, .pressedUp + bit 7, b + jr nz, .pressedDown + xor a + ld [wTownMapSpriteBlinkingEnabled], a + ldh [hJoy7], a + ld [wAnimCounter], a + call ExitTownMap + pop hl + pop af + ld [hl], a + ret +.pressedUp + ld a, [wWhichTownMapLocation] + inc a + cp TownMapOrderEnd - TownMapOrder ; number of list items + 1 + jr nz, .noOverflow + xor a +.noOverflow + ld [wWhichTownMapLocation], a + jp .townMapLoop +.pressedDown + ld a, [wWhichTownMapLocation] + dec a + cp -1 + jr nz, .noUnderflow + ld a, TownMapOrderEnd - TownMapOrder - 1 ; number of list items +.noUnderflow + ld [wWhichTownMapLocation], a + jp .townMapLoop + +.asm_70f87 + ldh a, [hJoy5] + and D_DOWN | D_UP + ret z + callfar PlayPikachuSoundClip + ret + +INCLUDE "data/maps/town_map_order.asm" + +TownMapCursor: + INCBIN "gfx/town_map/town_map_cursor.1bpp" +TownMapCursorEnd: + +LoadTownMap_Nest: + call LoadTownMap + ld hl, wUpdateSpritesEnabled + ld a, [hl] + push af + ld [hl], $ff + push hl + call DisplayWildLocations + call GetMonName + hlcoord 1, 0 + call PlaceString + ld h, b + ld l, c + ld de, MonsNestText + call PlaceString + call WaitForTextScrollButtonPress + call ExitTownMap + pop hl + pop af + ld [hl], a + ret + +MonsNestText: + db "'s NEST@" + +LoadTownMap_Fly:: + call ClearSprites + call LoadTownMap + ld a, $1 + ldh [hJoy7], a + call LoadPlayerSpriteGraphics + call LoadFontTilePatterns + ld de, BirdSprite + ld b, BANK(BirdSprite) + ld c, $c + ld hl, vSprites tile $04 + call CopyVideoData + ld de, TownMapUpArrow + ld hl, vChars1 tile $6d + lb bc, BANK(TownMapUpArrow), (TownMapUpArrowEnd - TownMapUpArrow) / $8 + call CopyVideoDataDouble + call BuildFlyLocationsList + ld hl, wUpdateSpritesEnabled + ld a, [hl] + push af + ld [hl], $ff + push hl + hlcoord 0, 0 + ld de, ToText + call PlaceString + ld a, [wCurMap] + ld b, $0 + call DrawPlayerOrBirdSprite + ld hl, wFlyLocationsList + decoord 18, 0 +.townMapFlyLoop + ld a, " " + ld [de], a + push hl + push hl + hlcoord 3, 0 + lb bc, 1, 15 + call ClearScreenArea + pop hl + ld a, [hl] + ld b, $4 + call DrawPlayerOrBirdSprite ; draw bird sprite + hlcoord 3, 0 + ld de, wcd6d + call PlaceString + ld c, 15 + call DelayFrames + hlcoord 18, 0 + ld [hl], "▶" + hlcoord 19, 0 + ld [hl], "▼" + pop hl +.inputLoop + push hl + call DelayFrame + call JoypadLowSensitivity + ldh a, [hJoy5] + ld b, a + pop hl + and A_BUTTON | B_BUTTON | D_UP | D_DOWN + jr z, .inputLoop + bit 0, b + jr nz, .pressedA + ld a, SFX_TINK + call PlaySound + bit 6, b + jr nz, .pressedUp + bit 7, b + jr nz, .pressedDown + jr .pressedB +.pressedA + ld a, SFX_HEAL_AILMENT + call PlaySound + ld a, [hl] + ld [wDestinationMap], a + ld hl, wd732 + set 3, [hl] + inc hl + set 7, [hl] +.pressedB + xor a + ld [wTownMapSpriteBlinkingEnabled], a + ldh [hJoy7], a + call GBPalWhiteOutWithDelay3 + pop hl + pop af + ld [hl], a + ret +.pressedUp + decoord 18, 0 + inc hl + ld a, [hl] + cp $ff + jr z, .wrapToStartOfList + cp NOT_VISITED + jr z, .pressedUp ; skip past unvisited towns + jp .townMapFlyLoop +.wrapToStartOfList + ld hl, wFlyLocationsList + jp .townMapFlyLoop +.pressedDown + decoord 19, 0 + dec hl + ld a, [hl] + cp $ff + jr z, .wrapToEndOfList + cp NOT_VISITED + jr z, .pressedDown ; skip past unvisited towns + jp .townMapFlyLoop +.wrapToEndOfList + ld hl, wFlyLocationsList + NUM_CITY_MAPS + jr .pressedDown + +ToText: + db "To@" + +BuildFlyLocationsList: + ld hl, wFlyLocationsList - 1 + ld [hl], $ff + inc hl + ld a, [wTownVisitedFlag] + ld e, a + ld a, [wTownVisitedFlag + 1] + ld d, a + lb bc, 0, NUM_CITY_MAPS +.loop + srl d + rr e + ld a, NOT_VISITED + jr nc, .notVisited + ld a, b ; store the map number of the town if it has been visited +.notVisited + ld [hl], a + inc hl + inc b + dec c + jr nz, .loop + ld [hl], $ff + ret + +TownMapUpArrow: + INCBIN "gfx/town_map/up_arrow.1bpp" +TownMapUpArrowEnd: + +LoadTownMap: + call GBPalWhiteOutWithDelay3 + call ClearScreen + call UpdateSprites + hlcoord 0, 0 + lb bc, $12, $12 + call TextBoxBorder + call DisableLCD + ld hl, WorldMapTileGraphics + ld de, vChars2 tile $60 + ld bc, WorldMapTileGraphicsEnd - WorldMapTileGraphics + ld a, BANK(WorldMapTileGraphics) + call FarCopyData + ld hl, MonNestIcon + ld de, vSprites tile $04 + ld bc, MonNestIconEnd - MonNestIcon + ld a, BANK(MonNestIcon) + call FarCopyDataDouble + hlcoord 0, 0 + ld de, CompressedMap +.nextTile + ld a, [de] + and a + jr z, .done + ld b, a + and $f + ld c, a + ld a, b + swap a + and $f + add $60 +.writeRunLoop + ld [hli], a + dec c + jr nz, .writeRunLoop + inc de + jr .nextTile +.done + call EnableLCD + ld b, SET_PAL_TOWN_MAP + call RunPaletteCommand + call Delay3 + call GBPalNormal + xor a + ld [wAnimCounter], a + inc a + ld [wTownMapSpriteBlinkingEnabled], a + ret + +CompressedMap: + INCBIN "gfx/town_map/town_map.rle" + +ExitTownMap: +; clear town map graphics data and load usual graphics data + xor a + ld [wTownMapSpriteBlinkingEnabled], a + call GBPalWhiteOut + call ClearScreen + call ClearSprites + call LoadPlayerSpriteGraphics + call LoadFontTilePatterns + call UpdateSprites + jp RunDefaultPaletteCommand + +DrawPlayerOrBirdSprite: +; a = map number +; b = OAM base tile + push af + ld a, b + ld [wOAMBaseTile], a + pop af + ld de, wTownMapCoords + call LoadTownMapEntry + ld a, [de] + push hl + call TownMapCoordsToOAMCoords + call WritePlayerOrBirdSpriteOAM + pop hl + ld de, wcd6d +.loop + ld a, [hli] + ld [de], a + inc de + cp "@" + jr nz, .loop + ld hl, wOAMBuffer + ld de, wTileMapBackup + ld bc, $a0 + jp CopyData + +DisplayWildLocations: + farcall FindWildLocationsOfMon + call ZeroOutDuplicatesInList + ld hl, wOAMBuffer + ld de, wTownMapCoords +.loop + ld a, [de] + cp $ff + jr z, .exitLoop + and a + jr z, .nextEntry + push hl + call LoadTownMapEntry + pop hl + ld a, [de] + cp $19 ; Cerulean Cave's coordinates + jr z, .nextEntry ; skip Cerulean Cave + call TownMapCoordsToOAMCoords + ld a, $4 ; nest icon tile no. + ld [hli], a + xor a + ld [hli], a +.nextEntry + inc de + jr .loop +.exitLoop + ld a, l + and a ; were any OAM entries written? + jr nz, .drawPlayerSprite +; if no OAM entries were written, print area unknown text + hlcoord 1, 7 + lb bc, 2, 15 + call TextBoxBorder + hlcoord 2, 9 + ld de, AreaUnknownText + call PlaceString + jr .done +.drawPlayerSprite + ld a, [wCurMap] + ld b, $0 + call DrawPlayerOrBirdSprite +.done + ld hl, wOAMBuffer + ld de, wTileMapBackup + ld bc, $a0 + jp CopyData + +AreaUnknownText: + db " AREA UNKNOWN@" + +TownMapCoordsToOAMCoords: +; in: lower nybble of a = x, upper nybble of a = y +; out: b and [hl] = (y * 8) + 24, c and [hl+1] = (x * 8) + 24 + push af + and $f0 + srl a + add 24 + ld b, a + ld [hli], a + pop af + and $f + swap a + srl a + add 24 + ld c, a + ld [hli], a + ret + +WritePlayerOrBirdSpriteOAM: + ld a, [wOAMBaseTile] + and a + ld hl, wOAMBuffer + $90 ; for player sprite + jr z, WriteTownMapSpriteOAM + ld hl, wOAMBuffer + $80 ; for bird sprite + +WriteTownMapSpriteOAM: + push hl + +; Subtract 4 from c (X coord) and 4 from b (Y coord). However, the carry from c +; is added to b, so the net result is that only 3 is subtracted from b. + lb hl, -4, -4 + add hl, bc + + ld b, h + ld c, l + pop hl + +WriteAsymmetricMonPartySpriteOAM: +; Writes 4 OAM blocks for a helix mon party sprite, since it does not have +; a vertical line of symmetry. + lb de, 2, 2 +.loop + push de + push bc +.innerLoop + ld a, b + ld [hli], a + ld a, c + ld [hli], a + ld a, [wOAMBaseTile] + ld [hli], a + inc a + ld [wOAMBaseTile], a + xor a + ld [hli], a + inc d + ld a, 8 + add c + ld c, a + dec e + jr nz, .innerLoop + pop bc + pop de + ld a, 8 + add b + ld b, a + dec d + jr nz, .loop + ret + +WriteSymmetricMonPartySpriteOAM: +; Writes 4 OAM blocks for a mon party sprite other than a helix. All the +; sprites other than the helix one have a vertical line of symmetry which allows +; the X-flip OAM bit to be used so that only 2 rather than 4 tile patterns are +; needed. + xor a + ld [wSymmetricSpriteOAMAttributes], a + lb de, 2, 2 +.loop + push de + push bc +.innerLoop + ld a, b + ld [hli], a ; Y + ld a, c + ld [hli], a ; X + ld a, [wOAMBaseTile] + ld [hli], a ; tile + ld a, [wSymmetricSpriteOAMAttributes] + ld [hli], a ; attributes + xor (1 << OAM_X_FLIP) + ld [wSymmetricSpriteOAMAttributes], a + inc d + ld a, 8 + add c + ld c, a + dec e + jr nz, .innerLoop + pop bc + pop de + push hl + ld hl, wOAMBaseTile + inc [hl] + inc [hl] + pop hl + ld a, 8 + add b + ld b, a + dec d + jr nz, .loop + ret + +ZeroOutDuplicatesInList: +; replace duplicate bytes in the list of wild pokemon locations with 0 + ld de, wBuffer +.loop + ld a, [de] + inc de + cp $ff + ret z + ld c, a + ld l, e + ld h, d +.zeroDuplicatesLoop + ld a, [hl] + cp $ff + jr z, .loop + cp c + jr nz, .skipZeroing + xor a + ld [hl], a +.skipZeroing + inc hl + jr .zeroDuplicatesLoop + +LoadTownMapEntry: +; in: a = map number +; out: lower nybble of [de] = x, upper nybble of [de] = y, hl = address of name + cp FIRST_INDOOR_MAP + jr c, .external + ld bc, 4 + ld hl, InternalMapEntries +.loop + cp [hl] + jr c, .foundEntry + add hl, bc + jr .loop +.foundEntry + inc hl + jr .readEntry +.external + ld hl, ExternalMapEntries + ld c, a + ld b, 0 + add hl, bc + add hl, bc + add hl, bc +.readEntry + ld a, [hli] + ld [de], a + ld a, [hli] + ld h, [hl] + ld l, a + ret + +INCLUDE "data/maps/town_map_entries.asm" + +INCLUDE "data/maps/names.asm" + +MonNestIcon: + INCBIN "gfx/town_map/mon_nest_icon.1bpp" +MonNestIconEnd: + +TownMapSpriteBlinkingAnimation:: + ld a, [wAnimCounter] + inc a + cp 25 + jr z, .hideSprites + cp 50 + jr nz, .done +; show sprites when the counter reaches 50 + ld hl, wTileMapBackup + ld de, wOAMBuffer + ld bc, $90 + call CopyData + xor a + jr .done +.hideSprites + ld hl, wOAMBuffer + ld b, $24 + ld de, $4 +.hideSpritesLoop + ld [hl], $a0 + add hl, de + dec b + jr nz, .hideSpritesLoop + ld a, 25 +.done + ld [wAnimCounter], a + jp DelayFrame |