2013年11月26日火曜日

mjpeg_server

wiki.ros.org/mjpeg_server

これを使ってみる

ブラウザ上で動画を見るために使えそう?

2013年10月6日日曜日

Node.jsの環境構築

ブラウザ上でROSを動かしたい
http://wiki.ros.org/rosjs-depricated
http://wiki.ros.org/rosbridge_suite

とりあえず、Node.jsを勉強しないと出来なさそうな感じ
Ubuntu13.04にNode.jsの環境を作ってみる

 $ wget http://nodejs.org/dist/v0.10.5/node-v0.10.5.tar.gz
 $ tar zxvf node-v0.10.5.tar.gz
 $ cd node-v0.10.5
 $ ./configure
 $ make
 $ sudo make install

あとは、任意のフォルダでソースコード (xxxxx.js) を書いて、

 $ node xxxxx.js

●参考

基礎から学ぶNode.js
http://gihyo.jp/dev/serial/01/nodejs/0001

ビギナーのための Node.jsプログラミング入門
http://libro.tuyano.com/index2?id=1115003

2013年9月30日月曜日

Xtionの有効範囲

http://www.asus.com/jp/News/iidy4mD9PKJk6Zi4/

↑この記事によると、Xtionの有効範囲は
0.8m~3.5mらしい

ということは、gmappingのパラメータをこの様に書き換えたほうがよいのだろうか?

$ rosrun gmapping slam_gmapping _map_update_interval:=0.1 _maxUrange:=3.5 _linearUpdate:=0.10 _angularUpdate:=0.262 _temporalUpdate:=0.5

2013年9月26日木曜日

amclパラメーター

http://wiki.ros.org/amcl?distro=hydro

amclのパラメーターは次の3種類である

(1) 総体的なフィルタ
(2) レーザーモデル
(3) オドメトリモデル


(1) 総体的なフィルタ
min_particles ( int型、デフォルト:100 )粒子の最小許容数。

max_particles ( int型、デフォルト:5000 )粒子の最大許容数。


kld_err (double型、デフォルト:0.01 )真の分布と推定分布の間の最大誤差。

kld_z (
double型、デフォルト: 150 )
pは推定distrubition上の誤差がkld_err未満になる確率ですが、 - の上限標準正規分位点( P 1 ) 。
よくわからない


update_min_d (
double型、デフォルト: 0.2メートル)
フィルタのアップデートを実行する前に必要とされる並進運動。 

update_min_a (double型、デフォルト: π/6.0ラジアン)フィルタのアップデートを実行する前に必要とされる回転運動。

resample_interval ( int型、デフォルト: 2)リサンプリング前に必要なフィルタ更新の数。

transform_tolerance (
double型、デフォルト: 0.1秒)わからない 

recovery_alpha_slow (double型、デフォルト:0.0 (無効) )ランダムポーズを追加することによって回復するときに決定する際に使用される低速の平均体重フィルタの指数関数的な減衰率。良い値は、0.001であるかもしれません。
ランダムポーズとは?


recovery_alpha_fast (
double型、デフォルト:0.0 (無効) )ランダムポーズを追加することによって回復するときに決定する際に使用される高速の平均体重フィルタの指数関数的な減衰率。良い値は0.1であるかも。

initial_pose_x (
double型、デフォルト: 0.0メートル)初期( x)は、ガウス分布を有するフィルタ初期化するために使用されることを意味をもたらす。
どういうことに使用されるのか?


initial_pose_y (
double型、デフォルト: 0.0メートル)初期、 ( y)の意味をもたらすガウス分布とフィルター初期化するために使用。 
initial_pose_a (double型、デフォルト:0.0ラジアン)初期ポーズはガウス分布とフィルター初期化するために使用し、 (ヨー)を意味します。

initial_cov_xx (
double型、デフォルト: 0.5× 0.5メートル)初期の共分散をポーズ( X * x)は、ガウス分布とフィルター初期化するために使用。 

initial_cov_yy (double型、デフォルト: 0.5× 0.5メートル)初期、 (Y * Y )共分散をもたらすガウス分布とフィルター初期化するために使用。

initial_cov_aa (
double型、デフォルト: ( π/12 )*( π/12 )ラジアン)初期、 (ヨー*ヨー)共分散をもたらすガウス分布とフィルター初期化するために使用。

gui_publish_rate (
double型、デフォルト: -1.0 Hz)最大レート(Hz )がれるスキャンやパスが無効に-1.0 、可視化のために公開されています。

save_pose_rate (
double型、デフォルト: 0.5 Hz)最大レート(Hz )がれる格納する最後の推定変数に、パラメータサーバへのポーズと共分散〜 initial_pose_ *と〜 initial_cov_ * 。このポーズは保存されたフィルタを初期化するために、後続の実行で使用されます。無効にするには-1.0 。

use_map_topic (ブール値、デフォルト:false)trueに設定すると、 AMCLはむしろそのマップを受信するサービスコールを作るよりも、マップのトピックにサブスクライブします。


first_map_only (ブール値、デフォルト:false)trueに設定すると、 AMCLだけむしろ新しいものが受信されるたびに更新するよりも、それがサブスクライブする最初のマップを使います。



