From f3be5ad22dd06f97c9d0400e18917496ad4ab3e1 Mon Sep 17 00:00:00 2001 From: DizzyEggg Date: Wed, 18 Jul 2018 22:07:48 +0200 Subject: [PATCH] Do new battler end turn effects. --- data/battle_scripts_1.s | 26 +++++ include/battle.h | 4 + include/battle_scripts.h | 5 + include/battle_util.h | 2 +- include/constants/battle.h | 3 + include/constants/battle_string_ids.h | 15 ++- src/battle_main.c | 2 +- src/battle_message.c | 28 +++++ src/battle_util.c | 153 +++++++++++++++++++++----- 9 files changed, 209 insertions(+), 29 deletions(-) diff --git a/data/battle_scripts_1.s b/data/battle_scripts_1.s index a777bef1f8..96479fd34c 100644 --- a/data/battle_scripts_1.s +++ b/data/battle_scripts_1.s @@ -3588,11 +3588,17 @@ BattleScript_WishButFullHp:: BattleScript_IngrainTurnHeal:: playanimation BS_ATTACKER, B_ANIM_INGRAIN_HEAL, NULL printstring STRINGID_PKMNABSORBEDNUTRIENTS +BattleScript_TurnHeal: waitmessage 0x40 orword gHitMarker, HITMARKER_IGNORE_SUBSTITUTE healthbarupdate BS_ATTACKER datahpupdate BS_ATTACKER end2 + +BattleScript_AquaRingHeal:: + playanimation BS_ATTACKER, B_ANIM_INGRAIN_HEAL, NULL + printstring STRINGID_AQUARINGHEAL + goto BattleScript_TurnHeal BattleScript_PrintMonIsRooted:: pause 0x20 @@ -3862,6 +3868,26 @@ BattleScript_YawnMakesAsleep:: waitstate makevisible BS_EFFECT_BATTLER end2 + +BattleScript_EmbargoEndTurn:: + printstring STRINGID_EMBARGOENDS + waitmessage 0x40 + end2 + +BattleScript_MagnetRiseEndTurn:: + printstring STRINGID_MAGNETRISEENDS + waitmessage 0x40 + end2 + +BattleScript_TelekinesisEndTurn:: + printstring STRINGID_TELEKINESISENDS + waitmessage 0x40 + end2 + +BattleScript_HealBlockEndTurn:: + printstring STRINGID_HEALBLOCKENDS + waitmessage 0x40 + end2 BattleScript_MoveEffectPoison:: statusanimation BS_EFFECT_BATTLER diff --git a/include/battle.h b/include/battle.h index 9bee3a6826..6c91466a82 100644 --- a/include/battle.h +++ b/include/battle.h @@ -173,6 +173,10 @@ struct DisableStruct /*0x19*/ u8 rechargeCounter; /*0x1A*/ u8 autonomizeCount; /*0x1B*/ u8 slowStartTimer; + u8 embargoTimer; + u8 magnetRiseTimer; + u8 telekinesisTimer; + u8 healBlockTimer; }; struct ProtectStruct diff --git a/include/battle_scripts.h b/include/battle_scripts.h index ffd9996602..febe816235 100644 --- a/include/battle_scripts.h +++ b/include/battle_scripts.h @@ -286,5 +286,10 @@ extern const u8 BattleScript_ActionWatchesCarefully[]; extern const u8 BattleScript_ActionGetNear[]; extern const u8 BattleScript_ActionThrowPokeblock[]; extern const u8 BattleScript_82DBEE3[]; +extern const u8 BattleScript_EmbargoEndTurn[]; +extern const u8 BattleScript_MagnetRiseEndTurn[]; +extern const u8 BattleScript_TelekinesisEndTurn[]; +extern const u8 BattleScript_HealBlockEndTurn[]; +extern const u8 BattleScript_AquaRingHeal[]; #endif // GUARD_BATTLE_SCRIPTS_H diff --git a/include/battle_util.h b/include/battle_util.h index 35f4546523..3032009e72 100644 --- a/include/battle_util.h +++ b/include/battle_util.h @@ -57,7 +57,7 @@ u8 CheckMoveLimitations(u8 battlerId, u8 unusableMoves, u8 check); bool8 AreAllMovesUnusable(void); u8 GetImprisonedMovesCount(u8 battlerId, u16 move); u8 UpdateTurnCounters(void); -u8 TurnBasedEffects(void); +u8 DoBattlerEndTurnEffects(void); bool8 HandleWishPerishSongOnTurnEnd(void); bool8 HandleFaintedMonActions(void); void TryClearRageStatuses(void); diff --git a/include/constants/battle.h b/include/constants/battle.h index 80ed2b7e23..045fa2ecc0 100644 --- a/include/constants/battle.h +++ b/include/constants/battle.h @@ -153,6 +153,9 @@ #define STATUS3_TELEKINESIS 0x800000 #define STATUS3_UNBURDEN 0x1000000 #define STATUS3_MIRACLE_EYED 0x2000000 +#define STATUS3_MAGNET_RISE 0x4000000 +#define STATUS3_HEAL_BLOCK 0x8000000 +#define STATUS3_AQUA_RING 0x10000000 #define STATUS3_SEMI_INVULNERABLE (STATUS3_UNDERGROUND | STATUS3_ON_AIR | STATUS3_UNDERWATER) // Not really sure what a "hitmarker" is. diff --git a/include/constants/battle_string_ids.h b/include/constants/battle_string_ids.h index 300ea9e404..9cd3cf4005 100644 --- a/include/constants/battle_string_ids.h +++ b/include/constants/battle_string_ids.h @@ -1,7 +1,7 @@ #ifndef GUARD_CONSTANTS_BATTLE_STRING_IDS_H #define GUARD_CONSTANTS_BATTLE_STRING_IDS_H -#define BATTLESTRINGS_COUNT 420 +#define BATTLESTRINGS_COUNT 433 #define BATTLESTRINGS_ID_ADDER 12 // all battlestrings have its ID + 12, because first 5 are reserved @@ -434,5 +434,18 @@ #define STRINGID_POSTPONETARGETMOVE 429 #define STRINGID_REFLECTTARGETSTYPE 430 #define STRINGID_TRANSFERHELDITEM 431 +#define STRINGID_EMBARGOENDS 432 +#define STRINGID_MAGNETRISEENDS 433 +#define STRINGID_HEALBLOCKENDS 434 +#define STRINGID_TELEKINESISENDS 435 +#define STRINGID_TAILWINDENDS 436 +#define STRINGID_LUCKYCHANTENDS 437 +#define STRINGID_TRICKROOMENDS 438 +#define STRINGID_WONDERROOMENDS 439 +#define STRINGID_MAGICROOMENDS 440 +#define STRINGID_MUDSPORTENDS 441 +#define STRINGID_WATERSPORTENDS 442 +#define STRINGID_GRAVITYENDS 443 +#define STRINGID_AQUARINGHEAL 444 #endif // GUARD_CONSTANTS_BATTLE_STRING_IDS_H diff --git a/src/battle_main.c b/src/battle_main.c index 4e67d00020..9453bc184a 100644 --- a/src/battle_main.c +++ b/src/battle_main.c @@ -3968,7 +3968,7 @@ void BattleTurnPassed(void) { if (UpdateTurnCounters()) return; - if (TurnBasedEffects()) + if (DoBattlerEndTurnEffects()) return; } if (HandleFaintedMonActions()) diff --git a/src/battle_message.c b/src/battle_message.c index d4d038315b..574406165f 100644 --- a/src/battle_message.c +++ b/src/battle_message.c @@ -574,6 +574,21 @@ static const u8 sText_PostponeTargetMove[] =_("{B_DEF_NAME_WITH_PREFIX}’s move static const u8 sText_ReflectTargetsType[] =_("{B_ATK_NAME_WITH_PREFIX}’s type\nchanged to match the {B_DEF_NAME_WITH_PREFIX}’s!"); static const u8 sText_TransferHeldItem[] =_("{B_DEF_NAME_WITH_PREFIX} recieved {B_LAST_ITEM}\nfrom {B_ATK_NAME_WITH_PREFIX}"); +// These strings are currently placeholders, to be fixed. +static const u8 sText_EmbargoEnds[] = _(""); +static const u8 sText_MagnetRiseEnds[] = _(""); +static const u8 sText_HealBlockEnds[] = _(""); +static const u8 sText_TelekinesisEnds[] = _(""); +static const u8 sText_TailwindEnds[] = _(""); +static const u8 sText_LuckyChantEnds[] = _(""); +static const u8 sText_TrickRoomEnds[] = _(""); +static const u8 sText_WonderRoomEnds[] = _(""); +static const u8 sText_MagicRoomEnds[] = _(""); +static const u8 sText_MudSportEnds[] = _(""); +static const u8 sText_WaterSportEnds[] = _(""); +static const u8 sText_GravityEnds[] = _(""); +static const u8 sText_AquaRingHeal[] = _(""); + const u8 *const gBattleStringsTable[BATTLESTRINGS_COUNT] = { sText_Trainer1LoseText, // 12 @@ -997,6 +1012,19 @@ const u8 *const gBattleStringsTable[BATTLESTRINGS_COUNT] = sText_PostponeTargetMove, // 429 sText_ReflectTargetsType, // 430 sText_TransferHeldItem, // 431 + sText_EmbargoEnds, // 432 + sText_MagnetRiseEnds, // 433 + sText_HealBlockEnds, // 434 + sText_TelekinesisEnds, // 435 + sText_TailwindEnds, // 436 + sText_LuckyChantEnds, // 437 + sText_TrickRoomEnds, // 438 + sText_WonderRoomEnds, // 439 + sText_MagicRoomEnds, // 440 + sText_MudSportEnds, // 441 + sText_WaterSportEnds, // 442 + sText_GravityEnds, // 443 + sText_AquaRingHeal, // 444 }; const u16 gMissStringIds[] = diff --git a/src/battle_util.c b/src/battle_util.c index b32238675c..29e610de2d 100644 --- a/src/battle_util.c +++ b/src/battle_util.c @@ -999,14 +999,41 @@ u8 UpdateTurnCounters(void) return (gBattleMainFunc != BattleTurnPassed); } -#define TURNBASED_MAX_CASE 19 - -u8 TurnBasedEffects(void) +enum { - u8 effect = 0; + ENDTURN_INGRAIN, + ENDTURN_AQUA_RING, + ENDTURN_ABILITIES, + ENDTURN_ITEMS1, + ENDTURN_LEECH_SEED, + ENDTURN_POISON, + ENDTURN_BAD_POISON, + ENDTURN_BURN, + ENDTURN_NIGHTMARES, + ENDTURN_CURSE, + ENDTURN_WRAP, + ENDTURN_UPROAR, + ENDTURN_THRASH, + ENDTURN_DISABLE, + ENDTURN_ENCORE, + ENDTURN_MAGNET_RISE, + ENDTURN_TELEKINESIS, + ENDTURN_HEALBLOCK, + ENDTURN_EMBARGO, + ENDTURN_LOCK_ON, + ENDTURN_CHARGE, + ENDTURN_TAUNT, + ENDTURN_YAWN, + ENDTURN_ITEMS2, + ENDTURN_BATTLER_COUNT +}; + +u8 DoBattlerEndTurnEffects(void) +{ + u8 effect = FALSE; gHitMarker |= (HITMARKER_GRUDGE | HITMARKER_x20); - while (gBattleStruct->turnEffectsBattlerId < gBattlersCount && gBattleStruct->turnEffectsTracker <= TURNBASED_MAX_CASE) + while (gBattleStruct->turnEffectsBattlerId < gBattlersCount && gBattleStruct->turnEffectsTracker <= ENDTURN_BATTLER_COUNT) { gActiveBattler = gBattlerAttacker = gBattlerByTurnOrder[gBattleStruct->turnEffectsBattlerId]; if (gAbsentBattlerFlags & gBitTable[gActiveBattler]) @@ -1017,9 +1044,10 @@ u8 TurnBasedEffects(void) { switch (gBattleStruct->turnEffectsTracker) { - case 0: // ingrain + case ENDTURN_INGRAIN: // ingrain if ((gStatuses3[gActiveBattler] & STATUS3_ROOTED) - && gBattleMons[gActiveBattler].hp != gBattleMons[gActiveBattler].maxHP + && !BATTLER_MAX_HP(gActiveBattler) + && !(gStatuses3[gActiveBattler] & STATUS3_HEAL_BLOCK) && gBattleMons[gActiveBattler].hp != 0) { gBattleMoveDamage = gBattleMons[gActiveBattler].maxHP / 16; @@ -1031,22 +1059,37 @@ u8 TurnBasedEffects(void) } gBattleStruct->turnEffectsTracker++; break; - case 1: // end turn abilities + case ENDTURN_AQUA_RING: // aqua ring + if ((gStatuses3[gActiveBattler] & STATUS3_AQUA_RING) + && !BATTLER_MAX_HP(gActiveBattler) + && !(gStatuses3[gActiveBattler] & STATUS3_HEAL_BLOCK) + && gBattleMons[gActiveBattler].hp != 0) + { + gBattleMoveDamage = gBattleMons[gActiveBattler].maxHP / 16; + if (gBattleMoveDamage == 0) + gBattleMoveDamage = 1; + gBattleMoveDamage *= -1; + BattleScriptExecute(BattleScript_AquaRingHeal); + effect++; + } + gBattleStruct->turnEffectsTracker++; + break; + case ENDTURN_ABILITIES: // end turn abilities if (AbilityBattleEffects(ABILITYEFFECT_ENDTURN, gActiveBattler, 0, 0, 0)) effect++; gBattleStruct->turnEffectsTracker++; break; - case 2: // item effects + case ENDTURN_ITEMS1: // item effects if (ItemBattleEffects(1, gActiveBattler, 0)) effect++; gBattleStruct->turnEffectsTracker++; break; - case 18: // item effects again + case ENDTURN_ITEMS2: // item effects again if (ItemBattleEffects(1, gActiveBattler, 1)) effect++; gBattleStruct->turnEffectsTracker++; break; - case 3: // leech seed + case ENDTURN_LEECH_SEED: // leech seed if ((gStatuses3[gActiveBattler] & STATUS3_LEECHSEED) && gBattleMons[gStatuses3[gActiveBattler] & STATUS3_LEECHSEED_BATTLER].hp != 0 && gBattleMons[gActiveBattler].hp != 0) @@ -1062,7 +1105,7 @@ u8 TurnBasedEffects(void) } gBattleStruct->turnEffectsTracker++; break; - case 4: // poison + case ENDTURN_POISON: // poison if ((gBattleMons[gActiveBattler].status1 & STATUS1_POISON) && gBattleMons[gActiveBattler].hp != 0) { gBattleMoveDamage = gBattleMons[gActiveBattler].maxHP / 8; @@ -1073,7 +1116,7 @@ u8 TurnBasedEffects(void) } gBattleStruct->turnEffectsTracker++; break; - case 5: // toxic poison + case ENDTURN_BAD_POISON: // toxic poison if ((gBattleMons[gActiveBattler].status1 & STATUS1_TOXIC_POISON) && gBattleMons[gActiveBattler].hp != 0) { gBattleMoveDamage = gBattleMons[gActiveBattler].maxHP / 16; @@ -1087,7 +1130,7 @@ u8 TurnBasedEffects(void) } gBattleStruct->turnEffectsTracker++; break; - case 6: // burn + case ENDTURN_BURN: // burn if ((gBattleMons[gActiveBattler].status1 & STATUS1_BURN) && gBattleMons[gActiveBattler].hp != 0) { gBattleMoveDamage = gBattleMons[gActiveBattler].maxHP / 8; @@ -1098,7 +1141,7 @@ u8 TurnBasedEffects(void) } gBattleStruct->turnEffectsTracker++; break; - case 7: // spooky nightmares + case ENDTURN_NIGHTMARES: // spooky nightmares if ((gBattleMons[gActiveBattler].status2 & STATUS2_NIGHTMARE) && gBattleMons[gActiveBattler].hp != 0) { // R/S does not perform this sleep check, which causes the nightmare effect to @@ -1118,7 +1161,7 @@ u8 TurnBasedEffects(void) } gBattleStruct->turnEffectsTracker++; break; - case 8: // curse + case ENDTURN_CURSE: // curse if ((gBattleMons[gActiveBattler].status2 & STATUS2_CURSED) && gBattleMons[gActiveBattler].hp != 0) { gBattleMoveDamage = gBattleMons[gActiveBattler].maxHP / 4; @@ -1129,7 +1172,7 @@ u8 TurnBasedEffects(void) } gBattleStruct->turnEffectsTracker++; break; - case 9: // wrap + case ENDTURN_WRAP: // wrap if ((gBattleMons[gActiveBattler].status2 & STATUS2_WRAPPED) && gBattleMons[gActiveBattler].hp != 0) { gBattleMons[gActiveBattler].status2 -= 0x2000; @@ -1162,7 +1205,7 @@ u8 TurnBasedEffects(void) } gBattleStruct->turnEffectsTracker++; break; - case 10: // uproar + case ENDTURN_UPROAR: // uproar if (gBattleMons[gActiveBattler].status2 & STATUS2_UPROAR) { for (gBattlerAttacker = 0; gBattlerAttacker < gBattlersCount; gBattlerAttacker++) @@ -1211,7 +1254,7 @@ u8 TurnBasedEffects(void) if (effect != 2) gBattleStruct->turnEffectsTracker++; break; - case 11: // thrash + case ENDTURN_THRASH: // thrash if (gBattleMons[gActiveBattler].status2 & STATUS2_LOCK_CONFUSE) { gBattleMons[gActiveBattler].status2 -= 0x400; @@ -1233,7 +1276,7 @@ u8 TurnBasedEffects(void) } gBattleStruct->turnEffectsTracker++; break; - case 12: // disable + case ENDTURN_DISABLE: // disable if (gDisableStructs[gActiveBattler].disableTimer1 != 0) { s32 i; @@ -1256,7 +1299,7 @@ u8 TurnBasedEffects(void) } gBattleStruct->turnEffectsTracker++; break; - case 13: // encore + case ENDTURN_ENCORE: // encore if (gDisableStructs[gActiveBattler].encoreTimer1 != 0) { if (gBattleMons[gActiveBattler].moves[gDisableStructs[gActiveBattler].encoredMovePos] != gDisableStructs[gActiveBattler].encoredMove) // pokemon does not have the encored move anymore @@ -1275,22 +1318,22 @@ u8 TurnBasedEffects(void) } gBattleStruct->turnEffectsTracker++; break; - case 14: // lock-on decrement + case ENDTURN_LOCK_ON: // lock-on decrement if (gStatuses3[gActiveBattler] & STATUS3_ALWAYS_HITS) gStatuses3[gActiveBattler] -= 0x8; gBattleStruct->turnEffectsTracker++; break; - case 15: // charge + case ENDTURN_CHARGE: // charge if (gDisableStructs[gActiveBattler].chargeTimer1 && --gDisableStructs[gActiveBattler].chargeTimer1 == 0) gStatuses3[gActiveBattler] &= ~STATUS3_CHARGED_UP; gBattleStruct->turnEffectsTracker++; break; - case 16: // taunt + case ENDTURN_TAUNT: // taunt if (gDisableStructs[gActiveBattler].tauntTimer1) gDisableStructs[gActiveBattler].tauntTimer1--; gBattleStruct->turnEffectsTracker++; break; - case 17: // yawn + case ENDTURN_YAWN: // yawn if (gStatuses3[gActiveBattler] & STATUS3_YAWN) { gStatuses3[gActiveBattler] -= 0x800; @@ -1309,7 +1352,63 @@ u8 TurnBasedEffects(void) } gBattleStruct->turnEffectsTracker++; break; - case 19: // done + case ENDTURN_EMBARGO: + if (gStatuses3[gActiveBattler] & STATUS3_EMBARGO) + { + if (gDisableStructs[gActiveBattler].embargoTimer != 0) + gDisableStructs[gActiveBattler].embargoTimer--; + if (gDisableStructs[gActiveBattler].embargoTimer == 0) + { + gStatuses3[gActiveBattler] &= ~(STATUS3_EMBARGO); + BattleScriptExecute(BattleScript_EmbargoEndTurn); + effect++; + } + } + gBattleStruct->turnEffectsTracker++; + break; + case ENDTURN_MAGNET_RISE: + if (gStatuses3[gActiveBattler] & STATUS3_MAGNET_RISE) + { + if (gDisableStructs[gActiveBattler].magnetRiseTimer != 0) + gDisableStructs[gActiveBattler].magnetRiseTimer--; + if (gDisableStructs[gActiveBattler].magnetRiseTimer == 0) + { + gStatuses3[gActiveBattler] &= ~(STATUS3_MAGNET_RISE); + BattleScriptExecute(BattleScript_MagnetRiseEndTurn); + effect++; + } + } + gBattleStruct->turnEffectsTracker++; + break; + case ENDTURN_TELEKINESIS: + if (gStatuses3[gActiveBattler] & STATUS3_TELEKINESIS) + { + if (gDisableStructs[gActiveBattler].telekinesisTimer != 0) + gDisableStructs[gActiveBattler].telekinesisTimer--; + if (gDisableStructs[gActiveBattler].telekinesisTimer == 0) + { + gStatuses3[gActiveBattler] &= ~(STATUS3_TELEKINESIS); + BattleScriptExecute(BattleScript_TelekinesisEndTurn); + effect++; + } + } + gBattleStruct->turnEffectsTracker++; + break; + case ENDTURN_HEALBLOCK: + if (gStatuses3[gActiveBattler] & STATUS3_HEAL_BLOCK) + { + if (gDisableStructs[gActiveBattler].healBlockTimer != 0) + gDisableStructs[gActiveBattler].healBlockTimer--; + if (gDisableStructs[gActiveBattler].healBlockTimer == 0) + { + gStatuses3[gActiveBattler] &= ~(STATUS3_HEAL_BLOCK); + BattleScriptExecute(BattleScript_HealBlockEndTurn); + effect++; + } + } + gBattleStruct->turnEffectsTracker++; + break; + case ENDTURN_BATTLER_COUNT: // done gBattleStruct->turnEffectsTracker = 0; gBattleStruct->turnEffectsBattlerId++; break; @@ -3693,6 +3792,8 @@ bool32 IsBattlerGrounded(u8 battlerId) else if (gStatuses3[battlerId] & STATUS3_TELEKINESIS) return FALSE; + else if (gStatuses3[battlerId] & STATUS3_MAGNET_RISE) + return FALSE; else if (GetBattlerAbility(battlerId) == ABILITY_LEVITATE) return FALSE; else if (IS_BATTLER_OF_TYPE(battlerId, TYPE_FLYING))