mirror of
https://github.com/zeldaret/ss
synced 2026-07-31 00:04:28 -04:00
d_lyt_drop_line almost OK
This commit is contained in:
@@ -0,0 +1,347 @@
|
||||
#include "d/lyt/d_lyt_drop_line.h"
|
||||
|
||||
#include "common.h"
|
||||
#include "d/a/d_a_item.h"
|
||||
#include "d/lyt/meter/d_lyt_meter.h"
|
||||
#include "d/snd/d_snd_small_effect_mgr.h"
|
||||
#include "d/snd/d_snd_wzsound.h"
|
||||
#include "f/f_base.h"
|
||||
#include "m/m_color.h"
|
||||
#include "m/m_vec.h"
|
||||
#include "nw4r/math/math_types.h"
|
||||
#include "toBeSorted/d_d3d.h"
|
||||
#include "toBeSorted/d_emitter.h"
|
||||
|
||||
class dLytDropLine_HIO_c {
|
||||
public:
|
||||
dLytDropLine_HIO_c();
|
||||
virtual ~dLytDropLine_HIO_c();
|
||||
|
||||
/* 0x04 */ f32 field_0x04;
|
||||
/* 0x08 */ s32 mMoveDuration;
|
||||
/* 0x0C */ u8 field_0x0C;
|
||||
};
|
||||
|
||||
static dLytDropLine_HIO_c sHio;
|
||||
|
||||
dLytDropLine_HIO_c::dLytDropLine_HIO_c() : field_0x04(5.0f), mMoveDuration(10), field_0x0C(0) {}
|
||||
dLytDropLine_HIO_c::~dLytDropLine_HIO_c() {}
|
||||
|
||||
STATE_DEFINE(dLytDropLineParts_c, Wait);
|
||||
STATE_DEFINE(dLytDropLineParts_c, Move);
|
||||
|
||||
int dLytDropLineParts_c::create(dLytDropLine_c *main) {
|
||||
mEmitter.init(main);
|
||||
mpTargetPane = nullptr;
|
||||
reset();
|
||||
mStateMgr.changeState(StateID_Wait);
|
||||
return fBase_c::SUCCEEDED;
|
||||
}
|
||||
|
||||
int dLytDropLineParts_c::doDelete() {
|
||||
// no-op
|
||||
return fBase_c::SUCCEEDED;
|
||||
}
|
||||
|
||||
int dLytDropLineParts_c::execute() {
|
||||
mStateMgr.executeState();
|
||||
return fBase_c::SUCCEEDED;
|
||||
}
|
||||
|
||||
int dLytDropLineParts_c::draw() {
|
||||
// no-op
|
||||
return fBase_c::SUCCEEDED;
|
||||
}
|
||||
|
||||
void dLytDropLineParts_c::startPickup(mVec3_c tearWorldPos, s32 trial) {
|
||||
d3d::worldToScreen(mStartPos, tearWorldPos);
|
||||
mStartPos.z = 0.0f;
|
||||
mEffectPos = mStartPos;
|
||||
mEffectPos.z = 0.0f;
|
||||
|
||||
mTrial = trial;
|
||||
mMoveRequest = true;
|
||||
mIsDone = false;
|
||||
mLeftRight = false;
|
||||
mIsChangeAnim = false;
|
||||
}
|
||||
|
||||
void dLytDropLineParts_c::startChange(mVec3_c startPos, s32 trial, bool leftRight) {
|
||||
mStartPos = startPos;
|
||||
mEffectPos = mStartPos;
|
||||
|
||||
mTrial = trial;
|
||||
mMoveRequest = true;
|
||||
mIsDone = false;
|
||||
mLeftRight = leftRight;
|
||||
mIsChangeAnim = true;
|
||||
}
|
||||
|
||||
void dLytDropLineParts_c::reset() {
|
||||
mStartPos.setZero();
|
||||
mEffectPos.setZero();
|
||||
field_0x8C.setZero();
|
||||
mMoveTimer = 0;
|
||||
mTrial = 4;
|
||||
mMoveRequest = false;
|
||||
mIsDone = false;
|
||||
mLeftRight = false;
|
||||
mIsChangeAnim = false;
|
||||
}
|
||||
|
||||
void dLytDropLineParts_c::initializeState_Wait() {}
|
||||
|
||||
void dLytDropLineParts_c::executeState_Wait() {
|
||||
if (mMoveRequest) {
|
||||
mStateMgr.changeState(StateID_Move);
|
||||
}
|
||||
}
|
||||
|
||||
void dLytDropLineParts_c::finalizeState_Wait() {}
|
||||
|
||||
void dLytDropLineParts_c::initializeState_Move() {
|
||||
mMoveTimer = 0;
|
||||
if (mpTargetPane != nullptr) {
|
||||
nw4r::math::MTX34 mtx = mpTargetPane->GetGlobalMtx();
|
||||
|
||||
// TODO
|
||||
mVec2_c v1 = mVec2_c(mtx._03, mtx._13);
|
||||
v1 -= mVec2_c(mStartPos.x, mStartPos.y);
|
||||
|
||||
field_0x8C.x =
|
||||
(v1.x + ((f32)sHio.mMoveDuration * sHio.field_0x04 * (f32)sHio.mMoveDuration)) / (f32)sHio.mMoveDuration;
|
||||
field_0x8C.y = v1.y / (f32)sHio.mMoveDuration;
|
||||
|
||||
if (!mIsChangeAnim) {
|
||||
dSndSmallEffectMgr_c::GetInstance()->playSound(SE_S_SIREN_SHIZUKU_GET_MOVE);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void dLytDropLineParts_c::executeState_Move() {
|
||||
bool isDone = false;
|
||||
if (mpTargetPane != nullptr) {
|
||||
nw4r::math::MTX34 mtx = mpTargetPane->GetGlobalMtx();
|
||||
mVec3_c panePos(mtx._03, mtx._13, 0.0f);
|
||||
|
||||
if (!mIsChangeAnim) {
|
||||
if (dLytMeter_c::getfn_800C9FE0()) {
|
||||
mEffectPos = panePos;
|
||||
mStateMgr.changeState(StateID_Wait);
|
||||
mMoveRequest = false;
|
||||
mIsDone = true;
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
if (mMoveTimer < sHio.mMoveDuration) {
|
||||
// Quadratic parabola
|
||||
if (mLeftRight) {
|
||||
mEffectPos.x = mStartPos.x -
|
||||
(field_0x8C.x * (f32)mMoveTimer - sHio.field_0x04 * (f32)mMoveTimer * (f32)mMoveTimer);
|
||||
} else {
|
||||
mEffectPos.x =
|
||||
mStartPos.x + field_0x8C.x * (f32)mMoveTimer - sHio.field_0x04 * (f32)mMoveTimer * (f32)mMoveTimer;
|
||||
}
|
||||
|
||||
mEffectPos.y = mStartPos.y + field_0x8C.y * (f32)mMoveTimer;
|
||||
mEffectPos.z = 0.0f;
|
||||
mMoveTimer++;
|
||||
} else {
|
||||
isDone = true;
|
||||
mEffectPos = panePos;
|
||||
}
|
||||
|
||||
static const mColor sColors1[] = {
|
||||
mColor(0xA0, 0xFF, 0xB4, 0xFF), // #A0FFB4FF
|
||||
mColor(0xFF, 0x80, 0xB4, 0xFF), // #FF80B4FF
|
||||
mColor(0xFF, 0xFF, 0x80, 0xFF), // #FFFF80FF
|
||||
mColor(0x80, 0xC8, 0xFF, 0xFF), // #80C8FFFF
|
||||
};
|
||||
|
||||
static const mColor sColors2[] = {
|
||||
mColor(0x00, 0xFF, 0x30, 0xFF), // #00FF30FF
|
||||
mColor(0xFF, 0x40, 0x80, 0xFF), // #FF4080FF
|
||||
mColor(0xFF, 0xFF, 0x00, 0xFF), // #FFFF00FF
|
||||
mColor(0x60, 0x96, 0xFF, 0xFF), // #6096FFFF
|
||||
};
|
||||
|
||||
mColor c1 = 0xFFFFFFFF;
|
||||
mColor c2 = 0xFFFFFFFF;
|
||||
switch (mTrial) {
|
||||
case dAcItem_c::TRIAL_SKYLOFT:
|
||||
c1 = sColors1[0];
|
||||
c2 = sColors2[0];
|
||||
break;
|
||||
case dAcItem_c::TRIAL_FARON:
|
||||
c1 = sColors1[1];
|
||||
c2 = sColors2[1];
|
||||
break;
|
||||
case dAcItem_c::TRIAL_ELDIN:
|
||||
c1 = sColors1[2];
|
||||
c2 = sColors2[2];
|
||||
break;
|
||||
case dAcItem_c::TRIAL_LANAYRU:
|
||||
c1 = sColors1[3];
|
||||
c2 = sColors2[3];
|
||||
break;
|
||||
}
|
||||
|
||||
mEmitter.holdUIEffect(PARTICLE_RESOURCE_ID_MAPPING_138_, mEffectPos, nullptr, nullptr, &c1, &c2);
|
||||
} else {
|
||||
isDone = true;
|
||||
}
|
||||
|
||||
if (isDone) {
|
||||
mStateMgr.changeState(StateID_Wait);
|
||||
mMoveRequest = false;
|
||||
mIsDone = true;
|
||||
mIsChangeAnim = false;
|
||||
}
|
||||
}
|
||||
|
||||
void dLytDropLineParts_c::finalizeState_Move() {}
|
||||
|
||||
SPECIAL_BASE_PROFILE(LYT_DROP_LINE, dLytDropLine_c, fProfile::LYT_DROP_LINE, 0x2B0, 0x6FD);
|
||||
|
||||
dLytDropLine_c *dLytDropLine_c::sInstance;
|
||||
|
||||
int dLytDropLine_c::create() {
|
||||
sInstance->createInternal();
|
||||
return SUCCEEDED;
|
||||
}
|
||||
|
||||
int dLytDropLine_c::doDelete() {
|
||||
sInstance->doDeleteInternal();
|
||||
return SUCCEEDED;
|
||||
}
|
||||
|
||||
int dLytDropLine_c::execute() {
|
||||
if (sInstance != nullptr) {
|
||||
sInstance->executeInternal();
|
||||
}
|
||||
return SUCCEEDED;
|
||||
}
|
||||
|
||||
int dLytDropLine_c::draw() {
|
||||
if (sInstance != nullptr) {
|
||||
sInstance->drawInternal();
|
||||
}
|
||||
return SUCCEEDED;
|
||||
}
|
||||
|
||||
void dLytDropLine_c::startPickup(mVec3_c tearWorldPos, dAcItem_c::Trial_e trial) {
|
||||
if (sInstance != nullptr) {
|
||||
sInstance->startPickupInternal(tearWorldPos, trial);
|
||||
}
|
||||
}
|
||||
|
||||
void dLytDropLine_c::startChange(
|
||||
nw4r::lyt::Pane *tearSlotPane, nw4r::lyt::Pane *flowerPane, dAcItem_c::Trial_e trial, bool leftRight
|
||||
) {
|
||||
if (sInstance != nullptr) {
|
||||
sInstance->startChangeInternal(tearSlotPane, flowerPane, trial, leftRight);
|
||||
}
|
||||
}
|
||||
|
||||
bool dLytDropLine_c::finishPart() {
|
||||
if (sInstance != nullptr) {
|
||||
return sInstance->finishPartInternal();
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void dLytDropLine_c::setPane(nw4r::lyt::Pane *pane) {
|
||||
if (sInstance != nullptr) {
|
||||
sInstance->setPaneInternal(pane);
|
||||
}
|
||||
}
|
||||
|
||||
nw4r::lyt::Pane *dLytDropLine_c::getActivePane() {
|
||||
if (sInstance != nullptr) {
|
||||
return sInstance->getActivePaneInternal();
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
int dLytDropLine_c::createInternal() {
|
||||
for (int i = 0; i < NUM_PARTS; i++) {
|
||||
mParts[i].create(this);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
int dLytDropLine_c::doDeleteInternal() {
|
||||
for (int i = 0; i < NUM_PARTS; i++) {
|
||||
mParts[i].doDelete();
|
||||
}
|
||||
return SUCCEEDED;
|
||||
}
|
||||
|
||||
int dLytDropLine_c::executeInternal() {
|
||||
for (int i = 0; i < NUM_PARTS; i++) {
|
||||
mParts[i].execute();
|
||||
}
|
||||
return SUCCEEDED;
|
||||
}
|
||||
|
||||
int dLytDropLine_c::drawInternal() {
|
||||
for (int i = 0; i < NUM_PARTS; i++) {
|
||||
mParts[i].draw();
|
||||
}
|
||||
return SUCCEEDED;
|
||||
}
|
||||
|
||||
void dLytDropLine_c::startPickupInternal(mVec3_c tearWorldPos, dAcItem_c::Trial_e trial) {
|
||||
for (int i = 0; i < NUM_PARTS; i++) {
|
||||
if (!mParts[i].isMoveRequest()) {
|
||||
mParts[i].startPickup(tearWorldPos, trial);
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void dLytDropLine_c::startChangeInternal(
|
||||
nw4r::lyt::Pane *tearSlotPane, nw4r::lyt::Pane *flowerPane, dAcItem_c::Trial_e trial, bool leftRight
|
||||
) {
|
||||
for (int i = 0; i < NUM_PARTS; i++) {
|
||||
if (!mParts[i].isMoveRequest()) {
|
||||
mParts[i].setTargetPane(flowerPane);
|
||||
if (tearSlotPane != nullptr) {
|
||||
nw4r::math::MTX34 mtx = tearSlotPane->GetGlobalMtx();
|
||||
mVec3_c startPos(mtx._03, mtx._13, 0.0f);
|
||||
mParts[i].startChange(startPos, trial, leftRight);
|
||||
} else {
|
||||
mVec3_c startPos(0.0f, -200.0f, 0.0f);
|
||||
mParts[i].startChange(startPos, trial, leftRight);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
bool dLytDropLine_c::finishPartInternal() {
|
||||
for (int i = 0; i < NUM_PARTS; i++) {
|
||||
if (mParts[i].isDone()) {
|
||||
mParts[i].finish();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void dLytDropLine_c::setPaneInternal(nw4r::lyt::Pane *pane) {
|
||||
for (int i = 0; i < NUM_PARTS; i++) {
|
||||
mParts[i].setTargetPane(pane);
|
||||
}
|
||||
}
|
||||
|
||||
nw4r::lyt::Pane *dLytDropLine_c::getActivePaneInternal() {
|
||||
for (int i = 0; i < NUM_PARTS; i++) {
|
||||
if (mParts[i].getTargetPane() != nullptr) {
|
||||
return mParts[i].getTargetPane();
|
||||
}
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
@@ -243,7 +243,7 @@ void LytMeterTimerPart1_c::startNextFruitAnim() {
|
||||
}
|
||||
|
||||
void LytMeterTimerPart1_c::startFruitAnim(s32 index) {
|
||||
if (field_0x780 < TIMER_01_NUM_TEARS && !mAnm[index + TIMER_01_ANIM_BOWL_NUT_OFFSET].isEnabled()) {
|
||||
if (mChangeFruitIndex < TIMER_01_NUM_TEARS && !mAnm[index + TIMER_01_ANIM_BOWL_NUT_OFFSET].isEnabled()) {
|
||||
mAnm[index + TIMER_01_ANIM_BOWL_NUT_OFFSET].setAnimEnable(true);
|
||||
}
|
||||
}
|
||||
@@ -264,7 +264,7 @@ void LytMeterTimerPart1_c::disableCurrentFruitAnim() {
|
||||
}
|
||||
|
||||
void LytMeterTimerPart1_c::stopFinishedFruit() {
|
||||
for (s32 i = 0; i <= field_0x780; i++) {
|
||||
for (s32 i = 0; i <= mChangeFruitIndex; i++) {
|
||||
if (mAnm[i + TIMER_01_ANIM_BOWL_NUT_OFFSET].isEnabled() && mAnm[i + TIMER_01_ANIM_BOWL_NUT_OFFSET].isStop2()) {
|
||||
mAnm[i + TIMER_01_ANIM_BOWL_NUT_OFFSET].setAnimEnable(false);
|
||||
return;
|
||||
@@ -292,7 +292,7 @@ bool LytMeterTimerPart1_c::isCurrentFruitAnimFinished() {
|
||||
}
|
||||
|
||||
bool LytMeterTimerPart1_c::isAnyFruitAnimFinished() {
|
||||
for (s32 i = 0; i <= field_0x780; i++) {
|
||||
for (s32 i = 0; i <= mChangeFruitIndex; i++) {
|
||||
if (mAnm[i + TIMER_01_ANIM_BOWL_NUT_OFFSET].isEnabled() && mAnm[i + TIMER_01_ANIM_BOWL_NUT_OFFSET].isStop2()) {
|
||||
return true;
|
||||
}
|
||||
@@ -312,7 +312,7 @@ bool LytMeterTimerPart1_c::isOutAnimFinished() {
|
||||
}
|
||||
|
||||
bool LytMeterTimerPart1_c::isAnyFruitAnimAtFrame(f32 f) const {
|
||||
for (int i = 0; i <= field_0x780; i++) {
|
||||
for (int i = 0; i <= mChangeFruitIndex; i++) {
|
||||
if (mAnm[i + TIMER_01_ANIM_BOWL_NUT_OFFSET].isEnabled() &&
|
||||
f - 1.0f < mAnm[i + TIMER_01_ANIM_BOWL_NUT_OFFSET].getFrame() &&
|
||||
mAnm[i + TIMER_01_ANIM_BOWL_NUT_OFFSET].getFrame() <= f) {
|
||||
@@ -324,7 +324,7 @@ bool LytMeterTimerPart1_c::isAnyFruitAnimAtFrame(f32 f) const {
|
||||
|
||||
bool LytMeterTimerPart1_c::incrementTearCount() {
|
||||
mActualTearCount = ItemflagManager::sInstance->getFlagDirect(500);
|
||||
if (mDisplayedTearCount < mActualTearCount && dLytDropLine_c::finishPartMaybe()) {
|
||||
if (mDisplayedTearCount < mActualTearCount && dLytDropLine_c::finishPart()) {
|
||||
startNextFruitAnim();
|
||||
if (!dLytMeter_c::getfn_800C9FE0()) {
|
||||
startEffect(mActualTearCount - 1);
|
||||
@@ -402,9 +402,9 @@ void LytMeterTimerPart1_c::startEffect(s32 fruitIndex) {
|
||||
);
|
||||
}
|
||||
|
||||
void LytMeterTimerPart1_c::updateDropLine(nw4r::lyt::Pane *pane) {
|
||||
u8 idx = field_0x780;
|
||||
dLytDropLine_c::update(mpPanes[idx], pane, mTrial, field_0x780 % 2 != 0);
|
||||
void LytMeterTimerPart1_c::startDropLineChange(nw4r::lyt::Pane *pane) {
|
||||
u8 idx = mChangeFruitIndex;
|
||||
dLytDropLine_c::startChange(mpPanes[idx], pane, mTrial, mChangeFruitIndex % 2 != 0);
|
||||
}
|
||||
|
||||
static const d2d::LytBrlanMapping brlanMapPart2[] = {
|
||||
@@ -1226,7 +1226,7 @@ void dLytMeterTimer_c::executeState_ChangeFruits() {
|
||||
mpPart2->resetSingleAnim(TIMER_02_ANIM_FLOWER_LOOP);
|
||||
}
|
||||
|
||||
if (dLytDropLine_c::finishPartMaybe()) {
|
||||
if (dLytDropLine_c::finishPart()) {
|
||||
if (mpPart1->isLastFruitAnimFinished()) {
|
||||
mpPart2->realizeFruitsColor();
|
||||
mpPart2->enableChangeFruitAnim();
|
||||
@@ -1238,10 +1238,10 @@ void dLytMeterTimer_c::executeState_ChangeFruits() {
|
||||
}
|
||||
|
||||
if (mpPart1->isAnyFruitAnimAtFrame(4.0f)) {
|
||||
s32 fruit = mpPart1->getField0x780() + 1;
|
||||
mpPart1->setField0x780(fruit);
|
||||
if (mpPart1->getField0x780() < TIMER_01_NUM_TEARS) {
|
||||
mpPart1->updateDropLine(mpPart2->i_getPane());
|
||||
s32 fruit = mpPart1->getChangeFruitIndex() + 1;
|
||||
mpPart1->setChangeFruitIndex(fruit);
|
||||
if (mpPart1->getChangeFruitIndex() < TIMER_01_NUM_TEARS) {
|
||||
mpPart1->startDropLineChange(mpPart2->i_getPane());
|
||||
mpPart1->startFruitAnim(fruit);
|
||||
mpPart1->startEffect(fruit);
|
||||
}
|
||||
@@ -1456,9 +1456,9 @@ void dLytMeterTimer_c::gotoSafe() {
|
||||
void dLytMeterTimer_c::gotoChangeFruits6() {
|
||||
if (mStateMgr.isState(StateID_Siren) || mStateMgr.isState(StateID_Safe)) {
|
||||
mpPart1->resetBowlNuts();
|
||||
mpPart1->updateDropLine(mpPart2->i_getPane());
|
||||
mpPart1->startFruitAnim(mpPart1->getField0x780());
|
||||
mpPart1->startEffect(mpPart1->getField0x780());
|
||||
mpPart1->startDropLineChange(mpPart2->i_getPane());
|
||||
mpPart1->startFruitAnim(mpPart1->getChangeFruitIndex());
|
||||
mpPart1->startEffect(mpPart1->getChangeFruitIndex());
|
||||
field_0x54 = false;
|
||||
field_0x56 = 6;
|
||||
mStateMgr.changeState(StateID_ChangeFruits);
|
||||
@@ -1504,9 +1504,9 @@ void dLytMeterTimer_c::startSafe() {
|
||||
|
||||
void dLytMeterTimer_c::doPickup() {
|
||||
mpPart1->resetBowlNuts();
|
||||
mpPart1->updateDropLine(mpPart2->i_getPane());
|
||||
mpPart1->startFruitAnim(mpPart1->getField0x780());
|
||||
mpPart1->startEffect(mpPart1->getField0x780());
|
||||
mpPart1->startDropLineChange(mpPart2->i_getPane());
|
||||
mpPart1->startFruitAnim(mpPart1->getChangeFruitIndex());
|
||||
mpPart1->startEffect(mpPart1->getChangeFruitIndex());
|
||||
field_0x56 = 6;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user