diff --git a/config/SOUE01/rels/d_a_t_wood_areaNP/splits.txt b/config/SOUE01/rels/d_a_t_wood_areaNP/splits.txt index 888c7762..77082fd2 100644 --- a/config/SOUE01/rels/d_a_t_wood_areaNP/splits.txt +++ b/config/SOUE01/rels/d_a_t_wood_areaNP/splits.txt @@ -17,3 +17,6 @@ REL/global_destructor_chain.c: REL/d/a/d_a_t_wood_area.cpp: .text start:0x000000F0 end:0x00000EB8 .ctors start:0x00000000 end:0x00000004 + .rodata start:0x00000000 end:0x0000001C + .data start:0x00000000 end:0x000001DC + .bss start:0x00000008 end:0x00000088 diff --git a/config/SOUE01/rels/d_a_t_wood_areaNP/symbols.txt b/config/SOUE01/rels/d_a_t_wood_areaNP/symbols.txt index 5290fe16..8b869b01 100644 --- a/config/SOUE01/rels/d_a_t_wood_areaNP/symbols.txt +++ b/config/SOUE01/rels/d_a_t_wood_areaNP/symbols.txt @@ -3,48 +3,48 @@ _epilog = .text:0x00000030; // type:function size:0x2C scope:global _unresolved = .text:0x00000060; // type:function size:0x4 scope:global __register_global_object = .text:0x00000070; // type:function size:0x1C scope:global __destroy_global_chain = .text:0x00000090; // type:function size:0x54 scope:global -fn_329_F0 = .text:0x000000F0; // type:function size:0xCC -fn_329_1C0 = .text:0x000001C0; // type:function size:0x58 -fn_329_220 = .text:0x00000220; // type:function size:0x6C -fn_329_290 = .text:0x00000290; // type:function size:0xA0 -fn_329_330 = .text:0x00000330; // type:function size:0xA4 -fn_329_3E0 = .text:0x000003E0; // type:function size:0x14 -fn_329_400 = .text:0x00000400; // type:function size:0x58 -fn_329_460 = .text:0x00000460; // type:function size:0x9C -fn_329_500 = .text:0x00000500; // type:function size:0x10 -fn_329_510 = .text:0x00000510; // type:function size:0x64 -fn_329_580 = .text:0x00000580; // type:function size:0x8 -fn_329_590 = .text:0x00000590; // type:function size:0x30 -fn_329_5C0 = .text:0x000005C0; // type:function size:0x10 -fn_329_5D0 = .text:0x000005D0; // type:function size:0x8 -fn_329_5E0 = .text:0x000005E0; // type:function size:0x4 -fn_329_5F0 = .text:0x000005F0; // type:function size:0x18 -fn_329_610 = .text:0x00000610; // type:function size:0x4 -fn_329_620 = .text:0x00000620; // type:function size:0x4 -fn_329_630 = .text:0x00000630; // type:function size:0x134 -fn_329_770 = .text:0x00000770; // type:function size:0x4 -fn_329_780 = .text:0x00000780; // type:function size:0xEC -fn_329_870 = .text:0x00000870; // type:function size:0x80 -fn_329_8F0 = .text:0x000008F0; // type:function size:0x64 -fn_329_960 = .text:0x00000960; // type:function size:0xD8 -fn_329_A40 = .text:0x00000A40; // type:function size:0x10 -fn_329_A50 = .text:0x00000A50; // type:function size:0x60 -fn_329_AB0 = .text:0x00000AB0; // type:function size:0xC -fn_329_AC0 = .text:0x00000AC0; // type:function size:0x1C -fn_329_AE0 = .text:0x00000AE0; // type:function size:0x1C -fn_329_B00 = .text:0x00000B00; // type:function size:0x1C -fn_329_B20 = .text:0x00000B20; // type:function size:0x10 -fn_329_B30 = .text:0x00000B30; // type:function size:0x10 -fn_329_B40 = .text:0x00000B40; // type:function size:0x10 -fn_329_B50 = .text:0x00000B50; // type:function size:0x10 -fn_329_B60 = .text:0x00000B60; // type:function size:0x10 -fn_329_B70 = .text:0x00000B70; // type:function size:0x10 -fn_329_B80 = .text:0x00000B80; // type:function size:0x30 -fn_329_BB0 = .text:0x00000BB0; // type:function size:0x30 -fn_329_BE0 = .text:0x00000BE0; // type:function size:0x30 -fn_329_C10 = .text:0x00000C10; // type:function size:0x1C0 -fn_329_DD0 = .text:0x00000DD0; // type:function size:0x58 -fn_329_E30 = .text:0x00000E30; // type:function size:0x88 +dAcTWoodArea_c_classInit__Fv = .text:0x000000F0; // type:function size:0xCC +__dt__27sFState_c<14dAcTWoodArea_c>Fv = .text:0x000001C0; // type:function size:0x58 +__dt__30sFStateFct_c<14dAcTWoodArea_c>Fv = .text:0x00000220; // type:function size:0x6C +__dt__83sStateMgr_c<14dAcTWoodArea_c,20sStateMethodUsr_FI_c,12sFStateFct_c,13sStateIDChk_c>Fv = .text:0x00000290; // type:function size:0xA0 +__dt__53sFStateMgr_c<14dAcTWoodArea_c,20sStateMethodUsr_FI_c>Fv = .text:0x00000330; // type:function size:0xA4 +__ct__14fLiNdBa_Wood_cFv = .text:0x000003E0; // type:function size:0x14 +__dt__14fLiNdBa_Wood_cFv = .text:0x00000400; // type:function size:0x58 +actorCreate__14dAcTWoodArea_cFv = .text:0x00000460; // type:function size:0x9C +changeState__83sStateMgr_c<14dAcTWoodArea_c,20sStateMethodUsr_FI_c,12sFStateFct_c,13sStateIDChk_c>FRC12sStateIDIf_c = .text:0x00000500; // type:function size:0x10 +actorPostCreate__14dAcTWoodArea_cFv = .text:0x00000510; // type:function size:0x64 +doDelete__14dAcTWoodArea_cFv = .text:0x00000580; // type:function size:0x8 +actorExecute__14dAcTWoodArea_cFv = .text:0x00000590; // type:function size:0x30 +executeState__83sStateMgr_c<14dAcTWoodArea_c,20sStateMethodUsr_FI_c,12sFStateFct_c,13sStateIDChk_c>Fv = .text:0x000005C0; // type:function size:0x10 +draw__14dAcTWoodArea_cFv = .text:0x000005D0; // type:function size:0x8 +initializeState_Init__14dAcTWoodArea_cFv = .text:0x000005E0; // type:function size:0x4 +executeState_Init__14dAcTWoodArea_cFv = .text:0x000005F0; // type:function size:0x18 +finalizeState_Init__14dAcTWoodArea_cFv = .text:0x00000610; // type:function size:0x4 +initializeState_Wait__14dAcTWoodArea_cFv = .text:0x00000620; // type:function size:0x4 +executeState_Wait__14dAcTWoodArea_cFv = .text:0x00000630; // type:function size:0x134 +finalizeState_Wait__14dAcTWoodArea_cFv = .text:0x00000770; // type:function size:0x4 +attachCloseObjects__14dAcTWoodArea_cFUs = .text:0x00000780; // type:function size:0xEC +dropItems__14dAcTWoodArea_cFv = .text:0x00000870; // type:function size:0x80 +attachObject__14dAcTWoodArea_cFP12dAcObjBase_c = .text:0x000008F0; // type:function size:0x64 +__dt__14dAcTWoodArea_cFv = .text:0x00000960; // type:function size:0xD8 +getStateID__83sStateMgr_c<14dAcTWoodArea_c,20sStateMethodUsr_FI_c,12sFStateFct_c,13sStateIDChk_c>CFv = .text:0x00000A40; // type:function size:0x10 +build__30sFStateFct_c<14dAcTWoodArea_c>FRC12sStateIDIf_c = .text:0x00000A50; // type:function size:0x60 +dispose__30sFStateFct_c<14dAcTWoodArea_c>FRP10sStateIf_c = .text:0x00000AB0; // type:function size:0xC +initialize__27sFState_c<14dAcTWoodArea_c>Fv = .text:0x00000AC0; // type:function size:0x1C +execute__27sFState_c<14dAcTWoodArea_c>Fv = .text:0x00000AE0; // type:function size:0x1C +finalize__27sFState_c<14dAcTWoodArea_c>Fv = .text:0x00000B00; // type:function size:0x1C +initializeState__83sStateMgr_c<14dAcTWoodArea_c,20sStateMethodUsr_FI_c,12sFStateFct_c,13sStateIDChk_c>Fv = .text:0x00000B20; // type:function size:0x10 +finalizeState__83sStateMgr_c<14dAcTWoodArea_c,20sStateMethodUsr_FI_c,12sFStateFct_c,13sStateIDChk_c>Fv = .text:0x00000B30; // type:function size:0x10 +refreshState__83sStateMgr_c<14dAcTWoodArea_c,20sStateMethodUsr_FI_c,12sFStateFct_c,13sStateIDChk_c>Fv = .text:0x00000B40; // type:function size:0x10 +getState__83sStateMgr_c<14dAcTWoodArea_c,20sStateMethodUsr_FI_c,12sFStateFct_c,13sStateIDChk_c>CFv = .text:0x00000B50; // type:function size:0x10 +getNewStateID__83sStateMgr_c<14dAcTWoodArea_c,20sStateMethodUsr_FI_c,12sFStateFct_c,13sStateIDChk_c>CFv = .text:0x00000B60; // type:function size:0x10 +getOldStateID__83sStateMgr_c<14dAcTWoodArea_c,20sStateMethodUsr_FI_c,12sFStateFct_c,13sStateIDChk_c>CFv = .text:0x00000B70; // type:function size:0x10 +finalizeState__29sFStateID_c<14dAcTWoodArea_c>CFR14dAcTWoodArea_c = .text:0x00000B80; // type:function size:0x30 +executeState__29sFStateID_c<14dAcTWoodArea_c>CFR14dAcTWoodArea_c = .text:0x00000BB0; // type:function size:0x30 +initializeState__29sFStateID_c<14dAcTWoodArea_c>CFR14dAcTWoodArea_c = .text:0x00000BE0; // type:function size:0x30 +__sinit_\d_a_t_wood_area_cpp = .text:0x00000C10; // type:function size:0x1C0 +__dt__29sFStateID_c<14dAcTWoodArea_c>Fv = .text:0x00000DD0; // type:function size:0x58 +isSameName__29sFStateID_c<14dAcTWoodArea_c>CFPCc = .text:0x00000E30; // type:function size:0x88 _ctors = .ctors:0x00000000; // type:label scope:global _dtors = .dtors:0x00000000; // type:label scope:global __destroy_global_chain_reference = .dtors:0x00000000; // type:object size:0x4 scope:global @@ -52,14 +52,14 @@ lbl_329_rodata_0 = .rodata:0x00000000; // type:object size:0x4 data:float lbl_329_rodata_4 = .rodata:0x00000004; // type:object size:0x4 data:float lbl_329_rodata_8 = .rodata:0x00000008; // type:object size:0x4 data:float lbl_329_rodata_C = .rodata:0x0000000C; // type:object size:0x4 data:float -lbl_329_rodata_10 = .rodata:0x00000010; // type:object size:0xC data:2byte -lbl_329_data_0 = .data:0x00000000; // type:object size:0x10 data:4byte -lbl_329_data_10 = .data:0x00000010; // type:object size:0x80 -lbl_329_data_90 = .data:0x00000090; // type:object size:0x30 -lbl_329_data_C0 = .data:0x000000C0; // type:object size:0x30 -lbl_329_data_F0 = .data:0x000000F0; // type:object size:0x18 -lbl_329_data_108 = .data:0x00000108; // type:object size:0xA0 -lbl_329_data_1A8 = .data:0x000001A8; // type:object size:0x34 +FILTER_PROFILE = .rodata:0x00000010; // type:object size:0xC data:2byte +g_profile_TAG_WOOD_AREA = .data:0x00000000; // type:object size:0x10 data:4byte +__vt__14dAcTWoodArea_c = .data:0x00000010; // type:object size:0x80 +__vt__53sFStateMgr_c<14dAcTWoodArea_c,20sStateMethodUsr_FI_c> = .data:0x00000090; // type:object size:0x30 +__vt__83sStateMgr_c<14dAcTWoodArea_c,20sStateMethodUsr_FI_c,12sFStateFct_c,13sStateIDChk_c> = .data:0x000000C0; // type:object size:0x30 +__vt__30sFStateFct_c<14dAcTWoodArea_c> = .data:0x000000F0; // type:object size:0x14 +__vt__27sFState_c<14dAcTWoodArea_c> = .data:0x00000108; // type:object size:0x18 +__vt__29sFStateID_c<14dAcTWoodArea_c> = .data:0x000001A8; // type:object size:0x34 __global_destructor_chain = .bss:0x00000000; // type:object size:0x4 scope:global lbl_329_bss_8 = .bss:0x00000008; // type:object size:0x10 data:4byte lbl_329_bss_18 = .bss:0x00000018; // type:object size:0x40 data:4byte diff --git a/config/SOUE01/symbols.txt b/config/SOUE01/symbols.txt index 166c10e1..0f0ef210 100644 --- a/config/SOUE01/symbols.txt +++ b/config/SOUE01/symbols.txt @@ -1110,8 +1110,8 @@ fn_8002DE90 = .text:0x8002DE90; // type:function size:0xC fn_8002DEA0 = .text:0x8002DEA0; // type:function size:0xC fn_8002DEB0 = .text:0x8002DEB0; // type:function size:0x14 fn_8002DED0 = .text:0x8002DED0; // type:function size:0x14 -fn_8002DEF0 = .text:0x8002DEF0; // type:function size:0x158 -fn_8002E050 = .text:0x8002E050; // type:function size:0x84 +__ct__12dAcObjBase_cFv = .text:0x8002DEF0; // type:function size:0x158 +__dt__12dAcObjBase_cFv = .text:0x8002E050; // type:function size:0x84 fn_8002E0E0 = .text:0x8002E0E0; // type:function size:0x70 fn_8002E150 = .text:0x8002E150; // type:function size:0x148 fn_8002E2A0 = .text:0x8002E2A0; // type:function size:0x90 diff --git a/include/d/a/d_a_base.h b/include/d/a/d_a_base.h index b705940e..2a6ca355 100644 --- a/include/d/a/d_a_base.h +++ b/include/d/a/d_a_base.h @@ -93,13 +93,13 @@ protected: public: /* 8002c3b0 */ dAcBase_c(); - void setPostion(mVec3_c &r) { + void setPostion(const mVec3_c &r) { position = r; } - void SetScale(mVec3_c &r) { + void SetScale(const mVec3_c &r) { scale = r; } - void SetRotation(mAng3_c &r) { + void SetRotation(const mAng3_c &r) { rotation = r; } @@ -113,8 +113,17 @@ public: void copyRotation() { rot_copy = rotation; } - mVec3_c GetPostionDifference(const dAcBase_c *other) { - return position - other->position; + mVec3_c GetPostionDifference(const dAcBase_c &other) { + return position - other.position; + } + + f32 getSquareDistanceTo(const mVec3_c &point) { + mVec3_c diff = position - point; + return diff.x * diff.x + diff.z * diff.z; + } + + bool IsOutOfRange(const mVec3_c &point, f32 radius) { + return getSquareDistanceTo(point) > radius; } public: diff --git a/include/d/a/obj/d_a_obj_base.h b/include/d/a/obj/d_a_obj_base.h index 8988b8f6..d4a30b6a 100644 --- a/include/d/a/obj/d_a_obj_base.h +++ b/include/d/a/obj/d_a_obj_base.h @@ -2,8 +2,10 @@ #define D_A_OBJ_BASE_H #include "d/a/d_a_base.h" +#include "m/m_mtx.h" #include "m/types_m.h" + // Ghidra: ActorObjectBase // size: 0x330 // vtable: 0x805015b8 @@ -25,6 +27,12 @@ public: f32 forwardAccel; f32 forwardMaxSpeed; // TODO: add the rest + u8 unk1[0x15C - 0x150]; + /* 0x15C */ mMtx_c worldMatrix; + + nw4r::math::AABB boundingBox; + + u8 unk_0x1A4[0x330 - 0x1A4]; public: // could be their own thing? @@ -39,12 +47,12 @@ public: public: /* 8002def0 */ dAcObjBase_c(); /* 8002e050 */ virtual ~dAcObjBase_c(); - /* 8002e0e0 */ virtual int preCreate(); - /* 8002e150 */ virtual int preExecute(); - /* 8002e2a0 */ virtual void postExecute(); - /* 8002e330 */ virtual int preDraw(); + /* 8002e0e0 */ virtual int preCreate() override; + /* 8002e150 */ virtual int preExecute() override; + /* 8002e2a0 */ virtual void postExecute(MAIN_STATE_e state) override; + /* 8002e330 */ virtual int preDraw() override; /* 8002e5b0 */ virtual void *getObjectListEntry(); - /* 8002e5c0 */ virtual bool restorePosRotFromCopy(); + /* 8002e5c0 */ virtual bool restorePosRotFromCopy() override; /* 8002ea10 */ virtual bool canBeLinkedToWoodTag(); /* 8002ea20 */ virtual bool drop(); diff --git a/include/d/d_player.h b/include/d/d_player.h index 28f737b0..cc99016f 100644 --- a/include/d/d_player.h +++ b/include/d/d_player.h @@ -6,6 +6,11 @@ class dPlayer: public dAcObjBase_c { public: + /* 0x330 */ u8 unk_0x330[0x350 - 0x330]; + /* 0x350 */ u32 someFlags; + + + static dPlayer *LINK; }; diff --git a/src/REL/d/a/d_a_t_wood_area.cpp b/src/REL/d/a/d_a_t_wood_area.cpp index e69de29b..32caa365 100644 --- a/src/REL/d/a/d_a_t_wood_area.cpp +++ b/src/REL/d/a/d_a_t_wood_area.cpp @@ -0,0 +1,160 @@ +#include +#include +#include +#include +#include + +// Look I don't know why these levels of subclasses work +class fLiNdBa_Wood_c : public fLiNdBaAutoUnlink_c { +public: + fLiNdBa_Wood_c() : fLiNdBaAutoUnlink_c(nullptr) {} +}; + +class dAcTWoodArea_c : public dAcObjBase_c { +public: + dAcTWoodArea_c() : mStateMgr(*this, sStateID::null) {} + virtual ~dAcTWoodArea_c() {} + virtual int actorCreate() override; + virtual int actorPostCreate() override; + virtual int actorExecute() override; + virtual int draw() override; + virtual int doDelete() override; + + void attachCloseObjects(ProfileName profID); + void dropItems(); + bool attachObject(dAcObjBase_c *obj); + + f32 getAttachRadius() { + return scale.x * scaleX; + } + f32 getAttachRadiusSquare() { + return getAttachRadius() * getAttachRadius(); + } + + f32 getAttachHeight() { + return scale.y * scaleY; + } + + STATE_FUNC_DECLARE(dAcTWoodArea_c, Init); + STATE_FUNC_DECLARE(dAcTWoodArea_c, Wait); + + static const f32 scaleX; + static const f32 scaleY; + +private: + STATE_MGR_DECLARE(dAcTWoodArea_c); + + fLiNdBa_Wood_c mRefs[8]; +}; + +const f32 dAcTWoodArea_c::scaleX = 100.0f; +const f32 dAcTWoodArea_c::scaleY = 100.0f; + +SPECIAL_ACTOR_PROFILE(TAG_WOOD_AREA, dAcTWoodArea_c, fProfile::WOODAREA_TAG, 0x166, 0, 2); + +STATE_DEFINE(dAcTWoodArea_c, Init); +STATE_DEFINE(dAcTWoodArea_c, Wait); + +int dAcTWoodArea_c::actorCreate() { + mStateMgr.changeState(StateID_Init); + PSMTXTrans(worldMatrix.m, position.x, position.y, position.z); + boundingBox.min = mVec3_c(-0.0f, -0.0f, -0.0f); + boundingBox.max = mVec3_c(0.0f, 0.0f, 0.0f); + return 1; +} + +static const ProfileName FILTER_PROFILE[] = { + fProfile::OBJ_FRUIT, + fProfile::ITEM, + fProfile::NPC_KYUI_THIRD, + fProfile::OBJ_IVY_ROPE, + fProfile::NPC_SORAJIMA_BOY, +}; + +int dAcTWoodArea_c::actorPostCreate() { + for (u32 i = 0; i < 5; i++) { + attachCloseObjects(FILTER_PROFILE[i]); + } + return 1; +} + +int dAcTWoodArea_c::doDelete() { + return 1; +} + +int dAcTWoodArea_c::actorExecute() { + mStateMgr.executeState(); + return 1; +} + +int dAcTWoodArea_c::draw() { + return 1; +} + +void dAcTWoodArea_c::initializeState_Init() {} +void dAcTWoodArea_c::executeState_Init() { + mStateMgr.changeState(StateID_Wait); +} +void dAcTWoodArea_c::finalizeState_Init() {} + +extern "C" void fn_800298B0(u16, mVec3_c *, mAng3_c *, u32, u32, u32, u32, u32); +extern u16 PARTICLE_RESOURCE_ID_MAPPING[]; + +void dAcTWoodArea_c::initializeState_Wait() {} +void dAcTWoodArea_c::executeState_Wait() { + if (dPlayer::LINK != nullptr && (dPlayer::LINK->someFlags & 0x2000)) { + // This is a bit messed up + mVec3_c dist = position - dPlayer::LINK->position; + f32 attachRadius = getAttachRadius(); + attachRadius = attachRadius * attachRadius; + if (dist.x * dist.x + dist.z * dist.z < attachRadius) { + bool someEffectThing = subtype != 1 ? (params & 0xF) != 0 ? false : true : true; + if (someEffectThing) { + fn_800298B0(PARTICLE_RESOURCE_ID_MAPPING[8], + &mVec3_c(position.x, position.y + getAttachHeight(), position.z), nullptr, 0, 0, 0, 0, 0); + } + dropItems(); + } + } +} +void dAcTWoodArea_c::finalizeState_Wait() {} + +void dAcTWoodArea_c::attachCloseObjects(ProfileName profID) { + fBase_c *base = nullptr; + f32 attachRadius = getAttachRadius() * getAttachRadius(); + while (true) { + base = fManager_c::searchBaseByProfName(profID, base); + if (base == nullptr) { + break; + } + + dAcObjBase_c *obj = static_cast(base); + if (obj->canBeLinkedToWoodTag()) { + if (!(obj->getSquareDistanceTo(position) > attachRadius)) { + if (!attachObject(obj)) { + return; + } + } + } + } +} + +void dAcTWoodArea_c::dropItems() { + for (int i = 0; i < 8; i++) { + if (mRefs[i].p_owner != nullptr) { + if (static_cast(mRefs[i].p_owner)->drop()) { + mRefs[i].unlink(); + } + } + } +} + +bool dAcTWoodArea_c::attachObject(dAcObjBase_c *obj) { + for (int i = 0; i < 8; i++) { + if (mRefs[i].p_owner == nullptr) { + mRefs[i].link(obj); + return true; + } + } + return false; +} diff --git a/src/d/a/d_a_base.cpp b/src/d/a/d_a_base.cpp index 770ce347..ddcf28f7 100644 --- a/src/d/a/d_a_base.cpp +++ b/src/d/a/d_a_base.cpp @@ -393,8 +393,8 @@ bool dAcBase_c::getDistanceAndAngleToActor(dAcBase_c *actor, f32 distThresh, s16 // 8002d3e0 bool dAcBase_c::isWithinPlayerRadius(f32 radius) { - mVec3_c dist_diff = GetPostionDifference(dPlayer::LINK); - return dist_diff.x * dist_diff.x + dist_diff.z * dist_diff.z < radius * radius; + f32 dist_diff = getSquareDistanceTo(dPlayer::LINK->position); + return dist_diff < radius * radius; } // 8002d440