Add CScriptSpawnPoint

This commit is contained in:
Henrique Gemignani Passos Lima 2022-10-17 22:19:07 +03:00
parent 49f6652114
commit 6d086a09e7
No known key found for this signature in database
GPG Key ID: E224F951761145F8
8 changed files with 144 additions and 9 deletions

View File

@ -21084,7 +21084,7 @@ lbl_800D84B4:
/* 800D84F0 000D5450 38 A1 00 30 */ addi r5, r1, 0x30
/* 800D84F4 000D5454 38 E1 00 40 */ addi r7, r1, 0x40
/* 800D84F8 000D5458 39 01 00 70 */ addi r8, r1, 0x70
/* 800D84FC 000D545C 48 00 A1 C1 */ bl "__ct__17CScriptSpawnPointF9TUniqueIdRCQ24rstl66basic_string<c,Q24rstl14char_traits<c>,Q24rstl17rmemory_allocator>RC11CEntityInfoRC12CTransform4fQ24rstl21reserved_vector<i,29>bbb"
/* 800D84FC 000D545C 48 00 A1 C1 */ bl "__ct__17CScriptSpawnPointF9TUniqueIdRCQ24rstl66basic_string<c,Q24rstl14char_traits<c>,Q24rstl17rmemory_allocator>RC11CEntityInfoRC12CTransform4fRCQ24rstl21reserved_vector<i,41>bbb"
/* 800D8500 000D5460 7C 7F 1B 78 */ mr r31, r3
lbl_800D8504:
/* 800D8504 000D5464 7F 00 07 75 */ extsb. r0, r24

View File

@ -3,8 +3,8 @@
.section .data
.balign 8
.global lbl_803DF850
lbl_803DF850:
.global __vt__17CScriptSpawnPoint
__vt__17CScriptSpawnPoint:
# ROM: 0x3DC850
.4byte 0
.4byte 0
@ -212,9 +212,9 @@ __dt__17CScriptSpawnPointFv:
/* 800E2610 000DF570 93 C1 00 08 */ stw r30, 8(r1)
/* 800E2614 000DF574 7C 7E 1B 79 */ or. r30, r3, r3
/* 800E2618 000DF578 41 82 00 88 */ beq lbl_800E26A0
/* 800E261C 000DF57C 3C 60 80 3E */ lis r3, lbl_803DF850@ha
/* 800E261C 000DF57C 3C 60 80 3E */ lis r3, __vt__17CScriptSpawnPoint@ha
/* 800E2620 000DF580 34 1E 00 64 */ addic. r0, r30, 0x64
/* 800E2624 000DF584 38 03 F8 50 */ addi r0, r3, lbl_803DF850@l
/* 800E2624 000DF584 38 03 F8 50 */ addi r0, r3, __vt__17CScriptSpawnPoint@l
/* 800E2628 000DF588 90 1E 00 00 */ stw r0, 0(r30)
/* 800E262C 000DF58C 41 82 00 58 */ beq lbl_800E2684
/* 800E2630 000DF590 80 BE 00 64 */ lwz r5, 0x64(r30)
@ -259,8 +259,8 @@ lbl_800E26A0:
/* 800E26B4 000DF614 38 21 00 10 */ addi r1, r1, 0x10
/* 800E26B8 000DF618 4E 80 00 20 */ blr
.global "__ct__17CScriptSpawnPointF9TUniqueIdRCQ24rstl66basic_string<c,Q24rstl14char_traits<c>,Q24rstl17rmemory_allocator>RC11CEntityInfoRC12CTransform4fQ24rstl21reserved_vector<i,29>bbb"
"__ct__17CScriptSpawnPointF9TUniqueIdRCQ24rstl66basic_string<c,Q24rstl14char_traits<c>,Q24rstl17rmemory_allocator>RC11CEntityInfoRC12CTransform4fQ24rstl21reserved_vector<i,29>bbb":
.global "__ct__17CScriptSpawnPointF9TUniqueIdRCQ24rstl66basic_string<c,Q24rstl14char_traits<c>,Q24rstl17rmemory_allocator>RC11CEntityInfoRC12CTransform4fRCQ24rstl21reserved_vector<i,41>bbb"
"__ct__17CScriptSpawnPointF9TUniqueIdRCQ24rstl66basic_string<c,Q24rstl14char_traits<c>,Q24rstl17rmemory_allocator>RC11CEntityInfoRC12CTransform4fRCQ24rstl21reserved_vector<i,41>bbb":
/* 800E26BC 000DF61C 94 21 FF D0 */ stwu r1, -0x30(r1)
/* 800E26C0 000DF620 7C 08 02 A6 */ mflr r0
/* 800E26C4 000DF624 90 01 00 34 */ stw r0, 0x34(r1)
@ -278,9 +278,9 @@ lbl_800E26A0:
/* 800E26F4 000DF654 7C 87 23 78 */ mr r7, r4
/* 800E26F8 000DF658 38 81 00 08 */ addi r4, r1, 8
/* 800E26FC 000DF65C 4B F6 EC 29 */ bl "__ct__7CEntityF9TUniqueIdRC11CEntityInfobRCQ24rstl66basic_string<c,Q24rstl14char_traits<c>,Q24rstl17rmemory_allocator>"
/* 800E2700 000DF660 3C 60 80 3E */ lis r3, lbl_803DF850@ha
/* 800E2700 000DF660 3C 60 80 3E */ lis r3, __vt__17CScriptSpawnPoint@ha
/* 800E2704 000DF664 7F 64 DB 78 */ mr r4, r27
/* 800E2708 000DF668 38 03 F8 50 */ addi r0, r3, lbl_803DF850@l
/* 800E2708 000DF668 38 03 F8 50 */ addi r0, r3, __vt__17CScriptSpawnPoint@l
/* 800E270C 000DF66C 38 7F 00 34 */ addi r3, r31, 0x34
/* 800E2710 000DF670 90 1F 00 00 */ stw r0, 0(r31)
/* 800E2714 000DF674 48 23 04 61 */ bl __ct__12CTransform4fFRC12CTransform4f

