diff --git a/include/z64skin.h b/include/z64skin.h index adb2f9b0fb..3d0969fb25 100644 --- a/include/z64skin.h +++ b/include/z64skin.h @@ -78,8 +78,8 @@ typedef struct { /* 0x04C */ SkelAnime skelAnime; } Skin; // size = 0x90 -typedef void (*SkinPostDraw)(struct Actor*, struct GlobalContext*, Skin*); -typedef s32 (*SkinOverrideLimbDraw)(struct Actor*, struct GlobalContext*, s32, Skin*); +typedef void (*SkinPostDraw)(struct Actor* thisx, struct GlobalContext* globalCtx, Skin* skin); +typedef s32 (*SkinOverrideLimbDraw)(struct Actor* thisx, struct GlobalContext* globalCtx, s32 limbIndex, Skin* skin); #define SKIN_DRAW_FLAG_CUSTOM_TRANSFORMS (1 << 0) #define SKIN_DRAW_FLAG_CUSTOM_MATRIX (1 << 1) diff --git a/spec b/spec index dc4eaa6b56..54a7826549 100644 --- a/spec +++ b/spec @@ -1169,8 +1169,7 @@ beginseg name "ovl_En_Horse_Link_Child" compress include "build/src/overlays/actors/ovl_En_Horse_Link_Child/z_en_horse_link_child.o" - include "build/data/ovl_En_Horse_Link_Child/ovl_En_Horse_Link_Child.data.o" - include "build/data/ovl_En_Horse_Link_Child/ovl_En_Horse_Link_Child.reloc.o" + include "build/src/overlays/actors/ovl_En_Horse_Link_Child/ovl_En_Horse_Link_Child_reloc.o" endseg beginseg diff --git a/src/overlays/actors/ovl_En_Horse_Link_Child/z_en_horse_link_child.c b/src/overlays/actors/ovl_En_Horse_Link_Child/z_en_horse_link_child.c index da62a57e0a..26295c6eb7 100644 --- a/src/overlays/actors/ovl_En_Horse_Link_Child/z_en_horse_link_child.c +++ b/src/overlays/actors/ovl_En_Horse_Link_Child/z_en_horse_link_child.c @@ -5,6 +5,7 @@ */ #include "z_en_horse_link_child.h" +#include "objects/object_horse_link_child/object_horse_link_child.h" #define FLAGS (ACTOR_FLAG_10 | ACTOR_FLAG_2000000) @@ -15,7 +16,16 @@ void EnHorseLinkChild_Destroy(Actor* thisx, GlobalContext* globalCtx); void EnHorseLinkChild_Update(Actor* thisx, GlobalContext* globalCtx); void EnHorseLinkChild_Draw(Actor* thisx, GlobalContext* globalCtx); -#if 0 +void func_808DEA0C(EnHorseLinkChild* this, GlobalContext* globalCtx); +void func_808DEB14(EnHorseLinkChild* this, GlobalContext* globalCtx); +void func_808DECA0(EnHorseLinkChild* this); +void func_808DED40(EnHorseLinkChild* this, GlobalContext* globalCtx); +void func_808DEFE8(EnHorseLinkChild* this); +void func_808DF194(EnHorseLinkChild* this, GlobalContext* globalCtx); +void func_808DF620(EnHorseLinkChild* this, GlobalContext* globalCtx); +void func_808DF788(EnHorseLinkChild* this); +void func_808DF838(EnHorseLinkChild* this, GlobalContext* globalCtx); + const ActorInit En_Horse_Link_Child_InitVars = { ACTOR_EN_HORSE_LINK_CHILD, ACTORCAT_BG, @@ -28,77 +38,560 @@ const ActorInit En_Horse_Link_Child_InitVars = { (ActorFunc)EnHorseLinkChild_Draw, }; -// static ColliderJntSphElementInit sJntSphElementsInit[1] = { -static ColliderJntSphElementInit D_808DFED4[1] = { +AnimationHeader* D_808DFEC0[] = { &object_horse_link_child_Anim_006D44, &object_horse_link_child_Anim_007468 }; + +AnimationHeader* D_808DFEC8[] = { &object_horse_link_child_Anim_007D50, &object_horse_link_child_Anim_0043AC, + &object_horse_link_child_Anim_002F98 }; + +static ColliderJntSphElementInit sJntSphElementsInit[] = { { - { ELEMTYPE_UNK0, { 0x00000000, 0x00, 0x00 }, { 0x00000000, 0x00, 0x00 }, TOUCH_NONE | TOUCH_SFX_NORMAL, BUMP_NONE, OCELEM_ON, }, + { + ELEMTYPE_UNK0, + { 0x00000000, 0x00, 0x00 }, + { 0x00000000, 0x00, 0x00 }, + TOUCH_NONE | TOUCH_SFX_NORMAL, + BUMP_NONE, + OCELEM_ON, + }, { 13, { { 0, 0, 0 }, 10 }, 100 }, }, }; -// static ColliderJntSphInit sJntSphInit = { -static ColliderJntSphInit D_808DFEF8 = { - { COLTYPE_NONE, AT_NONE, AC_ON | AC_TYPE_PLAYER, OC1_ON | OC1_TYPE_ALL, OC2_TYPE_1 | OC2_UNK1, COLSHAPE_JNTSPH, }, - 1, D_808DFED4, // sJntSphElementsInit, +static ColliderJntSphInit sJntSphInit = { + { + COLTYPE_NONE, + AT_NONE, + AC_ON | AC_TYPE_PLAYER, + OC1_ON | OC1_TYPE_ALL, + OC2_TYPE_1 | OC2_UNK1, + COLSHAPE_JNTSPH, + }, + ARRAY_COUNT(sJntSphElementsInit), + sJntSphElementsInit, }; -// sColChkInfoInit -static CollisionCheckInfoInit D_808DFF08 = { 10, 35, 100, MASS_HEAVY }; +static CollisionCheckInfoInit sColChkInfoInit = { 10, 35, 100, MASS_HEAVY }; -// static InitChainEntry sInitChain[] = { -static InitChainEntry D_808DFF2C[] = { +s32 D_808DFF10[] = { 1, 19 }; + +f32 D_808DFF18[] = { 1.0f, 1.0f, 1.5f, 1.5f, 1.5f }; + +static InitChainEntry sInitChain[] = { ICHAIN_F32(uncullZoneScale, 1200, ICHAIN_STOP), }; -#endif +EnHorseLinkChildUnkFunc D_808DFF30[] = { + func_808DEA0C, func_808DED40, func_808DEB14, func_808DF194, func_808DF838, func_808DF620, +}; -extern ColliderJntSphElementInit D_808DFED4[1]; -extern ColliderJntSphInit D_808DFEF8; -extern CollisionCheckInfoInit D_808DFF08; -extern InitChainEntry D_808DFF2C[]; +TexturePtr D_808DFF48[] = { object_horse_link_child_Tex_001D28, object_horse_link_child_Tex_001928, + object_horse_link_child_Tex_001B28 }; -extern UNK_TYPE D_06002F98; +s8 D_808DFF54[] = { 0, 1, 2, 1 }; -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/func_808DE5C0.s") +void func_808DE5C0(EnHorseLinkChild* this) { + if ((D_808DFF10[this->unk_1E8] < this->skin.skelAnime.curFrame) && + ((this->unk_1E8 != 0) || !(D_808DFF10[1] < this->skin.skelAnime.curFrame))) { + Audio_PlaySfxAtPos(&this->actor.projectedPos, NA_SE_EV_KID_HORSE_WALK); + this->unk_1E8++; + if (this->unk_1E8 >= 2) { + this->unk_1E8 = 0; + } + } +} -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/func_808DE660.s") +void func_808DE660(EnHorseLinkChild* this) { + if (this->unk_148 == 2) { + func_808DE5C0(this); + } else if (this->skin.skelAnime.curFrame == 0.0f) { + if ((this->unk_148 == 3) || (this->unk_148 == 4)) { + Audio_PlaySfxAtPos(&this->actor.projectedPos, NA_SE_EV_KID_HORSE_RUN); + } else if (this->unk_148 == 1) { + if (Rand_ZeroOne() > 0.5f) { + Audio_PlaySfxAtPos(&this->actor.projectedPos, NA_SE_EV_KID_HORSE_GROAN); + } else { + Audio_PlaySfxAtPos(&this->actor.projectedPos, NA_SE_EV_KID_HORSE_NEIGH); + } + } + } +} -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/func_808DE728.s") +f32 func_808DE728(EnHorseLinkChild* this) { + f32 phi_fv1; -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/EnHorseLinkChild_Init.s") + if (this->unk_148 == 2) { + phi_fv1 = D_808DFF18[this->unk_148] * this->actor.speedXZ * (1.0f / 2.0f); + } else if (this->unk_148 == 3) { + phi_fv1 = D_808DFF18[this->unk_148] * this->actor.speedXZ * (1.0f / 3.0f); + } else if (this->unk_148 == 4) { + phi_fv1 = D_808DFF18[this->unk_148] * this->actor.speedXZ * (1.0f / 5.0f); + } else { + phi_fv1 = D_808DFF18[this->unk_148]; + } + return phi_fv1; +} -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/EnHorseLinkChild_Destroy.s") +void EnHorseLinkChild_Init(Actor* thisx, GlobalContext* globalCtx) { + EnHorseLinkChild* this = THIS; -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/func_808DE9A8.s") + Actor_ProcessInitChain(&this->actor, sInitChain); + Actor_SetScale(&this->actor, 0.00648f); -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/func_808DEA0C.s") + this->actor.gravity = -3.5f; -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/func_808DEA54.s") + ActorShape_Init(&this->actor.shape, 0.0f, ActorShadow_DrawHorse, 20.0f); -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/func_808DEB14.s") + this->unk_144 = 1; + this->actor.speedXZ = 0.0f; + this->actor.focus.pos = this->actor.world.pos; + this->actor.focus.pos.y += 70.0f; -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/func_808DECA0.s") + Skin_Init(&globalCtx->state, &this->skin, &object_horse_link_child_Skel_00A480, + &object_horse_link_child_Anim_002F98); + this->unk_148 = 0; + Animation_PlayOnce(&this->skin.skelAnime, D_808DFEC0[0]); -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/func_808DED40.s") + Collider_InitCylinder(globalCtx, &this->colldierCylinder); + Collider_InitJntSph(globalCtx, &this->colliderJntSph); + Collider_SetJntSph(globalCtx, &this->colliderJntSph, &this->actor, &sJntSphInit, this->colliderJntSphElements); + CollisionCheck_SetInfo(&this->actor.colChkInfo, NULL, &sColChkInfoInit); -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/func_808DEFE8.s") + this->unk_1E8 = 0; + this->unk_1E4 = 0; -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/func_808DF088.s") + if (gSaveContext.sceneSetupIndex >= 4) { + func_808DEFE8(this); + } else { + func_808DEFE8(this); + } -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/func_808DF194.s") + this->actor.home.rot.z = this->actor.world.rot.z = this->actor.shape.rot.z = 0; +} -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/func_808DF560.s") +void EnHorseLinkChild_Destroy(Actor* thisx, GlobalContext* globalCtx) { + EnHorseLinkChild* this = THIS; -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/func_808DF620.s") + Skin_Free(&globalCtx->state, &this->skin); + Collider_DestroyCylinder(globalCtx, &this->colldierCylinder); + Collider_DestroyJntSph(globalCtx, &this->colliderJntSph); +} -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/func_808DF788.s") +void func_808DE9A8(EnHorseLinkChild* this) { + this->unk_144 = 0; + this->unk_148++; + if (this->unk_148 >= ARRAY_COUNT(D_808DFF18)) { + this->unk_148 = 0; + } + Animation_PlayOnce(&this->skin.skelAnime, D_808DFEC0[this->unk_148]); + this->skin.skelAnime.playSpeed = func_808DE728(this); +} -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/func_808DF838.s") +void func_808DEA0C(EnHorseLinkChild* this, GlobalContext* globalCtx) { + this->actor.speedXZ = 0.0f; + if (SkelAnime_Update(&this->skin.skelAnime)) { + func_808DE9A8(this); + } +} -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/EnHorseLinkChild_Update.s") +void func_808DEA54(EnHorseLinkChild* this, s32 arg1) { + this->unk_144 = 2; + this->actor.speedXZ = 0.0f; -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/func_808DFC3C.s") + if ((arg1 != 0) && (arg1 != 1)) { + arg1 = 0; + } -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/func_808DFDC8.s") + if (arg1 != this->unk_148) { + this->unk_148 = arg1; + Animation_Change(&this->skin.skelAnime, D_808DFEC0[this->unk_148], func_808DE728(this), 0.0f, + Animation_GetLastFrame(D_808DFEC0[this->unk_148]), ANIMMODE_ONCE, -5.0f); + } +} -#pragma GLOBAL_ASM("asm/non_matchings/overlays/ovl_En_Horse_Link_Child/EnHorseLinkChild_Draw.s") +void func_808DEB14(EnHorseLinkChild* this, GlobalContext* globalCtx) { + f32 sp44 = Actor_XZDistanceBetweenActors(&this->actor, &GET_PLAYER(globalCtx)->actor); + s32 phi_v0; + + if (SkelAnime_Update(&this->skin.skelAnime)) { + if ((sp44 < 1000.0f) && (sp44 > 70.0f)) { + func_808DECA0(this); + return; + } + + if (this->unk_148 == 1) { + phi_v0 = 0; + } else { + phi_v0 = 1; + } + + if (phi_v0 != this->unk_148) { + this->unk_148 = phi_v0; + Animation_Change(&this->skin.skelAnime, D_808DFEC0[this->unk_148], func_808DE728(this), 0.0f, + Animation_GetLastFrame(D_808DFEC0[this->unk_148]), ANIMMODE_ONCE, -5.0f); + } else { + Animation_Change(&this->skin.skelAnime, D_808DFEC0[this->unk_148], func_808DE728(this), 0.0f, + Animation_GetLastFrame(D_808DFEC0[this->unk_148]), ANIMMODE_ONCE, 0.0f); + } + } +} + +void func_808DECA0(EnHorseLinkChild* this) { + this->unk_144 = 1; + this->unk_148 = 0; + this->actor.speedXZ = 0.0f; + Animation_Change(&this->skin.skelAnime, D_808DFEC0[this->unk_148], func_808DE728(this), 0.0f, + Animation_GetLastFrame(D_808DFEC0[this->unk_148]), ANIMMODE_ONCE, -5.0f); +} + +void func_808DED40(EnHorseLinkChild* this, GlobalContext* globalCtx) { + f32 temp_fv0; + s16 temp_a0; + s32 phi_v0; + + if ((this->unk_148 == 4) || (this->unk_148 == 3) || (this->unk_148 == 2)) { + temp_a0 = Actor_YawBetweenActors(&this->actor, &GET_PLAYER(globalCtx)->actor) - this->actor.world.rot.y; + if (temp_a0 > 0x12C) { + this->actor.world.rot.y += 0x12C; + } else if (temp_a0 < -0x12C) { + this->actor.world.rot.y -= 0x12C; + } else { + this->actor.world.rot.y += temp_a0; + } + this->actor.shape.rot.y = this->actor.world.rot.y; + } + + if (SkelAnime_Update(&this->skin.skelAnime)) { + temp_fv0 = Actor_XZDistanceBetweenActors(&this->actor, &GET_PLAYER(globalCtx)->actor); + if (temp_fv0 > 1000.0f) { + func_808DEA54(this, 0); + return; + } + + if ((temp_fv0 < 1000.0f) && (temp_fv0 >= 300.0f)) { + phi_v0 = 4; + this->actor.speedXZ = 6.0f; + } else if ((temp_fv0 < 300.0f) && (temp_fv0 >= 150.0f)) { + phi_v0 = 3; + this->actor.speedXZ = 4.0f; + } else if ((temp_fv0 < 150.0f) && (temp_fv0 >= 70.0f)) { + phi_v0 = 2; + this->unk_1E8 = 0; + this->actor.speedXZ = 2.0f; + } else { + func_808DEA54(this, 1); + return; + } + + if (phi_v0 != this->unk_148) { + this->unk_148 = phi_v0; + Animation_Change(&this->skin.skelAnime, D_808DFEC0[this->unk_148], func_808DE728(this), 0.0f, + Animation_GetLastFrame(D_808DFEC0[this->unk_148]), ANIMMODE_ONCE, -5.0f); + } else { + Animation_Change(&this->skin.skelAnime, D_808DFEC0[this->unk_148], func_808DE728(this), 0.0f, + Animation_GetLastFrame(D_808DFEC0[this->unk_148]), ANIMMODE_ONCE, 0.0f); + } + } +} + +void func_808DEFE8(EnHorseLinkChild* this) { + this->unk_144 = 3; + this->unk_148 = 0; + this->actor.speedXZ = 0.0f; + Animation_Change(&this->skin.skelAnime, D_808DFEC0[this->unk_148], func_808DE728(this), 0.0f, + Animation_GetLastFrame(D_808DFEC0[this->unk_148]), ANIMMODE_ONCE, -5.0f); +} + +void func_808DF088(EnHorseLinkChild* this, GlobalContext* globalCtx) { + if ((this->unk_148 == 4) || (this->unk_148 == 3) || (this->unk_148 == 2)) { + Player* player = GET_PLAYER(globalCtx); + s16 sp32; + s32 phi_v0; + s32 pad; + + if (Math3D_Distance(&player->actor.world.pos, &this->actor.home.pos) < 250.0f) { + sp32 = player->actor.shape.rot.y; + if (Actor_YawBetweenActors(&this->actor, &player->actor) > 0) { + phi_v0 = 1; + } else { + phi_v0 = -1; + } + sp32 += (phi_v0 << 0xE); + } else { + sp32 = Math_Vec3f_Yaw(&this->actor.world.pos, &this->actor.home.pos) - this->actor.world.rot.y; + } + + if (sp32 > 0x12C) { + this->actor.world.rot.y += 0x12C; + } else if (sp32 < -0x12C) { + this->actor.world.rot.y += -0x12C; + } else { + this->actor.world.rot.y += sp32; + } + + this->actor.shape.rot.y = this->actor.world.rot.y; + } +} + +void func_808DF194(EnHorseLinkChild* this, GlobalContext* globalCtx) { + Player* player; + f32 sp50; + s32 sp4C; + s32 sp48; + + func_808DF088(this, globalCtx); + + player = GET_PLAYER(globalCtx); + sp50 = Actor_XZDistanceBetweenActors(&this->actor, &player->actor); + sp48 = this->unk_148; + sp4C = SkelAnime_Update(&this->skin.skelAnime); + + if ((sp4C != 0) || (this->unk_148 == 1) || (this->unk_148 == 0)) { + if ((gSaveContext.save.weekEventReg[1] & 0x20)) { + f32 sp44 = Math3D_Distance(&this->actor.world.pos, &this->actor.home.pos); + s32 pad; + + if (Math3D_Distance(&player->actor.world.pos, &this->actor.home.pos) > 250.0f) { + if (sp44 >= 300.0f) { + sp48 = 4; + this->actor.speedXZ = 6.0f; + } else if ((sp44 < 300.0f) && (sp44 >= 150.0f)) { + sp48 = 3; + this->actor.speedXZ = 4.0f; + } else if ((sp44 < 150.0f) && (sp44 >= 70.0f)) { + sp48 = 2; + this->unk_1E8 = 0; + this->actor.speedXZ = 2.0f; + } else { + this->actor.speedXZ = 0.0f; + if (this->unk_148 == 0) { + sp48 = (sp4C == 1) ? 1 : 0; + } else { + sp48 = (sp4C == 1) ? 0 : 1; + } + } + } else if (sp50 < 200.0f) { + sp48 = 4; + this->actor.speedXZ = 6.0f; + } else if (sp50 < 300.0f) { + sp48 = 3; + this->actor.speedXZ = 4.0f; + } else if (sp50 < 400.0f) { + sp48 = 2; + this->unk_1E8 = 0; + this->actor.speedXZ = 2.0f; + } else { + this->actor.speedXZ = 0.0f; + if (this->unk_148 == 0) { + sp48 = (sp4C == 1) ? 1 : 0; + } else { + sp48 = (sp4C == 1) ? 0 : 1; + } + } + } else { + this->actor.speedXZ = 0.0f; + if (this->unk_148 == 0) { + sp48 = (sp4C == 1) ? 1 : 0; + } else { + sp48 = (sp4C == 1) ? 0 : 1; + } + } + } + + if ((sp48 != this->unk_148) || (sp4C == 1)) { + this->unk_148 = sp48; + Animation_Change(&this->skin.skelAnime, D_808DFEC0[this->unk_148], func_808DE728(this), 0.0f, + Animation_GetLastFrame(D_808DFEC0[this->unk_148]), ANIMMODE_ONCE, -5.0f); + } else { + Animation_Change(&this->skin.skelAnime, D_808DFEC0[this->unk_148], func_808DE728(this), + this->skin.skelAnime.curFrame, Animation_GetLastFrame(D_808DFEC0[this->unk_148]), + ANIMMODE_ONCE, 0.0f); + } +} + +void func_808DF560(EnHorseLinkChild* this) { + this->unk_144 = 5; + + if (Rand_ZeroOne() > 0.5f) { + this->unk_148 = 0; + } else { + this->unk_148 = 1; + } + + D_801BDAA4 = 0; + Animation_Change(&this->skin.skelAnime, D_808DFEC0[this->unk_148], func_808DE728(this), 0.0f, + Animation_GetLastFrame(D_808DFEC0[this->unk_148]), ANIMMODE_ONCE, 0.0f); +} + +void func_808DF620(EnHorseLinkChild* this, GlobalContext* globalCtx) { + s16 sp36; + + if (D_801BDAA4 != 0) { + D_801BDAA4 = 0; + Audio_PlaySfxAtPos(&this->actor.projectedPos, NA_SE_EV_KID_HORSE_NEIGH); + func_808DF788(this); + return; + } + + this->actor.speedXZ = 0.0f; + sp36 = Actor_YawBetweenActors(&this->actor, &GET_PLAYER(globalCtx)->actor) - this->actor.world.rot.y; + + if ((Math_CosS(sp36) < 0.7071f) && (this->unk_148 == 2)) { + func_800F415C(&this->actor, &GET_PLAYER(globalCtx)->actor.world.pos, 0x12C); + } + + if (SkelAnime_Update(&this->skin.skelAnime)) { + if (Math_CosS(sp36) < 0.0f) { + this->unk_148 = 2; + Animation_Change(&this->skin.skelAnime, D_808DFEC0[this->unk_148], D_808DFF18[this->unk_148], 0.0f, + Animation_GetLastFrame(D_808DFEC8[0]), ANIMMODE_ONCE, -5.0f); + } else { + func_808DF560(this); + } + } +} + +void func_808DF788(EnHorseLinkChild* this) { + this->unk_1DC = 0; + this->unk_144 = 4; + this->unk_148 = 2; + this->unk_1E0 = 0; + this->actor.speedXZ = 2.0f; + Animation_Change(&this->skin.skelAnime, D_808DFEC0[this->unk_148], func_808DE728(this), 0.0f, + Animation_GetLastFrame(D_808DFEC0[this->unk_148]), ANIMMODE_ONCE, -5.0f); +} + +void func_808DF838(EnHorseLinkChild* this, GlobalContext* globalCtx) { + Player* player = GET_PLAYER(globalCtx); + f32 phi_fv0; + s32 phi_v0; + + this->unk_1DC++; + if (this->unk_1DC > 300) { + this->unk_1E0 = 1; + } + + if ((this->unk_148 == 4) || (this->unk_148 == 3) || (this->unk_148 == 2)) { + if (this->unk_1E0 == 0) { + func_800F415C(&this->actor, &player->actor.world.pos, 0x12C); + } else { + func_800F415C(&this->actor, &this->actor.home.pos, 0x12C); + } + } + + if (SkelAnime_Update(&this->skin.skelAnime)) { + if (this->unk_1E0 == 0) { + phi_fv0 = Actor_XZDistanceBetweenActors(&this->actor, &GET_PLAYER(globalCtx)->actor); + } else { + phi_fv0 = Math3D_Distance(&this->actor.world.pos, &this->actor.home.pos); + } + + if (this->unk_1E0 == 0) { + if (phi_fv0 >= 300.0f) { + phi_v0 = 4; + this->actor.speedXZ = 6.0f; + } else if (phi_fv0 >= 150.0f) { + phi_v0 = 3; + this->actor.speedXZ = 4.0f; + } else { + phi_v0 = 2; + this->unk_1E8 = 0; + this->actor.speedXZ = 2.0f; + } + } else if (phi_fv0 >= 300.0f) { + phi_v0 = 4; + this->actor.speedXZ = 6.0f; + } else if (phi_fv0 >= 150.0f) { + phi_v0 = 3; + this->actor.speedXZ = 4.0f; + } else if (phi_fv0 >= 70.0f) { + phi_v0 = 2; + this->unk_1E8 = 0; + this->actor.speedXZ = 2.0f; + } else { + func_808DF560(this); + return; + } + + if (phi_v0 != this->unk_148) { + this->unk_148 = phi_v0; + Animation_Change(&this->skin.skelAnime, D_808DFEC0[this->unk_148], func_808DE728(this), 0.0f, + Animation_GetLastFrame(D_808DFEC0[this->unk_148]), ANIMMODE_ONCE, -5.0f); + } else { + Animation_Change(&this->skin.skelAnime, D_808DFEC0[this->unk_148], func_808DE728(this), 0.0f, + Animation_GetLastFrame(D_808DFEC0[this->unk_148]), ANIMMODE_ONCE, 0.0f); + } + } +} + +void EnHorseLinkChild_Update(Actor* thisx, GlobalContext* globalCtx) { + s32 pad; + EnHorseLinkChild* this = THIS; + + D_808DFF30[this->unk_144](this, globalCtx); + Actor_MoveWithGravity(&this->actor); + Actor_UpdateBgCheckInfo(globalCtx, &this->actor, 20.0f, 55.0f, 100.0f, 0x1D); + + this->actor.focus.pos = this->actor.world.pos; + this->actor.focus.pos.y += 70.0f; + + if ((Rand_ZeroOne() < 0.025f) && (this->unk_1E4 == 0)) { + this->unk_1E4++; + } else if (this->unk_1E4 > 0) { + this->unk_1E4++; + if (this->unk_1E4 >= 4) { + this->unk_1E4 = 0; + } + } + + Collider_UpdateCylinder(&this->actor, &this->colldierCylinder); + CollisionCheck_SetOC(globalCtx, &globalCtx->colChkCtx, &this->colldierCylinder.base); + + func_808DE660(this); +} + +void EnHorseLinkChild_PostSkinDraw(Actor* thisx, GlobalContext* globalCtx, Skin* skin) { + Vec3f sp4C; + Vec3f sp40; + EnHorseLinkChild* this = THIS; + s32 i; + + for (i = 0; i < this->colliderJntSph.count; i++) { + sp4C.x = this->colliderJntSph.elements[i].dim.modelSphere.center.x; + sp4C.y = this->colliderJntSph.elements[i].dim.modelSphere.center.y; + sp4C.z = this->colliderJntSph.elements[i].dim.modelSphere.center.z; + + Skin_GetLimbPos(skin, this->colliderJntSph.elements[i].dim.limb, &sp4C, &sp40); + + this->colliderJntSph.elements[i].dim.worldSphere.center.x = sp40.x; + this->colliderJntSph.elements[i].dim.worldSphere.center.y = sp40.y; + this->colliderJntSph.elements[i].dim.worldSphere.center.z = sp40.z; + this->colliderJntSph.elements[i].dim.worldSphere.radius = + this->colliderJntSph.elements[i].dim.modelSphere.radius * this->colliderJntSph.elements[i].dim.scale; + } + + CollisionCheck_SetOC(globalCtx, &globalCtx->colChkCtx, &this->colliderJntSph.base); +} + +s32 EnHorseLinkChild_OverrideSkinDraw(Actor* thisx, GlobalContext* globalCtx, s32 limbIndex, Skin* skin) { + EnHorseLinkChild* this = THIS; + + OPEN_DISPS(globalCtx->state.gfxCtx); + + if (limbIndex == OBJECT_HORSE_LINK_CHILD_LIMB_0D) { + u8 index = D_808DFF54[this->unk_1E4]; + + gSPSegment(POLY_OPA_DISP++, 0x08, Lib_SegmentedToVirtual(D_808DFF48[index])); + } + + CLOSE_DISPS(globalCtx->state.gfxCtx); + + return true; +} + +void EnHorseLinkChild_Draw(Actor* thisx, GlobalContext* globalCtx) { + EnHorseLinkChild* this = THIS; + + func_8012C28C(globalCtx->state.gfxCtx); + func_80138258(&this->actor, globalCtx, &this->skin, EnHorseLinkChild_PostSkinDraw, + EnHorseLinkChild_OverrideSkinDraw, true); +} diff --git a/src/overlays/actors/ovl_En_Horse_Link_Child/z_en_horse_link_child.h b/src/overlays/actors/ovl_En_Horse_Link_Child/z_en_horse_link_child.h index ecc816c52b..0cdbdda9a8 100644 --- a/src/overlays/actors/ovl_En_Horse_Link_Child/z_en_horse_link_child.h +++ b/src/overlays/actors/ovl_En_Horse_Link_Child/z_en_horse_link_child.h @@ -6,9 +6,21 @@ struct EnHorseLinkChild; +typedef void (*EnHorseLinkChildUnkFunc)(struct EnHorseLinkChild*, GlobalContext*); + typedef struct EnHorseLinkChild { /* 0x000 */ Actor actor; - /* 0x144 */ char unk_144[0x158]; + /* 0x144 */ s32 unk_144; + /* 0x148 */ s32 unk_148; + /* 0x14C */ Skin skin; + /* 0x1DC */ s32 unk_1DC; + /* 0x1DC */ s32 unk_1E0; + /* 0x1E4 */ u8 unk_1E4; + /* 0x1E8 */ s32 unk_1E8; + /* 0x1EC */ ColliderCylinder colldierCylinder; + /* 0x238 */ ColliderJntSph colliderJntSph; + /* 0x258 */ ColliderJntSphElement colliderJntSphElements[1]; + /* 0x298 */ UNK_TYPE1 unk298[4]; } EnHorseLinkChild; // size = 0x29C extern const ActorInit En_Horse_Link_Child_InitVars; diff --git a/tools/disasm/functions.txt b/tools/disasm/functions.txt index 7e2be3b0ab..dbe8f14a64 100644 --- a/tools/disasm/functions.txt +++ b/tools/disasm/functions.txt @@ -6492,8 +6492,8 @@ 0x808DF788:("func_808DF788",), 0x808DF838:("func_808DF838",), 0x808DFB14:("EnHorseLinkChild_Update",), - 0x808DFC3C:("func_808DFC3C",), - 0x808DFDC8:("func_808DFDC8",), + 0x808DFC3C:("EnHorseLinkChild_PostSkinDraw",), + 0x808DFDC8:("EnHorseLinkChild_OverrideSkinDraw",), 0x808DFE3C:("EnHorseLinkChild_Draw",), 0x808E01A0:("DoorAna_SetupAction",), 0x808E01AC:("DoorAna_Init",), diff --git a/undefined_syms.txt b/undefined_syms.txt index 29dbf71be9..15bcad8c1b 100644 --- a/undefined_syms.txt +++ b/undefined_syms.txt @@ -1205,11 +1205,6 @@ D_0600B644 = 0x0600B644; D_0600F248 = 0x0600F248; D_06012A58 = 0x06012A58; -// ovl_En_Horse_Link_Child - -D_06002F98 = 0x06002F98; -D_0600A480 = 0x0600A480; - // ovl_En_Ik D_06000CE8 = 0x06000CE8;