NTRT Simulator  v1.1
 All Classes Namespaces Files Functions Variables Typedefs Friends Pages
tgHillyGround.cpp
Go to the documentation of this file.
1 
26 //This Module
27 #include "tgHillyGround.h"
28 
29 //Bullet Physics
30 #include "BulletCollision/CollisionShapes/btBoxShape.h"
31 #include "BulletCollision/CollisionShapes/btTriangleIndexVertexArray.h"
32 #include "BulletCollision/CollisionShapes/btBvhTriangleMeshShape.h"
33 #include "BulletDynamics/Dynamics/btRigidBody.h"
34 #include "LinearMath/btDefaultMotionState.h"
35 #include "LinearMath/btTransform.h"
36 
37 // The C++ Standard Library
38 #include <cassert>
39 
40 tgHillyGround::Config::Config(btVector3 eulerAngles,
41  btScalar friction,
42  btScalar restitution,
43  btVector3 size,
44  btVector3 origin,
45  size_t nx,
46  size_t ny,
47  double margin,
48  double triangleSize,
49  double waveHeight,
50  double offset) :
51  m_eulerAngles(eulerAngles),
52  m_friction(friction),
53  m_restitution(restitution),
54  m_size(size),
55  m_origin(origin),
56  m_nx(nx),
57  m_ny(ny),
58  m_margin(margin),
59  m_triangleSize(triangleSize),
60  m_waveHeight(waveHeight),
61  m_offset(offset)
62 {
63  assert((m_friction >= 0.0) && (m_friction <= 1.0));
64  assert((m_restitution >= 0.0) && (m_restitution <= 1.0));
65  assert((m_size[0] >= 0.0) && (m_size[1] >= 0.0) && (m_size[2] >= 0.0));
66  assert(m_nx > 0);
67  assert(m_ny > 0);
68  assert(m_margin >= 0.0);
69  assert(m_triangleSize >= 0.0);
70  assert(m_waveHeight >= 0.0);
71  assert(m_offset >= 0.0);
72 }
73 
75  m_config(Config())
76 {
77  // @todo make constructor aux to avoid repeated code
78  pGroundShape = hillyCollisionShape();
79 }
80 
82  m_config(config)
83 {
84  pGroundShape = hillyCollisionShape();
85 }
86 
88 {
89  const btScalar mass = 0.0;
90 
91  btTransform groundTransform;
92  groundTransform.setIdentity();
93  groundTransform.setOrigin(m_config.m_origin);
94 
95  btQuaternion orientation;
96  orientation.setEuler(m_config.m_eulerAngles[0], // Yaw
97  m_config.m_eulerAngles[1], // Pitch
98  m_config.m_eulerAngles[2]); // Roll
99  groundTransform.setRotation(orientation);
100 
101  // Using motionstate is recommended
102  // It provides interpolation capabilities, and only synchronizes 'active' objects
103  btDefaultMotionState* const pMotionState =
104  new btDefaultMotionState(groundTransform);
105 
106  const btVector3 localInertia(0, 0, 0);
107 
108  btRigidBody::btRigidBodyConstructionInfo const rbInfo(mass, pMotionState, pGroundShape, localInertia);
109 
110  btRigidBody* const pGroundBody = new btRigidBody(rbInfo);
111 
112  assert(pGroundBody);
113  return pGroundBody;
114 }
115 
117  btCollisionShape * pShape = 0;
118  // The number of vertices in the mesh
119  // Hill Paramenters: Subject to Change
120  const size_t vertexCount = m_config.m_nx * m_config.m_ny;
121 
122  if (vertexCount > 0) {
123  // The number of triangles in the mesh
124  const size_t triangleCount = 2 * (m_config.m_nx - 1) * (m_config.m_ny - 1);
125 
126  // A flattened array of all vertices in the mesh
127  btVector3 * const vertices = new btVector3[vertexCount];
128 
129  // Supplied by the derived class
130  setVertices(vertices);
131  // A flattened array of indices for each corner of each triangle
132  int *indices = new int[triangleCount * 3];
133 
134  // Supplied by the derived class
135  setIndices(indices);
136 
137  // Create the mesh object
138  btTriangleIndexVertexArray* const pMesh =
139  createMesh(triangleCount, indices, vertexCount, vertices);
140 
141  // Create the shape object
142  pShape = createShape(pMesh);
143 
144  // Set the margin
145  pShape->setMargin(m_config.m_margin);
146  // DO NOT deallocate vertices, indices or pMesh! The shape owns them.
147  }
148 
149  assert(pShape);
150  return pShape;
151 }
152 
153 btTriangleIndexVertexArray *tgHillyGround::createMesh(size_t triangleCount, int indices[], size_t vertexCount, btVector3 vertices[]) {
154  const int vertexStride = sizeof(btVector3);
155  const int indexStride = 3 * sizeof(int);
156 
157  btTriangleIndexVertexArray* const pMesh =
158  new btTriangleIndexVertexArray(triangleCount,
159  indices,
160  indexStride,
161  vertexCount,
162  (btScalar*) &vertices[0].x(),
163  vertexStride);
164  return pMesh;
165 }
166 
167 btCollisionShape *tgHillyGround::createShape(btTriangleIndexVertexArray *pMesh) {
168  const bool useQuantizedAabbCompression = true;
169  btCollisionShape *const pShape =
170  new btBvhTriangleMeshShape(pMesh, useQuantizedAabbCompression);
171  return pShape;
172 }
173 
174 void tgHillyGround::setVertices(btVector3 vertices[]) {
175  for (size_t i = 0; i < m_config.m_nx; i++)
176  {
177  for (size_t j = 0; j < m_config.m_ny; j++)
178  {
179  const btScalar x = (i - (m_config.m_nx * 0.5)) * m_config.m_triangleSize;
180  const btScalar y = (m_config.m_waveHeight * sinf((float)i) * cosf((float)j) +
181  m_config.m_offset);
182  const btScalar z = (j - (m_config.m_ny * 0.5)) * m_config.m_triangleSize;
183  vertices[i + (j * m_config.m_nx)].setValue(x, y, z);
184  }
185  }
186 }
187 
188 void tgHillyGround::setIndices(int indices[]) {
189  int index = 0;
190  for (std::size_t i = 0; i < m_config.m_nx - 1; i++)
191  {
192  for (std::size_t j = 0; j < m_config.m_ny - 1; j++)
193  {
194  indices[index++] = (j * m_config.m_nx) + i;
195  indices[index++] = (j * m_config.m_nx) + i + 1;
196  indices[index++] = ((j + 1) * m_config.m_nx) + i + 1;
197 
198  indices[index++] = (j * m_config.m_nx) + i;
199  indices[index++] = ((j + 1) * m_config.m_nx) + i + 1;
200  indices[index++] = ((j + 1) * m_config.m_nx) + i;
201  }
202  }
203 }
204 
Contains the definition of class tgHillyGround.
virtual btRigidBody * getGroundRigidBody() const
btCollisionShape * hillyCollisionShape()