Fix issue in Rocket.lua script.
[Cafu-Engine.git] / Common / CompGameEntity.cpp
blob400b783362a7878282e663f841f994a666af483a
1 /*
2 Cafu Engine, http://www.cafu.de/
3 Copyright (c) Carsten Fuchs and other contributors.
4 This project is licensed under the terms of the MIT license.
5 */
7 #include "CompGameEntity.hpp"
8 #include "World.hpp"
9 #include "ClipSys/ClipModel.hpp"
10 #include "ClipSys/CollisionModel_static.hpp"
11 #include "GameSys/World.hpp"
12 #include "SceneGraph/BspTreeNode.hpp"
16 * Note that as an alternative to using entity IDs as indices into WorldT::m_StaticEntityData[] as has been
17 * introduced in the revisions of 2013-07-26, it might be possible to let this class have a reference to the
18 * WorldT::m_StaticEntityData[] array, add an `unsigned int` member for the world file index, and to
19 * serialize/deserialize this index as part of the component. (`ComponentBaseT::Serialize()` would have to
20 * call a virtual `DoSerialize()` method that we had to override here.)
21 * This would liberate the entity ID from the requirements of double-purpose use, and would allow us to
22 * actually *copy* entities with associated world file information. But is it worth the effort?
23 * See the revisions of 2013-07-26 for additional details.
26 CompGameEntityT::CompGameEntityT(StaticEntityDataT* SED)
27 : m_StaticEntityData(SED ? SED : new StaticEntityDataT()),
28 m_DeleteSED(SED == NULL),
29 m_ClipModel(NULL),
30 m_ClipPrevOrigin(),
31 m_ClipPrevQuat()
36 CompGameEntityT::CompGameEntityT(const CompGameEntityT& Comp)
37 : m_StaticEntityData(new StaticEntityDataT()),
38 m_DeleteSED(true),
39 m_ClipModel(NULL),
40 m_ClipPrevOrigin(),
41 m_ClipPrevQuat()
43 // The problem with copying CompGameEntityT instances is that the
44 // m_StaticEntityData cannot be copied -- see the /*...*/ comment above.
45 // Therefore, make sure that only such instances are copied that use
46 // "dummy" StaticEntityDataT's anyway.
47 assert(Comp.m_StaticEntityData->m_BspTree == NULL || Comp.m_StaticEntityData->m_BspTree->Nodes.Size() == 0);
48 assert(Comp.m_StaticEntityData->m_CollModel == NULL);
52 CompGameEntityT::~CompGameEntityT()
54 delete m_ClipModel;
55 m_ClipModel = NULL;
57 if (m_DeleteSED)
58 delete m_StaticEntityData;
62 CompGameEntityT* CompGameEntityT::Clone() const
64 return new CompGameEntityT(*this);
68 void CompGameEntityT::UpdateDependencies(cf::GameSys::EntityT* Entity)
70 if (GetEntity() != Entity)
72 delete m_ClipModel;
73 m_ClipModel = NULL;
76 ComponentBaseT::UpdateDependencies(Entity);
78 UpdateClipModel();
82 BoundingBox3fT CompGameEntityT::GetCullingBB() const
84 if (m_StaticEntityData->m_BspTree)
85 return m_StaticEntityData->m_BspTree->GetBoundingBox().AsBoxOfFloat();
87 return BoundingBox3fT();
91 void CompGameEntityT::DoDeserialize(cf::Network::InStreamT& Stream, bool IsIniting)
93 // Deserialization may have updated our origin or orientation,
94 // so we have to update the clip model.
95 UpdateClipModel();
99 void CompGameEntityT::DoServerFrame(float t)
101 // TODO:
102 // This should actually be in some PostThink() method, so that we can be sure that
103 // all behaviour and physics scripts (that possibly alter the origin and orientation)
104 // have already been run when we update the clip model.
105 // (Same is true for the clip model in the ComponentCollisionModelT class.)
106 UpdateClipModel();
110 void CompGameEntityT::UpdateClipModel()
112 const bool IsNewClipModel = (m_ClipModel == NULL);
114 if (!m_ClipModel)
116 if (!m_StaticEntityData->m_CollModel) return;
117 if (!GetEntity()) return;
118 if (GetEntity()->GetID() == 0) return; // The world's collision model is already handled in the clip world!
119 if (!GetEntity()->GetWorld().GetClipWorld()) return;
121 m_ClipModel = new cf::ClipSys::ClipModelT(*GetEntity()->GetWorld().GetClipWorld());
123 m_ClipModel->SetCollisionModel(m_StaticEntityData->m_CollModel);
124 m_ClipModel->SetOwner(this);
127 // Has the origin or orientation changed since we last registered clip model? If so, re-register!
128 const Vector3fT o = GetEntity()->GetTransform()->GetOriginWS();
129 const cf::math::QuaternionfT q = GetEntity()->GetTransform()->GetQuatWS();
131 if (IsNewClipModel || o != m_ClipPrevOrigin || q != m_ClipPrevQuat)
133 m_ClipModel->SetOrigin(o.AsVectorOfDouble());
134 m_ClipModel->SetOrientation(cf::math::Matrix3x3dT(cf::math::QuaterniondT(q.x, q.y, q.z, q.w)));
135 m_ClipModel->Register();
137 m_ClipPrevOrigin = o;
138 m_ClipPrevQuat = q;