1
0
Fork 0
mirror of https://github.com/zeldaret/oot.git synced 2025-07-15 12:24:39 +00:00

En_Ex_Item (#567)

* first go

* match

* vt

* docs

* one last thing

* formatted

* bowling, why not

* header

* Update src/overlays/actors/ovl_En_Ex_Item/z_en_ex_item.h

Co-authored-by: Roman971 <32455037+Roman971@users.noreply.github.com>

* Update src/overlays/actors/ovl_En_Ex_Item/z_en_ex_item.c

Co-authored-by: Roman971 <32455037+Roman971@users.noreply.github.com>

* press FFFF

Co-authored-by: petrie911 <pmontag@DESKTOP-LG8A167.localdomain>
Co-authored-by: Roman971 <32455037+Roman971@users.noreply.github.com>
This commit is contained in:
petrie911 2020-12-31 18:56:02 -06:00 committed by GitHub
parent 600bad1f20
commit 7daadc5ea1
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
30 changed files with 554 additions and 1329 deletions

View file

@ -782,7 +782,7 @@ void func_8001F080(EnItem00* this, GlobalContext* globalCtx) {
gSPMatrix(POLY_OPA_DISP++, Matrix_NewMtx(globalCtx->state.gfxCtx, "../z_en_item00.c", 1607),
G_MTX_MODELVIEW | G_MTX_LOAD);
gSPDisplayList(POLY_OPA_DISP++, &D_0403F070);
gSPDisplayList(POLY_OPA_DISP++, D_0403F070);
CLOSE_DISPS(globalCtx->state.gfxCtx, "../z_en_item00.c", 1611);
}

View file

@ -1,6 +1,7 @@
#include "z_en_bom_bowl_man.h"
#include "vt.h"
#include "overlays/actors/ovl_En_Syateki_Niw/z_en_syateki_niw.h"
#include "overlays/actors/ovl_En_Ex_Item/z_en_ex_item.h"
#define FLAGS 0x08000039
@ -249,8 +250,8 @@ void EnBomBowMan_RunGame(EnBomBowlMan* this, GlobalContext* globalCtx) {
this->actor.textId = 0x1A;
this->dialogState = 4;
this->minigamePlayStatus = 0;
if ((this->exItem != NULL) && (this->exItem->actor.update != 0)) {
this->exItem->unk_160 = 1;
if ((this->exItem != NULL) && (this->exItem->actor.update != NULL)) {
this->exItem->killItem = true;
this->exItem = NULL;
}
globalCtx->bombchuBowlingStatus = 0;
@ -379,35 +380,36 @@ void EnBomBowMan_ChooseShowPrize(EnBomBowlMan* this, GlobalContext* globalCtx) {
if (this->prizeRevealTimer == 0) {
switch (this->prizeSelect) {
case 0:
prizeTemp = 0;
prizeTemp = EXITEM_BOMB_BAG_BOWLING;
if (gSaveContext.itemGetInf[1] & 2) {
prizeTemp = 4;
prizeTemp = EXITEM_PURPLE_RUPEE_BOWLING;
}
break;
case 1:
prizeTemp = 4;
prizeTemp = EXITEM_PURPLE_RUPEE_BOWLING;
break;
case 2:
prizeTemp = 2;
prizeTemp = EXITEM_BOMBCHUS_BOWLING;
break;
case 3:
prizeTemp = 1;
prizeTemp = EXITEM_HEART_PIECE_BOWLING;
if (gSaveContext.itemGetInf[1] & 4) {
prizeTemp = 4;
prizeTemp = EXITEM_PURPLE_RUPEE_BOWLING;
}
break;
case 4:
prizeTemp = 3;
prizeTemp = EXITEM_BOMBS_BOWLING;
break;
}
this->prizeIndex = prizeTemp;
if (BREG(7)) {
this->prizeIndex = BREG(7) - 1;
}
this->exItem = (EnExItem*)Actor_SpawnAsChild(
&globalCtx->actorCtx, &this->actor, globalCtx, ACTOR_EN_EX_ITEM,
sPrizePosOffset[this->prizeIndex].x + 148.0f, sPrizePosOffset[this->prizeIndex].y + 40.0f,
sPrizePosOffset[this->prizeIndex].z + 300.0f, 0, sPrizeRot[this->prizeIndex], 0, this->prizeIndex + 5);
this->exItem = (EnExItem*)Actor_SpawnAsChild(&globalCtx->actorCtx, &this->actor, globalCtx, ACTOR_EN_EX_ITEM,
sPrizePosOffset[this->prizeIndex].x + 148.0f,
sPrizePosOffset[this->prizeIndex].y + 40.0f,
sPrizePosOffset[this->prizeIndex].z + 300.0f, 0,
sPrizeRot[this->prizeIndex], 0, this->prizeIndex + EXITEM_COUNTER);
if (!this->startedPlaying) {
this->bowlPit = (EnBomBowlPit*)Actor_SpawnAsChild(&globalCtx->actorCtx, &this->actor, globalCtx,
ACTOR_EN_BOM_BOWL_PIT, 0.0f, 90.0f, -860.0f, 0, 0, 0, 0);

View file

@ -1,6 +1,7 @@
#include "z_en_bom_bowl_pit.h"
#include "vt.h"
#include "overlays/actors/ovl_En_Bom_Chu/z_en_bom_chu.h"
#include "overlays/actors/ovl_En_Ex_Item/z_en_ex_item.h"
#define FLAGS 0x00000010
@ -155,12 +156,12 @@ void EnBomBowlPit_SpawnPrize(EnBomBowlPit* this, GlobalContext* globalCtx) {
}
void EnBomBowlPit_SetupGivePrize(EnBomBowlPit* this, GlobalContext* globalCtx) {
if (this->unk_156 != 0) {
if (this->exItemDone != 0) {
switch (this->prizeIndex) {
case 0:
case EXITEM_BOMB_BAG_BOWLING:
gSaveContext.itemGetInf[1] |= 2;
break;
case 1:
case EXITEM_HEART_PIECE_BOWLING:
gSaveContext.itemGetInf[1] |= 4;
break;
}
@ -206,7 +207,7 @@ void EnBomBowlPit_Reset(EnBomBowlPit* this, GlobalContext* globalCtx) {
// Ah recovery! (?)
osSyncPrintf(VT_FGCOL(GREEN) "☆☆☆☆☆ あぁ回復! ☆☆☆☆☆ \n" VT_RST);
}
this->unk_156 = 0;
this->exItemDone = 0;
this->status = 2;
this->actionFunc = EnBomBowlPit_SetupDetectHit;
}

View file

@ -15,7 +15,7 @@ typedef struct EnBomBowlPit {
/* 0x0150 */ u16 unk_150;
/* 0x0152 */ s16 camId;
/* 0x0154 */ s16 unk_154;
/* 0x0156 */ s16 unk_156; // Set by EnExItem?
/* 0x0156 */ s16 exItemDone; // Set by EnExItem?
/* 0x0158 */ s16 timer;
/* 0x015A */ s16 prizeIndex;
/* 0x015C */ s16 start;

View file

@ -7,6 +7,7 @@
#include "z_en_changer.h"
#include "vt.h"
#include "overlays/actors/ovl_Item_Etcetera/z_item_etcetera.h"
#include "overlays/actors/ovl_En_Ex_Item/z_en_ex_item.h"
#define FLAGS 0x00000000
@ -246,7 +247,7 @@ void EnChanger_OpenChests(EnChanger* this, GlobalContext* globalCtx) {
Actor_Spawn(&globalCtx->actorCtx, globalCtx, ACTOR_EN_EX_ITEM, xPos, yPos, zPos, 0, 0, 0, 0xF);
Flags_SetSwitch(globalCtx, 0x32);
} else {
temp_s0_2 = (s16)(this->rightChestGetItemId - 0x72) + 0xA;
temp_s0_2 = (s16)(this->rightChestGetItemId - GI_RUPEE_GREEN_LOSE) + EXITEM_CHEST;
// Open right treasure (chest)
osSyncPrintf(VT_FGCOL(GREEN) "☆☆☆☆☆ 右宝開く ☆☆☆☆☆ %d\n" VT_RST, temp_s0_2);
Actor_Spawn(&globalCtx->actorCtx, globalCtx, ACTOR_EN_EX_ITEM, xPos, yPos, zPos, 0, 0, 0,

View file

@ -1,4 +1,12 @@
/*
* File: z_en_ex_item.c
* Overlay: ovl_En_Ex_Item
* Description: Minigame prize items
*/
#include "z_en_ex_item.h"
#include "vt.h"
#include "overlays/actors/ovl_En_Bom_Bowl_Pit/z_en_bom_bowl_pit.h"
#define FLAGS 0x00000030
@ -9,7 +17,22 @@ void EnExItem_Destroy(Actor* thisx, GlobalContext* globalCtx);
void EnExItem_Update(Actor* thisx, GlobalContext* globalCtx);
void EnExItem_Draw(Actor* thisx, GlobalContext* globalCtx);
/*
void EnExItem_DrawItems(EnExItem* this, GlobalContext* globalCtx);
void EnExItem_DrawHeartPiece(EnExItem* this, GlobalContext* globalCtx);
void EnExItem_DrawRupee(EnExItem* this, GlobalContext* globalCtx);
void EnExItem_DrawKey(EnExItem* this, GlobalContext* globalCtx, s32 index);
void EnExItem_DrawMagic(EnExItem* this, GlobalContext* globalCtx, s16 magicIndex);
void EnExItem_WaitForObject(EnExItem* this, GlobalContext* globalCtx);
void EnExItem_BowlPrize(EnExItem* this, GlobalContext* globalCtx);
void EnExItem_SetupBowlCounter(EnExItem* this, GlobalContext* globalCtx);
void EnExItem_BowlCounter(EnExItem* this, GlobalContext* globalCtx);
void EnExItem_ExitChest(EnExItem* this, GlobalContext* globalCtx);
void EnExItem_FairyMagic(EnExItem* this, GlobalContext* globalCtx);
void EnExItem_TargetPrizeApproach(EnExItem* this, GlobalContext* globalCtx);
void EnExItem_TargetPrizeGive(EnExItem* this, GlobalContext* globalCtx);
void EnExItem_TargetPrizeFinish(EnExItem* this, GlobalContext* globalCtx);
const ActorInit En_Ex_Item_InitVars = {
ACTOR_EN_EX_ITEM,
ACTORTYPE_PROP,
@ -21,39 +44,477 @@ const ActorInit En_Ex_Item_InitVars = {
(ActorFunc)EnExItem_Update,
(ActorFunc)EnExItem_Draw,
};
*/
#pragma GLOBAL_ASM("asm/non_matchings/overlays/actors/ovl_En_Ex_Item/EnExItem_Destroy.s")
#pragma GLOBAL_ASM("asm/non_matchings/overlays/actors/ovl_En_Ex_Item/EnExItem_Init.s")
void EnExItem_Destroy(Actor* thisx, GlobalContext* globalCtx) {
}
#pragma GLOBAL_ASM("asm/non_matchings/overlays/actors/ovl_En_Ex_Item/func_80A09054.s")
void EnExItem_Init(Actor* thisx, GlobalContext* globalCtx) {
s32 pad;
EnExItem* this = THIS;
#pragma GLOBAL_ASM("asm/non_matchings/overlays/actors/ovl_En_Ex_Item/func_80A09434.s")
this->actor.flags &= ~1;
this->type = this->actor.params & 0xFF;
this->unusedParam = (this->actor.params >> 8) & 0xFF;
osSyncPrintf("\n\n");
// What will come out?
osSyncPrintf(VT_FGCOL(GREEN) "☆☆☆☆☆ なにがでるかな? ☆☆☆☆☆ %d\n" VT_RST, this->type);
// What will come out?
osSyncPrintf(VT_FGCOL(YELLOW) "☆☆☆☆☆ なにがでるかな? ☆☆☆☆☆ %d\n" VT_RST, this->unusedParam);
this->initPos = this->actor.posRot.pos;
this->getItemObjId = -1;
switch (this->type) {
case EXITEM_BOMB_BAG_BOWLING:
case EXITEM_BOMB_BAG_COUNTER:
this->getItemObjId = OBJECT_GI_BOMBPOUCH;
break;
case EXITEM_HEART_PIECE_BOWLING:
case EXITEM_HEART_PIECE_COUNTER:
this->getItemObjId = OBJECT_GI_HEARTS;
break;
case EXITEM_BOMBCHUS_BOWLING:
case EXITEM_BOMBCHUS_COUNTER:
this->getItemObjId = OBJECT_GI_BOMB_2;
break;
case EXITEM_BOMBS_BOWLING:
case EXITEM_BOMBS_COUNTER:
this->getItemObjId = OBJECT_GI_BOMB_1;
break;
case EXITEM_PURPLE_RUPEE_BOWLING:
case EXITEM_PURPLE_RUPEE_COUNTER:
case EXITEM_GREEN_RUPEE_CHEST:
case EXITEM_BLUE_RUPEE_CHEST:
case EXITEM_RED_RUPEE_CHEST:
case EXITEM_13:
case EXITEM_14:
this->getItemObjId = OBJECT_GI_RUPY;
break;
case EXITEM_SMALL_KEY_CHEST:
this->scale = 0.05f;
this->actor.velocity.y = 10.0f;
this->timer = 7;
this->actionFunc = EnExItem_ExitChest;
break;
case EXITEM_MAGIC_FIRE:
case EXITEM_MAGIC_WIND:
case EXITEM_MAGIC_DARK:
this->getItemObjId = OBJECT_GI_GODDESS;
break;
case EXITEM_BULLET_BAG:
this->getItemObjId = OBJECT_GI_DEKUPOUCH;
}
#pragma GLOBAL_ASM("asm/non_matchings/overlays/actors/ovl_En_Ex_Item/func_80A0964C.s")
if (this->getItemObjId >= 0) {
this->objectIdx = Object_GetIndex(&globalCtx->objectCtx, this->getItemObjId);
this->actor.draw = NULL;
if (this->objectIdx < 0) {
Actor_Kill(&this->actor);
// What?
osSyncPrintf("なにみの? %d\n", this->actor.params);
// bank is funny
osSyncPrintf(VT_FGCOL(PURPLE) " バンクおかしいしぞ!%d\n" VT_RST "\n", this->actor.params);
return;
}
this->actionFunc = EnExItem_WaitForObject;
}
}
#pragma GLOBAL_ASM("asm/non_matchings/overlays/actors/ovl_En_Ex_Item/func_80A09670.s")
void EnExItem_WaitForObject(EnExItem* this, GlobalContext* globalCtx) {
s32 onCounter;
#pragma GLOBAL_ASM("asm/non_matchings/overlays/actors/ovl_En_Ex_Item/func_80A096A8.s")
if (Object_IsLoaded(&globalCtx->objectCtx, this->objectIdx)) {
// End of transfer
osSyncPrintf(VT_FGCOL(GREEN) "☆☆☆☆☆ 転送終了 ☆☆☆☆☆ %d\n" VT_RST, this->actor.params, this);
osSyncPrintf(VT_FGCOL(YELLOW) "☆☆☆☆☆ 転送終了 ☆☆☆☆☆ %d\n" VT_RST, this->actor.params, this);
osSyncPrintf(VT_FGCOL(BLUE) "☆☆☆☆☆ 転送終了 ☆☆☆☆☆ %d\n" VT_RST, this->actor.params, this);
osSyncPrintf(VT_FGCOL(PURPLE) "☆☆☆☆☆ 転送終了 ☆☆☆☆☆ %d\n" VT_RST, this->actor.params, this);
osSyncPrintf(VT_FGCOL(CYAN) "☆☆☆☆☆ 転送終了 ☆☆☆☆☆ %d\n\n" VT_RST, this->actor.params, this);
this->actor.objBankIndex = this->objectIdx;
this->actor.draw = EnExItem_Draw;
this->stopRotate = false;
onCounter = false;
switch (this->type) {
case EXITEM_BOMB_BAG_COUNTER:
onCounter = true;
case EXITEM_BOMB_BAG_BOWLING:
this->unk_17C = func_8002EBCC;
this->drawItemId = 0x18;
this->timer = 65;
this->prizeRotateTimer = 35;
this->scale = 0.5f;
if (onCounter == 0) {
this->actionFunc = EnExItem_BowlPrize;
} else {
this->actionFunc = EnExItem_SetupBowlCounter;
this->actor.shape.unk_08 = -18.0f;
}
break;
case EXITEM_HEART_PIECE_COUNTER:
onCounter = true;
case EXITEM_HEART_PIECE_BOWLING:
this->unk_17C = func_8002ED80;
this->timer = 65;
this->prizeRotateTimer = 35;
this->scale = 0.5f;
if (!onCounter) {
func_80078884(NA_SE_SY_PIECE_OF_HEART);
this->actionFunc = EnExItem_BowlPrize;
} else {
this->actionFunc = EnExItem_SetupBowlCounter;
this->actor.shape.unk_08 = -10.0f;
}
break;
case EXITEM_BOMBCHUS_COUNTER:
onCounter = true;
case EXITEM_BOMBCHUS_BOWLING:
this->unk_17C = func_8002EBCC;
this->drawItemId = 39;
this->timer = 65;
this->prizeRotateTimer = 35;
this->scale = 0.5f;
if (!onCounter) {
this->actionFunc = EnExItem_BowlPrize;
} else {
this->actionFunc = EnExItem_SetupBowlCounter;
}
break;
case EXITEM_BOMBS_BOWLING:
case EXITEM_BOMBS_COUNTER:
this->unk_17C = func_8002EBCC;
this->drawItemId = 0x1F;
this->timer = 65;
this->prizeRotateTimer = 35;
this->scale = 0.5f;
this->unkFloat = 0.5f;
if (this->type == EXITEM_BOMBS_BOWLING) {
this->actionFunc = EnExItem_BowlPrize;
} else {
this->actionFunc = EnExItem_SetupBowlCounter;
this->actor.shape.unk_08 = 10.0f;
}
break;
case EXITEM_PURPLE_RUPEE_BOWLING:
case EXITEM_PURPLE_RUPEE_COUNTER:
this->unk_17C = func_8002EBCC;
this->unk_180 = func_8002ED80;
this->drawItemId = 0x70;
this->timer = 65;
this->prizeRotateTimer = 35;
this->scale = 0.5f;
this->unkFloat = 0.5f;
if (this->type == EXITEM_PURPLE_RUPEE_BOWLING) {
this->actionFunc = EnExItem_BowlPrize;
} else {
this->actionFunc = EnExItem_SetupBowlCounter;
this->actor.shape.unk_08 = 40.0f;
}
break;
case EXITEM_GREEN_RUPEE_CHEST:
case EXITEM_BLUE_RUPEE_CHEST:
case EXITEM_RED_RUPEE_CHEST:
case EXITEM_13:
case EXITEM_14:
this->unk_17C = func_8002EBCC;
this->unk_180 = func_8002ED80;
this->timer = 7;
this->scale = 0.5f;
this->unkFloat = 0.5f;
this->actor.velocity.y = 10.0f;
switch (this->type) {
case EXITEM_GREEN_RUPEE_CHEST:
this->drawItemId = 0x6C;
break;
case EXITEM_BLUE_RUPEE_CHEST:
this->drawItemId = 0x6D;
break;
case EXITEM_RED_RUPEE_CHEST:
this->drawItemId = 0x6E;
break;
case EXITEM_14:
this->drawItemId = 0x70;
break;
}
this->actionFunc = EnExItem_ExitChest;
break;
case EXITEM_MAGIC_FIRE:
case EXITEM_MAGIC_WIND:
case EXITEM_MAGIC_DARK:
this->scale = 0.35f;
this->actionFunc = EnExItem_FairyMagic;
break;
case EXITEM_BULLET_BAG:
this->unk_17C = func_8002EBCC;
this->drawItemId = 0x6B;
this->scale = 0.1f;
this->timer = 80;
this->prizeRotateTimer = 35;
this->actionFunc = EnExItem_TargetPrizeApproach;
break;
case EXITEM_SMALL_KEY_CHEST:
break;
}
}
}
#pragma GLOBAL_ASM("asm/non_matchings/overlays/actors/ovl_En_Ex_Item/func_80A09710.s")
void EnExItem_BowlPrize(EnExItem* this, GlobalContext* globalCtx) {
s32 pad;
f32 tmpf1;
f32 tmpf2;
f32 tmpf3;
f32 tmpf4;
f32 tmpf5;
f32 tmpf6;
f32 tmpf7;
f32 sp3C;
#pragma GLOBAL_ASM("asm/non_matchings/overlays/actors/ovl_En_Ex_Item/func_80A09724.s")
if (!this->stopRotate) {
this->actor.shape.rot.y += 0x1000;
if ((this->prizeRotateTimer == 0) && ((this->actor.shape.rot.y & 0xFFFF) == 0x9000)) {
this->stopRotate++;
}
} else {
Math_SmoothStepToS(&this->actor.shape.rot.y, 0, 5, 0x1000, 0);
}
if (this->timer != 0) {
if (this->prizeRotateTimer != 0) {
sp3C = 250.0f;
if (this->type == EXITEM_BOMBCHUS_BOWLING) {
sp3C = 220.0f;
}
tmpf1 = globalCtx->view.lookAt.x - globalCtx->view.eye.x;
tmpf2 = globalCtx->view.lookAt.y - globalCtx->view.eye.y;
tmpf3 = globalCtx->view.lookAt.z + sp3C - globalCtx->view.eye.z;
tmpf4 = sqrtf(SQ(tmpf1) + SQ(tmpf2) + SQ(tmpf3));
#pragma GLOBAL_ASM("asm/non_matchings/overlays/actors/ovl_En_Ex_Item/func_80A09978.s")
tmpf5 = (tmpf1 / tmpf4) * 5.0f;
tmpf6 = (tmpf2 / tmpf4) * 5.0f;
tmpf7 = (tmpf3 / tmpf4) * 5.0f;
#pragma GLOBAL_ASM("asm/non_matchings/overlays/actors/ovl_En_Ex_Item/func_80A09A00.s")
tmpf1 = globalCtx->view.eye.x + tmpf5 - this->actor.posRot.pos.x;
tmpf2 = globalCtx->view.eye.y + tmpf6 - this->actor.posRot.pos.y;
tmpf3 = globalCtx->view.eye.z + tmpf7 - this->actor.posRot.pos.z;
#pragma GLOBAL_ASM("asm/non_matchings/overlays/actors/ovl_En_Ex_Item/EnExItem_Update.s")
this->actor.posRot.pos.x += (tmpf1 / tmpf4) * 5.0f;
this->actor.posRot.pos.y += (tmpf2 / tmpf4) * 5.0f;
this->actor.posRot.pos.z += (tmpf3 / tmpf4) * 5.0f;
}
} else {
// parent
osSyncPrintf(VT_FGCOL(GREEN) " ☆☆☆☆☆ 母親ー? ☆☆☆☆☆ %x\n" VT_RST, this->actor.parent);
// Can it move?
osSyncPrintf(VT_FGCOL(GREEN) " ☆☆☆☆☆ 動いてねー? ☆☆☆☆☆ %x\n" VT_RST, this->actor.parent->update);
if ((this->actor.parent != NULL) && (this->actor.parent->update != NULL)) {
((EnBomBowlPit*)this->actor.parent)->exItemDone = 1;
// It can't move!
osSyncPrintf(VT_FGCOL(GREEN) " ☆☆☆☆☆ さぁきえるぞ! ☆☆☆☆☆ \n" VT_RST);
}
Actor_Kill(&this->actor);
}
}
#pragma GLOBAL_ASM("asm/non_matchings/overlays/actors/ovl_En_Ex_Item/EnExItem_Draw.s")
void EnExItem_SetupBowlCounter(EnExItem* this, GlobalContext* globalCtx) {
this->actor.posRot.rot.y = this->actor.shape.rot.y = 0x4268;
this->actionFunc = EnExItem_BowlCounter;
}
#pragma GLOBAL_ASM("asm/non_matchings/overlays/actors/ovl_En_Ex_Item/func_80A09B6C.s")
void EnExItem_BowlCounter(EnExItem* this, GlobalContext* globalCtx) {
this->actor.shape.rot.y += 0x800;
if (this->killItem) {
Actor_Kill(&this->actor);
}
}
#pragma GLOBAL_ASM("asm/non_matchings/overlays/actors/ovl_En_Ex_Item/func_80A09BCC.s")
void EnExItem_ExitChest(EnExItem* this, GlobalContext* globalCtx) {
this->actor.shape.rot.y += 0x1000;
if (this->timer != 0) {
if (this->timer == 1) {
this->chestKillTimer = 20;
}
} else {
this->actor.velocity.y = 0.0f;
if (this->chestKillTimer == 0) {
Actor_Kill(&this->actor);
}
}
Actor_MoveForward(&this->actor);
}
#pragma GLOBAL_ASM("asm/non_matchings/overlays/actors/ovl_En_Ex_Item/func_80A09BFC.s")
void EnExItem_FairyMagic(EnExItem* this, GlobalContext* globalCtx) {
this->actor.shape.rot.y += 0x800;
}
#pragma GLOBAL_ASM("asm/non_matchings/overlays/actors/ovl_En_Ex_Item/func_80A09C40.s")
void EnExItem_TargetPrizeApproach(EnExItem* this, GlobalContext* globalCtx) {
f32 tmpf1;
f32 tmpf2;
f32 tmpf3;
f32 tmpf4;
f32 tmpf5;
f32 tmpf6;
f32 tmpf7;
#pragma GLOBAL_ASM("asm/non_matchings/overlays/actors/ovl_En_Ex_Item/func_80A09D6C.s")
Math_ApproachF(&this->scale, 0.8f, 0.1f, 0.02f);
if (!this->stopRotate) {
this->actor.shape.rot.y += 0x1000;
if ((this->prizeRotateTimer == 0) && ((this->actor.shape.rot.y & 0xFFFF) == 0x9000)) {
this->stopRotate++;
}
} else {
Math_SmoothStepToS(&this->actor.shape.rot.y, -0x4000, 5, 0x1000, 0);
}
if (this->timer != 0) {
if (this->prizeRotateTimer != 0) {
tmpf1 = globalCtx->view.lookAt.x - globalCtx->view.eye.x;
tmpf2 = globalCtx->view.lookAt.y - 10.0f - globalCtx->view.eye.y;
tmpf3 = globalCtx->view.lookAt.z + 10.0f - globalCtx->view.eye.z;
tmpf4 = sqrtf(SQ(tmpf1) + SQ(tmpf2) + SQ(tmpf3));
tmpf5 = (tmpf1 / tmpf4) * 5.0f;
tmpf6 = (tmpf2 / tmpf4) * 5.0f;
tmpf7 = (tmpf3 / tmpf4) * 5.0f;
tmpf1 = globalCtx->view.eye.x + tmpf5 - this->actor.posRot.pos.x;
tmpf2 = globalCtx->view.eye.y - 10.0f + tmpf6 - this->actor.posRot.pos.y;
tmpf3 = globalCtx->view.eye.z + 10.0f + tmpf7 - this->actor.posRot.pos.z;
this->actor.posRot.pos.x += (tmpf1 / tmpf4) * 5.0f;
this->actor.posRot.pos.y += (tmpf2 / tmpf4) * 5.0f;
this->actor.posRot.pos.z += (tmpf3 / tmpf4) * 5.0f;
}
} else {
s32 itemId;
this->actor.draw = NULL;
func_8002DF54(globalCtx, NULL, 7);
this->actor.parent = NULL;
if (CUR_UPG_VALUE(UPG_BULLET_BAG) == 1) {
itemId = GI_BULLET_BAG_40;
} else {
itemId = GI_BULLET_BAG_50;
}
func_8002F434(&this->actor, globalCtx, itemId, 2000.0f, 1000.0f);
this->actionFunc = EnExItem_TargetPrizeGive;
}
}
void EnExItem_TargetPrizeGive(EnExItem* this, GlobalContext* globalCtx) {
s32 itemId;
if (Actor_HasParent(&this->actor, globalCtx)) {
this->actionFunc = EnExItem_TargetPrizeFinish;
} else {
itemId = (CUR_UPG_VALUE(UPG_BULLET_BAG) == 2) ? GI_BULLET_BAG_50 : GI_BULLET_BAG_40;
func_8002F434(&this->actor, globalCtx, itemId, 2000.0f, 1000.0f);
}
}
void EnExItem_TargetPrizeFinish(EnExItem* this, GlobalContext* globalCtx) {
if ((func_8010BDBC(&globalCtx->msgCtx) == 6) && func_80106BC8(globalCtx)) {
// Successful completion
osSyncPrintf(VT_FGCOL(GREEN) "☆☆☆☆☆ 正常終了 ☆☆☆☆☆ \n" VT_RST);
gSaveContext.itemGetInf[1] |= 0x2000;
Actor_Kill(&this->actor);
}
}
void EnExItem_Update(Actor* thisx, GlobalContext* globalCtx) {
s32 pad;
EnExItem* this = THIS;
if (this->timer != 0) {
this->timer--;
}
if (this->chestKillTimer != 0) {
this->chestKillTimer--;
}
if (this->prizeRotateTimer != 0) {
this->prizeRotateTimer--;
}
this->actionFunc(this, globalCtx);
}
void EnExItem_Draw(Actor* thisx, GlobalContext* globalCtx) {
s32 pad;
EnExItem* this = THIS;
s32 magicType;
Actor_SetScale(&this->actor, this->scale);
switch (this->type) {
case EXITEM_BOMB_BAG_BOWLING:
case EXITEM_BOMBCHUS_BOWLING:
case EXITEM_BOMBS_BOWLING:
case EXITEM_BOMB_BAG_COUNTER:
case EXITEM_BOMBCHUS_COUNTER:
case EXITEM_BOMBS_COUNTER:
case EXITEM_BULLET_BAG:
EnExItem_DrawItems(this, globalCtx);
break;
case EXITEM_HEART_PIECE_BOWLING:
case EXITEM_HEART_PIECE_COUNTER:
EnExItem_DrawHeartPiece(this, globalCtx);
break;
case EXITEM_PURPLE_RUPEE_BOWLING:
case EXITEM_PURPLE_RUPEE_COUNTER:
case EXITEM_GREEN_RUPEE_CHEST:
case EXITEM_BLUE_RUPEE_CHEST:
case EXITEM_RED_RUPEE_CHEST:
case EXITEM_13:
case EXITEM_14:
EnExItem_DrawRupee(this, globalCtx);
break;
case EXITEM_SMALL_KEY_CHEST:
EnExItem_DrawKey(this, globalCtx, 0);
break;
case EXITEM_MAGIC_FIRE:
case EXITEM_MAGIC_WIND:
case EXITEM_MAGIC_DARK:
magicType = this->type - EXITEM_MAGIC_FIRE;
EnExItem_DrawMagic(this, globalCtx, magicType);
break;
}
}
void EnExItem_DrawItems(EnExItem* this, GlobalContext* globalCtx) {
if (this->unk_17C != NULL) {
this->unk_17C(&this->actor, globalCtx, 0);
}
if (this) {}
func_8002ED80(&this->actor, globalCtx, 0);
func_800694A0(globalCtx, this->drawItemId);
}
void EnExItem_DrawHeartPiece(EnExItem* this, GlobalContext* globalCtx) {
func_8002ED80(&this->actor, globalCtx, 0);
func_800694A0(globalCtx, 0x13);
}
void EnExItem_DrawMagic(EnExItem* this, GlobalContext* globalCtx, s16 magicIndex) {
static s16 drawItemIds[] = { 0x63, 0x64, 0x65 };
func_8002ED80(&this->actor, globalCtx, 0);
func_800694A0(globalCtx, drawItemIds[magicIndex]);
}
void EnExItem_DrawKey(EnExItem* this, GlobalContext* globalCtx, s32 index) {
static s32 keySegments[] = { 0x0403F140 };
OPEN_DISPS(globalCtx->state.gfxCtx, "../z_en_ex_item.c", 880);
func_8009460C(globalCtx->state.gfxCtx);
gSPMatrix(POLY_OPA_DISP++, Matrix_NewMtx(globalCtx->state.gfxCtx, "../z_en_ex_item.c", 887),
G_MTX_NOPUSH | G_MTX_LOAD | G_MTX_MODELVIEW);
gSPSegment(POLY_OPA_DISP++, 0x08, SEGMENTED_TO_VIRTUAL(keySegments[index]));
gSPDisplayList(POLY_OPA_DISP++, D_0403F070);
CLOSE_DISPS(globalCtx->state.gfxCtx, "../z_en_ex_item.c", 893);
}
void EnExItem_DrawRupee(EnExItem* this, GlobalContext* globalCtx) {
if (this->unk_17C != NULL) {
this->unk_17C(&this->actor, globalCtx, 0);
}
if (this->unk_180 != NULL) {
this->unk_180(&this->actor, globalCtx, 0);
}
func_800694A0(globalCtx, this->drawItemId);
}

View file

@ -6,13 +6,56 @@
struct EnExItem;
typedef void (*EnExItemActionFunc)(struct EnExItem* this, GlobalContext* globalCtx);
typedef void (*EnExItemLightFunc)(Actor*, GlobalContext*, s32);
typedef struct EnExItem {
/* 0x0000 */ Actor actor;
/* 0x014C */ char unk_14C[0x14];
/* 0x0160 */ s16 unk_160;
/* 0x0162 */ char unk_165[0x22];
/* 0x014C */ EnExItemActionFunc actionFunc;
/* 0x0150 */ s16 getItemObjId;
/* 0x0152 */ s16 type;
/* 0x0152 */ s16 unusedParam;
/* 0x0156 */ s16 drawItemId;
/* 0x0158 */ s16 stopRotate;
/* 0x015A */ s16 timer;
/* 0x015A */ s16 chestKillTimer;
/* 0x015A */ s16 prizeRotateTimer;
/* 0x0160 */ s16 killItem;
/* 0x0164 */ f32 scale;
/* 0x0168 */ f32 unkFloat; // set to the same value as scale, but unused
/* 0x016C */ s8 objectIdx;
/* 0x0170 */ Vec3f initPos; // unused
/* 0x017C */ EnExItemLightFunc unk_17C;
/* 0x0180 */ EnExItemLightFunc unk_180;
} EnExItem; // size = 0x0184
extern const ActorInit En_Ex_Item_InitVars;
typedef enum {
/* 0 */ EXITEM_BOMB_BAG_BOWLING,
/* 1 */ EXITEM_HEART_PIECE_BOWLING,
/* 2 */ EXITEM_BOMBCHUS_BOWLING,
/* 3 */ EXITEM_BOMBS_BOWLING,
/* 4 */ EXITEM_PURPLE_RUPEE_BOWLING,
/* 5 */ EXITEM_BOMB_BAG_COUNTER,
/* 6 */ EXITEM_HEART_PIECE_COUNTER,
/* 7 */ EXITEM_BOMBCHUS_COUNTER,
/* 8 */ EXITEM_BOMBS_COUNTER,
/* 9 */ EXITEM_PURPLE_RUPEE_COUNTER,
/* 10 */ EXITEM_GREEN_RUPEE_CHEST,
/* 11 */ EXITEM_BLUE_RUPEE_CHEST,
/* 12 */ EXITEM_RED_RUPEE_CHEST,
/* 13 */ EXITEM_13,
/* 14 */ EXITEM_14,
/* 15 */ EXITEM_SMALL_KEY_CHEST,
/* 16 */ EXITEM_MAGIC_FIRE,
/* 17 */ EXITEM_MAGIC_WIND,
/* 18 */ EXITEM_MAGIC_DARK,
/* 19 */ EXITEM_BULLET_BAG
} EnExItemType;
#define EXITEM_COUNTER 5
#define EXITEM_CHEST 10
#define EXITEM_MAGIC 16
#endif