我正在努力通过一次性学习Java和子弹物理来战斗。很可能有点太多了,但我喜欢挑战。
到目前为止,我已经学会了如何导入g3db对象,将bullet物理应用于它们并使用以下代码在屏幕上与它们进行交互:
assets = new AssetManager();
assets.load("globe.g3db", Model.class);
assets.load("crate.g3db", Model.class);
assets.finishLoading();
Model model = assets.get("globe.g3db", Model.class);
ModelInstance inst = new ModelInstance(model);
inst.transform.trn(0, 20, 0);
btRigidBody body;
btSphereShape sh = new btSphereShape(1);
sh.calculateLocalInertia(1, new Vector3(0,0,0));
body = new btRigidBody(new btRigidBody.btRigidBodyConstructionInfo(3, new btDefaultMotionState(inst.transform), sh));
body.setUserValue(Minstances.size);
body.proceedToTransform(inst.transform);
motionState = new MyMotionState();
motionState.transform = inst.transform;
body.setMotionState(motionState);
dynamicsWorld.addRigidBody(body );
Minstances.add(inst);
这样可以正常工作,如果我把它放在地面以上它会落在地上,然而当它移动时它会滑动而不是滚动。 有一个简单的解决方法吗?
答案 0 :(得分:1)
要允许物理身体滚动,您需要计算其局部惯性并将其提供给施工信息。在您的代码中,您几乎正确地做到了。
方法
btCollisionShape.calculateLocalInertia(float mass, Vector3 inertia)
确实计算了局部惯性,但将其存储在第二个参数'Vector3 inertia'中。没有对btCollisionShape
本身进行任何更改。
获得惯性矢量后,需要将其传递给
btRigidBodyConstructionInfo(float mass, btMotionState motionState, btCollisionShape collisionShape, Vector3 localInertia)
作为最后一个论点。
正确的代码应如下所示:
btRigidBody body;
btSphereShape sh = new btSphereShape(1);
Vector3 inertia = new Vector3(0,0,0);
sh.calculateLocalInertia(1, inertia);
body = new btRigidBody(new btRigidBody.btRigidBodyConstructionInfo(3, new btDefaultMotionState(inst.transform), sh, inertia));
执行模拟不需要局部惯性,但没有它,所有施加在物体上的力都被视为中心力,因此不会影响角速度。
答案 1 :(得分:0)
你需要读出并设置旋转,现在你正在阅读\应用翻译。
创建一个新的四元数并获取xyzw值并将它们应用于您的对象。
类似这样的东西(c ++代码,但你可以在java中轻松地做同样的事情):
btTransform trans;
Quat myquat;
yourBulletDynamicObject->getMotionState()->getWorldTransform(trans);
btQuaternion rot = trans.getRotation();
myquat.w = rot.w();
myquat.x = rot.x();
myquat.y = rot.z();
myquat.z = rot.y();
将myquat设置回你的对象。