View File

@ -49,6 +49,7 @@ public:
bool IsActive() const { return xf0_25_active; }
void SetAreaAttributes(const CScriptAreaAttributes* areaAttributes);
bool TryTakingOutOfARAM();
private:
enum EPhase {
@ -79,6 +80,22 @@ private:
bool xf0_28_validated : 1;
EPhase xf4_phase;
rstl::list< rstl::rc_ptr< IDvdRequest > > xf8_loadTransactions;
public:
enum EOcclusionState { kOS_Occluded, kOS_Visible };
struct CPostConstructed {
uchar x0_pad[0x10dc];
EOcclusionState x10dc_occlusionState;
};
EOcclusionState GetOcclusionState() const { return x12c_postConstructed->x10dc_occlusionState; }
private:
uchar x110_pad[0x1c];
rstl::single_ptr<CPostConstructed> x12c_postConstructed;
};
#endif // _CGAMEAREA

View File

@ -123,6 +123,7 @@ public:
TUniqueId GetIdForScript(TEditorId eid) const;
TIdListResult GetIdListForScript(TEditorId) const;
void SetActorAreaId(CActor& actor, TAreaId);
TAreaId GetNextAreaId() const { return x8cc_nextAreaId; }
void SetCurrentAreaId(TAreaId);

View File

