Refactor chooseboxmon (#8491)

Co-authored-by: Alex <93446519+AlexOn1ine@users.noreply.github.com>
This commit is contained in:
FosterProgramming
2026-01-22 19:54:19 +01:00
committed by GitHub
parent fb4c8ef62c
commit fe2c154b89
45 changed files with 1337 additions and 1691 deletions

View File

@@ -470,6 +470,7 @@ $(TEST_BUILDDIR)/%.o: CFLAGS := -mthumb -mthumb-interwork -O2 -mabi=apcs-gnu -mt
# Dependency rules (for the *.c & *.s sources to .o files)
# Have to be explicit or else missing files won't be reported.
$(C_BUILDDIR)/pokemon.o: $(C_SUBDIR)/pokemon.c $(DATA_SRC_SUBDIR)/pokemon/teachable_learnsets.h
$(C_BUILDDIR)/move_relearner.o: $(C_SUBDIR)/move_relearner.c $(DATA_SRC_SUBDIR)/tutor_moves.h
# As a side effect, they're evaluated immediately instead of when the rule is invoked.
# It doesn't look like $(shell) can be deferred so there might not be a better way (Icedude_907: there is soon).

View File

@@ -2628,6 +2628,47 @@
callnative DoFacilityTrainerBattle
.byte \facility
.endm
.macro ingame_trade tradeId:req wantTradeMsg:req, declineTradeJump:req, wrongMonJump:req, tradeCompleteMsg:req
setvar VAR_0x8005, \tradeId
specialvar VAR_0x8009, GetInGameTradeSpeciesInfo
msgbox \wantTradeMsg, MSGBOX_YESNO
goto_if_eq VAR_RESULT, NO, \declineTradeJump
chooseboxmon SELECT_PC_MON_TRADE
waitstate
goto_if_eq VAR_0x8004, PARTY_NOTHING_CHOSEN, \declineTradeJump
specialvar VAR_0x800B, GetTradeSpecies
goto_if_ne VAR_0x800B, VAR_0x8009, \wrongMonJump
special CreateInGameTradePokemon
special DoInGameTradeScene
waitstate
msgbox \tradeCompleteMsg, MSGBOX_DEFAULT
.endm
.macro move_tutor moveId:req, wantTeachingMsg:req, monSelectMsg:req, declinedJmp:req, taughtJmp:req, flagId=0
.if \flagId
goto_if_set \flagId, \taughtJmp
.endif
msgbox \wantTeachingMsg, MSGBOX_YESNO
goto_if_eq VAR_RESULT, NO, \declinedJmp
.if \flagId
call MoveTutor_EventScript_CanOnlyBeLearnedOnce
goto_if_eq VAR_RESULT, NO, \declinedJmp
.endif
msgbox \monSelectMsg, MSGBOX_DEFAULT
setvar VAR_0x8005, \moveId
call MoveTutor_EventScript_OpenBox
goto_if_eq VAR_RESULT, FALSE, \declinedJmp
.if \flagId
setflag \flagId
.endif
goto \taughtJmp
.endm
.macro chooseboxmon selectionType=SELECT_PC_MON_NORMAL
callnative ChooseBoxMon
.byte \selectionType
.endm
@ Follower NPCs

View File

@@ -12,8 +12,7 @@ BattleFrontier_Lounge1_EventScript_Breeder::
end
BattleFrontier_Lounge1_EventScript_ChooseMonToShowBreeder::
fadescreen FADE_TO_BLACK
special ChooseBoxMon
chooseboxmon
waitstate
goto_if_ne VAR_0x8004, PARTY_NOTHING_CHOSEN, BattleFrontier_Lounge1_EventScript_ShowMonToBreeder
goto_if_eq VAR_0x8004, PARTY_NOTHING_CHOSEN, BattleFrontier_Lounge1_EventScript_CancelMonSelect

View File

@@ -6,8 +6,7 @@ BattleFrontier_Lounge5_EventScript_NatureGirl::
faceplayer
msgbox BattleFrontier_Lounge5_Text_NatureGirlGreeting, MSGBOX_YESNO
goto_if_eq VAR_RESULT, NO, BattleFrontier_Lounge5_EventScript_NatureGirlNoneShown
fadescreen FADE_TO_BLACK
special ChooseBoxMon
chooseboxmon
waitstate
lock
faceplayer

View File

@@ -5,27 +5,7 @@ BattleFrontier_Lounge6_EventScript_Trader::
lock
faceplayer
goto_if_set FLAG_BATTLE_FRONTIER_TRADE_DONE, BattleFrontier_Lounge6_EventScript_TradeCompleted
setvar VAR_0x8008, INGAME_TRADE_MEOWTH
copyvar VAR_0x8004, VAR_0x8008
specialvar VAR_RESULT, GetInGameTradeSpeciesInfo
copyvar VAR_0x8009, VAR_RESULT
msgbox BattleFrontier_Lounge6_Text_WouldYouLikeToTrade, MSGBOX_YESNO
goto_if_eq VAR_RESULT, NO, BattleFrontier_Lounge6_EventScript_DeclineTrade
fadescreen FADE_TO_BLACK
special ChooseBoxMon
waitstate
copyvar VAR_0x800A, VAR_0x8004
goto_if_eq VAR_0x8004, PARTY_NOTHING_CHOSEN, BattleFrontier_Lounge6_EventScript_DeclineTrade
copyvar VAR_0x8005, VAR_0x800A
specialvar VAR_RESULT, GetTradeSpecies
copyvar VAR_0x800B, VAR_RESULT
goto_if_ne VAR_RESULT, VAR_0x8009, BattleFrontier_Lounge6_EventScript_NotRequestedMon
copyvar VAR_0x8004, VAR_0x8008
copyvar VAR_0x8005, VAR_0x800A
special CreateInGameTradePokemon
special DoInGameTradeScene
waitstate
msgbox BattleFrontier_Lounge6_Text_PromiseIllBeGoodToIt, MSGBOX_DEFAULT
ingame_trade INGAME_TRADE_MEOWTH, BattleFrontier_Lounge6_Text_WouldYouLikeToTrade, BattleFrontier_Lounge6_EventScript_DeclineTrade, BattleFrontier_Lounge6_EventScript_NotRequestedMon, BattleFrontier_Lounge6_Text_PromiseIllBeGoodToIt
setflag FLAG_BATTLE_FRONTIER_TRADE_DONE
release
end

View File

@@ -68,61 +68,61 @@ BattleFrontier_Lounge7_EventScript_ChooseNewLeftTutorMove::
BattleFrontier_Lounge7_EventScript_Softboiled::
setvar VAR_0x8008, 16
setvar VAR_ITEM_ID, MOVE_SOFT_BOILED
setvar VAR_0x8005, MOVE_SOFT_BOILED
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
BattleFrontier_Lounge7_EventScript_SeismicToss::
setvar VAR_0x8008, 24
setvar VAR_ITEM_ID, MOVE_SEISMIC_TOSS
setvar VAR_0x8005, MOVE_SEISMIC_TOSS
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
BattleFrontier_Lounge7_EventScript_DreamEater::
setvar VAR_0x8008, 24
setvar VAR_ITEM_ID, MOVE_DREAM_EATER
setvar VAR_0x8005, MOVE_DREAM_EATER
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
BattleFrontier_Lounge7_EventScript_MegaPunch::
setvar VAR_0x8008, 24
setvar VAR_ITEM_ID, MOVE_MEGA_PUNCH
setvar VAR_0x8005, MOVE_MEGA_PUNCH
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
BattleFrontier_Lounge7_EventScript_MegaKick::
setvar VAR_0x8008, 48
setvar VAR_ITEM_ID, MOVE_MEGA_KICK
setvar VAR_0x8005, MOVE_MEGA_KICK
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
BattleFrontier_Lounge7_EventScript_BodySlam::
setvar VAR_0x8008, 48
setvar VAR_ITEM_ID, MOVE_BODY_SLAM
setvar VAR_0x8005, MOVE_BODY_SLAM
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
BattleFrontier_Lounge7_EventScript_RockSlide::
setvar VAR_0x8008, 48
setvar VAR_ITEM_ID, MOVE_ROCK_SLIDE
setvar VAR_0x8005, MOVE_ROCK_SLIDE
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
BattleFrontier_Lounge7_EventScript_Counter::
setvar VAR_0x8008, 48
setvar VAR_ITEM_ID, MOVE_COUNTER
setvar VAR_0x8005, MOVE_COUNTER
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
BattleFrontier_Lounge7_EventScript_ThunderWave::
setvar VAR_0x8008, 48
setvar VAR_ITEM_ID, MOVE_THUNDER_WAVE
setvar VAR_0x8005, MOVE_THUNDER_WAVE
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
BattleFrontier_Lounge7_EventScript_SwordsDance::
setvar VAR_0x8008, 48
setvar VAR_ITEM_ID, MOVE_SWORDS_DANCE
setvar VAR_0x8005, MOVE_SWORDS_DANCE
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
@@ -192,61 +192,61 @@ BattleFrontier_Lounge7_EventScript_ChooseNewRightTutorMove::
BattleFrontier_Lounge7_EventScript_DefenseCurl::
setvar VAR_0x8008, 16
setvar VAR_ITEM_ID, MOVE_DEFENSE_CURL
setvar VAR_0x8005, MOVE_DEFENSE_CURL
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
BattleFrontier_Lounge7_EventScript_Snore::
setvar VAR_0x8008, 24
setvar VAR_ITEM_ID, MOVE_SNORE
setvar VAR_0x8005, MOVE_SNORE
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
BattleFrontier_Lounge7_EventScript_MudSlap::
setvar VAR_0x8008, 24
setvar VAR_ITEM_ID, MOVE_MUD_SLAP
setvar VAR_0x8005, MOVE_MUD_SLAP
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
BattleFrontier_Lounge7_EventScript_Swift::
setvar VAR_0x8008, 24
setvar VAR_ITEM_ID, MOVE_SWIFT
setvar VAR_0x8005, MOVE_SWIFT
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
BattleFrontier_Lounge7_EventScript_IcyWind::
setvar VAR_0x8008, 24
setvar VAR_ITEM_ID, MOVE_ICY_WIND
setvar VAR_0x8005, MOVE_ICY_WIND
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
BattleFrontier_Lounge7_EventScript_Endure::
setvar VAR_0x8008, 48
setvar VAR_ITEM_ID, MOVE_ENDURE
setvar VAR_0x8005, MOVE_ENDURE
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
BattleFrontier_Lounge7_EventScript_PsychUp::
setvar VAR_0x8008, 48
setvar VAR_ITEM_ID, MOVE_PSYCH_UP
setvar VAR_0x8005, MOVE_PSYCH_UP
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
BattleFrontier_Lounge7_EventScript_IcePunch::
setvar VAR_0x8008, 48
setvar VAR_ITEM_ID, MOVE_ICE_PUNCH
setvar VAR_0x8005, MOVE_ICE_PUNCH
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
BattleFrontier_Lounge7_EventScript_ThunderPunch::
setvar VAR_0x8008, 48
setvar VAR_ITEM_ID, MOVE_THUNDER_PUNCH
setvar VAR_0x8005, MOVE_THUNDER_PUNCH
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
BattleFrontier_Lounge7_EventScript_FirePunch::
setvar VAR_0x8008, 48
setvar VAR_ITEM_ID, MOVE_FIRE_PUNCH
setvar VAR_0x8005, MOVE_FIRE_PUNCH
goto BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection
end
@@ -277,21 +277,15 @@ BattleFrontier_Lounge7_EventScript_ConfirmMoveSelection::
goto BattleFrontier_Lounge7_EventScript_ChooseNewMove
end
BattleFrontier_Lounge7_EventScript_TeachTutorMove::
msgbox BattleFrontier_Lounge7_Text_TeachMoveToWhichMon, MSGBOX_DEFAULT
fadescreen FADE_TO_BLACK
special CloseBattlePointsWindow
special CloseBattleFrontierTutorWindow
special ChooseBoxMon
chooseboxmon SELECT_PC_MON_MOVE_TUTOR
waitstate
special IsSelectedMonEgg
goto_if_eq VAR_RESULT, TRUE, MoveTutor_EggCantForgetMoves
special CanTeachMoveBoxMon
goto_if_eq VAR_RESULT, 1, MoveTutor_CantLearnMove
goto_if_eq VAR_RESULT, 2, MoveTutor_AlreadyKnowsMove
goto_if_eq VAR_RESULT, 3, MoveTutor_EggCantForgetMoves
waitstate
goto_if_eq VAR_RESULT, 4, BattleFrontier_Lounge7_EventScript_CancelChooseMon
goto_if_eq VAR_RESULT, FALSE, BattleFrontier_Lounge7_EventScript_CancelChooseMon
msgbox BattleFrontier_Lounge7_Text_IllTakeBattlePoints, MSGBOX_DEFAULT
copyvar VAR_0x8004, VAR_0x8008
special TakeFrontierBattlePoints

View File

@@ -23,13 +23,13 @@ FallarborTown_MoveRelearnersHouse_EventScript_AskTeachMove::
FallarborTown_MoveRelearnersHouse_EventScript_ChooseMon::
msgbox FallarborTown_MoveRelearnersHouse_Text_TutorWhichMon, MSGBOX_DEFAULT
setmoverelearnerstate MOVE_RELEARNER_LEVEL_UP_MOVES @ Specifically supposed to teach level up moves
fadescreen FADE_TO_BLACK
special ChooseBoxMon
chooseboxmon SELECT_PC_MON_MOVE_RELEARNER
waitstate
goto_if_eq VAR_0x8004, PARTY_NOTHING_CHOSEN, FallarborTown_MoveRelearnersHouse_EventScript_ComeBackWithHeartScale
special IsSelectedMonEgg
goto_if_eq VAR_RESULT, TRUE, FallarborTown_MoveRelearnersHouse_EventScript_CantTeachEgg
goto_if_eq VAR_0x8005, 0, FallarborTown_MoveRelearnersHouse_EventScript_NoMoveToTeachMon
special HasMovesToRelearn
goto_if_eq VAR_RESULT, FALSE, FallarborTown_MoveRelearnersHouse_EventScript_NoMoveToTeachMon
goto FallarborTown_MoveRelearnersHouse_EventScript_ChooseMove
end

View File

@@ -5,28 +5,7 @@ FortreeCity_House1_EventScript_Trader::
lock
faceplayer
goto_if_set FLAG_FORTREE_NPC_TRADE_COMPLETED, FortreeCity_House1_EventScript_TradeCompleted
setvar VAR_0x8008, INGAME_TRADE_PLUSLE
copyvar VAR_0x8004, VAR_0x8008
specialvar VAR_RESULT, GetInGameTradeSpeciesInfo
copyvar VAR_0x8009, VAR_RESULT
msgbox FortreeCity_House1_Text_YouWillTradeWontYou, MSGBOX_YESNO
goto_if_eq VAR_RESULT, NO, FortreeCity_House1_EventScript_DeclineTrade
fadescreen FADE_TO_BLACK
special ChooseBoxMon
waitstate
copyvar VAR_0x800A, VAR_0x8004
goto_if_eq VAR_0x8004, PARTY_NOTHING_CHOSEN, FortreeCity_House1_EventScript_DeclineTrade
copyvar VAR_0x8005, VAR_0x800A
specialvar VAR_RESULT, GetTradeSpecies
copyvar VAR_0x800B, VAR_RESULT
goto_if_ne VAR_RESULT, VAR_0x8009, FortreeCity_House1_EventScript_NotRequestedMon
copyvar VAR_0x8004, VAR_0x8008
copyvar VAR_0x8005, VAR_0x800A
special CreateInGameTradePokemon
special DoInGameTradeScene
waitstate
bufferspeciesname STR_VAR_1, VAR_0x8009
msgbox FortreeCity_House1_Text_MonYouTakeCare, MSGBOX_DEFAULT
ingame_trade INGAME_TRADE_PLUSLE, FortreeCity_House1_Text_YouWillTradeWontYou, FortreeCity_House1_EventScript_DeclineTrade, FortreeCity_House1_EventScript_NotRequestedMon, FortreeCity_House1_Text_MonYouTakeCare
setflag FLAG_FORTREE_NPC_TRADE_COMPLETED
release
end

View File

@@ -14,8 +14,7 @@ LilycoveCity_MoveDeletersHouse_EventScript_MoveDeleter::
LilycoveCity_MoveDeletersHouse_EventScript_ChooseMonAndMoveToForget::
msgbox LilycoveCity_MoveDeletersHouse_Text_WhichMonShouldForget, MSGBOX_DEFAULT
fadescreen FADE_TO_BLACK
special ChooseBoxMon
chooseboxmon SELECT_PC_MON_MOVE_DELETER
waitstate
goto_if_eq VAR_0x8004, PARTY_NOTHING_CHOSEN, LilycoveCity_MoveDeletersHouse_EventScript_ComeAgain
special IsSelectedMonEgg

View File

@@ -5,28 +5,7 @@ PacifidlogTown_House3_EventScript_Trader::
lock
faceplayer
goto_if_set FLAG_PACIFIDLOG_NPC_TRADE_COMPLETED, PacifidlogTown_House3_EventScript_TradeCompleted
setvar VAR_0x8008, INGAME_TRADE_HORSEA
copyvar VAR_0x8004, VAR_0x8008
specialvar VAR_RESULT, GetInGameTradeSpeciesInfo
copyvar VAR_0x8009, VAR_RESULT
msgbox PacifidlogTown_House3_Text_WillingToTradeIt, MSGBOX_YESNO
goto_if_eq VAR_RESULT, NO, PacifidlogTown_House3_EventScript_DeclineTrade
fadescreen FADE_TO_BLACK
special ChooseBoxMon
waitstate
copyvar VAR_0x800A, VAR_0x8004
goto_if_eq VAR_0x8004, PARTY_NOTHING_CHOSEN, PacifidlogTown_House3_EventScript_DeclineTrade
copyvar VAR_0x8005, VAR_0x800A
specialvar VAR_RESULT, GetTradeSpecies
copyvar VAR_0x800B, VAR_RESULT
goto_if_ne VAR_RESULT, VAR_0x8009, PacifidlogTown_House3_EventScript_NotRequestedMon
copyvar VAR_0x8004, VAR_0x8008
copyvar VAR_0x8005, VAR_0x800A
special CreateInGameTradePokemon
special DoInGameTradeScene
waitstate
bufferspeciesname STR_VAR_1, VAR_0x8009
msgbox PacifidlogTown_House3_Text_ItsSubtlyDifferentThankYou, MSGBOX_DEFAULT
ingame_trade INGAME_TRADE_HORSEA, PacifidlogTown_House3_Text_WillingToTradeIt, PacifidlogTown_House3_EventScript_DeclineTrade, PacifidlogTown_House3_EventScript_NotRequestedMon, PacifidlogTown_House3_Text_ItsSubtlyDifferentThankYou
setflag FLAG_PACIFIDLOG_NPC_TRADE_COMPLETED
release
end

View File

@@ -5,27 +5,7 @@ RustboroCity_House1_EventScript_Trader::
lock
faceplayer
goto_if_set FLAG_RUSTBORO_NPC_TRADE_COMPLETED, RustboroCity_House1_EventScript_TradeCompleted
setvar VAR_0x8008, INGAME_TRADE_SEEDOT
copyvar VAR_0x8004, VAR_0x8008
specialvar VAR_RESULT, GetInGameTradeSpeciesInfo
copyvar VAR_0x8009, VAR_RESULT
msgbox RustboroCity_House1_Text_IllTradeIfYouWant, MSGBOX_YESNO
goto_if_eq VAR_RESULT, NO, RustboroCity_House1_EventScript_DeclineTrade
fadescreen FADE_TO_BLACK
special ChooseBoxMon
waitstate
copyvar VAR_0x800A, VAR_0x8004
goto_if_eq VAR_0x8004, PARTY_NOTHING_CHOSEN, RustboroCity_House1_EventScript_DeclineTrade
copyvar VAR_0x8005, VAR_0x800A
specialvar VAR_RESULT, GetTradeSpecies
copyvar VAR_0x800B, VAR_RESULT
goto_if_ne VAR_RESULT, VAR_0x8009, RustboroCity_House1_EventScript_NotRequestedMon
copyvar VAR_0x8004, VAR_0x8008
copyvar VAR_0x8005, VAR_0x800A
special CreateInGameTradePokemon
special DoInGameTradeScene
waitstate
msgbox RustboroCity_House1_Text_PleaseBeGoodToMyPokemon, MSGBOX_DEFAULT
ingame_trade INGAME_TRADE_SEEDOT, RustboroCity_House1_Text_IllTradeIfYouWant, RustboroCity_House1_EventScript_DeclineTrade, RustboroCity_House1_EventScript_NotRequestedMon, RustboroCity_House1_Text_PleaseBeGoodToMyPokemon
setflag FLAG_RUSTBORO_NPC_TRADE_COMPLETED
release
end

View File

@@ -11,8 +11,7 @@ SlateportCity_NameRatersHouse_EventScript_NameRater::
SlateportCity_NameRatersHouse_EventScript_ChooseMonToRate::
msgbox SlateportCity_NameRatersHouse_Text_CritiqueWhichMonNickname, MSGBOX_DEFAULT
fadescreen FADE_TO_BLACK
special ChooseBoxMon
chooseboxmon
waitstate
goto_if_ne VAR_0x8004, PARTY_NOTHING_CHOSEN, SlateportCity_NameRatersHouse_EventScript_RateMonNickname
goto_if_eq VAR_0x8004, PARTY_NOTHING_CHOSEN, SlateportCity_NameRatersHouse_EventScript_DeclineNameRate
@@ -49,8 +48,7 @@ SlateportCity_NameRatersHouse_EventScript_PlayerNotMonsOT::
SlateportCity_NameRatersHouse_EventScript_ChangeNickname::
msgbox SlateportCity_NameRatersHouse_Text_WhatShallNewNameBe, MSGBOX_DEFAULT
call_if_eq VAR_MON_BOX_ID, 0xFF, Common_EventScript_NameReceivedPartyMon
call_if_ne VAR_MON_BOX_ID, 0xFF, Common_EventScript_NameReceivedBoxMon
call Common_EventScript_NameReceivedPartyMon
specialvar VAR_RESULT, TryPutNameRaterShowOnTheAir
special BufferMonNickname
goto_if_eq VAR_RESULT, TRUE, SlateportCity_NameRatersHouse_EventScript_NewNameDifferent

View File

@@ -6,11 +6,10 @@ SootopolisCity_LotadAndSeedotHouse_EventScript_SeedotBrother::
lock
faceplayer
msgbox SootopolisCity_LotadAndSeedotHouse_Text_PleaseShowMeBigSeedot, MSGBOX_DEFAULT
fadescreen FADE_TO_BLACK
special ChooseBoxMon
setvar VAR_0x8009, SPECIES_SEEDOT
chooseboxmon SELECT_PC_MON_TRADE
waitstate
copyvar VAR_RESULT, VAR_0x8004
goto_if_eq VAR_RESULT, PARTY_NOTHING_CHOSEN, SootopolisCity_LotadAndSeedotHouse_EventScript_CancelShowSeedot
goto_if_eq VAR_0x8004, PARTY_NOTHING_CHOSEN, SootopolisCity_LotadAndSeedotHouse_EventScript_CancelShowSeedot
special CompareSeedotSize
goto_if_eq VAR_RESULT, 1, SootopolisCity_LotadAndSeedotHouse_EventScript_NotSeedot
goto_if_eq VAR_RESULT, 2, SootopolisCity_LotadAndSeedotHouse_EventScript_SmallSeedot
@@ -51,11 +50,10 @@ SootopolisCity_LotadAndSeedotHouse_EventScript_LotadBrother::
lock
faceplayer
msgbox SootopolisCity_LotadAndSeedotHouse_Text_PleaseShowMeBigLotad, MSGBOX_DEFAULT
fadescreen FADE_TO_BLACK
special ChooseBoxMon
setvar VAR_0x8009, SPECIES_LOTAD
chooseboxmon SELECT_PC_MON_TRADE
waitstate
copyvar VAR_RESULT, VAR_0x8004
goto_if_eq VAR_RESULT, PARTY_NOTHING_CHOSEN, SootopolisCity_LotadAndSeedotHouse_EventScript_CancelShowLotad
goto_if_eq VAR_0x8004, PARTY_NOTHING_CHOSEN, SootopolisCity_LotadAndSeedotHouse_EventScript_CancelShowLotad
special CompareLotadSize
goto_if_eq VAR_RESULT, 1, SootopolisCity_LotadAndSeedotHouse_EventScript_NotLotad
goto_if_eq VAR_RESULT, 2, SootopolisCity_LotadAndSeedotHouse_EventScript_SmallLotad

View File

@@ -89,8 +89,7 @@ Route117_PokemonDayCare_EventScript_GiveMonToRaise::
specialvar VAR_RESULT, CountPartyAliveNonEggMons
goto_if_eq VAR_RESULT, 2, Route117_PokemonDayCare_EventScript_OnlyTwoAliveMons
msgbox Route117_PokemonDayCare_Text_WhichMonShouldWeRaise, MSGBOX_DEFAULT
fadescreen FADE_TO_BLACK
special ChooseBoxMon
chooseboxmon SELECT_PC_MON_DAYCARE
waitstate
goto_if_eq VAR_0x8004, PARTY_NOTHING_CHOSEN, Route117_PokemonDayCare_EventScript_ComeAgain
specialvar VAR_RESULT, CountPartyAliveNonEggMons_IgnoreVar0x8004Slot

View File

@@ -71,12 +71,13 @@ MoveRelearner_EventScript_TeachMove::
getpartysize
goto_if_eq VAR_RESULT, 0, MoveRelearner_EventScript_NoPkmn
msgbox MoveRelearner_Text_ChoosePkmn, MSGBOX_DEFAULT
special ChooseMonForMoveRelearner
chooseboxmon SELECT_PC_MON_MOVE_RELEARNER
waitstate
call_if_eq VAR_0x8004, PARTY_NOTHING_CHOSEN, MoveRelearner_EventScript_AnythingElse
special IsSelectedMonEgg
call_if_eq VAR_RESULT, YES, MoveRelearner_EventScript_CantTeachMoveToEgg
call_if_eq VAR_0x8005, NO, MoveRelearner_EventScript_CantTeachMoveToPkmn
call_if_eq VAR_RESULT, TRUE, MoveRelearner_EventScript_CantTeachMoveToEgg
special HasMovesToRelearn
call_if_eq VAR_RESULT, FALSE, MoveRelearner_EventScript_CantTeachMoveToPkmn
msgbox MoveRelearner_Text_WhichXmoveShouldTeach, MSGBOX_DEFAULT
special TeachMoveRelearnerMove
waitstate

View File

@@ -1,18 +1,8 @@
SlateportCity_PokemonFanClub_EventScript_SwaggerTutor::
lock
faceplayer
goto_if_set FLAG_MOVE_TUTOR_TAUGHT_SWAGGER, MoveTutor_EventScript_SwaggerTaught
msgbox MoveTutor_Text_SwaggerTeach, MSGBOX_YESNO
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_SwaggerDeclined
call MoveTutor_EventScript_CanOnlyBeLearnedOnce
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_SwaggerDeclined
msgbox MoveTutor_Text_SwaggerWhichMon, MSGBOX_DEFAULT
setvar VAR_ITEM_ID, MOVE_SWAGGER
buffermovename STR_VAR_1, MOVE_SWAGGER
call MoveTutor_EventScript_OpenBox
goto_if_eq VAR_RESULT, 4, MoveTutor_EventScript_SwaggerDeclined
setflag FLAG_MOVE_TUTOR_TAUGHT_SWAGGER
goto MoveTutor_EventScript_SwaggerTaught
move_tutor MOVE_SWAGGER, MoveTutor_Text_SwaggerTeach, MoveTutor_Text_SwaggerWhichMon, MoveTutor_EventScript_SwaggerDeclined, MoveTutor_EventScript_SwaggerTaught, FLAG_MOVE_TUTOR_TAUGHT_SWAGGER
release
end
MoveTutor_EventScript_SwaggerDeclined::
@@ -28,18 +18,8 @@ MoveTutor_EventScript_SwaggerTaught::
MauvilleCity_EventScript_RolloutTutor::
lock
faceplayer
goto_if_set FLAG_MOVE_TUTOR_TAUGHT_ROLLOUT, MoveTutor_EventScript_RolloutTaught
msgbox MoveTutor_Text_RolloutTeach, MSGBOX_YESNO
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_RolloutDeclined
call MoveTutor_EventScript_CanOnlyBeLearnedOnce
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_RolloutDeclined
msgbox MoveTutor_Text_RolloutWhichMon, MSGBOX_DEFAULT
setvar VAR_ITEM_ID, MOVE_ROLLOUT
buffermovename STR_VAR_1, MOVE_ROLLOUT
call MoveTutor_EventScript_OpenBox
goto_if_eq VAR_RESULT, 4, MoveTutor_EventScript_RolloutDeclined
setflag FLAG_MOVE_TUTOR_TAUGHT_ROLLOUT
goto MoveTutor_EventScript_RolloutTaught
move_tutor MOVE_ROLLOUT, MoveTutor_Text_RolloutTeach, MoveTutor_Text_RolloutWhichMon, MoveTutor_EventScript_RolloutDeclined, MoveTutor_EventScript_RolloutTaught, FLAG_MOVE_TUTOR_TAUGHT_ROLLOUT
release
end
MoveTutor_EventScript_RolloutDeclined::
@@ -55,18 +35,7 @@ MoveTutor_EventScript_RolloutTaught::
VerdanturfTown_PokemonCenter_1F_EventScript_FuryCutterTutor::
lock
faceplayer
goto_if_set FLAG_MOVE_TUTOR_TAUGHT_FURY_CUTTER, MoveTutor_EventScript_FuryCutterTaught
msgbox MoveTutor_Text_FuryCutterTeach, MSGBOX_YESNO
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_FuryCutterDeclined
call MoveTutor_EventScript_CanOnlyBeLearnedOnce
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_FuryCutterDeclined
msgbox MoveTutor_Text_FuryCutterWhichMon, MSGBOX_DEFAULT
setvar VAR_ITEM_ID, MOVE_FURY_CUTTER
buffermovename STR_VAR_1, MOVE_FURY_CUTTER
call MoveTutor_EventScript_OpenBox
goto_if_eq VAR_RESULT, 4, MoveTutor_EventScript_FuryCutterDeclined
setflag FLAG_MOVE_TUTOR_TAUGHT_FURY_CUTTER
goto MoveTutor_EventScript_FuryCutterTaught
move_tutor MOVE_FURY_CUTTER, MoveTutor_Text_FuryCutterTeach, MoveTutor_Text_FuryCutterWhichMon, MoveTutor_EventScript_FuryCutterDeclined, MoveTutor_EventScript_FuryCutterTaught, FLAG_MOVE_TUTOR_TAUGHT_FURY_CUTTER
end
MoveTutor_EventScript_FuryCutterDeclined::
@@ -82,18 +51,7 @@ MoveTutor_EventScript_FuryCutterTaught::
LavaridgeTown_House_EventScript_MimicTutor::
lock
faceplayer
goto_if_set FLAG_MOVE_TUTOR_TAUGHT_MIMIC, MoveTutor_EventScript_MimicTaught
msgbox MoveTutor_MimicTeach, MSGBOX_YESNO
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_MimicDeclined
call MoveTutor_EventScript_CanOnlyBeLearnedOnce
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_MimicDeclined
msgbox MoveTutor_Text_MimicWhichMon, MSGBOX_DEFAULT
setvar VAR_ITEM_ID, MOVE_MIMIC
buffermovename STR_VAR_1, MOVE_MIMIC
call MoveTutor_EventScript_OpenBox
goto_if_eq VAR_RESULT, 4, MoveTutor_EventScript_MimicDeclined
setflag FLAG_MOVE_TUTOR_TAUGHT_MIMIC
goto MoveTutor_EventScript_MimicTaught
move_tutor MOVE_MIMIC, MoveTutor_MimicTeach, MoveTutor_Text_MimicWhichMon, MoveTutor_EventScript_MimicDeclined, MoveTutor_EventScript_MimicTaught, FLAG_MOVE_TUTOR_TAUGHT_MIMIC
end
MoveTutor_EventScript_MimicDeclined::
@@ -109,18 +67,7 @@ MoveTutor_EventScript_MimicTaught::
FallarborTown_Mart_EventScript_MetronomeTutor::
lock
faceplayer
goto_if_set FLAG_MOVE_TUTOR_TAUGHT_METRONOME, MoveTutor_EventScript_MetronomeTaught
msgbox MoveTutor_Text_MetronomeTeach, MSGBOX_YESNO
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_MetronomeDeclined
call MoveTutor_EventScript_CanOnlyBeLearnedOnce
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_MetronomeDeclined
msgbox MoveTutor_Text_MetronomeWhichMon, MSGBOX_DEFAULT
setvar VAR_ITEM_ID, MOVE_METRONOME
buffermovename STR_VAR_1, MOVE_METRONOME
call MoveTutor_EventScript_OpenBox
goto_if_eq VAR_RESULT, 4, MoveTutor_EventScript_MetronomeDeclined
setflag FLAG_MOVE_TUTOR_TAUGHT_METRONOME
goto MoveTutor_EventScript_MetronomeTaught
move_tutor MOVE_METRONOME, MoveTutor_Text_MetronomeTeach, MoveTutor_Text_MetronomeWhichMon, MoveTutor_EventScript_MetronomeDeclined, MoveTutor_EventScript_MetronomeTaught, FLAG_MOVE_TUTOR_TAUGHT_METRONOME
end
MoveTutor_EventScript_MetronomeDeclined::
@@ -136,18 +83,7 @@ MoveTutor_EventScript_MetronomeTaught::
FortreeCity_House2_EventScript_SleepTalkTutor::
lock
faceplayer
goto_if_set FLAG_MOVE_TUTOR_TAUGHT_SLEEP_TALK, MoveTutor_EventScript_SleepTalkTaught
msgbox MoveTutor_Text_SleepTalkTeach, MSGBOX_YESNO
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_SleepTalkDeclined
call MoveTutor_EventScript_CanOnlyBeLearnedOnce
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_SleepTalkDeclined
msgbox MoveTutor_Text_SleepTalkWhichMon, MSGBOX_DEFAULT
setvar VAR_ITEM_ID, MOVE_SLEEP_TALK
buffermovename STR_VAR_1, MOVE_SLEEP_TALK
call MoveTutor_EventScript_OpenBox
goto_if_eq VAR_RESULT, 4, MoveTutor_EventScript_SleepTalkDeclined
setflag FLAG_MOVE_TUTOR_TAUGHT_SLEEP_TALK
goto MoveTutor_EventScript_SleepTalkTaught
move_tutor MOVE_SLEEP_TALK, MoveTutor_Text_SleepTalkTeach, MoveTutor_Text_SleepTalkWhichMon, MoveTutor_EventScript_SleepTalkDeclined, MoveTutor_EventScript_SleepTalkTaught, FLAG_MOVE_TUTOR_TAUGHT_SLEEP_TALK
end
MoveTutor_EventScript_SleepTalkDeclined::
@@ -163,18 +99,7 @@ MoveTutor_EventScript_SleepTalkTaught::
LilycoveCity_DepartmentStoreRooftop_EventScript_SubstituteTutor::
lock
faceplayer
goto_if_set FLAG_MOVE_TUTOR_TAUGHT_SUBSTITUTE, MoveTutor_EventScript_SubstituteTaught
msgbox MoveTutor_Text_SubstituteTeach, MSGBOX_YESNO
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_SubstituteDeclined
call MoveTutor_EventScript_CanOnlyBeLearnedOnce
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_SubstituteDeclined
msgbox MoveTutor_Text_SubstituteWhichMon, MSGBOX_DEFAULT
setvar VAR_ITEM_ID, MOVE_SUBSTITUTE
buffermovename STR_VAR_1, MOVE_SUBSTITUTE
call MoveTutor_EventScript_OpenBox
goto_if_eq VAR_RESULT, 4, MoveTutor_EventScript_SubstituteDeclined
setflag FLAG_MOVE_TUTOR_TAUGHT_SUBSTITUTE
goto MoveTutor_EventScript_SubstituteTaught
move_tutor MOVE_SUBSTITUTE, MoveTutor_Text_SubstituteTeach, MoveTutor_Text_SubstituteWhichMon, MoveTutor_EventScript_SubstituteDeclined, MoveTutor_EventScript_SubstituteTaught, FLAG_MOVE_TUTOR_TAUGHT_SUBSTITUTE
end
MoveTutor_EventScript_SubstituteDeclined::
@@ -190,18 +115,7 @@ MoveTutor_EventScript_SubstituteTaught::
MossdeepCity_EventScript_DynamicPunchTutor::
lock
faceplayer
goto_if_set FLAG_MOVE_TUTOR_TAUGHT_DYNAMICPUNCH, MoveTutor_EventScript_DynamicPunchTaught
msgbox MoveTutor_Text_DynamicPunchTeach, MSGBOX_YESNO
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_DynamicPunchDeclined
call MoveTutor_EventScript_CanOnlyBeLearnedOnce
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_DynamicPunchDeclined
msgbox MoveTutor_Text_DynamicPunchWhichMon, MSGBOX_DEFAULT
setvar VAR_ITEM_ID, MOVE_DYNAMIC_PUNCH
buffermovename STR_VAR_1, MOVE_DYNAMIC_PUNCH
call MoveTutor_EventScript_OpenBox
goto_if_eq VAR_RESULT, 4, MoveTutor_EventScript_DynamicPunchDeclined
setflag FLAG_MOVE_TUTOR_TAUGHT_DYNAMICPUNCH
goto MoveTutor_EventScript_DynamicPunchTaught
move_tutor MOVE_DYNAMIC_PUNCH, MoveTutor_Text_DynamicPunchTeach, MoveTutor_Text_DynamicPunchWhichMon, MoveTutor_EventScript_DynamicPunchDeclined, MoveTutor_EventScript_DynamicPunchTaught, FLAG_MOVE_TUTOR_TAUGHT_DYNAMICPUNCH
end
MoveTutor_EventScript_DynamicPunchDeclined::
@@ -217,18 +131,7 @@ MoveTutor_EventScript_DynamicPunchTaught::
SootopolisCity_PokemonCenter_1F_EventScript_DoubleEdgeTutor::
lock
faceplayer
goto_if_set FLAG_MOVE_TUTOR_TAUGHT_DOUBLE_EDGE, MoveTutor_EventScript_DoubleEdgeTaught
msgbox MoveTutor_Text_DoubleEdgeTeach, MSGBOX_YESNO
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_DoubleEdgeDeclined
call MoveTutor_EventScript_CanOnlyBeLearnedOnce
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_DoubleEdgeDeclined
msgbox MoveTutor_Text_DoubleEdgeWhichMon, MSGBOX_DEFAULT
setvar VAR_ITEM_ID, MOVE_DOUBLE_EDGE
buffermovename STR_VAR_1, MOVE_DOUBLE_EDGE
call MoveTutor_EventScript_OpenBox
goto_if_eq VAR_RESULT, 4, MoveTutor_EventScript_DoubleEdgeDeclined
setflag FLAG_MOVE_TUTOR_TAUGHT_DOUBLE_EDGE
goto MoveTutor_EventScript_DoubleEdgeTaught
move_tutor MOVE_DOUBLE_EDGE, MoveTutor_Text_DoubleEdgeTeach, MoveTutor_Text_DoubleEdgeWhichMon, MoveTutor_EventScript_DoubleEdgeDeclined, MoveTutor_EventScript_DoubleEdgeTaught, FLAG_MOVE_TUTOR_TAUGHT_DOUBLE_EDGE
end
MoveTutor_EventScript_DoubleEdgeDeclined::
@@ -244,18 +147,7 @@ MoveTutor_EventScript_DoubleEdgeTaught::
PacifidlogTown_PokemonCenter_1F_EventScript_ExplosionTutor::
lock
faceplayer
goto_if_set FLAG_MOVE_TUTOR_TAUGHT_EXPLOSION, MoveTutor_EventScript_ExplosionTaught
msgbox MoveTutor_Text_ExplosionTeach, MSGBOX_YESNO
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_ExplosionDeclined
call MoveTutor_EventScript_CanOnlyBeLearnedOnce
goto_if_eq VAR_RESULT, NO, MoveTutor_EventScript_ExplosionDeclined
msgbox MoveTutor_Text_ExplosionWhichMon, MSGBOX_DEFAULT
setvar VAR_ITEM_ID, MOVE_EXPLOSION
buffermovename STR_VAR_1, MOVE_EXPLOSION
call MoveTutor_EventScript_OpenBox
goto_if_eq VAR_RESULT, 4, MoveTutor_EventScript_ExplosionDeclined
setflag FLAG_MOVE_TUTOR_TAUGHT_EXPLOSION
goto MoveTutor_EventScript_ExplosionTaught
move_tutor MOVE_EXPLOSION, MoveTutor_Text_ExplosionTeach, MoveTutor_Text_ExplosionWhichMon, MoveTutor_EventScript_ExplosionDeclined, MoveTutor_EventScript_ExplosionTaught, FLAG_MOVE_TUTOR_TAUGHT_EXPLOSION
end
MoveTutor_EventScript_ExplosionDeclined::
@@ -276,66 +168,18 @@ MoveTutor_EventScript_OpenPartyMenu::
return
MoveTutor_EventScript_OpenBox::
fadescreen FADE_TO_BLACK
special ChooseBoxMon
waitstate
special IsSelectedMonEgg
goto_if_eq VAR_RESULT, TRUE, MoveTutor_EggCantForgetMoves
special CanTeachMoveBoxMon
goto_if_eq VAR_RESULT, 1, MoveTutor_CantLearnMove
goto_if_eq VAR_RESULT, 2, MoveTutor_AlreadyKnowsMove
goto_if_eq VAR_RESULT, 3, MoveTutor_EggCantForgetMoves
waitstate
return
MoveTutor_ForgetMove::
special MoveDeleterChooseMoveToForget
fadescreen FADE_FROM_BLACK
msgbox LilycoveCity_MoveDeletersHouse_Text_MonsMoveShouldBeForgotten, MSGBOX_YESNO
switch VAR_RESULT
case YES, LilycoveCity_MoveDeletersHouse_EventScript_TryForgetMove
case NO, LilycoveCity_MoveDeletersHouse_EventScript_ComeAgain
goto_if_eq VAR_0x8005, MAX_MON_MOVES, LilycoveCity_MoveDeletersHouse_EventScript_ChooseMonAndMoveToForget
special BufferMoveDeleterNicknameAndMove
msgbox LilycoveCity_MoveDeletersHouse_Text_MonsMoveShouldBeForgotten, MSGBOX_YESNO
switch VAR_RESULT
case YES, LilycoveCity_MoveDeletersHouse_EventScript_TryForgetMove
case NO, LilycoveCity_MoveDeletersHouse_EventScript_ComeAgain
MoveTutor_MoveDeletersHouse_EventScript_TryForgetMove::
special MoveDeleterForgetMove
playfanfare MUS_MOVE_DELETED
waitfanfare
msgbox LilycoveCity_MoveDeletersHouse_Text_MonHasForgottenMove, MSGBOX_DEFAULT
chooseboxmon SELECT_PC_MON_MOVE_TUTOR
waitstate
lock
faceplayer
return
MoveTutor_EggCantForgetMoves::
msgbox LilycoveCity_MoveDeletersHouse_Text_EggCantForgetMoves, MSGBOX_DEFAULT
releaseall
end
MoveTutor_CantLearnMove::
msgbox MoveTutor_Text_CantLearnMove, MSGBOX_DEFAULT
releaseall
end
MoveTutor_AlreadyKnowsMove::
msgbox MoveTutor_Text_AlreadyKnowsMove, MSGBOX_DEFAULT
releaseall
end
MoveTutor_Text_CantLearnMove:
.string "But that Pokemon can't learn\n"
.string "{STR_VAR_1}.$"
MoveTutor_Text_AlreadyKnowsMove:
.string "But that Pokemon already knows\n"
.string "{STR_VAR_1}.$"
MoveTutor_EventScript_CanOnlyBeLearnedOnce::
msgbox MoveTutor_Text_ThisMoveCanOnlyBeLearnedOnce, MSGBOX_YESNO
return
MoveTutor_AfterChooseBoxMon::
waitstate
special CanTeachMoveBoxMon
waitstate
return

View File

@@ -7,7 +7,8 @@ Common_EventScript_GetGiftMonPartySlot::
Common_EventScript_NameReceivedBoxMon::
fadescreen FADE_TO_BLACK
special ChangeBoxPokemonNickname
setvar VAR_0x8004, PC_MON_CHOSEN
special ChangePokemonNickname
waitstate
lock
faceplayer

View File

@@ -346,6 +346,7 @@ gSpecials::
def_special GetContestMultiplayerId
def_special ScriptGetPartyMonSpecies
def_special IsSelectedMonEgg
def_special HasMovesToRelearn
def_special TryInitBattleTowerAwardManObjectEvent
def_special MoveOutOfSecretBaseFromOutside
def_special LoadPlayerBag
@@ -500,7 +501,6 @@ gSpecials::
def_special StartMirageTowerDisintegration
def_special StartMirageTowerShake
def_special StartMirageTowerFossilFallAndSink
def_special ChangeBoxPokemonNickname
def_special GetPCBoxToSendMon
def_special ShouldShowBoxWasFullMessage
def_special SetMatchCallRegisteredFlag
@@ -565,7 +565,6 @@ gSpecials::
def_special GetCodeFeedback
def_special SetHiddenNature
def_special SetAbility
def_special ChooseBoxMon
def_special CanTeachMoveBoxMon
def_special ObjectEventInteractionGetApricornTreeData
def_special ObjectEventInteractionPickApricornTree

19
include/chooseboxmon.h Normal file
View File

@@ -0,0 +1,19 @@
#ifndef GUARD_CHOOSEBOXMON_H
#define GUARD_CHOOSEBOXMON_H
struct MoveLearnUI {
void (*askConfirmation)(void);
s32 (*waitConfirmation)(void);
void (*printMessage)(const u8 *message);
void (*playFanfare)(u32 songId);
void (*showMoveList)(u8 taskId);
void (*endTask)(u8 taskId);
};
u32 IsBoxMonExcluded(struct BoxPokemon *boxmon);
bool32 CanBoxMonBeSelected(struct BoxPokemon *boxmon);
s32 LearnMove(const struct MoveLearnUI *ui, u8 taskId);
s32 GetLearnMoveStartState(void);
s32 GetLearnMoveResumeAfterSummaryScreenState(void);
#endif // GUARD_CHOOSEBOXMON_H

View File

@@ -12,6 +12,7 @@
#define OW_WHITEOUT_CUTSCENE GEN_LATEST // In Gen4+, whiting out shows an additional message and post whiteout event script cutscene with a healing NPC. (While this change was also in FRLG, for the sake of simplicity, setting this to GEN_3 will result in RSE behavior.)
#define OW_DEFOG_FIELD_MOVE FALSE // If enabled, Defog can be used as a Field Move as seen in DPPt.
#define OW_ROCK_CLIMB_FIELD_MOVE FALSE // If enabled, Rock Climb can be used as a Field Move as seen in DPPt.
#define OW_CHOOSE_FROM_PC_AND_PARTY TRUE // If enabled, NPCs like move tutors or trainers asking for trade will let you pick a pokemon from your PC or party instead of just your party
// Item Obtain Description Box
#define OW_ITEM_DESCRIPTIONS_OFF 0 // never show descriptions

View File

@@ -1,6 +1,7 @@
#ifndef GUARD_CONSTANTS_PARTY_MENU_H
#define GUARD_CONSTANTS_PARTY_MENU_H
#define PC_MON_CHOSEN 0xFE
#define PARTY_NOTHING_CHOSEN 0xFF
#define AILMENT_NONE 0
@@ -109,4 +110,22 @@
#define SELECTWINDOW_CATALOG 4
#define SELECTWINDOW_ZYGARDECUBE 5
enum PcMonSelectionType
{
SELECT_PC_MON_NORMAL,
SELECT_PC_MON_TRADE, // Also used for Lotad / Seedot size check
SELECT_PC_MON_DAYCARE,
SELECT_PC_MON_MOVE_TUTOR,
SELECT_PC_MON_MOVE_DELETER,
SELECT_PC_MON_MOVE_RELEARNER,
};
enum CanMoveBeLearned
{
CAN_LEARN_MOVE,
CANNOT_LEARN_MOVE,
ALREADY_KNOWS_MOVE,
CANNOT_LEARN_MOVE_IS_EGG
};
#endif // GUARD_CONSTANTS_PARTY_MENU_H

View File

@@ -686,5 +686,5 @@ extern const u8 EventScript_LostSignal[];
extern const u8 EventScript_TooDark[];
extern const u8 EventScript_MovedTooFast[];
extern const u8 MoveTutor_AfterChooseBoxMon[];
#endif // GUARD_EVENT_SCRIPTS_H

View File

@@ -29,6 +29,7 @@ u16 MailSpeciesToSpecies(u16 mailSpecies, u16 *buffer);
u8 GiveMailToMon(struct Pokemon *mon, struct Mail *mail);
void TakeMailFromMon(struct Pokemon *mon);
void ClearMailItemId(u8 mailId);
u8 SaveMailToPC(struct Mail *mail);
u8 TakeMailFromMonAndSave(struct Pokemon *mon);
bool8 ItemIsMail(enum Item itemId);

View File

@@ -7,6 +7,8 @@ void TeachMoveRelearnerMove(void);
void MoveRelearnerShowHideHearts(s32 move);
void MoveRelearnerShowHideCategoryIcon(s32);
void CB2_InitLearnMove(void);
bool32 CanBoxMonRelearnAnyMove(struct BoxPokemon *boxMon);
bool32 CanBoxMonRelearnMoves(struct BoxPokemon *boxMon, enum MoveRelearnerStates state);
extern enum MoveRelearnerStates gMoveRelearnerState;
extern enum RelearnMode gRelearnMode;

View File

@@ -733,6 +733,7 @@ u16 GiveMoveToMon(struct Pokemon *mon, enum Move move);
u16 GiveMoveToBoxMon(struct BoxPokemon *boxMon, enum Move move);
u16 GiveMoveToBattleMon(struct BattlePokemon *mon, enum Move move);
void SetMonMoveSlot(struct Pokemon *mon, enum Move move, u8 slot);
void SetBoxMonMoveSlot(struct BoxPokemon *mon, enum Move move, u8 slot);
void SetBattleMonMoveSlot(struct BattlePokemon *mon, enum Move move, u8 slot);
void GiveMonInitialMoveset(struct Pokemon *mon);
void GiveBoxMonInitialMoveset(struct BoxPokemon *boxMon);
@@ -804,6 +805,7 @@ const u16 *GetSpeciesFormTable(u16 species);
const struct FormChange *GetSpeciesFormChanges(u16 species);
u8 CalculatePPWithBonus(enum Move move, u8 ppBonuses, u8 moveIndex);
void RemoveMonPPBonus(struct Pokemon *mon, u8 moveIndex);
void RemoveBoxMonPPBonus(struct BoxPokemon *mon, u8 moveIndex);
void RemoveBattleMonPPBonus(struct BattlePokemon *mon, u8 moveIndex);
void PokemonToBattleMon(struct Pokemon *src, struct BattlePokemon *dst);
void CopyPartyMonToBattleData(u32 battler, u32 partyIndex);
@@ -836,24 +838,7 @@ void MonGainEVs(struct Pokemon *mon, u16 defeatedSpecies);
u16 GetMonEVCount(struct Pokemon *mon);
bool8 TryIncrementMonLevel(struct Pokemon *mon);
u8 CanLearnTeachableMove(u16 species, enum Move move);
u32 GetRelearnerLevelUpMoves(struct Pokemon *mon, u16 *moves);
u32 GetRelearnerLevelUpMovesBox(struct BoxPokemon *boxMon, u16 *moves);
u32 GetRelearnerEggMoves(struct Pokemon *mon, u16 *moves);
u32 GetRelearnerEggMovesBox(struct BoxPokemon *boxMon, u16 *moves);
u32 GetRelearnerTMMoves(struct Pokemon *mon, u16 *moves);
u32 GetRelearnerTMMovesBox(struct BoxPokemon *boxMon, u16 *moves);
u32 GetRelearnerTutorMoves(struct Pokemon *mon, u16 *moves);
u32 GetRelearnerTutorMovesBox(struct BoxPokemon *boxMon, u16 *moves);
bool32 HasRelearnerLevelUpMoves(struct Pokemon *mon);
bool32 HasRelearnerLevelUpMovesBox(struct BoxPokemon *boxMon);
bool32 HasRelearnerEggMoves(struct Pokemon *mon);
bool32 HasRelearnerEggMovesBox(struct BoxPokemon *boxMon);
bool32 HasRelearnerTMMoves(struct Pokemon *mon);
bool32 HasRelearnerTMMovesBox(struct BoxPokemon *boxMon);
bool32 HasRelearnerTutorMoves(struct Pokemon *mon);
bool32 HasRelearnerTutorMovesBox(struct BoxPokemon *boxMon);
u8 GetLevelUpMovesBySpecies(u16 species, u16 *moves);
u8 GetNumberOfRelearnableMoves(struct Pokemon *mon);
u16 SpeciesToPokedexNum(u16 species);
bool32 IsSpeciesInHoennDex(u16 species);
u16 GetBattleBGM(void);
@@ -925,6 +910,8 @@ struct Pokemon *GetSavedPlayerPartyMon(u32 index);
u8 *GetSavedPlayerPartyCount(void);
void SavePlayerPartyMon(u32 index, struct Pokemon *mon);
bool32 IsSpeciesOfType(u32 species, enum Type type);
struct BoxPokemon *GetSelectedBoxMonFromPcOrParty(void);
u32 GiveScriptedMonToPlayer(struct Pokemon *mon, u8 slot);
void ChangePokemonNicknameWithCallback(void (*callback)(void));
#endif // GUARD_POKEMON_H

View File

@@ -43,9 +43,6 @@ u32 GetBoxMonDataAt(u8 boxId, u8 boxPosition, s32 request);
void SetBoxMonDataAt(u8 boxId, u8 boxPosition, s32 request, const void *value);
u32 GetCurrentBoxMonData(u8 boxPosition, s32 request);
void SetCurrentBoxMonData(u8 boxPosition, s32 request, const void *value);
void GetBoxMonNickAt(u8 boxId, u8 boxPosition, u8 *dst);
u32 GetBoxMonLevelAt(u8 boxId, u8 boxPosition);
void SetBoxMonNickAt(u8 boxId, u8 boxPosition, const u8 *nick);
u32 GetAndCopyBoxMonDataAt(u8 boxId, u8 boxPosition, s32 request, void *dst);
void SetBoxMonAt(u8 boxId, u8 boxPosition, struct BoxPokemon *src);
void CopyBoxMonAt(u8 boxId, u8 boxPosition, struct BoxPokemon *dst);
@@ -73,8 +70,8 @@ u8 *GetWaldaPhrasePtr(void);
void SetWaldaPhrase(const u8 *src);
bool32 IsWaldaPhraseEmpty(void);
void EnterPokeStorage(u8 boxOption);
void ChooseMonFromStorage();
u32 CountPartyNonEggMons(void);
void ChooseBoxMon(void);
void RemoveSelectedPcMon(struct Pokemon *mon);
#endif // GUARD_POKEMON_STORAGE_SYSTEM_H

View File

@@ -32,9 +32,6 @@ enum PokemonSummaryScreenMode
SUMMARY_MODE_SELECT_MOVE,
SUMMARY_MODE_RELEARNER_BATTLE, // returning from move relearner initiated from battle moves page
SUMMARY_MODE_RELEARNER_CONTEST, // returning from move relearner initiated from contest moves page
SUMMARY_MODE_BOX_SELECT_MOVE,
SUMMARY_MODE_BOX_RELEARNER_BATTLE,
SUMMARY_MODE_BOX_RELEARNER_CONTEST,
};
enum PokemonSummaryScreenPage
@@ -54,8 +51,7 @@ enum PokemonSummarySkillsMode
};
void ShowPokemonSummaryScreen(u8 mode, void *mons, u8 monIndex, u8 maxMonIndex, void (*callback)(void));
void ShowSelectMovePokemonSummaryScreen(struct Pokemon *mons, u8 monIndex, u8 maxMonIndex, void (*callback)(void), u16 newMove);
void ShowSelectMoveBoxPokemonSummaryScreen(struct BoxPokemon *mons, u8 monIndex, u8 maxMonIndex, void (*callback)(void), u16 newMove);
void ShowSelectMovePokemonSummaryScreen(struct Pokemon *mons, u8 monIndex, void (*callback)(void), u16 newMove);
u8 GetMoveSlotToReplace(void);
void SummaryScreen_SetAnimDelayTaskId(u8 taskId);
bool32 CheckRelearnerStateFlag(enum MoveRelearnerStates state);

