diff options
Diffstat (limited to 'arm9/src')
-rw-r--r-- | arm9/src/hall_of_fame.c | 147 | ||||
-rw-r--r-- | arm9/src/pokemon.c | 8 | ||||
-rw-r--r-- | arm9/src/poketch.c | 262 | ||||
-rw-r--r-- | arm9/src/save_arrays.c | 19 |
4 files changed, 420 insertions, 16 deletions
diff --git a/arm9/src/hall_of_fame.c b/arm9/src/hall_of_fame.c new file mode 100644 index 00000000..7cc1c0f2 --- /dev/null +++ b/arm9/src/hall_of_fame.c @@ -0,0 +1,147 @@ +#include "global.h" +#include "pokemon.h" +#include "save_block_2.h" +#include "MI_memory.h" +#include "party.h" +#include "string16.h" +#include "RTC_api.h" +#include "hall_of_fame.h" + +#pragma thumb on + +u32 Sav2_HOF_sizeof(void) +{ + return sizeof(struct HallOfFame); +} + +void Sav2_HOF_init(struct HallOfFame * hof) +{ + MI_CpuClear32(hof, sizeof(struct HallOfFame)); +} + +void Sav2_HOF_RecordParty(struct HallOfFame * hof, struct PlayerParty * party, RTCDate * date) +{ + GF_ASSERT(hof != NULL); + GF_ASSERT(hof->next_record < NUM_HOF_RECORDS); + if (hof->num_total < 9999) + { + struct HOFParty * hof_party = &hof->parties[hof->next_record]; + int nmons = GetPartyCount(party); + struct String * str = String_ctor(POKEMON_NAME_LENGTH + 1, 0); + MI_CpuClear16(hof_party->party, 6 * sizeof(struct HOFMon)); + int i, j; + for (i = 0, j = 0; i < nmons; i++) + { + struct Pokemon * mon = GetPartyMonByIndex(party, i); + BOOL lock = AcquireMonLock(mon); + if (!GetMonData(mon, MON_DATA_IS_EGG, NULL)) + { + hof_party->party[j].species = (u16)GetMonData(mon, MON_DATA_SPECIES, NULL); + hof_party->party[j].level = (u8)GetMonData(mon, MON_DATA_LEVEL, NULL); + hof_party->party[j].forme = (u8)GetMonData(mon, MON_DATA_FORME, NULL); + hof_party->party[j].personality = GetMonData(mon, MON_DATA_PERSONALITY, NULL); + hof_party->party[j].otid = GetMonData(mon, MON_DATA_OTID, NULL); + hof_party->party[j].moves[0] = (u16)GetMonData(mon, MON_DATA_MOVE1, NULL); + hof_party->party[j].moves[1] = (u16)GetMonData(mon, MON_DATA_MOVE2, NULL); + hof_party->party[j].moves[2] = (u16)GetMonData(mon, MON_DATA_MOVE3, NULL); + hof_party->party[j].moves[3] = (u16)GetMonData(mon, MON_DATA_MOVE4, NULL); + if (str != NULL) + { + GetMonData(mon, MON_DATA_NICKNAME_3, str); + CopyStringToU16Array(str, hof_party->party[j].nickname, POKEMON_NAME_LENGTH + 1); + GetMonData(mon, MON_DATA_OT_NAME_2, str); + CopyStringToU16Array(str, hof_party->party[j].otname, OT_NAME_LENGTH + 1); + } + else + { + hof_party->party[j].nickname[0] = EOS; + hof_party->party[j].otname[0] = EOS; + } + j++; + } + ReleaseMonLock(mon, lock); + } + hof_party->year = (u16)date->year; + hof_party->month = (u8)date->month; + hof_party->day = (u8)date->day; + hof->next_record++; + if (hof->next_record >= NUM_HOF_RECORDS) + hof->next_record = 0; + hof->num_total++; + if (str != NULL) + String_dtor(str); + } +} + +u32 Sav2_HOF_GetNumRecords(struct HallOfFame * hof) +{ + GF_ASSERT(hof != NULL); + GF_ASSERT(hof->next_record < NUM_HOF_RECORDS); + if (hof->num_total < NUM_HOF_RECORDS) + return hof->num_total; + else + return NUM_HOF_RECORDS; +} + +int Sav2_HOF_TranslateRecordIdx(struct HallOfFame * hof, int a1) +{ + GF_ASSERT(hof != NULL); + GF_ASSERT(hof->next_record < NUM_HOF_RECORDS); + GF_ASSERT(a1 < NUM_HOF_RECORDS); + return (int)(hof->num_total - a1); +} + +u32 Sav2_HOF_RecordCountMons(struct HallOfFame * hof, int a1) +{ + GF_ASSERT(hof != NULL); + GF_ASSERT(hof->next_record < NUM_HOF_RECORDS); + GF_ASSERT(a1 < NUM_HOF_RECORDS); + int hofno = (int)(hof->next_record - 1 - a1); + if (hofno < 0) + hofno += NUM_HOF_RECORDS; + struct HOFParty * hof_party = &hof->parties[hofno]; + u32 i; + for (i = 0; i < 6; i++) + { + if (hof_party->party[i].species == SPECIES_NONE) + break; + } + return i; +} + +void Sav2_HOF_GetMonStatsByIndexPair(struct HallOfFame * hof, int a1, int a2, struct HofDisplayMon * dest) +{ + GF_ASSERT(hof != NULL); + GF_ASSERT(hof->next_record < NUM_HOF_RECORDS); + GF_ASSERT(a1 < NUM_HOF_RECORDS); + int hofno = (int)(hof->next_record - 1 - a1); + if (hofno < 0) + hofno += NUM_HOF_RECORDS; + struct HOFMon * mon = &hof->parties[hofno].party[a2]; + dest->species = mon->species; + dest->level = mon->level; + dest->personality = mon->personality; + dest->otid = mon->otid; + dest->forme = mon->forme; + CopyU16ArrayToString(dest->nickname, mon->nickname); + CopyU16ArrayToString(dest->otname, mon->otname); + for (int i = 0; i < 4; i++) + { + dest->moves[i] = mon->moves[i]; + } +} + +void Sav2_HOF_GetClearDate(struct HallOfFame * hof, int a1, RTCDate * dest) +{ + GF_ASSERT(hof != NULL); + GF_ASSERT(hof->next_record < NUM_HOF_RECORDS); + GF_ASSERT(a1 < NUM_HOF_RECORDS); + int hofno = (int)(hof->next_record - 1 - a1); + if (hofno < 0) + hofno += NUM_HOF_RECORDS; + struct HOFParty *party = &hof->parties[hofno]; + dest->year = party->year; + dest->month = party->month; + dest->day = party->day; + dest->week = RTC_WEEK_SUNDAY; +} diff --git a/arm9/src/pokemon.c b/arm9/src/pokemon.c index 97be796b..347cb5ac 100644 --- a/arm9/src/pokemon.c +++ b/arm9/src/pokemon.c @@ -58,7 +58,7 @@ u16 MonEncryptionLCRNG(u32 * seed); u16 CalcMonChecksum(u16 * datap, u32 size); PokemonDataBlock * GetSubstruct(struct BoxPokemon * boxmon, u32 personality, u8 which_struct); void LoadMonBaseStats_HandleAlternateForme(int species, int forme, struct BaseStats * baseStats); -u8 FUN_020690D4(struct BoxPokemon * boxmon); +u8 GetBoxMonUnownLetter(struct BoxPokemon * boxmon); #define ENCRY_ARGS_PTY(mon) (u16 *)&(mon)->party, sizeof((mon)->party), (mon)->box.pid #define ENCRY_ARGS_BOX(boxmon) (u16 *)&(boxmon)->substructs, sizeof((boxmon)->substructs), (boxmon)->checksum @@ -2458,12 +2458,12 @@ u32 FUN_020690C8(void) return sizeof(struct BoxPokemon); } -u8 FUN_020690CC(struct Pokemon * pokemon) +u8 GetMonUnownLetter(struct Pokemon * pokemon) { - return FUN_020690D4(&pokemon->box); + return GetBoxMonUnownLetter(&pokemon->box); } -u8 FUN_020690D4(struct BoxPokemon * boxmon) +u8 GetBoxMonUnownLetter(struct BoxPokemon * boxmon) { return (u8)GetBoxMonData(boxmon, MON_DATA_FORME, NULL); } diff --git a/arm9/src/poketch.c b/arm9/src/poketch.c new file mode 100644 index 00000000..54dff12b --- /dev/null +++ b/arm9/src/poketch.c @@ -0,0 +1,262 @@ +#include "global.h" +#include "MI_memory.h" +#include "pokemon.h" +#include "poketch.h" + +#pragma thumb on + +extern u16 BoxMon_GetAlternateForme(struct BoxPokemon * mon); + +static const u8 sMarkingMapInitialPos[][2] = { + { 0x68, 0x98 }, + { 0x78, 0x98 }, + { 0x88, 0x98 }, + { 0x98, 0x98 }, + { 0xA8, 0x98 }, + { 0xB8, 0x98 }, +}; + +u32 Sav2_Poketch_sizeof(void) +{ + return sizeof(struct SavePoketch); +} + +void Sav2_Poketch_init(struct SavePoketch * poketch) +{ + int i; + + for (i = 0; i < 32; i++) + { + poketch->unlockedApps[i] = 0; + } + poketch->numApps = 0; + poketch->selectedApp = 0; + poketch->isGiven = 0; + poketch->color = 0; + poketch->pedometerActive = 0; + poketch->stepCounter = 0; + poketch->alarmActive = 0; + poketch->alarmHour = 0; + poketch->alarmMinute = 0; + poketch->calendarMonth = 1; // January + poketch->calendarFlags = 0; + for (i = 0; i < 6; i++) + { + poketch->markingMapPos[i][0] = sMarkingMapInitialPos[i][0]; + poketch->markingMapPos[i][1] = sMarkingMapInitialPos[i][1]; + } + for (i = 0; i < 12; i++) + { + poketch->pokemonHistory[i][0] = SPECIES_NONE; + poketch->pokemonHistory[i][1] = 0; + } + poketch->dotArtistEnabled = 0; + Sav2_Poketch_UnlockApp(poketch, POKETCH_DIGITAL_WATCH); +} + +void Sav2_Poketch_Give(struct SavePoketch * poketch) +{ + poketch->isGiven = TRUE; +} + +BOOL Sav2_Poketch_IsGiven(struct SavePoketch * poketch) +{ + return poketch->isGiven; +} + +u8 Sav2_Poketch_AppIsUnlocked(struct SavePoketch * poketch, PoketchApp app) +{ + return poketch->unlockedApps[app]; +} + +BOOL Sav2_Poketch_UnlockApp(struct SavePoketch * poketch, PoketchApp app) +{ + GF_ASSERT(app >= FIRST_POKETCH_APP_ID && app < NUM_POKETCH_APPS); + if (poketch->numApps < NUM_POKETCH_APPS && !poketch->unlockedApps[app]) + { + poketch->unlockedApps[app] = TRUE; + poketch->numApps++; + if (app == POKETCH_PEDOMETER) // pedometer + { + poketch->pedometerActive = TRUE; + } + return TRUE; + } + return FALSE; +} + +PoketchApp Sav2_Poketch_GetSelectedApp(struct SavePoketch * poketch) +{ + return (PoketchApp)poketch->selectedApp; +} + +PoketchApp Sav2_Poketch_CycleNextApp(struct SavePoketch * poketch) +{ + PoketchApp app = (PoketchApp)poketch->selectedApp; + PoketchApp prev = app; + + while (1) + { + if (++app >= NUM_POKETCH_APPS) + app = FIRST_POKETCH_APP_ID; + if (app == prev) + break; + if (poketch->unlockedApps[app]) + break; + } + poketch->selectedApp = (s8)app; + return (PoketchApp)poketch->selectedApp; +} + +u8 Sav2_Poketch_GetScreenTint(struct SavePoketch * poketch) +{ + GF_ASSERT(poketch != NULL); + return poketch->color; +} + +void Sav2_Poketch_SetScreenTint(struct SavePoketch * poketch, u32 color) +{ + GF_ASSERT(poketch != NULL); + GF_ASSERT(color < 8); + poketch->color = (u8)color; +} + +u32 Sav2_Poketch_GetStepCounter(struct SavePoketch * poketch) +{ + return poketch->stepCounter; +} + +void Sav2_Poketch_SetStepCounter(struct SavePoketch * poketch, u32 steps) +{ + if (poketch->pedometerActive) + poketch->stepCounter = steps; +} + +BOOL Sav2_Poketch_GetAlarmState(struct SavePoketch * poketch) +{ + return poketch->alarmActive; +} + +void Sav2_Poketch_GetAlarmSetTime(struct SavePoketch * poketch, u32 * hour_p, u32 * min_p) +{ + *hour_p = poketch->alarmHour; + *min_p = poketch->alarmMinute; +} + +void Sav2_Poketch_SetAlarm(struct SavePoketch * poketch, BOOL enabled, u32 hour, u32 minute) +{ + poketch->alarmActive = enabled; + poketch->alarmHour = hour; + poketch->alarmMinute = minute; +} + +void Sav2_Poketch_CalendarDateHighlight(struct SavePoketch * poketch, u32 month, u32 day) +{ + if (poketch->calendarMonth == month) + { + poketch->calendarFlags |= (1u << (day - 1)); + } + else + { + poketch->calendarMonth = (u8)month; + poketch->calendarFlags = (1u << (day - 1)); + } +} + +void Sav2_Poketch_CalendarDateUnhighlight(struct SavePoketch * poketch, u32 month, u32 day) +{ + if (poketch->calendarMonth == month) + { + poketch->calendarFlags &= ~(1u << (day - 1)); + } + else + { + poketch->calendarMonth = (u8)month; + poketch->calendarFlags = 0; + } +} + +BOOL Sav2_Poketch_CalendarDateIsHighlighted(struct SavePoketch * poketch, u32 month, u32 day) +{ + if (poketch->calendarMonth == month) + { + return (BOOL)((poketch->calendarFlags >> (day - 1)) & 1); + } + else + { + return FALSE; + } +} + +void Sav2_Poketch_MarkingMapSetPos(struct SavePoketch * poketch, s32 mark, u8 x, u8 y) +{ + GF_ASSERT(mark < 6); + poketch->markingMapPos[mark][0] = x; + poketch->markingMapPos[mark][1] = y; +} + +void Sav2_Poketch_MarkingMapGetPos(struct SavePoketch * poketch, s32 mark, u8 * x_p, u8 * y_p) +{ + GF_ASSERT(mark < 6); + *x_p = poketch->markingMapPos[mark][0]; + *y_p = poketch->markingMapPos[mark][1]; +} + +u32 Sav2_Poketch_DotArtistIsEnabled(struct SavePoketch * poketch) +{ + return poketch->dotArtistEnabled; +} + +void Sav2_Poketch_DotArtistGetDrawing(struct SavePoketch * poketch, void * grid) +{ + if (poketch->dotArtistEnabled) + { + MI_CpuCopy8(poketch->dotArtistGrid, grid, DOT_ARTIST_SIZE); + } +} + +void Sav2_Poketch_DotArtistSetDrawingAndEnable(struct SavePoketch * poketch, void * grid) +{ + MI_CpuCopy8(grid, poketch->dotArtistGrid, DOT_ARTIST_SIZE); + poketch->dotArtistEnabled = TRUE; +} + +void Sav2_Poketch_PokemonHistoryAddMon(struct SavePoketch * poketch, struct BoxPokemon * mon) +{ + int i = Sav2_Poketch_PokemonHistoryGetFirstEmptySlot(poketch); + if (i >= 12) + { + for (i = 0; i < 11; i++) + { + poketch->pokemonHistory[i][0] = poketch->pokemonHistory[i + 1][0]; + poketch->pokemonHistory[i][1] = poketch->pokemonHistory[i + 1][1]; + } + i = 11; + } + poketch->pokemonHistory[i][0] = (u16)GetBoxMonData(mon, MON_DATA_SPECIES, NULL); + poketch->pokemonHistory[i][1] = BoxMon_GetAlternateForme(mon); +} + +int Sav2_Poketch_PokemonHistoryGetFirstEmptySlot(struct SavePoketch * poketch) +{ + int i; + for (i = 0; i < 12; i++) + { + if (poketch->pokemonHistory[i][0] == SPECIES_NONE) + return i; + } + return i; +} + +void Sav2_Poketch_PokemonHistoryGetSlotN(struct SavePoketch * poketch, s32 i, u32 * species_p, u32 * forme_p) +{ + GF_ASSERT(i < 12); + GF_ASSERT(poketch->pokemonHistory[i][0] != SPECIES_NONE); + *species_p = poketch->pokemonHistory[i][0]; + *forme_p = poketch->pokemonHistory[i][1]; +} + +struct SavePoketch * Sav2_Poketch_get(struct SaveBlock2 * sav2) +{ + return (struct SavePoketch *)SavArray_get(sav2, 5); +} diff --git a/arm9/src/save_arrays.c b/arm9/src/save_arrays.c index 58e1ff4c..797539d2 100644 --- a/arm9/src/save_arrays.c +++ b/arm9/src/save_arrays.c @@ -4,11 +4,13 @@ #include "save_block_2.h" #include "party.h" #include "event_data.h" +#include "pokemon_storage_system.h" +#include "sav_system_info.h" +#include "poketch.h" +#include "hall_of_fame.h" +#include "unk_020286F8.h" -extern u32 FUN_0202B034(void); extern u32 FUN_0202AC20(void); -extern u32 Sav2_SysInfo_sizeof(void); -extern u32 FUN_0204BE14(void); extern u32 FUN_02034D7C(void); extern u32 FUN_02023D64(void); extern u32 FUN_02023C40(void); @@ -20,7 +22,6 @@ extern u32 FUN_02023AC8(void); extern u32 FUN_02026FD8(void); extern u32 FUN_02025844(void); extern u32 FUN_02028054(void); -extern u32 FUN_020286F8(void); extern u32 FUN_02028980(void); extern u32 FUN_02029A84(void); extern u32 FUN_02029FB0(void); @@ -37,11 +38,7 @@ extern u32 FUN_02029AE0(void); extern u32 FUN_0202BE98(void); extern u32 FUN_0202C0E0(void); extern u32 FUN_02013B28(void); -extern u32 PCStorage_sizeof(void); -extern void FUN_0202B03C(void *); extern void FUN_0202AC28(void *); -extern void Sav2_SysInfo_init(void *); -extern void FUN_0204BE18(void *); extern void FUN_02034D98(void *); extern void FUN_02024378(void *); extern void FUN_02023C48(void *); @@ -53,7 +50,6 @@ extern void FUN_02023AD8(void *); extern void FUN_02026F60(void *); extern void FUN_0202584C(void *); extern void FUN_0202805C(void *); -extern void FUN_02028724(void *); extern void FUN_02028994(void *); extern void FUN_02029A8C(void *); extern void FUN_02029FB8(void *); @@ -70,10 +66,9 @@ extern void FUN_02029AE8(void *); extern void FUN_0202BEA0(void *); extern void FUN_0202C0E4(void *); extern void FUN_02013B2C(void *); -extern void PCStorage_init(void *); const struct SaveChunkHeader UNK_020EE6E0[] = { - { 0, 32, (SAVSIZEFN)FUN_0202B034, (SAVINITFN)FUN_0202B03C }, + { 0, 32, (SAVSIZEFN)Sav2_HOF_sizeof, (SAVINITFN)Sav2_HOF_init }, { 1, 35, (SAVSIZEFN)FUN_0202AC20, (SAVINITFN)FUN_0202AC28 } }; @@ -83,7 +78,7 @@ const struct SaveChunkHeader UNK_020EE700[] = { { 2, 0, (SAVSIZEFN)SavArray_Party_sizeof, (SAVINITFN)SavArray_Party_init }, { 3, 0, (SAVSIZEFN)Sav2_Bag_sizeof, (SAVINITFN)Sav2_Bag_init }, { 4, 0, (SAVSIZEFN)SavArray_Flags_sizeof, (SAVINITFN)SavArray_Flags_init }, - { 5, 0, (SAVSIZEFN)FUN_0204BE14, (SAVINITFN)FUN_0204BE18 }, + { 5, 0, (SAVSIZEFN)Sav2_Poketch_sizeof, (SAVINITFN)Sav2_Poketch_init }, { 6, 0, (SAVSIZEFN)FUN_02034D7C, (SAVINITFN)FUN_02034D98 }, { 7, 0, (SAVSIZEFN)FUN_02023D64, (SAVINITFN)FUN_02024378 }, { 8, 0, (SAVSIZEFN)FUN_02023C40, (SAVINITFN)FUN_02023C48 }, |