首页 > 技术文章 > Bullet 学习笔记之实例 VolumetricDeformable (一)

wghou09 2020-06-21 21:46 原文

参照 Bullet Physics 官方例程 VolumetricDeformable,梳理软体形变仿真流程。


0 环境搭建

仿真场景类为 btDeformableMultiBodyDynamicsWorld ,碰撞检测 broadphase 使用类 btDbvtBroadphase 完成,碰撞检测 narrowphase 使用类 btSoftBodyRigidBodyCollisionConfigurationbtCollisionDispatcher 完成。软体 solver 使用 btDeformableBodySolver ,约束求解使用 btDeformableMultiBodyConstraintSolver

仿真场景搭建部分代码:

///collision configuration contains default setup for memory, collision setup
m_collisionConfiguration = new btSoftBodyRigidBodyCollisionConfiguration();

///use the default collision dispatcher. For parallel processing you can use a diffent dispatcher (see Extras/BulletMultiThreaded)
m_dispatcher = new btCollisionDispatcher(m_collisionConfiguration);

m_broadphase = new btDbvtBroadphase();
btDeformableBodySolver* deformableBodySolver = new btDeformableBodySolver();

btDeformableMultiBodyConstraintSolver* sol = new btDeformableMultiBodyConstraintSolver();
sol->setDeformableSolver(deformableBodySolver);
m_solver = sol;

m_dynamicsWorld = new btDeformableMultiBodyDynamicsWorld(m_dispatcher, m_broadphase, sol, m_collisionConfiguration, deformableBodySolver);

1 初始化

1.1 新建软体对象

通过函数 btSoftBodyHelpers::CreateFromTetGenData(...) 建立了 btSoftBody 对象。新建及初始化 btSoftBody 的过程大致为:

(1) new 新的对象

(2) 新建碰撞对象 btSoftBody::m_collisionShape = new btSoftBodyCollisionShape(this);

(3) 添加软体对象中的节点 btSoftBody::m_nodes

在这个过程中,还会初始化软体对象的 CollisionObject 相关信息。

(4)根据四面体单元信息,向 btSoftBody 中添加四面体单元,线段等: psb->appendTetra(..) psb->appendLink(..) 。并初始化四面体单元的初始信息:

psb->initializeDmInverse();
psb->m_tetraScratches.resize(psb->m_tetras.size());
psb->m_tetraScratchesTn.resize(psb->m_tetras.size());

(5)生成软体的表面网格: btSoftBodyHelpers::generateBoundaryFaces(psb)

1.2 向仿真场景添加软体对象

通过函数 btDeformableMultiBodyDynamicsWorld::addSoftBody(..) 完成。主要做了以下几件事:(1)将软体对象存入 btDeformableMultiBodyDynamicsWorld::m_softBodies 中;(2)将仿真场景中的 softBodySolver 添加到该软体对象中,即 body->setSoftBodySolver(m_deformableBodySolver) ;(3)将该软体对象添加到碰撞检测场景中,即 btCollisionWorld::addCollisionObject(..)

1.3 向软体对象添加作用力

在该实例中,软体对象内有两种作用力:重力、N-H 弹性力。

btDeformableGravityForce* gravity_force =  new btDeformableGravityForce(gravity);
getDeformableDynamicsWorld()->addForce(psb, gravity_force);
        
btDeformableNeoHookeanForce* neohookean = new btDeformableNeoHookeanForce(30,100,0.05);
getDeformableDynamicsWorld()->addForce(psb, neohookean);

其中,函数 btDeformableMultiBodyDynamicsWorld::addForce(...) 做了两件事,一是将 force 对象添加到了 btDeformableMultiBodyDynamicsWorld::m_deformableBodySolver->m_objective->m_lf` 中,二是将 softBody 添加到了 force 对象中。


至此,便完成了软体对象的初始化,并将软体对象添加到了仿真场景中。接下来,便是软体对象在场景中的仿真过程。

推荐阅读