ODE についてメモ
インストール
パッケージ化されてない最新版をインストールするには以下のようにする。
-
http://sourceforge.net/projects/opende/
→[Code]→Read Only access にあるとおりに svn コマンドを使って
ソースをダウンロードする。
- INSTALL.txt にあるとおり、
./bootstrap して、./configure (例: ./configure --with-drawstuff=X11)して、make して、make install する。
(注: 現在のバージョン(r1904?)では --enable-double-precision すると drawstuff と衝突するようなので倍精度はやめた方がいいかも)
- このままだと drawstuff が入らないので、…/opende-code/drawstuff/src/.libs/libfrawstuff.a を /usr/local/lib/ にコピー。
- 同様に、…/opende-code/include/drawstuff/ 以下のヘッダファイル(*.h)を
/usr/local/include/drawstuff/ 以下にコピー。
- お好みで …/opende-code/drawstuff/textures/ を適当な場所にコピーするも良し。
composite object の作り方
基本的には
HOWTO composite objectsを見れば良い。
けっこう面倒だが、確かに fixed joint よりは精度が向上する。
- composite object ように body を1つ作る。
- geom は、space を 0 として、必要なだけ作る。
- transform は、space を使いたい space として geom と同じだけ作る。
- mass も必要なだけ作る。ただし、まだ body に関連づけない。
- 各 geom をローカル座標系上で希望する場所に dGeomSetPosition する。
- 対応する mass を同じ場所に dMassTranslate する。
- 以上をすべての構成要素に対して行ったら、mass を全部 dMassAdd して
一つにする。
- こうしてできた 総mass は重心が(0,0,0)ではなく、これは ODE では
body に関連づけられないらしい。ここがポイント。
- mass の c[0]〜c[2]メンバは、その mass の重心らしい。そこで、すべての
構成要素(geom)の場所を、5.の位置に対して相対的に (-c[0], -c[1], -c[2])
ずれた場所に、あらためて dGeomSetPosition しなおす。
- 次に、総mass 自体も(-c[0], -c[1], -c[2])だけ dMassTranslate する。
前項とこの操作で、composite 全体の重心が原点に来るはず。
- すべての transform を body に dGeomSetBody する。
- 総mass を body に dBodySetMass する。
composite object 内の各構成要素の位置と姿勢の求め方
基本的には
HOWTO composite objectsを見れば良い。
わかりやすいので敢えてここでメモするまでもない。
composite object の衝突判定
注意点をひとつ。
dCollide でセットされる dContact 構造体の geom.g1 と geom.g2 に
composite object の構成 geom がセットされず、なぜか 0 になってしまう。
バグなのか仕様なのかわからないが、とにかく出村先生の本にあるような
contact joint のくっつけかた
dJointAttach(c, dGeomGetBody(contact[i].geom.g1), dGeomGetBody(contact[i].geom.g2));
だとうまく行かなかった。
nearCallback の引数が o1 と o2 であれば単純に以下のようにすればok。
dJointAttach(c, dGeomGetBody(o1),dGeomGetBody(o2));
行列・ベクトル演算便利関数使用時の注意
dMULTIPLY0_331等、dMULTIPLY* を使って v = M * u のような計算をするとき、
v と u を同一にしてはいけないらしい。
演算速度重視というわけか…。自分ではまずやらない実装なのでハマった。
これは罠だった。
このページ読んだ貴方も注意してください。