Customizable FrontierMon Sets (#4313)

* more customization to struct FacilityMon, remove facility item ids, convert vanilla data, add CreateFacilityMon universal function

* fix some unused vars

* use TrainerMon struct instead of FacilityMon

* add dynamaxLevel, gigantamaxFactor to CreateFacilityMon

* some struct TrainerMon documentation

---------

Co-authored-by: ghoulslash <pokevoyager0@gmail.com>
This commit is contained in:
ghoulslash 2024-03-29 03:47:17 -04:00 committed by GitHub
parent b58ccac4bf
commit 5a986c6d04
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
10 changed files with 2262 additions and 2518 deletions

View file

@ -1,6 +1,8 @@
#ifndef GUARD_BATTLE_TOWER_H
#define GUARD_BATTLE_TOWER_H
#include "data.h"
struct RSBattleTowerRecord
{
/*0x00*/ u8 lvlMode; // 0 = level 50, 1 = level 100
@ -24,23 +26,13 @@ struct BattleFrontierTrainer
const u16 *monSet;
};
struct FacilityMon
{
u16 species;
u16 moves[MAX_MON_MOVES];
u8 itemTableId;
u8 evSpread;
u8 nature;
};
extern const u8 gTowerMaleFacilityClasses[30];
extern const u8 gTowerMaleTrainerGfxIds[30];
extern const u8 gTowerFemaleFacilityClasses[20];
extern const u8 gTowerFemaleTrainerGfxIds[20];
extern const u16 gBattleFrontierHeldItems[];
extern const struct FacilityMon gBattleFrontierMons[];
extern const struct TrainerMon gBattleFrontierMons[];
extern const struct BattleFrontierTrainer gBattleFrontierTrainers[];
extern const struct FacilityMon gSlateportBattleTentMons[];
extern const struct TrainerMon gSlateportBattleTentMons[];
extern const struct BattleFrontierTrainer gSlateportBattleTentTrainers[];
// Temporary storage for monIds of the opponent team
@ -48,7 +40,7 @@ extern const struct BattleFrontierTrainer gSlateportBattleTentTrainers[];
extern u16 gFrontierTempParty[];
extern const struct BattleFrontierTrainer *gFacilityTrainers;
extern const struct FacilityMon *gFacilityTrainerMons;
extern const struct TrainerMon *gFacilityTrainerMons;
void CallBattleTowerFunc(void);
u16 GetRandomScaledFrontierTrainerId(u8 challengeNum, u8 battleNum);
@ -84,5 +76,6 @@ s32 GetHighestLevelInPlayerParty(void);
u8 FacilityClassToGraphicsId(u8 facilityClass);
bool32 ValidateBattleTowerRecord(u8 recordId); // unused
void TrySetLinkBattleTowerEnemyPartyLevel(void);
void CreateFacilityMon(const struct TrainerMon *fmon, u16 level, u8 fixedIV, u32 otID, u32 flags, struct Pokemon *dst);
#endif //GUARD_BATTLE_TOWER_H

View file

@ -116,6 +116,7 @@
#define EXCHANGE_CORNER_VITAMIN_CLERK 2
#define EXCHANGE_CORNER_HOLD_ITEM_CLERK 3
// unused
#define F_EV_SPREAD_HP (1 << 0)
#define F_EV_SPREAD_ATTACK (1 << 1)
#define F_EV_SPREAD_DEFENSE (1 << 2)
@ -123,68 +124,7 @@
#define F_EV_SPREAD_SP_ATTACK (1 << 4)
#define F_EV_SPREAD_SP_DEFENSE (1 << 5)
#define BATTLE_FRONTIER_ITEM_NONE 0
#define BATTLE_FRONTIER_ITEM_KINGS_ROCK 1
#define BATTLE_FRONTIER_ITEM_SITRUS_BERRY 2
#define BATTLE_FRONTIER_ITEM_ORAN_BERRY 3
#define BATTLE_FRONTIER_ITEM_CHESTO_BERRY 4
#define BATTLE_FRONTIER_ITEM_HARD_STONE 5
#define BATTLE_FRONTIER_ITEM_FOCUS_BAND 6
#define BATTLE_FRONTIER_ITEM_PERSIM_BERRY 7
#define BATTLE_FRONTIER_ITEM_MIRACLE_SEED 8
#define BATTLE_FRONTIER_ITEM_BERRY_JUICE 9
#define BATTLE_FRONTIER_ITEM_MACHO_BRACE 10
#define BATTLE_FRONTIER_ITEM_SILVER_POWDER 11
#define BATTLE_FRONTIER_ITEM_CHERI_BERRY 12
#define BATTLE_FRONTIER_ITEM_BLACK_GLASSES 13
#define BATTLE_FRONTIER_ITEM_BLACK_BELT 14
#define BATTLE_FRONTIER_ITEM_SOUL_DEW 15
#define BATTLE_FRONTIER_ITEM_CHOICE_BAND 16
#define BATTLE_FRONTIER_ITEM_MAGNET 17
#define BATTLE_FRONTIER_ITEM_SILK_SCARF 18
#define BATTLE_FRONTIER_ITEM_WHITE_HERB 19
#define BATTLE_FRONTIER_ITEM_DEEP_SEA_SCALE 20
#define BATTLE_FRONTIER_ITEM_DEEP_SEA_TOOTH 21
#define BATTLE_FRONTIER_ITEM_MYSTIC_WATER 22
#define BATTLE_FRONTIER_ITEM_SHARP_BEAK 23
#define BATTLE_FRONTIER_ITEM_QUICK_CLAW 24
#define BATTLE_FRONTIER_ITEM_LEFTOVERS 25
#define BATTLE_FRONTIER_ITEM_RAWST_BERRY 26
#define BATTLE_FRONTIER_ITEM_LIGHT_BALL 27
#define BATTLE_FRONTIER_ITEM_POISON_BARB 28
#define BATTLE_FRONTIER_ITEM_NEVER_MELT_ICE 29
#define BATTLE_FRONTIER_ITEM_ASPEAR_BERRY 30
#define BATTLE_FRONTIER_ITEM_SPELL_TAG 31
#define BATTLE_FRONTIER_ITEM_BRIGHT_POWDER 32
#define BATTLE_FRONTIER_ITEM_LEPPA_BERRY 33
#define BATTLE_FRONTIER_ITEM_SCOPE_LENS 34
#define BATTLE_FRONTIER_ITEM_TWISTED_SPOON 35
#define BATTLE_FRONTIER_ITEM_METAL_COAT 36
#define BATTLE_FRONTIER_ITEM_MENTAL_HERB 37
#define BATTLE_FRONTIER_ITEM_CHARCOAL 38
#define BATTLE_FRONTIER_ITEM_PECHA_BERRY 39
#define BATTLE_FRONTIER_ITEM_SOFT_SAND 40
#define BATTLE_FRONTIER_ITEM_LUM_BERRY 41
#define BATTLE_FRONTIER_ITEM_DRAGON_SCALE 42
#define BATTLE_FRONTIER_ITEM_DRAGON_FANG 43
#define BATTLE_FRONTIER_ITEM_IAPAPA_BERRY 44
#define BATTLE_FRONTIER_ITEM_WIKI_BERRY 45
#define BATTLE_FRONTIER_ITEM_SEA_INCENSE 46
#define BATTLE_FRONTIER_ITEM_SHELL_BELL 47
#define BATTLE_FRONTIER_ITEM_SALAC_BERRY 48
#define BATTLE_FRONTIER_ITEM_LANSAT_BERRY 49
#define BATTLE_FRONTIER_ITEM_APICOT_BERRY 50
#define BATTLE_FRONTIER_ITEM_STARF_BERRY 51
#define BATTLE_FRONTIER_ITEM_LIECHI_BERRY 52
#define BATTLE_FRONTIER_ITEM_LEEK 53
#define BATTLE_FRONTIER_ITEM_LAX_INCENSE 54
#define BATTLE_FRONTIER_ITEM_AGUAV_BERRY 55
#define BATTLE_FRONTIER_ITEM_FIGY_BERRY 56
#define BATTLE_FRONTIER_ITEM_THICK_CLUB 57
#define BATTLE_FRONTIER_ITEM_MAGO_BERRY 58
#define BATTLE_FRONTIER_ITEM_METAL_POWDER 59
#define BATTLE_FRONTIER_ITEM_PETAYA_BERRY 60
#define BATTLE_FRONTIER_ITEM_LUCKY_PUNCH 61
#define BATTLE_FRONTIER_ITEM_GANLON_BERRY 62
// CreateFacilityMonFlags
#define FLAG_FRONTIER_MON_FACTORY (1 << 0)
#endif // GUARD_CONSTANTS_BATTLE_FRONTIER_H

View file

@ -53,6 +53,8 @@ struct TrainerBacksprite
#define TRAINER_PARTY_IVS(hp, atk, def, speed, spatk, spdef) (hp | (atk << 5) | (def << 10) | (speed << 15) | (spatk << 20) | (spdef << 25))
#define TRAINER_PARTY_EVS(hp, atk, def, speed, spatk, spdef) ((const u8[6]){hp,atk,def,spatk,spdef,speed})
// Shared by both trainer and frontier mons
// See CreateNPCTrainerPartyFromTrainer and CreateFacilityMon
struct TrainerMon
{
const u8 *nickname;

View file

@ -107,7 +107,7 @@ enum {
static u8 GetDomeTrainerMonIvs(u16);
static void SwapDomeTrainers(int, int, u16 *);
static void CalcDomeMonStats(u16, int, int, u8, u8, int *);
static void CalcDomeMonStats(const struct TrainerMon *fmon, int level, u8 ivs, int *stats);
static void CreateDomeOpponentMons(u16);
static int SelectOpponentMons_Good(u16, bool8);
static int SelectOpponentMons_Bad(u16, bool8);
@ -2000,7 +2000,7 @@ static void InitDomeTrainers(void)
if (alreadySelectedMonId == monId
|| species[0] == gFacilityTrainerMons[monId].species
|| species[1] == gFacilityTrainerMons[monId].species
|| gFacilityTrainerMons[alreadySelectedMonId].itemTableId == gFacilityTrainerMons[monId].itemTableId)
|| gFacilityTrainerMons[alreadySelectedMonId].heldItem == gFacilityTrainerMons[monId].heldItem)
break;
}
} while (k != j);
@ -2053,11 +2053,8 @@ static void InitDomeTrainers(void)
ivs = GetDomeTrainerMonIvs(DOME_TRAINERS[i].trainerId);
for (j = 0; j < FRONTIER_PARTY_SIZE; j++)
{
CalcDomeMonStats(gFacilityTrainerMons[DOME_MONS[i][j]].species,
monLevel, ivs,
gFacilityTrainerMons[DOME_MONS[i][j]].evSpread,
gFacilityTrainerMons[DOME_MONS[i][j]].nature,
statValues);
CalcDomeMonStats(&gFacilityTrainerMons[DOME_MONS[i][j]],
monLevel, ivs, statValues);
rankingScores[i] += statValues[STAT_ATK];
rankingScores[i] += statValues[STAT_DEF];
@ -2130,40 +2127,31 @@ static void InitDomeTrainers(void)
#define CALC_STAT(base, statIndex) \
{ \
u8 baseStat = gSpeciesInfo[species].base; \
u8 baseStat = gSpeciesInfo[fmon->species].base; \
stats[statIndex] = (((2 * baseStat + ivs + evs[statIndex] / 4) * level) / 100) + 5; \
stats[statIndex] = (u8) ModifyStatByNature(nature, stats[statIndex], statIndex); \
stats[statIndex] = (u8) ModifyStatByNature(fmon->nature, stats[statIndex], statIndex); \
}
static void CalcDomeMonStats(u16 species, int level, int ivs, u8 evBits, u8 nature, int *stats)
static void CalcDomeMonStats(const struct TrainerMon *fmon, int level, u8 ivs, int *stats)
{
int i, count;
u8 bits;
u16 resultingEvs;
int evs[NUM_STATS];
count = 0, bits = evBits;
for (i = 0; i < NUM_STATS; bits >>= 1, i++)
int i;
for (i = 0; i < NUM_STATS; i++)
{
if (bits & 1)
count++;
if (fmon->ev != NULL)
evs[i] = fmon->ev[i];
else
evs[i] = 0;
}
resultingEvs = MAX_TOTAL_EVS / count;
for (i = 0; i < NUM_STATS; bits <<= 1, i++)
{
evs[i] = 0;
if (evBits & bits)
evs[i] = resultingEvs;
}
if (species == SPECIES_SHEDINJA)
if (fmon->species == SPECIES_SHEDINJA)
{
stats[STAT_HP] = 1;
}
else
{
int n = 2 * gSpeciesInfo[species].baseHP;
int n = 2 * gSpeciesInfo[fmon->species].baseHP;
stats[STAT_HP] = (((n + ivs + evs[STAT_HP] / 4) * level) / 100) + level + 10;
}
@ -2205,33 +2193,15 @@ static void InitDomeOpponentParty(void)
static void CreateDomeOpponentMon(u8 monPartyId, u16 tournamentTrainerId, u8 tournamentMonId, u32 otId)
{
int i;
u8 friendship = MAX_FRIENDSHIP;
#ifdef BUGFIX
u8 fixedIv = GetDomeTrainerMonIvs(DOME_TRAINERS[tournamentTrainerId].trainerId);
#else
u8 fixedIv = GetDomeTrainerMonIvs(tournamentTrainerId); // BUG: Using the wrong ID. As a result, all Pokémon have ivs of 3.
#endif
u8 level = SetFacilityPtrsGetLevel();
CreateMonWithEVSpreadNatureOTID(&gEnemyParty[monPartyId],
gFacilityTrainerMons[DOME_MONS[tournamentTrainerId][tournamentMonId]].species,
level,
gFacilityTrainerMons[DOME_MONS[tournamentTrainerId][tournamentMonId]].nature,
fixedIv,
gFacilityTrainerMons[DOME_MONS[tournamentTrainerId][tournamentMonId]].evSpread, otId);
friendship = MAX_FRIENDSHIP;
for (i = 0; i < MAX_MON_MOVES; i++)
{
SetMonMoveSlot(&gEnemyParty[monPartyId],
gFacilityTrainerMons[DOME_MONS[tournamentTrainerId][tournamentMonId]].moves[i], i);
if (gMovesInfo[gFacilityTrainerMons[DOME_MONS[tournamentTrainerId][tournamentMonId]].moves[i]].effect == EFFECT_FRUSTRATION)
friendship = 0;
}
SetMonData(&gEnemyParty[monPartyId], MON_DATA_FRIENDSHIP, &friendship);
SetMonData(&gEnemyParty[monPartyId], MON_DATA_HELD_ITEM,
&gBattleFrontierHeldItems[gFacilityTrainerMons[DOME_MONS[tournamentTrainerId][tournamentMonId]].itemTableId]);
CreateFacilityMon(&gFacilityTrainerMons[DOME_MONS[tournamentTrainerId][tournamentMonId]],
level, fixedIv, otId, 0, &gEnemyParty[monPartyId]);
}
static void CreateDomeOpponentMons(u16 tournamentTrainerId)
@ -4463,23 +4433,14 @@ static void DisplayTrainerInfoOnCard(u8 flags, u8 trainerTourneyId)
{
for (i = 0; i < FRONTIER_PARTY_SIZE; i++)
{
int evBits = gFacilityTrainerMons[DOME_MONS[trainerTourneyId][i]].evSpread;
for (k = 0, j = 0; j < NUM_STATS; j++)
{
allocatedArray[j] = 0;
if (evBits & 1)
k++;
evBits >>= 1;
}
k = MAX_TOTAL_EVS / k;
evBits = gFacilityTrainerMons[DOME_MONS[trainerTourneyId][i]].evSpread;
for (j = 0; j < NUM_STATS; j++)
{
if (evBits & 1)
allocatedArray[j] = k;
evBits >>= 1;
if (gFacilityTrainerMons[DOME_MONS[trainerTourneyId][i]].ev != NULL)
allocatedArray[j] = gFacilityTrainerMons[DOME_MONS[trainerTourneyId][i]].ev[j];
else
allocatedArray[j] = 0;
}
allocatedArray[NUM_STATS] += allocatedArray[STAT_HP];
for (j = 0; j < NUM_NATURE_STATS; j++)
{
@ -5800,7 +5761,7 @@ static void InitRandomTourneyTreeResults(void)
if (alreadySelectedMonId == monId
|| species[0] == gFacilityTrainerMons[monId].species
|| species[1] == gFacilityTrainerMons[monId].species
|| gFacilityTrainerMons[alreadySelectedMonId].itemTableId == gFacilityTrainerMons[monId].itemTableId)
|| gFacilityTrainerMons[alreadySelectedMonId].heldItem == gFacilityTrainerMons[monId].heldItem)
break;
}
} while (k != j);
@ -5821,11 +5782,8 @@ static void InitRandomTourneyTreeResults(void)
ivs = GetDomeTrainerMonIvs(DOME_TRAINERS[i].trainerId);
for (j = 0; j < FRONTIER_PARTY_SIZE; j++)
{
CalcDomeMonStats(gFacilityTrainerMons[DOME_MONS[i][j]].species,
monLevel, ivs,
gFacilityTrainerMons[DOME_MONS[i][j]].evSpread,
gFacilityTrainerMons[DOME_MONS[i][j]].nature,
statValues);
CalcDomeMonStats(&gFacilityTrainerMons[DOME_MONS[i][j]],
monLevel, ivs, statValues);
statSums[i] += statValues[STAT_ATK];
statSums[i] += statValues[STAT_DEF];

View file

@ -362,7 +362,7 @@ static void GenerateOpponentMons(void)
// Ensure held items don't repeat on the opponent's team
for (k = firstMonId; k < firstMonId + i; k++)
{
if (heldItems[k] != ITEM_NONE && heldItems[k] == gBattleFrontierHeldItems[gFacilityTrainerMons[monId].itemTableId])
if (heldItems[k] != ITEM_NONE && heldItems[k] == gFacilityTrainerMons[monId].heldItem)
break;
}
if (k != firstMonId + i)
@ -370,7 +370,7 @@ static void GenerateOpponentMons(void)
// Successful selection
species[i] = gFacilityTrainerMons[monId].species;
heldItems[i] = gBattleFrontierHeldItems[gFacilityTrainerMons[monId].itemTableId];
heldItems[i] = gFacilityTrainerMons[monId].heldItem;
gFrontierTempParty[i] = monId;
i++;
}
@ -396,21 +396,17 @@ static void SetRentalsToOpponentParty(void)
gSaveBlock2Ptr->frontier.rentalMons[i + FRONTIER_PARTY_SIZE].ivs = GetBoxMonData(&gEnemyParty[i].box, MON_DATA_ATK_IV, NULL);
gSaveBlock2Ptr->frontier.rentalMons[i + FRONTIER_PARTY_SIZE].personality = GetMonData(&gEnemyParty[i], MON_DATA_PERSONALITY, NULL);
gSaveBlock2Ptr->frontier.rentalMons[i + FRONTIER_PARTY_SIZE].abilityNum = GetBoxMonData(&gEnemyParty[i].box, MON_DATA_ABILITY_NUM, NULL);
SetMonData(&gEnemyParty[i], MON_DATA_HELD_ITEM, &gBattleFrontierHeldItems[gFacilityTrainerMons[gFrontierTempParty[i]].itemTableId]);
SetMonData(&gEnemyParty[i], MON_DATA_HELD_ITEM, &gFacilityTrainerMons[gFrontierTempParty[i]].heldItem);
}
}
static void SetPlayerAndOpponentParties(void)
{
int i, j, k;
int count = 0;
u8 bits = 0;
int i;
u8 monLevel;
u16 monId;
u16 evs;
u8 ivs;
u8 friendship;
if (gSaveBlock2Ptr->frontier.lvlMode == FRONTIER_LVL_TENT)
{
gFacilityTrainerMons = gSlateportBattleTentMons;
@ -432,36 +428,11 @@ static void SetPlayerAndOpponentParties(void)
{
monId = gSaveBlock2Ptr->frontier.rentalMons[i].monId;
ivs = gSaveBlock2Ptr->frontier.rentalMons[i].ivs;
CreateMon(&gPlayerParty[i],
gFacilityTrainerMons[monId].species,
monLevel,
ivs,
TRUE, gSaveBlock2Ptr->frontier.rentalMons[i].personality,
OT_ID_PLAYER_ID, 0);
count = 0;
bits = gFacilityTrainerMons[monId].evSpread;
for (j = 0; j < NUM_STATS; bits >>= 1, j++)
{
if (bits & 1)
count++;
}
evs = MAX_TOTAL_EVS / count;
bits = 1;
for (j = 0; j < NUM_STATS; bits <<= 1, j++)
{
if (gFacilityTrainerMons[monId].evSpread & bits)
SetMonData(&gPlayerParty[i], MON_DATA_HP_EV + j, &evs);
}
CreateFacilityMon(&gFacilityTrainerMons[monId], monLevel, ivs, OT_ID_PLAYER_ID, FLAG_FRONTIER_MON_FACTORY, &gPlayerParty[i]);
SetMonData(&gPlayerParty[i], MON_DATA_PERSONALITY,
&gSaveBlock2Ptr->frontier.rentalMons[i].personality);
CalculateMonStats(&gPlayerParty[i]);
friendship = 0;
for (k = 0; k < MAX_MON_MOVES; k++)
SetMonMoveAvoidReturn(&gPlayerParty[i], gFacilityTrainerMons[monId].moves[k], k);
SetMonData(&gPlayerParty[i], MON_DATA_FRIENDSHIP, &friendship);
SetMonData(&gPlayerParty[i], MON_DATA_HELD_ITEM, &gBattleFrontierHeldItems[gFacilityTrainerMons[monId].itemTableId]);
SetMonData(&gPlayerParty[i], MON_DATA_ABILITY_NUM, &gSaveBlock2Ptr->frontier.rentalMons[i].abilityNum);
}
}
@ -473,34 +444,12 @@ static void SetPlayerAndOpponentParties(void)
{
monId = gSaveBlock2Ptr->frontier.rentalMons[i + FRONTIER_PARTY_SIZE].monId;
ivs = gSaveBlock2Ptr->frontier.rentalMons[i + FRONTIER_PARTY_SIZE].ivs;
CreateMon(&gEnemyParty[i],
gFacilityTrainerMons[monId].species,
monLevel,
ivs,
TRUE, gSaveBlock2Ptr->frontier.rentalMons[i + FRONTIER_PARTY_SIZE].personality,
OT_ID_PLAYER_ID, 0);
count = 0;
bits = gFacilityTrainerMons[monId].evSpread;
for (j = 0; j < NUM_STATS; bits >>= 1, j++)
{
if (bits & 1)
count++;
}
evs = MAX_TOTAL_EVS / count;
bits = 1;
for (j = 0; j < NUM_STATS; bits <<= 1, j++)
{
if (gFacilityTrainerMons[monId].evSpread & bits)
SetMonData(&gEnemyParty[i], MON_DATA_HP_EV + j, &evs);
}
CalculateMonStats(&gEnemyParty[i]);
for (k = 0; k < MAX_MON_MOVES; k++)
SetMonMoveAvoidReturn(&gEnemyParty[i], gFacilityTrainerMons[monId].moves[k], k);
SetMonData(&gEnemyParty[i], MON_DATA_HELD_ITEM, &gBattleFrontierHeldItems[gFacilityTrainerMons[monId].itemTableId]);
SetMonData(&gEnemyParty[i], MON_DATA_ABILITY_NUM, &gSaveBlock2Ptr->frontier.rentalMons[i + FRONTIER_PARTY_SIZE].abilityNum);
CreateFacilityMon(&gFacilityTrainerMons[monId],
monLevel, ivs, OT_ID_PLAYER_ID, FLAG_FRONTIER_MON_FACTORY,
&gEnemyParty[i]);
SetMonData(&gPlayerParty[i], MON_DATA_PERSONALITY,
&gSaveBlock2Ptr->frontier.rentalMons[i + FRONTIER_PARTY_SIZE].personality);
CalculateMonStats(&gPlayerParty[i]);
}
break;
}
@ -582,7 +531,7 @@ static void GenerateInitialRentalMons(void)
// Cannot have two same held items.
for (j = firstMonId; j < firstMonId + i; j++)
{
if (heldItems[j] != ITEM_NONE && heldItems[j] == gBattleFrontierHeldItems[gFacilityTrainerMons[monId].itemTableId])
if (heldItems[j] != ITEM_NONE && heldItems[j] == gFacilityTrainerMons[monId].heldItem)
{
if (gFacilityTrainerMons[monId].species == currSpecies)
currSpecies = SPECIES_NONE;
@ -594,7 +543,7 @@ static void GenerateInitialRentalMons(void)
gSaveBlock2Ptr->frontier.rentalMons[i].monId = monId;
species[i] = gFacilityTrainerMons[monId].species;
heldItems[i] = gBattleFrontierHeldItems[gFacilityTrainerMons[monId].itemTableId];
heldItems[i] = gFacilityTrainerMons[monId].heldItem;
monIds[i] = monId;
i++;
}
@ -724,7 +673,7 @@ static void RestorePlayerPartyHeldItems(void)
{
SetMonData(&gPlayerParty[i],
MON_DATA_HELD_ITEM,
&gBattleFrontierHeldItems[gFacilityTrainerMons[gSaveBlock2Ptr->frontier.rentalMons[i].monId].itemTableId]);
&gFacilityTrainerMons[gSaveBlock2Ptr->frontier.rentalMons[i].monId].heldItem);
}
}
@ -761,7 +710,6 @@ void FillFactoryBrainParty(void)
int i, j, k;
u16 species[FRONTIER_PARTY_SIZE];
u16 heldItems[FRONTIER_PARTY_SIZE];
u8 friendship;
int monLevel;
u8 fixedIV;
u32 otId;
@ -801,27 +749,17 @@ void FillFactoryBrainParty(void)
for (k = 0; k < i; k++)
{
if (heldItems[k] != ITEM_NONE && heldItems[k] == gBattleFrontierHeldItems[gFacilityTrainerMons[monId].itemTableId])
if (heldItems[k] != ITEM_NONE && heldItems[k] == gFacilityTrainerMons[monId].heldItem)
break;
}
if (k != i)
continue;
species[i] = gFacilityTrainerMons[monId].species;
heldItems[i] = gBattleFrontierHeldItems[gFacilityTrainerMons[monId].itemTableId];
CreateMonWithEVSpreadNatureOTID(&gEnemyParty[i],
gFacilityTrainerMons[monId].species,
monLevel,
gFacilityTrainerMons[monId].nature,
fixedIV,
gFacilityTrainerMons[monId].evSpread,
otId);
friendship = 0;
for (k = 0; k < MAX_MON_MOVES; k++)
SetMonMoveAvoidReturn(&gEnemyParty[i], gFacilityTrainerMons[monId].moves[k], k);
SetMonData(&gEnemyParty[i], MON_DATA_FRIENDSHIP, &friendship);
SetMonData(&gEnemyParty[i], MON_DATA_HELD_ITEM, &gBattleFrontierHeldItems[gFacilityTrainerMons[monId].itemTableId]);
heldItems[i] = gFacilityTrainerMons[monId].heldItem;
CreateFacilityMon(&gFacilityTrainerMons[monId],
monLevel, fixedIV, otId, FLAG_FRONTIER_MON_FACTORY,
&gEnemyParty[i]);
i++;
}
}