View File

@@ -4,6 +4,8 @@
#include "link_rfu.h"
#include "constants/trade.h"
#define TRADEMON_FROM_PC 1
extern struct Mail gTradeMail[PARTY_SIZE];
extern u8 gSelectedTradeMonPositions[2];

View File

@@ -5874,7 +5874,7 @@ static void Cmd_yesnoboxlearnmove(void)
if (!gPaletteFade.active)
{
FreeAllWindowBuffers();
ShowSelectMovePokemonSummaryScreen(gPlayerParty, gBattleStruct->expGetterMonId, gPlayerPartyCount - 1, ReshowBattleScreenAfterMenu, gMoveToLearn);
ShowSelectMovePokemonSummaryScreen(gPlayerParty, gBattleStruct->expGetterMonId, ReshowBattleScreenAfterMenu, gMoveToLearn);
gBattleScripting.learnMoveState++;
}
break;

313
src/chooseboxmon.c Normal file
View File

@@ -0,0 +1,313 @@
#include "global.h"
#include "chooseboxmon.h"
#include "daycare.h"
#include "event_data.h"
#include "event_scripts.h"
#include "field_weather.h"
#include "menu.h"
#include "move.h"
#include "move_relearner.h"
#include "overworld.h"
#include "palette.h"
#include "party_menu.h"
#include "pokemon.h"
#include "pokemon_summary_screen.h"
#include "pokemon_storage_system.h"
#include "script.h"
#include "string_util.h"
#include "strings.h"
#include "constants/party_menu.h"
#include "constants/songs.h"
#define VALID_MON 0
#define INVALID_MON 1
struct PcMonSelection
{
void (*partyMonBackup)(void);
u32 (*isMonInvalid)(struct BoxPokemon *);
const u8* postSelectionScript;
u32 isStrict:1;
u32 padding:31;
};
static EWRAM_DATA u8 sSelectionType = 0;
// All these filter functions return 0 when a mon is a valid or a number corresponding to the type of error
static u32 NoFilter(struct BoxPokemon *boxmon);
static u32 IsNotEgg(struct BoxPokemon *boxmon);
static u32 IsMatchingSpecies(struct BoxPokemon *boxmon);
static u32 CanMonDeleteMove(struct BoxPokemon *boxmon);
static u32 CanMonLearnMove(struct BoxPokemon *boxmon);
static u32 CanRelearnMoves(struct BoxPokemon *boxmon);
static const struct PcMonSelection sPcMonSelectionTypes[] =
{
[SELECT_PC_MON_NORMAL] = {ChoosePartyMon, NoFilter, NULL, FALSE},
[SELECT_PC_MON_TRADE] = {ChoosePartyMon, IsMatchingSpecies, NULL, FALSE},
[SELECT_PC_MON_DAYCARE] = {ChooseSendDaycareMon, IsNotEgg, NULL, TRUE},
[SELECT_PC_MON_MOVE_TUTOR] = {ChooseMonForMoveTutor, CanMonLearnMove, MoveTutor_AfterChooseBoxMon, FALSE},
[SELECT_PC_MON_MOVE_DELETER] = {ChoosePartyMon, CanMonDeleteMove, NULL, FALSE},
[SELECT_PC_MON_MOVE_RELEARNER] = {ChooseMonForMoveRelearner, CanRelearnMoves, NULL, FALSE}
};
static u32 NoFilter(struct BoxPokemon *boxmon)
{
return VALID_MON;
}
static u32 IsNotEgg(struct BoxPokemon *boxmon)
{
if (GetBoxMonData(boxmon, MON_DATA_IS_EGG))
return INVALID_MON;
return VALID_MON;
}
static u32 CanRelearnMoves(struct BoxPokemon *boxmon)
{
if (GetBoxMonData(boxmon, MON_DATA_IS_EGG))
return INVALID_MON;
if (CanBoxMonRelearnMoves(boxmon, gMoveRelearnerState))
return VALID_MON;
return INVALID_MON;
}
static u32 IsMatchingSpecies(struct BoxPokemon *boxmon)
{
if (GetBoxMonData(boxmon, MON_DATA_SPECIES_OR_EGG) == gSpecialVar_0x8009)
return VALID_MON;
return INVALID_MON;
}
static u32 CanMonDeleteMove(struct BoxPokemon *boxmon)
{
if (GetBoxMonData(boxmon, MON_DATA_IS_EGG))
return INVALID_MON;
if (GetBoxMonData(boxmon, MON_DATA_MOVE2) == MOVE_NONE) // Only has One move
return INVALID_MON;
return VALID_MON;
}
static u32 CanMonLearnMove(struct BoxPokemon *boxmon)
{
if (GetBoxMonData(boxmon, MON_DATA_IS_EGG))
return CANNOT_LEARN_MOVE_IS_EGG;
if (BoxMonKnowsMove(boxmon, gSpecialVar_0x8005))
return ALREADY_KNOWS_MOVE;
if (CanLearnTeachableMove(GetBoxMonData(boxmon, MON_DATA_SPECIES), gSpecialVar_0x8005))
return VALID_MON;
return CANNOT_LEARN_MOVE;
}
u32 IsBoxMonExcluded(struct BoxPokemon *boxmon)
{
return sPcMonSelectionTypes[sSelectionType].isMonInvalid(boxmon);
}
bool32 CanBoxMonBeSelected(struct BoxPokemon *boxmon)
{
if (!sPcMonSelectionTypes[sSelectionType].isStrict)
return TRUE;
return !IsBoxMonExcluded(boxmon);
}
static void Task_ChooseBoxMon(u8 taskId)
{
if (!gPaletteFade.active)
{
CleanupOverworldWindowsAndTilemaps();
ChooseMonFromStorage();
DestroyTask(taskId);
}
}
// Used as a script special for showing a box mon to various npcs (e.g. in-game trades, move deleter)
void ChooseBoxMon(struct ScriptContext *ctx)
{
sSelectionType = ScriptReadByte(ctx);
if (!OW_CHOOSE_FROM_PC_AND_PARTY)
{
sPcMonSelectionTypes[sSelectionType].partyMonBackup();
return;
}
LockPlayerFieldControls();
FadeScreen(FADE_TO_BLACK, 0);
CreateTask(Task_ChooseBoxMon, 10);
if (sPcMonSelectionTypes[sSelectionType].postSelectionScript)
{
ctx->scriptPtr++;
ScriptCall(ctx, sPcMonSelectionTypes[sSelectionType].postSelectionScript);
}
}
enum LearnMoveState
{
LEARN_MOVE_END,
MON_CAN_LEARN, //Start
LEARN_MOVE,
ASK_REPLACEMENT_1,
ASK_REPLACEMENT_2,
ASK_REPLACEMENT_3,
REFUSE_REPLACE_1,
REFUSE_REPLACE_2,
REFUSE_REPLACE_3,
WANT_REPLACE_1,
WANT_REPLACE_2,
WANT_REPLACE_3, //Return from Summary screen
LEARNED_MOVE_1,
LEARNED_MOVE_2,
FORGOT_MOVE_1,
REPLACE_MOVE_1,
DID_NOT_LEARN_1,
};
static struct BoxPokemon *LearnMove_GetBoxMonFromTaskData(u8 partyIndex)
{
struct BoxPokemon *boxmon;
if (partyIndex == PC_MON_CHOSEN)
boxmon = GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos);
else
boxmon = &(gPlayerParty[partyIndex].box);
return boxmon;
}
#define state gTasks[taskId].data[0]
#define partyIndex gTasks[taskId].data[1]
#define move gTasks[taskId].data[2]
// MoveLearnUI does not contain a waitMessage function and LearnMove assumes the calling task will wait when a printer is active
// Remember to update Task_LearnMove is you wish to change to an explicit waitMessage system
s32 LearnMove(const struct MoveLearnUI *ui, u8 taskId)
{
struct BoxPokemon *boxmon = LearnMove_GetBoxMonFromTaskData(partyIndex);
switch (state)
{
case MON_CAN_LEARN:
GetBoxMonNickname(boxmon, gStringVar1);
StringCopy(gStringVar2, GetMoveName(move));
gSpecialVar_Result = FALSE;
switch(CanMonLearnMove(boxmon))
{
case VALID_MON:
return LEARN_MOVE;
case ALREADY_KNOWS_MOVE:
ui->printMessage(gText_PkmnAlreadyKnows);
return LEARN_MOVE_END;
case CANNOT_LEARN_MOVE_IS_EGG:
case CANNOT_LEARN_MOVE:
default:
ui->printMessage(gText_PkmnCantLearnMove);
return LEARN_MOVE_END;
}
case LEARN_MOVE:
if (GiveMoveToBoxMon(boxmon, move) != MON_HAS_MAX_MOVES)
return LEARNED_MOVE_1;
else
return ASK_REPLACEMENT_1;
case ASK_REPLACEMENT_1:
GetBoxMonNickname(boxmon, gStringVar1);
StringCopy(gStringVar2, GetMoveName(move));
ui->printMessage(gText_PkmnNeedsToReplaceMove);
return ASK_REPLACEMENT_2;
case ASK_REPLACEMENT_2:
ui->askConfirmation();
return ASK_REPLACEMENT_3;
case ASK_REPLACEMENT_3:
switch (ui->waitConfirmation())
{
case 0: // Yes
return WANT_REPLACE_1;
case 1: // No
case MENU_B_PRESSED:
return REFUSE_REPLACE_1;
}
return state;
case REFUSE_REPLACE_1:
StringCopy(gStringVar2, GetMoveName(move));
ui->printMessage(gText_StopLearningMove2);
return REFUSE_REPLACE_2;
case REFUSE_REPLACE_2:
ui->askConfirmation();
return REFUSE_REPLACE_3;
case REFUSE_REPLACE_3:
switch (ui->waitConfirmation())
{
case 0: // Yes
return DID_NOT_LEARN_1;
case 1: // No
case MENU_B_PRESSED:
return WANT_REPLACE_1;
}
return state;
case WANT_REPLACE_1:
ui->printMessage(gText_WhichMoveToForget);
return WANT_REPLACE_2;
case WANT_REPLACE_2:
ui->showMoveList(taskId);
return WANT_REPLACE_3;
case WANT_REPLACE_3:
if (GetMoveSlotToReplace() == MAX_MON_MOVES)
return REFUSE_REPLACE_1;
else
return FORGOT_MOVE_1;
case LEARNED_MOVE_1:
GetBoxMonNickname(boxmon, gStringVar1);
StringCopy(gStringVar2, GetMoveName(move));
ui->printMessage(gText_PkmnLearnedMove4);
return LEARNED_MOVE_2;
case LEARNED_MOVE_2:
gSpecialVar_Result = TRUE;
ui->playFanfare(MUS_LEVEL_UP);
return LEARN_MOVE_END;
case FORGOT_MOVE_1:
GetBoxMonNickname(boxmon, gStringVar1);
StringCopy(gStringVar2, GetMoveName(GetBoxMonData(boxmon, MON_DATA_MOVE1 + GetMoveSlotToReplace())));
ui->printMessage(gText_12PoofForgotMove);
return REPLACE_MOVE_1;
case REPLACE_MOVE_1:
u32 slot = GetMoveSlotToReplace();
RemoveBoxMonPPBonus(boxmon, slot);
u32 pp = GetMovePP(move);
SetBoxMonData(boxmon, MON_DATA_MOVE1 + slot, &move);
SetBoxMonData(boxmon, MON_DATA_PP1 + slot, &pp);
GetBoxMonNickname(boxmon, gStringVar1);
StringCopy(gStringVar2, GetMoveName(move));
gSpecialVar_Result = TRUE;
ui->printMessage(gText_PkmnLearnedMove4);
return LEARN_MOVE_END;
case DID_NOT_LEARN_1:
GetBoxMonNickname(boxmon, gStringVar1);
StringCopy(gStringVar2, GetMoveName(move));
gSpecialVar_Result = FALSE;
ui->printMessage(gText_MoveNotLearned);
return LEARN_MOVE_END;
default:
errorf("Unknown LearnMove state %d\nEnding move learning ...", state);
case LEARN_MOVE_END:
ui->endTask(taskId);
return LEARN_MOVE_END;
}
}
s32 GetLearnMoveStartState(void)
{
return MON_CAN_LEARN;
}
//At the time of writing code for this, there was no prescribed way to make a task persist between scenes
//and I didn't want to implement one just for this, feel free to rewrite this if this has changed
s32 GetLearnMoveResumeAfterSummaryScreenState(void)
{
return WANT_REPLACE_3;
}
#undef state
#undef partyIndex
#undef move