(2) レーザーモデル

laser_min_range (double型、デフォルト: -1.0 )最小スキャン範囲。-1.0はレーザの報告最小範囲を使用。 
laser_max_range (double型、デフォルト: -1.0 )
最大スキャン範囲。-1.0 はレーザの報告最大範囲を使用。

laser_max_beams ( int型、デフォルト:30 )フィルタの更新時に各スキャンでどのように多くの等間隔のビームが使用される。 
laser_z_hit (double型、デフォルト:0.95 )モデルのz_hit部分の混合重み。 
laser_z_short (double型、デフォルト: 0.1)モデルのz_short部分の混合重み。
laser_z_max (
double型、デフォルト:0.05 )モデルのz_max部分の混合重み。
laser_z_rand (
double型、デフォルト:0.05 )モデルのz_rand部分の混合重み。
laser_sigma_hit (
double型、デフォルト: 0.2メートル)ガウスモデルの標準偏差は、モデルのz_hit一部に使用した。
laser_lambda_short (
double型、デフォルト: 0.1)モデルのz_short部分の指数関数的な減衰パラメータ。
laser_likelihood_max_dist (
double型、デフォルト: 2.0メートル)最大距離はlikelihood_fieldモデルで使用するために、地図上に障害物インフレを行うため。 
laser_model_type (文字列、デフォルトは" likelihood_field " )どのモデルを使用すると、ビームまたはlikelihood_fieldどちらか。


(3) オドメトリモデル
「差分」と「全方位」のモデルタイプがある

odom_model_type(文字列デフォルトは"diff"
どのモデル"diff(差分)"または "omni(全方位)"のいずれかを使用する

 
odom_alpha1ダブルデフォルト0.2)
ロボットの動きの回転成分からオドメトリの自転の見積りの予想ノイズを指定します

 

odom_alpha2ダブルデフォルト0.2)
ロボットの動きの並進成分からオドメトリの自転の見積りの予想ノイズを指定します

 
odom_alpha3ダブルデフォルト0.2)
ロボットの動きの並進成分からオドメトリ翻訳上の見積りの予想されるノイズを指定します

 
odom_alpha4ダブルデフォルト0.2)
ロボットの動きの回転成分からオドメトリ翻訳見積もりの予想ノイズを指定します


odom_alpha5ダブルデフォルト0.2)
翻訳関連のノイズパラメータモデルは"全方位"である場合にのみ使用