View file

@ -1735,10 +1735,9 @@ static void Select_Task_HandleChooseMons(u8 taskId)
static void CreateFrontierFactorySelectableMons(u8 firstMonId)
{
u8 i, j = 0;
u8 i = 0;
u8 ivs = 0;
u8 level = 0;
u8 friendship = 0;
u32 otId = 0;
u8 battleMode = VarGet(VAR_FRONTIER_BATTLE_MODE);
u8 lvlMode = gSaveBlock2Ptr->frontier.lvlMode;
@ -1762,27 +1761,18 @@ static void CreateFrontierFactorySelectableMons(u8 firstMonId)
ivs = GetFactoryMonFixedIV(challengeNum + 1, FALSE);
else
ivs = GetFactoryMonFixedIV(challengeNum, FALSE);
CreateMonWithEVSpreadNatureOTID(&sFactorySelectScreen->mons[i + firstMonId].monData,
gFacilityTrainerMons[monId].species,
level,
gFacilityTrainerMons[monId].nature,
ivs,
gFacilityTrainerMons[monId].evSpread,
otId);
friendship = 0;
for (j = 0; j < MAX_MON_MOVES; j++)
SetMonMoveAvoidReturn(&sFactorySelectScreen->mons[i + firstMonId].monData, gFacilityTrainerMons[monId].moves[j], j);
SetMonData(&sFactorySelectScreen->mons[i + firstMonId].monData, MON_DATA_FRIENDSHIP, &friendship);
SetMonData(&sFactorySelectScreen->mons[i + firstMonId].monData, MON_DATA_HELD_ITEM, &gBattleFrontierHeldItems[gFacilityTrainerMons[monId].itemTableId]);
CreateFacilityMon(&gFacilityTrainerMons[monId],
level, ivs, otId, FLAG_FRONTIER_MON_FACTORY,
&sFactorySelectScreen->mons[i + firstMonId].monData);
}
}
static void CreateSlateportTentSelectableMons(u8 firstMonId)
{
u8 i, j;
u8 i;
u8 ivs = 0;
u8 level = TENT_MIN_LEVEL;
u8 friendship = 0;
u32 otId = 0;
gFacilityTrainerMons = gSlateportBattleTentMons;
@ -1792,18 +1782,7 @@ static void CreateSlateportTentSelectableMons(u8 firstMonId)
{
u16 monId = gSaveBlock2Ptr->frontier.rentalMons[i].monId;
sFactorySelectScreen->mons[i + firstMonId].monId = monId;
CreateMonWithEVSpreadNatureOTID(&sFactorySelectScreen->mons[i + firstMonId].monData,
gFacilityTrainerMons[monId].species,
level,
gFacilityTrainerMons[monId].nature,
ivs,
gFacilityTrainerMons[monId].evSpread,
otId);
friendship = 0;
for (j = 0; j < MAX_MON_MOVES; j++)
SetMonMoveAvoidReturn(&sFactorySelectScreen->mons[i + firstMonId].monData, gFacilityTrainerMons[monId].moves[j], j);
SetMonData(&sFactorySelectScreen->mons[i + firstMonId].monData, MON_DATA_FRIENDSHIP, &friendship);
SetMonData(&sFactorySelectScreen->mons[i + firstMonId].monData, MON_DATA_HELD_ITEM, &gBattleFrontierHeldItems[gFacilityTrainerMons[monId].itemTableId]);
CreateFacilityMon(&gFacilityTrainerMons[monId], level, ivs, otId, 0, &sFactorySelectScreen->mons[i + firstMonId].monData);
}
}

