Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Added support for XY's Sky Battles #2950

Merged
merged 49 commits into from
Nov 26, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
49 commits
Select commit Hold shift + click to select a range
50754be
Original implementation from Phlayne
pkmnsnfrn Apr 24, 2023
4deaf37
Moved Sky Battle Flag / Var into a config
pkmnsnfrn Apr 24, 2023
8cbfca8
Optimized existing code and fixed existing bugs
pkmnsnfrn Apr 25, 2023
a10c1bd
Added compatibility for Gen7+
pkmnsnfrn Apr 25, 2023
1c3e61b
Commented out Volt Crash from banned moves
pkmnsnfrn Apr 25, 2023
3f82f7a
Merge branch 'upcoming' of https://github.com/rh-hideout/pokeemerald-…
pkmnsnfrn Apr 25, 2023
35c9e94
Cleaned up debug scripts from testing
pkmnsnfrn Apr 25, 2023
146e8a0
Fixed bug where player did not white out even if they had no healthy …
pkmnsnfrn Apr 25, 2023
db39306
Removed extra include from src/field_specials.c
pkmnsnfrn Apr 25, 2023
7b44742
Merged in most recent changes from upcoming
pkmnsnfrn Apr 27, 2023
f7e8a52
Added FLAG_DISABLED_IN_SKY_BATTLE
pkmnsnfrn Apr 27, 2023
8e2888c
Changed DoesSkyBattleCancelCurrentMove to look at move flags
pkmnsnfrn Apr 27, 2023
1da1765
Fixed alignment and spacing in battle_moves.h
pkmnsnfrn Apr 27, 2023
60a6a57
Added FLAG_DISABLED_IN_SKY_BATTLE to Sticky Web
pkmnsnfrn Apr 27, 2023
4aa9156
Added FLAG_DISABLED_IN_SKY_BATTLE to Steel Roller
pkmnsnfrn Apr 27, 2023
d2ada77
Disabled the ability to change Battle Terrain when Sky Battle is happ…
pkmnsnfrn Apr 27, 2023
7a6abe2
Fixed bug with SKY_BATTLE_STRICT_MECHANICS where conditions were not …
pkmnsnfrn Apr 28, 2023
2afa9ca
Merge branch 'upcoming' of https://github.com/rh-hideout/pokeemerald-…
pkmnsnfrn Apr 29, 2023
f3584a0
Add rulesVariants to the BattleStruct
pkmnsnfrn Apr 29, 2023
aec9817
Replaced B_FLAG_SKY_BATTLE checks with rulesVariants.skyBattle checks
pkmnsnfrn Apr 29, 2023
3b0626a
Fixed debug script
pkmnsnfrn Apr 29, 2023
95c4eaf
Reverted include/config/battle.h
pkmnsnfrn Apr 29, 2023
2755fb5
Fixed spacing and placement of functions
pkmnsnfrn Apr 29, 2023
2dd238f
Fixed debug script omission
pkmnsnfrn Apr 29, 2023
1cb676f
Merge branch 'upcoming' into SkyBattle
pkmnsnfrn Apr 30, 2023
cca1b41
Added FLAG_DISABLED_IN_SKY_BATTLE to Psychic Terrain
pkmnsnfrn May 3, 2023
be1d562
Merged in most recent expansion
pkmnsnfrn May 3, 2023
2c88a92
Merge branch 'SkyBattle' of https://github.com/PokemonSanFran/pokeeme…
pkmnsnfrn May 3, 2023
fe50f1e
Merge branch 'upcoming' into SkyBattle
pkmnsnfrn Jun 30, 2023
e3814e1
Addressed DizzyEgg PR feedback
pkmnsnfrn Jun 30, 2023
d01ead1
Forgot a file in last commit
pkmnsnfrn Jun 30, 2023
d002dab
Merged in upcoming
pkmnsnfrn Jul 5, 2023
260d171
Merge branch 'upcoming' of https://github.com/rh-hideout/pokeemerald-…
pkmnsnfrn Jul 8, 2023
dc3a6bd
Addressed feedback from DizzyEggg
pkmnsnfrn Jul 8, 2023
be205f8
Address Lunos' PR feedback
pkmnsnfrn Jul 9, 2023
f17e2d6
Update specials.inc
pkmnsnfrn Jul 9, 2023
eb0a034
Fixed spacing
pkmnsnfrn Jul 11, 2023
1a2877b
Merge branch 'upcoming' into SkyBattle
pkmnsnfrn Jul 18, 2023
9ef212f
Apply suggestions from code review
pkmnsnfrn Jul 19, 2023
dd2eb71
Updated skyBattleBanned and HandleBattleVariantEndParty to use correc…
pkmnsnfrn Jul 19, 2023
c674eef
Merge branch 'upcoming' of https://github.com/rh-hideout/pokeemerald-…
pkmnsnfrn Sep 24, 2023
2d0aa40
Removed STRICT_MOVES and STRICT_MECHANICS
pkmnsnfrn Sep 24, 2023
e5e3746
Fixed minor spacing issues with merge
pkmnsnfrn Sep 24, 2023
9444255
Merged with upcoming
pkmnsnfrn Nov 23, 2023
5f6a1b0
Merged in upcoming
pkmnsnfrn Nov 23, 2023
5da6117
Merge branch 'upcoming' into SkyBattle
pkmnsnfrn Nov 23, 2023
fca1d47
Implemented feedback from Jasper
pkmnsnfrn Nov 24, 2023
ea0fc3f
Merge branch 'upcoming' into SkyBattle
pkmnsnfrn Nov 24, 2023
67e4921
Merge branch 'upcoming' into SkyBattle
pkmnsnfrn Nov 26, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
13 changes: 13 additions & 0 deletions data/scripts/debug.inc
Original file line number Diff line number Diff line change
Expand Up @@ -95,6 +95,19 @@ Debug_BoxFilledMessage::
Debug_BoxFilledMessage_Text:
.string "Storage boxes filled!$"

