diff --git a/configure.py b/configure.py index 7a85dc1ecf..5ba1223497 100644 --- a/configure.py +++ b/configure.py @@ -2046,7 +2046,7 @@ config.libs = [ ActorRel(NonMatching, "d_a_obj_warp_obrg"), ActorRel(NonMatching, "d_a_obj_waterGate"), ActorRel(NonMatching, "d_a_obj_waterPillar"), - ActorRel(NonMatching, "d_a_obj_waterfall"), + ActorRel(Matching, "d_a_obj_waterfall"), ActorRel(NonMatching, "d_a_obj_wchain"), ActorRel(NonMatching, "d_a_obj_wdStick"), ActorRel(NonMatching, "d_a_obj_web0"), diff --git a/include/d/actor/d_a_obj_waterfall.h b/include/d/actor/d_a_obj_waterfall.h index 8aff42ab86..c71651b350 100644 --- a/include/d/actor/d_a_obj_waterfall.h +++ b/include/d/actor/d_a_obj_waterfall.h @@ -1,15 +1,16 @@ #ifndef D_A_OBJ_WATERFALL_H #define D_A_OBJ_WATERFALL_H +#include "SSystem/SComponent/c_phase.h" +#include "d/d_cc_d.h" #include "f_op/f_op_actor_mng.h" /** * @ingroup actors-objects * @class daObjWaterFall_c - * @brief Waterfall - * - * @details + * @brief Waterfall With Collision Object * + * @details Waterfalls that player cannot move through (e.g. those in Zora's Domain) */ class daObjWaterFall_c : public fopAc_ac_c { public: @@ -17,15 +18,37 @@ public: /* 80D2F034 */ void search_arrow(); /* 80D2F324 */ void initBaseMtx(); /* 80D2F344 */ void setBaseMtx(); - /* 80D2F39C */ void Create(); - /* 80D2F5A0 */ void create(); - /* 80D2F984 */ void execute(); + /* 80D2F39C */ cPhs__Step Create(); + /* 80D2F5A0 */ cPhs__Step create(); + /* 80D2F984 */ int execute(); /* 80D2FA6C */ void push_player(); - /* 80D2FC94 */ bool draw(); - /* 80D2FC9C */ void _delete(); - + /* 80D2FC94 */ int draw(); + /* 80D2FC9C */ int _delete(); private: - /* 0x568 */ u8 field_0x568[0x9cc - 0x568]; + /* 0x568 */ request_of_phase_process_class mPhase; + /* 0x570 */ u8 pad[4]; + /* 0x574 */ dCcD_Stts mCylColliderStts; + /* 0x5B0 */ dCcD_Tri mUnusedTriCollider[2]; + /* 0x868 */ dCcD_Cyl mCylCollider; + /* 0x9A4 */ cXyz mCylColliderCenterOscillationTargets[2]; + /* 0x9BC */ cXyz mCylColliderCenter; + /* 0x9C8 */ s8 mCylColliderCenterQuantizedOscillation; + + enum Type_e { + ALLOW_ARROWS_e + }; + + BOOL checkFallOut() { + return fopAcM_GetParamBit(this, 10, 4); + } + + Type_e getType() { + return static_cast(fopAcM_GetParamBit(this, 8, 2)); + } + + u32 getSwbit() { + return fopAcM_GetParamBit(this, 0, 8); + } }; STATIC_ASSERT(sizeof(daObjWaterFall_c) == 0x9cc); diff --git a/include/d/actor/d_a_tag_waterfall.h b/include/d/actor/d_a_tag_waterfall.h index 60d051eadd..b3ef34651d 100644 --- a/include/d/actor/d_a_tag_waterfall.h +++ b/include/d/actor/d_a_tag_waterfall.h @@ -3,6 +3,13 @@ #include "f_op/f_op_actor_mng.h" +/** + * @ingroup actors-tags + * @class daTagWaterFall_c + * @brief Waterfall Without Collision Tag + * + * @details Waterfalls player may move through (e.g. those in Iza's Rapid Ride) + */ class daTagWaterFall_c : public fopAc_ac_c { public: daTagWaterFall_c() {} @@ -49,4 +56,4 @@ public: /* 0x20 */ f32 field_0x20; }; -#endif /* D_A_TAG_WATERFALL_H */ \ No newline at end of file +#endif /* D_A_TAG_WATERFALL_H */ diff --git a/include/d/d_cc_d.h b/include/d/d_cc_d.h index 592a6d6e66..c1e68aa5c4 100644 --- a/include/d/d_cc_d.h +++ b/include/d/d_cc_d.h @@ -356,6 +356,7 @@ public: bool ChkAtStopNoConHit() { return mGObjAt.ChkSPrm(0x4); } bool ChkTgNoConHit() { return mGObjTg.ChkSPrm(2); } bool ChkTgStopNoConHit() { return mGObjTg.ChkSPrm(0x2000); } + void OnCoNoCamHit() { mGObjCo.OnSPrm(2); } bool ChkCoNoCamHit() { return mGObjCo.ChkSPrm(2); } dCcD_HitCallback GetCoHitCallback() { return mGObjCo.GetHitCallback(); } dCcD_HitCallback GetAtHitCallback() { return mGObjAt.GetHitCallback(); } diff --git a/src/d/actor/d_a_obj_waterfall.cpp b/src/d/actor/d_a_obj_waterfall.cpp index 1be7d1c90f..faba1c4320 100644 --- a/src/d/actor/d_a_obj_waterfall.cpp +++ b/src/d/actor/d_a_obj_waterfall.cpp @@ -1,184 +1,174 @@ /** * @file d_a_obj_waterfall.cpp - * */ #include "d/actor/d_a_obj_waterfall.h" -#include "d/d_cc_d.h" -#include "dol2asm.h" +#include "d/actor/d_a_arrow.h" +#include "d/d_com_inf_game.h" +#include "d/d_bomb.h" +#include "SSystem/SComponent/c_math.h" +#define MAX_TARGET_INFO_COUNT 10 -// -// Forward References: -// - -extern "C" static void s_b_sub__FPvPv(); -extern "C" static void s_a_sub__FPvPv(); -extern "C" void search_bomb__16daObjWaterFall_cFv(); -extern "C" void __dt__4cXyzFv(); -extern "C" void search_arrow__16daObjWaterFall_cFv(); -extern "C" void initBaseMtx__16daObjWaterFall_cFv(); -extern "C" void setBaseMtx__16daObjWaterFall_cFv(); -extern "C" void Create__16daObjWaterFall_cFv(); -extern "C" void create__16daObjWaterFall_cFv(); -extern "C" void __ct__4cXyzFv(); -extern "C" void __dt__8cM3dGCylFv(); -extern "C" void __dt__8cM3dGAabFv(); -extern "C" void __dt__8dCcD_TriFv(); -extern "C" void __ct__8dCcD_TriFv(); -extern "C" void __dt__8cM3dGTriFv(); -extern "C" void __dt__8cM3dGPlaFv(); -extern "C" void execute__16daObjWaterFall_cFv(); -extern "C" void push_player__16daObjWaterFall_cFv(); -extern "C" bool draw__16daObjWaterFall_cFv(); -extern "C" void _delete__16daObjWaterFall_cFv(); -extern "C" static void daObjWaterFall_Draw__FP16daObjWaterFall_c(); -extern "C" static void daObjWaterFall_Execute__FP16daObjWaterFall_c(); -extern "C" static void daObjWaterFall_Delete__FP16daObjWaterFall_c(); -extern "C" static void daObjWaterFall_Create__FP10fopAc_ac_c(); -extern "C" extern char const* const d_a_obj_waterfall__stringBase0; - -// -// External References: -// - -extern "C" void mDoMtx_ZXYrotM__FPA4_fsss(); -extern "C" void mDoMtx_YrotS__FPA4_fs(); -extern "C" void mDoMtx_YrotM__FPA4_fs(); -extern "C" void transS__14mDoMtx_stack_cFRC4cXyz(); -extern "C" void __ct__10fopAc_ac_cFv(); -extern "C" void fopAc_IsActor__FPv(); -extern "C" void fopAcM_delete__FP10fopAc_ac_c(); -extern "C" void fopAcM_searchActorDistanceXZ__FPC10fopAc_ac_cPC10fopAc_ac_c(); -extern "C" void fpcEx_Search__FPFPvPv_PvPv(); -extern "C" void dComIfG_resDelete__FP30request_of_phase_process_classPCc(); -extern "C" void checkWaterBomb__7dBomb_cFP10fopAc_ac_c(); -extern "C" void isSwitch__10dSv_info_cCFii(); -extern "C" void __ct__10dCcD_GSttsFv(); -extern "C" void Init__9dCcD_SttsFiiP10fopAc_ac_c(); -extern "C" void __ct__12dCcD_GObjInfFv(); -extern "C" void __dt__12dCcD_GObjInfFv(); -extern "C" void Set__8dCcD_CylFRC11dCcD_SrcCyl(); -extern "C" void Set__4cCcSFP8cCcD_Obj(); -extern "C" void __mi__4cXyzCFRC3Vec(); -extern "C" void cM_atan2s__Fff(); -extern "C" void SetC__8cM3dGCylFRC4cXyz(); -extern "C" void SetH__8cM3dGCylFf(); -extern "C" void SetR__8cM3dGCylFf(); -extern "C" void cLib_chasePosXZ__FP4cXyzRC4cXyzf(); -extern "C" void __dl__FPv(); -extern "C" void __construct_array(); -extern "C" void _savegpr_23(); -extern "C" void _savegpr_29(); -extern "C" void _restgpr_23(); -extern "C" void _restgpr_29(); -extern "C" extern void* __vt__8dCcD_Cyl[36]; -extern "C" extern void* __vt__8dCcD_Tri[36]; -extern "C" extern void* __vt__9dCcD_Stts[11]; -extern "C" extern void* __vt__12cCcD_CylAttr[25]; -extern "C" extern void* __vt__12cCcD_TriAttr[25]; -extern "C" extern void* __vt__14cCcD_ShapeAttr[22]; -extern "C" extern void* __vt__9cCcD_Stts[8]; -extern "C" u8 now__14mDoMtx_stack_c[48]; -extern "C" extern u8 g_dComIfG_gameInfo[122384]; - -// -// Declarations: -// +static int daObjWaterFall_Draw(daObjWaterFall_c* i_this); +static int daObjWaterFall_Execute(daObjWaterFall_c* i_this); +static int daObjWaterFall_Delete(daObjWaterFall_c* i_this); +static int daObjWaterFall_Create(fopAc_ac_c* i_this); /* ############################################################################################## */ /* 80D2FE50-80D2FE78 000000 0028+00 4/4 0/0 0/0 .bss target_info */ -static u8 target_info[40]; +static fopAc_ac_c* target_info[MAX_TARGET_INFO_COUNT]; /* 80D2FE78-80D2FE7C 000028 0004+00 4/4 0/0 0/0 .bss target_info_count */ -static u8 target_info_count[4]; +static s32 target_info_count; /* 80D2EC18-80D2ECA4 000078 008C+00 1/1 0/0 0/0 .text s_b_sub__FPvPv */ -static void s_b_sub(void* param_0, void* param_1) { - // NONMATCHING +static void* s_b_sub(void* param_0, void* unused) { + if(fopAcM_IsActor(param_0) && fopAcM_GetName(param_0) == PROC_NBOMB) { + dBomb_c* foundBomb = static_cast(param_0); + if(!foundBomb->checkWaterBomb(foundBomb) && fopAcM_GetParam(foundBomb) != dBomb_c::PRM_NORMAL_BOMB_EXPLODE) { + const u32 idx = target_info_count; // Regalloc issues if this isn't done + + if(target_info_count < MAX_TARGET_INFO_COUNT) { + target_info[idx] = foundBomb; + target_info_count++; + } + } + } + return NULL; } /* 80D2ECA4-80D2ED14 000104 0070+00 1/1 0/0 0/0 .text s_a_sub__FPvPv */ -static void s_a_sub(void* param_0, void* param_1) { - // NONMATCHING +static void* s_a_sub(void* param_0, void* unused) { + if(fopAcM_IsActor(param_0) && fopAcM_GetName(param_0) == PROC_ARROW) { + const u32 idx = target_info_count; // Regalloc issues if this isn't done + + if(target_info_count < MAX_TARGET_INFO_COUNT) { + daArrow_c* arrow_0 = static_cast(param_0); + target_info[idx] = arrow_0; + target_info_count++; + } + } + return NULL; } -/* ############################################################################################## */ -/* 80D2FD58-80D2FD5C 000000 0004+00 4/4 0/0 0/0 .rodata @3807 */ -SECTION_RODATA static u8 const lit_3807[4] = { - 0x00, - 0x00, - 0x00, - 0x00, -}; -COMPILER_STRIP_GATE(0x80D2FD58, &lit_3807); - -/* 80D2FD5C-80D2FD60 000004 0004+00 0/4 0/0 0/0 .rodata @3808 */ -#pragma push -#pragma force_active on -SECTION_RODATA static f32 const lit_3808 = 50.0f; -COMPILER_STRIP_GATE(0x80D2FD5C, &lit_3808); -#pragma pop - -/* 80D2FD60-80D2FD64 000008 0004+00 0/4 0/0 0/0 .rodata @3809 */ -#pragma push -#pragma force_active on -SECTION_RODATA static f32 const lit_3809 = 100.0f; -COMPILER_STRIP_GATE(0x80D2FD60, &lit_3809); -#pragma pop - /* 80D2ED14-80D2EFF8 000174 02E4+00 1/1 0/0 0/0 .text search_bomb__16daObjWaterFall_cFv */ void daObjWaterFall_c::search_bomb() { - // NONMATCHING -} + if(checkFallOut() != TRUE) { + // Get rid of previously found arrow or bomb processes populating target_info + target_info_count = 0; + for(u32 i = 0; i < MAX_TARGET_INFO_COUNT; i++) { + target_info[i] = NULL; + } -/* 80D2EFF8-80D2F034 000458 003C+00 1/1 0/0 0/0 .text __dt__4cXyzFv */ -// cXyz::~cXyz() { -extern "C" void __dt__4cXyzFv() { - // NONMATCHING + // Find first 10 bomb processes to populate target_info + fpcM_Search(s_b_sub, this); + + // Check whether the bomb processes are within bounds (and should therefore be deleted) + if(target_info_count) { + for(int i = 0; i < target_info_count; i++) { + cXyz vectorToOldBombPos; + cXyz vectorToCurrentBombPos; + dBomb_c* const bomb = static_cast(target_info[i]); + + vectorToOldBombPos = bomb->old.pos - current.pos; + vectorToCurrentBombPos = bomb->current.pos - current.pos; + + mDoMtx_stack_c::YrotS(-current.angle.y); + + mDoMtx_stack_c::multVec(&vectorToOldBombPos, &vectorToOldBombPos); + mDoMtx_stack_c::multVec(&vectorToCurrentBombPos, &vectorToCurrentBombPos); + + bool bombPassedZOriginPrevAndCurrentBombPosAreWithinXYBounds = ( + (vectorToOldBombPos.z * vectorToCurrentBombPos.z) < 0.0f && + (vectorToOldBombPos.x > -scale.x * 50.0f && vectorToOldBombPos.x < scale.x * 50.0f) && + (vectorToCurrentBombPos.x > -scale.x * 50.0f && vectorToCurrentBombPos.x < scale.x * 50.0f) && + (vectorToOldBombPos.y > 0.0f && vectorToOldBombPos.y < scale.y * 100.0f) && + (vectorToCurrentBombPos.y > 0.0f && vectorToCurrentBombPos.y < scale.y * 100.0f) + ); + + bool currentBombPosIsWithinXYZBounds = ( + (vectorToCurrentBombPos.x > -scale.x * 50.0f && vectorToCurrentBombPos.x < scale.x * 50.0f) && + (vectorToCurrentBombPos.y > 0.0f && vectorToCurrentBombPos.y < scale.y * 100.0f) && + (vectorToCurrentBombPos.z > -scale.z * 50.0f && vectorToCurrentBombPos.z < scale.z * 50.0f) + ); + + if(bombPassedZOriginPrevAndCurrentBombPosAreWithinXYBounds || currentBombPosIsWithinXYZBounds) + fopAcM_delete(bomb); + } + } + } } /* 80D2F034-80D2F324 000494 02F0+00 1/1 0/0 0/0 .text search_arrow__16daObjWaterFall_cFv */ void daObjWaterFall_c::search_arrow() { - // NONMATCHING + // Some waterfalls (e.g. in the Lakebed Temple) allow arrows to fly through them + if(getType() == ALLOW_ARROWS_e || checkFallOut() == TRUE) + return; + + // Get rid of previously found arrow or bomb processes populating target_info + target_info_count = 0; + for(u32 i = 0; i < MAX_TARGET_INFO_COUNT; i++) { + target_info[i] = NULL; + } + + // Find first 10 arrow processes to populate target_info + fpcM_Search(s_a_sub, this); + + // Check whether the arrow processes are within bounds (and should therefore be deleted) + if(target_info_count) { + for(int i = 0; i < target_info_count; i++) { + cXyz vectorToOldArrowPos; + cXyz vectorToCurrentArrowPos; + daArrow_c* const arrow = static_cast(target_info[i]); + + vectorToOldArrowPos = arrow->old.pos - current.pos; + vectorToCurrentArrowPos = arrow->current.pos - current.pos; + + mDoMtx_stack_c::YrotS(-current.angle.y); + + mDoMtx_stack_c::multVec(&vectorToOldArrowPos, &vectorToOldArrowPos); + mDoMtx_stack_c::multVec(&vectorToCurrentArrowPos, &vectorToCurrentArrowPos); + + bool arrowPassedZOriginPrevAndCurrentArrowPosAreWithinXYBounds = ( + (vectorToOldArrowPos.z * vectorToCurrentArrowPos.z) < 0.0f && + (vectorToOldArrowPos.x > -scale.x * 50.0f && vectorToOldArrowPos.x < scale.x * 50.0f) && + (vectorToCurrentArrowPos.x > -scale.x * 50.0f && vectorToCurrentArrowPos.x < scale.x * 50.0f) && + (vectorToOldArrowPos.y > 0.0f && vectorToOldArrowPos.y < scale.y * 100.0f) && + (vectorToCurrentArrowPos.y > 0.0f && vectorToCurrentArrowPos.y < scale.y * 100.0f) + ); + + bool currentArrowPosIsWithinXYZBounds = ( + (vectorToCurrentArrowPos.x > -scale.x * 50.0f && vectorToCurrentArrowPos.x < scale.x * 50.0f) && + (vectorToCurrentArrowPos.y > 0.0f && vectorToCurrentArrowPos.y < scale.y * 100.0f) && + (vectorToCurrentArrowPos.z > -scale.z * 50.0f && vectorToCurrentArrowPos.z < scale.z * 50.0f) + ); + + if(arrowPassedZOriginPrevAndCurrentArrowPosAreWithinXYBounds || currentArrowPosIsWithinXYZBounds) + fopAcM_delete(arrow); + } + } } /* 80D2F324-80D2F344 000784 0020+00 1/1 0/0 0/0 .text initBaseMtx__16daObjWaterFall_cFv */ void daObjWaterFall_c::initBaseMtx() { - // NONMATCHING + setBaseMtx(); } /* 80D2F344-80D2F39C 0007A4 0058+00 1/1 0/0 0/0 .text setBaseMtx__16daObjWaterFall_cFv */ void daObjWaterFall_c::setBaseMtx() { - // NONMATCHING + cXyz* pos = fopAcM_GetPosition_p(this); + PSMTXTrans(mDoMtx_stack_c::get(), pos->x, pos->y, pos->z); + + csXyz* shapeAngle = fopAcM_GetShapeAngle_p(this); + mDoMtx_stack_c::ZXYrotM(shapeAngle->x, shapeAngle->y, shapeAngle->z); } -/* ############################################################################################## */ -/* 80D2FD64-80D2FD68 00000C 0004+00 0/1 0/0 0/0 .rodata @3953 */ -#pragma push -#pragma force_active on -SECTION_RODATA static f32 const lit_3953 = -50.0f; -COMPILER_STRIP_GATE(0x80D2FD64, &lit_3953); -#pragma pop - -/* 80D2FD68-80D2FD6C 000010 0004+00 0/2 0/0 0/0 .rodata @3954 */ -#pragma push -#pragma force_active on -SECTION_RODATA static f32 const lit_3954 = 10.0f; -COMPILER_STRIP_GATE(0x80D2FD68, &lit_3954); -#pragma pop - -/* 80D2FD7C-80D2FD7C 000024 0000+00 0/0 0/0 0/0 .rodata @stringBase0 */ -#pragma push -#pragma force_active on -SECTION_DEAD static char const* const stringBase_80D2FD7C = "sample"; -#pragma pop - /* 80D2FD84-80D2FD88 -00001 0004+00 1/1 0/0 0/0 .data l_arcName */ -SECTION_DATA static void* l_arcName = (void*)&d_a_obj_waterfall__stringBase0; +static const char* l_arcName = "sample"; /* 80D2FD88-80D2FDCC 000004 0044+00 1/1 0/0 0/0 .data l_cyl_src */ static dCcD_SrcCyl l_cyl_src = { @@ -196,18 +186,58 @@ static dCcD_SrcCyl l_cyl_src = { }; /* 80D2F39C-80D2F5A0 0007FC 0204+00 1/1 0/0 0/0 .text Create__16daObjWaterFall_cFv */ -void daObjWaterFall_c::Create() { - // NONMATCHING +cPhs__Step daObjWaterFall_c::Create() { + initBaseMtx(); + + mCylColliderStts.Init(0, 0xFF, this); + mCylCollider.Set(l_cyl_src); + mCylCollider.SetStts(&mCylColliderStts); + mCylCollider.SetH(scale.y * 100.0f); + + if(scale.x < scale.z) + mCylCollider.SetR(scale.x * 50.0f); + else + mCylCollider.SetR(scale.z * 50.0f); + + mCylCollider.OnCoNoCamHit(); + + // If a waterfall process is not a circular cylinder (i.e. scale.x != scale.z), the circular cylindrical collider + // is oscillated in order to approximate the elliptical shape of the process. + // + // The member variable speedF (inherited from fopAc_ac_c) is used to control the speed of oscillation + // + // This effect can be observed at the largest waterfall in Zora's Domain + if(scale.x > scale.z) { + mCylColliderCenterOscillationTargets[0].set((scale.x * -50.0f) + (scale.z * 50.0f), 0.0f,0.0f); + mCylColliderCenterOscillationTargets[1].set((scale.x * 50.0f) - (scale.z * 50.0f), 0.0f,0.0f); + speedF = ((scale.x * 100.0f) - (scale.z * 100.0f)) / 10.0f; + } + else { + mCylColliderCenterOscillationTargets[0].set(0.0f, 0.0f,(scale.z * -50.0f) + (scale.x * 50.0f)); + mCylColliderCenterOscillationTargets[1].set(0.0f, 0.0f,(scale.z * 50.0f) - (scale.x * 50.0f)); + speedF = ((scale.z * 100.0f) - (scale.x * 100.0f)) / 10.0f; + } + + mDoMtx_stack_c::transS(home.pos); + mDoMtx_stack_c::YrotM(home.angle.y); + + PSMTXMultVec(mDoMtx_stack_c::get(), &mCylColliderCenterOscillationTargets[0], &mCylColliderCenterOscillationTargets[0]); + PSMTXMultVec(mDoMtx_stack_c::get(), &mCylColliderCenterOscillationTargets[1], &mCylColliderCenterOscillationTargets[1]); + + mCylColliderCenter = mCylColliderCenterOscillationTargets[0]; + mCylColliderCenterQuantizedOscillation = 1; + + return cPhs_LOADING_e; } /* ############################################################################################## */ /* 80D2FDCC-80D2FDEC -00001 0020+00 1/0 0/0 0/0 .data l_daObjWaterFall_Method */ static actor_method_class l_daObjWaterFall_Method = { - (process_method_func)daObjWaterFall_Create__FP10fopAc_ac_c, - (process_method_func)daObjWaterFall_Delete__FP16daObjWaterFall_c, - (process_method_func)daObjWaterFall_Execute__FP16daObjWaterFall_c, - 0, - (process_method_func)daObjWaterFall_Draw__FP16daObjWaterFall_c, + (process_method_func)daObjWaterFall_Create, + (process_method_func)daObjWaterFall_Delete, + (process_method_func)daObjWaterFall_Execute, + NULL, + (process_method_func)daObjWaterFall_Draw, }; /* 80D2FDEC-80D2FE1C -00001 0030+00 0/0 0/0 1/0 .data g_profile_Obj_WaterFall */ @@ -228,151 +258,107 @@ extern actor_process_profile_definition g_profile_Obj_WaterFall = { fopAc_CULLBOX_CUSTOM_e, // cullType }; -/* 80D2FE1C-80D2FE28 000098 000C+00 4/4 0/0 0/0 .data __vt__8cM3dGPla */ -SECTION_DATA extern void* __vt__8cM3dGPla[3] = { - (void*)NULL /* RTTI */, - (void*)NULL, - (void*)__dt__8cM3dGPlaFv, -}; - -/* 80D2FE28-80D2FE34 0000A4 000C+00 3/3 0/0 0/0 .data __vt__8cM3dGTri */ -SECTION_DATA extern void* __vt__8cM3dGTri[3] = { - (void*)NULL /* RTTI */, - (void*)NULL, - (void*)__dt__8cM3dGTriFv, -}; - -/* 80D2FE34-80D2FE40 0000B0 000C+00 2/2 0/0 0/0 .data __vt__8cM3dGCyl */ -SECTION_DATA extern void* __vt__8cM3dGCyl[3] = { - (void*)NULL /* RTTI */, - (void*)NULL, - (void*)__dt__8cM3dGCylFv, -}; - -/* 80D2FE40-80D2FE4C 0000BC 000C+00 4/4 0/0 0/0 .data __vt__8cM3dGAab */ -SECTION_DATA extern void* __vt__8cM3dGAab[3] = { - (void*)NULL /* RTTI */, - (void*)NULL, - (void*)__dt__8cM3dGAabFv, -}; - /* 80D2F5A0-80D2F6DC 000A00 013C+00 1/1 0/0 0/0 .text create__16daObjWaterFall_cFv */ -void daObjWaterFall_c::create() { - // NONMATCHING -} +cPhs__Step daObjWaterFall_c::create() { + fopAcM_SetupActor(this, daObjWaterFall_c); -/* 80D2F6DC-80D2F6E0 000B3C 0004+00 1/1 0/0 0/0 .text __ct__4cXyzFv */ -// cXyz::cXyz() { -extern "C" void __ct__4cXyzFv() { - /* empty function */ -} - -/* 80D2F6E0-80D2F728 000B40 0048+00 1/0 0/0 0/0 .text __dt__8cM3dGCylFv */ -// cM3dGCyl::~cM3dGCyl() { -extern "C" void __dt__8cM3dGCylFv() { - // NONMATCHING -} - -/* 80D2F728-80D2F770 000B88 0048+00 1/0 0/0 0/0 .text __dt__8cM3dGAabFv */ -// cM3dGAab::~cM3dGAab() { -extern "C" void __dt__8cM3dGAabFv() { - // NONMATCHING -} - -/* 80D2F770-80D2F850 000BD0 00E0+00 1/1 0/0 0/0 .text __dt__8dCcD_TriFv */ -// dCcD_Tri::~dCcD_Tri() { -extern "C" void __dt__8dCcD_TriFv() { - // NONMATCHING -} - -/* 80D2F850-80D2F8E0 000CB0 0090+00 1/1 0/0 0/0 .text __ct__8dCcD_TriFv */ -// dCcD_Tri::dCcD_Tri() { -extern "C" void __ct__8dCcD_TriFv() { - // NONMATCHING -} - -/* 80D2F8E0-80D2F93C 000D40 005C+00 1/0 0/0 0/0 .text __dt__8cM3dGTriFv */ -// cM3dGTri::~cM3dGTri() { -extern "C" void __dt__8cM3dGTriFv() { - // NONMATCHING -} - -/* 80D2F93C-80D2F984 000D9C 0048+00 1/0 0/0 0/0 .text __dt__8cM3dGPlaFv */ -// cM3dGPla::~cM3dGPla() { -extern "C" void __dt__8cM3dGPlaFv() { - // NONMATCHING + if(Create() == cPhs_INIT_e) { + return cPhs_ERROR_e; + } + + return cPhs_COMPLEATE_e; } /* 80D2F984-80D2FA6C 000DE4 00E8+00 1/1 0/0 0/0 .text execute__16daObjWaterFall_cFv */ -void daObjWaterFall_c::execute() { - // NONMATCHING +int daObjWaterFall_c::execute() { + if(getSwbit() != 0xFF && !fopAcM_isSwitch(this, getSwbit())) + return 1; + + push_player(); + search_bomb(); + search_arrow(); + + if(mCylColliderCenterQuantizedOscillation > 0) { + if(cLib_chasePosXZ(&mCylColliderCenter, mCylColliderCenterOscillationTargets[1], speedF)) + mCylColliderCenterQuantizedOscillation = -1; + } + else if(cLib_chasePosXZ(&mCylColliderCenter, mCylColliderCenterOscillationTargets[0], speedF)) { + mCylColliderCenterQuantizedOscillation = 1; + } + + mCylCollider.SetC(mCylColliderCenter); + dComIfG_Ccsp()->Set(&mCylCollider); + + return 1; } -/* ############################################################################################## */ -/* 80D2FD6C-80D2FD70 000014 0004+00 0/1 0/0 0/0 .rodata @4203 */ -#pragma push -#pragma force_active on -SECTION_RODATA static f32 const lit_4203 = 25.0f; -COMPILER_STRIP_GATE(0x80D2FD6C, &lit_4203); -#pragma pop - -/* 80D2FD70-80D2FD74 000018 0004+00 0/1 0/0 0/0 .rodata @4204 */ -#pragma push -#pragma force_active on -SECTION_RODATA static f32 const lit_4204 = -10.0f; -COMPILER_STRIP_GATE(0x80D2FD70, &lit_4204); -#pragma pop - -/* 80D2FD74-80D2FD78 00001C 0004+00 0/1 0/0 0/0 .rodata @4205 */ -#pragma push -#pragma force_active on -SECTION_RODATA static f32 const lit_4205 = 60.0f; -COMPILER_STRIP_GATE(0x80D2FD74, &lit_4205); -#pragma pop - -/* 80D2FD78-80D2FD7C 000020 0004+00 0/1 0/0 0/0 .rodata @4206 */ -#pragma push -#pragma force_active on -SECTION_RODATA static f32 const lit_4206 = -60.0f; -COMPILER_STRIP_GATE(0x80D2FD78, &lit_4206); -#pragma pop - /* 80D2FA6C-80D2FC94 000ECC 0228+00 1/1 0/0 0/0 .text push_player__16daObjWaterFall_cFv */ void daObjWaterFall_c::push_player() { - // NONMATCHING + daPy_py_c* const player = daPy_getPlayerActorClass(); + + f32 outMagnitude = 10.0f; + if(daPy_getLinkPlayerActorClass()->checkWolf()) + outMagnitude = 25.0f; + + if(scale.x == scale.z) { + // Waterfall is a circular cylinder + const f32 distToPlayer = fopAcM_searchPlayerDistanceXZ(this); + + if(distToPlayer < scale.x * 50.0f) { + cXyz vectorToPlayer = player->current.pos - current.pos; + s16 outAngle = cM_atan2s(vectorToPlayer.x, vectorToPlayer.z); + player->setOutPower(outMagnitude,outAngle,FALSE); + } + } + else { + // Waterfall is an elliptic cylinder + cXyz vectorToPlayer = player->current.pos - current.pos; + + mDoMtx_YrotS(mDoMtx_stack_c::get(), -current.angle.y); + PSMTXMultVec(mDoMtx_stack_c::get(), &vectorToPlayer, &vectorToPlayer); + + if((vectorToPlayer.x > -scale.x * 50.0f && vectorToPlayer.x < scale.x * 50.0f) && + vectorToPlayer.y > -10.0f && vectorToPlayer.y < scale.y * 100.0f) { + if(vectorToPlayer.z >= scale.z * 10.0f && vectorToPlayer.z < scale.z * 60.0f) { + player->setOutPower(outMagnitude, current.angle.y, FALSE); + } + else if(vectorToPlayer.z < scale.z * -10.0f && vectorToPlayer.z > scale.z * -60.0f) { + player->setOutPower(outMagnitude, (current.angle.y + (1 << 16)) - 0x8000, FALSE); + } + } + } } /* 80D2FC94-80D2FC9C 0010F4 0008+00 1/1 0/0 0/0 .text draw__16daObjWaterFall_cFv */ -bool daObjWaterFall_c::draw() { - return true; +int daObjWaterFall_c::draw() { + return 1; } /* 80D2FC9C-80D2FCD0 0010FC 0034+00 1/1 0/0 0/0 .text _delete__16daObjWaterFall_cFv */ -void daObjWaterFall_c::_delete() { - // NONMATCHING +int daObjWaterFall_c::_delete() { + dComIfG_resDelete(&mPhase, l_arcName); + return 1; } /* 80D2FCD0-80D2FCF0 001130 0020+00 1/0 0/0 0/0 .text daObjWaterFall_Draw__FP16daObjWaterFall_c */ -static void daObjWaterFall_Draw(daObjWaterFall_c* param_0) { - // NONMATCHING +static int daObjWaterFall_Draw(daObjWaterFall_c* i_this) { + return i_this->draw(); } /* 80D2FCF0-80D2FD10 001150 0020+00 1/0 0/0 0/0 .text daObjWaterFall_Execute__FP16daObjWaterFall_c */ -static void daObjWaterFall_Execute(daObjWaterFall_c* param_0) { - // NONMATCHING +static int daObjWaterFall_Execute(daObjWaterFall_c* i_this) { + return i_this->execute(); } /* 80D2FD10-80D2FD30 001170 0020+00 1/0 0/0 0/0 .text daObjWaterFall_Delete__FP16daObjWaterFall_c */ -static void daObjWaterFall_Delete(daObjWaterFall_c* param_0) { - // NONMATCHING +static int daObjWaterFall_Delete(daObjWaterFall_c* i_this) { + return i_this->_delete(); } /* 80D2FD30-80D2FD50 001190 0020+00 1/0 0/0 0/0 .text daObjWaterFall_Create__FP10fopAc_ac_c */ -static void daObjWaterFall_Create(fopAc_ac_c* param_0) { - // NONMATCHING +static int daObjWaterFall_Create(fopAc_ac_c* i_this) { + return static_cast(i_this)->create(); } - -/* 80D2FD7C-80D2FD7C 000024 0000+00 0/0 0/0 0/0 .rodata @stringBase0 */ \ No newline at end of file