My level's mesh is in an .obj, and I'm trying to load it into a btBvhTriangleMeshShape. I've had some success so far, with half the level working almost perfectly. My problem is the MeshShape doesn't seem to exist below x=0. If I step too far over x, I just end up in an infinite fall.
Here's some code. The vectors seem to fill up perfectly, and I don't see anything wrong with moving the data into the arrays. I tried to mimic the ConcavePhysics demo as closely as possible.
Code: Select all
struct CollisionVertex
{
float x, y, z;
};
//Parse .obj file
ifstream objfile;
objfile.open(file);
if(!objfile.bad())
{
//Temp vectors to be filled with vert/index data
vector<CollisionVertex> verts = vector<CollisionVertex>();
vector<int> inds = vector<int>();
while(!objfile.eof())
{
string line = "";
getline(objfile, line);
vector<string> strs;
boost::split(strs, line, boost::is_any_of(" "));
vector<string> cleanstrs = vector<string>();
for(int i=0;i<(int)strs.size();i++)
{
if(strs[i] != "") cleanstrs.push_back(strs[i]);
}
strs = cleanstrs;
if(strs.size() == 4)
{
string type = strs[0];
if(type == "v")
{
CollisionVertex vert;
vert.x = (float)atof(strs[1].c_str());
vert.y = (float)atof(strs[2].c_str());
vert.z = (float)atof(strs[3].c_str());
verts.push_back(vert);
}
else if(type == "f")
{
inds.push_back(atoi(strs[1].c_str()));
inds.push_back(atoi(strs[2].c_str()));
inds.push_back(atoi(strs[3].c_str()));
}
}
}
objfile.close();
int totalTris = (int)(inds.size() / 3);
int indexStride = 3*sizeof(int);
int vertStride = sizeof(btVector3);
gVertices = new btVector3[verts.size()];
gIndices = new int[inds.size()];
for(int v=0;v<(int)verts.size();v++)
{
gVertices[v].setValue(verts[v].x, verts[v].y, verts[v].z);
}
for(int i=0;i<(int)inds.size();i++)
{
gIndices[i] = inds[i];
}
vertexarray = new btTriangleIndexVertexArray(totalTris, gIndices, indexStride, verts.size(), (btScalar*)&gVertices[0].x(), vertStride);
btVector3 aabbMin(-1000,-1000,-1000),aabbMax(1000,1000,1000);
trimeshShape = new btBvhTriangleMeshShape(vertexarray,true);//,aabbMin,aabbMax); //runtime error if these are included
}
The shape gets passed to here, where it's used in the RigidBody.
Code: Select all
//Level collision
level_collision_mesh = new CollisionMesh("D:/Programming/Islands/levels/test/comp/testlevel_collision.obj");
level_shape = level_collision_mesh->trimeshShape;
level_motion = new btDefaultMotionState(btTransform(btQuaternion(0,0,0,1), btVector3(0,0,0)));
level = new btRigidBody(0, level_motion, level_shape);
//Player collision
player_shape = new btSphereShape(1);
player_motion = new btDefaultMotionState(btTransform(btQuaternion(0,0,0,1), btVector3(0,60,0)));
player = new btRigidBody(10, player_motion, player_shape);
//Create world
btVector3 worldMin(-1000,-1000,-1000);
btVector3 worldMax(1000,1000,1000);
collisionConfiguration = new btDefaultCollisionConfiguration();
dispatcher = new btCollisionDispatcher(collisionConfiguration);
broadphase = new btAxisSweep3(worldMin,worldMax);
solver = new btSequentialImpulseConstraintSolver;
world = new btDiscreteDynamicsWorld(dispatcher, broadphase, solver, collisionConfiguration);
world->setGravity(btVector3(0,-10,0));
world->addRigidBody(level);
world->addRigidBody(player);
Thanks for taking the time to read, hopefully someone can help out!