Debug_FlagsAndVarNotSetBattleConfigMessage::
lockall
message Debug_FlagsAndVarNotSetBattleConfigMessage_Text
waitmessage
waitbuttonpress
releaseall
end

Debug_FlagsAndVarNotSetBattleConfigMessage_Text:
.string "Feature unavailable! Please define a\n"
.string "usable flag and a usable var in:\l"
.string "'include/config/battle.h'!$"

Debug_EventScript_Script_1::
end

Expand Down
1 change: 1 addition & 0 deletions data/specials.inc
Original file line number Diff line number Diff line change
Expand Up @@ -539,3 +539,4 @@ gSpecials::
def_special GetNumberSprayStrength
def_special GetSprayId
def_special GetLastUsedSprayType
def_special TrySkyBattle
1 change: 1 addition & 0 deletions include/battle.h
Original file line number Diff line number Diff line change
Expand Up @@ -731,6 +731,7 @@ struct BattleStruct
u32 aiDelayFrames; // Number of frames it took to choose an action.
bool8 transformZeroToHero[PARTY_SIZE][NUM_BATTLE_SIDES];
u8 pledgeMove:1;
bool8 isSkyBattle:1;
};

// The palaceFlags member of struct BattleStruct contains 1 flag per move to indicate which moves the AI should consider,
Expand Down
2 changes: 2 additions & 0 deletions include/battle_script_commands.h
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ s32 CalcCritChanceStage(u32 battlerAtk, u32 battlerDef, u32 move, bool32 recordA
s32 GetCritHitChance(s32 critChanceIndex);
u32 GetTotalAccuracy(u32 battlerAtk, u32 battlerDef, u32 move, u32 atkAbility, u32 defAbility, u32 atkHoldEffect, u32 defHoldEffect);
u8 GetBattlerTurnOrderNum(u8 battlerId);
bool32 NoAliveMonsForPlayer(void);
bool32 NoAliveMonsForEitherParty(void);
void SetMoveEffect(bool32 primary, u32 certain);
bool32 CanBattlerSwitch(u32 battlerId);
Expand All @@ -52,6 +53,7 @@ void StealTargetItem(u8 battlerStealer, u8 battlerItem);
u8 GetCatchingBattler(void);
u32 GetHighestStatId(u32 battlerId);
bool32 ProteanTryChangeType(u32 battler, u32 ability, u32 move, u32 moveType);
bool32 IsMoveNotAllowedInSkyBattles(u32 move);
bool32 DoSwitchInAbilitiesItems(u32 battlerId);
u8 GetFirstFaintedPartyIndex(u8 battlerId);
bool32 IsMoveAffectedByParentalBond(u32 move, u32 battler);
Expand Down
2 changes: 2 additions & 0 deletions include/battle_util.h
Original file line number Diff line number Diff line change
Expand Up @@ -249,5 +249,7 @@ bool32 AreBattlersOfOppositeGender(u32 battler1, u32 battler2);
bool32 AreBattlersOfSameGender(u32 battler1, u32 battler2);
u32 CalcSecondaryEffectChance(u32 battler, u8 secondaryEffectChance, u16 moveEffect);
u8 GetBattlerType(u32 battler, u8 typeIndex);
bool8 CanMonParticipateInSkyBattle(struct Pokemon *mon);
bool8 IsMonBannedFromSkyBattles(u16 species);

#endif // GUARD_BATTLE_UTIL_H
6 changes: 6 additions & 0 deletions include/config/battle.h
Original file line number Diff line number Diff line change
Expand Up @@ -170,6 +170,12 @@
#define VAR_TERRAIN 0 // If this var has a value, assigning a STATUS_FIELD_xx_TERRAIN to it before battle causes the battle to start with that terrain active
#define B_VAR_WILD_AI_FLAGS 0 // If not 0, you can use this var to add to default wild AI flags. NOT usable with flags above (1 << 15)

// Sky Battles
#define B_FLAG_SKY_BATTLE 0 // If this flag has a value, the player will be able to engage in scripted Sky Battles.
#define B_VAR_SKY_BATTLE 0 // If this var has a value, the game will remember the positions of Pokémon used in Sky Battles.

#define B_SKY_BATTLE_STRICT_ELIGIBILITY FALSE //If TRUE, Sky Battles will use the eligibility from Pokémon XY. If FALSE, all Flying-types or Pokémon with Levitate are allowed.
Bassoonian marked this conversation as resolved.
Show resolved Hide resolved

// Flag and Var settings
#define B_RESET_FLAGS_VARS_AFTER_WHITEOUT TRUE // If TRUE, Overworld_ResetBattleFlagsAndVars will reset battle-related Flags and Vars when the player whites out.

Expand Down
1 change: 1 addition & 0 deletions include/debug.h
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
#define GUARD_DEBUG_H

void Debug_ShowMainMenu(void);
extern const u8 Debug_FlagsAndVarNotSetBattleConfigMessage[];

extern EWRAM_DATA bool8 gIsDebugBattle;
extern EWRAM_DATA u32 gDebugAIFlags;
Expand Down
1 change: 1 addition & 0 deletions include/field_specials.h
Original file line number Diff line number Diff line change
Expand Up @@ -31,5 +31,6 @@ bool8 UsedPokemonCenterWarp(void);
void ResetFanClub(void);
bool8 ShouldShowBoxWasFullMessage(void);
void SetPCBoxToSendMon(u8 boxId);
void PreparePartyForSkyBattle(void);

#endif // GUARD_FIELD_SPECIALS_H
1 change: 1 addition & 0 deletions include/pokemon.h
Original file line number Diff line number Diff line change
Expand Up @@ -393,6 +393,7 @@ struct BattleMove
u32 instructBanned:1;
u32 encoreBanned:1;
u32 parentalBondBanned:1;
u32 skyBattleBanned:1;
};

