Ovl_En_Fg OK (#133)

* En_Fg Frogs 9/18 decompiled

* En_Fg Frogs One Non-Matching

* documentation and cleanup

* final matched function

* code_script

* whitespace

* Fixed some mistakes, EnFg_UpdateDust no longer matches?

* fixed nonmatching

* Minor fixes and documentation

* PR suggestions

* Fixed genericHeader rename to common

* Fix Warnings

* PR Good Documentation Suggestions

* update names

* more pr suggestions

Co-authored-by: Jared Collette <jcollette@4000v-udp25-l.eng.unimelb.edu.au>
Co-authored-by: engineer124 <engineer124enginer124@gmail.com>
This commit is contained in:
engineer124 2021-05-23 01:36:21 +10:00 committed by GitHub
parent f4687fbbe7
commit cf3eb3b2e1
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
5 changed files with 503 additions and 31 deletions

View File

@ -4379,9 +4379,9 @@ SECTIONS
ovl_En_Fg : AT(RomLocation) ovl_En_Fg : AT(RomLocation)
{ {
build/src/overlays/actors/ovl_En_Fg/z_en_fg.o(.text) build/src/overlays/actors/ovl_En_Fg/z_en_fg.o(.text)
build/asm/overlays/ovl_En_Fg_data.o(.data) build/src/overlays/actors/ovl_En_Fg/z_en_fg.o(.data)
build/src/overlays/actors/ovl_En_Fg/z_en_fg.o(.rodata) build/src/overlays/actors/ovl_En_Fg/z_en_fg.o(.rodata)
build/asm/overlays/ovl_En_Fg_rodata.o(.rodata) build/src/overlays/actors/ovl_En_Fg/z_en_fg_overlay.o(.ovl)
} }
SegmentEnd = .; SegmentEnd = .;
SegmentSize = SegmentEnd - SegmentStart; SegmentSize = SegmentEnd - SegmentStart;

View File

@ -1,3 +1,4 @@
/* gameplay_keep */
D_040008D0 = 0x040008D0; D_040008D0 = 0x040008D0;
D_04029CB0 = 0x04029CB0; D_04029CB0 = 0x04029CB0;
D_04029CF0 = 0x04029CF0; D_04029CF0 = 0x04029CF0;
@ -25,6 +26,14 @@ D_04076BC0 = 0x04076BC0;
D_04075A40 = 0x04075A40; D_04075A40 = 0x04075A40;
D_04077480 = 0x04077480; D_04077480 = 0x04077480;
D_04075B30 = 0x04075B30; D_04075B30 = 0x04075B30;
D_0408DBE0 = 0x0408DBE0;
D_0408DFE0 = 0x0408DFE0;
D_0408E3E0 = 0x0408E3E0;
D_0408E7E0 = 0x0408E7E0;
D_0408EBE0 = 0x0408EBE0;
D_0408EFE0 = 0x0408EFE0;
D_0408F3E0 = 0x0408F3E0;
D_0408F7E0 = 0x0408F7E0;
/* gameplay_dangeon_keep */ /* gameplay_dangeon_keep */
D_05018090 = 0x05018090; D_05018090 = 0x05018090;
@ -246,6 +255,15 @@ D_06000958 = 0x06000958;
/* z_en_jc_mato */ /* z_en_jc_mato */
D_06000390 = 0x06000390; D_06000390 = 0x06000390;
/* z_en_fg */
D_06001534 = 0x06001534;
D_060011C0 = 0x060011C0;
D_060007BC = 0x060007BC;
D_060059A0 = 0x060059A0;
D_0600B328 = 0x0600B328;
D_0600B338 = 0x0600B338;
D_0600B538 = 0x0600B538;
/* z_bg_ladder */ /* z_bg_ladder */
D_060000A0 = 0x060000A0; D_060000A0 = 0x060000A0;
D_060001D8 = 0x060001D8; D_060001D8 = 0x060001D8;
@ -265,4 +283,4 @@ D_04089070 = 0x04089070;
/* z_obj_moon_stone */ /* z_obj_moon_stone */
D_06001C60 = 0x06001C60; D_06001C60 = 0x06001C60;
D_06000D78 = 0x06000D78; D_06000D78 = 0x06000D78;
D_06000C80 = 0x06000C80; D_06000C80 = 0x06000C80;

View File

@ -1,3 +1,9 @@
/*
* File: z_en_fg.c
* Overlay: En_Fg
* Description: Likely beta frogs, a version where they were all enemies
*/
#include "z_en_fg.h" #include "z_en_fg.h"
#define FLAGS 0x00004209 #define FLAGS 0x00004209
@ -9,7 +15,29 @@ void EnFg_Destroy(Actor* thisx, GlobalContext* globalCtx);
void EnFg_Update(Actor* thisx, GlobalContext* globalCtx); void EnFg_Update(Actor* thisx, GlobalContext* globalCtx);
void EnFg_Draw(Actor* thisx, GlobalContext* globalCtx); void EnFg_Draw(Actor* thisx, GlobalContext* globalCtx);
/* void EnFg_Jump(EnFg* this, GlobalContext* globalCtx);
void EnFg_DoNothing(EnFg* this, GlobalContext* globalCtx);
void EnFg_Knockback(EnFg* this, GlobalContext* globalCtx);
void EnFg_AddDust(EnFgEffectDust* dustEffect, Vec3f* worldPos);
void EnFg_UpdateDust(EnFgEffectDust* dustEffect);
void EnFg_DrawDust(GlobalContext* globalCtx, EnFgEffectDust* dustEffect);
extern u64 D_0408DBE0[]; // gDust1Tex
extern u64 D_0408DFE0[]; // gDust2Tex
extern u64 D_0408E3E0[]; // gDust3Tex
extern u64 D_0408E7E0[]; // gDust4Tex
extern u64 D_0408EBE0[]; // gDust5Tex
extern u64 D_0408EFE0[]; // gDust6Tex
extern u64 D_0408F3E0[]; // gDust7Tex
extern u64 D_0408F7E0[]; // gDust8Tex
extern AnimationHeader D_06001534;
extern AnimationHeader D_060011C0;
extern AnimationHeader D_060007BC;
extern Gfx* D_060059A0[];
extern Gfx* D_0600B328[];
extern Gfx* D_0600B338[];
extern FlexSkeletonHeader D_0600B538;
const ActorInit En_Fg_InitVars = { const ActorInit En_Fg_InitVars = {
ACTOR_EN_FG, ACTOR_EN_FG,
ACTORCAT_NPC, ACTORCAT_NPC,
@ -21,40 +49,418 @@ const ActorInit En_Fg_InitVars = {
(ActorFunc)EnFg_Update, (ActorFunc)EnFg_Update,
(ActorFunc)EnFg_Draw, (ActorFunc)EnFg_Draw,
}; };
*/
#pragma GLOBAL_ASM("./asm/non_matchings/overlays/ovl_En_Fg_0x80A2D280/func_80A2D280.asm") static ColliderCylinderInit sCylinderInit = {
{
COLTYPE_HIT0,
AT_NONE,
AC_ON | AC_TYPE_PLAYER,
OC1_ON | OC1_TYPE_ALL,
OC2_TYPE_1,
COLSHAPE_CYLINDER,
},
{
ELEMTYPE_UNK1,
{ 0x00000000, 0x00, 0x00 },
{ 0x000010AA, 0x00, 0x00 },
TOUCH_NONE | TOUCH_SFX_NORMAL,
BUMP_ON | BUMP_HOOKABLE,
OCELEM_ON,
},
{ 8, 10, 0, { 0, 0, 0 } },
};
#pragma GLOBAL_ASM("./asm/non_matchings/overlays/ovl_En_Fg_0x80A2D280/func_80A2D348.asm") static CollisionCheckInfoInit2 sColChkInfoInit2 = {
1, 0, 0, 0, MASS_IMMOVABLE,
};
#pragma GLOBAL_ASM("./asm/non_matchings/overlays/ovl_En_Fg_0x80A2D280/func_80A2D3D4.asm") static DamageTable sDamageTable = {
0x00, 0x11, 0x00, 0x01, 0x00, 0xE1, 0x11, 0xF0, 0x00, 0x00, 0x00, 0x00, 0x31, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
};
#pragma GLOBAL_ASM("./asm/non_matchings/overlays/ovl_En_Fg_0x80A2D280/func_80A2D400.asm") static EnFgAnimation sAnimations[] = {
{ &D_06001534, 1.0f, 0, -1, 0, 0 },
{ &D_06001534, 1.0f, 0, -1, 0, -4 },
{ &D_060011C0, 1.0f, 0, -1, 0, -4 },
{ &D_060007BC, 1.0f, 0, -1, 2, -4 },
};
#pragma GLOBAL_ASM("./asm/non_matchings/overlays/ovl_En_Fg_0x80A2D280/func_80A2D42C.asm") s32 EnFg_UpdateAnimation(SkelAnime* skelAnime, s16 animIndex) {
s16 frameCount;
s32 ret;
#pragma GLOBAL_ASM("./asm/non_matchings/overlays/ovl_En_Fg_0x80A2D280/func_80A2D4B8.asm") ret = false;
if (animIndex >= 0 && animIndex < 4) {
ret = true;
frameCount = sAnimations[animIndex].frameCount;
if (frameCount < 0) {
frameCount = SkelAnime_GetFrameCount(&sAnimations[animIndex].animationSeg->common);
}
SkelAnime_ChangeAnim(skelAnime, sAnimations[animIndex].animationSeg, sAnimations[animIndex].playbackSpeed,
sAnimations[animIndex].frame, frameCount, sAnimations[animIndex].mode,
sAnimations[animIndex].transitionRate);
}
return ret;
}
#pragma GLOBAL_ASM("./asm/non_matchings/overlays/ovl_En_Fg_0x80A2D280/func_80A2D778.asm") void func_80A2D348(EnFg* this, GlobalContext* globalCtx) {
if (this->actor.colChkInfo.health != 0) {
this->collider.dim.pos.x = this->actor.world.pos.x;
this->collider.dim.pos.y = this->actor.world.pos.y;
this->collider.dim.pos.z = this->actor.world.pos.z;
CollisionCheck_SetAC(globalCtx, &globalCtx->colCheckCtx, &this->collider.base);
CollisionCheck_SetOC(globalCtx, &globalCtx->colCheckCtx, &this->collider.base);
}
}
#pragma GLOBAL_ASM("./asm/non_matchings/overlays/ovl_En_Fg_0x80A2D280/func_80A2D9CC.asm") void func_80A2D3D4(EnFg* this, GlobalContext* globalCtx) {
SkelAnime_FrameUpdateMatrix(&this->skelAnime);
}
#pragma GLOBAL_ASM("./asm/non_matchings/overlays/ovl_En_Fg_0x80A2D280/func_80A2D9DC.asm") u8 EnFg_UpdateHealth(EnFg* this) {
if (this->actor.colChkInfo.damage >= this->actor.colChkInfo.health) {
this->actor.colChkInfo.health = 0;
} else {
this->actor.colChkInfo.health -= this->actor.colChkInfo.damage;
}
return this->actor.colChkInfo.health;
}
#pragma GLOBAL_ASM("./asm/non_matchings/overlays/ovl_En_Fg_0x80A2D280/EnFg_Init.asm") s32 EnFg_GetDamageEffect(EnFg* this) {
s32 ret = 0;
#pragma GLOBAL_ASM("./asm/non_matchings/overlays/ovl_En_Fg_0x80A2D280/EnFg_Destroy.asm") if (this->collider.base.acFlags & 2) {
switch (this->actor.colChkInfo.damageEffect) {
case 1:
ret = FG_DMGEFFECT_DEKUSTICK;
break;
case 15:
ret = FG_DMGEFFECT_HOOKSHOT;
break;
case 14:
ret = FG_DMGEFFECT_ARROW;
break;
case 3:
ret = FG_DMGEFFECT_ICEARROW;
break;
default:
ret = FG_DMGEFFECT_EXPLOSION;
break;
}
this->collider.base.acFlags &= ~2;
EnFg_UpdateHealth(this);
}
return ret;
}
#pragma GLOBAL_ASM("./asm/non_matchings/overlays/ovl_En_Fg_0x80A2D280/EnFg_Update.asm") void EnFg_Idle(EnFg* this, GlobalContext* globalCtx) {
Actor* ac;
s16 rotY;
s16 rotX;
#pragma GLOBAL_ASM("./asm/non_matchings/overlays/ovl_En_Fg_0x80A2D280/func_80A2DCE0.asm") switch (EnFg_GetDamageEffect(this)) {
case FG_DMGEFFECT_DEKUSTICK:
this->actor.flags &= ~1;
Audio_PlayActorSound2(this, 0x28E4);
this->skelAnime.animPlaybackSpeed = 0.0f;
this->actor.shape.shadowDraw = NULL;
this->actor.scale.x *= 1.5f;
this->actor.scale.z *= 1.5f;
this->actor.scale.y = 0.001f;
this->actor.world.pos.y = this->actor.floorHeight + 2.0f;
this->actionFunc = EnFg_DoNothing;
break;
case FG_DMGEFFECT_HOOKSHOT:
break;
case FG_DMGEFFECT_ARROW:
this->actor.flags &= ~1;
this->skelAnime.animPlaybackSpeed = 0.0f;
rotY = this->collider.base.ac->world.rot.y;
rotX = this->collider.base.ac->world.rot.x;
this->actor.scale.x = fabsf(0.01f * Math_CosS(rotY));
this->actor.scale.y = fabsf(0.01f * Math_CosS(rotX));
this->actor.scale.z = fabsf(0.01f * Math_SinS(rotY));
this->actor.scale.x = CLAMP_MIN(this->actor.scale.x, 0.001f);
this->actor.scale.y = CLAMP_MIN(this->actor.scale.y, 0.001f);
this->actor.scale.z = CLAMP_MIN(this->actor.scale.z, 0.001f);
this->actionFunc = EnFg_DoNothing;
break;
case FG_DMGEFFECT_EXPLOSION:
this->actor.flags &= ~1;
Audio_PlayActorSound2(this, 0x28E3);
if(1) {}
this->actor.params = FG_BLACK;
this->skelAnime.animPlaybackSpeed = 0.0f;
ac = this->collider.base.ac;
this->actor.world.rot.y = Math_Vec3f_Yaw(&ac->world.pos, &this->actor.world.pos);
this->actor.shape.rot = this->actor.world.rot;
this->actor.velocity.y = 10.0f;
this->actor.speedXZ = 3.0f;
this->actor.gravity = -0.8f;
this->bounceCounter = 1;
this->timer = 0;
this->actionFunc = EnFg_Knockback;
break;
default:
if (DECR(this->timer) == 0) {
Audio_PlayActorSound2(this, 0x28B1);
EnFg_UpdateAnimation(&this->skelAnime, 3);
this->actor.velocity.y = 10.0f;
this->timer = Rand_S16Offset(30, 30);
this->actionFunc = EnFg_Jump;
}
}
Actor_SetVelocityAndMoveYRotationAndGravity(&this->actor);
}
#pragma GLOBAL_ASM("./asm/non_matchings/overlays/ovl_En_Fg_0x80A2D280/func_80A2DD34.asm") void EnFg_Jump(EnFg* this, GlobalContext* globalCtx) {
Actor* ac;
s32 pad;
s16 rotY;
s16 rotX;
#pragma GLOBAL_ASM("./asm/non_matchings/overlays/ovl_En_Fg_0x80A2D280/EnFg_Draw.asm") switch (EnFg_GetDamageEffect(this)) {
case FG_DMGEFFECT_ARROW:
this->actor.flags &= ~1;
this->skelAnime.animPlaybackSpeed = 0.0f;
ac = this->collider.base.ac;
rotY = ac->world.rot.y;
rotX = ac->world.rot.x;
this->actor.scale.x = fabsf(Math_CosS(rotY) * 0.01f);
this->actor.scale.y = fabsf(Math_CosS(rotX) * 0.01f);
this->actor.scale.z = fabsf(Math_SinS(rotY) * 0.01f);
this->actor.scale.x = CLAMP_MIN(this->actor.scale.x, 0.001f);
this->actor.scale.y = CLAMP_MIN(this->actor.scale.y, 0.001f);
this->actor.scale.z = CLAMP_MIN(this->actor.scale.z, 0.001f);
this->actionFunc = EnFg_DoNothing;
break;
case FG_DMGEFFECT_HOOKSHOT:
break;
case FG_DMGEFFECT_EXPLOSION:
this->actor.flags &= ~1;
Audio_PlayActorSound2(this, 0x28E3);
EnFg_UpdateAnimation(&this->skelAnime, 0);
this->actor.params = FG_BLACK;
this->skelAnime.animPlaybackSpeed = 0.0f;
ac = this->collider.base.ac;
this->actor.world.rot.y = Math_Vec3f_Yaw(&ac->world.pos, &this->actor.world.pos);
this->actor.shape.rot = this->actor.world.rot;
this->actor.velocity.y = 10.0f;
this->actor.speedXZ = 3.0f;
this->actor.gravity = -0.8f;
this->bounceCounter = 1;
this->timer = 0;
this->actionFunc = EnFg_Knockback;
break;
default:
if (func_801378B8(&this->skelAnime, 8.0f)) {
this->skelAnime.animCurrentFrame = 8.0f;
this->skelAnime.animPlaybackSpeed = 0.0f;
}
#pragma GLOBAL_ASM("./asm/non_matchings/overlays/ovl_En_Fg_0x80A2D280/func_80A2DFC4.asm") if ((this->actor.velocity.y <= 0.0f) && (this->actor.bgCheckFlags & 1)) {
EnFg_UpdateAnimation(&this->skelAnime, 0);
this->actionFunc = EnFg_Idle;
this->actor.velocity.y = 0.0f;
} else {
Actor_SetVelocityAndMoveYRotationAndGravity(&this->actor);
}
}
}
#pragma GLOBAL_ASM("./asm/non_matchings/overlays/ovl_En_Fg_0x80A2D280/func_80A2E0A0.asm") void EnFg_DoNothing(EnFg* this, GlobalContext* globalCtx) {
}
#pragma GLOBAL_ASM("./asm/non_matchings/overlays/ovl_En_Fg_0x80A2D280/func_80A2E268.asm") void EnFg_Knockback(EnFg* this, GlobalContext* globalCtx) {
if ((this->actor.velocity.y <= 0.0f) && (this->actor.bgCheckFlags & 1)) {
this->bounceCounter++;
if (this->bounceCounter < 4) {
this->actor.shape.rot.x += 0x1000;
this->actor.velocity.y = 10.0f / this->bounceCounter;
} else {
this->actionFunc = EnFg_DoNothing;
}
} else {
if (this->actor.bgCheckFlags & 8) {
this->actor.world.rot.y = this->actor.wallYaw;
this->actor.shape.rot = this->actor.world.rot;
}
if (DECR(this->timer) == 0) {
EnFg_AddDust(&this->dustEffect[0], &this->actor.world.pos);
}
this->actor.shape.rot.x += 0x1000;
Actor_SetVelocityAndMoveYRotationAndGravity(&this->actor);
}
}
void EnFg_Init(Actor* thisx, GlobalContext* globalCtx) {
EnFg* this = THIS;
ActorShape_Init(&this->actor.shape, 0.0f, func_800B3FC0, 10.0f);
SkelAnime_InitSV(globalCtx, &this->skelAnime, &D_0600B538, NULL, this->limbDrawTbl, this->transitionDrawTbl, 24);
EnFg_UpdateAnimation(&this->skelAnime, 0);
Collider_InitCylinder(globalCtx, &this->collider);
Collider_SetCylinder(globalCtx, &this->collider, &this->actor, &sCylinderInit);
CollisionCheck_SetInfo2(&this->actor.colChkInfo, &sDamageTable, &sColChkInfoInit2);
this->actor.flags |= 0x4000;
Actor_SetScale(&this->actor, 0.01f);
this->actor.gravity = -1.6f;
this->actionFunc = EnFg_Idle;
}
void EnFg_Destroy(Actor* thisx, GlobalContext* globalCtx) {
EnFg* this = THIS;
Collider_DestroyCylinder(globalCtx, &this->collider);
}
void EnFg_Update(Actor* thisx, GlobalContext* globalCtx) {
EnFg* this = THIS;
s32 flag;
s32 flagSet;
flag = this->actor.flags;
flagSet = ((flag & 0x2000) == 0x2000);
if (1) {}
if (!flagSet) {
flagSet = ((flag & 0x8000) == 0x8000);
if (1) {}
if (!flagSet) {
this->actionFunc(this, globalCtx);
func_800B78B8(globalCtx, &this->actor, BASE_REG(16, 0), BASE_REG(16, 1), 0.0f, 5);
}
}
func_80A2D3D4(this, globalCtx);
EnFg_UpdateDust(&this->dustEffect[0]);
func_80A2D348(this, globalCtx);
}
s32 EnFg_OverrideLimbDraw(GlobalContext* globalCtx, s32 limbIndex, Gfx** dList, Vec3f* pos, Vec3s* rot, Actor* thisx) {
EnFg* this = THIS;
if ((limbIndex == 7) || (limbIndex == 8)) {
*dList = NULL;
}
if (this->actor.colChkInfo.health == 0) {
if ((limbIndex == 5) || (limbIndex == 9)) {
*dList = NULL;
}
}
return 0;
}
void EnFg_PostLimbDraw(GlobalContext* globalCtx, s32 limbIndex, Gfx** dList, Vec3s* rot, Actor* thisx) {
EnFg* this = THIS;
s16 pad;
Vec3f vec1 = { 0.0f, 0.0f, 0.0f };
if ((limbIndex == 7) || (limbIndex == 8)) {
OPEN_DISPS(globalCtx->state.gfxCtx);
Matrix_Push();
SysMatrix_NormalizeXYZ(&globalCtx->unk187FC);
gSPMatrix(POLY_OPA_DISP++, Matrix_NewMtx(globalCtx->state.gfxCtx), G_MTX_NOPUSH | G_MTX_LOAD | G_MTX_MODELVIEW);
gSPDisplayList(POLY_OPA_DISP++, *dList);
Matrix_Pop();
CLOSE_DISPS(globalCtx->state.gfxCtx);
}
if (limbIndex == 4) {
SysMatrix_MultiplyVector3fByState(&vec1, &this->actor.focus.pos);
}
}
void EnFg_Draw(Actor* thisx, GlobalContext* globalCtx) {
EnFg* this = THIS;
s32 pad;
Color_RGBA8 envColor[] = {
{ 200, 170, 0, 255 }, { 0, 170, 200, 255 }, { 210, 120, 100, 255 },
{ 120, 130, 230, 255 }, { 190, 190, 190, 255 }, { 0, 0, 0, 255 },
};
Matrix_Push();
EnFg_DrawDust(globalCtx, &this->dustEffect[0]);
Matrix_Pop();
OPEN_DISPS(globalCtx->state.gfxCtx);
func_8012C28C(globalCtx->state.gfxCtx);
gDPPipeSync(POLY_OPA_DISP++);
gDPSetEnvColor(POLY_OPA_DISP++, envColor[this->actor.params].r, envColor[this->actor.params].g, envColor[this->actor.params].b, envColor[this->actor.params].a);
gSPSegment(POLY_OPA_DISP++, 0x08, Lib_SegmentedToVirtual(&D_060059A0));
gSPSegment(POLY_OPA_DISP++, 0x09, Lib_SegmentedToVirtual(&D_060059A0));
SkelAnime_DrawSV(globalCtx, this->skelAnime.skeleton, this->skelAnime.limbDrawTbl, this->skelAnime.dListCount,
EnFg_OverrideLimbDraw, EnFg_PostLimbDraw, &this->actor);
CLOSE_DISPS(globalCtx->state.gfxCtx);
}
void EnFg_AddDust(EnFgEffectDust* dustEffect, Vec3f* worldPos) {
Vec3f vel = { 0.0f, 3.0f, 0.0f };
Vec3f unk_20 = { 0.0f, 0.0f, 0.0f };
s32 i;
for (i = 0; i < 10; i++, dustEffect++) {
if (!dustEffect->type) {
dustEffect->type = true;
dustEffect->timer = 16;
dustEffect->pos = *worldPos;
dustEffect->velocity = vel;
dustEffect->unk_20 = unk_20;
dustEffect->xyScale = 0.4f;
break;
}
}
}
void EnFg_UpdateDust(EnFgEffectDust* dustEffect) {
s32 i;
for (i = 0; i < 10; i++, dustEffect++) {
if (dustEffect->type == true) {
if (DECR(dustEffect->timer) == 0) {
dustEffect->type = false;
}
dustEffect->pos.y += dustEffect->velocity.y;
}
}
}
u64* sDustTex[] = {
D_0408F7E0, D_0408F3E0, D_0408EFE0, D_0408EBE0, D_0408E7E0, D_0408E3E0, D_0408DFE0, D_0408DBE0,
};
void EnFg_DrawDust(GlobalContext* globalCtx, EnFgEffectDust* dustEffect) {
s16 i;
s16 alpha;
s16 index;
s16 firstDone = false;
OPEN_DISPS(globalCtx->state.gfxCtx);
func_8012C2DC(globalCtx->state.gfxCtx);
for (i = 0; i < 10; i++, dustEffect++) {
if (dustEffect->type) {
if (!firstDone) {
POLY_XLU_DISP = Gfx_CallSetupDL(POLY_XLU_DISP, 0);
gSPDisplayList(POLY_XLU_DISP++, D_0600B328);
gDPSetEnvColor(POLY_XLU_DISP++, 0, 0, 0, 0);
firstDone = true;
}
if (1) {}
alpha = (255.0f / 16.0f) * dustEffect->timer;
gDPSetPrimColor(POLY_XLU_DISP++, 0, 0, 0, 0, 0, alpha);
gDPPipeSync(POLY_XLU_DISP++);
SysMatrix_InsertTranslation(dustEffect->pos.x, dustEffect->pos.y, dustEffect->pos.z, MTXMODE_NEW);
SysMatrix_NormalizeXYZ(&globalCtx->unk187FC);
Matrix_Scale(dustEffect->xyScale, dustEffect->xyScale, 1.0f, MTXMODE_APPLY);
gSPMatrix(POLY_XLU_DISP++, Matrix_NewMtx(globalCtx->state.gfxCtx), G_MTX_NOPUSH | G_MTX_LOAD | G_MTX_MODELVIEW);
index = 0.5f * dustEffect->timer;
gSPSegment(POLY_XLU_DISP++, 0x08, Lib_SegmentedToVirtual(sDustTex[index]));
gSPDisplayList(POLY_XLU_DISP++, D_0600B338);
}
}
CLOSE_DISPS(globalCtx->state.gfxCtx);
}

