bambooflow Note

物体の固定

最終更新:

Bot(ページ名リンク)

- view
メンバー限定 登録/ログイン

物体の固定


ここでは物体を固定する方法について説明します。
実は簡単で、固定したいオブジェクトを衝突検出のみさせるようにすればよいだけです。
つまり、dGeomIDは設定する必要はあるがdBodyIDを設定する必要はないということです。
dBodyIDを設定しなければ物体は移動することができず、その場所に固定されます。

static dGeomID g_fixed;

g_fixed = dCreateBox( space, f_box_sizes[0], f_box_sizes[1], f_box_sizes[2] );

このとき、dGeomSetBodyは設定しません。



サンプルコード


fixed_obj.tgz; - ODE v0.9
fixed_obj_v02.tgz; - ODE v0.11


ODE付属のサンプルコードでdemo_buggy.cppを参考にしました。


/***********************************************************
 * Hajime no Ippo --- file : hjime.cpp
 ***********************************************************/
#include <ode/ode.h>
#include <drawstuff/drawstuff.h>
 
#define MAX_CONTACTS 4
static dWorldID world;
static dSpaceID space;
static dJointGroupID contactgroup;
 
static dBodyID b_sphere;
static dGeomID g_sphere;
static dGeomID g_fixed;
static dReal  radius = 0.5;
static dReal  f_box_sizes[3] = { 2.0, 2.0, 1.0 };
 
#ifdef dDOUBLE
  #define dsDrawSphere dsDrawSphereD
  #define dsDrawBox dsDrawBoxD
#endif
 
static void nearCallback( void *data, dGeomID o1, dGeomID o2 )
{
  dBodyID b1 = dGeomGetBody( o1 );
  dBodyID b2 = dGeomGetBody( o2 );
 
  if ( b1 && b2 && dAreConnectedExcluding( b1, b2, dJointTypeContact ) )
    return;
 
  dContact contact[MAX_CONTACTS];
  for ( int i=0; i<MAX_CONTACTS; i++ )
  {
    //contact[i].surface.mode = dContactBounce | dContactSoftERP | dContactSoftCFM;
    contact[i].surface.mode = dContactBounce;
    contact[i].surface.mu = dInfinity;
    contact[i].surface.bounce = 1.0;
    //contact[i].surface.soft_erp = 0.2;
    //contact[i].surface.soft_cfm = 0.00001;
  }
 
  int numc = dCollide( o1, o2, MAX_CONTACTS, &contact[0].geom, sizeof( dContact ) ); 
  if ( numc > 0 )
  {
    for ( int i=0; i<numc; i++ )
    {
      dJointID c = dJointCreateContact( world, contactgroup, contact+i );
      dJointAttach( c, b1, b2 );
    }
  }
}
 
// start simulation - set viewpoint
static void start()
{
  static float xyz[3] = { 0.0f, 7.0f, 5.0f };
  static float hpr[3] = { -90.f, -15.f, 0.f };
 
  dsSetViewpoint( xyz, hpr );
}
 
// simulation loop
static void simLoop( int pause )
{
  dSpaceCollide( space, 0, &nearCallback );
 
  if (!pause)
  {
    dWorldStep( world, 0.005 );
  }
 
  dJointGroupEmpty( contactgroup );
 
  dsSetColor( 1.0, 1.0, 0.0 );
  dsDrawSphere( dBodyGetPosition( b_sphere ), dBodyGetRotation( b_sphere ), radius );
  dsSetColor( 0.5, 0.5, 0.5 );
  dsDrawBox( dGeomGetPosition( g_fixed ), dGeomGetRotation( g_fixed ), f_box_sizes );
}
 
 
int main( int argc, char* argv[] )
{
  // setup pointers to drawstuff callback functions
  dsFunctions fn;
  fn.version = DS_VERSION;
  fn.start   = &start;
  fn.step    = &simLoop;
  fn.command = 0;
  fn.stop    = 0;
  fn.path_to_textures = "../../drawstuff/textures";
 
  dInitODE();
 
  // creating world
  world = dWorldCreate();
  space = dHashSpaceCreate( 0 );
  contactgroup = dJointGroupCreate( 0 );
  dCreatePlane( space, 0, 0, 1, 0 );
  dWorldSetGravity( world, 0.0, 0.0, -9.8 );
  dWorldSetERP( world, 0.8 );
  dWorldSetCFM( world, 0.00001 );
 
  // creating Sphere
  b_sphere = dBodyCreate( world );
  dReal pos[3] = { 0.0, 0.0, 5.0 };
  dBodySetPosition( b_sphere, pos[0], pos[1], pos[2] );
  dMass sphere_mass;
  dMassSetSphere( &sphere_mass, 1.0, radius );
  dBodySetMass( b_sphere, &sphere_mass );
  g_sphere = dCreateSphere( space, radius );
  dGeomSetBody( g_sphere, b_sphere );
 
  // creating Fixed Box
  g_fixed = dCreateBox( space, f_box_sizes[0], f_box_sizes[1], f_box_sizes[2] );
  dMatrix3 R;
  dRFromAxisAndAngle( R, 0, 1, 0, -0.30 );
  dGeomSetRotation( g_fixed, R);              // 方向指定
  dGeomSetPosition( g_fixed, 0.0, 0.0, 0.5 ); // 位置指定
 
  // starting simulation
  dsSimulationLoop( argc, argv, 320, 240, &fn );
 
  dJointGroupDestroy( contactgroup );
  dSpaceDestroy( space );
  dWorldDestroy( world );
  return 0;
}
 


以上

タグ:

ODE
記事メニュー
ウィキ募集バナー