@ -7,6 +7,7 @@
#include "MetroidPrime/TGameTypes.hpp"
#include "Kyoto/IObjectStore.hpp"
#include "Kyoto/Audio/CSfxHandle.hpp"
#include "rstl/string.hpp"
@ -66,6 +67,8 @@ public:
CAssetId GetWorldAssetId() const { return x8_mlvlId; }
TAreaId GetAreaIdForSaveId(int saveId) const;
static void PropogateAreaChain(CGameArea::EOcclusionState occlusionState, CGameArea* area, CWorld* world);
private:
enum Phase {
kP_Loading,

View File

@ -184,6 +184,9 @@ public:
EGunHolsterState GetGunHolsterState() const { return x498_gunHolsterState; }
NPlayer::EPlayerMovementState GetPlayerMovementState() const { return x258_movementState; }
void Teleport(const CTransform4f& xf, CStateManager& mgr, bool resetBallCam);
void SetSpawnedMorphBallState(EPlayerMorphBallState state, CStateManager& mgr);
private:
struct CVisorSteam {
float x0_curTargetAlpha;

View File

@ -0,0 +1,29 @@
#ifndef _CSCRIPTSPAWNPOINT
#define _CSCRIPTSPAWNPOINT
#include "MetroidPrime/CEntity.hpp"
#include "MetroidPrime/Player/CPlayerState.hpp"
#include "Kyoto/Math/CTransform4f.hpp"
class CScriptSpawnPoint : public CEntity {
CTransform4f x34_xf;
rstl::reserved_vector< int, int(CPlayerState::kIT_Max) > x64_itemCounts;
bool x10c_24_firstSpawn : 1;
bool x10c_25_morphed : 1;
public:
CScriptSpawnPoint(TUniqueId, const rstl::string& name, const CEntityInfo& info,
const CTransform4f& xf,
const rstl::reserved_vector< int, int(CPlayerState::kIT_Max) >& itemCounts,
bool, bool, bool);
~CScriptSpawnPoint();
const CTransform4f& GetTransform() const;
int GetPowerup(const CPlayerState::EItemType&) const;
void AcceptScriptMsg(EScriptObjectMessage, TUniqueId, CStateManager&);
void Accept(IVisitor&);
};
#endif // _CSCRIPTSPAWNPOINT

View File

@ -0,0 +1,82 @@
#include "MetroidPrime/ScriptObjects/CScriptSpawnPoint.hpp"
#include "MetroidPrime/CGameArea.hpp"
#include "MetroidPrime/CStateManager.hpp"
#include "MetroidPrime/CWorld.hpp"
#include "MetroidPrime/Player/CPlayer.hpp"
CScriptSpawnPoint::CScriptSpawnPoint(
TUniqueId uid, const rstl::string& name, const CEntityInfo& info, const CTransform4f& xf,
const rstl::reserved_vector< int, int(CPlayerState::kIT_Max) >& itemCounts, bool defaultSpawn,
bool active, bool morphed)
: CEntity(uid, info, active, name)
, x34_xf(xf)
, x64_itemCounts(itemCounts)
, x10c_24_firstSpawn(defaultSpawn)
, x10c_25_morphed(morphed) {}
CScriptSpawnPoint::~CScriptSpawnPoint() {}
const CTransform4f& CScriptSpawnPoint::GetTransform() const { return x34_xf; }
int CScriptSpawnPoint::GetPowerup(const CPlayerState::EItemType& type) const {
if (CPlayerState::kIT_Max <= type || type < 0) {
return x64_itemCounts.front();
}
return x64_itemCounts[type];
}
void CScriptSpawnPoint::AcceptScriptMsg(EScriptObjectMessage msg, TUniqueId objId,
CStateManager& stateMgr) {
CEntity::AcceptScriptMsg(msg, objId, stateMgr);
switch (msg) {
case kSM_Reset:
for (int i = 0; i < CPlayerState::kIT_Max; ++i) {
CPlayerState::EItemType e = CPlayerState::EItemType(i);
stateMgr.PlayerState()->ReInitializePowerUp(CPlayerState::EItemType(i), GetPowerup(e));
stateMgr.PlayerState()->ResetAndIncrPickUp(CPlayerState::EItemType(i), GetPowerup(e));
}
case kSM_SetToZero:
if (GetActive()) {
CPlayer* player = stateMgr.Player();
TAreaId thisAreaId = x4_areaId;
TAreaId nextAreaId = stateMgr.GetNextAreaId();
if (thisAreaId != nextAreaId) {
bool propagateAgain = false;
CGameArea* area = stateMgr.World()->Area(thisAreaId);
CGameArea::EOcclusionState occlusionState =
area->IsLoaded() ? area->GetOcclusionState() : CGameArea::kOS_Occluded;
if (occlusionState == CGameArea::kOS_Occluded) {
while (!area->TryTakingOutOfARAM()) {
}
CWorld::PropogateAreaChain(CGameArea::kOS_Visible, area, stateMgr.World());
propagateAgain = true;
}
stateMgr.SetCurrentAreaId(thisAreaId);
stateMgr.SetActorAreaId(*player, thisAreaId);
player->Teleport(x34_xf, stateMgr, true);
player->SetSpawnedMorphBallState(
x10c_25_morphed ? CPlayer::kMS_Morphed : CPlayer::kMS_Unmorphed, stateMgr);
if (propagateAgain) {
CWorld::PropogateAreaChain(CGameArea::kOS_Occluded, stateMgr.World()->Area(nextAreaId),
stateMgr.World());
}
} else {
player->Teleport(x34_xf, stateMgr, true);
player->SetSpawnedMorphBallState(
x10c_25_morphed ? CPlayer::kMS_Morphed : CPlayer::kMS_Unmorphed, stateMgr);
}
CEntity::SendScriptMsgs(kSS_Zero, stateMgr, kSM_None);
}
}
}
void CScriptSpawnPoint::Accept(IVisitor& visitor) { visitor.Visit(*this); }