[Remove] Some bits of ODE collision detection from ModelBody.

[Add] Some Accessor/Mutator's for rotations/position in geoms and
Dynamic bodies.
This commit is contained in:
Rtch90 2018-04-06 22:38:48 +01:00
parent 37d3c3a16b
commit e8af5d4678
8 changed files with 44 additions and 106 deletions

View File

@ -14,6 +14,12 @@ Geom::Geom(GeomTree* geomtree) {
m_data = 0;
}
matrix4x4d Geom::GetRotation(void) const {
matrix4x4d m = GetTransform();
m[12] = 0; m [13] = 0; m[14] = 0;
return m;
}
void Geom::MoveTo(const matrix4x4d& m) {
m_orientIdx = !m_orientIdx;
m_orient[m_orientIdx] = m;

View File

@ -12,8 +12,9 @@ public:
Geom(GeomTree*);
void MoveTo(const matrix4x4d& m);
void MoveTo(const matrix4x4d& m, const vector3d pos);
const matrix4x4d& GetInvTransform(void) { return m_invOrient; }
const matrix4x4d& GetTransform(void) { return m_orient[m_orientIdx]; }
const matrix4x4d& GetInvTransform(void) const { return m_invOrient; }
const matrix4x4d& GetTransform(void) const { return m_orient[m_orientIdx]; }
matrix4x4d GetRotation(void) const;
vector3d GetPosition(void) const;
void Enable(void) { m_active = true; }
void Disable(void) {m_active = false; }

View File

@ -27,6 +27,22 @@ void DynamicBody::Load(void) {
SetVelocity(rd_vector3d());
}
void DynamicBody::SetPosition(vector3d p) {
dBodySetPosition(m_body, p.x, p.y, p.z);
ModelBody::SetPosition(p);
}
void DynamicBody::TimeStepUpdate(const float timeStep) {
matrix4x4d t;
GetRotMatrix(t);
const dReal* v = dBodyGetPosition(m_body);
t[12] = v[0];
t[13] = v[1];
t[14] = v[2];
TriMeshUpdateLastPos(t);
}
void DynamicBody::Enable(void) {
ModelBody::Enable();
dBodyEnable(m_body);

View File

@ -14,6 +14,7 @@ public:
virtual void SetRotMatrix(const matrix4x4d& r);
virtual void GetRotMatrix(matrix4x4d& m);
virtual void SetVelocity(vector3d v);
virtual void SetPosition(vector3d p);
virtual vector3d GetVelocity(void);
vector3d GetAngVelocity(void);
void SetAngVelocity(vector3d v);
@ -24,6 +25,7 @@ public:
virtual void Disable(void);
virtual void Enable(void);
virtual double GetMass(void) const { return m_mass.mass; }
virtual void TimeStepUpdate(const float timeStep);
dBodyID m_body;
dMass m_mass;

View File

@ -10,16 +10,13 @@
#include "collider/collider.h"
ModelBody::ModelBody(void): Body() {
m_triMeshLastMatrixIndex = 0;
m_collMeshSet = 0;
m_geom = 0;
}
ModelBody::~ModelBody(void) {
SetFrame(0); /* Will remove geom from frame if necessary. */
for(unsigned int i = 0; i < geoms.size(); i++) {
dGeomDestroy(geoms[i]);
}
delete m_geom;
}
void ModelBody::Save(void) {
@ -33,21 +30,14 @@ void ModelBody::Load(void) {
}
void ModelBody::Disable(void) {
for(unsigned int i = 0; i < geoms.size(); i++) {
dGeomDisable(geoms[i]);
}
m_geom->Disable();
}
void ModelBody::Enable(void) {
for(unsigned int i = 0; i < geoms.size(); i++) {
dGeomEnable(geoms[i]);
}
m_geom->Enable();
}
void ModelBody::GeomsSetBody(dBodyID body) {
for(unsigned int i = 0; i < geoms.size(); i++) {
dGeomSetBody(geoms[i], body);
}
}
void ModelBody::GetAabb(Aabb& aabb) {
@ -55,22 +45,12 @@ void ModelBody::GetAabb(Aabb& aabb) {
}
void ModelBody::SetModel(int sbreModel) {
assert(geoms.size() == 0);
assert(m_geom == 0);
CollMeshSet* mset = GetModelCollMeshSet(sbreModel);
m_geom = new Geom(mset->m_geomTree);
m_geom->SetUserData((void*)this);
geomColl.resize(mset->numMeshParts);
geoms.resize(mset->numMeshParts);
for(int i = 0; i < mset->numMeshParts; i++) {
geoms[i] = dCreateTriMesh(0, mset->meshParts[i], NULL, NULL, NULL);
geomColl[i].parent = this;
geomColl[i].flags = mset->meshInfo[i].flags;
dGeomSetData(geoms[i], static_cast<Object*>(&geomColl[i]));
}
m_collMeshSet = mset;
}
@ -79,109 +59,50 @@ void ModelBody::SetPosition(vector3d p) {
GetRotMatrix(m);
m_geom->MoveTo(m, p);
m_geom->MoveTo(m, p);
for(unsigned int i = 0; i < geoms.size(); i++) {
dGeomSetPosition(geoms[i], p.x, p.y, p.z);
}
}
vector3d ModelBody::GetPosition(void) const {
const dReal* pos = dGeomGetPosition(geoms[0]);
return vector3d(pos[0], pos[1], pos[2]);
return m_geom->GetPosition();
}
double ModelBody::GetRadius(void) const {
/* Calculate single AABB containing all geoms. */
dReal aabbAll[6] = {
std::numeric_limits<double>::max(),
std::numeric_limits<double>::min(),
std::numeric_limits<double>::max(),
std::numeric_limits<double>::min(),
std::numeric_limits<double>::max(),
std::numeric_limits<double>::min()
};
for(size_t i = 0; i < geoms.size(); ++i) {
dReal aabbGeom[6];
dGeomGetAABB(geoms[i], aabbGeom);
aabbAll[0] = std::min(aabbAll[0], aabbGeom[0]);
aabbAll[1] = std::max(aabbAll[1], aabbGeom[1]);
aabbAll[2] = std::min(aabbAll[2], aabbGeom[2]);
aabbAll[3] = std::max(aabbAll[3], aabbGeom[3]);
aabbAll[4] = std::min(aabbAll[4], aabbGeom[4]);
aabbAll[5] = std::max(aabbAll[5], aabbGeom[5]);
}
Aabb aabb = m_geom->GetGeomTree()->GetAabb();
/* Return size of largest dimension. */
return std::max(aabbAll[1] - aabbAll[0], std::max(aabbAll[3] - aabbAll[2], aabbAll[5] - aabbAll[4]));
return std::max(aabb.max.x - aabb.min.x, std::max(aabb.max.y, aabb.max.z - aabb.min.z));
}
void ModelBody::SetRotMatrix(const matrix4x4d& r) {
dMatrix3 _m;
r.SaveToOdeMatrix(_m);
for(unsigned int i = 0; i < geoms.size(); i++) {
dGeomSetRotation(geoms[i], _m);
}
vector3d pos = m_geom->GetPosition();
m_geom->MoveTo(r, pos);
m_geom->MoveTo(r, pos);
}
void ModelBody::GetRotMatrix(matrix4x4d& m) const {
m.LoadFromOdeMatrix(dGeomGetRotation(geoms[0]));
m = m_geom->GetRotation();
}
void ModelBody::TransformToModelCoords(const Frame* camFrame) {
const vector3d pos = GetPosition();
const dReal* r = dGeomGetRotation(geoms[0]);
matrix4x4d m, m2;
matrix4x4d m = m_geom->GetTransform();
matrix4x4d m2;
Frame::GetFrameTransform(GetFrame(), camFrame, m2);
m[ 0] = r[ 0]; m[ 1] = r[ 4]; m[ 2] = r[ 8]; m[ 3] = 0;
m[ 4] = r[ 1]; m[ 5] = r[ 5]; m[ 6] = r[ 9]; m[ 7] = 0;
m[ 8] = r[ 2]; m[ 9] = r[ 6]; m[10] = r[10]; m[11] = 0;
m[12] = pos.x; m[13] = pos.y; m[14] = pos.z; m[15] = 1;
m = m2 * m;
glMultMatrixd(&m[0]);
}
void ModelBody::SetFrame(Frame* f) {
if(GetFrame()) {
for(unsigned int i = 0; i < geoms.size(); i++) {
GetFrame()->_RemoveGeom(geoms[i]);
}
GetFrame()->RemoveGeom(m_geom);
}
Body::SetFrame(f);
if(f) {
for(unsigned int i = 0; i < geoms.size(); i++) {
f->_AddGeom(geoms[i]);
}
f->AddGeom(m_geom);
}
}
void ModelBody::TriMeshUpdateLastPos(void) {
/* ODE tri mesh likes to know our old position. */
const dReal* r = dGeomGetRotation(geoms[0]);
vector3d pos = GetPosition();
dReal* t = m_triMeshTrans + 16*m_triMeshLastMatrixIndex;
t[ 0] = r[0]; t[1] = r[1]; t[ 2] = r[ 2]; t[ 3] = 0;
t[ 4] = r[4]; t[5] = r[5]; t[ 6] = r[ 6]; t[ 7] = 0;
t[ 8] = r[8]; t[9] = r[9]; t[10] = r[10]; t[11] = 0;
t[12] = pos.x; t[13] = pos.y; t[14] = pos.z; t[15] = 1;
/* REESTED! */
matrix4x4d wtf;
memcpy(&wtf[0], t, 16*sizeof(double));
m_geom->MoveTo(wtf);
m_triMeshLastMatrixIndex = !m_triMeshLastMatrixIndex;
for(unsigned int i = 0; i < geoms.size(); i++) {
dGeomTriMeshSetLastTransform(geoms[i], *(dMatrix4*)(m_triMeshTrans + 16*m_triMeshLastMatrixIndex));
}
void ModelBody::TriMeshUpdateLastPos(matrix4x4d currentTransform) {
m_geom->MoveTo(currentTransform);
}
void ModelBody::RenderSbreModel(const Frame* camFrame, int model, ObjParams* params) {
@ -211,7 +132,7 @@ void ModelBody::RenderSbreModel(const Frame* camFrame, int model, ObjParams* par
pos = frameTrans * pos;
Vector p; p.x = pos.x; p.y = pos.y; p.z = -pos.z;
matrix4x4d rot;
rot.LoadFromOdeMatrix(dGeomGetRotation(geoms[0]));
GetRotMatrix(rot);
frameTrans.ClearToRotOnly();
rot = frameTrans * rot;
Matrix m;

View File

@ -28,7 +28,7 @@ public:
virtual void Enable(void);
void GetAabb(Aabb& aabb);
void TriMeshUpdateLastPos(void);
void TriMeshUpdateLastPos(matrix4x4d currentTransform);
void SetModel(int sbreModel);
void RenderSbreModel(const Frame* camFrame, int model, ObjParams* params);
@ -42,12 +42,8 @@ public:
protected:
virtual void Save(void);
virtual void Load(void);
std::vector<GeomBit> geomColl;
private:
CollMeshSet* m_collMeshSet;
std::vector<dGeomID> geoms;
Geom* m_geom;
dReal m_triMeshTrans[32];
int m_triMeshLastMatrixIndex;
};

View File

@ -252,9 +252,9 @@ void Ship::TestLanded(void) {
}
void Ship::TimeStepUpdate(const float timeStep) {
DynamicBody::TimeStepUpdate(timeStep);
m_dockingTimer = (m_dockingTimer-timeStep > 0 ? m_dockingTimer-timeStep : 0);
/* ODE tri mesh likes to know our old position. */
TriMeshUpdateLastPos();
m_launchLockTimeout -= timeStep;
if(m_launchLockTimeout < 0) m_launchLockTimeout = 0;

View File

@ -52,7 +52,6 @@ void SpaceStation::GetDockingSurface(CollMeshSet* mset, int midx) {
assert(m_numPorts <= MAX_DOCKING_PORTS);
assert((minfo->flags & 0xf) < MAX_DOCKING_PORTS);
assert(minfo->flags & 0x10);
assert(minfo->numTris);
dport->center = vector3d(0.0);
@ -97,11 +96,8 @@ void SpaceStation::Init(void) {
SetModel(sbreModel);
CollMeshSet* mset = GetModelCollMeshSet(sbreModel);
for(unsigned int i = 0; i < geomColl.size(); i++) {
if(geomColl[i].flags & 0x10) {
/* Docking surface. */
GetDockingSurface(mset, i);
}
for(int i = 0; i < mset->numMeshParts; i++) {
if(mset->meshInfo[i].flags & 0x10) GetDockingSurface(mset, i);
}
}