#define SPINDA_SPOT_WIDTH 16
Expand Down
18 changes: 14 additions & 4 deletions src/battle_script_commands.c
Original file line number Diff line number Diff line change
Expand Up @@ -1256,6 +1256,11 @@ bool32 ProteanTryChangeType(u32 battler, u32 ability, u32 move, u32 moveType)
return FALSE;
}

bool32 IsMoveNotAllowedInSkyBattles(u32 move)
{
return ((gBattleStruct->isSkyBattle) && (gBattleMoves[gCurrentMove].skyBattleBanned));
}

pkmnsnfrn marked this conversation as resolved.
Show resolved Hide resolved
static void Cmd_attackcanceler(void)
{
CMD_ARGS();
Expand Down Expand Up @@ -1363,9 +1368,10 @@ static void Cmd_attackcanceler(void)
}

gHitMarker |= HITMARKER_OBEYS;
// Check if no available target present on the field.
if (NoTargetPresent(gBattlerAttacker, gCurrentMove)
// Check if no available target present on the field or if Sky Battles ban the move
if ((NoTargetPresent(gBattlerAttacker, gCurrentMove)
&& (!gBattleMoves[gCurrentMove].twoTurnMove || (gBattleMons[gBattlerAttacker].status2 & STATUS2_MULTIPLETURNS)))
|| (IsMoveNotAllowedInSkyBattles(gCurrentMove)))
{
if (gBattleMoves[gCurrentMove].effect == EFFECT_FLING) // Edge case for removing a mon's item when there is no target available after using Fling.
gBattlescriptCurrInstr = BattleScript_FlingFailConsumeItem;
Expand Down Expand Up @@ -3595,7 +3601,11 @@ void SetMoveEffect(bool32 primary, u32 certain)
{
gBattleCommunication[MULTISTRING_CHOOSER] = B_MSG_SPIKESSCATTERED;
BattleScriptPush(gBattlescriptCurrInstr + 1);
gBattlescriptCurrInstr = BattleScript_SpikesActivates;

if (gBattleStruct->isSkyBattle)
gBattlescriptCurrInstr++;
else
gBattlescriptCurrInstr = BattleScript_SpikesActivates;
}
break;
case MOVE_EFFECT_TRIPLE_ARROWS:
Expand Down Expand Up @@ -4324,7 +4334,7 @@ static bool32 NoAliveMonsForPlayerAndPartner(void)
return (HP_count == 0);
}

static bool32 NoAliveMonsForPlayer(void)
bool32 NoAliveMonsForPlayer(void)
{
u32 i;
u32 HP_count = 0;
Expand Down
30 changes: 29 additions & 1 deletion src/battle_setup.c
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
#include "global.h"
#include "battle.h"
#include "load_save.h"
#include "battle_setup.h"
#include "battle_transition.h"
#include "main.h"
Expand Down Expand Up @@ -81,6 +82,8 @@ static void TryUpdateGymLeaderRematchFromTrainer(void);
static void CB2_GiveStarter(void);
static void CB2_StartFirstBattle(void);
static void CB2_EndFirstBattle(void);
static void SaveChangesToPlayerParty(void);
static void HandleBattleVariantEndParty(void);
static void CB2_EndTrainerBattle(void);
static bool32 IsPlayerDefeated(u32 battleOutcome);
static u16 GetRematchTrainerId(u16 trainerId);
Expand Down Expand Up @@ -1380,15 +1383,40 @@ void BattleSetup_StartTrainerBattle_Debug(void)
ScriptContext_Stop();
}

static void SaveChangesToPlayerParty(void)
{
u8 i = 0, j = 0;
u8 participatedPokemon = VarGet(B_VAR_SKY_BATTLE);
for (i = 0; i < PARTY_SIZE; i++)
{
if ((participatedPokemon >> i & 1) == 1)
{
gSaveBlock1Ptr->playerParty[i] = gPlayerParty[j];
j++;
}
}
}

static void HandleBattleVariantEndParty(void)
{
if (B_FLAG_SKY_BATTLE == 0 || !FlagGet(B_FLAG_SKY_BATTLE))
return;
SaveChangesToPlayerParty();
LoadPlayerParty();
FlagClear(B_FLAG_SKY_BATTLE);
}

static void CB2_EndTrainerBattle(void)
{
HandleBattleVariantEndParty();

if (gTrainerBattleOpponent_A == TRAINER_SECRET_BASE)
{
SetMainCallback2(CB2_ReturnToFieldContinueScriptPlayMapMusic);
}
else if (IsPlayerDefeated(gBattleOutcome) == TRUE)
{
if (InBattlePyramid() || InTrainerHillChallenge())
if (InBattlePyramid() || InTrainerHillChallenge() || (!NoAliveMonsForPlayer()))
SetMainCallback2(CB2_ReturnToFieldContinueScriptPlayMapMusic);
else
SetMainCallback2(CB2_WhiteOut);
Expand Down
53 changes: 52 additions & 1 deletion src/battle_util.c
Original file line number Diff line number Diff line change
Expand Up @@ -4095,7 +4095,7 @@ bool32 TryChangeBattleWeather(u32 battler, u32 weatherEnumId, bool32 viaAbility)

static bool32 TryChangeBattleTerrain(u32 battler, u32 statusFlag, u8 *timer)
{
if (!(gFieldStatuses & statusFlag))
if ((!(gFieldStatuses & statusFlag) && (!gBattleStruct->isSkyBattle)))
{
gFieldStatuses &= ~(STATUS_FIELD_MISTY_TERRAIN | STATUS_FIELD_GRASSY_TERRAIN | STATUS_FIELD_ELECTRIC_TERRAIN | STATUS_FIELD_PSYCHIC_TERRAIN);
gFieldStatuses |= statusFlag;
Expand Down Expand Up @@ -5756,6 +5756,7 @@ u32 AbilityBattleEffects(u32 caseID, u32 battler, u32 ability, u32 special, u32
break;
case ABILITY_TOXIC_DEBRIS:
if (!(gMoveResultFlags & MOVE_RESULT_NO_EFFECT)
&& (!gBattleStruct->isSkyBattle)
&& !gProtectStructs[gBattlerAttacker].confusionSelfDmg
&& IS_MOVE_PHYSICAL(gCurrentMove)
&& TARGET_TURN_DAMAGED
Expand Down Expand Up @@ -11267,6 +11268,56 @@ bool32 IsGen6ExpShareEnabled(void)
#endif
}

bool8 CanMonParticipateInSkyBattle(struct Pokemon *mon)
{
u16 species = GetMonData(mon, MON_DATA_SPECIES);
u16 monAbilityNum = GetMonData(mon, MON_DATA_ABILITY_NUM, NULL);

bool8 hasLevitateAbility = gSpeciesInfo[species].abilities[monAbilityNum] == ABILITY_LEVITATE;
bool8 isFlyingType = gSpeciesInfo[species].types[0] == TYPE_FLYING || gSpeciesInfo[species].types[1] == TYPE_FLYING;
bool8 monIsValidAndNotEgg = GetMonData(mon, MON_DATA_SANITY_HAS_SPECIES) && !GetMonData(mon, MON_DATA_IS_EGG);

if (monIsValidAndNotEgg)
{
if ((hasLevitateAbility || isFlyingType) && !IsMonBannedFromSkyBattles(species))
return TRUE;
}
return FALSE;
}

bool8 IsMonBannedFromSkyBattles(u16 species)
{
switch (species)
{
#if B_SKY_BATTLE_STRICT_ELIGIBILITY == TRUE
case SPECIES_SPEAROW:
case SPECIES_FARFETCHD:
case SPECIES_DODUO:
case SPECIES_DODRIO:
case SPECIES_HOOTHOOT:
case SPECIES_NATU:
case SPECIES_MURKROW:
case SPECIES_DELIBIRD:
case SPECIES_TAILLOW:
case SPECIES_STARLY:
case SPECIES_CHATOT:
case SPECIES_SHAYMIN:
case SPECIES_PIDOVE:
case SPECIES_ARCHEN:
case SPECIES_DUCKLETT:
case SPECIES_RUFFLET:
case SPECIES_VULLABY:
case SPECIES_FLETCHLING:
case SPECIES_HAWLUCHA:
case SPECIES_ROWLET:
case SPECIES_PIKIPEK:
#endif
case SPECIES_EGG:
return TRUE;
default:
return FALSE;
}
}

u8 GetBattlerType(u32 battler, u8 typeIndex)
{
Expand Down
4 changes: 4 additions & 0 deletions src/battle_util2.c
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,10 @@ void AllocateBattleResources(void)

gBattleStruct = AllocZeroed(sizeof(*gBattleStruct));

#if B_FLAG_SKY_BATTLE
gBattleStruct->isSkyBattle = FlagGet(B_FLAG_SKY_BATTLE);
#endif

gBattleResources = AllocZeroed(sizeof(*gBattleResources));
gBattleResources->secretBase = AllocZeroed(sizeof(*gBattleResources->secretBase));
gBattleResources->flags = AllocZeroed(sizeof(*gBattleResources->flags));
Expand Down