Tutorial?
ここでは物体を落下させる動力学シミュレーションを行う新しい仮想空間を作成します。
インストールしたパッケージのディレクトリ構造は以下のようになります。
sigverse-<version>
      |
      |---bin
      |---include
      |     └----sigverse       
      └---shared 
            └----sigverse
                    |----data
                    |     |----xml
                    |     └----shape
                    |----etc
                    |----jar
                    └----samples  
今回はsigverse-<version>/binに新しくディレクトリを作りそこを作業場所とします。
※別の場所(たとえばホームディレクトリ)に作業ディレクトリを作成しても構いません。その時は作成したファイルを指定するときなどディレクトリ構造に注意してください。
簡単なエージェントコントローラを作成します。 エージェントとは仮想世界で自律動作を行う物体のことを言います。 まずSIGVerseの sigverse-<version>/binに移動します。
$ cd ~/sigverse-<version>/bin
ここに新しいディレクトリを作成します。
$ mkdir NewWorld $ cd NewWorld
emacsまたはviなどのエディタを使ってMoveController.cppファイルを作成します。
$ emacs MoveController.cpp
MoveController.cpp
#include "Controller.h"
#include "Logger.h"
//ControllerのサブクラスMoveControllerの宣言します。
class MoveController : public Controller {
public:
  //定期的な処理を行うonActionの利用を宣言します。
  double onAction(ActionEvent&);
};
double MoveController::onAction(ActionEvent &evt) {
  return 5.0;      //次にonActionが呼ばれるまでの時間を返します。
}
//自身のインスタンスをSIGVerseに返します。
extern "C" Controller * createController() {
     return new MoveController;
}
※ファイル保存時にコードシステムを聞かれたら今後すべてutf-8を指定してください。
これは何もしないコントローラです。5秒ごとに何もしない関数onActionが呼び出されます。
次に作成したコードのコンパイルを行うためのmakefileを作成します。
$ emacs Makefile
Makefile
#SIGVerseソースの場所指定
SIG_SRC  = /home/<username>/sigverse-<version>/include/sigverse
#オブジェクトファイルの指定
OBJS     = MoveController.so
all: $(OBJS)
#コンパイルを行います。
./%.so: ./%.cpp
        g++ -DCONTROLLER -DNDEBUG -DUSE_ODE -I$(SIG_SRC) -I$(SIG_SRC)/comm/controller  -fPIC -shared -o $@   $<
※<username>はユーザー名、<version>はバージョン番号に置き換えます。 コマンド行のg++の前のスペースはTabですので注意してください。
makeを実行します。
$ make
MoveController.soが作成されていればコンパイル成功です。
$ ls Makefile MoveController.cpp MoveController.so
次に仮想世界の設定を記述した世界ファイルを作成します。世界ファイルでは仮想世界に登場するエージェントの設定を行います。
世界ファイルをsigverse-<version>/share/sigverse/data/xmlに作成します。
$ cd ~/sigverse-<version>/share/sigverse/data/xml $ emacs NewWorld.xml
NewWorld.xml
<?xml version="1.0" encoding="utf8"?>
<world name="newworld">
<!--重力の設定-->
  <gravity x="0.0" y="-9.8" z="0.0"/>  
 
<!--エージェントToy_Dのインスタンス作成-->
  <instanciate class="seToy_D.xml">
<!--エージェント名-->
        <set-attr-value name="name" value="Toy_D"/>  
<!--C++言語の指定-->
        <set-attr-value name="language" value="c++"/> 
<!--作成したコントローラの指定-->
        <set-attr-value name="implementation"
value="./NewWorld/MoveController.so"/>
<!--動力学演算フラグ-->
        <set-attr-value name="dynamics" value="true"/>
 
<!--エージェントの最初の位置(x,y,z)-->
        <set-attr-value name="x" value="0.0"/>
        <set-attr-value name="y" value="18.0"/>
        <set-attr-value name="z" value="5.0"/>
 
 </instanciate>
ここでは動力学シミュレーションを行うため"dynamics"を"true"に設定しました。また、エージェントとしてseToy_D.xmlというファイルを読み込むように設定しています。さまざまなエージェントやエンティティの形状ファイル(x3d,wrlファイル)やそれに付随したxmlファイルがあらかじめ用意されているので、それを用います。
これで準備は完了です。
それではSIGVerseを起動してみます。
$ cd ~/sigverse-<version>/bin
$ ./sigserver.sh -w NewWorld.xml -p 9001
      :
      :
[SYS]  waiting for connection...
[SYS]  Controller attached to "Toy_D"
[SYS]  127.0.0.1 connected
[SYS]  Toy_D : dataport
[SYS]  127.0.0.1 connected
作成した世界ファイルを-wオプションで指定します。(何も指定しないときはMyWorld.xmlが読み込まれます。)
xmlファイルの中で今回作成したコントローラを指定したので、SIGVerseの起動と同時に自動的にエージェント"Toy_D"にアタッチされました。 次にSIGViewerを起動して接続するホスト名とポート番号を入力し、Connect to SimServerボタンをクリックしてサーバに接続します。
#ref(): File not found: "toy_1.jpg" at page "Samples/Dynamics simulation"
エージェントToy_Dが世界ファイルで記述した位置(0.0, 18.0, 5.0)でスタンバイしている様子が確認できます。SIGVerseではy方向が高さになります。
次にSIM_CTRL_CMDの枠の中がSTARTとなっている状態でSendボタンを押してシミュレーションを開始します。
#ref(): File not found: "toy_2.jpg" at page "Samples/Dynamics simulation"
シミュレーションが開始し、エージェント(toy_D)が地面に落下して弾んでいるのが確認できます。
次にエージェントに力を与えて移動させます。MoveController.cppを修正します。
$ cd NewWorld $ emacs MoveController.cpp
double MoveController::onAction(ActionEvent &evt) { の下に以下の2行を追加します。
SimObj *obj = getObj(myname()); //自分自身の取得 obj->setForce(0,0,300); //z軸方向に300の力を加える
コンパイルして実行します。
$ make $ cd .. $ ./sigserver.sh -w NewWorld.xml -p 9001
SIGViewerで確認すると、5秒に一回エージェントがz方向に力が加えられて、移動しているのがわかります。
#ref(): File not found: "toy_3.jpg" at page "Samples/Dynamics simulation"
力を与える関数setForce以外にも加速度を設定するsetAccelやトルクを設定するsetTorqueなどもあるのでいろいろ試してみると面白いと思います。