#include "script_manager.h" #include #include #include "constants/battle.h" #include "generated/map_headers.h" #include "generated/text_banks.h" #include "data/field/hidden_items.h" #include "field/field_system.h" #include "field/scripts/scr_seq.naix" #include "field_menu.h" #include "field_task.h" #include "heap.h" #include "map_header.h" #include "map_header_data.h" #include "map_object.h" #include "math.h" #include "message.h" #include "narc.h" #include "player_avatar.h" #include "strbuf.h" #include "trainer_data.h" #include "vars_flags.h" #include "constdata/const_020EAB80.h" #include "constdata/const_020EAC58.h" static BOOL FieldTask_RunScript(FieldTask *taskManager); static ScriptManager *ScriptManager_New(); static void ScriptContext_Free(ScriptContext *ctx); static void sub_0203EA68(FieldSystem *fieldSystem, ScriptManager *scriptManager, u16 scriptID, MapObject *object, void *saveType); static void sub_0203EAF4(FieldSystem *fieldSystem, ScriptContext *ctx, u16 scriptID, u8 dummy); static u16 ScriptContext_LoadAndOffsetID(FieldSystem *fieldSystem, ScriptContext *ctx, u16 scriptID); static void ScriptContext_Load(FieldSystem *fieldSystem, ScriptContext *ctx, int scriptFile, u32 textBank); static void ScriptContext_LoadFromCurrentMap(FieldSystem *fieldSystem, ScriptContext *ctx); static void sub_0203F0E4(ScriptContext *ctx, u16 param1); static void *ScriptContext_LoadScripts(int headerID); static u32 MapHeaderToMsgArchive(int headerID); static BOOL ScriptManager_SetHiddenItem(ScriptManager *scriptManager, u16 scriptID); static u16 sub_0203F610(const u8 *param0, u8 param1); static u16 sub_0203F638(FieldSystem *fieldSystem, const u8 *param1, u8 param2); void ScriptManager_Set(FieldSystem *fieldSystem, u16 scriptID, MapObject *object) { ScriptManager *scriptManager = ScriptManager_New(); sub_0203EA68(fieldSystem, scriptManager, scriptID, object, NULL); FieldSystem_CreateTask(fieldSystem, FieldTask_RunScript, scriptManager); } void ScriptManager_SetApproachingTrainer(FieldSystem *fieldSystem, MapObject *object, int sightRange, int direction, int scriptID, int trainerID, int trainerType, int approachNum) { ScriptManager *scriptManager = FieldTask_GetEnv(fieldSystem->task); ApproachingTrainer *trainer = &scriptManager->trainers[approachNum]; trainer->sightRange = sightRange; trainer->direction = direction; trainer->scriptID = scriptID; trainer->trainerID = trainerID; trainer->trainerType = trainerType; trainer->object = object; } void ScriptManager_Start(FieldTask *taskManager, u16 scriptID, MapObject *object, void *saveType) { FieldSystem *fieldSystem = FieldTask_GetFieldSystem(taskManager); ScriptManager *scriptManager = ScriptManager_New(); sub_0203EA68(fieldSystem, scriptManager, scriptID, object, saveType); FieldTask_InitCall(taskManager, FieldTask_RunScript, scriptManager); } void ScriptManager_Change(FieldTask *taskManager, u16 scriptID, MapObject *object) { FieldSystem *fieldSystem = FieldTask_GetFieldSystem(taskManager); ScriptManager *scriptManager = ScriptManager_New(); sub_0203EA68(fieldSystem, scriptManager, scriptID, object, NULL); FieldTask_InitJump(taskManager, FieldTask_RunScript, scriptManager); } static BOOL FieldTask_RunScript(FieldTask *taskManager) { int i; FieldSysFunc scriptFunction; ScriptContext *ctx = NULL; ScriptManager *scriptManager = FieldTask_GetEnv(taskManager); FieldSystem *fieldSystem = FieldTask_GetFieldSystem(taskManager); switch (scriptManager->state) { case 0: scriptManager->ctx[SCRIPT_CONTEXT_MAIN] = ScriptContext_CreateAndStart(fieldSystem, scriptManager->scriptID); scriptManager->numActiveContexts = 1; scriptManager->strTemplate = StringTemplate_New(8, 64, 11); scriptManager->msgBuf = Strbuf_Init(1024, 11); scriptManager->tmpBuf = Strbuf_Init(1024, 11); scriptManager->state++; case 1: for (i = 0; i < NUM_SCRIPT_CONTEXTS; i++) { ctx = scriptManager->ctx[i]; if (ctx != NULL && ScriptContext_Run(ctx) == FALSE) { ScriptContext_Free(ctx); GF_ASSERT(scriptManager->numActiveContexts != 0); scriptManager->ctx[i] = NULL; scriptManager->numActiveContexts--; } } if (scriptManager->numActiveContexts <= 0) { scriptFunction = scriptManager->function; StringTemplate_Free(scriptManager->strTemplate); Strbuf_Free(scriptManager->msgBuf); Strbuf_Free(scriptManager->tmpBuf); scriptManager->magic = 0; Heap_FreeToHeap(scriptManager); if (scriptFunction != NULL) { scriptFunction(fieldSystem); return FALSE; } return TRUE; } break; } return FALSE; } static ScriptManager *ScriptManager_New() { ScriptManager *scriptManager = Heap_AllocFromHeap(11, sizeof(ScriptManager)); GF_ASSERT(scriptManager != NULL); memset(scriptManager, 0, sizeof(ScriptManager)); scriptManager->magic = SCRIPT_MANAGER_MAGIC_NUMBER; return scriptManager; } static void ScriptContext_Free(ScriptContext *ctx) { MessageLoader_Free(ctx->loader); Heap_FreeToHeap(ctx->scripts); Heap_FreeToHeap(ctx); } static void sub_0203EA68(FieldSystem *fieldSystem, ScriptManager *scriptManager, u16 scriptID, MapObject *object, void *saveType) { u16 *targetID = ScriptManager_GetMemberPtr(scriptManager, SCRIPT_DATA_TARGET_OBJECT_ID); scriptManager->playerDir = PlayerAvatar_GetDir(fieldSystem->playerAvatar); scriptManager->targetObject = object; scriptManager->scriptID = scriptID; scriptManager->saveType = saveType; if (object != NULL) { *targetID = MapObject_GetLocalID(object); } if (scriptID >= SCRIPT_ID_OFFSET_HIDDEN_ITEMS && scriptID <= SCRIPT_ID_OFFSET_SAFARI_ZONE - 1) { ScriptManager_SetHiddenItem(scriptManager, scriptID); } } ScriptContext *ScriptContext_CreateAndStart(FieldSystem *fieldSystem, u16 scriptID) { ScriptContext *ctx = Heap_AllocFromHeap(11, sizeof(ScriptContext)); GF_ASSERT(ctx != NULL); ScriptContext_Init(ctx, Unk_020EAC58, Unk_020EAB80); sub_0203EAF4(fieldSystem, ctx, scriptID, 0); return ctx; } static void sub_0203EAF4(FieldSystem *fieldSystem, ScriptContext *ctx, u16 scriptID, u8 dummy) { ctx->fieldSystem = fieldSystem; u16 offsetID = ScriptContext_LoadAndOffsetID(fieldSystem, ctx, scriptID); ScriptContext_Start(ctx, ctx->scripts); sub_0203F0E4(ctx, offsetID); ScriptContext_SetTask(ctx, fieldSystem->task); } static u16 ScriptContext_LoadAndOffsetID(FieldSystem *fieldSystem, ScriptContext *ctx, u16 scriptID) { u16 retScriptID = scriptID; if (retScriptID >= 10490) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0499, TEXT_BANK_UNK_0541); retScriptID -= 10490; } else if (retScriptID >= 10450) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0500, TEXT_BANK_UNK_0016); retScriptID -= 10450; } else if (retScriptID >= 10400) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0400, TEXT_BANK_UNK_0203); retScriptID -= 10400; } else if (retScriptID >= 10300) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_1051, TEXT_BANK_UNK_0552); retScriptID -= 10300; } else if (retScriptID >= 10200) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0407, TEXT_BANK_UNK_0379); retScriptID -= 10200; } else if (retScriptID >= 10150) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_1116, TEXT_BANK_UNK_0621); retScriptID -= 10150; } else if (retScriptID >= 10100) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_1115, TEXT_BANK_UNK_0622); retScriptID -= 10100; } else if (retScriptID >= 10000) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0409, TEXT_BANK_UNK_0381); retScriptID -= 10000; } else if (retScriptID >= 9950) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0411, TEXT_BANK_UNK_0383); retScriptID -= 9950; } else if (retScriptID >= 9900) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0397, TEXT_BANK_COMMON_STRINGS); retScriptID -= 9900; } else if (retScriptID >= 9800) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0212, TEXT_BANK_UNK_0217); retScriptID -= 9800; } else if (retScriptID >= 9700) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0422, TEXT_BANK_UNK_0429); retScriptID -= 9700; } else if (retScriptID >= 9600) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0412, TEXT_BANK_COMMON_STRINGS); retScriptID -= 9600; } else if (retScriptID >= 9500) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0501, TEXT_BANK_UNK_0547); retScriptID -= 9500; } else if (retScriptID >= 9400) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0426, TEXT_BANK_UNK_0432); retScriptID -= 9400; } else if (retScriptID >= 9300) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0406, TEXT_BANK_UNK_0374); retScriptID -= 9300; } else if (retScriptID >= 9200) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0423, TEXT_BANK_UNK_0430); retScriptID -= 9200; } else if (retScriptID >= 9100) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0000, TEXT_BANK_UNK_0011); retScriptID -= 9100; } else if (retScriptID >= 9000) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0213, TEXT_BANK_UNK_0221); retScriptID -= 9000; } else if (retScriptID >= 8970) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0425, TEXT_BANK_UNK_0007); retScriptID -= 8970; } else if (retScriptID >= 8950) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0498, TEXT_BANK_UNK_0539); retScriptID -= 8950; } else if (retScriptID >= 8900) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0424, TEXT_BANK_UNK_0431); retScriptID -= 8900; } else if (retScriptID >= SCRIPT_ID_OFFSET_SAFARI_ZONE) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0497, TEXT_BANK_UNK_0538); retScriptID -= SCRIPT_ID_OFFSET_SAFARI_ZONE; } else if (retScriptID >= SCRIPT_ID_OFFSET_HIDDEN_ITEMS) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0408, TEXT_BANK_UNK_0380); retScriptID -= SCRIPT_ID_OFFSET_HIDDEN_ITEMS; } else if (retScriptID >= 7000) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0404, TEXT_BANK_UNK_0369); retScriptID -= 7000; } else if (retScriptID >= SCRIPT_ID_OFFSET_DOUBLE_BATTLES) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_1114, TEXT_BANK_COMMON_STRINGS); retScriptID -= SCRIPT_ID_OFFSET_DOUBLE_BATTLES; } else if (retScriptID >= SCRIPT_ID_OFFSET_SINGLE_BATTLES) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_1114, TEXT_BANK_COMMON_STRINGS); retScriptID -= SCRIPT_ID_OFFSET_SINGLE_BATTLES; } else if (retScriptID >= 2800) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0413, TEXT_BANK_UNK_0397); retScriptID -= 2800; } else if (retScriptID >= 2500) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0001, TEXT_BANK_UNK_0017); retScriptID -= 2500; } else if (retScriptID >= 2000) { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0211, TEXT_BANK_COMMON_STRINGS); retScriptID -= 2000; } else if (retScriptID >= 1) { ScriptContext_LoadFromCurrentMap(fieldSystem, ctx); retScriptID -= 1; } else { ScriptContext_Load(fieldSystem, ctx, scripts_unk_0402, TEXT_BANK_UNK_0355); retScriptID = 0; } return retScriptID; } static void ScriptContext_Load(FieldSystem *fieldSystem, ScriptContext *ctx, int scriptFile, u32 textBank) { u8 *scripts = NARC_AllocAndReadWholeMemberByIndexPair(NARC_INDEX_FIELDDATA__SCRIPT__SCR_SEQ, scriptFile, 11); ctx->scripts = scripts; ctx->loader = MessageLoader_Init(MESSAGE_LOADER_NARC_HANDLE, NARC_INDEX_MSGDATA__PL_MSG, textBank, 11); } static void ScriptContext_LoadFromCurrentMap(FieldSystem *fieldSystem, ScriptContext *ctx) { u8 *scripts = ScriptContext_LoadScripts(fieldSystem->location->mapId); ctx->scripts = scripts; ctx->loader = MessageLoader_Init(MESSAGE_LOADER_NARC_HANDLE, NARC_INDEX_MSGDATA__PL_MSG, MapHeaderToMsgArchive(fieldSystem->location->mapId), 11); } void *ScriptManager_GetMemberPtr(ScriptManager *scriptManager, u32 member) { ApproachingTrainer *trainer; switch (member) { case 0: return &scriptManager->unk_10; case SCRIPT_MANAGER_WINDOW: return &scriptManager->window; case SCRIPT_MANAGER_UI_CONTROL: return &scriptManager->ctrlUI; case SCRIPT_MANAGER_MESSAGE_ID: return &scriptManager->messageID; case SCRIPT_MANAGER_MOVEMENT_COUNT: return &scriptManager->movementCount; case SCRIPT_MANAGER_SUB_CONTEXT_ACTIVE: return &scriptManager->subCtxActive; case SCRIPT_MANAGER_IS_MSG_BOX_OPEN: return &scriptManager->isMsgBoxOpen; case SCRIPT_MANAGER_NUM_ACTIVE_CONTEXTS: return &scriptManager->numActiveContexts; case SCRIPT_MANAGER_SCRIPT_ID: return &scriptManager->scriptID; case SCRIPT_MANAGER_PLAYER_DIR: return &scriptManager->playerDir; case SCRIPT_MANAGER_TARGET_OBJECT: return &scriptManager->targetObject; case SCRIPT_MANAGER_CAMERA_OBJECT: return &scriptManager->cameraObject; case SCRIPT_MANAGER_SAVE_TYPE: return &scriptManager->saveType; case SCRIPT_MANAGER_MAIN_CONTEXT: return &scriptManager->ctx[SCRIPT_CONTEXT_MAIN]; case SCRIPT_MANAGER_SUB_CONTEXT: return &scriptManager->ctx[SCRIPT_CONTEXT_SUB]; case SCRIPT_MANAGER_STR_TEMPLATE: return &scriptManager->strTemplate; case SCRIPT_MANAGER_MESSAGE_BUF: return &scriptManager->msgBuf; case SCRIPT_MANAGER_TEMPORARY_BUF: return &scriptManager->tmpBuf; case SCRIPT_MANAGER_SAVING_ICON: return &scriptManager->savingIcon; case SCRIPT_MANAGER_PARTY_MANAGEMENT_DATA: return &scriptManager->partyManagementDataPtr; case SCRIPT_MANAGER_DATA_PTR: return &scriptManager->dataPtr; case 21: return &scriptManager->unk_B0; case SCRIPT_MANAGER_PLAYER_TASK: return &scriptManager->playerTask; case SCRIPT_MANAGER_BATTLE_RESULT: return &scriptManager->battleResult; case SCRIPT_MANAGER_TRAINER_0_SIGHT_RANGE: trainer = &scriptManager->trainers[0]; return &trainer->sightRange; case SCRIPT_MANAGER_TRAINER_0_DIRECTION: trainer = &scriptManager->trainers[0]; return &trainer->direction; case SCRIPT_MANAGER_TRAINER_0_SCRIPT_ID: trainer = &scriptManager->trainers[0]; return &trainer->scriptID; case SCRIPT_MANAGER_TRAINER_0_ID: trainer = &scriptManager->trainers[0]; return &trainer->trainerID; case SCRIPT_MANAGER_TRAINER_0_TYPE: trainer = &scriptManager->trainers[0]; return &trainer->trainerType; case SCRIPT_MANAGER_TRAINER_0_MAP_OBJECT: trainer = &scriptManager->trainers[0]; return &trainer->object; case SCRIPT_MANAGER_TRAINER_0_TASK: trainer = &scriptManager->trainers[0]; return &trainer->task; case SCRIPT_MANAGER_TRAINER_1_SIGHT_RANGE: trainer = &scriptManager->trainers[1]; return &trainer->sightRange; case SCRIPT_MANAGER_TRAINER_1_DIRECTION: trainer = &scriptManager->trainers[1]; return &trainer->direction; case SCRIPT_MANAGER_TRAINER_1_SCRIPT_ID: trainer = &scriptManager->trainers[1]; return &trainer->scriptID; case SCRIPT_MANAGER_TRAINER_1_ID: trainer = &scriptManager->trainers[1]; return &trainer->trainerID; case SCRIPT_MANAGER_TRAINER_1_TYPE: trainer = &scriptManager->trainers[1]; return &trainer->trainerType; case SCRIPT_MANAGER_TRAINER_1_MAP_OBJECT: trainer = &scriptManager->trainers[1]; return &trainer->object; case SCRIPT_MANAGER_TRAINER_1_TASK: trainer = &scriptManager->trainers[1]; return &trainer->task; case SCRIPT_MANAGER_COIN_WINDOW: return &scriptManager->coinWindow; case SCRIPT_MANAGER_MONEY_WINDOW: return &scriptManager->moneyWindow; case SCRIPT_MANAGER_SAVE_INFO_WINDOW: return &scriptManager->saveInfoWin; case SCRIPT_DATA_PARAMETER_0: case SCRIPT_DATA_PARAMETER_1: case SCRIPT_DATA_PARAMETER_2: case SCRIPT_DATA_PARAMETER_3: case SCRIPT_DATA_BG3_SCROLL_COUNT_X: case SCRIPT_DATA_BG3_SCROLL_COUNT_Y: case SCRIPT_DATA_DUMMY_0: case SCRIPT_DATA_DUMMY_1: case SCRIPT_DATA_BG3_SCROLL_DIST_X: case SCRIPT_DATA_BG3_SCROLL_DIR_X: case SCRIPT_DATA_BG3_SCROLL_DIST_Y: case SCRIPT_DATA_BG3_SCROLL_DIR_Y: case SCRIPT_DATA_DUMMY_2: case SCRIPT_DATA_TARGET_OBJECT_ID: return &scriptManager->data[member - SCRIPT_DATA_START]; } GF_ASSERT(FALSE); return NULL; } void *FieldSystem_GetScriptMemberPtr(FieldSystem *fieldSystem, u32 member) { ScriptManager *script = FieldTask_GetEnv(fieldSystem->task); GF_ASSERT(script->magic == SCRIPT_MANAGER_MAGIC_NUMBER); return ScriptManager_GetMemberPtr(script, member); } void sub_0203F0C0(FieldSystem *fieldSystem) { ScriptManager *scriptManager = FieldTask_GetEnv(fieldSystem->task); if (sub_0203A9C8(fieldSystem) == 1) { scriptManager->function = sub_0203AB00; } } static void sub_0203F0E4(ScriptContext *ctx, u16 param1) { ctx->scriptPtr += (param1 * 4); ctx->scriptPtr += ScriptContext_ReadWord(ctx); } static void *ScriptContext_LoadScripts(int headerID) { return NARC_AllocAndReadWholeMemberByIndexPair(NARC_INDEX_FIELDDATA__SCRIPT__SCR_SEQ, MapHeader_GetScriptsArchiveID(headerID), 11); } static u32 MapHeaderToMsgArchive(int headerID) { return MapHeader_GetMsgArchiveID(headerID); } u16 *FieldSystem_GetVarPointer(FieldSystem *fieldSystem, u16 varID) { VarsFlags *varsFlags = SaveData_GetVarsFlags(fieldSystem->saveData); if (varID < VARS_START) { return NULL; } if (varID < SPECIAL_VARS_START) { return VarsFlags_GetVarAddress(varsFlags, varID); } return FieldSystem_GetScriptMemberPtr(fieldSystem, SCRIPT_DATA_START + varID - SPECIAL_VARS_START); } u16 FieldSystem_TryGetVar(FieldSystem *fieldSystem, u16 varID) { u16 *var = FieldSystem_GetVarPointer(fieldSystem, varID); if (var == NULL) { return varID; } return *var; } u16 sub_0203F164(FieldSystem *fieldSystem, u16 varID) { GF_ASSERT(varID < 16); return FieldSystem_TryGetVar(fieldSystem, (((0 + VARS_START) + 32) + varID)); } BOOL FieldSystem_CheckFlag(FieldSystem *fieldSystem, u16 flagID) { return VarsFlags_CheckFlag(SaveData_GetVarsFlags(fieldSystem->saveData), flagID); } void FieldSystem_SetFlag(FieldSystem *fieldSystem, u16 flagID) { VarsFlags_SetFlag(SaveData_GetVarsFlags(fieldSystem->saveData), flagID); } void FieldSystem_ClearFlag(FieldSystem *fieldSystem, u16 flagID) { VarsFlags_ClearFlag(SaveData_GetVarsFlags(fieldSystem->saveData), flagID); } void FieldSystem_ClearLocalFlags(FieldSystem *fieldSystem) { VarsFlags *varsFlags = SaveData_GetVarsFlags(fieldSystem->saveData); memset(VarsFlags_GetFlagChunk(varsFlags, 1), 0, (64 / 8)); memset(VarsFlags_GetVarAddress(varsFlags, (0 + VARS_START)), 0, 2 * 32); } void sub_0203F1FC(FieldSystem *fieldSystem) { VarsFlags *varsFlags = SaveData_GetVarsFlags(fieldSystem->saveData); memset(VarsFlags_GetFlagChunk(varsFlags, 2400 + 320), 0, 192 / 8); } void FieldSystem_SetScriptParameters(FieldSystem *fieldSystem, u16 scriptParam0, u16 scriptParam1, u16 scriptParam2, u16 scriptParam3) { *(u16 *)FieldSystem_GetScriptMemberPtr(fieldSystem, SCRIPT_DATA_PARAMETER_0) = scriptParam0; *(u16 *)FieldSystem_GetScriptMemberPtr(fieldSystem, SCRIPT_DATA_PARAMETER_1) = scriptParam1; *(u16 *)FieldSystem_GetScriptMemberPtr(fieldSystem, SCRIPT_DATA_PARAMETER_2) = scriptParam2; *(u16 *)FieldSystem_GetScriptMemberPtr(fieldSystem, SCRIPT_DATA_PARAMETER_3) = scriptParam3; } u16 Script_GetTrainerID(u16 scriptID) { if (scriptID < SCRIPT_ID_OFFSET_DOUBLE_BATTLES) { return scriptID - SCRIPT_ID_OFFSET_SINGLE_BATTLES + 1; } else { return scriptID - SCRIPT_ID_OFFSET_DOUBLE_BATTLES + 1; } } int Script_GetTrainerBattlerIndex(u16 scriptID) { return !(scriptID < SCRIPT_ID_OFFSET_DOUBLE_BATTLES); } BOOL Script_IsTrainerDoubleBattle(u16 trainerID) { return Trainer_LoadParam(trainerID, TRDATA_BATTLE_TYPE) != BATTLE_TYPE_SINGLES; } BOOL Script_IsTrainerDefeated(FieldSystem *fieldSystem, u16 trainerID) { return VarsFlags_CheckFlag(SaveData_GetVarsFlags(fieldSystem->saveData), FLAG_OFFSET_TRAINER_DEFEATED + trainerID); } void Script_SetTrainerDefeated(FieldSystem *fieldSystem, u16 trainerID) { VarsFlags_SetFlag(SaveData_GetVarsFlags(fieldSystem->saveData), FLAG_OFFSET_TRAINER_DEFEATED + trainerID); } void Script_ClearTrainerDefeated(FieldSystem *fieldSystem, u16 trainerID) { VarsFlags_ClearFlag(SaveData_GetVarsFlags(fieldSystem->saveData), FLAG_OFFSET_TRAINER_DEFEATED + trainerID); } u16 Script_GetHiddenItemFlag(u16 scriptID) { return scriptID - SCRIPT_ID_OFFSET_HIDDEN_ITEMS + FLAG_OFFSET_HIDDEN_ITEMS; } u16 Script_GetHiddenItemScript(u16 scriptID) { return scriptID - SCRIPT_ID_OFFSET_HIDDEN_ITEMS; } static u16 sIronIslandHiddenItemFlags[][2] = { { MAP_HEADER_IRON_ISLAND_B1F_RIGHT_ROOM, 0x34 }, { MAP_HEADER_IRON_ISLAND_B2F_RIGHT_ROOM, 0x35 }, { MAP_HEADER_IRON_ISLAND_B2F_LEFT_ROOM, 0x36 }, { MAP_HEADER_IRON_ISLAND_B2F_LEFT_ROOM, 0x37 } }; static u16 sFloaromaMeadowHiddenItemFlags[] = { 0x3A, 0x3B, 0xDB, 0xDC, 0xDD, 0xDE }; void FieldSystem_ClearDailyHiddenItemFlags(FieldSystem *fieldSystem) { u8 rand = LCRNG_Next() % NELEMS(sIronIslandHiddenItemFlags); if (fieldSystem->location->mapId != sIronIslandHiddenItemFlags[rand][0]) { FieldSystem_ClearFlag(fieldSystem, (FLAG_OFFSET_HIDDEN_ITEMS + sIronIslandHiddenItemFlags[rand][1])); } rand = LCRNG_Next() % NELEMS(sIronIslandHiddenItemFlags); if (fieldSystem->location->mapId != sIronIslandHiddenItemFlags[rand][0]) { FieldSystem_ClearFlag(fieldSystem, FLAG_OFFSET_HIDDEN_ITEMS + sIronIslandHiddenItemFlags[rand][1]); } if (fieldSystem->location->mapId != MAP_HEADER_FLOAROMA_MEADOW) { rand = LCRNG_Next() % NELEMS(sFloaromaMeadowHiddenItemFlags); FieldSystem_ClearFlag(fieldSystem, FLAG_OFFSET_HIDDEN_ITEMS + sFloaromaMeadowHiddenItemFlags[rand]); rand = LCRNG_Next() % NELEMS(sFloaromaMeadowHiddenItemFlags); FieldSystem_ClearFlag(fieldSystem, FLAG_OFFSET_HIDDEN_ITEMS + sFloaromaMeadowHiddenItemFlags[rand]); } } u8 Script_GetHiddenItemRange(u16 scriptID) { int i; const HiddenItem *item = gHiddenItems; u16 itemScript = Script_GetHiddenItemScript(scriptID); for (i = 0; i < NELEMS(gHiddenItems); i++) { if (item[i].script == itemScript) { break; } } if (i >= NELEMS(gHiddenItems)) { GF_ASSERT(FALSE); return 0; } return item[i].range; } static BOOL ScriptManager_SetHiddenItem(ScriptManager *scriptManager, u16 scriptID) { int i; u16 *scriptParam0 = ScriptManager_GetMemberPtr(scriptManager, SCRIPT_DATA_PARAMETER_0); u16 *scriptParam1 = ScriptManager_GetMemberPtr(scriptManager, SCRIPT_DATA_PARAMETER_1); u16 *scriptParam2 = ScriptManager_GetMemberPtr(scriptManager, SCRIPT_DATA_PARAMETER_2); const HiddenItem *item = gHiddenItems; u16 itemScript = Script_GetHiddenItemScript(scriptID); for (i = 0; i < NELEMS(gHiddenItems); i++) { if (item[i].script == itemScript) { break; } } if (i >= NELEMS(gHiddenItems)) { GF_ASSERT(FALSE); return FALSE; } *scriptParam0 = item[i].item; *scriptParam1 = item[i].qty; *scriptParam2 = Script_GetHiddenItemFlag(scriptID); return TRUE; } UnkStruct_0203F478 *sub_0203F478(FieldSystem *fieldSystem, int param1) { UnkStruct_0203F478 *v0; const BgEvent *v1; int v2, v3, v4, v5, v6, v7; int v8, v9, v10, v11; v6 = 0; v5 = MapHeaderData_GetNumBgEvents(fieldSystem); v5++; v0 = Heap_AllocFromHeap(param1, sizeof(UnkStruct_0203F478) * v5); if (v5 == 1) { v0[0].unk_04 = 0xff; v0[0].unk_00 = 0xffff; v0[0].unk_02 = 0xffff; return v0; } v1 = MapHeaderData_GetBgEvents(fieldSystem); if (v1 == NULL) { v0[0].unk_04 = 0xff; v0[0].unk_00 = 0xffff; v0[0].unk_02 = 0xffff; return v0; } v2 = Player_GetXPos(fieldSystem->playerAvatar); v3 = Player_GetZPos(fieldSystem->playerAvatar); v8 = v2 - 7; v9 = v2 + 7; v10 = v3 - 7; v11 = v3 + 6; if (v8 < 0) { v8 = 0; } if (v10 < 0) { v10 = 0; } for (v4 = 0; v4 < v5; v4++) { if ((v1[v4].type == 2) && (FieldSystem_CheckFlag(fieldSystem, Script_GetHiddenItemFlag(v1[v4].script)) == 0)) { if ((v1[v4].x >= v8) && (v1[v4].x <= v9) && (v1[v4].z >= v10) && (v1[v4].z <= v11)) { v0[v6].unk_04 = Script_GetHiddenItemRange(v1[v4].script); v7 = (v2 - v1[v4].x); v0[v6].unk_00 = abs(7 - v7); v7 = (v3 - v1[v4].z); v0[v6].unk_02 = abs(7 - v7); v6++; } } } v0[v6].unk_04 = 0xff; v0[v6].unk_00 = 0xffff; v0[v6].unk_02 = 0xffff; return v0; } void FieldSystem_InitNewGameState(FieldSystem *fieldSystem) { FieldSystem_RunScript(fieldSystem, 9600); } void FieldSystem_RunScript(FieldSystem *fieldSystem, u16 scriptID) { ScriptContext *ctx = ScriptContext_CreateAndStart(fieldSystem, scriptID); while (ScriptContext_Run(ctx) == TRUE) ; ScriptContext_Free(ctx); } BOOL sub_0203F5C0(FieldSystem *fieldSystem, u8 param1) { const u8 *initScripts = MapHeaderData_GetInitScripts(fieldSystem); if (initScripts == NULL) { return FALSE; } u16 scriptID; if (param1 == 1) { scriptID = sub_0203F638(fieldSystem, initScripts, param1); } else { scriptID = sub_0203F610(initScripts, param1); } if (scriptID == 0xffff) { return FALSE; } if (param1 == 1) { ScriptManager_Set(fieldSystem, scriptID, NULL); } else { FieldSystem_RunScript(fieldSystem, scriptID); } return TRUE; } static u16 sub_0203F610(const u8 *param0, u8 param1) { while (TRUE) { if (*param0 == 0) { return 0xffff; } if (*param0 == param1) { param0++; return *param0 + (*(param0 + 1) << 8); } param0 += (1 + 2 + 2); } return 0xffff; } static u16 sub_0203F638(FieldSystem *fieldSystem, const u8 *param1, u8 param2) { u16 v0, v1; u32 v2; v2 = 0; while (TRUE) { if (*param1 == 0) { return 0xffff; } if ((*param1) == param2) { param1++; v2 = (*param1 + (*(param1 + 1) << 8) + (*(param1 + 2) << 16) + (*(param1 + 3) << 24)); param1 += 4; break; } param1 += (1 + 4); } if (v2 == 0) { return 0xffff; } param1 = (param1 + v2); while (TRUE) { if (*param1 == 0) { return 0xffff; } v0 = (*param1 + (*(param1 + 1) << 8)); if (v0 == 0) { return 0xffff; } param1 += 2; v1 = (*param1 + (*(param1 + 1) << 8)); param1 += 2; if (FieldSystem_TryGetVar(fieldSystem, v0) == FieldSystem_TryGetVar(fieldSystem, v1)) { return *param1 + (*(param1 + 1) << 8); } param1 += 2; } return 0xffff; }