odom_frame_id(文字列デフォルトは"odom"
どのフレームオドメトリに使用する


base_frame_id(文字列デフォルトは"base_link"
どのフレームロボットベースに使用する


global_frame_id(文字列デフォルトは"map"
座標系の名前はローカライゼーションシステムによって発行される












 
 

2013年9月24日火曜日

gmappingしながらnavigation

この動画では、gmappingしながらnavigationスタックを利用している



やり方は、
$ roslaunch openni_launch openni.launch
 新しい端末を開いて
$ rosrun depthimage_to_laserscan depthimage_to_laserscan image:=/camera/depth/image
 新しい端末を開いて
$ rosrun rviz rviz
 新しい端末を開いて
$ rosrun ROSARIA RosAria
 新しい端末を開いて
$ rosrun tf static_transform_publisher 0.150 0.0 0.270 0.0 0.0 0.0 /base_link /camera_link 100
 新しい端末を開いて
$ rosrun ROSARIA rob_teleop
 新しい端末を開いて
$ rosrun gmapping slam_gmapping 
このとき、mapフレームとodomフレームがtfで変換できているので、
amclを使わなくてもmove_base.launchができる

$ roslaunch mypack move_base.launch

そして、ROSARIAの場合、cmd_velトピックは/RosAria/cmd_velなので、
$ rosrun topic_tools relay cmd_vel RosAria/cmd_vel 
 
あとは、rvizを開いて2dnavgoalでゴールを指定する
なお、地図化されていない部分をゴールとして指定したら、移動車は回転する。
自己位置を推定するためだろうか?
 
地図のマッチングを行いながら移動するため、挙動がつっかえたりする。
つまり、移動車がスムーズに動きにくい。 

2013年9月21日土曜日

navigationのゴールを直接送る

rviz上でゴールを指定するのも便利だけど、やっぱ自分でゴールをパブリッシュ出来た方が良いので、やってみる

http://wiki.ros.org/navigation/Tutorials/SendingSimpleGoals

2013年9月19日木曜日

gmappingをいかに改善していくか?

gmapping machingで画像検索して
自分のぶつかってる問題と関係ありそうな症状を見つけてみた。

いろいろ記事を読んでみて、わかったことは3つ

  • KInectを使っていたとしても、デフォルトの値でもあまり問題は生じない
    • それよりも、オドメトリかロボットの操縦方法に異常があるのではという指摘
    • 異常なオドメトリに関しての対処は書いてないが、ロボットの操縦についてはヒントがかかれている
    • 既知のコーナー(おそらくマッピングが既になされている)を常にカメラの視野に入れておくこと
  • それでもパラメーターを変更してマップの精度を上げたければ、以下の三つであると
    • linearUpdate
      • 減らしたほうがよい
    • angularUpdate 
      • 上と同様、減らしたほうがよい
    • particles  
      • 増やしたほうがよい(100がちょうど良い)
  • 更新速度とパーティクルを増やすと上手く行くらしい。あとは運。 


それから、もしかすると赤外線の長さも、短くした方がいいかも
おそらく、距離が長いと、それだけ誤差が大きくなるから

2013年9月16日月曜日

gmapping色々やってみてしらべてわかったこと

Kinectをつかってgmappingしているページ
http://www.hessmer.org/blog/2011/04/10/2d-slam-with-ros-and-kinect/

この動画によると・・・


とてもゆっくり動かしている
LaserScanを使い、 マッチングするまで待ってから、動かしている
僕は今まで、何にも考えずぐるぐる動かしていた
だから地図がちゃんとつくれなかった
パラメーターは、おそらく、そんなに関係ないと思う

この動画みたいにして動かさないと、ちゃんとした地図が作れない

あと、推測だけど、カメラを置く位置を正確に測ってtfしないと、地図がズレる
もしかしたら、カメラの位置は、中心位置からあまり動かさない方がいいのかもしれない

gmappingのパラメータ

https://sites.google.com/site/slamnavigation/
あてずっぽうにパラメータをいじくるよりも、このサイトを参考にしてやってみたほうが上手くいきそう
このサイトのパラメータはこんな感じ

$ rosrun gmapping slam_gmapping _map_update_interval:=2.0 _maxUrange:=6.0 _sigma:=0.05 _kernelSize:=1 _lstep:=0.05 _astep:=0.05 _iterations:=5 _lsigma=0.075 _ogain:=3.0 _lskip:=0 _srr:=0.01 _srt:=0.02 _str:=0.01 _stt:=0.02 _linearUpdate:=0.25 _angularUpdate:=0.262 _temporalUpdate:=-1.0 _resampleThreshold:=0.5 _particles:=300 _xmin:=-50.0 _ymin:=-50.0 _xmax:=50.0 _ymax:=50.0 _delta:=0.05 _llsamplerange:=0.01 _llsamplestep:=0.01 _lasamplerange:=0.005 _lasamplestep:=0.005


パラメータの解釈
  • _map_update_interval:=2.0 
    • mapの更新間の時間は2.0s
  • _maxUrange:=6.0 
    • レーザーが届く最大範囲は6m
  • _sigma:=0.05
    • デフォルトの値
  • _kernelSize:=1
    • デフォルトの値
  • _lstep:=0.05 
    • デフォルトの値
  • _astep:=0.05 
    • デフォルトの値
  • _iterations:=5 
    • デフォルトの値
  • _lsigma=0.075 
    • デフォルトの値
  • _ogain:=3.0 
    • デフォルトの値
  • _lskip:=0 
    • デフォルトの値
  • _srr:=0.01 
    • 0.01m以内のズレを誤差とする
  • _srt:=0.02 
    •  0.02m以内のズレを誤差とする
  • _str:=0.01
    • 0.01m以内のズレを誤差とする
  • _stt:=0.02 
    • 0.02m以内のズレを誤差とする
  • _linearUpdate:=0.25
    • 0.25m平行移動したらスキャンの更新
  • _angularUpdate:=0.262 
    • 0.262回転したらスキャンの更新
  • _temporalUpdate:=-1.0 
    • デフォルトの値
    • 時間毎のスキャン更新は無し
  • _resampleThreshold:=0.5 
    • デフォルトの値
  • _particles:=300 
    • パーティクルはデフォルトの10倍
  • _xmin:=-50.0 
  • _ymin:=-50.0 
  • _xmax:=50.0 
  • _ymax:=50.0 
    • 初期マップの大きさ
  • _delta:=0.05 
    • デフォルトの値
  • _llsamplerange:=0.01 
    • デフォルトの値
  • _llsamplestep:=0.01
    • デフォルトの値
  • _lasamplerange:=0.005 
    • デフォルトの値
  • _lasamplestep:=0.005
    • デフォルトの値 

2013年9月14日土曜日

gmappingのパラメータ(昨日の続き)

gmappingについて
自己位置が不用意に動くというのは、おそらく、センサから得たデータとマッチングしているためではないか
つまり、gmappingはマッチングを優先させてしまっているのではないか
だから、自己位置がズレてしまうのではないか



それが原因だとすると、対処としては…

(1) 自己位置を優先させてマッチングさせる→できるかどうか不明
(2) マッチングの回数(頻度)を減らす→ブレを減らすため
(3) あんまり正確にマッチングさせない(?)→アバウトにすることで、自己位置を動かないようにする

とりあえず、gmappingのパラメータを洗うところから
http://wiki.ros.org/gmapping#Parameters

関係ありそうなのは、
  • ~map_update_interval (float, default: 5.0)  
  • ~transform_publish_period (float, default: 0.05)
かなあ
次点で、
  • ~throttle_scans (int, default: 1)
  • ~maxUrange (float, default: 80.0)
  • ~sigma (float, default: 0.05)  

以下、google翻訳を使って調べてみた
  • ~inverted_laser (string, default: "false"
    •  反転レーザー(?)。反転させるかどうかみたいな?
  • ~throttle_scans (int, default: 1) 
    •  どれだけスキャンデータをスキップ(無視)するか
    • この数値を増やせば、その分だけスキップする
    • たとえば、数値を3に設定すると、3回に1回データを取る
  • ~map_update_interval (float, default: 5.0)  
    • 更新頻度に関わるパラメータ
    • 数値を減らすと、更新頻度が短くなり、負荷が大きくなる
    • 更新頻度が短くなれば、それだけ地図が正確になるのだろうか?
  • ~maxUrange (float, default: 80.0) 
    • レーザーの最大範囲
    • この数値を下げたら、マップとして認識する範囲が短くなる
    • デフォルトでは、80(m?)以上はマップとして認識しない
  • ~sigma (float, default: 0.05)  
    • 欲張り法における数値(?)
    • 数値を大きくすると、新しいマッチングが追加されなくなる(つまり、数値以下であれば、同じマッチングだと認識する)
    • 実験して確かめてみるしかなさそう
  • ~kernelSize (int, default: 1) 
    • マッチングを見る範囲の大きさみたいな?
    • マッチングの範囲が小さければ、マッチングは合う可能性が高いが、マッチングの範囲が広ければ、マッチングが合わなくなる可能性が高い
    • しかし程度が分からないので、実験して調べてみる
  • ~lstep (float, default: 0.05)
    • 平行移動におけるズレ
    • よくわからない
  • ~astep (float, default: 0.05)
    • 回転におけるズレ
  • ~iterations (int, default: 5)  
    • スキャンマッチャーの対応の回数
    • マッチングを何回繰り返すか?
    • つまり、マッチング回数が多ければ正確になるが、処理は重くなる
  •  ~lsigma (float, default: 0.075) 
    • 尤度計算に使用されるビームのシグマ
    • ビームを足し合わせるってこと?
    • そもそもビームってなに?
  • ~ogain (float, default: 3.0) 
    • 尤度の評価中に再サンプリングの効果を平滑化するため、使用するゲイン。
    • ゲイン??? 
    • よくわからない
  • ~lskip (int, default: 0) 
    • 各スキャンでスキップするビームの数。
    • だからビームとは? 
  • ~srr (float, default: 0.1) 
    •  オドメトリ(ρ/ρ)の誤差
  • ~srt (float, default: 0.2)
    • 回転動作におけるオドメトリ(ρ/θ)の誤差
  • ~str (float, default: 0.1)
    • 回転オドメトリ(θ/ρ)の誤差
  • ~stt (float, default: 0.2)
    • 回転動作における回転オドメトリ(θ/θ)の誤差 
  • ~linearUpdate (float, default: 1.0) 
    • ロボットが引数分だけ動いたら、スキャンを更新する
    • つまり、デフォルトでは1m動いたらスキャンを更新する
    • 小さくした方が良いように思われる
  • ~angularUpdate (float, default: 0.5) 
    • ロボットが引数分だけ回転したら、スキャンを更新する
    • 小さくした方が良いように思われる
  • ~temporalUpdate (float, default: -1.0) 
    • 時間毎のスキャンの更新
    • デフォルトでは、時間毎の更新はオフになっている
  • ~resampleThreshold (float, default: 0.5)
    • ネフベースのリサンプリングのしきい値
    • ネフベースとは?
  • ~particles (int, default: 30) 
    • フィルター中の粒子の数
    • パーティクルを増やすと正確になる 
  • ~xmin (float, default: -100.0)
    • 初期マップサイズ
  • ~ymin (float, default: -100.0)
    • 初期マップサイズ 
  • ~xmax (float, default: 100.0)
    • 初期マップサイズ
  • ~ymax (float, default: 100.0)
    • 初期マップサイズ 
  • ~delta (float, default: 0.05) 
    • マップの解像度
  • ~llsamplerange (float, default: 0.01) 
    • 尤度のための翻訳サンプリングの範囲
  • ~llsamplestep (float, default: 0.01) 
    • 尤度のための翻訳サンプリングの範囲
  • ~lasamplerange (float, default: 0.005)  
    • 尤度のための角度サンプリングの範囲
  • ~lasamplestep (float, default: 0.005)
    • 尤度のための角度サンプリングの範囲
  • ~transform_publish_period (float, default: 0.05) 
    • tfパブリッシュの間をどれだけとるか(秒)
  • ~occ_thresh (float, default: 0.25) 
    • 障害物のある確率
    • 高ければマップが更新されない(?)
  • ~maxRange (float
    • センサの最大範囲




2013年9月13日金曜日

gmappingの地図がちゃんとしていない(途中)

gmappingが上手くできない…
直線コースがうまく地図にできない…まっすぐができない

症状:
gmapping中に直線コースをたどるとき、rviz上で、自己位置tfが戻ってしまう。つまり、まっすぐの距離が縮んでしまい、尺の合わない地図が生成されてしまう。
この状態だと、costmapしたときに、地図上の障害物と実際の障害物が不一致になるため、思ったとおりの動きをしない。

原因は何だろう
考えられる原因としては、

(1) エンコーダーの問題(ちゃんと距離を取れていない)
(2) tfの問題(/odomと/base_linkの変換が上手くいっていない)
(3) gmappingのパラメーターがおかしい

(1)について
エンコーダーの数値は、移動車をまっすぐ進めたらそれだけ増えるので、おかしいとは思えない…

(2)について
 /odomと/base_linkの変換はRosAriaというノードによって行われている。
おかしいとしたらこの変換なんだけどなあ…

→rvizでtfを可視化して確かめてみた。すると、tfだけなら位置のズレはまったく起こっていない
ちゃんと進んだ分だけrviz上のtfも動く。つまり、実測値とコンピューター上の値との齟齬はない

では、gmappingのやり方がおかしい。

ところで自分は、/odom -> /base_link -> camera_linkという変換をしている
しかし、 このページでは、間にfootprintをかませている。
つまり、/odom -> /base_footprint -> /base_link -> camera_link
でやっている。
これを直すか?
または、 (3)について、パラメーターがおかしいのか。

この様にやっている人もいる
$ rosrun gmapping slam_gmapping _xmin:=-5.0 _ymin:=-5.0 _xmax:=5.0 _ymax:=5.0 _maxUrange:=59.0 _maxRange:=63.0 _map_update_interval:=5.0 _linearUpdate:=0.2 _angularUpdate:=0.15 _particles:=50 _delta:=0.02

パラメーターの扱いはまだよくわかっていない…
このページをみて勉強しよう

そもそも
なぜマップを正確に取りたいかというと、move_baseを使いたいから
しかし、用意されたマップを用いるならば、こんな作業はおそらく必要ない。
正確なマップを使ってみるのも手段ではある…

2013年8月25日日曜日

move_base使ってみた

自律移動できた
詳しいことは後日まとめるとして、個人用メモ

roslaunch amcl amcl_deff.launch
move_base.launch
rorsrun topic_tools relay cmd_vel RosAria/cmd_vel
rvizの2dnavで移動先の指定

move_baseのyamlファイルとかがややこしい
というか自分の場合launchがうまくいかないので、わざわざlaunchファイルが置いてある場所に移動してからroslaunchしてる

topic_toolsについて

任意のトピックにパブリッシュするためのモジュール
http://ros.org/wiki/topic_tools

これかなあ?
http://ros.org/wiki/topic_tools/relay

2013年7月30日火曜日

launchファイルを作りたい

いま、自律移動やってるんですけど、
launchファイルを作らないといけない状況になってる。
でも、launchファイルって、どういう仕組みで作られているのか未だに良く分からない。
パッケージに、launchしたいノードのソースコードを入れるべきなのか、そうじゃないのか。
launchファイルも別のlaunchファイルに含められるのか。
launchファイルはフォルダのどこにおくべきなのか。

わからないことだらけ。

でも、ググってみたら、日本語のサイトがあった。やったー。

http://code.google.com/p/rtm-ros-robotics/wiki/ROS_Example_Launch_Syntax

2013年7月23日火曜日

gmappingのやり方

0. 環境

Pioneer3dx, Xtion PRO LIVEを使用する。

1. 前準備

 

1.1 ROSARIAを導入する

ROSARIAは以下のページを参照して導入する。

 

1.2 openni_launchを使えるようにする

KinectやXtionを使用するためのモジュールである
http://asukiaaa.blogspot.jp/2013/05/xtion_20.html

 

1.3 depthimage_to_laserscanを入れる

$ sudo apt-get install ros-groovy-depthimage_to_laserscan
赤外線データを取得するためのモジュールである。
これで入らない場合は、~/catkin_ws/src以下にgit cloneを使って入れる
$ cd ~/catkin_ws/src 
$ git clone https://github.com/ros-perception/depthimage_to_laserscan 
$ cd ~/catkin_ws 
$ catkin_make

 

1.4 rob_teleop.cppを追加する

rob_teleop.cppは、pioneer3dxをキー操作するためのモジュールである。
今回は、ROSARIAのパッケージにこのモジュールを追加した。

2. 手順

 

2.1 ROSARIAを使ってSLAMする(map_serverでマップを生成する場合)

$ roslaunch openni_launch openni.launch
 新しい端末を開いて
$ rosrun depthimage_to_laserscan depthimage_to_laserscan image:=/camera/depth/image
 新しい端末を開いて
$ rosrun ROSARIA RosAria
 新しい端末を開いて
$ rosrun tf static_transform_publisher 0.170 0.0 0.270 0.0 0.0 0.0 /base_link /camera_link 100
 新しい端末を開いて
$ rosrun ROSARIA rob_teleop
 新しい端末を開いて
$ rosbag record /scan /tf
 データの記録が始まるので、必要な分だけロボットを動かす。
 その時のデータは、その時のディレクトリにbagファイルとして保存される。
 Ctrl + c で強制終了。
 すべての端末を終了させて,
$ roscore
 新しい端末を開いて
$ rosparam set use_sim_time true
$ rosrun gmapping slam_gmapping scan:=scan
 新しい端末を開いて
$ rosbag play (保存したbagファイルの名前).bag
 処理が終わるまで待つ。
$ rosrun map_server map_saver
 すると、カレントディレクトリに map.pgm と map.yaml が生成される。

 

2.2 ROSARIAを使ってSLAMする(rvizでリアルタイムマップ生成)

$ roslaunch openni_launch openni.launch
 新しい端末を開いて
$ rosrun depthimage_to_laserscan depthimage_to_laserscan image:=/camera/depth/image
 新しい端末を開いて
$ rosrun rviz rviz
 新しい端末を開いて
$ rosrun ROSARIA RosAria
 新しい端末を開いて
$ rosrun tf static_transform_publisher 0.170 0.0 0.270 0.0 0.0 0.0 /base_link /camera_link 100
 新しい端末を開いて
$ rosrun ROSARIA rob_teleop
 新しい端末を開いて
$ rosrun gmapping slam_gmapping scan:=scan
 rvizの画面に戻り、mapをAddする。frameとtopicを/mapに設定する。
 rviz上で地図の生成が始まる。
$ rosrun map_server map_saver
すると、カレントディレクトリに map.pgm と map.yaml が生成される。

3. 上手くいかなかったら

 

3.1 tfに関するエラー(警告)が出た場合

以下のコマンドのフレームを調整する。
$ rosrun tf static_transform_publisher 0.17 0.0 0.270 0.0 0.0 0.0 /base_link /camera_link 100
 ここでは、tfを使って、レーザのリンクをオドメトリに渡している。
 /camera_link,/base_link,/base_footpointはロボットのフレームである。
 これらのフレーム変換によって、レーザースキャンデータをロボットの中心からレーザーが出ているように変換している。
 存在しないフレームがあると、データが所得できない。TF_OLD_DATAみたいなWARNINGが出る。
 したがって、tfで上手くいかなければ、まず、そのフレームが存在するかどうかを調べるべき。
 今回はそれでつまづいた。
$ rosrun tf static_transform_publisher 0.034 0.0 0.250 0.0 0.0 0.0 /base_link /camera_link 100
 デフォルトでは/laserのフレームを/base_linkに変換している。しかし、今回はXtionを使ったため、Xtion(OpenNI)のフレーム/camera_linkを指定しなければならなかった。

3.2 自己位置がrviz上で上手く反映されない場合(tfがチカチカする)
おそらく、単一のフレーム間に、tfが複数かかっていると思われる。
たとえば、ROSARIAでは、/odomから/base_linkのtfが、ROSARIAのモジュール内でなされている。
そのとき、/odomから/base_linkのtfを別にやってしまうと、rviz上でのtfの表示がチラつくようになる。
また、マップも上手く生成されなくなる。
これは、view frameで気づくことができないから、要注意である。
rqt_graphで、二重にかかっていないかチェックする。

4. 参考にしたページ

2013年7月16日火曜日

gmappingできた

gmappingできました

また後日清書します
それに伴って、ROSについて誤解していた記事も訂正・削除します

今は殴り書きだけ

$ roslaunch openni_launch openni.launch

$ rosrun depthimage_to_laserscan depthimage_to_laserscan image:=/camera/depth/image

$ rosrun rviz rviz

$ rosrun ROSARIA RosAria

$ rosrun tf static_transform_publisher 0.0 0.0 0.0 0.0 0.0 0.0 /base_footprint /camera_link 100

※ここで注意するのは、/laserじゃなくて/camera_linkで取得しなければならなかった
チュートリアルとかのデフォでは、/laserになっている。
でも、自分の場合、/laserというリンクが存在しなかったので、tfエラーが起きてた。 
よって、/laserを/camera_linkに変更したらできた
/camera_linkとは、camera(Xtion)の中心位置

$ rosrun tf static_transform_publisher 0.0 0.0 0.0 0.0 0.0 0.0 /be_footprint /base_link 100
$ rosrun gmapping slam_gmapping scan:=scan
$ rosrun map_server map_saver




rvizで、mapだけを追加して、topicを/mapにすると、リアルタイムでマップ生成が見れる
その場合は。gmappingの前に
$ rosparam set use_sim_time true
しないと、マップ情報がちぐはぐになって(?)ぐちゃぐちゃなマップができてしまう
LaserScanを加えると、コアダンプしてrvizが落ちる

gmappingができない原因

gmappingが上手くいかない原因として考えられるのは

1,オドメトリがレーザー(Xtion)の位置に変換できていない
2,Xtionからのレーザー情報に不備がある(?)
3,適切なやり方(PC的には何も失敗していない)ができていない。手順がおかしい。





openni_launchのチュートリアル
http://www.ros.org/wiki/openni_launch/Tutorials

 

2013年6月23日日曜日

マッピングできない

http://www.ist.tugraz.at/robotics/bin/view/Main/Poineer_mapping

マッピングするためには以下の変換が必要

1./base_linkと/laser
2./base_footprintと/base_link
3./odomと/base_footprint

上記の変換をするためには以下のようにして変換しなければならない

/odom --> /base_footprint --> /base_link --> /laser


●実際は以下のように変換する

//○変換:/base_link --> /laser
    tf::Quaternion laserQ;
    laserQ.setRPY(0.0, 0.0, 0.0);
    tf::Transform txLaser =  tf::Transform(
                        laserQ,
                        tf::Point(0.034, 0.0, 0.250)
                        );
    tf.sendTransform(
            tf::StampedTransform(
                        txLaser,
                        ros::Time::now(),
                        "base_link",
                        "laser"
                        )
            );
   
//○変換:/base_footprint --> /base_link
    tf::Transform txIdentity(
                tf::createIdentityQuaternion(),
                tf::Point(0.0, 0.0, 0.0)
                );
    tf.sendTransform(
            tf::StampedTransform(
                        txIdentity,
                        ros::Time::now(),
                        "base_footprint",
                        "base_link")
                        );
   
//○変換:/odom --> /base_footprint
    tf::Quaternion odomQ;
    tf::quaternionMsgToTF(
                position.pose.pose.orientation,
                odomQ
                );<b>map_saver</b>
    tf::Transform txOdom(
                odomQ, tf::Point(
                        (double) pos.getX()/1000.0,
                        (double) pos.getY()/1000.0,
                        pos.getTh()
                        )
                );
    tf.sendTransform(
            tf::StampedTransform(
                        txOdom,
                        ros::Time::now() ,
                        "odom",
                        "base_footprint")
                        );


※Quatarnionについて
http://www.bulletphysics.com/Bullet/BulletFull/classbtQuaternion.html
仕様が変わってるらしい


○また、上記の変換は以下のようにして端末上で変換することも出来る
$ rosrun tf static_transform_publisher 0.034 0.0 0.250 0.0 0.0 0.0 /base_link /laser 100
$ rosrun tf static_transform_publisher 0.0 0.0 0.0 0.0 0.0 0.0 /base_footprint /base_link 100


○これでいけるかやってみた
$ roslaunch openni_launch openni.launch
$ rosrun depthimage_to_laserscan depthimage_to_laserscan image:=/camera/depth/image_raw
$ rosrun rviz rviz
でlaserscanデータを取得
$ rosrun ROSARIA RosAria
$ rosrun tf static_transform_publisher 0.034 0.0 0.250 0.0 0.0 0.0 /base_link /laser 100
$ rosrun tf static_transform_publisher 0.0 0.0 0.0 0.0 0.0 0.0 /base_footprint /base_link 100
$ rosrun ROSARIA theo.key

で、あとはデータを取得

$ rosbag record -a
$ rosparam set use_sim_time true
$ rosrun gmapping slam_gmapping
$ rosbag play .....................bag
$ rosrun map_server map_saver

ちなみに$ rosrun gmapping slam_gmappingした端末では、以下のような警告が
ここに書いてる
http://www.ros.org/wiki/navigation/Troubleshooting


[ WARN] [1371981822.770704891]: TF_OLD_DATA ignoring data from the past for frame /base_link at time 1.37198e+09 according to authority /play_1371981806796107282
Possible reasons are listed at
[ WARN] [1371981822.770915036]: TF_OLD_DATA ignoring data from the past for frame /camera_depth_frame at time 1.37198e+09 according to authority /play_1371981806796107282
Possible reasons are listed at
[ WARN] [1371981822.771151442]: TF_OLD_DATA ignoring data from the past for frame /camera_rgb_optical_frame at time 1.37198e+09 according to authority /play_1371981806796107282
Possible reasons are listed at

うーん

マップ出来ない
上手く行ったらmy_lab_map.yamlmy_lab_map.pgmが生成されるらしいけど
できていない 
rosbagでgmappingに必要なデータが取得できていないのだろう
後一歩のところで届いてないみたいな

今回のリンクはとても参考になった
グラフ






2013年6月21日金曜日

ROSARIAを使ってオドメトリを取る(1)

●MobileRobot社のpioneerロボットを使うため、
 ROSARIAからオドメトリ情報を取得する

 http://www.ros.org/wiki/ROSARIA/Tutorials/How%20to%20use%20ROSARIA
※p2osのlanuchファイルがどうしても使えなかったので、ROSARIAを使ってみる

おそらく出来る
しかも、あまりいじらないで出来ると思う

なぜなら、nav_msgs/Odometoryを使っているから。
それを出力するだけでも十分いけるように思う


○ROSARIA odomでググったら

http://www.ist.tugraz.at/robotics/bin/view/Main/Poineer_mapping

また、git-hubで

https://github.com/giorgosera/HCR-project/blob/master/src/KeyBoardController.cpp


○拡張できそうなソースコードが揃った

ROSARIAのパッケージの、RosAriaがあるフォルダに、

theo_key.cpp(キーボード操作)
https://github.com/giorgosera/HCR-project/blob/master/src/KeyBoardController.cpp
reb_teleop.cpp(キーボード操作?)
http://www.ist.tugraz.at/robotics/bin/viewfile/Main/Poineer_mapping?rev=1;filename=rob_teleop.cpp
transform.cpp(odom出力?)
http://www.ist.tugraz.at/robotics/bin/viewfile/Main/Poineer_mapping?rev=1;filename=transform.cpp

を追加


○CMakeLists.txtを開いて、追加

だいたい44行めあたりに(見たらなんとなくわかる)

add_executable(theo_key theo_key.cpp)#
add_dependencies(theo_key ROSARIA_gencfg)#
add_executable(rob_teleop rob_teleop.cpp)#
add_dependencies(rob_teleop ROSARIA_gencfg)#
add_executable(transform transform.cpp)#
add_dependencies(transform ROSARIA_gencfg)#

target_link_libraries(theo_key ${catkin_LIBRARIES} ${Boost_LIBRARIES} Aria pthread dl rt)#
set_target_properties(theo_key PROPERTIES COMPILE_FLAGS "-fPIC")#
target_link_libraries(rob_teleop ${catkin_LIBRARIES} ${Boost_LIBRARIES} Aria pthread dl rt)#
set_target_properties(rob_teleop PROPERTIES COMPILE_FLAGS "-fPIC")#
target_link_libraries(transform ${catkin_LIBRARIES} ${Boost_LIBRARIES} Aria pthread dl rt)#
set_target_properties(transform PROPERTIES COMPILE_FLAGS "-fPIC")#

を追加


○catkin_wsに戻って

$catkin_make

※rob_teleopをコンパイルするとエラーが出てくるので、エラーが出てる箇所を削除してみる
http://answers.ros.org/question/11980/teleop_base-compile-errors-from-boost/


※トピックが違うので変更してあげる(適切に指定しないと動かない)
rob_teleopだいたい82行め

pub_ = n_.advertise<geometry_msgs::Twist>("/cmd_vel",1);

pub_ = n_.advertise<geometry_msgs::Twist>("/RosAria/cmd_vel",1);


※データが古いので以下のような警告がでるかもしれない

警告: ‘tf::Quaternion::Quaternion(const tfScalar&, const tfScalar&, const tfScalar&)’ は廃止されました (宣言位置 /opt/ros/groovy/include/tf/LinearMath/Quaternion.h:51) [-Wdeprecated-declarations]

tf::Quaternion(0, 0, 0)

tf::Quaternion(0, 0, 0, 1)
にしたら直った


○実行してみる

$ roscore
$ rosrun ROSARIA RosAria
$ rosrun ROSARIA reb_teleop

動かないときは、トピックの指定が違っているかも
/cmd_vel→/RosAria/cmd_vel

theo_keyでも動く

$ rosrun ROSARIA theo_key

矢印キーを押したら動く(加速するので注意)
で、次に自己位置データ

$ rosrun ROSARIA transform
[ INFO] [1371822464.617404922]: odometry frame sent
[ INFO] [1371822464.715979980]: odometry frame sent
[ INFO] [1371822464.816018004]: odometry frame sent
[ INFO] [1371822464.915978903]: odometry frame sent
[ INFO] [1371822465.015940424]: odometry frame sent
[ INFO] [1371822465.115958098]: odometry frame sent
[ INFO] [1371822465.215978116]: odometry frame sent
[ INFO] [1371822465.315948702]: odometry frame sent
[ INFO] [1371822465.416017841]: odometry frame sent
[ INFO] [1371822465.515966884]: odometry frame sent
[ INFO] [1371822465.615961342]: odometry frame sent
[ INFO] [1371822465.716013449]: odometry frame sent
[ INFO] [1371822465.815990326]: odometry frame sent
[ INFO] [1371822465.915962577]: odometry frame sent
...
...
...
何かいっぱい出た!
しかし、自己位置を取っているのかは不明

次は、キーボードでロボットを動かして、そのときの自己位置を出力するように改造してみる










オドメトリをパブリッシュする

slamするためには パッケージを探すよりも、必要なデータを出力することが必要
そこで、
Subscribed Topics
マップを作るために入力されるデータ
tf (tf/tfMessage)   
 レーザーと本体と推定された現在位置を変換するために必要

scan (sensor_msgs/LaserScan) 
マップを作るための赤外線データ

自己位置をパブリッシュするためには、 Odometryを取ってこないといけない。
navigationスタックを利用して、自己位置(オドメトリ)をパブリッシュするコードを書く。

http://www.ros.org/wiki/navigation/Tutorials/RobotSetup/Odom
上のリンク先にパブリッシャのコードが載っている
ただ、navigationのチュートリアルはgroovyに対応していないので、
多少書き換える必要がある

$ cd catkin_ws/src
$ catkin_create_pkg robot_odom_test roscpp tf geometry_msgs nav_msgs

パッケージ作成時にnav_msgsを追加する
パッケージ名は適当に、robot_odom_test

$ cd src
$ emacs odom_test.cpp &

でsrcフォルダ内にodom_test.cppを作成し、リンク先のコードをコピペ

$ cd  ..
$ emacs CMakeLists.txt &

でrobot_odom_test直下に戻り、CMakeList.txtの末尾に

add_executable(odom_test src/odom_test.cpp)
target_link_libraries(odom_test ${catkin_LIBRARIES})

を追加
catkin_wsに戻って、

$ catkin_make

パブリッシュされてるか確認

$ roscore
$ rosrun robot_odom_test odom_test
$ rostopic list
/odom
/rosout
/rosout_agg
/tf


今度はリスナーを書く(そっちの方が難しそう・・・)
参考にする
http://www.ros.org/wiki/ja/navigation/Tutorials/RobotSetup/TF