From 696f7a97728f0c4c0f9cdb6b1efb328098edf423 Mon Sep 17 00:00:00 2001 From: Phillip Stephens Date: Tue, 24 Jan 2017 09:23:10 -0800 Subject: [PATCH] Implement CScriptGenerator --- Runtime/CStateManager.cpp | 5 ++ Runtime/CStateManager.hpp | 25 ++++-- Runtime/Character/CModelData.hpp | 3 + Runtime/World/CActor.cpp | 8 ++ Runtime/World/CActor.hpp | 6 +- Runtime/World/CMakeLists.txt | 1 + Runtime/World/CScriptGenerator.cpp | 132 +++++++++++++++++++++++++--- Runtime/World/CScriptGenerator.hpp | 8 +- Runtime/World/CScriptSound.cpp | 88 ++++++++++++++++--- Runtime/World/CScriptSound.hpp | 49 ++++++++++- Runtime/World/CWallCrawlerSwarm.cpp | 26 ++++++ Runtime/World/CWallCrawlerSwarm.hpp | 63 +++++++++++++ Runtime/World/ScriptLoader.cpp | 100 +++++++++++++++------ 13 files changed, 446 insertions(+), 68 deletions(-) diff --git a/Runtime/CStateManager.cpp b/Runtime/CStateManager.cpp index 6fd07a5a7..e7b189a86 100644 --- a/Runtime/CStateManager.cpp +++ b/Runtime/CStateManager.cpp @@ -407,6 +407,11 @@ void CStateManager::LoadScriptObjects(TAreaId aid, CInputStream& in, std::vector void CStateManager::LoadScriptObject(TAreaId, EScriptObjectType, u32, CInputStream& in) {} +std::pair CStateManager::GenerateObject(TEditorId) +{ + return {kInvalidEditorId, kInvalidUniqueId}; +} + void CStateManager::InitScriptObjects(std::vector& ids) { for (TEditorId id : ids) diff --git a/Runtime/CStateManager.hpp b/Runtime/CStateManager.hpp index 1f9f50e21..74f6384ff 100644 --- a/Runtime/CStateManager.hpp +++ b/Runtime/CStateManager.hpp @@ -144,12 +144,12 @@ class CStateManager { struct { - bool xe86_24_; - bool xe86_25_; - bool xe86_26_; - bool xe86_27_; - bool xe86_28_; - bool xe86_29_; + bool xe86_24_ : 1; + bool xe86_25_ : 1; + bool xe86_26_ : 1; + bool xe86_27_ : 1; + bool xe86_28_ : 1; + bool xe86_29_ : 1; }; u16 _dummy = 0; }; @@ -165,10 +165,18 @@ class CStateManager TUniqueId xf74_lastTrigger = kInvalidUniqueId; TUniqueId xf76_lastRelay = kInvalidUniqueId; + union + { + struct + { + bool xf94_26_generatingObject : 1; + }; + u32 xf94_ = 0; + }; + public: /* TODO: Public for CFirstPersonCamera */ u32 x904_; - CStateManager(const std::weak_ptr&, const std::weak_ptr&, const std::weak_ptr&, @@ -221,6 +229,7 @@ public: GetIdListForScript(TEditorId) const; void LoadScriptObjects(TAreaId, CInputStream& in, std::vector& idsOut); void LoadScriptObject(TAreaId, EScriptObjectType, u32, CInputStream& in); + std::pair GenerateObject(TEditorId); void InitScriptObjects(std::vector& ids); void InformListeners(const zeus::CVector3f&, EListenNoiseType); bool ApplyKnockBack(CActor& actor, const CDamageInfo& info, @@ -312,6 +321,8 @@ public: void SetLastRelayId(TUniqueId uid) { xf76_lastRelay = uid; } TUniqueId* GetLastRelayIdPtr() { return &xf76_lastRelay; } TUniqueId GetLastRelayId() const { return xf76_lastRelay; } + bool GetIsGeneratingObject() const { return xf94_26_generatingObject; } + void SetIsGeneratingObject(bool gen) { xf94_26_generatingObject = gen; } }; } diff --git a/Runtime/Character/CModelData.hpp b/Runtime/Character/CModelData.hpp index da5a0c953..510790af8 100644 --- a/Runtime/Character/CModelData.hpp +++ b/Runtime/Character/CModelData.hpp @@ -145,6 +145,9 @@ public: const TLockedToken& GetXRayModel() const { return x2c_xrayModel; } const TLockedToken& GetThermalModel() const { return x3c_infraModel; } bool IsNull() { return !x10_animData && !x1c_normalModel; } + + const zeus::CVector3f& GetScale() const { return x0_scale; } + void SetScale(const zeus::CVector3f& scale) { x0_scale = scale; } }; } diff --git a/Runtime/World/CActor.cpp b/Runtime/World/CActor.cpp index a0ca702e0..955c78b4f 100644 --- a/Runtime/World/CActor.cpp +++ b/Runtime/World/CActor.cpp @@ -269,6 +269,14 @@ void CActor::SetTranslation(const zeus::CVector3f& tr) xe4_29_ = true; } +void CActor::SetTransform(const zeus::CTransform& tr) +{ + x34_transform = tr; + xe4_27_ = true; + xe4_28_ = true; + xe4_29_ = true; +} + void CActor::SetAddedToken(u32 tok) { xcc_addedToken = tok; } float CActor::GetPitch() const { return zeus::CQuaternion(x34_transform.buildMatrix3f()).pitch(); } diff --git a/Runtime/World/CActor.hpp b/Runtime/World/CActor.hpp index 748fd80a8..f598da642 100644 --- a/Runtime/World/CActor.hpp +++ b/Runtime/World/CActor.hpp @@ -50,7 +50,8 @@ protected: float xd0_; u8 xd4_ = 0x7F; u32 xd8_ = 2; - union { + union + { struct { bool xe4_27_ : 1; @@ -117,6 +118,7 @@ public: void RemoveEmitter(); const zeus::CTransform& GetTransform() const { return x34_transform; } + const zeus::CVector3f& GetTranslation() const { return x34_transform.origin; } const zeus::CTransform GetScaledLocatorTransform(const std::string& segName) const; const zeus::CTransform GetLocatorTransform(const std::string& segName) const; void RemoveMaterial(EMaterialTypes, EMaterialTypes, EMaterialTypes, EMaterialTypes, CStateManager&); @@ -142,10 +144,12 @@ public: void SetSfxPitchBend(s32); void SetRotation(const zeus::CQuaternion& q); void SetTranslation(const zeus::CVector3f& tr); + void SetTransform(const zeus::CTransform& tr); void SetAddedToken(u32 tok); float GetPitch() const; float GetYaw() const; const CModelData* GetModelData() const { return x64_modelData.get(); } + CModelData* ModelData() { return x64_modelData.get(); } void EnsureRendered(const CStateManager&); void EnsureRendered(const CStateManager&, const zeus::CVector3f&, const zeus::CVector3f&); }; diff --git a/Runtime/World/CMakeLists.txt b/Runtime/World/CMakeLists.txt index a72fa97e1..e0b17b361 100644 --- a/Runtime/World/CMakeLists.txt +++ b/Runtime/World/CMakeLists.txt @@ -69,6 +69,7 @@ set(WORLD_SOURCES CScriptTargetingPoint.hpp CScriptTargetingPoint.cpp CScriptPlayerActor.hpp CScriptPlayerActor.cpp CScriptSwitch.hpp CScriptSwitch.cpp + CWallCrawlerSwarm.hpp CWallCrawlerSwarm.cpp CScriptAiJumpPoint.hpp CScriptAiJumpPoint.cpp CScriptRoomAcoustics.hpp CScriptRoomAcoustics.cpp CScriptColorModulate.hpp CScriptColorModulate.cpp diff --git a/Runtime/World/CScriptGenerator.cpp b/Runtime/World/CScriptGenerator.cpp index 1fda3537a..6aa303c26 100644 --- a/Runtime/World/CScriptGenerator.cpp +++ b/Runtime/World/CScriptGenerator.cpp @@ -1,31 +1,137 @@ #include "CScriptGenerator.hpp" #include "CStateManager.hpp" +#include "CWallCrawlerSwarm.hpp" #include "TCastTo.hpp" namespace urde { -CScriptGenerator::CScriptGenerator(TUniqueId uid, const std::string& name, const CEntityInfo& info, - u32 w1, bool b1, const zeus::CVector3f& vec1, bool b2, bool active, float minScale, float maxScale) -: CEntity(uid, info, active, name), - x34_(w1), - x38_24_(b1), - x38_25_(b2), - x3c_(vec1), - x48_minScale(minScale), - x4c_maxScale(maxScale) +CScriptGenerator::CScriptGenerator(TUniqueId uid, const std::string& name, const CEntityInfo& info, u32 w1, bool b1, + const zeus::CVector3f& vec1, bool follow, bool active, float minScale, + float maxScale) +: CEntity(uid, info, active, name) +, x34_spawnCount(w1) +, x38_24_reuseFollowers(b1) +, x38_25_inheritTransform(follow) +, x3c_offset(vec1) +, x48_minScale(minScale) +, x4c_maxScale(maxScale) { } -void CScriptGenerator::Accept(IVisitor& visitor) -{ - visitor.Visit(this); -} +void CScriptGenerator::Accept(IVisitor& visitor) { visitor.Visit(this); } void CScriptGenerator::AcceptScriptMsg(EScriptObjectMessage msg, TUniqueId objId, CStateManager& stateMgr) { if (msg == EScriptObjectMessage::SetToZero && GetActive()) { + if (!x20_conns.empty()) + { + std::vector follows; + follows.reserve(x20_conns.size()); + for (const SConnection& conn : x20_conns) + { + if (conn.x0_state != EScriptObjectState::Zero || conn.x4_msg != EScriptObjectMessage::Follow) + continue; + + TUniqueId uid = stateMgr.GetIdForScript(conn.x8_objId); + if (stateMgr.GetObjectById(uid) != nullptr) + follows.push_back(uid); + } + + std::vector> activates; + activates.reserve(x20_conns.size()); + + for (const SConnection& conn : x20_conns) + { + if (conn.x0_state != EScriptObjectState::Zero) + continue; + + TUniqueId uid = stateMgr.GetIdForScript(conn.x8_objId); + + if (conn.x4_msg != EScriptObjectMessage::Activate) + { + stateMgr.SendScriptMsgAlways(GetUniqueId(), uid, conn.x4_msg); + continue; + } + + if (stateMgr.GetObjectById(uid) != nullptr) + activates.emplace_back(uid, conn.x8_objId); + } + + for (u32 i = 0; i < x34_spawnCount; ++i) + { + if (activates.size() == 0 || follows.size() == 0) + return; + + u32 activatesRand = 0.99f * (stateMgr.GetActiveRandom()->Float() * activates.size()); + u32 followsRand = 0.99f * (stateMgr.GetActiveRandom()->Float() * follows.size()); + + for (u32 j = 0; j < activates.size(); ++j) + if (TCastToConstPtr(stateMgr.GetObjectById(activates[j].first))) + activatesRand = j; + + std::pair idPair = activates[activatesRand]; + CEntity* activate = stateMgr.ObjectById(idPair.first); + CEntity* follow = stateMgr.ObjectById(follows[followsRand]); + + if (!activate || !follow) + break; + + bool oldGeneratingObject = stateMgr.GetIsGeneratingObject(); + stateMgr.SetIsGeneratingObject(true); + std::pair objId = stateMgr.GenerateObject(idPair.second); + stateMgr.SetIsGeneratingObject(oldGeneratingObject); + + if (objId.second != kInvalidUniqueId) + { + TCastToPtr activateActor(stateMgr.ObjectById(idPair.first)); + TCastToPtr followActor(follow); + TCastToPtr wallCrawlerSwarm(follow); + + if (activateActor && wallCrawlerSwarm) + { + if (x38_25_inheritTransform) + activateActor->SetTransform(wallCrawlerSwarm->GetTransform()); + activateActor->SetTranslation(wallCrawlerSwarm->GetLastKilledOffset() + x3c_offset); + } + else if (activateActor && followActor) + { + if (x38_25_inheritTransform) + activateActor->SetTransform(followActor->GetTransform()); + activateActor->SetTranslation(activateActor->GetTranslation() + x3c_offset); + } + else if (follow != nullptr) + { + TCastToPtr activateActor(stateMgr.ObjectById(objId.second)); + + if (activateActor && wallCrawlerSwarm) + { + if (x38_25_inheritTransform) + activateActor->SetTransform(wallCrawlerSwarm->GetTransform()); + activateActor->SetTranslation(wallCrawlerSwarm->GetLastKilledOffset() + x3c_offset); + } + else if (activateActor && followActor) + { + if (x38_25_inheritTransform) + activateActor->SetTransform(followActor->GetTransform()); + activateActor->SetTranslation(activateActor->GetTranslation() + x3c_offset); + } + + float rnd = stateMgr.GetActiveRandom()->Range(x48_minScale, x4c_maxScale); + CModelData* mData = followActor->ModelData(); + if (mData && (mData->AnimationData() || mData->GetNormalModel())) + mData->SetScale(rnd * mData->GetScale()); + } + + stateMgr.SendScriptMsg(activate, GetUniqueId(), EScriptObjectMessage::Activate); + + activates.erase(std::find(activates.begin(), activates.end(), idPair)); + if (!x38_24_reuseFollowers) + follows.erase(std::find(follows.begin(), follows.end(), follows[followsRand])); + } + } + } } CEntity::AcceptScriptMsg(msg, objId, stateMgr); diff --git a/Runtime/World/CScriptGenerator.hpp b/Runtime/World/CScriptGenerator.hpp index fd83f809a..34b9b520f 100644 --- a/Runtime/World/CScriptGenerator.hpp +++ b/Runtime/World/CScriptGenerator.hpp @@ -9,16 +9,16 @@ namespace urde class CScriptGenerator : public CEntity { - u32 x34_; + u32 x34_spawnCount; union { struct { - bool x38_24_ : 1; - bool x38_25_ : 1; + bool x38_24_reuseFollowers : 1; + bool x38_25_inheritTransform : 1; }; u8 dummy1 = 0; }; - zeus::CVector3f x3c_; + zeus::CVector3f x3c_offset; float x48_minScale; float x4c_maxScale; diff --git a/Runtime/World/CScriptSound.cpp b/Runtime/World/CScriptSound.cpp index e5f69a7dd..09864d842 100644 --- a/Runtime/World/CScriptSound.cpp +++ b/Runtime/World/CScriptSound.cpp @@ -6,18 +6,84 @@ namespace urde { +bool CScriptSound::sFirstInFrame = false; -CScriptSound::CScriptSound(TUniqueId uid, const std::string& name, const CEntityInfo& info, - const zeus::CTransform& xf, s16 soundId, bool active, float, float, float, - u32, u32, u32, u32, u32, bool, bool, bool, bool, bool, bool, bool, bool, u32) -: CActor(uid, active, name, info, xf, CModelData::CModelDataNull(), - CMaterialList(), CActorParameters::None(), kInvalidUniqueId) +CScriptSound::CScriptSound(TUniqueId uid, const std::string& name, const CEntityInfo& info, const zeus::CTransform& xf, + s16 soundId, bool active, float f1, float f2, float f3, u32 w1, u32 w2, u32 w3, u32 w4, + u32 w5, u32 w6, bool b1, bool b2, bool b3, bool b4, bool b5, bool b6, bool b7, u32 w7) +: CActor(uid, active, name, info, xf, CModelData::CModelDataNull(), CMaterialList(EMaterialTypes::Unknown), + CActorParameters::None(), kInvalidUniqueId) +, xfc_(f3) +, x100_soundId(CSfxManager::TranslateSFXID(soundId)) +, x104_(f1) +, x108_(f2) +, x10c_(w1) +, x10e_(w2) +, x110_(w3) +, x112_(w4) +, x114_(w5) +, x116_(w6) +, x118_(w7 + 8192) +, x11c_25_(b1) +, x11c_26_(b2) +, x11c_27_(b3) +, x11c_28_(b4) +, x11c_29_(b5) +, x11c_30_(b6) +, x11d_24_(b7) +{ + if (x11c_30_ && (!x11c_26_ || !x11c_25_)) + x11c_30_ = false; +} + +void CScriptSound::Accept(IVisitor& visitor) { visitor.Visit(this); } + +void CScriptSound::PreThink(float dt, CStateManager& mgr) +{ + CEntity::PreThink(dt, mgr); + sFirstInFrame = true; + x11d_25_ = false; +} + +void CScriptSound::Think(float, CStateManager&) {} + +void CScriptSound::AcceptScriptMsg(EScriptObjectMessage msg, TUniqueId uid, CStateManager& mgr) +{ + CActor::AcceptScriptMsg(msg, uid, mgr); + + switch (msg) + { + case EScriptObjectMessage::InternalMessage11: + { + } + break; + case EScriptObjectMessage::Play: + { + } + break; + case EScriptObjectMessage::Stop: + { + } + break; + case EScriptObjectMessage::Deactivate: + { + } + break; + case EScriptObjectMessage::Activate: + { + } + break; + case EScriptObjectMessage::InternalMessage12: + { + } + break; + default:break; + } +} + +void CScriptSound::PlaySound(CStateManager&) {} + +void CScriptSound::StopSound() { } - -void CScriptSound::Accept(IVisitor& visitor) -{ - visitor.Visit(this); -} - } diff --git a/Runtime/World/CScriptSound.hpp b/Runtime/World/CScriptSound.hpp index 3c9da12cb..cbc6fde22 100644 --- a/Runtime/World/CScriptSound.hpp +++ b/Runtime/World/CScriptSound.hpp @@ -8,14 +8,55 @@ namespace urde class CScriptSound : public CActor { + static bool sFirstInFrame; + + float xe8_ = 0.f; + std::unique_ptr xec_sfxHandle; + s16 xf0_ = 0; + s16 xf4_ = 0; + float xf8_ = 0.f; + float xfc_; + s16 x100_soundId; + float x104_; + float x108_; + s16 x10c_; + s16 x10e_; + s16 x110_; + s16 x112_; + s16 x114_; + bool x116_; + u32 x118_; + union + { + struct + { + bool x11c_24_ : 1; + bool x11c_25_ : 1; + bool x11c_26_ : 1; + bool x11c_27_ : 1; + bool x11c_28_ : 1; + bool x11c_29_ : 1; + bool x11c_30_ : 1; + bool x11c_31_ : 1; + bool x11d_24_ : 1; + bool x11d_25_ : 1; + }; + u32 x11c_dummy = 0; + }; + public: - CScriptSound(TUniqueId, const std::string& name, const CEntityInfo& info, - const zeus::CTransform& xf, s16 soundId, bool, float, float, float, - u32, u32, u32, u32, u32, bool, bool, bool, bool, bool, bool, bool, bool, u32); + CScriptSound(TUniqueId, const std::string& name, const CEntityInfo& info, const zeus::CTransform& xf, s16 soundId, + bool, float, float, float, u32, u32, u32, u32, u32, u32, bool, bool, bool, bool, bool, bool, bool, u32); void Accept(IVisitor& visitor); + void AddToRenderer(const zeus::CFrustum&, const CStateManager&) const {} + void PreThink(float, CStateManager&); + void Think(float, CStateManager&); + void AcceptScriptMsg(EScriptObjectMessage, TUniqueId, CStateManager&); + void GetOccludedVolumeAmount(const zeus::CVector3f&, const CStateManager&); + void PlaySound(CStateManager&); + void StopSound(); }; - } #endif // __URDE_CSCRIPTSOUND_HPP__ diff --git a/Runtime/World/CWallCrawlerSwarm.cpp b/Runtime/World/CWallCrawlerSwarm.cpp index e69de29bb..f3a2c5b0a 100644 --- a/Runtime/World/CWallCrawlerSwarm.cpp +++ b/Runtime/World/CWallCrawlerSwarm.cpp @@ -0,0 +1,26 @@ +#include "World/CWallCrawlerSwarm.hpp" +#include "World/CActorParameters.hpp" +#include "Collision/CMaterialList.hpp" +#include "TCastTo.hpp" + +namespace urde +{ + +CMaterialList MakeMaterialList() +{ + return CMaterialList(EMaterialTypes::Scannable, EMaterialTypes::Trigger, EMaterialTypes::NonSolidDamageable, + EMaterialTypes::ExcludeFromLineOfSightTest); +} + +CWallCrawlerSwarm::CWallCrawlerSwarm(TUniqueId uid, bool active, const std::string& name, const CEntityInfo& info, + const zeus::CVector3f&, const zeus::CTransform& xf, u32, const CAnimRes&, u32, u32, + u32, u32, u32, u32, const CDamageInfo&, const CDamageInfo&, float, float, float, + float, u32, u32, float, float, float, float, float, float, float, float, float, + u32, float, float, float, const CHealthInfo&, const CDamageVulnerability&, u32, + u32, const CActorParameters& aParams) +: CActor(uid, active, name, info, xf, CModelData::CModelDataNull(), MakeMaterialList(), aParams, kInvalidUniqueId) +{ +} + +void CWallCrawlerSwarm::Accept(IVisitor& visitor) { visitor.Visit(this); } +} diff --git a/Runtime/World/CWallCrawlerSwarm.hpp b/Runtime/World/CWallCrawlerSwarm.hpp index e69de29bb..f50a9c1ba 100644 --- a/Runtime/World/CWallCrawlerSwarm.hpp +++ b/Runtime/World/CWallCrawlerSwarm.hpp @@ -0,0 +1,63 @@ +#ifndef __URDE_CWALLCRAWLERSWARM_HPP__ +#define __URDE_CWALLCRAWLERSWARM_HPP__ + +#include "World/CActor.hpp" +#include "Collision/CCollisionSurface.hpp" + +namespace urde +{ +class CWallCrawlerSwarm : public CActor +{ +public: + class CBoid + { + zeus::CTransform x0_; + float x30_ = 0.f; + float x34_ = 0.f; + float x38_ = 0.f; + TUniqueId x3c_ = kInvalidUniqueId; + zeus::CColor x40_ = zeus::CColor(0.3f, 0.3f, 0.3f, 1.f); + u32 x44_ = 0; + float x48_ = 0.f; + float x4c_ = 0.f; + CCollisionSurface x50_ = CCollisionSurface(zeus::CVector3f(0.f, 0.f, 1.f), zeus::CVector3f(0.f, 1.f, 0.f), + zeus::CVector3f(1.f, 0.f, 0.f), -1); + union + { + struct + { + u32 x7c_unk1 : 8; + u32 x7c_unk2 : 10; + }; + u32 x7c_; + }; + + union + { + struct + { + bool x80_24_ : 1; + bool x80_25_ : 1; + bool x80_26_ : 1; + bool x80_27_ : 1; + bool x80_28_ : 1; + }; + u32 x80_; + }; + }; + + zeus::CAABox xe8_aabox = zeus::CAABox::skNullBox; + zeus::CVector3f x130_lastKilledOffset; +public: + CWallCrawlerSwarm(TUniqueId, bool, const std::string&, const CEntityInfo&, const zeus::CVector3f&, + const zeus::CTransform&, u32, const CAnimRes&, u32, u32, u32, u32, u32, u32, const CDamageInfo&, + const CDamageInfo&, float, float, float, float, u32, u32, float, float, float, float, float, + float, float, float, float, u32, float, float, float, const CHealthInfo&, const CDamageVulnerability&, + u32, u32, const CActorParameters&); + + void Accept(IVisitor &visitor); + zeus::CVector3f GetLastKilledOffset() const { return x130_lastKilledOffset; } +}; +} + +#endif // __URDE_CWALLCRAWLERSWARM_HPP__ diff --git a/Runtime/World/ScriptLoader.cpp b/Runtime/World/ScriptLoader.cpp index 3a2c52b9e..98e183675 100644 --- a/Runtime/World/ScriptLoader.cpp +++ b/Runtime/World/ScriptLoader.cpp @@ -48,6 +48,7 @@ #include "CScriptActorRotate.hpp" #include "CScriptSpecialFunction.hpp" #include "CScriptSwitch.hpp" +#include "CWallCrawlerSwarm.hpp" #include "CScriptAiJumpPoint.hpp" #include "CScriptColorModulate.hpp" #include "CRepulsor.hpp" @@ -666,30 +667,30 @@ CEntity* ScriptLoader::LoadSound(CStateManager& mgr, CInputStream& in, int propC return nullptr; SActorHead head = LoadActorHead(in, mgr); - s32 soundId = in.readInt32Big(); - bool b1 = in.readBool(); - float f1 = in.readFloatBig(); - float f2 = in.readFloatBig(); + bool active = in.readBool(); + float maxDistance = in.readFloatBig(); + float minDistance = in.readFloatBig(); float f3 = in.readFloatBig(); - u32 w2 = in.readUint32Big(); - u32 w3 = in.readUint32Big(); - u32 w4 = in.readUint32Big(); - u32 w5 = in.readUint32Big(); - bool b2 = in.readBool(); - bool b3 = in.readBool(); + u32 priority = in.readUint32Big(); + u32 maxVolume = in.readUint32Big(); + u32 minVolume = in.readUint32Big(); + u32 panning = in.readUint32Big(); + bool loop = in.readBool(); + bool persistent = in.readBool(); + bool triggered = in.readBool(); bool b4 = in.readBool(); - bool b5 = in.readBool(); + bool roomAcoustic = in.readBool(); bool b6 = in.readBool(); bool b7 = in.readBool(); - bool b8 = in.readBool(); - u32 w6 = in.readUint32Big(); + u32 w5 = in.readUint32Big(); if (soundId < 0) return nullptr; - return new CScriptSound(mgr.AllocateUniqueId(), head.x0_name, info, head.x10_transform, soundId, b1, f1, f2, f3, w2, - w3, w4, w5, w6, 0, b2, b3, b4, b5, b6, b7, b8, w6); + return new CScriptSound(mgr.AllocateUniqueId(), head.x0_name, info, head.x10_transform, soundId, active, + maxDistance, minDistance, f3, priority, maxVolume, 0, minVolume, panning, 0, loop, + persistent, triggered, b4, roomAcoustic, b6, b7, w5); } CEntity* ScriptLoader::LoadGenerator(CStateManager& mgr, CInputStream& in, int propCount, const CEntityInfo& info) @@ -703,8 +704,7 @@ CEntity* ScriptLoader::LoadGenerator(CStateManager& mgr, CInputStream& in, int p bool b1 = in.readBool(); bool b2 = in.readBool(); - zeus::CVector3f v1; - v1.readBig(in); + zeus::CVector3f v1 = zeus::CVector3f::ReadBig(in); bool b3 = in.readBool(); float f1 = in.readFloatBig(); @@ -836,7 +836,8 @@ CEntity* ScriptLoader::LoadSpawnPoint(CStateManager& mgr, CInputStream& in, int morphed = in.readBool(); return new CScriptSpawnPoint(mgr.AllocateUniqueId(), name, info, - ConvertEditorEulerToTransform4f(rotation, position), itemCounts, defaultSpawn, active, morphed); + ConvertEditorEulerToTransform4f(rotation, position), itemCounts, defaultSpawn, active, + morphed); } CEntity* ScriptLoader::LoadCameraHint(CStateManager& mgr, CInputStream& in, int propCount, const CEntityInfo& info) @@ -1739,7 +1740,52 @@ CEntity* ScriptLoader::LoadThardus(CStateManager& mgr, CInputStream& in, int pro CEntity* ScriptLoader::LoadWallCrawlerSwarm(CStateManager& mgr, CInputStream& in, int propCount, const CEntityInfo& info) { - return nullptr; + if (!EnsurePropertyCount(propCount, 39, "WallCrawlerSwarm")) + return nullptr; + + SScaledActorHead aHead = LoadScaledActorHead(in, mgr); + bool active = in.readBool(); + CActorParameters aParams = LoadActorParameters(in); + u32 w1 = in.readUint32Big(); + u32 w2 = in.readUint32Big(); + u32 w3 = in.readUint32Big(); + u32 w4 = in.readUint32Big(); + u32 w5 = in.readUint32Big(); + u32 w6 = in.readUint32Big(); + u32 w7 = in.readUint32Big(); + u32 w8 = in.readUint32Big(); + u32 w9 = in.readUint32Big(); + u32 w10 = in.readUint32Big(); + CDamageInfo dInfo1(in); + float f1 = in.readFloatBig(); + CDamageInfo dInfo2(in); + float f2 = in.readFloatBig(); + float f3 = in.readFloatBig(); + float f4 = in.readFloatBig(); + float f5 = in.readFloatBig(); + u32 w11 = in.readUint32Big(); + u32 w12 = in.readUint32Big(); + float f6 = in.readFloatBig(); + float f7 = in.readFloatBig(); + float f8 = in.readFloatBig(); + float f9 = in.readFloatBig(); + float f10 = in.readFloatBig(); + float f11 = in.readFloatBig(); + float f12 = in.readFloatBig(); + float f13 = in.readFloatBig(); + u32 w13 = in.readUint32Big(); + float f14 = in.readFloatBig(); + float f15 = in.readFloatBig(); + float f16 = in.readFloatBig(); + CHealthInfo hInfo(in); + CDamageVulnerability dVulns(in); + u32 w14 = in.readUint32Big(); + u32 w15 = in.readUint32Big(); + + return new CWallCrawlerSwarm(mgr.AllocateUniqueId(), active, aHead.x0_name, info, + aHead.x40_scale, aHead.x10_transform, w1, CAnimRes(w2, w3, {1.5f}, w4, true), w5, w6, + w7, w8, w9, w10, dInfo1, dInfo2, f1, f2, f3, f4, w11, w12, f5, f6, f7, f8, f9, f10, + f11, f12, f13, w13, f14, f15, f16, hInfo, dVulns, w14, w15, aParams); } CEntity* ScriptLoader::LoadAiJumpPoint(CStateManager& mgr, CInputStream& in, int propCount, const CEntityInfo& info) @@ -1798,8 +1844,8 @@ CEntity* ScriptLoader::LoadRoomAcoustics(CStateManager& mgr, CInputStream& in, i u32 _d = in.readUint32Big(); u32 _e = in.readUint32Big(); - return new CScriptRoomAcoustics(mgr.AllocateUniqueId(), name, info, a, b, c, d, e, f, g, h, i, j, - k, l, m, n, o, p, q, r, s, t, u, v, w, x, y, z, _a, _b, _c, _d, _e); + return new CScriptRoomAcoustics(mgr.AllocateUniqueId(), name, info, a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, + q, r, s, t, u, v, w, x, y, z, _a, _b, _c, _d, _e); } CEntity* ScriptLoader::LoadColorModulate(CStateManager& mgr, CInputStream& in, int propCount, const CEntityInfo& info) @@ -1821,8 +1867,7 @@ CEntity* ScriptLoader::LoadColorModulate(CStateManager& mgr, CInputStream& in, i bool b4 = in.readBool(); bool b5 = in.readBool(); bool active = in.readBool(); - return new CScriptColorModulate(mgr.AllocateUniqueId(), name, info, c1, c2, bm, f1, f2, b1, b2, b3, b4, b5, - active); + return new CScriptColorModulate(mgr.AllocateUniqueId(), name, info, c1, c2, bm, f1, f2, b1, b2, b3, b4, b5, active); } CEntity* ScriptLoader::LoadThardusRockProjectile(CStateManager& mgr, CInputStream& in, int propCount, @@ -1851,9 +1896,8 @@ CEntity* ScriptLoader::LoadStreamedAudio(CStateManager& mgr, CInputStream& in, i u32 oneShot = in.readUint32Big(); bool music = in.readBool(); - return new CScriptStreamedMusic(mgr.AllocateUniqueId(), info, name, - active, fileName, noStopOnDeactivate, - fadeIn, fadeOut, volume, !oneShot, music); + return new CScriptStreamedMusic(mgr.AllocateUniqueId(), info, name, active, fileName, noStopOnDeactivate, fadeIn, + fadeOut, volume, !oneShot, music); } CEntity* ScriptLoader::LoadRepulsor(CStateManager& mgr, CInputStream& in, int propCount, const CEntityInfo& info) @@ -1902,8 +1946,8 @@ CEntity* ScriptLoader::LoadRadialDamage(CStateManager& mgr, CInputStream& in, in zeus::CTransform xf = ConvertEditorEulerToTransform4f(zeus::CVector3f::skZero, center); return new CScriptSpecialFunction( - mgr.AllocateUniqueId(), name, info, xf, CScriptSpecialFunction::ESpecialFunction::RadialDamage, "", radius, - 0.f, 0.f, 0.f, zeus::CVector3f::skZero, zeus::CColor::skBlack, active, dInfo, -1, -1, -1, -1, -1, -1); + mgr.AllocateUniqueId(), name, info, xf, CScriptSpecialFunction::ESpecialFunction::RadialDamage, "", radius, 0.f, + 0.f, 0.f, zeus::CVector3f::skZero, zeus::CColor::skBlack, active, dInfo, -1, -1, -1, -1, -1, -1); } CEntity* ScriptLoader::LoadCameraPitchVolume(CStateManager& mgr, CInputStream& in, int propCount,