MapObj: Implement BossKnuckleFix (#1021)

This commit is contained in:
guymakinggames 2026-04-22 22:27:25 +01:00 committed by GitHub
parent 572c2d6736
commit 9090655294
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
4 changed files with 133 additions and 12 deletions

View file

@ -59551,45 +59551,45 @@ MapObj/BossKnuckleFix.o:
- offset: 0x222ee4
size: 128
label: _ZN14BossKnuckleFixC2EPKc
status: NotDecompiled
status: Matching
- offset: 0x222f64
size: 140
label: _ZN14BossKnuckleFixC1EPKc
status: NotDecompiled
status: Matching
- offset: 0x222ff0
size: 336
label: _ZN14BossKnuckleFix4initERKN2al13ActorInitInfoE
status: NotDecompiled
status: Matching
- offset: 0x223140
size: 208
label: _ZN14BossKnuckleFix10receiveMsgEPKN2al9SensorMsgEPNS0_9HitSensorES5_
status: NotDecompiled
status: Matching
- offset: 0x223210
size: 60
label: _ZN14BossKnuckleFix7exeWaitEv
status: NotDecompiled
status: Matching
- offset: 0x22324c
size: 88
label: _ZN14BossKnuckleFix11exeReactionEv
status: NotDecompiled
status: Matching
- offset: 0x2232a4
size: 104
label: _ZN14BossKnuckleFix16exeReactionLargeEv
status: NotDecompiled
status: Matching
- offset: 0x22330c
size: 64
label: _ZNK12_GLOBAL__N_121BossKnuckleFixNrvWait7executeEPN2al11NerveKeeperE
status: NotDecompiled
status: Matching
guess: true
- offset: 0x22334c
size: 108
label: _ZNK12_GLOBAL__N_130BossKnuckleFixNrvReactionLarge7executeEPN2al11NerveKeeperE
status: NotDecompiled
status: Matching
guess: true
- offset: 0x2233b8
size: 92
label: _ZNK12_GLOBAL__N_125BossKnuckleFixNrvReaction7executeEPN2al11NerveKeeperE
status: NotDecompiled
status: Matching
guess: true
MapObj/BreakablePole.o:
'.text':
@ -133676,7 +133676,7 @@ Scene/ProjectActorFactory.o:
- offset: 0x4b66dc
size: 52
label: _ZN2al19createActorFunctionI14BossKnuckleFixEEPNS_9LiveActorEPKc
status: NotDecompiled
status: Matching
lazy: true
- offset: 0x4b6710
size: 52

View file

@ -0,0 +1,89 @@
#include "MapObj/BossKnuckleFix.h"
#include <math/seadVector.h>
#include "Library/LiveActor/ActorActionFunction.h"
#include "Library/LiveActor/ActorAnimFunction.h"
#include "Library/LiveActor/ActorCollisionFunction.h"
#include "Library/LiveActor/ActorInitUtil.h"
#include "Library/LiveActor/ActorPoseUtil.h"
#include "Library/LiveActor/ActorResourceFunction.h"
#include "Library/LiveActor/ActorSensorUtil.h"
#include "Library/LiveActor/LiveActorFunction.h"
#include "Library/Nerve/NerveSetupUtil.h"
#include "Library/Nerve/NerveUtil.h"
#include "Library/Obj/CollisionObj.h"
#include "Library/Stage/StageSwitchUtil.h"
#include "Util/SensorMsgFunction.h"
namespace {
NERVE_IMPL(BossKnuckleFix, Wait);
NERVE_IMPL(BossKnuckleFix, ReactionLarge);
NERVE_IMPL(BossKnuckleFix, Reaction);
NERVES_MAKE_STRUCT(BossKnuckleFix, Wait, ReactionLarge, Reaction);
} // namespace
BossKnuckleFix::BossKnuckleFix(const char* name) : al::LiveActor(name) {}
void BossKnuckleFix::init(const al::ActorInitInfo& info) {
al::initActorWithArchiveName(this, info, "BossKnuckleBody", "Fix");
al::initNerve(this, &NrvBossKnuckleFix.Wait, 0);
// NOTE: color of embedded grand shine is hardcoded to 5 (Sand)
al::startMclAnimAndSetFrameAndStop(al::getSubActor(this, "グランドシャイン"), "Color", 5.0f);
al::trySyncStageSwitchKill(this);
makeActorAlive();
mCollisionObj = new al::CollisionObj(info, al::getModelResource(this), "MoveLimit",
al::getHitSensor(this, "Body"), nullptr, nullptr);
al::setCollisionPartsSpecialPurposeName(mCollisionObj, "MoveLimit");
al::setTrans(mCollisionObj, al::getTrans(this));
al::setRotate(mCollisionObj, {0.0f, 90.0f, 0.0f});
mCollisionObj->makeActorAlive();
}
bool BossKnuckleFix::receiveMsg(const al::SensorMsg* message, al::HitSensor* other,
al::HitSensor* self) {
if (rs::isMsgPlayerDisregardHomingAttack(message))
return true;
if (al::isNerve(this, &NrvBossKnuckleFix.Wait) &&
(rs::isMsgSphinxRideAttackTouch(message) || rs::isMsgPlayerAndCapHipDropAll(message))) {
rs::requestHitReactionToAttacker(message, self, other);
mReactionCount++;
if (mReactionCount >= 3) {
mReactionCount = 0;
al::setNerve(this, &NrvBossKnuckleFix.ReactionLarge);
} else
al::setNerve(this, &NrvBossKnuckleFix.Reaction);
return !rs::isMsgPlayerAndCapHipDropAll(message);
}
return false;
}
void BossKnuckleFix::exeWait() {
if (al::isFirstStep(this))
al::startAction(this, "MapWait");
}
void BossKnuckleFix::exeReaction() {
if (al::isFirstStep(this))
al::startAction(this, "MapReaction");
if (al::isActionEnd(this))
al::setNerve(this, &NrvBossKnuckleFix.Wait);
}
void BossKnuckleFix::exeReactionLarge() {
if (al::isFirstStep(this)) {
al::startAction(this, "MapReactionLarge");
al::tryOnStageSwitch(this, "ReactionOn");
}
if (al::isActionEnd(this))
al::setNerve(this, &NrvBossKnuckleFix.Wait);
}

View file

@ -0,0 +1,31 @@
#pragma once
#include <basis/seadTypes.h>
#include "Library/LiveActor/LiveActor.h"
namespace al {
struct ActorInitInfo;
class CollisionObj;
class HitSensor;
class SensorMsg;
} // namespace al
class BossKnuckleFix : public al::LiveActor {
public:
BossKnuckleFix(const char* name);
void init(const al::ActorInitInfo& info) override;
bool receiveMsg(const al::SensorMsg* message, al::HitSensor* other,
al::HitSensor* self) override;
void exeWait();
void exeReaction();
void exeReactionLarge();
private:
al::CollisionObj* mCollisionObj = nullptr;
s32 mReactionCount = 0;
};
static_assert(sizeof(BossKnuckleFix) == 0x118);

View file

@ -69,6 +69,7 @@
#include "MapObj/AllDeadWatcherWithShine.h"
#include "MapObj/AnagramAlphabet.h"
#include "MapObj/BlockEmpty2D.h"
#include "MapObj/BossKnuckleFix.h"
#include "MapObj/CapBomb.h"
#include "MapObj/CapHanger.h"
#include "MapObj/CapSwitch.h"
@ -164,7 +165,7 @@ const al::NameToCreator<al::ActorCreatorFunction> sProjectActorFactoryEntries[]
{"BossForestWander", al::createActorFunction<BossForestWander>},
{"BossKnuckle", nullptr},
{"BossKnuckleCounterGround", nullptr},
{"BossKnuckleFix", nullptr},
{"BossKnuckleFix", al::createActorFunction<BossKnuckleFix>},
{"BossMagma", nullptr},
{"BossRaid", nullptr},
{"BossRaidNpc", nullptr},