mirror of
https://github.com/encounter/Petari.git
synced 2026-03-30 11:34:15 -07:00
205 lines
5.6 KiB
C++
205 lines
5.6 KiB
C++
#include "Game/MapObj/BallRail.hpp"
|
|
#include <JSystem/JMath/JMath.hpp>
|
|
|
|
BallRail::BallRail(const char *pName) : LiveActor(pName) {
|
|
mRailPoints = nullptr;
|
|
_90 = nullptr;
|
|
mNumPoints = 0;
|
|
mAcceleration = 1.5f;
|
|
mDeceleration = 0.995f;
|
|
_AC = 100.0f;
|
|
}
|
|
|
|
void BallRail::init(const JMapInfoIter &rIter) {
|
|
if (MR::getJMapInfoArg0NoInit(rIter, &mAcceleration)) {
|
|
mAcceleration /= 1000.0f;
|
|
}
|
|
|
|
if (MR::getJMapInfoArg1NoInit(rIter, &mDeceleration)) {
|
|
mDeceleration /= 1000.0f;
|
|
}
|
|
|
|
MR::connectToSceneMapObjMovement(this);
|
|
MR::invalidateClipping(this);
|
|
MR::onCalcGravity(this);
|
|
initRailRider(rIter);
|
|
initRailPoints();
|
|
MR::moveCoordToStartPos(this);
|
|
MR::setRailCoordSpeed(this, 0.0f);
|
|
initHitSensor(1);
|
|
TVec3f offs;
|
|
offs.y = _AC;
|
|
offs.x = 0.0f;
|
|
offs.z = 0.0f;
|
|
MR::addHitSensor(this, "bind", 0x7B, 8, _AC, offs);
|
|
initNerve(&NrvBallRail::BallRailNrvWait::sInstance);
|
|
appear();
|
|
}
|
|
|
|
void BallRail::control() {
|
|
|
|
}
|
|
|
|
bool BallRail::receiveOtherMsg(u32 msg, HitSensor *a2, HitSensor *a3) {
|
|
if (msg == 173 && isNerve(&NrvBallRail::BallRailNrvWait::sInstance)) {
|
|
TVec3f v9(a2->mActor->mVelocity);
|
|
TVec3f v8 = a2->mPosition - a3->mPosition;
|
|
|
|
if (v8.dot(v9) > 0.0f) {
|
|
return false;
|
|
}
|
|
|
|
if (mGravity.dot(v8) > 0.0f) {
|
|
MR::normalizeOrZero(&v8);
|
|
v8.dot(v9);
|
|
MR::zeroVelocity(a2->mActor);
|
|
return false;
|
|
}
|
|
else {
|
|
_90 = a2;
|
|
return true;
|
|
}
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
// there is a minor regswap here but I'm marking it as done anyways
|
|
// TODO -- fix regswap
|
|
void BallRail::initRailPoints() {
|
|
#warning "BallRail::initRailPoints has a regswap"
|
|
u32 numPoints = (u32)(MR::getRailTotalLength(this) / 100.0f) + 2;
|
|
mNumPoints = numPoints;
|
|
mRailPoints = new BallRailPoint[numPoints];
|
|
MR::moveCoordToStartPos(this);
|
|
MR::setRailCoordSpeed(this, 100.0f);
|
|
|
|
for (u32 i = 0; i < mNumPoints - 1; i++) {
|
|
mRailPoints[i]._0 = MR::getRailPos(this);
|
|
mRailPoints[i]._24 = MR::getRailDirection(this);
|
|
MR::moveRailRider(this);
|
|
}
|
|
|
|
MR::moveCoordToEndPos(this);
|
|
mRailPoints[mNumPoints - 1]._0 = MR::getRailPos(this);
|
|
mRailPoints[mNumPoints - 1]._24 = MR::getRailDirection(this);
|
|
MR::moveCoordToStartPos(this);
|
|
MR::setRailCoordSpeed(this, 0.0f);
|
|
|
|
TVec3f v17(0, 1, 0);
|
|
|
|
if (mNumPoints >= 2) {
|
|
BallRailPoint* pnt = mRailPoints;
|
|
PSVECCrossProduct(pnt->_24.toCVec(), v17.toCVec(), pnt->_C.toVec());
|
|
MR::normalizeOrZero(&pnt->_C);
|
|
}
|
|
|
|
for (u32 i = 0; i < mNumPoints; i++) {
|
|
BallRailPoint* pnt = &mRailPoints[i];
|
|
PSVECCrossProduct(pnt->_24.toCVec(), v17.toCVec(), pnt->_C.toVec());
|
|
MR::normalizeOrZero(&pnt->_C);
|
|
}
|
|
|
|
if (mNumPoints >= 2) {
|
|
BallRailPoint* lastPnt = &mRailPoints[mNumPoints - 1];
|
|
PSVECCrossProduct(lastPnt->_24.toCVec(), v17.toCVec(), lastPnt->_C.toVec());
|
|
MR::normalizeOrZero(&lastPnt->_C);
|
|
}
|
|
}
|
|
|
|
void BallRail::exeWait() {
|
|
MR::moveCoordToNearestPos(this, *MR::getPlayerPos());
|
|
MR::moveTransToCurrentRailPos(this);
|
|
|
|
if (_90 != nullptr) {
|
|
setNerve(&NrvBallRail::BallRailNrvSetUp::sInstance);
|
|
}
|
|
}
|
|
|
|
void BallRail::exeSetUp() {
|
|
if (MR::isFirstStep(this)) {
|
|
_94 = _90->mPosition;
|
|
MR::zeroVelocity(_90->mActor);
|
|
MR::setRailCoordSpeed(this, 0.0f);
|
|
}
|
|
|
|
MR::moveCoord(this, 3.0f);
|
|
MR::moveTransToCurrentRailPos(this);
|
|
|
|
TVec3f v7;
|
|
|
|
if (MR::isLessStep(this, 15)) {
|
|
TVec3f v6;
|
|
JMAVECScaleAdd(mGravity.toCVec(), mPosition.toCVec(), v6.toVec(), -_90->mRadius);
|
|
f32 rate = MR::calcNerveEaseInRate(this, 15);
|
|
MR::vecBlend(_94, v6, &v7, rate);
|
|
}
|
|
else {
|
|
JMAVECScaleAdd(mGravity.toCVec(), mPosition.toCVec(), v7.toVec(), -_90->mRadius);
|
|
}
|
|
|
|
if (MR::isStep(this, 15)) {
|
|
MR::tryRumblePadStrong(this, 0);
|
|
}
|
|
|
|
MR::subtractAndSet(_90->mActor->mVelocity, v7, &_90->mPosition);
|
|
|
|
if (MR::isGreaterStep(this, 45)) {
|
|
setNerve(&NrvBallRail::BallRailNrvRun::sInstance);
|
|
}
|
|
}
|
|
|
|
void BallRail::exeRun() {
|
|
if (MR::isFirstStep(this)) {
|
|
MR::setRailCoordSpeed(this, 0.0f);
|
|
}
|
|
|
|
TVec3f v14(MR::getRailDirection(this));
|
|
TVec3f v13 = mGravity * mAcceleration;
|
|
TVec3f v12;
|
|
MR::accelerateRailCoordSpeed(this, v13.dot(v14));
|
|
MR::slowDownRailCoordSpeed(this, mDeceleration);
|
|
|
|
if (!MR::isRailGoingToEnd(this) || MR::getRailCoordSpeed(this) < 6.0f) {
|
|
if (!MR::isRailGoingToEnd(this)) {
|
|
MR::setRailDirectionToEnd(this);
|
|
}
|
|
|
|
MR::setRailCoordSpeed(this, 6.0f);
|
|
}
|
|
|
|
MR::moveRailRider(this);
|
|
MR::moveTransToCurrentRailPos(this);
|
|
JMAVECScaleAdd(mGravity.toCVec(), mPosition.toCVec(), v12.toVec(), -_90->mRadius);
|
|
MR::subtractAndSet(_90->mActor->mVelocity, v12, &_90->mPosition);
|
|
|
|
if (MR::isRailReachedGoal(this)) {
|
|
LiveActor* actor = _90->mActor;
|
|
TVec3f* vec = &actor->mVelocity;
|
|
MR::multAndSet(vec, MR::getRailDirection(this), MR::getRailCoordSpeed(this));
|
|
getSensor("bind")->receiveMessage(178, _90);
|
|
_90 = nullptr;
|
|
setNerve(&NrvBallRail::BallRailNrvNoBind::sInstance);
|
|
}
|
|
}
|
|
|
|
void BallRail::exeNoBind() {
|
|
if (getNerveStep() > 60) {
|
|
setNerve(&NrvBallRail::BallRailNrvWait::sInstance);
|
|
}
|
|
}
|
|
|
|
BallRailPoint::BallRailPoint() : _0(0, 0, 0), _C(1, 0, 0), _18(0, 1, 0), _24(0, 0, 1) {
|
|
|
|
}
|
|
|
|
BallRail::~BallRail() {
|
|
|
|
}
|
|
|
|
namespace NrvBallRail {
|
|
INIT_NERVE(BallRailNrvWait);
|
|
INIT_NERVE(BallRailNrvSetUp);
|
|
INIT_NERVE(BallRailNrvRun);
|
|
INIT_NERVE(BallRailNrvNoBind);
|
|
}; |