View File

@@ -22,9 +22,11 @@
#include "overworld.h"
#include "item.h"
#include "regions.h"
#include "malloc.h"
#include "constants/form_change_types.h"
#include "constants/items.h"
#include "constants/moves.h"
#include "constants/party_menu.h"
#include "constants/region_map_sections.h"
#define IS_DITTO(species) (gSpeciesInfo[species].eggGroups[0] == EGG_GROUP_DITTO || gSpeciesInfo[species].eggGroups[1] == EGG_GROUP_DITTO)
@@ -276,17 +278,6 @@ void StorePokemonInDaycare(struct Pokemon *mon, struct DaycareMon *daycareMon)
TransferEggMoves();
}
static void StoreBoxMonInDaycare(struct BoxPokemon *mon, struct DaycareMon *daycareMon)
{
daycareMon->mon = *mon;
daycareMon->steps = 0;
ZeroBoxMonData(mon);
if (P_EGG_MOVE_TRANSFER >= GEN_8)
TransferEggMoves();
}
static void StorePokemonInEmptyDaycareSlot(struct Pokemon *mon, struct DayCare *daycare)
{
s8 slotId = Daycare_FindEmptySpot(daycare);
@@ -295,19 +286,19 @@ static void StorePokemonInEmptyDaycareSlot(struct Pokemon *mon, struct DayCare *
void StoreSelectedPokemonInDaycare(void)
{
if (gSpecialVar_MonBoxId == 0xFF)
struct Pokemon *mon;
if (gSpecialVar_0x8004 == PC_MON_CHOSEN)
{
StorePokemonInEmptyDaycareSlot(&gPlayerParty[GetCursorSelectionMonId()], &gSaveBlock1Ptr->daycare);
}
else if (gSpecialVar_MonBoxId == TOTAL_BOXES_COUNT) // Selected party mon from PC
{
StorePokemonInEmptyDaycareSlot(&gPlayerParty[gSpecialVar_MonBoxPos], &gSaveBlock1Ptr->daycare);
mon = Alloc(sizeof(struct Pokemon));
RemoveSelectedPcMon(mon);
}
else
{
s8 slotId = Daycare_FindEmptySpot(&gSaveBlock1Ptr->daycare);
StoreBoxMonInDaycare(GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos), &gSaveBlock1Ptr->daycare.mons[slotId]);
mon = &gPlayerParty[gSpecialVar_0x8004];
}
StorePokemonInEmptyDaycareSlot(mon, &gSaveBlock1Ptr->daycare);
if (gSpecialVar_0x8004 == PC_MON_CHOSEN)
Free(mon);
}
// Shifts the second daycare Pokémon slot into the first slot.
@@ -1265,21 +1256,9 @@ static void _GetDaycareMonNicknames(struct DayCare *daycare)
u16 GetSelectedMonNicknameAndSpecies(void)
{
if(gSpecialVar_MonBoxId == 0xFF)
{
GetBoxMonNickname(&gPlayerParty[GetCursorSelectionMonId()].box, gStringVar1);
return GetBoxMonData(&gPlayerParty[GetCursorSelectionMonId()].box, MON_DATA_SPECIES);
}
else if (gSpecialVar_MonBoxId == TOTAL_BOXES_COUNT) // Selected party mon from PC
{
GetBoxMonNickname(&gPlayerParty[gSpecialVar_MonBoxPos].box, gStringVar1);
return GetBoxMonData(&gPlayerParty[gSpecialVar_MonBoxPos].box, MON_DATA_SPECIES);
}
else
{
GetBoxMonNickname(&gPokemonStoragePtr->boxes[gSpecialVar_MonBoxId][gSpecialVar_MonBoxPos], gStringVar1);
return GetBoxMonData(&gPokemonStoragePtr->boxes[gSpecialVar_MonBoxId][gSpecialVar_MonBoxPos], MON_DATA_SPECIES);
}
struct BoxPokemon *boxmon = GetSelectedBoxMonFromPcOrParty();
GetBoxMonNickname(boxmon, gStringVar1);
return GetBoxMonData(boxmon, MON_DATA_SPECIES);
}
void GetDaycareMonNicknames(void)

View File

@@ -31,9 +31,10 @@
#include "trade.h"
#include "util.h"
#include "constants/battle_string_ids.h"
#include "constants/songs.h"
#include "constants/rgb.h"
#include "constants/items.h"
#include "constants/party_menu.h"
#include "constants/rgb.h"
#include "constants/songs.h"
struct EvoInfo
{
@@ -379,7 +380,11 @@ static void CB2_EvolutionSceneLoadGraphics(void)
static void CB2_TradeEvolutionSceneLoadGraphics(void)
{
struct Pokemon *mon = &gPlayerParty[gTasks[sEvoStructPtr->evoTaskId].tPartyId];
struct Pokemon *mon;
if (gTasks[sEvoStructPtr->evoTaskId].tPartyId == PC_MON_CHOSEN)
mon = &gEnemyParty[TRADEMON_FROM_PC];
else
mon = &gPlayerParty[gTasks[sEvoStructPtr->evoTaskId].tPartyId];
u16 postEvoSpecies = gTasks[sEvoStructPtr->evoTaskId].tPostEvoSpecies;
switch (gMain.state)
@@ -974,7 +979,7 @@ static void Task_EvolutionScene(u8 taskId)
{
FreeAllWindowBuffers();
ShowSelectMovePokemonSummaryScreen(gPlayerParty, gTasks[taskId].tPartyId,
gPlayerPartyCount - 1, CB2_EvolutionSceneLoadGraphics,
CB2_EvolutionSceneLoadGraphics,
gMoveToLearn);
gTasks[taskId].tLearnMoveState++;
}
@@ -1098,7 +1103,11 @@ enum {
static void Task_TradeEvolutionScene(u8 taskId)
{
u32 var = 0;
struct Pokemon *mon = &gPlayerParty[gTasks[taskId].tPartyId];
struct Pokemon *mon;
if (gTasks[taskId].tPartyId == PC_MON_CHOSEN)
mon = &gEnemyParty[TRADEMON_FROM_PC];
else
mon = &gPlayerParty[gTasks[taskId].tPartyId];
switch (gTasks[taskId].tState)
{
@@ -1357,9 +1366,24 @@ static void Task_TradeEvolutionScene(u8 taskId)
Free(GetBgTilemapBuffer(0));
FreeAllWindowBuffers();
ShowSelectMovePokemonSummaryScreen(gPlayerParty, gTasks[taskId].tPartyId,
gPlayerPartyCount - 1, CB2_TradeEvolutionSceneLoadGraphics,
gMoveToLearn);
if (gTasks[taskId].tPartyId == PC_MON_CHOSEN)
{
ShowSelectMovePokemonSummaryScreen(
gEnemyParty,
TRADEMON_FROM_PC,
CB2_TradeEvolutionSceneLoadGraphics,
gMoveToLearn
);
}
else
{
ShowSelectMovePokemonSummaryScreen(
gPlayerParty,
gTasks[taskId].tPartyId,
CB2_TradeEvolutionSceneLoadGraphics,
gMoveToLearn
);
}
gTasks[taskId].tLearnMoveState++;
}
break;

View File

@@ -76,6 +76,7 @@
#include "palette.h"
#include "battle_util.h"
#include "naming_screen.h"
#include "chooseboxmon.h"
#define TAG_ITEM_ICON 5500
@@ -86,14 +87,6 @@
#define ELEVATOR_WINDOW_HEIGHT 3
#define ELEVATOR_LIGHT_STAGES 3
enum
{
CAN_LEARN_MOVE,
CANNOT_LEARN_MOVE,
ALREADY_KNOWS_MOVE,
CANNOT_LEARN_MOVE_IS_EGG
};
EWRAM_DATA bool8 gBikeCyclingChallenge = FALSE;
EWRAM_DATA u8 gBikeCollisions = 0;
static EWRAM_DATA u32 sBikeCyclingTimer = 0;
@@ -156,18 +149,8 @@ static void Task_CloseBattlePikeCurtain(u8);
static u8 DidPlayerGetFirstFans(void);
static void SetInitialFansOfPlayer(void);
static u16 PlayerGainRandomTrainerFan(void);
static void Task_LearnedMoveBoxMon(u8);
static void Task_ReplaceBoxMonMoveYesNo(u8);
static void Task_DoLearnedBoxMonMoveFanfareAfterText(u8);
static void Task_HandleReplaceBoxMonMoveYesNoInput(u8);
static void Task_ShowSummaryScreenToForgetBoxMonMove(u8);
static void StopLearningBoxMonMovePrompt(u8);
static void CB2_ReturnToFieldWhileLearningMove(void);
static void Task_ReturnToFieldWhileLearningMove(void);
static void Task_BoxMonReplaceMove(u8);
static void Task_StopLearningBoxMonMoveYesNo(u8);
static void Task_HandleStopLearningBoxMonMoveYesNoInput(u8);
static void Task_DidntLearnMove(u8);
#if FREE_LINK_BATTLE_RECORDS == FALSE
static void BufferFanClubTrainerName_(struct LinkBattleRecords *, u8, u8);
#else
@@ -1610,10 +1593,13 @@ u8 GetLeadMonIndex(void)
u16 ScriptGetPartyMonSpecies(void)
{
if(gSpecialVar_MonBoxId == 0xFF)
return GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_SPECIES_OR_EGG);
else
return GetBoxMonDataAt(gSpecialVar_MonBoxId,gSpecialVar_MonBoxPos, MON_DATA_SPECIES_OR_EGG);
return GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_SPECIES_OR_EGG, NULL);
}
u16 ScriptGetSelectedMonSpecies(void)
{
struct BoxPokemon *boxmon = GetSelectedBoxMonFromPcOrParty();
return GetBoxMonData(boxmon, MON_DATA_SPECIES_OR_EGG);
}
// Removed for Emerald
@@ -1641,10 +1627,11 @@ u16 SetPacifidlogTMReceivedDay(void)
bool8 MonOTNameNotPlayer(void)
{
if (GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_LANGUAGE) != GAME_LANGUAGE)
struct BoxPokemon *boxmon = GetSelectedBoxMonFromPcOrParty();
if (GetBoxMonData(boxmon, MON_DATA_LANGUAGE) != GAME_LANGUAGE)
return TRUE;
GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_OT_NAME, gStringVar1);
GetBoxMonData(boxmon, MON_DATA_OT_NAME, gStringVar1);
if (!StringCompare(gSaveBlock2Ptr->playerName, gStringVar1))
return FALSE;
@@ -2038,26 +2025,14 @@ static void Task_MoveElevatorWindowLights(u8 taskId)
void BufferVarsForIVRater(void)
{
u8 i;
u32 i;
u32 ivStorage[NUM_STATS];
if(gSpecialVar_MonBoxId == 0xFF)
struct BoxPokemon *boxmon = GetSelectedBoxMonFromPcOrParty();;
for (i = 0; i < NUM_STATS; i++)
{
ivStorage[STAT_HP] = GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_HP_IV);
ivStorage[STAT_ATK] = GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_ATK_IV);
ivStorage[STAT_DEF] = GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_DEF_IV);
ivStorage[STAT_SPEED] = GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_SPEED_IV);
ivStorage[STAT_SPATK] = GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_SPATK_IV);
ivStorage[STAT_SPDEF] = GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_SPDEF_IV);
}
else
{
ivStorage[STAT_HP] = GetBoxMonDataAt(gSpecialVar_MonBoxId,gSpecialVar_MonBoxPos, MON_DATA_HP_IV);
ivStorage[STAT_ATK] = GetBoxMonDataAt(gSpecialVar_MonBoxId,gSpecialVar_MonBoxPos, MON_DATA_ATK_IV);
ivStorage[STAT_DEF] = GetBoxMonDataAt(gSpecialVar_MonBoxId,gSpecialVar_MonBoxPos, MON_DATA_DEF_IV);
ivStorage[STAT_SPEED] = GetBoxMonDataAt(gSpecialVar_MonBoxId,gSpecialVar_MonBoxPos, MON_DATA_SPEED_IV);
ivStorage[STAT_SPATK] = GetBoxMonDataAt(gSpecialVar_MonBoxId,gSpecialVar_MonBoxPos, MON_DATA_SPATK_IV);
ivStorage[STAT_SPDEF] = GetBoxMonDataAt(gSpecialVar_MonBoxId,gSpecialVar_MonBoxPos, MON_DATA_SPDEF_IV);
ivStorage[i] = GetBoxMonData(boxmon, MON_DATA_HP_IV + i);
}
gSpecialVar_0x8005 = 0;
@@ -2863,16 +2838,13 @@ void SetBattleTowerLinkPlayerGfx(void)
void ShowNatureGirlMessage(void)
{
u8 nature;
u32 nature;
u32 personality;
if (gSpecialVar_0x8004 >= PARTY_SIZE)
gSpecialVar_0x8004 = 0;
struct BoxPokemon *boxmon = GetSelectedBoxMonFromPcOrParty();
if(gSpecialVar_MonBoxId == 0xFF)
nature = GetNature(&gPlayerParty[gSpecialVar_0x8004]);
else
nature = GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_PERSONALITY) % NUM_NATURES;
personality = GetBoxMonData(boxmon, MON_DATA_PERSONALITY);
nature = GetNatureFromPersonality(personality);
ShowFieldMessage(gNaturesInfo[nature].natureGirlMessage);
}
@@ -3125,7 +3097,7 @@ static void HideFrontierExchangeCornerItemIcon(enum ScrollMulti menu, u16 unused
void BufferBattleFrontierTutorMoveName(void)
{
StringCopy(gStringVar1, GetMoveName(gSpecialVar_ItemId));
StringCopy(gStringVar1, GetMoveName(gSpecialVar_0x8005));
}
static void ShowBattleFrontierTutorWindow(enum ScrollMulti menu, u16 selection)
@@ -4402,244 +4374,92 @@ void UseBlankMessageToCancelPokemonPic(void)
ScriptMenu_HidePokemonPic();
}
static void UIAskConfirmation(void)
{
DisplayYesNoMenuDefaultYes();
}
static s32 UIWaitConfirmation(void)
{
return Menu_ProcessInputNoWrapClearOnChoose();
}
static void UIPrintMessage(const u8 *message)
{
ShowFieldMessage(message);
}
static void UIPlayFanfare(u32 songId)
{
PlayFanfare(songId);
}
static void UIEndTask(u8 taskId)
{
DestroyTask(taskId);
ScriptContext_Enable();
}
#define tState data[0]
#define tPartyIndex data[1]
#define tMove data[2]
static void UIShowMoveList(u8 taskId)
{
gSpecialVar_0x8008 = gTasks[taskId].tPartyIndex;
gSpecialVar_0x8009 = gTasks[taskId].tMove;
DestroyTask(taskId);
ShowSelectMovePokemonSummaryScreen(gPlayerParty, gTasks[taskId].tPartyIndex, CB2_ReturnToFieldWhileLearningMove, gTasks[taskId].tMove);
}
static const struct MoveLearnUI sMoveLearnUI =
{
.askConfirmation = UIAskConfirmation,
.waitConfirmation = UIWaitConfirmation,
.printMessage = UIPrintMessage,
.playFanfare = UIPlayFanfare,
.showMoveList = UIShowMoveList,
.endTask = UIEndTask
};
static void Task_LearnMove(u8 taskId)
{
if (IsTextPrinterActiveOnWindow(0))
return;
gTasks[taskId].tState = LearnMove(&sMoveLearnUI, taskId);
}
void CanTeachMoveBoxMon(void)
{
ScriptContext_Stop();
if(gSpecialVar_MonBoxId == 0xFF)
if (gSpecialVar_0x8004 == PARTY_NOTHING_CHOSEN)
{
if (GetMonData(&gPlayerParty[gSpecialVar_MonBoxPos], MON_DATA_IS_EGG))
{
gSpecialVar_Result = CANNOT_LEARN_MOVE_IS_EGG;
ScriptContext_Enable();
}
else if (MonKnowsMove(&gPlayerParty[gSpecialVar_MonBoxPos], gSpecialVar_ItemId) == TRUE)
{
gSpecialVar_Result = ALREADY_KNOWS_MOVE;
ScriptContext_Enable();
}
else if (CanLearnTeachableMove(GetMonData(&gPlayerParty[gSpecialVar_MonBoxPos], MON_DATA_SPECIES_OR_EGG), gSpecialVar_ItemId) == FALSE)
{
gSpecialVar_Result = CANNOT_LEARN_MOVE;
ScriptContext_Enable();
}
else
{
if (GiveMoveToMon(&gPlayerParty[gSpecialVar_MonBoxPos], gSpecialVar_ItemId) != MON_HAS_MAX_MOVES)
{
CreateTask(Task_LearnedMoveBoxMon, 1);
}
else
{
GetMonNickname(&gPlayerParty[gSpecialVar_MonBoxPos], gStringVar1);
StringCopy(gStringVar2, GetMoveName(gSpecialVar_ItemId));
ShowFieldMessage(gText_PkmnNeedsToReplaceMove);
CreateTask(Task_ReplaceBoxMonMoveYesNo, 1);
}
}
}
else
{
if (GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_IS_EGG))
{
gSpecialVar_Result = CANNOT_LEARN_MOVE_IS_EGG;
ScriptContext_Enable();
}
else if (BoxMonKnowsMove(GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos), gSpecialVar_ItemId) == TRUE)
{
gSpecialVar_Result = ALREADY_KNOWS_MOVE;
ScriptContext_Enable();
}
else if (CanLearnTeachableMove(GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_SPECIES_OR_EGG), gSpecialVar_ItemId) == FALSE)
{
gSpecialVar_Result = CANNOT_LEARN_MOVE;
ScriptContext_Enable();
}
else
{
if (GiveMoveToBoxMon(GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos), gSpecialVar_ItemId) != MON_HAS_MAX_MOVES)
CreateTask(Task_LearnedMoveBoxMon, 1);
else
{
GetBoxMonNickname(GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos), gStringVar1);
StringCopy(gStringVar2, GetMoveName(gSpecialVar_ItemId));
ShowFieldMessage(gText_PkmnNeedsToReplaceMove);
CreateTask(Task_ReplaceBoxMonMoveYesNo, 1);
}
}
}
}
static void Task_LearnedMoveBoxMon(u8 taskId)
{
s16 move = gSpecialVar_ItemId;
if(gSpecialVar_MonBoxId == 0xFF)
GetMonNickname(&gPlayerParty[gSpecialVar_MonBoxPos], gStringVar1);
else
GetBoxMonNickname(GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos), gStringVar1);
StringCopy(gStringVar2, GetMoveName(move));
ShowFieldMessage(gText_PkmnLearnedMove4);
gTasks[taskId].func = Task_DoLearnedBoxMonMoveFanfareAfterText;
}
static void Task_DoLearnedBoxMonMoveFanfareAfterText(u8 taskId)
{
if (IsTextPrinterActiveOnWindow(0) != TRUE)
{
PlayFanfare(MUS_LEVEL_UP);
gSpecialVar_Result = CAN_LEARN_MOVE;
DestroyTask(taskId);
ScriptContext_Enable();
}
}
static void Task_ReplaceBoxMonMoveYesNo(u8 taskId)
{
if (IsTextPrinterActiveOnWindow(0) != TRUE)
{
DisplayYesNoMenuDefaultYes();
gTasks[taskId].func = Task_HandleReplaceBoxMonMoveYesNoInput;
}
}
static void Task_HandleReplaceBoxMonMoveYesNoInput(u8 taskId)
{
switch (Menu_ProcessInputNoWrapClearOnChoose())
{
case 0:
ShowFieldMessage(gText_WhichMoveToForget);
gTasks[taskId].func = Task_ShowSummaryScreenToForgetBoxMonMove;
break;
case MENU_B_PRESSED:
PlaySE(SE_SELECT);
// fallthrough
case 1:
StopLearningBoxMonMovePrompt(taskId);
break;
}
}
static void Task_ShowSummaryScreenToForgetBoxMonMove(u8 taskId)
{
if (IsTextPrinterActiveOnWindow(0) != TRUE)
{
DestroyTask(taskId);
if(gSpecialVar_MonBoxId == 0xFF)
ShowSelectMovePokemonSummaryScreen(gPlayerParty, gSpecialVar_MonBoxPos, gPlayerPartyCount - 1, CB2_ReturnToFieldWhileLearningMove, gSpecialVar_ItemId);
else
ShowSelectMoveBoxPokemonSummaryScreen(GetBoxedMonPtr(StorageGetCurrentBox(), 0), gSpecialVar_MonBoxPos, IN_BOX_COUNT - 1, CB2_ReturnToFieldWhileLearningMove, gSpecialVar_ItemId);
// We want to wait one frame before using ScriptContext_Enable() or the game freezes
CreateTask(UIEndTask, 1);
return;
}
u32 taskId = CreateTask(Task_LearnMove, 1);
gTasks[taskId].tState = GetLearnMoveStartState();
gTasks[taskId].tPartyIndex = gSpecialVar_0x8004;
gTasks[taskId].tMove = gSpecialVar_0x8005;
}
static void CB2_ReturnToFieldWhileLearningMove(void)
{
if (!gPaletteFade.active)
{
gFieldCallback = Task_ReturnToFieldWhileLearningMove;
SetMainCallback2(CB2_ReturnToField);
}
gFieldCallback = Task_ReturnToFieldWhileLearningMove;
CB2_ReturnToField();
}
static void Task_ReturnToFieldWhileLearningMove(void)
{
if (GetMoveSlotToReplace() < MAX_MON_MOVES)
{
if(gSpecialVar_MonBoxId == 0xFF)
{
GetMonNickname(&gPlayerParty[gSpecialVar_MonBoxPos], gStringVar1);
StringCopy(gStringVar2, GetMoveName(GetMonData(&gPlayerParty[gSpecialVar_MonBoxPos], MON_DATA_MOVE1 + GetMoveSlotToReplace())));
}
else
{
GetBoxMonNickAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, gStringVar1);
StringCopy(gStringVar2, GetMoveName(GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_MOVE1 + GetMoveSlotToReplace())));
}
ShowFieldMessage(gText_12PoofForgotMove);
CreateTask(Task_BoxMonReplaceMove,1);
}
else
CreateTask(StopLearningBoxMonMovePrompt,1);
u32 taskId = CreateTask(Task_LearnMove, 1);
gTasks[taskId].tState = GetLearnMoveResumeAfterSummaryScreenState();
gTasks[taskId].tPartyIndex = gSpecialVar_0x8008;
gTasks[taskId].tMove = gSpecialVar_0x8009;
}
static void Task_BoxMonReplaceMove(u8 taskId)
{
if (IsTextPrinterActiveOnWindow(0) != TRUE)
{
enum Move move = gSpecialVar_ItemId;
if(gSpecialVar_MonBoxId == 0xFF)
{
RemoveMonPPBonus(&gPlayerParty[gSpecialVar_MonBoxPos], GetMoveSlotToReplace());
SetMonMoveSlot(&gPlayerParty[gSpecialVar_MonBoxPos], move, GetMoveSlotToReplace());
}
else
{
struct BoxPokemon *mon = GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos);
u8 ppBonuses = GetBoxMonData(mon, MON_DATA_PP_BONUSES);
ppBonuses &= gPPUpClearMask[GetMoveSlotToReplace()];
SetBoxMonData(mon, MON_DATA_PP_BONUSES, &ppBonuses);
SetBoxMonData(mon, MON_DATA_MOVE1 + GetMoveSlotToReplace(), &move);
SetBoxMonData(mon, MON_DATA_PP1 + GetMoveSlotToReplace(), &gMovesInfo[move].pp);
}
Task_LearnedMoveBoxMon(taskId);
}
}
static void StopLearningBoxMonMovePrompt(u8 taskId)
{
StringCopy(gStringVar2, GetMoveName(gSpecialVar_ItemId));
ShowFieldMessage(gText_StopLearningMove2);
gTasks[taskId].func = Task_StopLearningBoxMonMoveYesNo;
}
static void Task_StopLearningBoxMonMoveYesNo(u8 taskId)
{
if (IsTextPrinterActiveOnWindow(0) != TRUE)
{
DisplayYesNoMenuDefaultYes();
gTasks[taskId].func = Task_HandleStopLearningBoxMonMoveYesNoInput;
}
}
static void Task_HandleStopLearningBoxMonMoveYesNoInput(u8 taskId)
{
switch (Menu_ProcessInputNoWrapClearOnChoose())
{
case 0:
if(gSpecialVar_MonBoxId == 0xFF)
GetMonNickname(&gPlayerParty[gSpecialVar_MonBoxPos], gStringVar1);
else
GetBoxMonNickAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, gStringVar1);
ShowFieldMessage(gText_MoveNotLearned);
gSpecialVar_Result = 4;
gTasks[taskId].func = Task_DidntLearnMove;
break;
case MENU_B_PRESSED:
PlaySE(SE_SELECT);
// fallthrough
case 1:
if(gSpecialVar_MonBoxId == 0xFF)
GetMonNickname(&gPlayerParty[gSpecialVar_MonBoxPos], gStringVar1);
else
GetBoxMonNickAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, gStringVar1);
ShowFieldMessage(gText_PkmnNeedsToReplaceMove);
gTasks[taskId].func = Task_ReplaceBoxMonMoveYesNo;
break;
}
}
static void Task_DidntLearnMove(u8 taskId)
{
if (IsTextPrinterActiveOnWindow(0) != TRUE)
{
DestroyTask(taskId);
ScriptContext_Enable();
}
}
#undef tState
#undef tPartyIndex
#undef tMove
void EnterCode(void)
{

View File

@@ -156,32 +156,38 @@ void ClearMailItemId(u8 mailId)
gSaveBlock1Ptr->mail[mailId].itemId = ITEM_NONE;
}
u8 TakeMailFromMonAndSave(struct Pokemon *mon)
u8 SaveMailToPC(struct Mail *mail)
{
u8 i;
u8 newHeldItem[2];
u8 newMailId;
newHeldItem[0] = ITEM_NONE;
newHeldItem[1] = ITEM_NONE << 8;
newMailId = MAIL_NONE;
for (i = PARTY_SIZE; i < MAIL_COUNT; i++)
for (u32 i = PARTY_SIZE; i < MAIL_COUNT; i++)
{
if (gSaveBlock1Ptr->mail[i].itemId == ITEM_NONE)
{
memcpy(&gSaveBlock1Ptr->mail[i], &gSaveBlock1Ptr->mail[GetMonData(mon, MON_DATA_MAIL)], sizeof(struct Mail));
gSaveBlock1Ptr->mail[GetMonData(mon, MON_DATA_MAIL)].itemId = ITEM_NONE;
SetMonData(mon, MON_DATA_MAIL, &newMailId);
SetMonData(mon, MON_DATA_HELD_ITEM, newHeldItem);
memcpy(&gSaveBlock1Ptr->mail[i], mail, sizeof(struct Mail));
return i;
}
}
// No space to save mail
return MAIL_NONE;
}
u8 TakeMailFromMonAndSave(struct Pokemon *mon)
{
u32 heldItem;
u32 mailId, newMailId;
mailId = GetMonData(mon, MON_DATA_MAIL);
newMailId = SaveMailToPC(&gSaveBlock1Ptr->mail[mailId]);
if (newMailId != MAIL_NONE)
{
gSaveBlock1Ptr->mail[mailId].itemId = ITEM_NONE;
mailId = MAIL_NONE;
SetMonData(mon, MON_DATA_MAIL, &mailId);
heldItem = ITEM_NONE;
SetMonData(mon, MON_DATA_HELD_ITEM, &heldItem);
}
return newMailId;
}
bool8 ItemIsMail(enum Item itemId)
{
switch (itemId)

View File

@@ -27,8 +27,11 @@
#include "string_util.h"
#include "strings.h"
#include "task.h"
#include "constants/party_menu.h"
#include "constants/rgb.h"
#include "constants/songs.h"
#include "data/pokemon/egg_moves.h"
#include "data/tutor_moves.h"
/*
* Move relearner state machine
@@ -163,6 +166,11 @@ enum {
#define GFXTAG_UI 5525
#define PALTAG_UI 5526
struct RelearnType
{
bool32 (*hasMoveToRelearn)(struct BoxPokemon*);
};
static EWRAM_DATA struct
{
u8 state;
@@ -365,6 +373,22 @@ static s32 GetCurrentSelectedMove(void);
static void FreeMoveRelearnerResources(void);
static void RemoveScrollArrows(void);
static void HideHeartSpritesAndShowTeachMoveText(bool8);
static bool32 HasRelearnerLevelUpMoves(struct BoxPokemon *boxMon);
static bool32 HasRelearnerEggMoves(struct BoxPokemon *boxMon);
static bool32 HasRelearnerTMMoves(struct BoxPokemon *boxMon);
static bool32 HasRelearnerTutorMoves(struct BoxPokemon *boxMon);
static u32 GetRelearnerLevelUpMoves(struct BoxPokemon *mon, u16 *moves);
static u32 GetRelearnerEggMoves(struct BoxPokemon *mon, u16 *moves);
static u32 GetRelearnerTMMoves(struct BoxPokemon *mon, u16 *moves);
static u32 GetRelearnerTutorMoves(struct BoxPokemon *mon, u16 *moves);
static const struct RelearnType sRelearnTypes[MOVE_RELEARNER_COUNT] =
{
[MOVE_RELEARNER_LEVEL_UP_MOVES] = {HasRelearnerLevelUpMoves},
[MOVE_RELEARNER_EGG_MOVES] = {HasRelearnerEggMoves},
[MOVE_RELEARNER_TM_MOVES] = {HasRelearnerTMMoves},
[MOVE_RELEARNER_TUTOR_MOVES] = {HasRelearnerTutorMoves},
};
static void VBlankCB_MoveRelearner(void)
{
@@ -567,30 +591,20 @@ static void DoMoveRelearnerMain(void)
if (selection == 0)
{
if(gSpecialVar_MonBoxId == 0xFF){
if (GiveMoveToMon(&gPlayerParty[sMoveRelearnerStruct->partyMon], GetCurrentSelectedMove()) != MON_HAS_MAX_MOVES)
{
PrintMessageWithPlaceholders(gText_MoveRelearnerPkmnLearnedMove);
gSpecialVar_0x8004 = TRUE;
sMoveRelearnerStruct->state = MENU_STATE_PRINT_TEXT_THEN_FANFARE;
}
else
{
sMoveRelearnerStruct->state = MENU_STATE_PRINT_TRYING_TO_LEARN_PROMPT;
}
struct BoxPokemon *boxmon;
if (sMoveRelearnerStruct->partyMon == PC_MON_CHOSEN)
boxmon = GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos);
else
boxmon = &(gPlayerParty[sMoveRelearnerStruct->partyMon].box);
if (GiveMoveToBoxMon(boxmon, GetCurrentSelectedMove()) != MON_HAS_MAX_MOVES)
{
PrintMessageWithPlaceholders(gText_MoveRelearnerPkmnLearnedMove);
gSpecialVar_0x8004 = TRUE;
sMoveRelearnerStruct->state = MENU_STATE_PRINT_TEXT_THEN_FANFARE;
}
else
{
if (GiveMoveToBoxMon(GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos), GetCurrentSelectedMove()) != MON_HAS_MAX_MOVES)
{
PrintMessageWithPlaceholders(gText_MoveRelearnerPkmnLearnedMove);
gSpecialVar_0x8004 = TRUE;
sMoveRelearnerStruct->state = MENU_STATE_PRINT_TEXT_THEN_FANFARE;
}
else
{
sMoveRelearnerStruct->state = MENU_STATE_PRINT_TRYING_TO_LEARN_PROMPT;
}
sMoveRelearnerStruct->state = MENU_STATE_PRINT_TRYING_TO_LEARN_PROMPT;
}
}
else if (selection == MENU_B_PRESSED || selection == 1)
@@ -734,10 +748,7 @@ static void DoMoveRelearnerMain(void)
case MENU_STATE_SHOW_MOVE_SUMMARY_SCREEN:
if (!gPaletteFade.active)
{
if(gSpecialVar_MonBoxId == 0xFF)
ShowSelectMovePokemonSummaryScreen(gPlayerParty, sMoveRelearnerStruct->partyMon, gPlayerPartyCount - 1, CB2_InitLearnMoveReturnFromSelectMove, GetCurrentSelectedMove());
else
ShowPokemonSummaryScreen(SUMMARY_MODE_BOX_SELECT_MOVE, GetBoxedMonPtr(gSpecialVar_MonBoxId, 0), gSpecialVar_MonBoxPos, IN_BOX_COUNT - 1, CB2_InitLearnMoveReturnFromSelectMove);
ShowSelectMovePokemonSummaryScreen(gPlayerParty, gSpecialVar_0x8004, CB2_InitLearnMoveReturnFromSelectMove, GetCurrentSelectedMove());
FreeMoveRelearnerResources();
}
break;
@@ -772,10 +783,10 @@ static void DoMoveRelearnerMain(void)
ShowPokemonSummaryScreen(SUMMARY_MODE_RELEARNER_CONTEST, gPlayerParty, sMoveRelearnerStruct->partyMon, gPlayerPartyCount - 1, gInitialSummaryScreenCallback);
break;
case RELEARN_MODE_BOX_PSS_PAGE_BATTLE_MOVES:
ShowPokemonSummaryScreen(SUMMARY_MODE_BOX_RELEARNER_BATTLE, GetBoxedMonPtr(gSpecialVar_MonBoxId, 0), gSpecialVar_MonBoxPos, IN_BOX_COUNT - 1, gInitialSummaryScreenCallback);
ShowPokemonSummaryScreen(SUMMARY_MODE_RELEARNER_BATTLE, GetBoxedMonPtr(gSpecialVar_MonBoxId, 0), gSpecialVar_MonBoxPos, IN_BOX_COUNT - 1, gInitialSummaryScreenCallback);
break;
case RELEARN_MODE_BOX_PSS_PAGE_CONTEST_MOVES:
ShowPokemonSummaryScreen(SUMMARY_MODE_BOX_RELEARNER_CONTEST, GetBoxedMonPtr(gSpecialVar_MonBoxId, 0), gSpecialVar_MonBoxPos, IN_BOX_COUNT - 1, gInitialSummaryScreenCallback);
ShowPokemonSummaryScreen(SUMMARY_MODE_RELEARNER_CONTEST, GetBoxedMonPtr(gSpecialVar_MonBoxId, 0), gSpecialVar_MonBoxPos, IN_BOX_COUNT - 1, gInitialSummaryScreenCallback);
break;
default:
ShowPokemonSummaryScreen(SUMMARY_MODE_NORMAL, gPlayerParty, sMoveRelearnerStruct->partyMon, gPlayerPartyCount - 1, gInitialSummaryScreenCallback);
@@ -815,36 +826,20 @@ static void DoMoveRelearnerMain(void)
else
{
enum Move move;
if(gSpecialVar_MonBoxId == 0xFF)
{
move = GetMonData(&gPlayerParty[sMoveRelearnerStruct->partyMon], MON_DATA_MOVE1 + sMoveRelearnerStruct->moveSlot);
u8 originalPP = GetMonData(&gPlayerParty[sMoveRelearnerStruct->partyMon], MON_DATA_PP1 + sMoveRelearnerStruct->moveSlot);
RemoveMonPPBonus(&gPlayerParty[sMoveRelearnerStruct->partyMon], sMoveRelearnerStruct->moveSlot);
SetMonMoveSlot(&gPlayerParty[sMoveRelearnerStruct->partyMon], GetCurrentSelectedMove(), sMoveRelearnerStruct->moveSlot);
u8 newPP = GetMonData(&gPlayerParty[sMoveRelearnerStruct->partyMon], MON_DATA_PP1 + sMoveRelearnerStruct->moveSlot);
if (!P_SUMMARY_MOVE_RELEARNER_FULL_PP
&& (gRelearnMode == RELEARN_MODE_PSS_PAGE_BATTLE_MOVES || gRelearnMode == RELEARN_MODE_PSS_PAGE_CONTEST_MOVES) && originalPP < newPP)
SetMonData(&gPlayerParty[sMoveRelearnerStruct->partyMon], MON_DATA_PP1 + sMoveRelearnerStruct->moveSlot, &originalPP);
}
struct BoxPokemon *boxmon;
if (sMoveRelearnerStruct->partyMon == PC_MON_CHOSEN)
boxmon = GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos);
else
{
move = GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_MOVE1 + sMoveRelearnerStruct->moveSlot);
u8 originalPP = GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_PP1 + sMoveRelearnerStruct->moveSlot);
u8 ppBonuses = GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_PP_BONUSES);
ppBonuses &= gPPUpClearMask[sMoveRelearnerStruct->moveSlot];
SetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_PP_BONUSES, &ppBonuses);
boxmon = &(gPlayerParty[sMoveRelearnerStruct->partyMon].box);
move = GetBoxMonData(boxmon, MON_DATA_MOVE1 + sMoveRelearnerStruct->moveSlot);
u8 originalPP = GetBoxMonData(boxmon, MON_DATA_PP1 + sMoveRelearnerStruct->moveSlot);
SetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_MOVE1 + sMoveRelearnerStruct->moveSlot, &sMoveRelearnerStruct->menuItems[sMoveRelearnerMenuState.listRow + sMoveRelearnerMenuState.listOffset].id);
SetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_PP1 + sMoveRelearnerStruct->moveSlot, &gMovesInfo[sMoveRelearnerStruct->menuItems[sMoveRelearnerMenuState.listRow + sMoveRelearnerMenuState.listOffset].id].pp);
u8 newPP = GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_PP1 + sMoveRelearnerStruct->moveSlot);
if (!P_SUMMARY_MOVE_RELEARNER_FULL_PP
&& (gRelearnMode == RELEARN_MODE_BOX_PSS_PAGE_BATTLE_MOVES || gRelearnMode == RELEARN_MODE_BOX_PSS_PAGE_CONTEST_MOVES) && originalPP < newPP)
SetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_PP1 + sMoveRelearnerStruct->moveSlot, &originalPP);
}
RemoveBoxMonPPBonus(boxmon, sMoveRelearnerStruct->moveSlot);
SetBoxMonMoveSlot(boxmon, GetCurrentSelectedMove(), sMoveRelearnerStruct->moveSlot);
u8 newPP = GetBoxMonData(boxmon, MON_DATA_PP1 + sMoveRelearnerStruct->moveSlot);
if (!P_SUMMARY_MOVE_RELEARNER_FULL_PP
&& (gRelearnMode == RELEARN_MODE_PSS_PAGE_BATTLE_MOVES || gRelearnMode == RELEARN_MODE_PSS_PAGE_CONTEST_MOVES) && originalPP < newPP)
SetBoxMonData(boxmon, MON_DATA_PP1 + sMoveRelearnerStruct->moveSlot, &originalPP);
StringCopy(gStringVar3, GetMoveName(move));
StringCopy(gStringVar2, GetMoveName(GetCurrentSelectedMove()));
@@ -1043,36 +1038,24 @@ static void RemoveScrollArrows(void)
static void CreateLearnableMovesList(void)
{
s32 i;
u8 nickname[POKEMON_NAME_LENGTH + 1];
struct BoxPokemon *boxmon = GetSelectedBoxMonFromPcOrParty();
switch (gMoveRelearnerState)
{
case MOVE_RELEARNER_EGG_MOVES:
if (gSpecialVar_MonBoxId == 0xFF)
sMoveRelearnerStruct->numMenuChoices = GetRelearnerEggMoves(&gPlayerParty[sMoveRelearnerStruct->partyMon], sMoveRelearnerStruct->movesToLearn);
else
sMoveRelearnerStruct->numMenuChoices = GetRelearnerEggMovesBox(GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos), sMoveRelearnerStruct->movesToLearn);
sMoveRelearnerStruct->numMenuChoices = GetRelearnerEggMoves(boxmon, sMoveRelearnerStruct->movesToLearn);
break;
case MOVE_RELEARNER_TM_MOVES:
if (gSpecialVar_MonBoxId == 0xFF)
sMoveRelearnerStruct->numMenuChoices = GetRelearnerTMMoves(&gPlayerParty[sMoveRelearnerStruct->partyMon], sMoveRelearnerStruct->movesToLearn);
else
sMoveRelearnerStruct->numMenuChoices = GetRelearnerTMMovesBox(GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos), sMoveRelearnerStruct->movesToLearn);
sMoveRelearnerStruct->numMenuChoices = GetRelearnerTMMoves(boxmon, sMoveRelearnerStruct->movesToLearn);
break;
case MOVE_RELEARNER_TUTOR_MOVES:
if (gSpecialVar_MonBoxId == 0xFF)
sMoveRelearnerStruct->numMenuChoices = GetRelearnerTutorMoves(&gPlayerParty[sMoveRelearnerStruct->partyMon], sMoveRelearnerStruct->movesToLearn);
else
sMoveRelearnerStruct->numMenuChoices = GetRelearnerTutorMovesBox(GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos), sMoveRelearnerStruct->movesToLearn);
sMoveRelearnerStruct->numMenuChoices = GetRelearnerTutorMoves(boxmon, sMoveRelearnerStruct->movesToLearn);
break;
case MOVE_RELEARNER_LEVEL_UP_MOVES:
default:
if (gSpecialVar_MonBoxId == 0xFF)
sMoveRelearnerStruct->numMenuChoices = GetRelearnerLevelUpMoves(&gPlayerParty[sMoveRelearnerStruct->partyMon], sMoveRelearnerStruct->movesToLearn);
else
sMoveRelearnerStruct->numMenuChoices = GetRelearnerLevelUpMovesBox(GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos), sMoveRelearnerStruct->movesToLearn);
sMoveRelearnerStruct->numMenuChoices = GetRelearnerLevelUpMoves(boxmon, sMoveRelearnerStruct->movesToLearn);
break;
}
}
for (i = 0; i < sMoveRelearnerStruct->numMenuChoices; i++)
{
@@ -1080,11 +1063,8 @@ static void CreateLearnableMovesList(void)
sMoveRelearnerStruct->menuItems[i].id = sMoveRelearnerStruct->movesToLearn[i];
}
if(gSpecialVar_MonBoxId == 0xFF)
GetMonData(&gPlayerParty[sMoveRelearnerStruct->partyMon], MON_DATA_NICKNAME, nickname);
else
GetBoxMonNickAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, nickname);
StringCopy_Nickname(gStringVar1, nickname);
GetBoxMonData(boxmon, MON_DATA_NICKNAME, gStringVar1);
sMoveRelearnerStruct->menuItems[sMoveRelearnerStruct->numMenuChoices].name = gText_Cancel;
sMoveRelearnerStruct->menuItems[sMoveRelearnerStruct->numMenuChoices].id = LIST_CANCEL;
sMoveRelearnerStruct->numMenuChoices++;
@@ -1151,3 +1131,300 @@ void MoveRelearnerShowHideCategoryIcon(s32 moveId)
StartSpriteAnim(&gSprites[sMoveRelearnerStruct->categoryIconSpriteId], GetBattleMoveCategory(moveId));
}
}
static void QuickSortMoves(u16 *moves, s32 left, s32 right)
{
if (left >= right)
return;
u16 pivot = moves[(left + right) / 2];
s32 i = left, j = right;
while (i <= j)
{
while (moves[i] != MOVE_NONE && StringCompare(GetMoveName(moves[i]), GetMoveName(pivot)) < 0)
i++;
while (moves[j] != MOVE_NONE && StringCompare(GetMoveName(moves[j]), GetMoveName(pivot)) > 0)
j--;
if (i <= j)
{
u16 temp = moves[i];
moves[i] = moves[j];
moves[j] = temp;
i++;
j--;
}
}
QuickSortMoves(moves, left, j);
QuickSortMoves(moves, i, right);
}
static void SortMovesAlphabetically(u16 *moves, u32 numMoves)
{
if (numMoves > 1)
QuickSortMoves(moves, 0, numMoves - 1);
}
static u32 GetRelearnerLevelUpMoves(struct BoxPokemon *mon, u16 *moves)
{
u32 numMoves = 0;
u32 species = GetBoxMonData(mon, MON_DATA_SPECIES_OR_EGG);
if (species == SPECIES_EGG)
return 0;
u32 level = (P_ENABLE_ALL_LEVEL_UP_MOVES ? MAX_LEVEL : GetLevelFromBoxMonExp(mon));
do
{
const struct LevelUpMove *learnset = GetSpeciesLevelUpLearnset(species);
for (u32 i = 0; i < MAX_LEVEL_UP_MOVES && learnset[i].move != LEVEL_UP_MOVE_END; i++)
{
if (learnset[i].level > level)
break;
if (!BoxMonKnowsMove(mon, learnset[i].move))
moves[numMoves++] = learnset[i].move;
}
species = (P_PRE_EVO_MOVES ? GetSpeciesPreEvolution(species) : SPECIES_NONE);
} while (species != SPECIES_NONE);
if (P_SORT_MOVES)
SortMovesAlphabetically(moves, numMoves);
return numMoves;
}
static u32 GetRelearnerEggMoves(struct BoxPokemon *mon, u16 *moves)
{
if (!FlagGet(P_FLAG_EGG_MOVES) && !P_ENABLE_MOVE_RELEARNERS)
return 0;
u32 species = GetBoxMonData(mon, MON_DATA_SPECIES_OR_EGG);
if (species == SPECIES_EGG)
return 0;
u32 numMoves = 0;
while (GetSpeciesPreEvolution(species) != SPECIES_NONE)
species = GetSpeciesPreEvolution(species);
const u16 *eggMoves = GetSpeciesEggMoves(species);
if (eggMoves == sNoneEggMoveLearnset)
return 0;
for (u32 i = 0; eggMoves[i] != MOVE_UNAVAILABLE; i++)
{
if (!BoxMonKnowsMove(mon, eggMoves[i]))
moves[numMoves++] = eggMoves[i];
}
if (P_SORT_MOVES)
SortMovesAlphabetically(moves, numMoves);
return numMoves;
}
static u32 GetRelearnerTMMoves(struct BoxPokemon *mon, u16 *moves)
{
if (!P_TM_MOVES_RELEARNER && !P_ENABLE_MOVE_RELEARNERS)
return 0;
u32 species = GetBoxMonData(mon, MON_DATA_SPECIES_OR_EGG);
if (species == SPECIES_EGG)
return 0;
u32 numMoves = 0;
for (u32 i = 0; i < NUM_ALL_MACHINES; i++)
{
enum Item item = GetTMHMItemId(i + 1);
enum Move move = GetTMHMMoveId(i + 1);
if (move == MOVE_NONE)
continue;
if (!P_ENABLE_ALL_TM_MOVES && !CheckBagHasItem(item, 1))
continue;
if (!CanLearnTeachableMove(species, move))
continue;
if (!BoxMonKnowsMove(mon, move))
moves[numMoves++] = move;
}
if (P_SORT_MOVES)
SortMovesAlphabetically(moves, numMoves);
return numMoves;
}
static u32 GetRelearnerTutorMoves(struct BoxPokemon *mon, u16 *moves)
{
if (!FlagGet(P_FLAG_TUTOR_MOVES) && !P_ENABLE_MOVE_RELEARNERS)
return 0;
u32 species = GetBoxMonData(mon, MON_DATA_SPECIES_OR_EGG);
if (species == SPECIES_EGG)
return 0;
u32 numMoves = 0;
for (u32 i = 0; gTutorMoves[i] != MOVE_UNAVAILABLE; i++)
{
enum Move move = gTutorMoves[i];
if (!CanLearnTeachableMove(species, move))
continue;
if (!BoxMonKnowsMove(mon, move))
moves[numMoves++] = move;
}
if (P_SORT_MOVES)
SortMovesAlphabetically(moves, numMoves);
return numMoves;
}
void HasMovesToRelearn(void)
{
struct BoxPokemon *boxmon = GetSelectedBoxMonFromPcOrParty();
if (CanBoxMonRelearnMoves(boxmon, gMoveRelearnerState))
gSpecialVar_Result = TRUE;
else
gSpecialVar_Result = FALSE;
}
bool32 CanBoxMonRelearnAnyMove(struct BoxPokemon *boxMon)
{
for (u32 i = MOVE_RELEARNER_LEVEL_UP_MOVES; i < MOVE_RELEARNER_COUNT; i++)
{
if (sRelearnTypes[i].hasMoveToRelearn(boxMon))
return TRUE;
}
return FALSE;
}
bool32 CanBoxMonRelearnMoves(struct BoxPokemon *boxMon, enum MoveRelearnerStates state)
{
return sRelearnTypes[state].hasMoveToRelearn(boxMon);
}
static bool32 HasRelearnerLevelUpMoves(struct BoxPokemon *boxMon)
{
u32 species = GetBoxMonData(boxMon, MON_DATA_SPECIES_OR_EGG);
if (species == SPECIES_EGG)
return FALSE;
u32 level = (P_ENABLE_ALL_LEVEL_UP_MOVES == TRUE) ? MAX_LEVEL : GetLevelFromBoxMonExp(boxMon);
do
{
const struct LevelUpMove *learnset = GetSpeciesLevelUpLearnset(species);
for (u32 i = 0; i < MAX_LEVEL_UP_MOVES && learnset[i].move != LEVEL_UP_MOVE_END; i++)
{
if (learnset[i].level > level)
break;
if (!BoxMonKnowsMove(boxMon, learnset[i].move))
return TRUE;
}
species = (P_PRE_EVO_MOVES ? GetSpeciesPreEvolution(species) : SPECIES_NONE);
} while (species != SPECIES_NONE);
return FALSE;
}
static bool32 HasRelearnerEggMoves(struct BoxPokemon *boxMon)
{
if (!FlagGet(P_FLAG_EGG_MOVES) && !P_ENABLE_MOVE_RELEARNERS)
return FALSE;
u32 species = GetBoxMonData(boxMon, MON_DATA_SPECIES_OR_EGG);
if (species == SPECIES_EGG)
return FALSE;
while (GetSpeciesPreEvolution(species) != SPECIES_NONE)
species = GetSpeciesPreEvolution(species);
const u16 *eggMoves = GetSpeciesEggMoves(species);
if (eggMoves == sNoneEggMoveLearnset)
return FALSE;
for (u32 i = 0; eggMoves[i] != MOVE_UNAVAILABLE; i++)
{
if (!BoxMonKnowsMove(boxMon, eggMoves[i]))
return TRUE;
}
return FALSE;
}
static bool32 HasRelearnerTMMoves(struct BoxPokemon *boxMon)
{
if (!P_TM_MOVES_RELEARNER && !P_ENABLE_MOVE_RELEARNERS)
return FALSE;
u32 species = GetBoxMonData(boxMon, MON_DATA_SPECIES_OR_EGG);
if (species == SPECIES_EGG)
return FALSE;
for (u32 i = 0; i < NUM_ALL_MACHINES; i++)
{
enum Item item = GetTMHMItemId(i + 1);
enum Move move = GetTMHMMoveId(i + 1);
if (move == MOVE_NONE)
continue;
if (!P_ENABLE_ALL_TM_MOVES && !CheckBagHasItem(item, 1))
continue;
if (!CanLearnTeachableMove(species, move))
continue;
if (!BoxMonKnowsMove(boxMon, move))
return TRUE;
}
return FALSE;
}
static bool32 HasRelearnerTutorMoves(struct BoxPokemon *boxMon)
{
if (!FlagGet(P_FLAG_TUTOR_MOVES) && !P_ENABLE_MOVE_RELEARNERS)
return FALSE;
u32 species = GetBoxMonData(boxMon, MON_DATA_SPECIES_OR_EGG);
if (species == SPECIES_EGG)
return FALSE;
for (u32 i = 0; gTutorMoves[i] != MOVE_UNAVAILABLE; i++)
{
enum Move move = gTutorMoves[i];
if (!CanLearnTeachableMove(species, move))
continue;
if (!BoxMonKnowsMove(boxMon, move))
return TRUE;
}
return FALSE;
}

View File

@@ -211,7 +211,6 @@ void NewGameInitData(void)
ResetContestLinkResults();
SetCurrentDifficultyLevel(DIFFICULTY_NORMAL);
ResetItemFlags();
gSpecialVar_MonBoxId = 0xFF;
ResetDexNav();
ClearFollowerNPCData();
}

View File

@@ -166,13 +166,6 @@ enum {
#define MENU_DIR_RIGHT 2
#define MENU_DIR_LEFT -2
enum {
CAN_LEARN_MOVE,
CANNOT_LEARN_MOVE,
ALREADY_KNOWS_MOVE,
CANNOT_LEARN_MOVE_IS_EGG
};
enum {
// Window ids 0-5 are implicitly assigned to each party Pokémon in InitPartyMenuBoxes
WIN_MSG = PARTY_SIZE,
@@ -279,7 +272,7 @@ static void DisplayPartyPokemonHPBarCheck(struct Pokemon *, struct PartyMenuBox
static void DisplayPartyPokemonDescriptionText(u8, struct PartyMenuBox *, u8);
static bool8 IsMonAllowedInMinigame(u8);
static void DisplayPartyPokemonDataToTeachMove(u8, enum Move);
static u8 CanTeachMove(struct Pokemon *, enum Move);
static enum CanMoveBeLearned CanTeachMove(struct Pokemon *, enum Move);
static void DisplayPartyPokemonBarDetail(u8, const u8 *, u8, const u8 *);
static void DisplayPartyPokemonBarDetailToFit(u8 windowId, const u8 *str, u8 color, const u8 *align, u32 width);
static void DisplayPartyPokemonLevel(u8, struct PartyMenuBox *);
@@ -463,8 +456,7 @@ static void Task_ChoosePartyMon(u8 taskId);
static void Task_ChooseMonForMoveRelearner(u8);
static void CB2_ChooseMonForMoveRelearner(void);
static void Task_BattlePyramidChooseMonHeldItems(u8);
static void ShiftMoveSlot(struct Pokemon *, u8, u8);
static void ShiftMoveSlotBoxMon(u8, u8);
static void ShiftMoveSlot(struct BoxPokemon *, u8, u8);
static void BlitBitmapToPartyWindow_LeftColumn(u8, u8, u8, u8, u8, bool8);
static void BlitBitmapToPartyWindow_RightColumn(u8, u8, u8, u8, u8, bool8);
static void CursorCb_Summary(u8);
@@ -1101,25 +1093,7 @@ static void DisplayPartyPokemonDataForContest(u8 slot)
static void DisplayPartyPokemonDataForRelearner(u8 slot)
{
struct Pokemon *mon = &gPlayerParty[slot];
bool32 hasMoves = FALSE;
switch (gMoveRelearnerState)
{
case MOVE_RELEARNER_EGG_MOVES:
hasMoves = HasRelearnerEggMoves(mon);
break;
case MOVE_RELEARNER_TM_MOVES:
hasMoves = HasRelearnerTMMoves(mon);
break;
case MOVE_RELEARNER_TUTOR_MOVES:
hasMoves = HasRelearnerTutorMoves(mon);
break;
default:
hasMoves = HasRelearnerLevelUpMoves(mon);
break;
}
bool32 hasMoves = CanBoxMonRelearnMoves(&gPlayerParty[slot].box, gMoveRelearnerState);
u32 desc = (hasMoves ? PARTYBOX_DESC_ABLE_2 : PARTYBOX_DESC_NOT_ABLE_2);
DisplayPartyPokemonDescriptionData(slot, desc);
}
@@ -2273,7 +2247,7 @@ static void Task_HandleCancelParticipationYesNoInput(u8 taskId)
}
}
static u8 CanTeachMove(struct Pokemon *mon, enum Move move)
static enum CanMoveBeLearned CanTeachMove(struct Pokemon *mon, enum Move move)
{
if (GetMonData(mon, MON_DATA_IS_EGG))
return CANNOT_LEARN_MOVE_IS_EGG;
@@ -2883,10 +2857,11 @@ static void SetPartyMonFieldSelectionActions(struct Pokemon *mons, u8 slotId)
AppendToList(sPartyMenuInternal->actions, &sPartyMenuInternal->numActions, MENU_SUMMARY);
if (P_PARTY_MOVE_RELEARNER
&& (GetMonData(&mons[slotId], MON_DATA_SPECIES)
&& (HasRelearnerLevelUpMoves(&mons[slotId]) || HasRelearnerEggMoves(&mons[slotId])
|| HasRelearnerTMMoves(&mons[slotId]) || HasRelearnerTutorMoves(&mons[slotId]))))
&& GetMonData(&mons[slotId], MON_DATA_SPECIES)
&& CanBoxMonRelearnAnyMove(&mons[slotId].box))
{
AppendToList(sPartyMenuInternal->actions, &sPartyMenuInternal->numActions, MENU_SUB_MOVES);
}
// Add field moves to action list
for (i = 0; i < MAX_MON_MOVES; i++)
@@ -2915,26 +2890,17 @@ static void SetPartyMonFieldSelectionActions(struct Pokemon *mons, u8 slotId)
static void SetPartyMonLearnMoveSelectionActions(struct Pokemon *mons, u8 slotId)
{
if (GetMonData(&mons[slotId], MON_DATA_SPECIES) != SPECIES_NONE && HasRelearnerLevelUpMoves(&mons[slotId]))
if (CanBoxMonRelearnMoves(&mons[slotId].box, MOVE_RELEARNER_LEVEL_UP_MOVES))
AppendToList(sPartyMenuInternal->actions, &sPartyMenuInternal->numActions, MENU_LEVEL_UP_MOVES);
if (P_ENABLE_MOVE_RELEARNERS || (P_FLAG_EGG_MOVES != 0 && FlagGet(P_FLAG_EGG_MOVES)))
{
if (GetMonData(&mons[slotId], MON_DATA_SPECIES) != SPECIES_NONE && HasRelearnerEggMoves(&mons[slotId]))
AppendToList(sPartyMenuInternal->actions, &sPartyMenuInternal->numActions, MENU_EGG_MOVES);
}
if (CanBoxMonRelearnMoves(&mons[slotId].box, MOVE_RELEARNER_EGG_MOVES))
AppendToList(sPartyMenuInternal->actions, &sPartyMenuInternal->numActions, MENU_EGG_MOVES);
if (P_ENABLE_MOVE_RELEARNERS || P_TM_MOVES_RELEARNER)
{
if (GetMonData(&mons[slotId], MON_DATA_SPECIES) != SPECIES_NONE && HasRelearnerTMMoves(&mons[slotId]))
AppendToList(sPartyMenuInternal->actions, &sPartyMenuInternal->numActions, MENU_TM_MOVES);
}
if (CanBoxMonRelearnMoves(&mons[slotId].box, MOVE_RELEARNER_TM_MOVES))
AppendToList(sPartyMenuInternal->actions, &sPartyMenuInternal->numActions, MENU_TM_MOVES);
if (P_ENABLE_MOVE_RELEARNERS || (P_FLAG_TUTOR_MOVES != 0 && FlagGet(P_FLAG_TUTOR_MOVES)))
{
if (GetMonData(&mons[slotId], MON_DATA_SPECIES) != SPECIES_NONE && HasRelearnerTutorMoves(&mons[slotId]))
AppendToList(sPartyMenuInternal->actions, &sPartyMenuInternal->numActions, MENU_TUTOR_MOVES);
}
if (CanBoxMonRelearnMoves(&mons[slotId].box, MOVE_RELEARNER_TUTOR_MOVES))
AppendToList(sPartyMenuInternal->actions, &sPartyMenuInternal->numActions, MENU_TUTOR_MOVES);
AppendToList(sPartyMenuInternal->actions, &sPartyMenuInternal->numActions, MENU_CANCEL1);
}
@@ -5509,6 +5475,8 @@ void ItemUseCB_TMHM(u8 taskId, TaskFunc task)
case ALREADY_KNOWS_MOVE:
DisplayLearnMoveMessageAndClose(taskId, gText_PkmnAlreadyKnows);
return;
default:
break;
}
if (GiveMoveToMon(mon, move) != MON_HAS_MAX_MOVES)
@@ -5605,7 +5573,7 @@ static void Task_ShowSummaryScreenToForgetMove(u8 taskId)
static void CB2_ShowSummaryScreenToForgetMove(void)
{
ShowSelectMovePokemonSummaryScreen(gPlayerParty, gPartyMenu.slotId, gPlayerPartyCount - 1, CB2_ReturnToPartyMenuWhileLearningMove, gPartyMenu.data1);
ShowSelectMovePokemonSummaryScreen(gPlayerParty, gPartyMenu.slotId, CB2_ReturnToPartyMenuWhileLearningMove, gPartyMenu.data1);
}
static void CB2_ReturnToPartyMenuWhileLearningMove(void)
@@ -6265,7 +6233,7 @@ void DeleteMove(struct Pokemon *mon, enum Move move)
SetMonMoveSlot(mon, MOVE_NONE, i);
RemoveMonPPBonus(mon, i);
for (j = i; j < MAX_MON_MOVES - 1; j++)
ShiftMoveSlot(mon, j, j + 1);
ShiftMoveSlot(&mon->box, j, j + 1);
break;
}
}
@@ -7412,7 +7380,6 @@ void ChooseMonForTradingBoard(u8 menuType, MainCallback callback)
void ChooseMonForMoveTutor(void)
{
gSpecialVar_MonBoxId = 0xFF;
InitPartyMenu(PARTY_MENU_TYPE_FIELD, PARTY_LAYOUT_SINGLE, PARTY_ACTION_MOVE_TUTOR, FALSE, PARTY_MSG_TEACH_WHICH_MON, Task_HandleChooseMonInput, CB2_ReturnToFieldContinueScriptPlayMapMusic);
}
@@ -7927,7 +7894,6 @@ static void CB2_ChooseContestMon(void)
// Used as a script special for showing a party mon to various npcs (e.g. in-game trades, move deleter)
void ChoosePartyMon(void)
{
gSpecialVar_MonBoxId = 0xFF;
LockPlayerFieldControls();
FadeScreen(FADE_TO_BLACK, 0);
CreateTask(Task_ChoosePartyMon, 10);
@@ -7945,7 +7911,6 @@ static void Task_ChoosePartyMon(u8 taskId)
void ChooseMonForMoveRelearner(void)
{
gSpecialVar_MonBoxId = 0xFF;
gRelearnMode = RELEARN_MODE_SCRIPT;
LockPlayerFieldControls();
FadeScreen(FADE_TO_BLACK, 0);
@@ -7969,24 +7934,6 @@ static void CB2_ChooseMonForMoveRelearner(void)
{
gSpecialVar_0x8004 = PARTY_NOTHING_CHOSEN;
}
else
{
switch(gMoveRelearnerState)
{
case MOVE_RELEARNER_EGG_MOVES:
gSpecialVar_0x8005 = HasRelearnerEggMoves(&gPlayerParty[gSpecialVar_0x8004]);
break;
case MOVE_RELEARNER_TM_MOVES:
gSpecialVar_0x8005 = HasRelearnerTMMoves(&gPlayerParty[gSpecialVar_0x8004]);
break;
case MOVE_RELEARNER_TUTOR_MOVES:
gSpecialVar_0x8005 = HasRelearnerTutorMoves(&gPlayerParty[gSpecialVar_0x8004]);
break;
default:
gSpecialVar_0x8005 = HasRelearnerLevelUpMoves(&gPlayerParty[gSpecialVar_0x8004]);
break;
}
}
gFieldCallback2 = CB2_FadeFromPartyMenu;
SetMainCallback2(CB2_ReturnToField);
}
@@ -8027,80 +7974,52 @@ static void Task_BattlePyramidChooseMonHeldItems(u8 taskId)
void MoveDeleterChooseMoveToForget(void)
{
if(gSpecialVar_MonBoxId == 0xFF)
ShowPokemonSummaryScreen(SUMMARY_MODE_SELECT_MOVE, gPlayerParty, gSpecialVar_0x8004, gPlayerPartyCount - 1, CB2_ReturnToField);
else
ShowPokemonSummaryScreen(SUMMARY_MODE_BOX_SELECT_MOVE, GetBoxedMonPtr(StorageGetCurrentBox(), 0), gSpecialVar_MonBoxPos, IN_BOX_COUNT - 1, CB2_ReturnToField);
ShowPokemonSummaryScreen(SUMMARY_MODE_SELECT_MOVE, gPlayerParty, gSpecialVar_0x8004, gPlayerPartyCount - 1, CB2_ReturnToField);
gFieldCallback = FieldCB_ContinueScriptHandleMusic;
}
void GetNumMovesSelectedMonHas(void)
{
u8 i;
u32 i;
struct BoxPokemon *boxmon = GetSelectedBoxMonFromPcOrParty();
gSpecialVar_Result = 0;
for (i = 0; i < MAX_MON_MOVES; i++)
{
if(gSpecialVar_MonBoxId == 0xFF){
if (GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_MOVE1 + i) != MOVE_NONE)
gSpecialVar_Result++;
}
else{
if (GetBoxMonDataAt(gSpecialVar_MonBoxId,gSpecialVar_MonBoxPos, MON_DATA_MOVE1 + i) != MOVE_NONE)
gSpecialVar_Result++;
}
if (GetBoxMonData(boxmon , MON_DATA_MOVE1 + i) != MOVE_NONE)
gSpecialVar_Result++;
}
}
void BufferMoveDeleterNicknameAndMove(void)
{
enum Move move = 0;
if(gSpecialVar_MonBoxId == 0xFF){
struct Pokemon *mon = &gPlayerParty[gSpecialVar_0x8004];
move = GetMonData(mon, MON_DATA_MOVE1 + gSpecialVar_0x8005);
GetMonNickname(mon, gStringVar1);
}
else{
move = GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_MOVE1 + gSpecialVar_0x8005);
GetBoxMonNickAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, gStringVar1);
}
struct BoxPokemon *boxmon = GetSelectedBoxMonFromPcOrParty();
move = GetBoxMonData(boxmon, MON_DATA_MOVE1 + gSpecialVar_0x8005);
GetBoxMonData(boxmon, MON_DATA_NICKNAME, gStringVar1);
StringCopy(gStringVar2, GetMoveName(move));
}
void MoveDeleterForgetMove(void)
{
u16 i;
if(gSpecialVar_MonBoxId == 0xFF)
{
SetMonMoveSlot(&gPlayerParty[gSpecialVar_0x8004], MOVE_NONE, gSpecialVar_0x8005);
RemoveMonPPBonus(&gPlayerParty[gSpecialVar_0x8004], gSpecialVar_0x8005);
for (i = gSpecialVar_0x8005; i < MAX_MON_MOVES - 1; i++)
ShiftMoveSlot(&gPlayerParty[gSpecialVar_0x8004], i, i + 1);
}
else
{
i = MOVE_NONE;
SetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_MOVE1 + gSpecialVar_0x8005, &i);
SetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_PP1 + gSpecialVar_0x8005, &gMovesInfo[MOVE_NONE].pp);
u8 ppBonuses = GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_PP_BONUSES);
ppBonuses &= gPPUpClearMask[gSpecialVar_0x8005];
SetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_PP_BONUSES, &ppBonuses);
for (i = gSpecialVar_0x8005; i < MAX_MON_MOVES - 1; i++)
ShiftMoveSlotBoxMon(i, i + 1);
}
enum Move move = MOVE_NONE;
struct BoxPokemon *boxmon = GetSelectedBoxMonFromPcOrParty();
SetBoxMonData(boxmon, MON_DATA_MOVE1 + gSpecialVar_0x8005, &move);
SetBoxMonData(boxmon, MON_DATA_PP1 + gSpecialVar_0x8005, &gMovesInfo[MOVE_NONE].pp);
u8 ppBonuses = GetBoxMonData(boxmon, MON_DATA_PP_BONUSES);
ppBonuses &= gPPUpClearMask[gSpecialVar_0x8005];
SetBoxMonData(boxmon, MON_DATA_PP_BONUSES, &ppBonuses);
for (u32 i = gSpecialVar_0x8005; i < MAX_MON_MOVES - 1; i++)
ShiftMoveSlot(boxmon, i, i + 1);
}
static void ShiftMoveSlot(struct Pokemon *mon, u8 slotTo, u8 slotFrom)
static void ShiftMoveSlot(struct BoxPokemon *mon, u8 slotTo, u8 slotFrom)
{
enum Move move1 = GetMonData(mon, MON_DATA_MOVE1 + slotTo);
enum Move move0 = GetMonData(mon, MON_DATA_MOVE1 + slotFrom);
u8 pp1 = GetMonData(mon, MON_DATA_PP1 + slotTo);
u8 pp0 = GetMonData(mon, MON_DATA_PP1 + slotFrom);
u8 ppBonuses = GetMonData(mon, MON_DATA_PP_BONUSES);
enum Move move1 = GetBoxMonData(mon, MON_DATA_MOVE1 + slotTo);
enum Move move0 = GetBoxMonData(mon, MON_DATA_MOVE1 + slotFrom);
u8 pp1 = GetBoxMonData(mon, MON_DATA_PP1 + slotTo);
u8 pp0 = GetBoxMonData(mon, MON_DATA_PP1 + slotFrom);
u8 ppBonuses = GetBoxMonData(mon, MON_DATA_PP_BONUSES);
u8 ppBonusMask1 = gPPUpGetMask[slotTo];
u8 ppBonusMove1 = (ppBonuses & ppBonusMask1) >> (slotTo * 2);
u8 ppBonusMask2 = gPPUpGetMask[slotFrom];
@@ -8108,49 +8027,20 @@ static void ShiftMoveSlot(struct Pokemon *mon, u8 slotTo, u8 slotFrom)
ppBonuses &= ~ppBonusMask1;
ppBonuses &= ~ppBonusMask2;
ppBonuses |= (ppBonusMove1 << (slotFrom * 2)) + (ppBonusMove2 << (slotTo * 2));
SetMonData(mon, MON_DATA_MOVE1 + slotTo, &move0);
SetMonData(mon, MON_DATA_MOVE1 + slotFrom, &move1);
SetMonData(mon, MON_DATA_PP1 + slotTo, &pp0);
SetMonData(mon, MON_DATA_PP1 + slotFrom, &pp1);
SetMonData(mon, MON_DATA_PP_BONUSES, &ppBonuses);
}
static void ShiftMoveSlotBoxMon( u8 slotTo, u8 slotFrom)
{
enum Move move1 = GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_MOVE1 + slotTo);
enum Move move0 = GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_MOVE1 + slotFrom);
u8 pp1 = GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_PP1 + slotTo);
u8 pp0 = GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_PP1 + slotFrom);
u8 ppBonuses = GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_PP_BONUSES);
u8 ppBonusMask1 = gPPUpGetMask[slotTo];
u8 ppBonusMove1 = (ppBonuses & ppBonusMask1) >> (slotTo * 2);
u8 ppBonusMask2 = gPPUpGetMask[slotFrom];
u8 ppBonusMove2 = (ppBonuses & ppBonusMask2) >> (slotFrom * 2);
ppBonuses &= ~ppBonusMask1;
ppBonuses &= ~ppBonusMask2;
ppBonuses |= (ppBonusMove1 << (slotFrom * 2)) + (ppBonusMove2 << (slotTo * 2));
SetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_MOVE1 + slotTo, &move0);
SetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_MOVE1 + slotFrom, &move1);
SetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_PP1 + slotTo, &pp0);
SetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_PP1 + slotFrom, &pp1);
SetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_PP_BONUSES, &ppBonuses);
SetBoxMonData(mon, MON_DATA_MOVE1 + slotTo, &move0);
SetBoxMonData(mon, MON_DATA_MOVE1 + slotFrom, &move1);
SetBoxMonData(mon, MON_DATA_PP1 + slotTo, &pp0);
SetBoxMonData(mon, MON_DATA_PP1 + slotFrom, &pp1);
SetBoxMonData(mon, MON_DATA_PP_BONUSES, &ppBonuses);
}
void IsSelectedMonEgg(void)
{
if(gSpecialVar_MonBoxId == 0xFF)
{
if (GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_IS_EGG))
gSpecialVar_Result = TRUE;
else
gSpecialVar_Result = FALSE;
}
else{
if (GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_0x8004, MON_DATA_IS_EGG))
gSpecialVar_Result = TRUE;
else
gSpecialVar_Result = FALSE;
}
struct BoxPokemon *boxmon = GetSelectedBoxMonFromPcOrParty();
if (GetBoxMonData(boxmon, MON_DATA_IS_EGG))
gSpecialVar_Result = TRUE;
else
gSpecialVar_Result = FALSE;
}
void IsLastMonThatKnowsSurf(void)
@@ -8159,11 +8049,10 @@ void IsLastMonThatKnowsSurf(void)
u32 i, j;
gSpecialVar_Result = FALSE;
if(gSpecialVar_MonBoxId == 0xFF)
move = GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_MOVE1 + gSpecialVar_0x8005);
else
move = GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_MOVE1 + gSpecialVar_0x8005);
if (gSpecialVar_0x8004 == PC_MON_CHOSEN)
return;
move = GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_MOVE1 + gSpecialVar_0x8005);
if (move == MOVE_SURF)
{
for (i = 0; i < CalculatePlayerPartyCount(); i++)

View File

@@ -30,6 +30,7 @@
#include "m4a.h"
#include "main.h"
#include "move_relearner.h"
#include "naming_screen.h"
#include "overworld.h"
#include "party_menu.h"
#include "pokedex.h"
@@ -65,6 +66,7 @@
#include "constants/items.h"
#include "constants/layouts.h"
#include "constants/moves.h"
#include "constants/party_menu.h"
#include "constants/regions.h"
#include "constants/songs.h"
#include "constants/trainers.h"
@@ -99,7 +101,6 @@ EWRAM_DATA static u8 sTriedEvolving = 0;
EWRAM_DATA u16 gFollowerSteps = 0;
#include "data/abilities.h"
#include "data/tutor_moves.h"
// Used in an unreferenced function in RS.
// Unreferenced here and in FRLG.
@@ -1689,9 +1690,14 @@ u16 GiveMoveToBattleMon(struct BattlePokemon *mon, enum Move move)
void SetMonMoveSlot(struct Pokemon *mon, enum Move move, u8 slot)
{
SetMonData(mon, MON_DATA_MOVE1 + slot, &move);
SetBoxMonMoveSlot(&mon->box, move, slot);
}
void SetBoxMonMoveSlot(struct BoxPokemon *mon, enum Move move, u8 slot)
{
SetBoxMonData(mon, MON_DATA_MOVE1 + slot, &move);
u32 pp = GetMovePP(move);
SetMonData(mon, MON_DATA_PP1 + slot, &pp);
SetBoxMonData(mon, MON_DATA_PP1 + slot, &pp);
}
static void SetMonMoveSlot_KeepPP(struct Pokemon *mon, enum Move move, u8 slot)
@@ -3530,9 +3536,14 @@ u8 CalculatePPWithBonus(enum Move move, u8 ppBonuses, u8 moveIndex)
void RemoveMonPPBonus(struct Pokemon *mon, u8 moveIndex)
{
u8 ppBonuses = GetMonData(mon, MON_DATA_PP_BONUSES);
RemoveBoxMonPPBonus(&mon->box, moveIndex);
}
void RemoveBoxMonPPBonus(struct BoxPokemon *mon, u8 moveIndex)
{
u8 ppBonuses = GetBoxMonData(mon, MON_DATA_PP_BONUSES);
ppBonuses &= gPPUpClearMask[moveIndex];
SetMonData(mon, MON_DATA_PP_BONUSES, &ppBonuses);
SetBoxMonData(mon, MON_DATA_PP_BONUSES, &ppBonuses);
}
void RemoveBattleMonPPBonus(struct BattlePokemon *mon, u8 moveIndex)
@@ -5360,321 +5371,6 @@ u8 CanLearnTeachableMove(u16 species, enum Move move)
return FALSE;
}
static void QuickSortMoves(u16 *moves, s32 left, s32 right)
{
if (left >= right)
return;
u16 pivot = moves[(left + right) / 2];
s32 i = left, j = right;
while (i <= j)
{
while (moves[i] != MOVE_NONE && StringCompare(GetMoveName(moves[i]), GetMoveName(pivot)) < 0)
i++;
while (moves[j] != MOVE_NONE && StringCompare(GetMoveName(moves[j]), GetMoveName(pivot)) > 0)
j--;
if (i <= j)
{
u16 temp = moves[i];
moves[i] = moves[j];
moves[j] = temp;
i++;
j--;
}
}
QuickSortMoves(moves, left, j);
QuickSortMoves(moves, i, right);
}
static void SortMovesAlphabetically(u16 *moves, u32 numMoves)
{
if (numMoves > 1)
QuickSortMoves(moves, 0, numMoves - 1);
}
u32 GetRelearnerLevelUpMovesBox(struct BoxPokemon *boxMon, u16 *moves)
{
u32 species = GetBoxMonData(boxMon, MON_DATA_SPECIES_OR_EGG);
if (species == SPECIES_EGG)
return 0;
u32 numMoves = 0;
u32 level = (P_ENABLE_ALL_LEVEL_UP_MOVES == TRUE) ? MAX_LEVEL : GetLevelFromBoxMonExp(boxMon);
do
{
const struct LevelUpMove *learnset = GetSpeciesLevelUpLearnset(species);
for (u32 i = 0; i < MAX_LEVEL_UP_MOVES && learnset[i].move != LEVEL_UP_MOVE_END; i++)
{
if (learnset[i].level > level)
break;
if (!BoxMonKnowsMove(boxMon, learnset[i].move))
moves[numMoves++] = learnset[i].move;
}
species = (P_PRE_EVO_MOVES ? GetSpeciesPreEvolution(species) : SPECIES_NONE);
} while (species != SPECIES_NONE);
if (P_SORT_MOVES)
SortMovesAlphabetically(moves, numMoves);
return numMoves;
}
u32 GetRelearnerLevelUpMoves(struct Pokemon *mon, u16 *moves)
{
return GetRelearnerLevelUpMovesBox(&mon->box, moves);
}
u32 GetRelearnerEggMovesBox(struct BoxPokemon *boxMon, u16 *moves)
{
if (!FlagGet(P_FLAG_EGG_MOVES) && !P_ENABLE_MOVE_RELEARNERS)
return 0;
u32 species = GetBoxMonData(boxMon, MON_DATA_SPECIES_OR_EGG);
if (species == SPECIES_EGG)
return 0;
u32 numMoves = 0;
while (GetSpeciesPreEvolution(species) != SPECIES_NONE)
species = GetSpeciesPreEvolution(species);
const u16 *eggMoves = GetSpeciesEggMoves(species);
if (eggMoves == sNoneEggMoveLearnset)
return 0;
for (u32 i = 0; eggMoves[i] != MOVE_UNAVAILABLE; i++)
{
if (!BoxMonKnowsMove(boxMon, eggMoves[i]))
moves[numMoves++] = eggMoves[i];
}
if (P_SORT_MOVES)
SortMovesAlphabetically(moves, numMoves);
return numMoves;
}
u32 GetRelearnerEggMoves(struct Pokemon *mon, u16 *moves)
{
return GetRelearnerEggMovesBox(&mon->box, moves);
}
u32 GetRelearnerTMMovesBox(struct BoxPokemon *boxMon, u16 *moves)
{
if (!P_TM_MOVES_RELEARNER && !P_ENABLE_MOVE_RELEARNERS)
return 0;
u32 species = GetBoxMonData(boxMon, MON_DATA_SPECIES_OR_EGG);
if (species == SPECIES_EGG)
return 0;
u32 numMoves = 0;
for (u32 i = 0; i < NUM_ALL_MACHINES; i++)
{
enum Item item = GetTMHMItemId(i + 1);
enum Move move = GetTMHMMoveId(i + 1);
if (move == MOVE_NONE)
continue;
if (!P_ENABLE_ALL_TM_MOVES && !CheckBagHasItem(item, 1))
continue;
if (!CanLearnTeachableMove(species, move))
continue;
if (!BoxMonKnowsMove(boxMon, move))
moves[numMoves++] = move;
}
if (P_SORT_MOVES)
SortMovesAlphabetically(moves, numMoves);
return numMoves;
}
u32 GetRelearnerTMMoves(struct Pokemon *mon, u16 *moves)
{
return GetRelearnerTMMovesBox(&mon->box, moves);
}
u32 GetRelearnerTutorMovesBox(struct BoxPokemon *boxMon, u16 *moves)
{
if (!FlagGet(P_FLAG_TUTOR_MOVES) && !P_ENABLE_MOVE_RELEARNERS)
return 0;
u32 species = GetBoxMonData(boxMon, MON_DATA_SPECIES_OR_EGG);
if (species == SPECIES_EGG)
return 0;
u32 numMoves = 0;
for (u32 i = 0; gTutorMoves[i] != MOVE_UNAVAILABLE; i++)
{
enum Move move = gTutorMoves[i];
if (!CanLearnTeachableMove(species, move))
continue;
if (!BoxMonKnowsMove(boxMon, move))
moves[numMoves++] = move;
}
if (P_SORT_MOVES)
SortMovesAlphabetically(moves, numMoves);
return numMoves;
}
u32 GetRelearnerTutorMoves(struct Pokemon *mon, u16 *moves)
{
return GetRelearnerTutorMovesBox(&mon->box, moves);
}
bool32 HasRelearnerLevelUpMovesBox(struct BoxPokemon *boxMon)
{
u32 species = GetBoxMonData(boxMon, MON_DATA_SPECIES_OR_EGG);
if (species == SPECIES_EGG)
return FALSE;
u32 level = (P_ENABLE_ALL_LEVEL_UP_MOVES == TRUE) ? MAX_LEVEL : GetLevelFromBoxMonExp(boxMon);
do
{
const struct LevelUpMove *learnset = GetSpeciesLevelUpLearnset(species);
for (u32 i = 0; i < MAX_LEVEL_UP_MOVES && learnset[i].move != LEVEL_UP_MOVE_END; i++)
{
if (learnset[i].level > level)
break;
if (!BoxMonKnowsMove(boxMon, learnset[i].move))
return TRUE;
}
species = (P_PRE_EVO_MOVES ? GetSpeciesPreEvolution(species) : SPECIES_NONE);
} while (species != SPECIES_NONE);
return FALSE;
}
bool32 HasRelearnerLevelUpMoves(struct Pokemon *mon)
{
return HasRelearnerLevelUpMovesBox(&mon->box);
}
bool32 HasRelearnerEggMovesBox(struct BoxPokemon *boxMon)
{
if (!FlagGet(P_FLAG_EGG_MOVES) && !P_ENABLE_MOVE_RELEARNERS)
return FALSE;
u32 species = GetBoxMonData(boxMon, MON_DATA_SPECIES_OR_EGG);
if (species == SPECIES_EGG)
return FALSE;
while (GetSpeciesPreEvolution(species) != SPECIES_NONE)
species = GetSpeciesPreEvolution(species);
const u16 *eggMoves = GetSpeciesEggMoves(species);
if (eggMoves == sNoneEggMoveLearnset)
return FALSE;
for (u32 i = 0; eggMoves[i] != MOVE_UNAVAILABLE; i++)
{
if (!BoxMonKnowsMove(boxMon, eggMoves[i]))
return TRUE;
}
return FALSE;
}
bool32 HasRelearnerEggMoves(struct Pokemon *mon)
{
return HasRelearnerEggMovesBox(&mon->box);
}
bool32 HasRelearnerTMMovesBox(struct BoxPokemon *boxMon)
{
if (!P_TM_MOVES_RELEARNER && !P_ENABLE_MOVE_RELEARNERS)
return FALSE;
u32 species = GetBoxMonData(boxMon, MON_DATA_SPECIES_OR_EGG);
if (species == SPECIES_EGG)
return FALSE;
for (u32 i = 0; i < NUM_ALL_MACHINES; i++)
{
enum Item item = GetTMHMItemId(i + 1);
enum Move move = GetTMHMMoveId(i + 1);
if (move == MOVE_NONE)
continue;
if (!P_ENABLE_ALL_TM_MOVES && !CheckBagHasItem(item, 1))
continue;
if (!CanLearnTeachableMove(species, move))
continue;
if (!BoxMonKnowsMove(boxMon, move))
return TRUE;
}
return FALSE;
}
bool32 HasRelearnerTMMoves(struct Pokemon *mon)
{
return HasRelearnerTMMovesBox(&mon->box);
}
bool32 HasRelearnerTutorMovesBox(struct BoxPokemon *boxMon)
{
if (!FlagGet(P_FLAG_TUTOR_MOVES) && !P_ENABLE_MOVE_RELEARNERS)
return FALSE;
u32 species = GetBoxMonData(boxMon, MON_DATA_SPECIES_OR_EGG);
if (species == SPECIES_EGG)
return FALSE;
for (u32 i = 0; gTutorMoves[i] != MOVE_UNAVAILABLE; i++)
{
enum Move move = gTutorMoves[i];
if (!CanLearnTeachableMove(species, move))
continue;
if (!BoxMonKnowsMove(boxMon, move))
return TRUE;
}
return FALSE;
}
bool32 HasRelearnerTutorMoves(struct Pokemon *mon)
{
return HasRelearnerTutorMovesBox(&mon->box);
}
u8 GetLevelUpMovesBySpecies(u16 species, u16 *moves)
{
u8 numMoves = 0;
@@ -5687,66 +5383,6 @@ u8 GetLevelUpMovesBySpecies(u16 species, u16 *moves)
return numMoves;
}
u8 GetNumberOfRelearnableMoves(struct Pokemon *mon)
{
enum Move learnedMoves[MAX_MON_MOVES];
enum Move moves[MAX_LEVEL_UP_MOVES];
u8 numMoves = 0;
u16 species;
u8 level;
if(gSpecialVar_MonBoxId == 0xFF)
{
species = GetMonData(mon, MON_DATA_SPECIES_OR_EGG, 0);
level = GetMonData(mon, MON_DATA_LEVEL, 0);
}
else
{
species = GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_SPECIES_OR_EGG);
level = GetBoxMonLevelAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos);
}
const struct LevelUpMove *learnset = GetSpeciesLevelUpLearnset(species);
int i, j, k;
if (species == SPECIES_EGG)
return 0;
for (i = 0; i < MAX_MON_MOVES; i++)
{
if(gSpecialVar_MonBoxId == 0xFF)
learnedMoves[i] = GetMonData(mon, MON_DATA_MOVE1 + i, 0);
else
learnedMoves[i] = GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_MOVE1 + i);
}
for (i = 0; i < MAX_LEVEL_UP_MOVES; i++)
{
u16 moveLevel;
if (learnset[i].move == LEVEL_UP_MOVE_END)
break;
moveLevel = learnset[i].level;
if (moveLevel <= level)
{
for (j = 0; j < MAX_MON_MOVES && learnedMoves[j] != learnset[i].move; j++)
;
if (j == MAX_MON_MOVES)
{
for (k = 0; k < numMoves && moves[k] != learnset[i].move; k++)
;
if (k == numMoves)
moves[numMoves++] = learnset[i].move;
}
}
}
return numMoves;
}
u16 SpeciesToPokedexNum(u16 species)
{
if (IsNationalPokedexEnabled())
@@ -7223,6 +6859,16 @@ bool32 IsSpeciesOfType(u32 species, enum Type type)
return FALSE;
}
struct BoxPokemon *GetSelectedBoxMonFromPcOrParty(void)
{
struct BoxPokemon *boxmon;
if (gSpecialVar_0x8004 == PC_MON_CHOSEN)
boxmon = GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos);
else
boxmon = &(gPlayerParty[gSpecialVar_0x8004].box);
return boxmon;
}
u32 GiveScriptedMonToPlayer(struct Pokemon *mon, u8 slot)
{
u32 sentToPc;
@@ -7257,3 +6903,11 @@ u32 GiveScriptedMonToPlayer(struct Pokemon *mon, u8 slot)
}
return sentToPc;
}
void ChangePokemonNicknameWithCallback(void (*callback)(void))
{
struct BoxPokemon *boxMon = GetSelectedBoxMonFromPcOrParty();
GetBoxMonData(boxMon, MON_DATA_NICKNAME, gStringVar3);
GetBoxMonData(boxMon, MON_DATA_NICKNAME, gStringVar2);
DoNamingScreen(NAMING_SCREEN_NICKNAME, gStringVar2, GetBoxMonData(boxMon, MON_DATA_SPECIES), GetBoxMonGender(boxMon), GetBoxMonData(boxMon, MON_DATA_PERSONALITY), callback);
}

View File

@@ -57,21 +57,6 @@ enum
extern const u8 gText_DecimalPoint[];
extern const u8 gText_Marco[];
static u32 GetMonSizeHash(struct Pokemon *pkmn)
{
u16 personality = GetMonData(pkmn, MON_DATA_PERSONALITY);
u16 hpIV = GetMonData(pkmn, MON_DATA_HP_IV) & 0xF;
u16 attackIV = GetMonData(pkmn, MON_DATA_ATK_IV) & 0xF;
u16 defenseIV = GetMonData(pkmn, MON_DATA_DEF_IV) & 0xF;
u16 speedIV = GetMonData(pkmn, MON_DATA_SPEED_IV) & 0xF;
u16 spAtkIV = GetMonData(pkmn, MON_DATA_SPATK_IV) & 0xF;
u16 spDefIV = GetMonData(pkmn, MON_DATA_SPDEF_IV) & 0xF;
u32 hibyte = ((attackIV ^ defenseIV) * hpIV) ^ (personality & 0xFF);
u32 lobyte = ((spAtkIV ^ spDefIV) * speedIV) ^ (personality >> 8);
return (hibyte << 8) + lobyte;
}
static u32 GetBoxMonSizeHash(struct BoxPokemon *pkmn)
{
u16 personality = GetBoxMonData(pkmn, MON_DATA_PERSONALITY);
@@ -144,62 +129,30 @@ static u8 CompareMonSize(u16 species, u16 *sizeRecord)
{
return POKEMON_NONE;
}
else if(gSpecialVar_MonBoxId == 0xFF)
struct BoxPokemon *boxmon = GetSelectedBoxMonFromPcOrParty();
if (GetBoxMonData(boxmon, MON_DATA_IS_EGG) == TRUE || GetBoxMonData(boxmon, MON_DATA_SPECIES) != species)
{
struct Pokemon *pkmn = &gPlayerParty[gSpecialVar_Result];
if (GetMonData(pkmn, MON_DATA_IS_EGG) == TRUE || GetMonData(pkmn, MON_DATA_SPECIES) != species)
{
return POKEMON_INCORRECT_SPECIES;
}
else
{
u32 oldSize;
u32 newSize;
u16 sizeParams;
*(&sizeParams) = GetMonSizeHash(pkmn);
newSize = GetMonSize(species, sizeParams);
oldSize = GetMonSize(species, *sizeRecord);
FormatMonSizeRecord(gStringVar2, newSize);
if (newSize <= oldSize)
{
return POKEMON_SIZE_SMALLER;
}
else
{
*sizeRecord = sizeParams;
return POKEMON_SIZE_LARGER;
}
}
return POKEMON_INCORRECT_SPECIES;
}
else
{
struct BoxPokemon *pkmn = GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos);
u32 oldSize;
u32 newSize;
u16 sizeParams;
if (GetBoxMonData(pkmn, MON_DATA_IS_EGG) == TRUE || GetBoxMonData(pkmn, MON_DATA_SPECIES) != species)
*(&sizeParams) = GetBoxMonSizeHash(boxmon);
newSize = GetMonSize(species, sizeParams);
oldSize = GetMonSize(species, *sizeRecord);
FormatMonSizeRecord(gStringVar2, newSize);
if (newSize <= oldSize)
{
return POKEMON_INCORRECT_SPECIES;
return POKEMON_SIZE_SMALLER;
}
else
{
u32 oldSize;
u32 newSize;
u16 sizeParams;
*(&sizeParams) = GetBoxMonSizeHash(pkmn);
newSize = GetMonSize(species, sizeParams);
oldSize = GetMonSize(species, *sizeRecord);
FormatMonSizeRecord(gStringVar2, newSize);
if (newSize <= oldSize)
{
return POKEMON_SIZE_SMALLER;
}
else
{
*sizeRecord = sizeParams;
return POKEMON_SIZE_LARGER;
}
*sizeRecord = sizeParams;
return POKEMON_SIZE_LARGER;
}
}
}

View File

@@ -39,10 +39,13 @@
#include "window.h"
#include "constants/form_change_types.h"
#include "constants/items.h"
#include "constants/party_menu.h"
#include "constants/moves.h"
#include "constants/rgb.h"
#include "constants/songs.h"
#include "constants/pokemon_icon.h"
#include "chooseboxmon.h"
#include "party_menu.h"
/*
NOTE: This file is large. Some general groups of functions have
@@ -795,9 +798,11 @@ static void SetUpScrollToBox(u8);
static bool8 ScrollToBox(void);
static s8 DetermineBoxScrollDirection(u8);
static void SetCurrentBox(u8);
static struct BoxPokemon *GetCursorBoxMon(void);
// Misc
static void CreateMainMenu(u8, s16 *);
static void EnterPokeStorage(u8 boxOption);
static u8 GetCurrentBoxOption(void);
static void ScrollBackground(void);
static void UpdateCloseBoxButtonFlash(void);
@@ -1962,7 +1967,7 @@ static void CB2_PokeStorage(void)
BuildOamBuffer();
}
void EnterPokeStorage(u8 boxOption)
static void EnterPokeStorage(u8 boxOption)
{
ResetTasks();
sCurrentBoxOption = boxOption;
@@ -2681,20 +2686,21 @@ static void Task_OnSelectedMon(u8 taskId)
break;
case MENU_SELECT:
PlaySE(SE_SELECT);
struct BoxPokemon *boxmon = GetCursorBoxMon();
if (sInPartyMenu)
{
gSpecialVar_Result = GetBoxMonData(&gPlayerParty[sCursorPosition].box, MON_DATA_SPECIES);
gSpecialVar_MonBoxId = TOTAL_BOXES_COUNT;
gSpecialVar_0x8005 = GetNumberOfRelearnableMoves(&gPlayerParty[sCursorPosition]);
gSpecialVar_0x8004 = sCursorPosition;
}
else
{
gSpecialVar_Result = GetBoxMonDataAt(StorageGetCurrentBox(), sCursorPosition, MON_DATA_SPECIES);
gSpecialVar_0x8004 = PC_MON_CHOSEN;
gSpecialVar_MonBoxPos = sCursorPosition;
gSpecialVar_MonBoxId = StorageGetCurrentBox();
gSpecialVar_0x8005 = GetNumberOfRelearnableMoves(&gPlayerParty[0]);
}
gSpecialVar_MonBoxPos = sCursorPosition;
gSpecialVar_0x8004 = sCursorPosition;
if (IsBoxMonExcluded(boxmon))
gSpecialVar_Result = FALSE;
else
gSpecialVar_Result = TRUE;
sStorage->screenChangeType = SCREEN_CHANGE_EXIT_BOX;
SetPokeStorageTask(Task_ChangeScreen);
break;
@@ -3654,7 +3660,10 @@ static void Task_OnCloseBoxPressed(u8 taskId)
UpdateBoxToSendMons();
gPlayerPartyCount = CalculatePlayerPartyCount();
if (sStorage->boxOption == OPTION_SELECT_MON)
gSpecialVar_0x8004 = 0xFF;
{
gSpecialVar_0x8004 = PARTY_NOTHING_CHOSEN;
gSpecialVar_Result = FALSE;
}
sStorage->screenChangeType = SCREEN_CHANGE_EXIT_BOX;
SetPokeStorageTask(Task_ChangeScreen);
}
@@ -3729,7 +3738,10 @@ static void Task_OnBPressed(u8 taskId)
UpdateBoxToSendMons();
gPlayerPartyCount = CalculatePlayerPartyCount();
if (sStorage->boxOption == OPTION_SELECT_MON)
gSpecialVar_0x8004 = 0xFF;
{
gSpecialVar_0x8004 = PARTY_NOTHING_CHOSEN;
gSpecialVar_Result = FALSE;
}
sStorage->screenChangeType = SCREEN_CHANGE_EXIT_BOX;
SetPokeStorageTask(Task_ChangeScreen);
}
@@ -4448,6 +4460,17 @@ static void CreateMovingMonIcon(void)
sStorage->movingMonSprite->callback = SpriteCB_HeldMon;
}
static bool32 ShouldBoxmonSpriteBeTransparent(u32 boxId, u32 boxPosition)
{
if (sStorage->boxOption == OPTION_MOVE_ITEMS
&& GetBoxMonDataAt(boxId, boxPosition, MON_DATA_HELD_ITEM) == ITEM_NONE)
return TRUE;
if (sStorage->boxOption == OPTION_SELECT_MON
&& IsBoxMonExcluded(GetBoxedMonPtr(boxId, boxPosition)))
return TRUE;
return FALSE;
}
static void InitBoxMonSprites(u8 boxId)
{
u8 boxPosition;
@@ -4469,6 +4492,9 @@ static void InitBoxMonSprites(u8 boxId)
{
personality = GetBoxMonDataAt(boxId, boxPosition, MON_DATA_PERSONALITY);
sStorage->boxMonsSprites[count] = CreateMonIconSprite(species, personality, 8 * (3 * j) + 100, 8 * (3 * i) + 44, 2, 19 - j, isEgg);
if (ShouldBoxmonSpriteBeTransparent(boxId, boxPosition))
sStorage->boxMonsSprites[boxPosition]->oam.objMode = ST_OAM_OBJ_BLEND;
}
else
{
@@ -4478,16 +4504,6 @@ static void InitBoxMonSprites(u8 boxId)
count++;
}
}
// If in item mode, set all Pokémon icons with no item to be transparent
if (sStorage->boxOption == OPTION_MOVE_ITEMS)
{
for (boxPosition = 0; boxPosition < IN_BOX_COUNT; boxPosition++)
{
if (GetBoxMonDataAt(boxId, boxPosition, MON_DATA_HELD_ITEM) == ITEM_NONE)
sStorage->boxMonsSprites[boxPosition]->oam.objMode = ST_OAM_OBJ_BLEND;
}
}
}
static void CreateBoxMonIconAtPos(u8 boxPosition)
@@ -4502,7 +4518,7 @@ static void CreateBoxMonIconAtPos(u8 boxPosition)
u32 personality = GetCurrentBoxMonData(boxPosition, MON_DATA_PERSONALITY);
sStorage->boxMonsSprites[boxPosition] = CreateMonIconSprite(species, personality, x, y, 2, 19 - (boxPosition % IN_BOX_COLUMNS), isEgg);
if (sStorage->boxOption == OPTION_MOVE_ITEMS)
if (ShouldBoxmonSpriteBeTransparent(StorageGetCurrentBox(), boxPosition))
sStorage->boxMonsSprites[boxPosition]->oam.objMode = ST_OAM_OBJ_BLEND;
}
}
@@ -4592,55 +4608,27 @@ static u8 CreateBoxMonIconsInColumn(u8 column, u16 distance, s16 speed)
u8 iconsCreated = 0;
u8 boxPosition = column;
if (sStorage->boxOption != OPTION_MOVE_ITEMS)
for (i = 0; i < IN_BOX_ROWS; i++)
{
for (i = 0; i < IN_BOX_ROWS; i++)
if (sStorage->boxSpecies[boxPosition] != SPECIES_NONE)
{
if (sStorage->boxSpecies[boxPosition] != SPECIES_NONE)
sStorage->boxMonsSprites[boxPosition] = CreateMonIconSprite(sStorage->boxSpecies[boxPosition],
sStorage->boxPersonalities[boxPosition],
x, y, 2, subpriority,
sStorage->boxIsEgg[boxPosition]);
if (sStorage->boxMonsSprites[boxPosition] != NULL)
{
sStorage->boxMonsSprites[boxPosition] = CreateMonIconSprite(sStorage->boxSpecies[boxPosition],
sStorage->boxPersonalities[boxPosition],
x, y, 2, subpriority,
sStorage->boxIsEgg[boxPosition]);
if (sStorage->boxMonsSprites[boxPosition] != NULL)
{
sStorage->boxMonsSprites[boxPosition]->sDistance = distance;
sStorage->boxMonsSprites[boxPosition]->sSpeed = speed;
sStorage->boxMonsSprites[boxPosition]->sScrollInDestX = xDest;
sStorage->boxMonsSprites[boxPosition]->callback = SpriteCB_BoxMonIconScrollIn;
iconsCreated++;
}
sStorage->boxMonsSprites[boxPosition]->sDistance = distance;
sStorage->boxMonsSprites[boxPosition]->sSpeed = speed;
sStorage->boxMonsSprites[boxPosition]->sScrollInDestX = xDest;
sStorage->boxMonsSprites[boxPosition]->callback = SpriteCB_BoxMonIconScrollIn;
if (ShouldBoxmonSpriteBeTransparent(sStorage->incomingBoxId, boxPosition))
sStorage->boxMonsSprites[boxPosition]->oam.objMode = ST_OAM_OBJ_BLEND;
iconsCreated++;
}
boxPosition += IN_BOX_COLUMNS;
y += 24;
}
}
else
{
// Separate case for Move Items mode is used
// to create the icons with the proper blend
for (i = 0; i < IN_BOX_ROWS; i++)
{
if (sStorage->boxSpecies[boxPosition] != SPECIES_NONE)
{
sStorage->boxMonsSprites[boxPosition] = CreateMonIconSprite(sStorage->boxSpecies[boxPosition],
sStorage->boxPersonalities[boxPosition],
x, y, 2, subpriority,
sStorage->boxIsEgg[boxPosition]);
if (sStorage->boxMonsSprites[boxPosition] != NULL)
{
sStorage->boxMonsSprites[boxPosition]->sDistance = distance;
sStorage->boxMonsSprites[boxPosition]->sSpeed = speed;
sStorage->boxMonsSprites[boxPosition]->sScrollInDestX = xDest;
sStorage->boxMonsSprites[boxPosition]->callback = SpriteCB_BoxMonIconScrollIn;
if (GetBoxMonDataAt(sStorage->incomingBoxId, boxPosition, MON_DATA_HELD_ITEM) == ITEM_NONE)
sStorage->boxMonsSprites[boxPosition]->oam.objMode = ST_OAM_OBJ_BLEND;
iconsCreated++;
}
}
boxPosition += IN_BOX_COLUMNS;
y += 24;
}
boxPosition += IN_BOX_COLUMNS;
y += 24;
}
return iconsCreated;
@@ -4796,6 +4784,15 @@ static void CreatePartyMonsSprites(bool8 visible)
sStorage->partySprites[i]->oam.objMode = ST_OAM_OBJ_BLEND;
}
}
if (sStorage->boxOption == OPTION_SELECT_MON)
{
for (i = 0; i < PARTY_SIZE; i++)
{
if (sStorage->partySprites[i] != NULL && IsBoxMonExcluded(&(gPlayerParty[i].box)))
sStorage->partySprites[i]->oam.objMode = ST_OAM_OBJ_BLEND;
}
}
}
static void CompactPartySprites(void)
@@ -7757,7 +7754,7 @@ static bool8 SetMenuTexts_Mon(void)
}
break;
case OPTION_SELECT_MON:
if (species != SPECIES_NONE)
if (species != SPECIES_NONE && CanBoxMonBeSelected(GetCursorBoxMon()))
SetMenuText(MENU_SELECT);
else
return FALSE;
@@ -9528,6 +9525,16 @@ static void SetCurrentBox(u8 boxId)
gPokemonStoragePtr->currentBox = boxId;
}
static struct BoxPokemon *GetCursorBoxMon(void)
{
struct BoxPokemon *boxmon;
if (sInPartyMenu)
boxmon = &(gPlayerParty[sCursorPosition].box);
else
boxmon = GetBoxedMonPtr(StorageGetCurrentBox(), sCursorPosition);
return boxmon;
}
u32 GetBoxMonDataAt(u8 boxId, u8 boxPosition, s32 request)
{
if (boxId < TOTAL_BOXES_COUNT && boxPosition < IN_BOX_COUNT)
@@ -9552,34 +9559,6 @@ void SetCurrentBoxMonData(u8 boxPosition, s32 request, const void *value)
SetBoxMonDataAt(gPokemonStoragePtr->currentBox, boxPosition, request, value);
}
void GetBoxMonNickAt(u8 boxId, u8 boxPosition, u8 *dst)
{
if (boxId < TOTAL_BOXES_COUNT && boxPosition < IN_BOX_COUNT)
GetBoxMonData(&gPokemonStoragePtr->boxes[boxId][boxPosition], MON_DATA_NICKNAME, dst);
else
*dst = EOS;
}
u32 GetBoxMonLevelAt(u8 boxId, u8 boxPosition)
{
u32 lvl;
if (boxId < TOTAL_BOXES_COUNT && boxPosition < IN_BOX_COUNT && GetBoxMonData(&gPokemonStoragePtr->boxes[boxId][boxPosition], MON_DATA_SANITY_HAS_SPECIES))
lvl = GetLevelFromBoxMonExp(&gPokemonStoragePtr->boxes[boxId][boxPosition]);
#ifdef BUGFIX
else
#endif
lvl = 0;
return lvl;
}
void SetBoxMonNickAt(u8 boxId, u8 boxPosition, const u8 *nick)
{
if (boxId < TOTAL_BOXES_COUNT && boxPosition < IN_BOX_COUNT)
SetBoxMonData(&gPokemonStoragePtr->boxes[boxId][boxPosition], MON_DATA_NICKNAME, nick);
}
u32 GetAndCopyBoxMonDataAt(u8 boxId, u8 boxPosition, s32 request, void *dst)
{
if (boxId < TOTAL_BOXES_COUNT && boxPosition < IN_BOX_COUNT)
@@ -10109,16 +10088,19 @@ void UpdateSpeciesSpritePSS(struct BoxPokemon *boxMon)
{
DestroyBoxMonIconAtPosition(sCursorPosition);
CreateBoxMonIconAtPos(sCursorPosition);
if (sStorage->boxOption == OPTION_MOVE_ITEMS)
SetBoxMonIconObjMode(sCursorPosition, (GetBoxMonData(boxMon, MON_DATA_HELD_ITEM) == ITEM_NONE ? ST_OAM_OBJ_BLEND : ST_OAM_OBJ_NORMAL));
}
}
sJustOpenedBag = FALSE;
}
// Used as a script special for showing a box mon to various npcs (e.g. in-game trades, move deleter)
void ChooseBoxMon(void)
void ChooseMonFromStorage(void)
{
gSpecialVar_MonBoxId = 0xFF;
EnterPokeStorage(OPTION_SELECT_MON);
}
void RemoveSelectedPcMon(struct Pokemon *mon)
{
struct BoxPokemon *boxmon = GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos);
BoxMonToMon(boxmon, mon);
ZeroBoxMonData(boxmon);
}

View File

@@ -320,9 +320,7 @@ static bool32 ShouldShowRename(void);
static bool32 ShouldShowIvEvPrompt(void);
static void BufferLeftColumnIvEvStats(void);
static void CB2_ReturnToSummaryScreenFromNamingScreen(void);
static void CB2_ReturnToSummaryScreenFromNamingScreenBox(void);
static void CB2_PssChangePokemonNickname(void);
static void CB2_PssChangeBoxPokemonNickname(void);
static void ShowUtilityPrompt(s16 mode);
static void ShowMonSkillsInfo(u8 taskId, s16 mode);
static void WriteToStatsTilemapBuffer(u32 length, u32 block, u32 statsCoordX, u32 statsCoordY);
@@ -338,6 +336,7 @@ static void ClearStatLabel(u32 length, u32 statsCoordX, u32 statsCoordY);
u32 GetAdjustedIvData(struct Pokemon *mon, u32 stat);
static void TryUpdateRelearnType(enum IncrDecrUpdateValues delta);
static void ShowRelearnPrompt(void);
static struct BoxPokemon *GetCurrentBoxmon(void);
static const struct BgTemplate sBgTemplates[] =
{
@@ -1195,14 +1194,23 @@ void ShowPokemonSummaryScreen(u8 mode, void *mons, u8 monIndex, u8 maxMonIndex,
{
sMonSummaryScreen = AllocZeroed(sizeof(*sMonSummaryScreen));
sMonSummaryScreen->mode = mode;
sMonSummaryScreen->monList.mons = mons;
sMonSummaryScreen->curMonIndex = monIndex;
sMonSummaryScreen->maxMonIndex = maxMonIndex;
if (monIndex == PC_MON_CHOSEN)
{
sMonSummaryScreen->monList.boxMons = GetBoxedMonPtr(gSpecialVar_MonBoxId, 0);
sMonSummaryScreen->curMonIndex = gSpecialVar_MonBoxPos;
sMonSummaryScreen->maxMonIndex = IN_BOX_COUNT - 1;
}
else
{
sMonSummaryScreen->monList.mons = mons;
sMonSummaryScreen->curMonIndex = monIndex;
sMonSummaryScreen->maxMonIndex = maxMonIndex;
}
sMonSummaryScreen->callback = callback;
if (gInitialSummaryScreenCallback == NULL)
gInitialSummaryScreenCallback = callback;
if (mode == SUMMARY_MODE_BOX || mode == SUMMARY_MODE_BOX_SELECT_MOVE || mode == SUMMARY_MODE_BOX_RELEARNER_BATTLE || mode == SUMMARY_MODE_BOX_RELEARNER_CONTEST)
if (mode == SUMMARY_MODE_BOX || monIndex == PC_MON_CHOSEN)
sMonSummaryScreen->isBoxMon = TRUE;
else
sMonSummaryScreen->isBoxMon = FALSE;
@@ -1214,8 +1222,6 @@ void ShowPokemonSummaryScreen(u8 mode, void *mons, u8 monIndex, u8 maxMonIndex,
case SUMMARY_MODE_BOX_CURSOR:
case SUMMARY_MODE_RELEARNER_BATTLE:
case SUMMARY_MODE_RELEARNER_CONTEST:
case SUMMARY_MODE_BOX_RELEARNER_BATTLE:
case SUMMARY_MODE_BOX_RELEARNER_CONTEST:
sMonSummaryScreen->minPageIndex = 0;
sMonSummaryScreen->maxPageIndex = PSS_PAGE_COUNT - 1;
break;
@@ -1229,16 +1235,11 @@ void ShowPokemonSummaryScreen(u8 mode, void *mons, u8 monIndex, u8 maxMonIndex,
sMonSummaryScreen->maxPageIndex = PSS_PAGE_COUNT - 1;
sMonSummaryScreen->lockMonFlag = TRUE;
break;
case SUMMARY_MODE_BOX_SELECT_MOVE:
sMonSummaryScreen->minPageIndex = PSS_PAGE_BATTLE_MOVES;
sMonSummaryScreen->maxPageIndex = PSS_PAGE_COUNT - 1;
sMonSummaryScreen->lockMonFlag = TRUE;
break;
}
if (mode == SUMMARY_MODE_RELEARNER_BATTLE || mode == SUMMARY_MODE_BOX_RELEARNER_BATTLE)
if (mode == SUMMARY_MODE_RELEARNER_BATTLE)
sMonSummaryScreen->currPageIndex = PSS_PAGE_BATTLE_MOVES;
else if (mode == SUMMARY_MODE_RELEARNER_CONTEST || mode == SUMMARY_MODE_BOX_RELEARNER_CONTEST)
else if (mode == SUMMARY_MODE_RELEARNER_CONTEST)
sMonSummaryScreen->currPageIndex = PSS_PAGE_CONTEST_MOVES;
else
sMonSummaryScreen->currPageIndex = sMonSummaryScreen->minPageIndex;
@@ -1255,15 +1256,9 @@ void ShowPokemonSummaryScreen(u8 mode, void *mons, u8 monIndex, u8 maxMonIndex,
SetMainCallback2(CB2_InitSummaryScreen);
}
void ShowSelectMovePokemonSummaryScreen(struct Pokemon *mons, u8 monIndex, u8 maxMonIndex, void (*callback)(void), u16 newMove)
void ShowSelectMovePokemonSummaryScreen(struct Pokemon *mons, u8 monIndex, void (*callback)(void), u16 newMove)
{
ShowPokemonSummaryScreen(SUMMARY_MODE_SELECT_MOVE, mons, monIndex, maxMonIndex, callback);
sMonSummaryScreen->newMove = newMove;
}
void ShowSelectMoveBoxPokemonSummaryScreen(struct BoxPokemon *mons, u8 monIndex, u8 maxMonIndex, void (*callback)(void), u16 newMove)
{
ShowPokemonSummaryScreen(SUMMARY_MODE_BOX_SELECT_MOVE, mons, monIndex, maxMonIndex, callback);
ShowPokemonSummaryScreen(SUMMARY_MODE_SELECT_MOVE, mons, monIndex, gPlayerPartyCount - 1, callback);
sMonSummaryScreen->newMove = newMove;
}
@@ -1392,7 +1387,7 @@ static bool8 LoadGraphics(void)
gMain.state++;
break;
case 22:
if (sMonSummaryScreen->mode != SUMMARY_MODE_SELECT_MOVE && sMonSummaryScreen->mode != SUMMARY_MODE_BOX_SELECT_MOVE)
if (sMonSummaryScreen->mode != SUMMARY_MODE_SELECT_MOVE)
CreateTask(Task_HandleInput, 0);
else
CreateTask(Task_SetHandleReplaceMoveInput, 0);
@@ -1501,6 +1496,13 @@ static bool8 DecompressGraphics(void)
return FALSE;
}
static struct BoxPokemon *GetCurrentBoxmon(void)
{
if (sMonSummaryScreen->isBoxMon)
return &sMonSummaryScreen->monList.boxMons[sMonSummaryScreen->curMonIndex];
return &sMonSummaryScreen->monList.mons[sMonSummaryScreen->curMonIndex].box;
}
static void CopyMonToSummaryStruct(struct Pokemon *mon)
{
if (!sMonSummaryScreen->isBoxMon)
@@ -1573,8 +1575,8 @@ static bool8 ExtractMonDataToSummaryStruct(struct Pokemon *mon)
static void SetDefaultTilemaps(void)
{
if ((sMonSummaryScreen->currPageIndex != PSS_PAGE_BATTLE_MOVES && sMonSummaryScreen->currPageIndex != PSS_PAGE_CONTEST_MOVES)
|| sMonSummaryScreen->mode == SUMMARY_MODE_RELEARNER_BATTLE || sMonSummaryScreen->mode == SUMMARY_MODE_BOX_RELEARNER_BATTLE
|| sMonSummaryScreen->mode == SUMMARY_MODE_RELEARNER_CONTEST || sMonSummaryScreen->mode == SUMMARY_MODE_BOX_RELEARNER_CONTEST)
|| sMonSummaryScreen->mode == SUMMARY_MODE_RELEARNER_BATTLE
|| sMonSummaryScreen->mode == SUMMARY_MODE_RELEARNER_CONTEST)
{
PositionPowerAccSlidingWindow(0, 0xFF);
PositionAppealJamSlidingWindow(0, 0xFF, 0);
@@ -1592,7 +1594,7 @@ static void SetDefaultTilemaps(void)
}
// these blocks handle preparing the gfx to return straight to the respective move info screens
if (sMonSummaryScreen->mode == SUMMARY_MODE_RELEARNER_BATTLE || sMonSummaryScreen->mode == SUMMARY_MODE_BOX_RELEARNER_BATTLE)
if (sMonSummaryScreen->mode == SUMMARY_MODE_RELEARNER_BATTLE)
{
SetBgTilemapBuffer(1, sMonSummaryScreen->bgTilemapBuffers[PSS_PAGE_SKILLS][0]);
SetBgTilemapBuffer(2, sMonSummaryScreen->bgTilemapBuffers[PSS_PAGE_BATTLE_MOVES][0]);
@@ -1603,7 +1605,7 @@ static void SetDefaultTilemaps(void)
ShowBg(1);
ShowBg(2);
}
else if (sMonSummaryScreen->mode == SUMMARY_MODE_RELEARNER_CONTEST || sMonSummaryScreen->mode == SUMMARY_MODE_BOX_RELEARNER_CONTEST)
else if (sMonSummaryScreen->mode == SUMMARY_MODE_RELEARNER_CONTEST)
{
sMonSummaryScreen->bgDisplayOrder = 1;
SetBgTilemapBuffer(1, sMonSummaryScreen->bgTilemapBuffers[PSS_PAGE_CONTEST_MOVES][0]);
@@ -1739,18 +1741,16 @@ static void Task_HandleInput(u8 taskId)
{
if (ShouldShowRename())
{
if (!sMonSummaryScreen->isBoxMon)
if (sMonSummaryScreen->isBoxMon)
{
sMonSummaryScreen->callback = CB2_PssChangePokemonNickname;
gSpecialVar_MonBoxId = 0xFF;
gSpecialVar_0x8004 = PC_MON_CHOSEN;
gSpecialVar_MonBoxPos = sMonSummaryScreen->curMonIndex;
}
else
{
sMonSummaryScreen->callback = CB2_PssChangeBoxPokemonNickname;
gSpecialVar_MonBoxId = StorageGetCurrentBox();
gSpecialVar_0x8004 = sMonSummaryScreen->curMonIndex;
}
gSpecialVar_0x8004 = sMonSummaryScreen->curMonIndex;
gSpecialVar_MonBoxPos = sMonSummaryScreen->curMonIndex;
sMonSummaryScreen->callback = CB2_PssChangePokemonNickname;
}
StopPokemonAnimations();
@@ -1784,17 +1784,16 @@ static void Task_HandleInput(u8 taskId)
&& (sMonSummaryScreen->currPageIndex == PSS_PAGE_BATTLE_MOVES || sMonSummaryScreen->currPageIndex == PSS_PAGE_CONTEST_MOVES))
{
sMonSummaryScreen->callback = CB2_InitLearnMove;
gSpecialVar_0x8004 = sMonSummaryScreen->curMonIndex;
gRelearnMode = sMonSummaryScreen->currPageIndex;
gSpecialVar_MonBoxPos = sMonSummaryScreen->curMonIndex;
if (!sMonSummaryScreen->isBoxMon)
if (sMonSummaryScreen->isBoxMon)
{
gRelearnMode = sMonSummaryScreen->currPageIndex;
gSpecialVar_MonBoxId = 0xFF;
gSpecialVar_0x8004 = PC_MON_CHOSEN;
gSpecialVar_MonBoxPos = sMonSummaryScreen->curMonIndex;
}
else
{
gRelearnMode = sMonSummaryScreen->currPageIndex + 3;
gSpecialVar_MonBoxId = StorageGetCurrentBox();
gSpecialVar_0x8004 = sMonSummaryScreen->curMonIndex;
}
StopPokemonAnimations();
PlaySE(SE_SELECT);
@@ -1934,21 +1933,7 @@ void ExtractMonSkillEvData(struct Pokemon *mon, struct PokeSummary *sum)
bool32 HasAnyRelearnableMoves(enum MoveRelearnerStates state)
{
struct Pokemon *mon = &sMonSummaryScreen->currentMon;
switch (state)
{
case MOVE_RELEARNER_EGG_MOVES:
return HasRelearnerEggMoves(mon);
case MOVE_RELEARNER_TM_MOVES:
return HasRelearnerTMMoves(mon);
case MOVE_RELEARNER_TUTOR_MOVES:
return HasRelearnerTutorMoves(mon);
case MOVE_RELEARNER_LEVEL_UP_MOVES:
return HasRelearnerLevelUpMoves(mon);
default:
return FALSE;
}
return CanBoxMonRelearnMoves(GetCurrentBoxmon(), state);
}
bool32 NoMovesAvailableToRelearn(void)
@@ -2764,6 +2749,7 @@ static void Task_HandleReplaceMoveInput(u8 taskId)
PlaySE(SE_SELECT);
sMoveSlotToReplace = sMonSummaryScreen->firstMoveIndex;
gSpecialVar_0x8005 = sMoveSlotToReplace;
gSpecialVar_Result = TRUE;
BeginCloseSummaryScreen(taskId);
}
else
@@ -2778,6 +2764,7 @@ static void Task_HandleReplaceMoveInput(u8 taskId)
PlaySE(SE_SELECT);
sMoveSlotToReplace = MAX_MON_MOVES;
gSpecialVar_0x8005 = MAX_MON_MOVES;
gSpecialVar_Result = FALSE;
BeginCloseSummaryScreen(taskId);
}
}
@@ -3456,7 +3443,7 @@ static void PutPageWindowTilemaps(u8 page)
case PSS_PAGE_BATTLE_MOVES:
PutWindowTilemap(PSS_LABEL_WINDOW_BATTLE_MOVES_TITLE);
PutWindowTilemap(PSS_LABEL_WINDOW_PROMPT_UTILITY);
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE || sMonSummaryScreen->mode == SUMMARY_MODE_BOX_SELECT_MOVE)
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE)
{
if (sMonSummaryScreen->newMove != MOVE_NONE || sMonSummaryScreen->firstMoveIndex != MAX_MON_MOVES)
PutWindowTilemap(PSS_LABEL_WINDOW_MOVES_POWER_ACC);
@@ -3470,7 +3457,7 @@ static void PutPageWindowTilemaps(u8 page)
case PSS_PAGE_CONTEST_MOVES:
PutWindowTilemap(PSS_LABEL_WINDOW_CONTEST_MOVES_TITLE);
PutWindowTilemap(PSS_LABEL_WINDOW_PROMPT_UTILITY);
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE || sMonSummaryScreen->mode == SUMMARY_MODE_BOX_SELECT_MOVE)
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE)
{
if (sMonSummaryScreen->newMove != MOVE_NONE || sMonSummaryScreen->firstMoveIndex != MAX_MON_MOVES)
PutWindowTilemap(PSS_LABEL_WINDOW_MOVES_APPEAL_JAM);
@@ -3511,7 +3498,7 @@ static void ClearPageWindowTilemaps(u8 page)
ClearWindowTilemap(PSS_LABEL_WINDOW_PROMPT_RELEARN);
break;
case PSS_PAGE_BATTLE_MOVES:
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE || sMonSummaryScreen->mode == SUMMARY_MODE_BOX_SELECT_MOVE)
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE)
{
if (sMonSummaryScreen->newMove != MOVE_NONE || sMonSummaryScreen->firstMoveIndex != MAX_MON_MOVES)
{
@@ -3523,7 +3510,7 @@ static void ClearPageWindowTilemaps(u8 page)
ClearWindowTilemap(PSS_LABEL_WINDOW_PROMPT_RELEARN);
break;
case PSS_PAGE_CONTEST_MOVES:
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE || sMonSummaryScreen->mode == SUMMARY_MODE_BOX_SELECT_MOVE)
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE)
{
if (sMonSummaryScreen->newMove != MOVE_NONE || sMonSummaryScreen->firstMoveIndex != MAX_MON_MOVES)
ClearWindowTilemap(PSS_LABEL_WINDOW_MOVES_APPEAL_JAM);
@@ -4098,7 +4085,7 @@ static void PrintBattleMoves(void)
PrintMoveNameAndPP(1);
PrintMoveNameAndPP(2);
PrintMoveNameAndPP(3);
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE || sMonSummaryScreen->mode == SUMMARY_MODE_BOX_SELECT_MOVE)
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE)
{
PrintNewMoveDetailsOrCancelText();
if (sMonSummaryScreen->firstMoveIndex == MAX_MON_MOVES)
@@ -4132,11 +4119,11 @@ static void Task_PrintBattleMoves(u8 taskId)
PrintMoveNameAndPP(3);
break;
case 5:
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE || sMonSummaryScreen->mode == SUMMARY_MODE_BOX_SELECT_MOVE)
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE)
PrintNewMoveDetailsOrCancelText();
break;
case 6:
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE || sMonSummaryScreen->mode == SUMMARY_MODE_BOX_SELECT_MOVE)
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE)
{
if (sMonSummaryScreen->firstMoveIndex == MAX_MON_MOVES)
data[1] = sMonSummaryScreen->newMove;
@@ -4145,7 +4132,7 @@ static void Task_PrintBattleMoves(u8 taskId)
}
break;
case 7:
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE || sMonSummaryScreen->mode == SUMMARY_MODE_BOX_SELECT_MOVE)
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE)
{
if (sMonSummaryScreen->newMove != MOVE_NONE || sMonSummaryScreen->firstMoveIndex != MAX_MON_MOVES)
PrintMoveDetails(data[1]);
@@ -4235,7 +4222,7 @@ static void PrintContestMoves(void)
PrintMoveNameAndPP(2);
PrintMoveNameAndPP(3);
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE || sMonSummaryScreen->mode == SUMMARY_MODE_BOX_SELECT_MOVE)
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE)
{
PrintNewMoveDetailsOrCancelText();
PrintContestMoveDescription(sMonSummaryScreen->firstMoveIndex);
@@ -4261,11 +4248,11 @@ static void Task_PrintContestMoves(u8 taskId)
PrintMoveNameAndPP(3);
break;
case 5:
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE || sMonSummaryScreen->mode == SUMMARY_MODE_BOX_SELECT_MOVE)
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE)
PrintNewMoveDetailsOrCancelText();
break;
case 6:
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE || sMonSummaryScreen->mode == SUMMARY_MODE_BOX_SELECT_MOVE)
if (sMonSummaryScreen->mode == SUMMARY_MODE_SELECT_MOVE)
{
if (sMonSummaryScreen->newMove != MOVE_NONE || sMonSummaryScreen->firstMoveIndex != MAX_MON_MOVES)
PrintContestMoveDescription(sMonSummaryScreen->firstMoveIndex);
@@ -4864,8 +4851,7 @@ static inline bool32 ShouldShowIvEvPrompt(void)
if (P_SUMMARY_SCREEN_IV_EV_BOX_ONLY)
{
return (P_SUMMARY_SCREEN_IV_EV_INFO || FlagGet(P_FLAG_SUMMARY_SCREEN_IV_EV_INFO))
&& (sMonSummaryScreen->mode == SUMMARY_MODE_BOX || sMonSummaryScreen->mode == SUMMARY_MODE_BOX_CURSOR
|| sMonSummaryScreen->mode == SUMMARY_MODE_BOX_RELEARNER_BATTLE || sMonSummaryScreen->mode == SUMMARY_MODE_BOX_RELEARNER_CONTEST);
&& (sMonSummaryScreen->mode == SUMMARY_MODE_BOX || sMonSummaryScreen->mode == SUMMARY_MODE_BOX_CURSOR);
}
else if (!P_SUMMARY_SCREEN_IV_EV_BOX_ONLY)
{
@@ -4993,33 +4979,11 @@ static void ShowRelearnPrompt(void)
static void CB2_ReturnToSummaryScreenFromNamingScreen(void)
{
SetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_NICKNAME, gStringVar2);
SetBoxMonData(GetSelectedBoxMonFromPcOrParty(), MON_DATA_NICKNAME, gStringVar2);
ShowPokemonSummaryScreen(SUMMARY_MODE_NORMAL, gPlayerParty, gSpecialVar_0x8004, gPlayerPartyCount - 1, gInitialSummaryScreenCallback);
}
static void CB2_ReturnToSummaryScreenFromNamingScreenBox(void)
{
SetBoxMonNickAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, gStringVar2);
ShowPokemonSummaryScreen(SUMMARY_MODE_BOX, GetBoxedMonPtr(gSpecialVar_MonBoxId, 0), gSpecialVar_MonBoxPos, IN_BOX_COUNT - 1, gInitialSummaryScreenCallback);
}
static void CB2_PssChangePokemonNickname(void)
{
GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_NICKNAME, gStringVar3);
GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_NICKNAME, gStringVar2);
DoNamingScreen(NAMING_SCREEN_NICKNAME, gStringVar2, GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_SPECIES, NULL),
GetMonGender(&gPlayerParty[gSpecialVar_0x8004]), GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_PERSONALITY, NULL),
CB2_ReturnToSummaryScreenFromNamingScreen);
}
static void CB2_PssChangeBoxPokemonNickname(void)
{
struct BoxPokemon *boxMon;
boxMon = GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos);
GetBoxMonData(boxMon, MON_DATA_NICKNAME, gStringVar3);
GetBoxMonData(boxMon, MON_DATA_NICKNAME, gStringVar2);
DoNamingScreen(NAMING_SCREEN_NICKNAME, gStringVar2, GetBoxMonData(boxMon, MON_DATA_SPECIES, NULL),
GetBoxMonGender(boxMon), GetBoxMonData(boxMon, MON_DATA_PERSONALITY, NULL),
CB2_ReturnToSummaryScreenFromNamingScreenBox);
ChangePokemonNicknameWithCallback(CB2_ReturnToSummaryScreenFromNamingScreen);
}

View File

@@ -46,6 +46,7 @@
#include "constants/contest.h"
#include "constants/items.h"
#include "constants/moves.h"
#include "constants/party_menu.h"
#include "constants/region_map_sections.h"
#include "constants/rgb.h"
#include "constants/songs.h"
@@ -2763,30 +2764,12 @@ static u32 TradeGetMultiplayerId(void)
return 0;
}
static void LoadTradeMonPic(u8 whichParty, u8 state)
static void LoadTradeMonPic(struct Pokemon *mon, u8 state)
{
int pos = 0;
struct Pokemon *mon = NULL;
u16 species = SPECIES_NONE;
u32 personality;
if (whichParty == TRADE_PLAYER)
{
if(gSpecialVar_MonBoxId == 0xFF)
mon = &gPlayerParty[gSelectedTradeMonPositions[TRADE_PLAYER]];
else
mon = &gEnemyParty[gSelectedTradeMonPositions[TRADE_PLAYER]];
pos = B_POSITION_OPPONENT_LEFT;
}
if (whichParty == TRADE_PARTNER)
{
mon = &gEnemyParty[gSelectedTradeMonPositions[TRADE_PARTNER] % PARTY_SIZE];
pos = B_POSITION_OPPONENT_RIGHT;
}
u32 species, personality;
u32 whichParty = state / 2;
species = GetMonData(mon, MON_DATA_SPECIES_OR_EGG);
switch (state)
switch (state % 2)
{
case 0:
personality = GetMonData(mon, MON_DATA_PERSONALITY);
@@ -2798,12 +2781,13 @@ static void LoadTradeMonPic(u8 whichParty, u8 state)
sTradeAnim->monPersonalities[whichParty] = personality;
break;
case 1:
SetMultiuseSpriteTemplateToPokemon(species, pos);
SetMultiuseSpriteTemplateToPokemon(species, whichParty * 2 + B_POSITION_OPPONENT_LEFT);
sTradeAnim->monSpriteIds[whichParty] = CreateSprite(&gMultiuseSpriteTemplate, 120, 60, 6);
gSprites[sTradeAnim->monSpriteIds[whichParty]].invisible = TRUE;
gSprites[sTradeAnim->monSpriteIds[whichParty]].callback = SpriteCallbackDummy;
break;
}
}
void CB2_LinkTrade(void)
@@ -2887,19 +2871,19 @@ void CB2_LinkTrade(void)
sTradeAnim->playerFinishStatus = 0;
sTradeAnim->partnerFinishStatus = 0;
sTradeAnim->scheduleLinkTransfer = 0;
LoadTradeMonPic(TRADE_PLAYER, 0);
LoadTradeMonPic(&gPlayerParty[gSelectedTradeMonPositions[TRADE_PLAYER]], 0);
gMain.state++;
break;
case 6:
LoadTradeMonPic(TRADE_PLAYER, 1);
LoadTradeMonPic(&gPlayerParty[gSelectedTradeMonPositions[TRADE_PLAYER]], 1);
gMain.state++;
break;
case 7:
LoadTradeMonPic(TRADE_PARTNER, 0);
LoadTradeMonPic(&gEnemyParty[gSelectedTradeMonPositions[TRADE_PARTNER] % PARTY_SIZE], 2);
gMain.state++;
break;
case 8:
LoadTradeMonPic(TRADE_PARTNER, 1);
LoadTradeMonPic(&gEnemyParty[gSelectedTradeMonPositions[TRADE_PARTNER] % PARTY_SIZE], 3);
LinkTradeDrawWindow();
gMain.state++;
break;
@@ -2973,17 +2957,24 @@ static void CB2_InitInGameTrade(void)
{
u8 otName[11];
struct Pokemon *playerMon;
if (gSpecialVar_0x8004 == PC_MON_CHOSEN)
playerMon = &gEnemyParty[TRADEMON_FROM_PC];
else
playerMon = &gPlayerParty[gSpecialVar_0x8004];
switch (gMain.state)
{
case 0:
//If not in the party then we're using ChooseBoxMon, a bit easier to chnage it into a Mon now and store in gEnemyParty
if(gSpecialVar_MonBoxId == 0xFF)
gSelectedTradeMonPositions[TRADE_PLAYER] = gSpecialVar_0x8005;
//If ChooseBoxMon points to a pc mon, we store it into gEnemyParty
if(gSpecialVar_0x8004 == PC_MON_CHOSEN)
{
gSelectedTradeMonPositions[TRADE_PLAYER] = TRADEMON_FROM_PC;
RemoveSelectedPcMon(&gEnemyParty[TRADEMON_FROM_PC]);
}
else
{
gSelectedTradeMonPositions[TRADE_PLAYER] = 1;
BoxMonToMon(&gPokemonStoragePtr->boxes[gSpecialVar_MonBoxId][gSpecialVar_0x8005], &gEnemyParty[1]);
ZeroBoxMonData(&gPokemonStoragePtr->boxes[gSpecialVar_MonBoxId][gSpecialVar_0x8005]);
gSelectedTradeMonPositions[TRADE_PLAYER] = gSpecialVar_0x8004;
}
gSelectedTradeMonPositions[TRADE_PARTNER] = PARTY_SIZE;
StringCopy(gLinkPlayers[0].name, gSaveBlock2Ptr->playerName);
@@ -3013,20 +3004,20 @@ static void CB2_InitInGameTrade(void)
gMain.state = 5;
break;
case 5:
LoadTradeMonPic(TRADE_PLAYER, 0);
LoadTradeMonPic(playerMon, 0);
gMain.state++;
break;
case 6:
LoadTradeMonPic(TRADE_PLAYER, 1);
LoadTradeMonPic(playerMon, 1);
gMain.state++;
break;
case 7:
LoadTradeMonPic(TRADE_PARTNER, 0);
LoadTradeMonPic(&gEnemyParty[0], 2);
ShowBg(0);
gMain.state++;
break;
case 8:
LoadTradeMonPic(TRADE_PARTNER, 1);
LoadTradeMonPic(&gEnemyParty[0], 3);
FillWindowPixelBuffer(0, PIXEL_FILL(15));
PutWindowTilemap(0);
CopyWindowToVram(0, COPYWIN_FULL);
@@ -3062,7 +3053,11 @@ static void CB2_InitInGameTrade(void)
static void UpdatePokedexForReceivedMon(u8 partyIdx)
{
struct Pokemon *mon = &gPlayerParty[partyIdx];
struct Pokemon *mon;
if (partyIdx == PC_MON_CHOSEN)
mon = &gEnemyParty[TRADEMON_FROM_PC];
else
mon = &gPlayerParty[partyIdx];
if (!GetMonData(mon, MON_DATA_IS_EGG))
{
@@ -3086,11 +3081,14 @@ static void TryEnableNationalDexFromLinkPartner(void)
static void TradeMons(u8 playerPartyIdx, u8 partnerPartyIdx)
{
u8 friendship;
struct Pokemon *playerMon, *partnerMon;
if (playerPartyIdx == PC_MON_CHOSEN)
playerMon = &gEnemyParty[TRADEMON_FROM_PC];
else
playerMon = &gPlayerParty[playerPartyIdx];
struct Pokemon *playerMon = &gPlayerParty[playerPartyIdx];
u16 playerMail = GetMonData(playerMon, MON_DATA_MAIL);
struct Pokemon *partnerMon = &gEnemyParty[partnerPartyIdx];
partnerMon = &gEnemyParty[partnerPartyIdx];
u16 partnerMail = GetMonData(partnerMon, MON_DATA_MAIL);
// The mail attached to the sent Pokémon no longer exists in your file.
@@ -3106,9 +3104,21 @@ static void TradeMons(u8 playerPartyIdx, u8 partnerPartyIdx)
SetMonData(playerMon, MON_DATA_FRIENDSHIP, &friendship);
if (partnerMail != MAIL_NONE)
GiveMailToMon(playerMon, &gTradeMail[partnerMail]);
{
if (playerPartyIdx == PC_MON_CHOSEN)
{
//TODO: add message explaining mail has been send to PC OR couldn't be saved
SaveMailToPC(&gTradeMail[partnerMail]);
TakeMailFromMon(playerMon);
}
else
{
GiveMailToMon(playerMon, &gTradeMail[partnerMail]);
}
}
UpdatePokedexForReceivedMon(playerPartyIdx);
if (playerPartyIdx == PC_MON_CHOSEN)
CopyMonToPC(playerMon);
if (gReceivedRemoteLinkPlayers)
TryEnableNationalDexFromLinkPartner();
}
@@ -3328,13 +3338,13 @@ static void BufferTradeSceneStrings(void)
}
else
{
ingameTrade = &sIngameTrades[gSpecialVar_0x8004];
ingameTrade = &sIngameTrades[gSpecialVar_0x8005];
StringCopy(gStringVar1, ingameTrade->otName);
StringCopy_Nickname(gStringVar3, ingameTrade->nickname);
if(gSpecialVar_MonBoxId == 0xFF)
GetMonData(&gPlayerParty[gSpecialVar_0x8005], MON_DATA_NICKNAME, name);
if(gSpecialVar_0x8004 == PC_MON_CHOSEN)
GetMonData(&gEnemyParty[TRADEMON_FROM_PC], MON_DATA_NICKNAME, name);
else
GetMonData(&gEnemyParty[1], MON_DATA_NICKNAME, name);
GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_NICKNAME, name);
StringCopy_Nickname(gStringVar2, name);
}
}
@@ -4358,23 +4368,19 @@ static bool8 DoTradeAnim_Wireless(void)
sTradeAnim->state++;
break;
case STATE_TRY_EVOLUTION: // Only if in-game trade, link trades use CB2_TryLinkTradeEvolution
if(gSpecialVar_MonBoxId == 0xFF)
TradeMons(gSpecialVar_0x8005, 0);
else
{
if(CalculatePartyCount(gPlayerParty) < PARTY_SIZE)
CopyMon(&gPlayerParty[CalculatePartyCount(gPlayerParty)],&gEnemyParty[0],100);
else
CopyMonToPC(&gEnemyParty[0]);
}
TradeMons(gSpecialVar_0x8004, 0);
gCB2_AfterEvolution = CB2_InGameTrade;
evoTarget = GetEvolutionTargetSpecies(&gPlayerParty[gSelectedTradeMonPositions[TRADE_PLAYER]], EVO_MODE_TRADE, ITEM_NONE, &gEnemyParty[0], NULL, CHECK_EVO);
struct Pokemon *canEvolveMon;
if (gSpecialVar_0x8004 == PC_MON_CHOSEN)
canEvolveMon = &gEnemyParty[TRADEMON_FROM_PC];
else
canEvolveMon = &gPlayerParty[gSpecialVar_0x8004];
evoTarget = GetEvolutionTargetSpecies(canEvolveMon, EVO_MODE_TRADE, ITEM_NONE, &gEnemyParty[0], NULL, CHECK_EVO);
if (evoTarget != SPECIES_NONE)
{
GetEvolutionTargetSpecies(&gPlayerParty[gSelectedTradeMonPositions[TRADE_PLAYER]], EVO_MODE_TRADE, ITEM_NONE, &gEnemyParty[0], NULL, DO_EVO);
TradeEvolutionScene(&gPlayerParty[gSelectedTradeMonPositions[TRADE_PLAYER]], evoTarget, sTradeAnim->monSpriteIds[TRADE_PARTNER], gSelectedTradeMonPositions[TRADE_PLAYER]);
GetEvolutionTargetSpecies(canEvolveMon, EVO_MODE_TRADE, ITEM_NONE, &gEnemyParty[0], NULL, DO_EVO);
TradeEvolutionScene(canEvolveMon, evoTarget, sTradeAnim->monSpriteIds[TRADE_PARTNER], gSpecialVar_0x8004);
}
sTradeAnim->state++;
break;
case STATE_FADE_OUT_END:
@@ -4536,7 +4542,7 @@ static void SpriteCB_BouncingPokeballArrive(struct Sprite *sprite)
u16 GetInGameTradeSpeciesInfo(void)
{
const struct InGameTrade *inGameTrade = &sIngameTrades[gSpecialVar_0x8004];
const struct InGameTrade *inGameTrade = &sIngameTrades[gSpecialVar_0x8005];
StringCopy(gStringVar1, GetSpeciesName(inGameTrade->requestedSpecies));
StringCopy(gStringVar2, GetSpeciesName(inGameTrade->species));
return inGameTrade->requestedSpecies;
@@ -4545,7 +4551,7 @@ u16 GetInGameTradeSpeciesInfo(void)
static void BufferInGameTradeMonName(void)
{
u8 nickname[max(32, POKEMON_NAME_BUFFER_SIZE)];
const struct InGameTrade *inGameTrade = &sIngameTrades[gSpecialVar_0x8004];
const struct InGameTrade *inGameTrade = &sIngameTrades[gSpecialVar_0x8005];
GetMonData(&gPlayerParty[gSpecialVar_0x8005], MON_DATA_NICKNAME, nickname);
StringCopy_Nickname(gStringVar1, nickname);
StringCopy(gStringVar2, GetSpeciesName(inGameTrade->species));
@@ -4554,11 +4560,8 @@ static void BufferInGameTradeMonName(void)
static void CreateInGameTradePokemonInternal(u8 whichPlayerMon, u8 whichInGameTrade)
{
const struct InGameTrade *inGameTrade = &sIngameTrades[whichInGameTrade];
u8 level;
if(gSpecialVar_MonBoxId == 0xFF)
level = GetMonData(&gPlayerParty[whichPlayerMon], MON_DATA_LEVEL);
else
level = GetBoxMonLevelAt(gSpecialVar_MonBoxId, whichPlayerMon);
struct BoxPokemon *boxmon = GetSelectedBoxMonFromPcOrParty();
u32 level = GetLevelFromBoxMonExp(boxmon);
struct Mail mail;
metloc_u8_t metLocation = METLOC_IN_GAME_TRADE;
@@ -4624,23 +4627,16 @@ static void GetInGameTradeMail(struct Mail *mail, const struct InGameTrade *trad
u16 GetTradeSpecies(void)
{
if(gSpecialVar_MonBoxId == 0xFF)
{
if (GetMonData(&gPlayerParty[gSpecialVar_0x8005], MON_DATA_IS_EGG))
return SPECIES_NONE;
return GetMonData(&gPlayerParty[gSpecialVar_0x8005], MON_DATA_SPECIES);
}
else
{
if (GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_0x8005, MON_DATA_IS_EGG))
return SPECIES_NONE;
return GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_0x8005, MON_DATA_SPECIES);
}
struct BoxPokemon *boxmon = GetSelectedBoxMonFromPcOrParty();
if (GetBoxMonData(boxmon, MON_DATA_IS_EGG))
return SPECIES_NONE;
u32 species = GetBoxMonData(boxmon, MON_DATA_SPECIES);
return species;
}
void CreateInGameTradePokemon(void)
{
CreateInGameTradePokemonInternal(gSpecialVar_0x8005, gSpecialVar_0x8004);
CreateInGameTradePokemonInternal(gSpecialVar_0x8004, gSpecialVar_0x8005);
}
static void CB2_UpdateLinkTrade(void)

View File

@@ -1534,26 +1534,28 @@ void TryPutSmartShopperOnAir(void)
void PutNameRaterShowOnTheAir(void)
{
TVShow *show;
struct BoxPokemon *boxmon;
InterviewBefore_NameRater();
if (gSpecialVar_Result != 1)
{
GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_NICKNAME, gStringVar1);
boxmon = GetSelectedBoxMonFromPcOrParty();
GetBoxMonData(boxmon, MON_DATA_NICKNAME, gStringVar1);
if (StringLength(gSaveBlock2Ptr->playerName) > 1 && StringLength(gStringVar1) > 1)
{
show = &gSaveBlock1Ptr->tvShows[sCurTVShowSlot];
show->nameRaterShow.kind = TVSHOW_NAME_RATER_SHOW;
show->nameRaterShow.active = TRUE;
show->nameRaterShow.species = GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_SPECIES);
show->nameRaterShow.species = GetBoxMonData(boxmon, MON_DATA_SPECIES);
show->nameRaterShow.random = Random() % 3;
show->nameRaterShow.random2 = Random() % 2;
show->nameRaterShow.randomSpecies = GetRandomDifferentSpeciesSeenByPlayer(show->nameRaterShow.species);
StringCopy(show->nameRaterShow.trainerName, gSaveBlock2Ptr->playerName);
GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_NICKNAME10, show->nameRaterShow.pokemonName);
GetBoxMonData(boxmon, MON_DATA_NICKNAME10, show->nameRaterShow.pokemonName);
StripExtCtrlCodes(show->nameRaterShow.pokemonName);
StorePlayerIdInNormalShow(show);
show->nameRaterShow.language = gGameLanguage;
show->nameRaterShow.pokemonNameLanguage = GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_LANGUAGE);
show->nameRaterShow.pokemonNameLanguage = GetBoxMonData(boxmon, MON_DATA_LANGUAGE);
}
}
}
@@ -3262,7 +3264,7 @@ bool8 IsTVShowAlreadyInQueue(void)
bool8 TryPutNameRaterShowOnTheAir(void)
{
GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_NICKNAME, gStringVar1);
GetBoxMonData(GetSelectedBoxMonFromPcOrParty(), MON_DATA_NICKNAME, gStringVar1);
// Nickname wasnt changed
if (!StringCompare(gStringVar3, gStringVar1))
@@ -3272,61 +3274,31 @@ bool8 TryPutNameRaterShowOnTheAir(void)
return TRUE;
}
void ChangePokemonNickname(void)
{
void ChangePokemonNickname_CB(void);
GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_NICKNAME, gStringVar3);
GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_NICKNAME, gStringVar2);
DoNamingScreen(NAMING_SCREEN_NICKNAME, gStringVar2, GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_SPECIES), GetMonGender(&gPlayerParty[gSpecialVar_0x8004]), GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_PERSONALITY), ChangePokemonNickname_CB);
}
void ChangePokemonNickname_CB(void)
{
SetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_NICKNAME, gStringVar2);
CB2_ReturnToFieldContinueScriptPlayMapMusic();
}
void ChangeBoxPokemonNickname(void)
{
struct BoxPokemon *boxMon;
boxMon = GetBoxedMonPtr(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos);
GetBoxMonData(boxMon, MON_DATA_NICKNAME, gStringVar3);
GetBoxMonData(boxMon, MON_DATA_NICKNAME, gStringVar2);
DoNamingScreen(NAMING_SCREEN_NICKNAME, gStringVar2, GetBoxMonData(boxMon, MON_DATA_SPECIES), GetBoxMonGender(boxMon), GetBoxMonData(boxMon, MON_DATA_PERSONALITY), ChangeBoxPokemonNickname_CB);
}
static void ChangeBoxPokemonNickname_CB(void)
{
SetBoxMonNickAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, gStringVar2);
SetBoxMonData(GetSelectedBoxMonFromPcOrParty(), MON_DATA_NICKNAME, gStringVar2);
CB2_ReturnToFieldContinueScriptPlayMapMusic();
}
void ChangePokemonNickname(void)
{
ChangePokemonNicknameWithCallback(ChangeBoxPokemonNickname_CB);
}
void BufferMonNickname(void)
{
if(gSpecialVar_MonBoxId == 0xFF)
GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_NICKNAME, gStringVar1);
else
GetBoxMonNickAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, gStringVar1);
StringGet_Nickname(gStringVar1);
struct BoxPokemon *boxmon = GetSelectedBoxMonFromPcOrParty();
GetBoxMonData(boxmon, MON_DATA_NICKNAME, gStringVar1);
//StringGet_Nickname(gStringVar1);
}
void IsMonOTIDNotPlayers(void)
{
if(gSpecialVar_MonBoxId == 0xFF){
if (GetPlayerIDAsU32() == GetMonData(&gPlayerParty[gSpecialVar_0x8004], MON_DATA_OT_ID))
gSpecialVar_Result = FALSE;
else
gSpecialVar_Result = TRUE;
}
else{
if (GetPlayerIDAsU32() == GetBoxMonDataAt(gSpecialVar_MonBoxId, gSpecialVar_MonBoxPos, MON_DATA_OT_ID))
gSpecialVar_Result = FALSE;
else
gSpecialVar_Result = TRUE;
}
struct BoxPokemon *boxmon = GetSelectedBoxMonFromPcOrParty();
if (GetPlayerIDAsU32() == GetBoxMonData(boxmon, MON_DATA_OT_ID))
gSpecialVar_Result = FALSE;
else
gSpecialVar_Result = TRUE;
}
static u8 GetTVGroupByShowId(u8 kind)

View File

@@ -121,8 +121,6 @@ def prepare_output(all_learnables: dict[str, set[str]], tms: list[str], tutors:
return new
def prepare_header(h_align: int, tmshms: list[str], tutors: list[str], universals: list[str]) -> str:
universals_title = "Near-universal moves found in data/special_movesets.json:"
tmhm_title = "TM/HM moves found in \"include/constants/tms_hms.h\":"

View File

@@ -10,7 +10,9 @@ import typing
CONFIG_ENABLED_PAT = re.compile(r"#define P_LEARNSET_HELPER_TEACHABLE\s+(?P<cfg_val>[^ ]*)")
INCFILE_HAS_TUTOR_PAT = re.compile(r"special ChooseMonForMoveTutor")
INCFILE_MOVE_PAT = re.compile(r"setvar VAR_ITEM_ID, (MOVE_.*)")
INCFILE_HAS_TUTOR_PAT2 = re.compile(r"chooseboxmon SELECT_PC_MON_MOVE_TUTOR")
INCFILE_MOVE_PAT = re.compile(r"setvar VAR_0x8005, (MOVE_[A-Z_]*)")
INCFILE_MOVE_PAT2 = re.compile(r"move_tutor (MOVE_[A-Z_]*)")
def enabled() -> bool:
"""
@@ -29,12 +31,15 @@ def extract_repo_tutors() -> typing.Generator[str, None, None]:
for inc_fname in chain(glob.glob("./data/scripts/*.inc"), glob.glob("./data/maps/*/scripts.inc")):
with open(inc_fname, "r") as inc_fp:
incfile = inc_fp.read()
if not INCFILE_HAS_TUTOR_PAT.search(incfile):
if not INCFILE_HAS_TUTOR_PAT.search(incfile) and not INCFILE_HAS_TUTOR_PAT2.search(incfile):
continue
for move in INCFILE_MOVE_PAT.finditer(incfile):
yield move.group(1)
for move in INCFILE_MOVE_PAT2.finditer(incfile):
yield move.group(1)
def dump_output(file, data):
with open(file, "w") as fp:
fp.write(data)