FieldMoveJumptableReset: xor a ld hl, wFieldMoveData ld bc, wFieldMoveDataEnd - wFieldMoveData call ByteFill ret FieldMoveJumptable: ld a, [wFieldMoveJumptableIndex] rst JumpTable ld [wFieldMoveJumptableIndex], a bit 7, a jr nz, .okay and a ret .okay and $7f scf ret GetPartyNickname: ; write wCurPartyMon nickname to wStringBuffer1-3 ld hl, wPartyMonNicknames ld a, BOXMON ld [wMonType], a ld a, [wCurPartyMon] call GetNickname call CopyName1 ; copy text from wStringBuffer2 to wStringBuffer3 ld de, wStringBuffer2 ld hl, wStringBuffer3 call CopyName2 ret CheckEngineFlag: ; Check engine flag de ; Return carry if flag is not set ld b, CHECK_FLAG farcall EngineFlagAction ld a, c and a jr nz, .isset scf ret .isset xor a ret CheckBadge: ; Check engine flag a (ENGINE_ZEPHYRBADGE thru ENGINE_EARTHBADGE) ; Display "Badge required" text and return carry if the badge is not owned call CheckEngineFlag ret nc ld hl, .BadgeRequiredText call MenuTextboxBackup ; push text to queue scf ret .BadgeRequiredText: text_far _BadgeRequiredText text_end CheckPartyMoveIndex: ; Check if a monster in your party has move hl. call GetMoveIDFromIndex ld d, a CheckPartyMove: ; Check if a monster in your party has move d. ld e, 0 xor a ld [wCurPartyMon], a .loop ld c, e ld b, 0 ld hl, wPartySpecies add hl, bc ld a, [hl] and a jr z, .no cp -1 jr z, .no cp EGG jr z, .next ld bc, PARTYMON_STRUCT_LENGTH ld hl, wPartyMon1Moves ld a, e call AddNTimes ld b, NUM_MOVES .check ld a, [hli] cp d jr z, .yes dec b jr nz, .check .next inc e jr .loop .yes ld a, e ld [wCurPartyMon], a ; which mon has the move xor a ret .no scf ret FieldMoveFailed: ld hl, .CantUseItemText call MenuTextboxBackup ret .CantUseItemText: text_far _CantUseItemText text_end CutFunction: call FieldMoveJumptableReset .loop ld hl, .Jumptable call FieldMoveJumptable jr nc, .loop and $7f ld [wFieldMoveSucceeded], a ret .Jumptable: dw .CheckAble dw .DoCut dw .FailCut .CheckAble: ld de, ENGINE_HIVEBADGE call CheckBadge jr c, .nohivebadge call CheckMapForSomethingToCut jr c, .nothingtocut ld a, $1 ret .nohivebadge ld a, $80 ret .nothingtocut ld a, $2 ret .DoCut: ld hl, Script_CutFromMenu call QueueScript ld a, $81 ret .FailCut: ld hl, CutNothingText call MenuTextboxBackup ld a, $80 ret UseCutText: text_far _UseCutText text_end CutNothingText: text_far _CutNothingText text_end CheckMapForSomethingToCut: ; Does the collision data of the facing tile permit cutting? call GetFacingTileCoord ld c, a push de farcall CheckCutCollision pop de jr nc, .fail ; Get the location of the current block in wOverworldMapBlocks. call GetBlockLocation ld c, [hl] ; See if that block contains something that can be cut. push hl ld hl, CutTreeBlockPointers call CheckOverworldTileArrays pop hl jr nc, .fail ; Save the Cut field move data ld a, l ld [wCutWhirlpoolOverworldBlockAddr], a ld a, h ld [wCutWhirlpoolOverworldBlockAddr + 1], a ld a, b ld [wCutWhirlpoolReplacementBlock], a ld a, c ld [wCutWhirlpoolAnimationType], a xor a ret .fail scf ret Script_CutFromMenu: reloadmappart special UpdateTimePals Script_Cut: callasm GetPartyNickname writetext UseCutText reloadmappart callasm CutDownTreeOrGrass closetext end CutDownTreeOrGrass: ld hl, wCutWhirlpoolOverworldBlockAddr ld a, [hli] ld h, [hl] ld l, a ld a, [wCutWhirlpoolReplacementBlock] ld [hl], a xor a ldh [hBGMapMode], a call OverworldTextModeSwitch call UpdateSprites call DelayFrame ld a, [wCutWhirlpoolAnimationType] ld e, a farcall OWCutAnimation call BufferScreen call GetMovementPermissions call UpdateSprites call DelayFrame call LoadStandardFont ret CheckOverworldTileArrays: ; Input: c contains the tile you're facing ; Output: Replacement tile in b and effect on wild encounters in c, plus carry set. ; Carry is not set if the facing tile cannot be replaced, or if the tileset ; does not contain a tile you can replace. ; Dictionary lookup for pointer to tile replacement table push bc ld a, [wMapTileset] ld de, 3 call IsInArray pop bc jr nc, .nope ; Load the pointer inc hl ld a, [hli] ld h, [hl] ld l, a ; Look up the tile you're facing ld de, 3 ld a, c call IsInArray jr nc, .nope ; Load the replacement to b inc hl ld b, [hl] ; Load the animation type parameter to c inc hl ld c, [hl] scf ret .nope xor a ret INCLUDE "data/collision/field_move_blocks.asm" FlashFunction: call .CheckUseFlash and $7f ld [wFieldMoveSucceeded], a ret .CheckUseFlash: ld de, ENGINE_ZEPHYRBADGE farcall CheckBadge jr c, .nozephyrbadge push hl farcall SpecialAerodactylChamber pop hl jr c, .useflash ld a, [wTimeOfDayPalset] cp DARKNESS_PALSET jr nz, .notadarkcave .useflash call UseFlash ld a, $81 ret .notadarkcave call FieldMoveFailed ld a, $80 ret .nozephyrbadge ld a, $80 ret UseFlash: ld hl, Script_UseFlash jp QueueScript Script_UseFlash: reloadmappart special UpdateTimePals writetext UseFlashTextScript callasm BlindingFlash closetext end UseFlashTextScript: text_far _BlindingFlashText text_asm call WaitSFX ld de, SFX_FLASH call PlaySFX call WaitSFX ld hl, .BlankText ret .BlankText: text_end SurfFunction: call FieldMoveJumptableReset .loop ld hl, .Jumptable call FieldMoveJumptable jr nc, .loop and $7f ld [wFieldMoveSucceeded], a ret .Jumptable: dw .TrySurf dw .DoSurf dw .FailSurf dw .AlreadySurfing .TrySurf: ld de, ENGINE_FOGBADGE call CheckBadge jr c, .nofogbadge ld hl, wBikeFlags bit BIKEFLAGS_ALWAYS_ON_BIKE_F, [hl] jr nz, .cannotsurf ld a, [wPlayerState] cp PLAYER_SURF jr z, .alreadyfail cp PLAYER_SURF_PIKA jr z, .alreadyfail call GetFacingTileCoord call GetTileCollision cp WATER_TILE jr nz, .cannotsurf call CheckDirection jr c, .cannotsurf farcall CheckFacingObject jr c, .cannotsurf ld a, $1 ret .nofogbadge ld a, $80 ret .alreadyfail ld a, $3 ret .cannotsurf ld a, $2 ret .DoSurf: call GetSurfType ld [wSurfingPlayerState], a call GetPartyNickname ld hl, SurfFromMenuScript call QueueScript ld a, $81 ret .FailSurf: ld hl, CantSurfText call MenuTextboxBackup ld a, $80 ret .AlreadySurfing: ld hl, AlreadySurfingText call MenuTextboxBackup ld a, $80 ret SurfFromMenuScript: special UpdateTimePals UsedSurfScript: ; BUG: Surfing directly across a map connection does not load the new map (see docs/bugs_and_glitches.md) writetext UsedSurfText ; "used SURF!" waitbutton closetext callasm .stubbed_fn readmem wSurfingPlayerState writevar VAR_MOVEMENT special UpdatePlayerSprite special PlayMapMusic ; step into the water (slow_step DIR, step_end) special SurfStartStep applymovement PLAYER, wMovementBuffer end .stubbed_fn farcall StubbedTrainerRankings_Surf ret UsedSurfText: text_far _UsedSurfText text_end CantSurfText: text_far _CantSurfText text_end AlreadySurfingText: text_far _AlreadySurfingText text_end GetSurfType: ; Surfing on Pikachu uses an alternate sprite. ; This is done by using a separate movement type. ld a, [wCurPartyMon] ld e, a ld d, 0 ld hl, PIKACHU call GetPokemonIDFromIndex ld hl, wPartySpecies add hl, de cp [hl] ld a, PLAYER_SURF_PIKA ret z ld a, PLAYER_SURF ret CheckDirection: ; Return carry if a tile permission prevents you ; from moving in the direction you're facing. ; Get player direction ld a, [wPlayerDirection] and %00001100 ; bits 2 and 3 contain direction rrca rrca ld e, a ld d, 0 ld hl, .Directions add hl, de ; Can you walk in this direction? ld a, [wTilePermissions] and [hl] jr nz, .quit xor a ret .quit scf ret .Directions: db FACE_DOWN db FACE_UP db FACE_LEFT db FACE_RIGHT TrySurfOW:: ; Checking a tile in the overworld. ; Return carry if fail is allowed. ; Don't ask to surf if already fail. ld a, [wPlayerState] cp PLAYER_SURF_PIKA jr z, .quit cp PLAYER_SURF jr z, .quit ; Must be facing water. ld a, [wFacingTileID] call GetTileCollision cp WATER_TILE jr nz, .quit ; Check tile permissions. call CheckDirection jr c, .quit ld de, ENGINE_FOGBADGE call CheckEngineFlag jr c, .quit ld hl, SURF call CheckPartyMoveIndex jr c, .quit ld hl, wBikeFlags bit BIKEFLAGS_ALWAYS_ON_BIKE_F, [hl] jr nz, .quit call GetSurfType ld [wSurfingPlayerState], a call GetPartyNickname ld a, BANK(AskSurfScript) ld hl, AskSurfScript call CallScript scf ret .quit xor a ret AskSurfScript: opentext writetext AskSurfText yesorno iftrue UsedSurfScript closetext end AskSurfText: text_far _AskSurfText text_end FlyFunction: call FieldMoveJumptableReset .loop ld hl, .Jumptable call FieldMoveJumptable jr nc, .loop and $7f ld [wFieldMoveSucceeded], a ret .Jumptable: dw .TryFly dw .DoFly dw .FailFly .TryFly: ld de, ENGINE_STORMBADGE call CheckBadge jr c, .nostormbadge ld a, [wMapTileset] cp TILESET_UNDERWATER jr z, .indoors call GetMapEnvironment call CheckOutdoorMap jr z, .outdoors jr .indoors .outdoors xor a ldh [hMapAnims], a call LoadStandardMenuHeader call ClearSprites farcall _FlyMap ld a, e cp -1 jr z, .illegal cp NUM_SPAWNS jr nc, .illegal ld [wDefaultSpawnpoint], a call CloseWindow ld a, $1 ret .nostormbadge ld a, $82 ret .indoors ld a, $2 ret .illegal call CloseWindow call WaitBGMap ld a, $80 ret .DoFly: ld hl, .FlyScript call QueueScript ld a, $81 ret .FailFly: call FieldMoveFailed ld a, $82 ret .FlyScript: reloadmappart callasm HideSprites special UpdateTimePals callasm FlyFromAnim farscall Script_AbortBugContest special WarpToSpawnPoint callasm SkipUpdateMapSprites loadvar VAR_MOVEMENT, PLAYER_NORMAL newloadmap MAPSETUP_FLY callasm FlyToAnim special WaitSFX callasm .ReturnFromFly end .ReturnFromFly: farcall RespawnPlayer call DelayFrame call UpdatePlayerSprite farcall LoadOverworldFont ret WaterfallFunction: call .TryWaterfall and $7f ld [wFieldMoveSucceeded], a ret .TryWaterfall: ld de, ENGINE_RISINGBADGE farcall CheckBadge ld a, $80 ret c call CheckMapCanWaterfall jr c, .failed ld hl, Script_WaterfallFromMenu call QueueScript ld a, $81 ret .failed call FieldMoveFailed ld a, $80 ret CheckMapCanWaterfall: ld a, [wPlayerDirection] and $c cp FACE_UP jr nz, .failed ld a, [wTileUp] call CheckWaterfallTile jr nz, .failed xor a ret .failed scf ret Script_WaterfallFromMenu: reloadmappart special UpdateTimePals Script_UsedWaterfall: callasm GetPartyNickname writetext .UseWaterfallText waitbutton closetext playsound SFX_BUBBLEBEAM .loop applymovement PLAYER, .WaterfallStep callasm .CheckContinueWaterfall iffalse .loop end .CheckContinueWaterfall: xor a ld [wScriptVar], a ld a, [wPlayerTile] call CheckWaterfallTile ret z farcall StubbedTrainerRankings_Waterfall ld a, $1 ld [wScriptVar], a ret .WaterfallStep: turn_waterfall UP step_end .UseWaterfallText: text_far _UseWaterfallText text_end TryWaterfallOW:: ld hl, WATERFALL call CheckPartyMoveIndex jr c, .failed ld de, ENGINE_RISINGBADGE call CheckEngineFlag jr c, .failed call CheckMapCanWaterfall jr c, .failed ld a, BANK(Script_AskWaterfall) ld hl, Script_AskWaterfall call CallScript scf ret .failed ld a, BANK(Script_CantDoWaterfall) ld hl, Script_CantDoWaterfall call CallScript scf ret Script_CantDoWaterfall: jumptext .HugeWaterfallText .HugeWaterfallText: text_far _HugeWaterfallText text_end Script_AskWaterfall: opentext writetext .AskWaterfallText yesorno iftrue Script_UsedWaterfall closetext end .AskWaterfallText: text_far _AskWaterfallText text_end EscapeRopeFunction: call FieldMoveJumptableReset ld a, $1 jr EscapeRopeOrDig DigFunction: call FieldMoveJumptableReset ld a, $2 EscapeRopeOrDig: ld [wEscapeRopeOrDigType], a .loop ld hl, .DigTable call FieldMoveJumptable jr nc, .loop and $7f ld [wFieldMoveSucceeded], a ret .DigTable: dw .CheckCanDig dw .DoDig dw .FailDig .CheckCanDig: call GetMapEnvironment cp CAVE jr z, .incave cp DUNGEON jr z, .incave cp FOREST jr z, .incave .fail ld a, $2 ret .incave ld hl, wDigWarpNumber ld a, [hli] and a jr z, .fail ld a, [hli] and a jr z, .fail ld a, [hl] and a jr z, .fail ld a, $1 ret .DoDig: ld hl, wDigWarpNumber ld de, wNextWarp ld bc, 3 call CopyBytes call GetPartyNickname ld a, [wEscapeRopeOrDigType] cp $2 jr nz, .escaperope ld hl, .UsedDigScript call QueueScript ld a, $81 ret .escaperope farcall SpecialKabutoChamber ld hl, .UsedEscapeRopeScript call QueueScript ld a, $81 ret .FailDig: ld a, [wEscapeRopeOrDigType] cp $2 jr nz, .failescaperope ld hl, .CantUseDigText call MenuTextbox call WaitPressAorB_BlinkCursor call CloseWindow .failescaperope ld a, $80 ret .UseDigText: text_far _UseDigText text_end .UseEscapeRopeText: text_far _UseEscapeRopeText text_end .CantUseDigText: text_far _CantUseDigText text_end .UsedEscapeRopeScript: reloadmappart special UpdateTimePals writetext .UseEscapeRopeText sjump .UsedDigOrEscapeRopeScript .UsedDigScript: reloadmappart special UpdateTimePals writetext .UseDigText .UsedDigOrEscapeRopeScript: waitbutton closetext playsound SFX_WARP_TO applymovement PLAYER, .DigOut farscall Script_AbortBugContest special WarpToSpawnPoint loadvar VAR_MOVEMENT, PLAYER_NORMAL newloadmap MAPSETUP_DOOR playsound SFX_WARP_FROM applymovement PLAYER, .DigReturn end .DigOut: step_dig 32 hide_object step_end .DigReturn: show_object return_dig 32 step_end TeleportFunction: call FieldMoveJumptableReset .loop ld hl, .Jumptable call FieldMoveJumptable jr nc, .loop and $7f ld [wFieldMoveSucceeded], a ret .Jumptable: dw .TryTeleport dw .DoTeleport dw .FailTeleport .TryTeleport: call GetMapEnvironment call CheckOutdoorMap jr z, .CheckIfSpawnPoint jr .nope .CheckIfSpawnPoint: ld a, [wLastSpawnMapGroup] ld d, a ld a, [wLastSpawnMapNumber] ld e, a farcall IsSpawnPoint jr nc, .nope ld a, c ld [wDefaultSpawnpoint], a ld a, $1 ret .nope ld a, $2 ret .DoTeleport: call GetPartyNickname ld hl, .TeleportScript call QueueScript ld a, $81 ret .FailTeleport: ld hl, .CantUseTeleportText call MenuTextboxBackup ld a, $80 ret .TeleportReturnText: text_far _TeleportReturnText text_end .CantUseTeleportText: text_far _CantUseTeleportText text_end .TeleportScript: reloadmappart special UpdateTimePals writetext .TeleportReturnText pause 60 reloadmappart closetext playsound SFX_WARP_TO applymovement PLAYER, .TeleportFrom farscall Script_AbortBugContest special WarpToSpawnPoint loadvar VAR_MOVEMENT, PLAYER_NORMAL newloadmap MAPSETUP_TELEPORT playsound SFX_WARP_FROM applymovement PLAYER, .TeleportTo end .TeleportFrom: teleport_from step_end .TeleportTo: teleport_to step_end StrengthFunction: call .TryStrength and $7f ld [wFieldMoveSucceeded], a ret .TryStrength: ld de, ENGINE_PLAINBADGE call CheckBadge jr c, .Failed jr .UseStrength .AlreadyUsingStrengthText: text_far _AlreadyUsingStrengthText text_end .Failed: ld a, $80 ret .UseStrength: ld hl, Script_StrengthFromMenu call QueueScript ld a, $81 ret SetStrengthFlag: ld hl, wBikeFlags set BIKEFLAGS_STRENGTH_ACTIVE_F, [hl] ld a, [wCurPartyMon] ld e, a ld d, 0 ld hl, wPartySpecies add hl, de ld a, [hl] ld [wStrengthSpecies], a call GetPartyNickname ret Script_StrengthFromMenu: reloadmappart special UpdateTimePals Script_UsedStrength: callasm SetStrengthFlag writetext .UseStrengthText readmem wStrengthSpecies cry 0 ; plays [wStrengthSpecies] cry pause 3 writetext .MoveBoulderText closetext end .UseStrengthText: text_far _UseStrengthText text_end .MoveBoulderText: text_far _MoveBoulderText text_end AskStrengthScript: callasm TryStrengthOW iffalse .AskStrength ifequal $1, .DontMeetRequirements sjump .AlreadyUsedStrength .DontMeetRequirements: jumptext BouldersMayMoveText .AlreadyUsedStrength: jumptext BouldersMoveText .AskStrength: opentext writetext AskStrengthText yesorno iftrue Script_UsedStrength closetext end AskStrengthText: text_far _AskStrengthText text_end BouldersMoveText: text_far _BouldersMoveText text_end BouldersMayMoveText: text_far _BouldersMayMoveText text_end TryStrengthOW: ld hl, STRENGTH call CheckPartyMoveIndex jr c, .nope ld de, ENGINE_PLAINBADGE call CheckEngineFlag jr c, .nope ld hl, wBikeFlags bit BIKEFLAGS_STRENGTH_ACTIVE_F, [hl] jr z, .already_using ld a, 2 jr .done .nope ld a, 1 jr .done .already_using xor a jr .done .done ld [wScriptVar], a ret WhirlpoolFunction: call FieldMoveJumptableReset .loop ld hl, .Jumptable call FieldMoveJumptable jr nc, .loop and $7f ld [wFieldMoveSucceeded], a ret .Jumptable: dw .TryWhirlpool dw .DoWhirlpool dw .FailWhirlpool .TryWhirlpool: ld de, ENGINE_GLACIERBADGE call CheckBadge jr c, .noglacierbadge call TryWhirlpoolMenu jr c, .failed ld a, $1 ret .failed ld a, $2 ret .noglacierbadge ld a, $80 ret .DoWhirlpool: ld hl, Script_WhirlpoolFromMenu call QueueScript ld a, $81 ret .FailWhirlpool: call FieldMoveFailed ld a, $80 ret UseWhirlpoolText: text_far _UseWhirlpoolText text_end TryWhirlpoolMenu: call GetFacingTileCoord ld c, a push de call CheckWhirlpoolTile pop de jr c, .failed call GetBlockLocation ld c, [hl] push hl ld hl, WhirlpoolBlockPointers call CheckOverworldTileArrays pop hl jr nc, .failed ; Save the Whirlpool field move data ld a, l ld [wCutWhirlpoolOverworldBlockAddr], a ld a, h ld [wCutWhirlpoolOverworldBlockAddr + 1], a ld a, b ld [wCutWhirlpoolReplacementBlock], a ld a, c ld [wCutWhirlpoolAnimationType], a xor a ret .failed scf ret Script_WhirlpoolFromMenu: reloadmappart special UpdateTimePals Script_UsedWhirlpool: callasm GetPartyNickname writetext UseWhirlpoolText reloadmappart callasm DisappearWhirlpool closetext end DisappearWhirlpool: ld hl, wCutWhirlpoolOverworldBlockAddr ld a, [hli] ld h, [hl] ld l, a ld a, [wCutWhirlpoolReplacementBlock] ld [hl], a xor a ldh [hBGMapMode], a call OverworldTextModeSwitch ld a, [wCutWhirlpoolAnimationType] ld e, a farcall PlayWhirlpoolSound call BufferScreen call GetMovementPermissions ret TryWhirlpoolOW:: ld hl, WHIRLPOOL call CheckPartyMoveIndex jr c, .failed ld de, ENGINE_GLACIERBADGE call CheckEngineFlag jr c, .failed call TryWhirlpoolMenu jr c, .failed ld a, BANK(Script_AskWhirlpoolOW) ld hl, Script_AskWhirlpoolOW call CallScript scf ret .failed ld a, BANK(Script_MightyWhirlpool) ld hl, Script_MightyWhirlpool call CallScript scf ret Script_MightyWhirlpool: jumptext .MayPassWhirlpoolText .MayPassWhirlpoolText: text_far _MayPassWhirlpoolText text_end Script_AskWhirlpoolOW: opentext writetext AskWhirlpoolText yesorno iftrue Script_UsedWhirlpool closetext end AskWhirlpoolText: text_far _AskWhirlpoolText text_end HeadbuttFunction: call TryHeadbuttFromMenu and $7f ld [wFieldMoveSucceeded], a ret TryHeadbuttFromMenu: call GetFacingTileCoord call CheckHeadbuttTreeTile jr nz, .no_tree ld hl, HeadbuttFromMenuScript call QueueScript ld a, $81 ret .no_tree call FieldMoveFailed ld a, $80 ret UseHeadbuttText: text_far _UseHeadbuttText text_end HeadbuttNothingText: text_far _HeadbuttNothingText text_end HeadbuttFromMenuScript: reloadmappart special UpdateTimePals HeadbuttScript: callasm GetPartyNickname writetext UseHeadbuttText reloadmappart callasm ShakeHeadbuttTree callasm TreeMonEncounter iffalse .no_battle closetext randomwildmon startbattle reloadmapafterbattle end .no_battle writetext HeadbuttNothingText waitbutton closetext end TryHeadbuttOW:: ld hl, HEADBUTT call CheckPartyMoveIndex jr c, .no ld a, BANK(AskHeadbuttScript) ld hl, AskHeadbuttScript call CallScript scf ret .no xor a ret AskHeadbuttScript: opentext callasm TrySweetHoneyOW writetext AskHeadbuttText yesorno iftrue HeadbuttScript closetext end AskHeadbuttText: text_far _AskHeadbuttText text_end TrySweetHoneyOW: ; is player at the right position? call CheckSavedSweetHoneySpot ret nz ; return if not farcall _CheckSweetHoneyTimer ld a, [wSweetHoneyTimer] and a ; ret z ; - added day 2 check- ld hl, .TwoDaysAgoText jr z, .print_message ; - end add - ld hl, .YesterdayText cp 1 ; day left jr z, .print_message cp 2 ; days left ret nz ld hl, .TodayText .print_message ; writetext push hl call SpeechTextbox call SafeUpdateSprites ld a, 1 ldh [hOAMUpdate], a call ApplyTilemap pop hl call PrintTextboxText xor a ldh [hOAMUpdate], a ret .TodayText: text "There's SWEET HONEY" line "on the tree!" para "It's still fresh." prompt .YesterdayText: text "There's SWEET HONEY" line "on the tree!" para "It's about a day" line "old." prompt .TwoDaysAgoText: text "There's SWEET HONEY" line "on the tree!" para "Looks ripe!" prompt CheckSavedSweetHoneySpot: ; Z flag is set when player is in the exact spot ; where Sweet Honey is applied ; check map group ld hl, wSweetHoneyMapGroup ld a, [wMapGroup] cp [hl] ret nz ; map number inc hl ; wSweetHoneyMapNumber ld a, [wMapNumber] cp [hl] ret nz ; X and Y call GetFacingTileCoord ld a, [wSweetHoneyX] cp d ret nz ld a, [wSweetHoneyY] cp e ret RockSmashFunction: call TryRockSmashFromMenu and $7f ld [wFieldMoveSucceeded], a ret TryRockSmashFromMenu: call GetFacingObject jr c, .no_rock ld a, d cp SPRITEMOVEDATA_SMASHABLE_ROCK jr nz, .no_rock ld hl, RockSmashFromMenuScript call QueueScript ld a, $81 ret .no_rock call FieldMoveFailed ld a, $80 ret GetFacingObject: farcall CheckFacingObject jr nc, .fail ldh a, [hObjectStructIndex] call GetObjectStruct ld hl, OBJECT_MAP_OBJECT_INDEX add hl, bc ld a, [hl] ldh [hLastTalked], a call GetMapObject ld hl, MAPOBJECT_MOVEMENT add hl, bc ld a, [hl] ld d, a and a ret .fail scf ret RockSmashFromMenuScript: reloadmappart special UpdateTimePals RockSmashScript: callasm GetPartyNickname writetext UseRockSmashText closetext special WaitSFX playsound SFX_STRENGTH earthquake 84 applymovementlasttalked MovementData_RockSmash disappear -2 callasm RockMonEncounter readmem wTempWildMonSpecies iffalse .no_battle randomwildmon startbattle reloadmapafterbattle end ; from https://github.com/pret/pokecrystal/wiki/Smashing-rocks-has-a-chance-to-contain-items .no_battle callasm RockItemEncounter iffalse .no_item opentext verbosegiveitem ITEM_FROM_MEM closetext .no_item end MovementData_RockSmash: rock_smash 10 step_end UseRockSmashText: text_far _UseRockSmashText text_end AskRockSmashScript: callasm HasRockSmash ifequal 1, .no opentext writetext AskRockSmashText yesorno iftrue RockSmashScript closetext end .no jumptext MaySmashText MaySmashText: text_far _MaySmashText text_end AskRockSmashText: text_far _AskRockSmashText text_end HasRockSmash: ld hl, ROCK_SMASH call CheckPartyMoveIndex jr nc, .yes ; no ld a, 1 jr .done .yes xor a jr .done .done ld [wScriptVar], a ret FishFunction: ld a, e push af call FieldMoveJumptableReset pop af ld [wFishingRodUsed], a .loop ld hl, .FishTable call FieldMoveJumptable jr nc, .loop and $7f ld [wFieldMoveSucceeded], a ret .FishTable: dw .TryFish dw .FishNoBite dw .FishGotSomething dw .FailFish dw .FishNoFish .TryFish: ; BUG: You can fish on top of NPCs (see docs/bugs_and_glitches.md) ld a, [wPlayerState] cp PLAYER_SURF jr z, .fail cp PLAYER_SURF_PIKA jr z, .fail cp PLAYER_WATER_SPORT jr z, .fail call GetFacingTileCoord call GetTileCollision cp WATER_TILE jr z, .facingwater .fail ld a, $3 ret .facingwater call GetFishingGroup and a jr nz, .goodtofish ld a, $4 ret .goodtofish ld d, a ld a, [wFishingRodUsed] ld e, a farcall Fish ld a, d and a jr z, .nonibble ld [wTempWildMonSpecies], a ld a, e ld [wCurPartyLevel], a ld a, BATTLETYPE_FISH ld [wBattleType], a ld a, $2 ret .nonibble ld a, $1 ret .FailFish: ld a, $80 ret .FishGotSomething: ld a, $1 ld [wFishingResult], a ld hl, Script_GotABite call QueueScript ld a, $81 ret .FishNoBite: ld a, $2 ld [wFishingResult], a ld hl, Script_NotEvenANibble call QueueScript ld a, $81 ret .FishNoFish: ld a, $0 ld [wFishingResult], a ld hl, Script_NotEvenANibble2 call QueueScript ld a, $81 ret Script_NotEvenANibble: scall Script_FishCastRod writetext RodNothingText sjump Script_NotEvenANibble_FallThrough Script_NotEvenANibble2: scall Script_FishCastRod writetext RodNothingText Script_NotEvenANibble_FallThrough: loademote EMOTE_SHADOW callasm PutTheRodAway closetext end Script_GotABite: scall Script_FishCastRod callasm Fishing_CheckFacingUp iffalse .NotFacingUp applymovement PLAYER, .Movement_FacingUp sjump .FightTheHookedPokemon .NotFacingUp: applymovement PLAYER, .Movement_NotFacingUp .FightTheHookedPokemon: pause 40 applymovement PLAYER, .Movement_RestoreRod writetext RodBiteText callasm PutTheRodAway closetext randomwildmon startbattle reloadmapafterbattle end .Movement_NotFacingUp: fish_got_bite fish_got_bite fish_got_bite fish_got_bite show_emote step_end .Movement_FacingUp: fish_got_bite fish_got_bite fish_got_bite fish_got_bite step_sleep 1 show_emote step_end .Movement_RestoreRod: hide_emote fish_cast_rod step_end Fishing_CheckFacingUp: ld a, [wPlayerDirection] and $c cp OW_UP ld a, $1 jr z, .up xor a .up ld [wScriptVar], a ret Script_FishCastRod: reloadmappart loadmem hBGMapMode, $0 special UpdateTimePals loademote EMOTE_ROD callasm LoadFishingGFX loademote EMOTE_SHOCK applymovement PLAYER, MovementData_CastRod pause 40 end MovementData_CastRod: fish_cast_rod step_end PutTheRodAway: xor a ldh [hBGMapMode], a ld a, $1 ld [wPlayerAction], a call UpdateSprites call UpdatePlayerSprite ret RodBiteText: text_far _RodBiteText text_end RodNothingText: text_far _RodNothingText text_end UnusedNothingHereText: ; unreferenced text_far _UnusedNothingHereText text_end BikeFunction: call .TryBike and $7f ld [wFieldMoveSucceeded], a ret .TryBike: call .CheckEnvironment jr c, .CannotUseBike ld a, [wPlayerState] cp PLAYER_NORMAL jr z, .GetOnBike cp PLAYER_BIKE jr z, .GetOffBike jr .CannotUseBike .GetOnBike: ld hl, Script_GetOnBike ld de, Script_GetOnBike_Register call .CheckIfRegistered call QueueScript xor a ld [wMusicFade], a ld de, MUSIC_NONE call PlayMusic call DelayFrame call MaxVolume ld de, MUSIC_BICYCLE ld a, e ld [wMapMusic], a call PlayMusic ld a, $1 ret .GetOffBike: ld hl, wBikeFlags bit BIKEFLAGS_ALWAYS_ON_BIKE_F, [hl] jr nz, .CantGetOffBike ld hl, Script_GetOffBike ld de, Script_GetOffBike_Register call .CheckIfRegistered ld a, BANK(Script_GetOffBike) jr .done .CantGetOffBike: ld hl, Script_CantGetOffBike jr .done .CannotUseBike: ld a, $0 ret .done call QueueScript ld a, $1 ret .CheckIfRegistered: ld a, [wUsingItemWithSelect] and a ret z ld h, d ld l, e ret .CheckEnvironment: call GetMapEnvironment call CheckOutdoorMap jr z, .ok cp CAVE jr z, .ok cp GATE jr z, .ok cp FOREST jr z, .ok jr .nope .ok call GetPlayerTile and $f ; lo nybble only jr nz, .nope ; not FLOOR_TILE xor a ret .nope scf ret Script_GetOnBike: reloadmappart special UpdateTimePals loadvar VAR_MOVEMENT, PLAYER_BIKE writetext GotOnBikeText waitbutton closetext special UpdatePlayerSprite end Script_GetOnBike_Register: loadvar VAR_MOVEMENT, PLAYER_BIKE closetext special UpdatePlayerSprite end Overworld_DummyFunction: ; unreferenced nop ret Script_GetOffBike: reloadmappart special UpdateTimePals loadvar VAR_MOVEMENT, PLAYER_NORMAL writetext GotOffBikeText waitbutton FinishGettingOffBike: closetext special UpdatePlayerSprite special PlayMapMusic end Script_GetOffBike_Register: loadvar VAR_MOVEMENT, PLAYER_NORMAL sjump FinishGettingOffBike Script_CantGetOffBike: writetext .CantGetOffBikeText waitbutton closetext end .CantGetOffBikeText: text_far _CantGetOffBikeText text_end GotOnBikeText: text_far _GotOnBikeText text_end GotOffBikeText: text_far _GotOffBikeText text_end TryCutOW:: ld hl, CUT call CheckPartyMoveIndex jr c, .cant_cut ld de, ENGINE_HIVEBADGE call CheckEngineFlag jr c, .cant_cut ld a, BANK(AskCutScript) ld hl, AskCutScript call CallScript scf ret .cant_cut ld a, BANK(CantCutScript) ld hl, CantCutScript call CallScript scf ret AskCutScript: opentext writetext AskCutText yesorno iffalse .declined callasm .CheckMap iftrue Script_Cut .declined closetext end .CheckMap: xor a ld [wScriptVar], a call CheckMapForSomethingToCut ret c ld a, TRUE ld [wScriptVar], a ret AskCutText: text_far _AskCutText text_end CantCutScript: jumptext CanCutText CanCutText: text_far _CanCutText text_end ; Strong Arm is currently just Rock Climb. It's progressgated to after the Earth Badge, just as Rock Climb was in HGSS. ; This is a fine reward for beating Kanto, so I think it's ok to be here. ; It implies Rock Climb will be given in Oak's Lab. ; Eventually, this will also contain checks that jump to Strength and Rock Smash. StrongArmFunction: call FieldMoveJumptableReset .loop ld hl, .jumptable call FieldMoveJumptable jr nc, .loop and $7f ld [wFieldMoveSucceeded], a ret .jumptable: dw .TryStrongArm dw .DoStrongArm dw .FailStrongArm .TryStrongArm: ld de, ENGINE_EARTHBADGE farcall CheckBadge jr c, .noearthbadge call TryStrongArmMenu jr c, .failed ld a, $1 ret .noearthbadge ld a, $80 ret .failed ld a, $2 ret .DoStrongArm: ld hl, StrongArmFromMenuScript call QueueScript ld a, $81 ret .FailStrongArm: call FieldMoveFailed ld a, $80 ret TryStrongArmMenu: call GetFacingTileCoord ld c, a push de call CheckRockyWallTile pop de jr nz, .failed xor a ret .failed scf ret ; You land here when you've successfully checked a wall. TryStrongArmOW:: ; First, check if you have the Earth Badge. ; You will, because you get the move afterwards, it just covers trading. ld de, ENGINE_EARTHBADGE call CheckEngineFlag jr c, .cant_climb ; Now check if Strong Arm is in the party. This takes longer, thus the above going first. ld d, STRONG_ARM call CheckPartyMove jr c, .cant_climb ld a, BANK(AskStrongArmScript) ld hl, AskStrongArmScript call CallScript scf ret .cant_climb ld a, BANK(CantStrongArmScript) ld hl, CantStrongArmScript call CallScript scf ret AskStrongArmScript: opentext writetext AskStrongArmText yesorno iftrue UsedStrongArmScript closetext end CantStrongArmScript: jumptext CantStrongArmText StrongArmFromMenuScript: reloadmappart special UpdateTimePals UsedStrongArmScript: callasm GetPartyNickname ; BUG: When used in the OW, the Pokemon is picked wrong. Tested with Machamp and Furret in party, and Furret would always be picked, regardless of party position. Seems to be finding the wrong Pokemon in OW scenarios specifically. wStringBuffer2 is failing to update. writetext UsedStrongArmText closetext loadvar VAR_MOVEMENT, PLAYER_NORMAL special UpdatePlayerSprite waitsfx playsound SFX_STRENGTH readvar VAR_FACING if_equal DOWN, .Down .loop_up applymovement PLAYER, .StrongArmUpStep callasm .CheckContinueStrongArm iffalse .loop_up end .Down: applymovement PLAYER, .StrongArmFixFacing .loop_down applymovement PLAYER, .StrongArmDownStep callasm .CheckContinueStrongArm iffalse .loop_down applymovement PLAYER, .StrongArmRemoveFixedFacing end .CheckContinueStrongArm: xor a ld [wScriptVar], a ld a, [wPlayerTile] call CheckRockyWallTile ret z ld a, $1 ld [wScriptVar], a ret .StrongArmUpStep: step UP step_end .StrongArmDownStep: step DOWN step_end .StrongArmFixFacing: turn_head UP fix_facing step_end .StrongArmRemoveFixedFacing: remove_fixed_facing turn_head DOWN step_end AskStrongArmText: text_far _AskStrongArmText text_end UsedStrongArmText: text_far _UsedStrongArmText text_end CantStrongArmText: text_far _CantStrongArmText text_end WaterSportFunction: call FieldMoveJumptableReset .loop ld hl, .Jumptable call FieldMoveJumptable jr nc, .loop and $7f ld [wFieldMoveSucceeded], a ret .Jumptable: dw .TryWaterSport dw .DoWaterSport dw .FailWaterSport .TryWaterSport: ld de, ENGINE_CASCADEBADGE call CheckBadge jr c, .nocascadebadge call CheckMapCanWaterSport jr nz, .cannotdive ld a, $1 ret .nocascadebadge ld a, $80 ret .cannotdive ld a, $2 ret .DoWaterSport: call GetPartyNickname ld hl, WaterSportFromMenuScript call QueueScript ld a, $81 ret .FailWaterSport: ld hl, CantWaterSportText call MenuTextboxBackup ld a, $80 ret CantWaterSportText: text_jump _CantWaterSportText db "@" CheckMapCanWaterSport: ld a, [wDiveMapGroup] and a jr z, .failed ld a, [wDiveMapNumber] and a jr z, .failed ld a, [wPlayerTile] call CheckDiveTile jr nz, .failed xor a ret .failed scf ret TryWaterSportOW:: call CheckMapCanWaterSport jr c, .failed ld de, ENGINE_CASCADEBADGE call CheckEngineFlag jr c, .cant ld d, WATER_SPORT call CheckPartyMove jr c, .cant call GetPartyNickname ld a, BANK(AskWaterSportScript) ld hl, AskWaterSportScript call CallScript scf ret .failed xor a ret .cant ld a, BANK(CantWaterSportScript) ld hl, CantWaterSportScript call CallScript scf ret CantWaterSportScript: jumptext CanWaterSportText CanWaterSportText: text_jump _CanWaterSportText db "@" AskWaterSportScript: opentext copybytetovar wPlayerTile ifequal COLL_DIVE_UP, .up writetext AskWaterSportDownText jump .continue .up writetext AskWaterSportUpText .continue yesorno iftrue UsedWaterSportScript closetext end AskWaterSportDownText: text_jump _AskWaterSportDownText db "@" AskWaterSportUpText: text_jump _AskWaterSportUpText db "@" WaterSportFromMenuScript: special UpdateTimePals UsedWaterSportScript: writetext UsedWaterSportText waitbutton closetext special FadeOutPalettes waitsfx divewarp end UsedWaterSportText: text_jump _UsedWaterSportText db "@"