View file

@ -329,7 +329,7 @@ static void GenerateInitialRentalMons(void)
// Cannot have two same held items.
for (j = firstMonId; j < i + firstMonId; j++)
{
if (heldItems[j] != 0 && heldItems[j] == gBattleFrontierHeldItems[gFacilityTrainerMons[monSetId].itemTableId])
if (heldItems[j] != 0 && heldItems[j] == gFacilityTrainerMons[monSetId].heldItem)
{
if (gFacilityTrainerMons[monSetId].species == currSpecies)
currSpecies = SPECIES_NONE;
@ -341,7 +341,7 @@ static void GenerateInitialRentalMons(void)
gSaveBlock2Ptr->frontier.rentalMons[i].monId = monSetId;
species[i] = gFacilityTrainerMons[monSetId].species;
heldItems[i] = gBattleFrontierHeldItems[gFacilityTrainerMons[monSetId].itemTableId];
heldItems[i] = gFacilityTrainerMons[monSetId].heldItem;
monIds[i] = monSetId;
i++;
}
@ -411,7 +411,7 @@ static void GenerateOpponentMons(void)
// Ensure held items don't repeat on the opponent's team
for (k = 0; k < i; k++)
{
if (heldItems[k] != ITEM_NONE && heldItems[k] == gBattleFrontierHeldItems[gFacilityTrainerMons[sRandMonId].itemTableId])
if (heldItems[k] != ITEM_NONE && heldItems[k] == gFacilityTrainerMons[sRandMonId].heldItem)
break;
}
if (k != i)
@ -419,7 +419,7 @@ static void GenerateOpponentMons(void)
// Successful selection
species[i] = gFacilityTrainerMons[sRandMonId].species;
heldItems[i] = gBattleFrontierHeldItems[gFacilityTrainerMons[sRandMonId].itemTableId];
heldItems[i] = gFacilityTrainerMons[sRandMonId].heldItem;
gFrontierTempParty[i] = sRandMonId;
i++;
}

