Files
st/src/001_SceneInit/UnkStruct_027e0cd8_0C_001.cpp
T
Yanis 8d759ee331 Decompile overlay 1 (Part 7) (#106)
* run ninja format

* delink what's left from overlay 1 (except dsprotect)

* fix regressions

* UnkStruct_027e0ce0_1C_001 97%

* UnkStruct_0204a110_001 OK

* UnkStruct_ov024_020d86a0_001 OK

* UnkStruct_ov000_020b50c0_001 OK

* GameModeCreate OK

* AdventureModeManager_001 OK

* GameModeAdventure_001 OK

* AdventureModeManager_001 OKn't because weak issues

* ZeldaCollisionBinary OK

* UnkStruct_027e09c0_001 OK

* UnkStruct_ov000_020b504c_001 OK

* UnkStruct_ov000_02067bc4.hpp -> UnkStruct_ov000_020b504c.hpp

* match overlay 97

* match overlay 100

* run ninja format
2026-07-13 18:41:32 +02:00

489 lines
15 KiB
C++

#include "Actor/ActorManager.hpp"
#include "Cutscene/Cutscene.hpp"
#include "Game/GameModeManager.hpp"
#include "MapObject/MapObjectManager.hpp"
#include "Physics/AABB.hpp"
#include "Unknown/UnkStruct_027e095c.hpp"
#include "Unknown/UnkStruct_027e09a0.hpp"
#include "Unknown/UnkStruct_027e09ac.hpp"
#include "Unknown/UnkStruct_027e09b0.hpp"
#include "Unknown/UnkStruct_027e09b8.hpp"
#include "Unknown/UnkStruct_027e09c0.hpp"
#include "Unknown/UnkStruct_027e0cd8.hpp"
#include <nns/g3d/g3d.h>
#include <printf.h>
#include <vector>
extern "C" BMDSectionModel *func_ov000_0205abcc(void *, void *, unk32, unk32, void *);
extern "C" void func_ov089_02165c34(void *);
extern AABB data_027e0ca8;
extern AABB data_027e0cc0;
extern AABB data_027e0c90;
extern int data_ov089_02171540;
static UnkStruct_ov001_020c40f4 data_ov001_020c40f4[0x40];
struct UnkStruct_ov001_020c2a40 {
/* 00 */ unk32 unk_00;
/* 04 */ unk32 unk_04;
/* 08 */ unk16 unk_08;
/* 0A */ u8 unk_0A;
/* 0B */ u8 unk_0B;
/* 0C */ u8 unk_0C;
/* 0D */ u8 unk_0D;
/* 0E */ u8 unk_0E;
/* 0F */ u8 unk_0F;
/* 10 */ u8 unk_10;
/* 11 */ STRUCT_PAD(0x11, 0x14); // pad?
/* 14 */
UnkStruct_ov001_020c2a40(unk32 param1, unk32 param2, unk16 param3, unk8 param4, unk8 param5, unk8 param6, unk8 param7) {
this->unk_00 = param1;
this->unk_04 = param2;
this->unk_08 = param3;
this->unk_0A = param4;
this->unk_0B = param5;
this->unk_0C = param6;
this->unk_0D = param7;
this->unk_0E = 0x2B;
this->unk_0F = 0;
this->unk_10 = 0;
}
};
static const UnkStruct_ov001_020c2a40 data_ov001_020c2a40[] = {
UnkStruct_ov001_020c2a40(0x36, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3C),
UnkStruct_ov001_020c2a40(0x29, 0x00, 0x00, 0x0B, 0x01, 0x00, 0x3D),
UnkStruct_ov001_020c2a40(0x35, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3E),
UnkStruct_ov001_020c2a40(0x04, 0x00, 0x00, 0x00, 0xFA, 0x00, 0x3F),
};
// https://decomp.me/scratch/JcRNn
UnkStruct_027e0cd8_0C_Base::UnkStruct_027e0cd8_0C_Base(UnkStruct_027e0cd8 *param1) :
mUnk_004(NULL, 0x9B, 0x01, 0x01),
mSceneRender(NULL),
mUnk_070(NULL, 0x9B, 0x01, 0x00),
mUnk_084_00(0),
mUnk_084_01(0),
mUnk_098(0),
mUnk_09C((Vec2us *) &param1->mUnk_00),
mUnk_0AC(false),
mUnk_0AD(false),
mUnk_0AE(false),
mUnk_0AF(false),
mUnk_0FC(0),
mIsCS(false),
mUnk_104(0),
mUnk_108(0),
mUnk_10C(0),
mUnk_110(0),
mUnk_114(0),
mUnk_118(0),
mUnk_11C(1),
mUnk_120(0),
mUnk_124(0),
mUnk_128(0),
mUnk_12A(true),
mUnk_12B(false),
mUnk_12C(false),
mUnk_12D(false),
mUnk_12E(false),
mpROMB(NULL),
mpCAME(NULL),
mpCMPT(NULL) {
Vec2s local_30;
VecFx32 sp18;
VecFx32 spC;
this->mUnk_0A0.x = 0;
this->mUnk_0A0.y = 0;
this->mUnk_0A0.z = 0;
fx32 y = (this->mUnk_11C << 14);
fx32 z = ((u32) (u16) this->mUnk_09C.y >> 1) << 12;
fx32 x = ((u32) (u16) this->mUnk_09C.x >> 1) << 12;
data_027e0c90.min.x = -x;
data_027e0c90.min.y = -y;
data_027e0c90.min.z = -z;
data_027e0c90.max.x = x;
data_027e0c90.max.y = 0;
data_027e0c90.max.z = z;
spC = data_027e0c90.min;
data_027e0ca8.min = spC;
sp18 = data_027e0c90.max;
data_027e0ca8.max = sp18;
data_027e0cc0.min = spC;
data_027e0cc0.max = sp18;
this->mUnk_13C.Init(data_ov001_020c40f4, 0x40);
Vec2s_Copy((Vec2s *) &this->mUnk_09C, &local_30);
gpMapObjManager->func_ov001_020baea0((u16 *) &local_30);
data_027e095c->func_ov000_020592a0();
}
UnkStruct_027e0cd8_0C_Base::~UnkStruct_027e0cd8_0C_Base() {
data_027e095c->func_ov000_020592ec();
gpMapObjManager->func_ov001_020baf28();
DELETE(this->mUnk_098);
this->mpROMB = NULL;
this->mpCMPT = NULL;
this->mpCAME = NULL;
this->mUnk_154.clear();
this->func_ov001_020b8aec();
}
void UnkStruct_027e0cd8_0C_Base::vfunc_38() {}
void UnkStruct_027e0cd8_0C_Base::vfunc_08() {}
void UnkStruct_027e0cd8_0C_Base::func_ov001_020b85d0(const EntranceInfo *param1) {
this->mIsCS = param1->isCS;
wchar_t local_c8[2];
local_c8[0] = L'\0';
local_c8[sizeof(local_c8) / 2 - 1] = L'\0';
snprintf((char *) local_c8, sizeof(local_c8), "M%02d", param1->roomIndex);
this->mUnk_084[0] = local_c8[0];
this->mUnk_084[1] = local_c8[1];
CourseListEntry *pEntry = data_027e09a0->GetCourseEntry(param1->sceneIndex);
wchar_t local_34[16];
local_34[0] = L'\0';
local_34[sizeof(local_34) / 2 - 1] = L'\0';
snprintf((char *) local_34, sizeof(local_34), "Map/%s/map%02d.bin", pEntry->name, param1->roomIndex);
this->mUnk_004.~UnkSystem3();
this->mUnk_004.mUnk_00 = local_34;
this->mUnk_004.func_0201541c((char *) local_c8, 0x10);
this->LoadSceneModel(param1);
snprintf((char *) local_34, sizeof(local_34), "%s:zcb/%s_%02d.zcb", local_c8, pEntry->name, param1->roomIndex);
UnkFileSystem3 local_44((char *) local_34);
data_027e09c0->func_ov001_020be3dc(&local_44, this);
wchar_t local_64[16];
local_64[0] = L'\0';
local_64[sizeof(local_64) / 2 - 1] = L'\0';
snprintf((char *) local_64, sizeof(local_64), "%s:zmb/%s_%02d.zmb", local_c8, pEntry->name, param1->roomIndex);
UnkFileSystem3 local_74((char *) local_64);
local_74.vfunc_08(0x10);
ZMBFileInfos zmbFileInfos;
zmbFileInfos.pFile = local_74.mpFile;
zmbFileInfos.size = local_74.mFileSize;
zmbFileInfos.unk_08 = 0;
zmbFileInfos.unk_0A = 0;
zmbFileInfos.unk_0C = 0;
zmbFileInfos.unk_0E = 0;
ZMB_ParseFile(&zmbFileInfos, this, true);
gpMapObjManager->func_ov001_020bade0();
gpActorManager->func_ov001_020bb630();
if (param1->isCS == false) {
gpActorManager->func_ov001_020bb6b0((EntranceInfo *) param1);
}
data_027e095c->func_ov000_020592a0();
u32 isCs = this->mIsCS;
snprintf((char *) local_34, sizeof(local_34), "%s:zob/motype_%02d_%1d.zob", local_c8, param1->roomIndex, isCs);
UnkFileSystem3 local_94((char *) local_34);
this->mUnk_0B4 = (ZeldaObjectList *) local_94.vfunc_08(sizeof(ZOBHeader));
gpMapObjManager->func_ov001_020bae40(this->mUnk_0B4);
for (int i = 0; i < ARRAY_LEN(this->mUnk_0B8); i++) {
// i + 2 because 0 is the default one and 1 is the cutscene one
snprintf((char *) local_34, sizeof(local_34), "%s:zob/motype_%02d_%1d.zob", local_c8, param1->roomIndex, i + 2);
UnkFileSystem3 local_a4((char *) local_34);
this->mUnk_0B8[i] = (ZeldaObjectList *) local_a4.vfunc_08(sizeof(ZOBHeader));
}
isCs = this->mIsCS;
snprintf((char *) local_34, sizeof(local_34), "%s:zob/npctype_%02d_%1d.zob", local_c8, param1->roomIndex, isCs);
UnkFileSystem3 local_b4((char *) local_34);
this->mUnk_0D8 = (ZeldaObjectList *) local_b4.vfunc_08(sizeof(ZOBHeader));
gpActorManager->func_ov001_020bb7b0(this->mUnk_0D8);
for (int i = 0; i < ARRAY_LEN(this->mUnk_0DC); i++) {
// i + 2 because 0 is the default one and 1 is the cutscene one
snprintf((char *) local_34, sizeof(local_34), "%s:zob/npctype_%02d_%1d.zob", local_c8, param1->roomIndex, i + 2);
UnkFileSystem3 local_c4((char *) local_34);
this->mUnk_0DC[i] = (ZeldaObjectList *) local_c4.vfunc_08(sizeof(ZOBHeader));
}
data_027e09b0->func_ov000_02072cc4(0x0000, 0x7FFF);
ZMB_ParseFile(&zmbFileInfos, this, false);
this->vfunc_40(param1->spawnIndex);
if (param1->sceneIndex == SceneIndex_t_area1) {
if (GET_FLAG(data_027e09b8->mAdventureFlags, AdventureFlag_ObtainedSnowSource)) {
this->mUnk_110 = 0x0A;
}
} else if (param1->sceneIndex == SceneIndex_t_area3) {
if (GET_FLAG(data_027e09b8->mAdventureFlags, AdventureFlag_ObtainedFireSource)) {
this->mUnk_110 = 0x10;
this->mUnk_114 = 0x1F;
}
}
this->func_ov001_020b8db8();
this->func_ov001_020b8e24();
if (param1->isCS == true) {
this->mUnk_114 = Cutscene_GetParamEntry(param1->csIndex)->mUnk_0E;
}
data_027e09ac->func_ov000_020726f0(this->mUnk_114, 0x00, 0x00);
this->vfunc_38();
}
void UnkStruct_027e0cd8_0C_Base::func_ov001_020b88c0(unk32 param1) {
gpMapObjManager->func_ov001_020bae40(this->mUnk_0B8[param1]);
gpActorManager->func_ov001_020bb7b0(this->mUnk_0DC[param1]);
}
void UnkStruct_027e0cd8_0C_Base::func_ov001_020b88ec() {
this->func_ov001_020b8e54();
this->mUnk_088.func_ov000_0208261c();
gpMapObjManager->func_ov001_020bae6c();
gpActorManager->func_ov001_020bb7f0();
data_027e095c->func_ov000_020592ec();
data_027e09c0->func_ov001_020be400();
this->mUnk_004.~UnkSystem3();
if (this->mUnk_128 & 0x200) {
func_ov089_02165c34(&data_ov089_02171540);
}
}
void UnkStruct_027e0cd8_0C_Base::LoadSceneModel(const EntranceInfo *param1) {
const char *pName = data_027e09a0->GetCourseEntry(param1->sceneIndex)->name;
wchar_t local_40[20];
local_40[0] = L'\0';
local_40[sizeof(local_40) / 2 - 1] = L'\0';
snprintf((char *) local_40, sizeof(local_40), "%s:nsbmd/%s_%02d.nsbmd", this->mUnk_084, pName, param1->roomIndex);
UnkFileSystem3 local_50((char *) local_40);
wchar_t local_78[20];
local_78[0] = L'\0';
local_78[sizeof(local_78) / 2 - 1] = L'\0';
const char *path = "Map/%s/map%02d.nsbtx";
snprintf((char *) local_78, sizeof(local_78), path, pName, param1->roomIndex);
this->mUnk_070.vfunc_0C();
this->mUnk_070.mUnk_04 = (char *) local_78;
this->mUnk_070.vfunc_08(0x10);
BMDSectionModel *pBMD = func_ov000_0205abcc(&local_50, &this->mUnk_070, 0x01, 0x00, NULL);
G3d_Model *pModel = G3d_GetModelPtr(pBMD);
G3d_0200e6a0(pModel, 0x00, 0x40);
G3d_0200e6a0(pModel, 0x00, 0x80);
this->mSceneRender.vfunc_08(pModel);
}
void UnkStruct_027e0cd8_0C_Base::vfunc_1C(const EntranceInfo *param1, bool param2, bool param3) {
SceneIndex sceneIndex = param1->sceneIndex;
u8 roomIndex = param1->roomIndex;
if (param2 != 0) {
if (param3 == 0) {
return;
}
roomIndex = 99;
}
gpCurrentGameModeMgr->vfunc_38(sceneIndex, roomIndex, 0x01, 0x00);
}
void UnkStruct_027e0cd8_0C_Base::vfunc_20() {}
const UnkStruct_ov001_020c40f4 *UnkStruct_027e0cd8_0C_Base::func_ov001_020b8a5c(unk32 spawnIndex, unk32 param1) {
UnkStruct_ov001_020c40f4 *result =
std::find_if(this->mUnk_13C.begin(), this->mUnk_13C.end(), UnkStruct_ov001_020c40f4::Predicate(spawnIndex, param1));
if (param1 == 0) {
if (result == this->mUnk_13C.end()) {
result = this->mUnk_13C.begin();
}
if (result->mUnk_0F == 0) {
result->mUnk_00.y = this->vfunc_28(&result->mUnk_00, 1, 0);
}
return result;
} else {
if (result == this->mUnk_13C.end()) {
return this->func_ov001_020b8a5c(spawnIndex, 0x00);
}
if (result->mUnk_0F == 0) {
result->mUnk_00.y = this->vfunc_28(&result->mUnk_00, 1, 0);
}
return result;
}
}
void UnkStruct_027e0cd8_0C_Base::func_ov001_020b8aec() {
STACK_PAD(0x24);
this->mUnk_148.unk_action1();
}
void UnkStruct_027e0cd8_0C_Base::func_ov001_020b8b94(ZMBEntryARAB *pARAB) {
UnkStruct_027e0cd8_0C_Base_148_00_Base *ptr = NULL;
if (pARAB->unk_0C == 1) {
ptr = new(HeapIndex_1) UnkStruct_027e0cd8_0C_Base_148_02(pARAB);
} else if (pARAB->unk_0D == 1) {
ptr = new(HeapIndex_1) UnkStruct_027e0cd8_0C_Base_148_01(pARAB);
} else {
ptr = new(HeapIndex_1) UnkStruct_027e0cd8_0C_Base_148_00(pARAB);
}
this->mUnk_148.push_back(ptr);
}
void UnkStruct_027e0cd8_0C_Base::func_ov001_020b8c30(const EntranceInfo &param1) {
this->mUnk_154.push_back(param1);
}
void *UnkStruct_027e0cd8_0C_Base::func_ov001_020b8c80(unk32 param1) {
return (void *) &data_ov001_020c2a40[param1 - 0x3C];
}
void UnkStruct_027e0cd8_0C_Base::func_ov001_020b8c90(ZMBSectionCMPT *pCMPT) {
this->mpCMPT = pCMPT;
}
void UnkStruct_027e0cd8_0C_Base::func_ov001_020b8c98(ZMBSectionCAME *pCAME) {
this->mpCAME = pCAME;
}
void UnkStruct_027e0cd8_0C_Base::ZMB_ParseROMB(ZMBSectionROMB *pROMB) {
this->mpROMB = pROMB;
}
void UnkStruct_027e0cd8_0C_Base::vfunc_40(u8 spawnIndex) {
switch (spawnIndex) {
case 0xFB:
case 0xFC:
case 0xFD:
case 0xFE: {
UnkStruct_ov001_020c40f4 stack_elem;
UnkStruct_WarpUnk1_A0 *pEntry = data_027e09a4->func_ov000_02070538();
VecFx32 pos = pEntry->mUnk_04;
fx16 angle = DEG_TO_ANG(0);
switch (spawnIndex) {
case 0xFB:
pos.z = data_027e0c90.max.z - FLOAT_TO_FX32(0.5f);
angle = DEG_TO_ANG(180);
break;
case 0xFC:
pos.z = data_027e0c90.min.z + FLOAT_TO_FX32(0.5f);
angle = DEG_TO_ANG(0);
break;
case 0xFD:
pos.x = data_027e0c90.max.x - FLOAT_TO_FX32(0.5f);
angle = DEG_TO_ANG(270);
break;
case 0xFE:
pos.x = data_027e0c90.min.x + FLOAT_TO_FX32(0.5f);
angle = DEG_TO_ANG(90);
break;
default:
break;
}
stack_elem.mUnk_0E = spawnIndex;
VecFx32_Copy(&pos, &stack_elem.mUnk_00);
stack_elem.mUnk_0C = angle;
stack_elem.mUnk_10 = 0xFD;
UnkStruct_ov001_020c40f4 *pEnd = this->mUnk_13C.end();
if (pEnd != NULL) {
pEnd->mUnk_00 = stack_elem.mUnk_00;
pEnd->mUnk_0C = stack_elem.mUnk_0C;
pEnd->mUnk_0E = stack_elem.mUnk_0E;
pEnd->mUnk_0F = stack_elem.mUnk_0F;
pEnd->mUnk_10 = stack_elem.mUnk_10;
pEnd->mUnk_14 = stack_elem.mUnk_14;
}
this->mUnk_13C.grow_by(1);
break;
}
default:
break;
}
}
void UnkStruct_027e0cd8_0C_Base::func_ov001_020b8db8() {
unk32 uVar1;
uVar1 = 0;
switch (this->mUnk_110) {
case 0x00:
case 0x03:
uVar1 = 0x0A;
break;
case 0x0E:
uVar1 = 0x01;
break;
case 0x05:
case 0x09:
uVar1 = 0x02;
break;
case 0x0A:
uVar1 = 0x03;
break;
case 0x02:
uVar1 = 0x04;
break;
case 0x0F:
uVar1 = 0x05;
break;
case 0x10:
uVar1 = 0x06;
break;
case 0x08:
uVar1 = 0x00;
break;
case 0x0C:
uVar1 = 0x09;
break;
case 0x06:
uVar1 = 0x07;
break;
case 0x01:
case 0x07:
case 0x04:
case 0x0B:
break;
default:
uVar1 = 0x00;
break;
}
this->mUnk_088.func_ov000_020823a8(uVar1);
}
void UnkStruct_027e0cd8_0C_Base::func_ov001_020b8e24() {
if (this->mUnk_110 == 7 && this->mUnk_098 == NULL) {
this->mUnk_098 = new(HeapIndex_1) UnkStruct_027e0cd8_0C_Base_98();
}
}
void UnkStruct_027e0cd8_0C_Base::func_ov001_020b8e54() {
DELETE(this->mUnk_098);
}