View File

@ -5,11 +5,59 @@
struct EnFg; struct EnFg;
typedef void (*EnFgActionFunc)(struct EnFg*, GlobalContext*);
// Based on the envColor data. Related to params but mostly unused.
typedef enum {
/* 0x00 */ FG_YELLOW,
/* 0x01 */ FG_CYAN,
/* 0x02 */ FG_PINK,
/* 0x03 */ FG_BLUE,
/* 0x04 */ FG_WHITE,
/* 0x05 */ FG_BLACK, // All frogs are blackened when hit by an explosion
} FrogType;
typedef enum {
/* 0x00 */ FG_DMGEFFECT_NONE,
/* 0x01 */ FG_DMGEFFECT_EXPLOSION, // Bomb or bombchu, not powderkeg
/* 0x02 */ FG_DMGEFFECT_DEKUSTICK,
/* 0x03 */ FG_DMGEFFECT_HOOKSHOT,
/* 0x04 */ FG_DMGEFFECT_ARROW,
/* 0x05 */ FG_DMGEFFECT_ICEARROW,
} FrogDamageEffect;
// TODO: This is a common struct and may be moved to a more global header
// Typically the frame/transition data is f32, not s16.
typedef struct {
/* 0x00 */ AnimationHeader* animationSeg;
/* 0x04 */ f32 playbackSpeed;
/* 0x08 */ s16 frame;
/* 0x0A */ s16 frameCount;
/* 0x0C */ u8 mode;
/* 0x0E */ s16 transitionRate;
} EnFgAnimation; // size = 0x10
typedef struct {
/* 0x0000 */ u8 type;
/* 0x0001 */ u8 timer;
/* 0x0004 */ f32 xyScale;
/* 0x0008 */ UNK_TYPE1 unk_08[0xC];
/* 0x0014 */ Vec3f pos;
/* 0x0020 */ Vec3f unk_20; // Likely acceleration, set to 0 but unused
/* 0x002C */ Vec3f velocity;
/* 0x0038 */ UNK_TYPE1 unk_38[0x4];
} EnFgEffectDust; // size = 0x3C
typedef struct EnFg { typedef struct EnFg {
/* 0x000 */ Actor actor; /* 0x000 */ Actor actor;
/* 0x144 */ char unk_144[0x410]; /* 0x144 */ EnFgActionFunc actionFunc;
/* 0x148 */ SkelAnime skelAnime;
/* 0x18C */ ColliderCylinder collider;
/* 0x1D8 */ Vec3s limbDrawTbl[24];
/* 0x268 */ Vec3s transitionDrawTbl[24];
/* 0x2F8 */ s16 timer;
/* 0x2FA */ s16 bounceCounter;
/* 0x2FC */ EnFgEffectDust dustEffect[10];
} EnFg; // size = 0x554 } EnFg; // size = 0x554
extern const ActorInit En_Fg_InitVars;
#endif // Z_EN_FG_H #endif // Z_EN_FG_H

View File

@ -10115,12 +10115,12 @@
0x80A2DAF4:("EnFg_Init",), 0x80A2DAF4:("EnFg_Init",),
0x80A2DBE8:("EnFg_Destroy",), 0x80A2DBE8:("EnFg_Destroy",),
0x80A2DC14:("EnFg_Update",), 0x80A2DC14:("EnFg_Update",),
0x80A2DCE0:("func_80A2DCE0",), 0x80A2DCE0:("EnFg_OverrideLimbDraw",),
0x80A2DD34:("func_80A2DD34",), 0x80A2DD34:("EnFg_PostLimbDraw",),
0x80A2DE34:("EnFg_Draw",), 0x80A2DE34:("EnFg_Draw",),
0x80A2DFC4:("func_80A2DFC4",), 0x80A2DFC4:("EnFg_AddDust",),
0x80A2E0A0:("func_80A2E0A0",), 0x80A2E0A0:("EnFg_UpdateDust",),
0x80A2E268:("func_80A2E268",), 0x80A2E268:("EnFg_DrawDust",),
0x80A2E7A0:("DmRavine_Init",), 0x80A2E7A0:("DmRavine_Init",),
0x80A2E828:("DmRavine_Destroy",), 0x80A2E828:("DmRavine_Destroy",),
0x80A2E838:("DmRavine_DoNothing",), 0x80A2E838:("DmRavine_DoNothing",),