我正在编写一个角色动画渲染引擎,它使用Bullet Physics作为物理模拟引擎。
序列将在屏幕上没有模型的情况下开始,然后将动画分配给该模型,模型将移动到动画的第0帧,引擎将开始使用动画渲染模型。 / p>
在第0帧初始化刚体时,在角色模型上重新定位刚体的正确方法是什么?
目前我正在使用此代码,在将动画分配给模型并将骨骼移动到第0帧位置后立即调用该代码:
_world->removeRigidBody(_body);
bool k = (_type == Kinematics);
_body->setCollisionFlags(_body->getCollisionFlags() & ~btCollisionObject::CF_NO_CONTACT_RESPONSE);
btTransform tr = BulletPhysics::ConvertD3DXMatrix(&(_bone->getCombinedTrans()));
tr *= _trans;
_body->setCenterOfMassTransform(tr);
_body->clearForces();
_body->setLinearVelocity(btVector3(0,0,0));
_body->setAngularVelocity(btVector3(0,0,0));
_world->addRigidBody(_body, _groupID, _groupMask);
问题在于,有时这是有效的,有时则不然。举个例子,拿一个模特的裙子。有时它会出现在自然位置,有时会略微错位并且会落到位,有时会显示出完全夹在身体上,好像碰撞被关闭了,有些力量将它推向那个方向。这在大多数情况下都有意义,因为在测试动画中我使用模型的初始位置位于屏幕的中心,但动画从屏幕的左侧开始。有谁知道如何解决这个问题?
我知道裙子上的骨头不是问题,因为我关闭了物理并迫使它每帧手动更新骨骼位置,并且整个动画中的所有内容都处于正确的位置。
编辑:我也有约束,可能是造成这种情况的原因吗?答案 0 :(得分:0)
我无法告诉你移动刚体时导致异常结果的原因,但我绝对可以同情!
为了解决这个问题,您需要做三件事:
答案 1 :(得分:0)
经过测试的简短代码段通过将刚体的运动状态更新为新的位置和方向,并消除了作用在其上的所有速度和力,有效地传送了刚体。
void teleport(btVector3 position, btQuaternion& orientation) const {
btTransform transform;
transform.setIdentity();
transform.setOrigin(position);
transform.setRotation(orientation);
m_rigidBodyVehicle->setWorldTransform(transform);
m_rigidBodyVehicle->getMotionState()->setWorldTransform(transform);
m_rigidBodyVehicle->setLinearVelocity(btVector3(0.0f, 0.0f, 0.0f));
m_rigidBodyVehicle->setAngularVelocity(btVector3(0.0f, 0.0f, 0.0f));
m_rigidBodyVehicle->clearForces();
}