Decompile Title overlay (#20)

* Decompile Title overlay

* math structs as cpp when applicable

* fixes and improvements

* regressions fix 1

* regressions fix 2
This commit is contained in:
Yanis
2026-01-15 19:04:43 +01:00
committed by GitHub
parent 76c1ec9acf
commit ed672be03f
57 changed files with 1788 additions and 784 deletions
+107
View File
@@ -0,0 +1,107 @@
#include "Game/GameModeTitleScreen.hpp"
#include "TitleScreen/TitleScreen.hpp"
#include "Unknown/UnkStruct_02049a2c.hpp"
#include "Unknown/UnkStruct_0204a088.hpp"
#include "Unknown/UnkStruct_0204a110.hpp"
#include "Unknown/UnkStruct_027e09a4.hpp"
struct UnkStruct_ov000_020a782c {
/* 00 */ unk32 mUnk_00;
/* 04 */ u8 mUnk_04;
/* 05 */ u8 mUnk_05;
/* 06 */ u8 mUnk_06;
/* 07 */ u8 mUnk_07;
};
extern "C" {
void func_0201659c();
void func_0200e234();
void func_ov001_020b6520(unk32 param1);
UnkStruct_ov000_020a782c *func_ov000_020a782c(unk32 param1);
}
ARM GameModeTitleScreen::GameModeTitleScreen() {
func_0201659c();
data_02049a2c.func_02013370(2);
data_0204a110.func_ov001_020bd514(0, TitleScreenManager::Create, 0, 1);
func_ov001_020b6520(2);
}
ARM GameModeTitleScreen::~GameModeTitleScreen() {
UnkStruct_027e09a4::func_ov025_020c4a60();
func_0200e234();
}
struct stack_struct {
/* 00 */ unk32 mUnk_00;
/* 04 */ unk32 mUnk_04;
/* 08 */ unk16 mUnk_08;
/* 0A */ unk8 mUnk_0A;
/* 0B */ unk8 mUnk_0B;
/* 0C */ unk8 mUnk_0C;
/* 0D */ unk8 mUnk_0D;
/* 0E */ unk8 mUnk_0E;
/* 0F */ unk8 mmUnk_0F;
/* 10 */ unk8 mUnk_10;
/* 11 */ unk8 mUnk_11;
/* 12 */ unk8 mUnk_12;
/* 13 */ unk8 mUnk_13;
/* 14 */
};
ARM void GameModeTitleScreen::vfunc_08(unk32 param1, unk32 param2, unk32 param3) {
this->GameModeBase::vfunc_08(param1, param2, param3);
UnkStruct_ov000_020a782c *iVar1 = func_ov000_020a782c(0);
u8 mUnk_04 = iVar1->mUnk_04;
u8 mUnk_07 = iVar1->mUnk_07;
u8 mUnk_06 = iVar1->mUnk_06;
u8 mUnk_05 = iVar1->mUnk_05;
stack_struct stack;
stack.mUnk_00 = mUnk_04;
stack.mUnk_04 = 0;
stack.mUnk_08 = 0;
stack.mUnk_0A = mUnk_05;
stack.mUnk_0B = mUnk_06;
stack.mUnk_0C = 1;
stack.mUnk_0D = 0;
stack.mUnk_0E = mUnk_07;
stack.mmUnk_0F = 0;
stack.mUnk_10 = 0;
data_027e09a4->func_ov000_020707a8(&stack);
}
ARM void GameModeTitleScreen::vfunc_0C() {
data_027e09a4->func_ov000_0207087c(data_0204a110.mUnk_DF8);
}
ARM void GameModeTitleScreen::vfunc_10() {
data_027e09a4->func_ov000_020708d8(data_0204a110.mUnk_DF8);
}
ARM void GameModeTitleScreen::vfunc_14() {
data_027e09a4->func_ov000_02070834(&data_0204a110.mUnk_DF2);
}
ARM void GameModeTitleScreen::vfunc_18() {
data_027e09a4->func_ov000_02070938(data_0204a110.mUnk_DF8);
}
ARM void GameModeTitleScreen::vfunc_1C() {
data_027e09a4->func_ov000_02070a4c(data_0204a110.mUnk_DF8);
}
ARM void GameModeTitleScreen::vfunc_20() {
UnkStruct_027e09a4 *ptr4 = data_027e09a4;
void *ptr = &data_0204a110.mUnk_DF2;
if ((data_0204a088->mUnk_120 & 1) != 0) {
ptr4->func_ov017_020bb994(ptr);
}
}
ARM void UnkStruct_027e09a4::func_ov025_020c4a60() {
delete data_027e09a4;
}
+397
View File
@@ -0,0 +1,397 @@
#include "TitleScreen/TitleScreen.hpp"
#include "Unknown/UnkStruct_02049be0.hpp"
#include "Unknown/UnkStruct_0204a060.hpp"
#include "Unknown/UnkStruct_0204aeac.hpp"
#include "Unknown/UnkStruct_0204af1c.hpp"
#include "Unknown/UnkStruct_027e0954.hpp"
#include "Unknown/UnkStruct_ov000_020b5214.hpp"
#include "nitro/button.h"
#include "regs.h"
#include "versions.h"
#include <string.h>
#pragma dont_reuse_strings off
extern "C" {
void func_02018424();
void func_ov000_0205be34(void *param1, unk32 param2);
void func_ov000_0205bedc(void *param1, void *param2, void *param3, void *param4, unk32 param5, int);
}
static TitleScreenPTMF<TitleScreen> data_ov025_020c5aec[TitleScreenState_Max] = {
TitleScreen::func_ov025_020c5200, // TitleScreenState_None
TitleScreen::func_ov025_020c5204, // TitleScreenState_IdleBeforeUI
TitleScreen::func_ov025_020c5240, // TitleScreenState_DrawUIOnInput
TitleScreen::func_ov025_020c53d0, // TitleScreenState_DrawUIOnCsCmd
TitleScreen::func_ov025_020c55a4, // TitleScreenState_IdleBeforeFileSelect
TitleScreen::func_ov025_020c55e4, // TitleScreenState_ToFileSelect
};
#if IS_JP
static const Vec2s data_ov025_020c5ae4(0x0000, 0x0000);
static const Vec2s data_ov025_020c5ae8(0x0000, 0x0000);
static const Vec2us data_ov025_020c5ae0(0x0100, 0x0080);
static const Vec2s data_ov025_020c7398(0x0100, 0x0080);
static const Vec2s data_ov025_020c7394(0x0000, 0x0094);
static const Vec2s data_ov025_020c738e(0x0100, 0x0020);
static const Vec2s data_ov025_020c738c(0x0100, 0x0020);
#else
static const Vec2s data_ov025_020c5ae4(0x0000, 0x0020);
static const Vec2s data_ov025_020c5ae8(0x0100, 0x0080);
static const Vec2us data_ov025_020c5ae0(0x0100, 0x0080);
#endif
struct UnkStruct_StackTitleScreen {
/* 00 */ unk32 pad[5];
/* 14 */
UnkStruct_StackTitleScreen(const char *path, unk32 param1);
void func_ov000_02059270(unk32 param1, char *param2, unk32 param3);
void func_ov000_02059240();
};
TitleScreen::TitleScreen() :
mState(TitleScreenState_None),
mShowUI(false),
mUnk_021(false) {
this->mUnk_18 = 1;
this->mUnk_19 = 1;
this->mUnk_1A = 1;
wchar_t acStack_54[32];
char *pcVar1 = data_02049be0.func_02014ff4();
acStack_54[ARRAY_LEN(acStack_54) - 1] = '\0';
strncpy((char *) acStack_54, pcVar1, sizeof(acStack_54) - 1);
char *path = "/Screen/tex2d.bin";
size_t len = strlen((char *) acStack_54);
strncpy((char *) acStack_54 + len, path, sizeof(acStack_54) - len - 1);
UnkStruct_StackTitleScreen auStack_68((char *) acStack_54, 1);
auStack_68.func_ov000_02059270(0x3E, "title", 0x32500000);
auStack_68.func_ov000_02059240();
data_0204aeac.func_0201c494(3);
this->mUnk_218.func_0201effc(0x0F, 1, 0x1F);
}
TitleScreen::~TitleScreen() {
data_ov000_020b5214.func_ov000_0206d83c(0x1E);
this->func_ov025_020c5964();
}
void TitleScreen::func_ov025_020c4e54() {
this->mShowUI = true;
this->func_ov025_020c4ea0(TitleScreenState_DrawUIOnInput);
}
void TitleScreen::func_ov025_020c4e6c() {
if (!this->mShowUI) {
this->mShowUI = true;
this->func_ov025_020c4ea0(TitleScreenState_DrawUIOnCsCmd);
}
}
void TitleScreen::func_ov025_020c4e90() {
this->func_ov025_020c4ea0(TitleScreenState_IdleBeforeUI);
}
void TitleScreen::func_ov025_020c4ea0(TitleScreenState state) {
this->mState = state;
switch (this->mState) {
case TitleScreenState_None:
break;
case TitleScreenState_IdleBeforeUI:
break;
case TitleScreenState_DrawUIOnCsCmd:
this->mUnk_344 = 0;
this->mUnk_218.func_0201effc(0x1E, 1, 0x1F);
this->mUnk_218.mUnk_0A = true;
this->mUnk_218.mUnk_0B = false;
this->mUnk_218.mUnk_0C = false;
if (this->mUnk_218.mUnk_04 == this->mUnk_218.mUnk_06) {
this->mUnk_218.mUnk_0A = false;
this->mUnk_218.mUnk_0C = true;
}
this->mUnk_204.mUnk_10 = true;
this->mUnk_23C.UnknownAction(0x59, 2);
this->mUnk_254.func_ov000_0206082c(0x59, 2);
this->mUnk_2CC.func_ov000_0206082c(0x59, 0);
this->mUnk_024.func_ov000_0206082c(0x58, 1);
this->mUnk_09C.func_ov000_0206082c(0x58, 3);
this->mUnk_114.func_ov000_0206082c(0x58, 5);
this->mUnk_18C.func_ov000_0206082c(0x58, 7);
this->mUnk_254.mUnk_6E = false;
this->mUnk_2CC.mUnk_6E = false;
this->mUnk_024.mUnk_6E = false;
this->mUnk_09C.mUnk_6E = false;
this->mUnk_114.mUnk_6E = false;
this->mUnk_18C.mUnk_6E = false;
break;
case TitleScreenState_DrawUIOnInput:
this->mUnk_218.func_0201effc(0x0F, 1, 0x1F);
this->mUnk_218.mUnk_0A = true;
this->mUnk_218.mUnk_0B = false;
this->mUnk_218.mUnk_0C = false;
if (this->mUnk_218.mUnk_04 == this->mUnk_218.mUnk_06) {
this->mUnk_218.mUnk_0A = false;
this->mUnk_218.mUnk_0C = true;
}
this->mUnk_204.mUnk_10 = true;
this->mUnk_23C.UnknownAction(0x59, 2);
this->mUnk_254.func_ov000_0206082c(0x59, 2);
this->mUnk_2CC.func_ov000_0206082c(0x59, 0);
this->mUnk_024.func_ov000_0206082c(0x58, 1);
this->mUnk_09C.func_ov000_0206082c(0x58, 3);
this->mUnk_114.func_ov000_0206082c(0x58, 5);
this->mUnk_18C.func_ov000_0206082c(0x58, 7);
break;
case TitleScreenState_IdleBeforeFileSelect:
this->mUnk_024.func_ov000_0206082c(0x58, 0);
break;
case TitleScreenState_ToFileSelect:
this->mUnk_024.func_ov000_0206082c(0x58, 2);
this->mUnk_09C.func_ov000_0206082c(0x58, 4);
this->mUnk_114.func_ov000_0206082c(0x58, 6);
this->mUnk_18C.func_ov000_0206082c(0x58, 8);
data_ov000_020b5214.func_ov000_0206d83c(0x1E);
break;
default:
break;
}
}
void TitleScreen::vfunc_08(GameModePTMFParam2Struct *param1, TouchControl *pTouchControl) {
if (this->mShowUI) {
this->mUnk_024.func_ov000_020609c4();
this->mUnk_09C.func_ov000_020609c4();
this->mUnk_114.func_ov000_020609c4();
this->mUnk_18C.func_ov000_020609c4();
this->mUnk_254.func_ov000_020609c4();
this->mUnk_2CC.func_ov000_020609c4();
}
CALL_PTMF(TitleScreenPTMF<TitleScreen>, data_ov025_020c5aec[this->mState], param1, pTouchControl);
data_0204aeac.func_0201c4d8(0, 0x0B, 8);
data_0204aeac.func_0201c504(1, 10, 0x10, 8);
}
void TitleScreen::func_ov025_020c5200(GameModePTMFParam2Struct *param1, TouchControl *pTouchControl) {}
// https://decomp.me/scratch/6nDGM
void TitleScreen::func_ov025_020c5204(GameModePTMFParam2Struct *param1, TouchControl *pTouchControl) {
if (pTouchControl->mFlags & 1) {
this->mUnk_021 = 1U;
}
if ((pTouchControl->mFlags & 2) && (this->mUnk_021 != 0)) {
goto test;
}
if (!(param1->mButtons & 8)) {
return;
}
test:
func_ov025_020c4e54();
}
void TitleScreen::func_ov025_020c5240(GameModePTMFParam2Struct *param1, TouchControl *pTouchControl) {
this->mUnk_218.UnkOperations();
this->mUnk_204.mUnk_10 = this->mUnk_218.func_0201f04c();
if (this->mUnk_024.func_ov000_02060af8() == 0) {
return;
}
if (this->mUnk_09C.func_ov000_02060af8() == 0) {
return;
}
if (this->mUnk_114.func_ov000_02060af8() == 0) {
return;
}
if (this->mUnk_18C.func_ov000_02060af8() == 0) {
return;
}
this->func_ov025_020c4ea0(TitleScreenState_IdleBeforeFileSelect);
}
void TitleScreen::func_ov025_020c53d0(GameModePTMFParam2Struct *param1, TouchControl *pTouchControl) {
this->mUnk_344++;
if (this->mUnk_344 == 15) {
// do subscreen animations (logo)
this->mUnk_254.mUnk_6E = true;
this->mUnk_2CC.mUnk_6E = true;
} else if (this->mUnk_344 == 60) {
// do main screen animations (feather, strings and bg)
this->mUnk_024.mUnk_6E = true;
this->mUnk_09C.mUnk_6E = true;
this->mUnk_114.mUnk_6E = true;
this->mUnk_18C.mUnk_6E = true;
}
this->mUnk_218.UnkOperations();
this->mUnk_204.mUnk_10 = this->mUnk_218.func_0201f04c();
if (this->mUnk_218.mUnk_0C) {
if (this->mUnk_024.func_ov000_02060af8() == 0) {
return;
}
if (this->mUnk_09C.func_ov000_02060af8() == 0) {
return;
}
if (this->mUnk_114.func_ov000_02060af8() == 0) {
return;
}
if (this->mUnk_18C.func_ov000_02060af8() == 0) {
return;
}
this->func_ov025_020c4ea0(TitleScreenState_IdleBeforeFileSelect);
}
}
void TitleScreen::func_ov025_020c55a4(GameModePTMFParam2Struct *param1, TouchControl *pTouchControl) {
if (CHECK_TOUCH_FLAGS(pTouchControl, TouchFlag_UntouchedNow) || CHECK_BUTTON_COMBO(param1->mButtons, BTN_START)) {
data_ov000_020b5214.func_ov000_0206db44(0x0B);
this->func_ov025_020c4ea0(TitleScreenState_ToFileSelect);
}
}
void TitleScreen::func_ov025_020c55e4(GameModePTMFParam2Struct *param1, TouchControl *pTouchControl) {
if (this->mUnk_024.func_ov000_02060af8() == 0) {
return;
}
if (this->mUnk_09C.func_ov000_02060af8() == 0) {
return;
}
if (this->mUnk_114.func_ov000_02060af8() == 0) {
return;
}
if (this->mUnk_18C.func_ov000_02060af8() == 0) {
return;
}
data_0204a060.func_020183d4(true, func_02018424, 1);
}
void TitleScreen::vfunc_14(unk8 *param1) {
if (param1[1] == 0) {
this->func_ov025_020c592c();
data_0204aeac.func_0201c494(3);
}
if (param1[0] == 0) {
this->func_ov025_020c5964();
data_0204aeac.func_0201c494(0);
}
}
void TitleScreen::vfunc_10(unk8 *param1) {
if (this->mShowUI) {
if (param1[0] == 0 && this->mUnk_09C.mUnk_6E) {
UnkStruct_ov019_020d24c8_28_258 uStack_3c(0x58, 0x00);
data_0204af1c.func_0201aad0(&this->mUnk_09C, &uStack_3c.mPos, 0, 0);
UnkStruct_ov019_020d24c8_28_258 uStack_54(0x58, 0x01);
data_0204af1c.func_0201aad0(&this->mUnk_024, &uStack_54.mPos, 0, 0);
UnkStruct_ov019_020d24c8_28_258 uStack_6c(0x58, 0x02);
data_0204af1c.func_0201aad0(&this->mUnk_18C, &uStack_6c.mPos, 0, 0);
UnkStruct_ov019_020d24c8_28_258 uStack_84(0x58, 0x03);
data_0204af1c.func_0201aad0(&this->mUnk_114, &uStack_84.mPos, 0, 0);
}
if (param1[1] == 0 && this->mUnk_254.mUnk_6E) {
#if IS_JP
Vec2us pos1;
pos1.x = this->mUnk_23C.mPos.x + data_ov025_020c5ae4.x;
pos1.y = this->mUnk_23C.mPos.y + data_ov025_020c5ae4.y;
data_0204af1c.func_0201aa44(&this->mUnk_23C, &pos1, 0, 0);
UnkStruct_ov019_020d24c8_28_258 uStack_9c(0x59, 0x01);
Vec2us pos2;
pos2.x = uStack_9c.mPos.x + data_ov025_020c5ae4.x;
pos2.y = uStack_9c.mPos.y + data_ov025_020c5ae4.y;
data_0204af1c.func_0201aad0(&this->mUnk_254, &pos2, 0, 0);
UnkStruct_ov019_020d24c8_28_258 uStack_b4(0x59, 0x00);
Vec2us pos3;
pos3.x = uStack_b4.mPos.x + data_ov025_020c5ae4.x;
pos3.y = uStack_b4.mPos.y + data_ov025_020c5ae4.y;
data_0204af1c.func_0201aad0(&this->mUnk_2CC, &pos3, 0, 0);
#else
data_0204af1c.func_0201aa44(&this->mUnk_23C, &this->mUnk_23C.mPos, 0, 0);
UnkStruct_ov019_020d24c8_28_258 uStack_9c(0x59, 0x01);
data_0204af1c.func_0201aad0(&this->mUnk_254, &uStack_9c.mPos, 0, 0);
UnkStruct_ov019_020d24c8_28_258 uStack_b4(0x59, 0x00);
data_0204af1c.func_0201aad0(&this->mUnk_2CC, &uStack_b4.mPos, 0, 0);
#endif
}
}
}
//! TODO: fake match?
void TitleScreen::vfunc_0C(unk32 param1) {
if (param1 == 1 && this->mShowUI) {
UnkStruct_027e0954 *ptr = data_027e0954;
void *iVar1 = &this->mUnk_204;
if (iVar1 != NULL) {
iVar1 = (u32 *) iVar1 + 1;
}
ptr->mUnk_14.func_020166f4(iVar1);
}
}
void TitleScreen::func_ov025_020c592c() {
REG_DISPCNT &= ~0xE000;
REG_DISPCNT |= 0x8000;
REG_WINOUT = (REG_WINOUT & ~0x3F00) | 0x1900;
REG_WINOUT = (REG_WINOUT & ~0x3F) | 0x09;
}
void TitleScreen::func_ov025_020c5964() {
REG_DISPCNT &= ~0xE000;
REG_WINOUT = (REG_WINOUT & ~0x3F) | 0x30;
}
struct stack_struct {
unk16 a;
bool mUnk_02;
};
void TitleScreen_Sub2::vfunc_00() {
stack_struct sp14;
Vec2s sp10;
Vec2s spC;
Vec2us sp8;
func_ov000_0205be34(&sp14, 0x3E);
sp14.mUnk_02 = this->mUnk_10;
sp8 = data_ov025_020c5ae0;
spC = data_ov025_020c5ae8;
sp10 = data_ov025_020c5ae4;
func_ov000_0205bedc(&sp14, &sp10, &spC, &sp8, 0, 0);
}
+63
View File
@@ -0,0 +1,63 @@
#include "TitleScreen/TitleScreen.hpp"
#include "regs.h"
const unk16 data_ov025_020c5a0c[] = {0x0016, 0x003C};
extern "C" {
void GX_SetGraphicsMode(unk32 param1, unk32 param2, unk32 param3);
void GXS_SetGraphicsMode(unk32 param1);
}
ARM TitleScreenManager *TitleScreenManager::Create(unk32 param1) {
return new(HeapIndex_1) TitleScreenManager(param1);
}
ARM void TitleScreenManager::vfunc_14() {
this->mUnk_004.func_ov001_020bd734((unk32 *) data_ov025_020c5a0c);
this->mUnk_004.func_0201c00c(0x24, 1);
TitleScreen *pTitleScreen = new(HeapIndex_1) TitleScreen();
void *pUVar2 = pTitleScreen;
if (pTitleScreen != NULL) {
pUVar2 = &pTitleScreen->mUnk_04;
}
this->mpTitleScreen = pTitleScreen;
this->mUnk_104.mUnk_04.func_020166cc(pUVar2);
pTitleScreen->vfunc_18();
}
ARM void TitleScreenManager::vfunc_18() {
this->mUnk_004.func_ov001_020bd784();
delete this->mpTitleScreen;
this->mpTitleScreen = NULL;
}
ARM void TitleScreenManager::vfunc_24() {
this->GameModeManagerBase::vfunc_24();
this->func_0201875c();
this->func_02018908();
}
ARM void TitleScreenManager::vfunc_28(unk32 param1) {
this->GameModeManagerBase::vfunc_28(param1);
this->func_02018a14(param1);
}
ARM void TitleScreenManager::vfunc_2C(unk32 param1) {
this->func_02018984(param1);
this->func_02018830(param1);
}
ARM void TitleScreenManager::vfunc_38() {}
ARM void TitleScreenManager::func_ov025_020c4c20() {
this->mpTitleScreen->func_ov025_020c4e6c();
}
ARM void TitleScreenManager::func_ov025_020c4c30() {
this->mpTitleScreen->func_ov025_020c4e90();
}
TitleScreenManager::~TitleScreenManager() {}