View file

@ -42,7 +42,7 @@
// EWRAM vars.
EWRAM_DATA const struct BattleFrontierTrainer *gFacilityTrainers = NULL;
EWRAM_DATA const struct FacilityMon *gFacilityTrainerMons = NULL;
EWRAM_DATA const struct TrainerMon *gFacilityTrainerMons = NULL;
// IWRAM common
u16 gFrontierTempParty[MAX_FRONTIER_PARTY_SIZE];
@ -81,73 +81,6 @@ static void SetEReaderTrainerChecksum(struct BattleTowerEReaderTrainer *ereaderT
#endif //FREE_BATTLE_TOWER_E_READER
static u8 SetTentPtrsGetLevel(void);
const u16 gBattleFrontierHeldItems[] =
{
[BATTLE_FRONTIER_ITEM_NONE] = ITEM_NONE,
[BATTLE_FRONTIER_ITEM_KINGS_ROCK] = ITEM_KINGS_ROCK,
[BATTLE_FRONTIER_ITEM_SITRUS_BERRY] = ITEM_SITRUS_BERRY,
[BATTLE_FRONTIER_ITEM_ORAN_BERRY] = ITEM_ORAN_BERRY,
[BATTLE_FRONTIER_ITEM_CHESTO_BERRY] = ITEM_CHESTO_BERRY,
[BATTLE_FRONTIER_ITEM_HARD_STONE] = ITEM_HARD_STONE,
[BATTLE_FRONTIER_ITEM_FOCUS_BAND] = ITEM_FOCUS_BAND,
[BATTLE_FRONTIER_ITEM_PERSIM_BERRY] = ITEM_PERSIM_BERRY,
[BATTLE_FRONTIER_ITEM_MIRACLE_SEED] = ITEM_MIRACLE_SEED,
[BATTLE_FRONTIER_ITEM_BERRY_JUICE] = ITEM_BERRY_JUICE,
[BATTLE_FRONTIER_ITEM_MACHO_BRACE] = ITEM_MACHO_BRACE,
[BATTLE_FRONTIER_ITEM_SILVER_POWDER] = ITEM_SILVER_POWDER,
[BATTLE_FRONTIER_ITEM_CHERI_BERRY] = ITEM_CHERI_BERRY,
[BATTLE_FRONTIER_ITEM_BLACK_GLASSES] = ITEM_BLACK_GLASSES,
[BATTLE_FRONTIER_ITEM_BLACK_BELT] = ITEM_BLACK_BELT,
[BATTLE_FRONTIER_ITEM_SOUL_DEW] = ITEM_SOUL_DEW,
[BATTLE_FRONTIER_ITEM_CHOICE_BAND] = ITEM_CHOICE_BAND,
[BATTLE_FRONTIER_ITEM_MAGNET] = ITEM_MAGNET,
[BATTLE_FRONTIER_ITEM_SILK_SCARF] = ITEM_SILK_SCARF,
[BATTLE_FRONTIER_ITEM_WHITE_HERB] = ITEM_WHITE_HERB,
[BATTLE_FRONTIER_ITEM_DEEP_SEA_SCALE] = ITEM_DEEP_SEA_SCALE,
[BATTLE_FRONTIER_ITEM_DEEP_SEA_TOOTH] = ITEM_DEEP_SEA_TOOTH,
[BATTLE_FRONTIER_ITEM_MYSTIC_WATER] = ITEM_MYSTIC_WATER,
[BATTLE_FRONTIER_ITEM_SHARP_BEAK] = ITEM_SHARP_BEAK,
[BATTLE_FRONTIER_ITEM_QUICK_CLAW] = ITEM_QUICK_CLAW,
[BATTLE_FRONTIER_ITEM_LEFTOVERS] = ITEM_LEFTOVERS,
[BATTLE_FRONTIER_ITEM_RAWST_BERRY] = ITEM_RAWST_BERRY,
[BATTLE_FRONTIER_ITEM_LIGHT_BALL] = ITEM_LIGHT_BALL,
[BATTLE_FRONTIER_ITEM_POISON_BARB] = ITEM_POISON_BARB,
[BATTLE_FRONTIER_ITEM_NEVER_MELT_ICE] = ITEM_NEVER_MELT_ICE,
[BATTLE_FRONTIER_ITEM_ASPEAR_BERRY] = ITEM_ASPEAR_BERRY,
[BATTLE_FRONTIER_ITEM_SPELL_TAG] = ITEM_SPELL_TAG,
[BATTLE_FRONTIER_ITEM_BRIGHT_POWDER] = ITEM_BRIGHT_POWDER,
[BATTLE_FRONTIER_ITEM_LEPPA_BERRY] = ITEM_LEPPA_BERRY,
[BATTLE_FRONTIER_ITEM_SCOPE_LENS] = ITEM_SCOPE_LENS,
[BATTLE_FRONTIER_ITEM_TWISTED_SPOON] = ITEM_TWISTED_SPOON,
[BATTLE_FRONTIER_ITEM_METAL_COAT] = ITEM_METAL_COAT,
[BATTLE_FRONTIER_ITEM_MENTAL_HERB] = ITEM_MENTAL_HERB,
[BATTLE_FRONTIER_ITEM_CHARCOAL] = ITEM_CHARCOAL,
[BATTLE_FRONTIER_ITEM_PECHA_BERRY] = ITEM_PECHA_BERRY,
[BATTLE_FRONTIER_ITEM_SOFT_SAND] = ITEM_SOFT_SAND,
[BATTLE_FRONTIER_ITEM_LUM_BERRY] = ITEM_LUM_BERRY,
[BATTLE_FRONTIER_ITEM_DRAGON_SCALE] = ITEM_DRAGON_SCALE,
[BATTLE_FRONTIER_ITEM_DRAGON_FANG] = ITEM_DRAGON_FANG,
[BATTLE_FRONTIER_ITEM_IAPAPA_BERRY] = ITEM_IAPAPA_BERRY,
[BATTLE_FRONTIER_ITEM_WIKI_BERRY] = ITEM_WIKI_BERRY,
[BATTLE_FRONTIER_ITEM_SEA_INCENSE] = ITEM_SEA_INCENSE,
[BATTLE_FRONTIER_ITEM_SHELL_BELL] = ITEM_SHELL_BELL,
[BATTLE_FRONTIER_ITEM_SALAC_BERRY] = ITEM_SALAC_BERRY,
[BATTLE_FRONTIER_ITEM_LANSAT_BERRY] = ITEM_LANSAT_BERRY,
[BATTLE_FRONTIER_ITEM_APICOT_BERRY] = ITEM_APICOT_BERRY,
[BATTLE_FRONTIER_ITEM_STARF_BERRY] = ITEM_STARF_BERRY,
[BATTLE_FRONTIER_ITEM_LIECHI_BERRY] = ITEM_LIECHI_BERRY,
[BATTLE_FRONTIER_ITEM_LEEK] = ITEM_LEEK,
[BATTLE_FRONTIER_ITEM_LAX_INCENSE] = ITEM_LAX_INCENSE,
[BATTLE_FRONTIER_ITEM_AGUAV_BERRY] = ITEM_AGUAV_BERRY,
[BATTLE_FRONTIER_ITEM_FIGY_BERRY] = ITEM_FIGY_BERRY,
[BATTLE_FRONTIER_ITEM_THICK_CLUB] = ITEM_THICK_CLUB,
[BATTLE_FRONTIER_ITEM_MAGO_BERRY] = ITEM_MAGO_BERRY,
[BATTLE_FRONTIER_ITEM_METAL_POWDER] = ITEM_METAL_POWDER,
[BATTLE_FRONTIER_ITEM_PETAYA_BERRY] = ITEM_PETAYA_BERRY,
[BATTLE_FRONTIER_ITEM_LUCKY_PUNCH] = ITEM_LUCKY_PUNCH,
[BATTLE_FRONTIER_ITEM_GANLON_BERRY] = ITEM_GANLON_BERRY,
};
#include "data/battle_frontier/battle_frontier_trainer_mons.h"
#include "data/battle_frontier/battle_frontier_trainers.h"
#include "data/battle_frontier/battle_frontier_mons.h"
@ -1627,11 +1560,93 @@ static void FillTentTrainerParty(u8 monsCount)
FillTentTrainerParty_(gTrainerBattleOpponent_A, 0, monsCount);
}
void CreateFacilityMon(const struct TrainerMon *fmon, u16 level, u8 fixedIV, u32 otID, u32 flags, struct Pokemon *dst)
{
u8 ball = (fmon->ball == 0xFF) ? Random() % POKEBALL_COUNT : fmon->ball;
u16 move;
u32 personality, ability, friendship, j;
if (fmon->gender == TRAINER_MON_MALE)
{
personality = GeneratePersonalityForGender(MON_MALE, fmon->species);
}
else if (fmon->gender == TRAINER_MON_FEMALE)
{
personality = GeneratePersonalityForGender(MON_FEMALE, fmon->species);
}
ModifyPersonalityForNature(&personality, fmon->nature);
CreateMon(dst, fmon->species, level, fixedIV, TRUE, personality, otID, OT_ID_PRESET);
friendship = MAX_FRIENDSHIP;
// Give the chosen Pokémon its specified moves.
for (j = 0; j < MAX_MON_MOVES; j++)
{
move = fmon->moves[j];
if (flags & FLAG_FRONTIER_MON_FACTORY && move == MOVE_RETURN)
move = MOVE_FRUSTRATION;
SetMonMoveSlot(dst, move, j);
if (gMovesInfo[move].effect == EFFECT_FRUSTRATION)
friendship = 0; // Frustration is more powerful the lower the pokemon's friendship is.
}
SetMonData(dst, MON_DATA_FRIENDSHIP, &friendship);
SetMonData(dst, MON_DATA_HELD_ITEM, &fmon->heldItem);
// try to set ability. Otherwise, random of non-hidden as per vanilla
if (fmon->ability != ABILITY_NONE)
{
const struct SpeciesInfo *speciesInfo = &gSpeciesInfo[fmon->species];
u32 maxAbilities = ARRAY_COUNT(speciesInfo->abilities);
for (ability = 0; ability < maxAbilities; ++ability)
{
if (speciesInfo->abilities[ability] == fmon->ability)
break;
}
if (ability >= maxAbilities)
ability = 0;
SetMonData(dst, MON_DATA_ABILITY_NUM, &ability);
}
if (fmon->ev != NULL)
{
SetMonData(dst, MON_DATA_HP_EV, &(fmon->ev[0]));
SetMonData(dst, MON_DATA_ATK_EV, &(fmon->ev[1]));
SetMonData(dst, MON_DATA_DEF_EV, &(fmon->ev[2]));
SetMonData(dst, MON_DATA_SPATK_EV, &(fmon->ev[3]));
SetMonData(dst, MON_DATA_SPDEF_EV, &(fmon->ev[4]));
SetMonData(dst, MON_DATA_SPEED_EV, &(fmon->ev[5]));
}
if (fmon->iv)
SetMonData(dst, MON_DATA_IVS, &(fmon->iv));
if (fmon->isShiny)
{
u32 data = TRUE;
SetMonData(dst, MON_DATA_IS_SHINY, &data);
}
if (fmon->dynamaxLevel > 0)
{
u32 data = fmon->dynamaxLevel;
SetMonData(dst, MON_DATA_DYNAMAX_LEVEL, &data);
}
if (fmon->gigantamaxFactor)
{
u32 data = fmon->gigantamaxFactor;
SetMonData(dst, MON_DATA_GIGANTAMAX_FACTOR, &data);
}
SetMonData(dst, MON_DATA_POKEBALL, &ball);
CalculateMonStats(dst);
}
static void FillTrainerParty(u16 trainerId, u8 firstMonId, u8 monCount)
{
s32 i, j;
u16 chosenMonIndices[MAX_FRONTIER_PARTY_SIZE];
u8 friendship = MAX_FRIENDSHIP;
u8 level = SetFacilityPtrsGetLevel();
u8 fixedIV = 0;
u8 bfMonCount;
@ -1708,7 +1723,7 @@ static void FillTrainerParty(u16 trainerId, u8 firstMonId, u8 monCount)
for (j = 0; j < i + firstMonId; j++)
{
if (GetMonData(&gEnemyParty[j], MON_DATA_HELD_ITEM, NULL) != ITEM_NONE
&& GetMonData(&gEnemyParty[j], MON_DATA_HELD_ITEM, NULL) == gBattleFrontierHeldItems[gFacilityTrainerMons[monId].itemTableId])
&& GetMonData(&gEnemyParty[j], MON_DATA_HELD_ITEM, NULL) == gFacilityTrainerMons[monId].heldItem)
break;
}
if (j != i + firstMonId)
@ -1725,27 +1740,9 @@ static void FillTrainerParty(u16 trainerId, u8 firstMonId, u8 monCount)
continue;
chosenMonIndices[i] = monId;
// Place the chosen Pokémon into the trainer's party.
CreateMonWithEVSpreadNatureOTID(&gEnemyParty[i + firstMonId],
gFacilityTrainerMons[monId].species,
level,
gFacilityTrainerMons[monId].nature,
fixedIV,
gFacilityTrainerMons[monId].evSpread,
otID);
friendship = MAX_FRIENDSHIP;
// Give the chosen Pokémon its specified moves.
for (j = 0; j < MAX_MON_MOVES; j++)
{
SetMonMoveSlot(&gEnemyParty[i + firstMonId], gFacilityTrainerMons[monId].moves[j], j);
if (gMovesInfo[gFacilityTrainerMons[monId].moves[j]].effect == EFFECT_FRUSTRATION)
friendship = 0; // Frustration is more powerful the lower the pokemon's friendship is.
}
SetMonData(&gEnemyParty[i + firstMonId], MON_DATA_FRIENDSHIP, &friendship);
SetMonData(&gEnemyParty[i + firstMonId], MON_DATA_HELD_ITEM, &gBattleFrontierHeldItems[gFacilityTrainerMons[monId].itemTableId]);
CreateFacilityMon(&gFacilityTrainerMons[monId], level, fixedIV, otID, 0, &gEnemyParty[i + firstMonId]);
// The Pokémon was successfully added to the trainer's party, so it's safe to move on to
// the next party slot.
@ -1822,8 +1819,7 @@ static void FillFactoryTrainerParty(void)
static void FillFactoryFrontierTrainerParty(u16 trainerId, u8 firstMonId)
{
u8 i, j;
u8 friendship;
u8 i;
u8 level;
u8 fixedIV;
u32 otID;
@ -1868,27 +1864,15 @@ static void FillFactoryFrontierTrainerParty(u16 trainerId, u8 firstMonId)
for (i = 0; i < FRONTIER_PARTY_SIZE; i++)
{
u16 monId = gFrontierTempParty[i];
CreateMonWithEVSpreadNatureOTID(&gEnemyParty[firstMonId + i],
gFacilityTrainerMons[monId].species,
level,
gFacilityTrainerMons[monId].nature,
fixedIV,
gFacilityTrainerMons[monId].evSpread,
otID);
friendship = 0;
for (j = 0; j < MAX_MON_MOVES; j++)
SetMonMoveAvoidReturn(&gEnemyParty[firstMonId + i], gFacilityTrainerMons[monId].moves[j], j);
SetMonData(&gEnemyParty[firstMonId + i], MON_DATA_FRIENDSHIP, &friendship);
SetMonData(&gEnemyParty[firstMonId + i], MON_DATA_HELD_ITEM, &gBattleFrontierHeldItems[gFacilityTrainerMons[monId].itemTableId]);
CreateFacilityMon(&gFacilityTrainerMons[monId],
level, fixedIV, otID, FLAG_FRONTIER_MON_FACTORY,
&gEnemyParty[firstMonId + i]);
}
}
static void FillFactoryTentTrainerParty(u16 trainerId, u8 firstMonId)
{
u8 i, j;
u8 friendship;
u8 i;
u8 level = TENT_MIN_LEVEL;
u8 fixedIV = 0;
u32 otID = T1_READ_32(gSaveBlock2Ptr->playerTrainerId);
@ -1896,24 +1880,9 @@ static void FillFactoryTentTrainerParty(u16 trainerId, u8 firstMonId)
for (i = 0; i < FRONTIER_PARTY_SIZE; i++)
{
u16 monId = gFrontierTempParty[i];
CreateMonWithEVSpreadNatureOTID(&gEnemyParty[firstMonId + i],
gFacilityTrainerMons[monId].species,
level,
gFacilityTrainerMons[monId].nature,
fixedIV,
gFacilityTrainerMons[monId].evSpread,
otID);
friendship = 0;
for (j = 0; j < MAX_MON_MOVES; j++)
{
SetMonMoveAvoidReturn(&gEnemyParty[firstMonId + i], gFacilityTrainerMons[monId].moves[j], j);
if (gMovesInfo[gFacilityTrainerMons[monId].moves[j]].effect == EFFECT_FRUSTRATION)
friendship = 0;
}
SetMonData(&gEnemyParty[firstMonId + i], MON_DATA_FRIENDSHIP, &friendship);
SetMonData(&gEnemyParty[firstMonId + i], MON_DATA_HELD_ITEM, &gBattleFrontierHeldItems[gFacilityTrainerMons[monId].itemTableId]);
CreateFacilityMon(&gFacilityTrainerMons[monId],
level, fixedIV, otID, 0,
&gEnemyParty[firstMonId + i]);
}
}
@ -2348,7 +2317,7 @@ static void LoadMultiPartnerCandidatesData(void)
while (1)
{
monId = GetRandomFrontierMonFromSet(trainerId);
if (j % 2 != 0 && gFacilityTrainerMons[gSaveBlock2Ptr->frontier.trainerIds[r10 - 1]].itemTableId == gFacilityTrainerMons[monId].itemTableId)
if (j % 2 != 0 && gFacilityTrainerMons[gSaveBlock2Ptr->frontier.trainerIds[r10 - 1]].heldItem == gFacilityTrainerMons[monId].heldItem)
continue;
for (k = 8; k < r10; k++)
@ -3017,7 +2986,6 @@ static void FillPartnerParty(u16 trainerId)
s32 i, j, k;
u32 firstIdPart = 0, secondIdPart = 0, thirdIdPart = 0;
u32 ivs, level, personality;
u32 friendship;
u16 monId;
u32 otID;
u8 trainerName[(PLAYER_NAME_LENGTH * 3) + 1];
@ -3124,22 +3092,7 @@ static void FillPartnerParty(u16 trainerId)
for (i = 0; i < FRONTIER_MULTI_PARTY_SIZE; i++)
{
monId = gSaveBlock2Ptr->frontier.trainerIds[i + 18];
CreateMonWithEVSpreadNatureOTID(&gPlayerParty[MULTI_PARTY_SIZE + i],
gFacilityTrainerMons[monId].species,
level,
gFacilityTrainerMons[monId].nature,
ivs,
gFacilityTrainerMons[monId].evSpread,
otID);
friendship = MAX_FRIENDSHIP;
for (j = 0; j < MAX_MON_MOVES; j++)
{
SetMonMoveSlot(&gPlayerParty[MULTI_PARTY_SIZE + i], gFacilityTrainerMons[monId].moves[j], j);
if (gMovesInfo[gFacilityTrainerMons[monId].moves[j]].effect == EFFECT_FRUSTRATION)
friendship = 0;
}
SetMonData(&gPlayerParty[MULTI_PARTY_SIZE + i], MON_DATA_FRIENDSHIP, &friendship);
SetMonData(&gPlayerParty[MULTI_PARTY_SIZE + i], MON_DATA_HELD_ITEM, &gBattleFrontierHeldItems[gFacilityTrainerMons[monId].itemTableId]);
CreateFacilityMon(&gFacilityTrainerMons[monId], level, ivs, otID, 0, &gPlayerParty[MULTI_PARTY_SIZE + i]);
for (j = 0; j < PLAYER_NAME_LENGTH + 1; j++)
trainerName[j] = gFacilityTrainers[trainerId].trainerName[j];
SetMonData(&gPlayerParty[MULTI_PARTY_SIZE + i], MON_DATA_OT_NAME, &trainerName);
@ -3499,7 +3452,6 @@ static void FillTentTrainerParty_(u16 trainerId, u8 firstMonId, u8 monCount)
{
s32 i, j;
u16 chosenMonIndices[MAX_FRONTIER_PARTY_SIZE];
u8 friendship;
u8 level = SetTentPtrsGetLevel();
u8 fixedIV = 0;
u8 bfMonCount;
@ -3538,7 +3490,7 @@ static void FillTentTrainerParty_(u16 trainerId, u8 firstMonId, u8 monCount)
for (j = 0; j < i + firstMonId; j++)
{
if (GetMonData(&gEnemyParty[j], MON_DATA_HELD_ITEM, NULL) != ITEM_NONE
&& GetMonData(&gEnemyParty[j], MON_DATA_HELD_ITEM, NULL) == gBattleFrontierHeldItems[gFacilityTrainerMons[monId].itemTableId])
&& GetMonData(&gEnemyParty[j], MON_DATA_HELD_ITEM, NULL) == gFacilityTrainerMons[monId].heldItem)
break;
}
if (j != i + firstMonId)
@ -3555,27 +3507,9 @@ static void FillTentTrainerParty_(u16 trainerId, u8 firstMonId, u8 monCount)
continue;
chosenMonIndices[i] = monId;
// Place the chosen Pokémon into the trainer's party.
CreateMonWithEVSpreadNatureOTID(&gEnemyParty[i + firstMonId],
gFacilityTrainerMons[monId].species,
level,
gFacilityTrainerMons[monId].nature,
fixedIV,
gFacilityTrainerMons[monId].evSpread,
otID);
friendship = MAX_FRIENDSHIP;
// Give the chosen Pokémon its specified moves.
for (j = 0; j < MAX_MON_MOVES; j++)
{
SetMonMoveSlot(&gEnemyParty[i + firstMonId], gFacilityTrainerMons[monId].moves[j], j);
if (gMovesInfo[gFacilityTrainerMons[monId].moves[j]].effect == EFFECT_FRUSTRATION)
friendship = 0; // Frustration is more powerful the lower the pokemon's friendship is.
}
SetMonData(&gEnemyParty[i + firstMonId], MON_DATA_FRIENDSHIP, &friendship);
SetMonData(&gEnemyParty[i + firstMonId], MON_DATA_HELD_ITEM, &gBattleFrontierHeldItems[gFacilityTrainerMons[monId].itemTableId]);
CreateFacilityMon(&gFacilityTrainerMons[monId],
level, fixedIV, otID, 0,
&gEnemyParty[i + firstMonId]);
// The Pokémon was successfully added to the trainer's party, so it's safe to move on to
// the next party slot.

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff