8000 World plugins · modulabs/gazebo-tutorial Wiki · GitHub
[go: up one dir, main page]
More Web Proxy on the site http://driver.im/
Skip to content
Hancheol Choi edited this page Feb 10, 2018 · 7 revisions

Prerequisites:

Code:

Source code: gazebo/examples/plugins/factory

실행중인 시뮬레이션에서 어떤 모델이 존재하는지 그리고 언제 삽입되어야 하는지를 제어하는 것은 유용할 수 있다. 이번 튜토리얼에서는 사전 정의된 모델과 사용자 정의 모델을 가제보에 삽입하는 방법을 설명한다.

이전에 설명한 gazebo_plugin_tutorial을 사용한다

$ mkdir ~/gazebo_plugin_tutorial
$ cd ~/gazebo_plugin_tutorial

새로운 파일을 생성한다:

$ gedit factory.cc

factory.cc 파일에 아래 내용을 복사한다:

#include <ignition/math/Pose3.hh>
#include "gazebo/physics/physics.hh"
#include "gazebo/common/common.hh"
#include "gazebo/gazebo.hh"

namespace gazebo
{
class Factory : public WorldPlugin
{
  public: void Load(physics::WorldPtr _parent, sdf::ElementPtr /*_sdf*/)
  {
    // Option 1: Insert model from file via function call.
    // The filename must be in the GAZEBO_MODEL_PATH environment variable.
    _parent->InsertModelFile("model://box");

    // Option 2: Insert model from string via function call.
    // Insert a sphere model from string
    sdf::SDF sphereSDF;
    sphereSDF.SetFromString(
       "<sdf version ='1.4'>\
          <model name ='sphere'>\
            <pose>1 0 0 0 0 0</pose>\
            <link name ='link'>\
              <pose>0 0 .5 0 0 0</pose>\
              <collision name ='collision'>\
                <geometry>\
                  <sphere><radius>0.5</radius></sphere>\
                </geometry>\
              </collision>\
              <visual name ='visual'>\
                <geometry>\
                  <sphere><radius>0.5</radius></sphere>\
                </geometry>\
              </visual>\
            </link>\
          </model>\
        </sdf>");
    // Demonstrate using a custom model name.
    sdf::ElementPtr model = sphereSDF.Root()->GetElement("model");
    model->GetAttribute("name")->SetFromString("unique_sphere");
    _parent->InsertModelSDF(sphereSDF);

    // Option 3: Insert model from file via message passing.
    {
      // Create a new transport node
      transport::NodePtr node(new transport::Node());

      // Initialize the node with the world name
      node->Init(_parent->GetName());

      // Create a publisher on the ~/factory topic
      transport::PublisherPtr factoryPub =
      node->Advertise<msgs::Factory>("~/factory");

      // Create the message
      msgs::Factory msg;

      // Model file to load
      msg.set_sdf_filename("model://cylinder");

      // Pose to initialize the model to
      msgs::Set(msg.mutable_pose(),
          ignition::math::Pose3d(
            ignition::math::Vector3d(1, -2, 0),
            ignition::math::Quaterniond(0, 0, 0)));

      // Send the message
      factoryPub->Publish(msg);
    }
  }
};

// Register this plugin with the simulator
GZ_REGISTER_WORLD_PLUGIN(Factory)
}

The Code Explained

코드의 첫부분에 world 러그인을 생성한다.

#include <ignition/math/Pose3.hh>
#include "gazebo/physics/physics.hh"
#include "gazebo/common/common.hh"
#include "gazebo/gazebo.hh"

namespace gazebo
{
class Factory : public WorldPlugin
{
  public: void Load(physics::WorldPtr _parent, sdf::ElementPtr /*_sdf*/)

Load 함수에서는 모델 삽입을 위한 세가지 방법이 있다.

첫번째는 World method를 사용하여 GAZEBO_MODEL_PATH 환경 변수로 정의된 리소스 경로에 있는 파일을 기반으로 모델을 로드하는 방법이다.

    // Option 1: Insert model from file via function call.
    // The filename must be in the GAZEBO_MODEL_PATH environment variable.
    _parent->InsertModelFile("model://box");

두번째는 World method를 사용하여 문자열 데이터(string data)로 이루어진 모델 파일을 로드하는 것이다.

    // Option 2: Insert model from string via function call.
    // Insert a sphere model from string
    sdf::SDF sphereSDF;
    sphereSDF.SetFromString(
       "<sdf version ='1.4'>\
          <model name ='sphere'>\
            <pose>1 0 0 0 0 0</pose>\
            <link name ='link'>\
              <pose>0 0 .5 0 0 0</pose>\
              <collision name ='collision'>\
                <geometry>\
                  <sphere><radius>0.5</radius></sphere>\
                </geometry>\
              </collision>\
              <visual name ='visual'>\
                <geometry>\
                  <sphere><radius>0.5</radius></sphere>\
                </geometry>\
              </visual>\
            </link>\
          </model>\
        </sdf>");
    // Demonstrate using a custom model name.
    sdf::ElementPtr model = sphereSDF.Root()->GetElement("model");
    model->GetAttribute("name")->SetFromString("unique_sphere");
    _parent->InsertModelSDF(sphereSDF);

세번째는 메시지 전달 메커니즘을 사용하여 모델을 삽입하는 것이다. 이 방법은 네트워크 연결을 통해 가제보와 통신하는 독립 실행형 응용 프로그램에 가장 유용하다

    // Option 3: Insert model from file via message passing.
    {
      // Create a new transport node
      transport::NodePtr node(new transport::Node());

      // Initialize the node with the world name
      node->Init(_parent->GetName());

      // Create a publisher on the ~/factory topic
      transport::PublisherPtr factoryPub =
      node->Advertise<msgs::Factory>("~/factory");

      // Create the message
      msgs::Factory msg;

      // Model file to load
      msg.set_sdf_filename("model://cylinder");

      // Pose to initialize the model to
      msgs::Set(msg.mutable_pose(),
          ignition::math::Pose3d(
            ignition::math::Vector3d(1, -2, 0),
            ignition::math::Quaterniond(0, 0, 0)));

      // Send the message
      factoryPub->Publish(msg);

Compile

Plugin Overview Tutorial 과정을 거쳤다면, 위 코드를 ~/gazebo_plugin_tutorial/factory.cc로 저장하고 ~/gazebo_plugin_tutorial/CMakeLists.txt에 다음행을 추가하면 된다.

add_library(factory SHARED factory.cc)
target_link_libraries(factory ${GAZEBO_LIBRARIES})

이 코드를 컴파일 하면, 가제보 시뮬레이션에 삽입할 수 있는 공유 라이브러리 ~/gazebo_plugin_tutorial/build/libfactory.so가 생성된다

$ mkdir ~/gazebo_plugin_tutorial/build
$ cd ~/gazebo_plugin_tutorial/build
$ cmake ../
$ make

Make the shapes

모델 디렉토리와 박스, 실린더를 만든다

$ mkdir ~/gazebo_plugin_tutorial/models
$ cd ~/gazebo_plugin_tutorial/models
$ mkdir box cylinder

박스 모델을 만든다

$ cd box
$ gedit model.sdf

box/model.sdf에 아래 내용을 복사한다

<?xml version='1.0'?>
<sdf version ='1.6'>
  <model name ='box'>
    <pose>1 2 0 0 0 0</pose>
    <link name ='link'>
      <pose>0 0 .5 0 0 0</pose>
      <collision name ='collision'>
        <geometry>
          <box><size>1 1 1</size></box>
        </geometry>
      </collision>
      <visual name ='visual'>
        <geometry>
          <box><size>1 1 1</size></box>
        </geometry>
      </visual>
    </link>
  </model>
</sdf>

model.config 파일을 생성한다

$ gedit model.config

model.config에 아래 내용을 복사한다

<?xml version='1.0'?>

<model>
  <name>box</name>
  <version>1.0</version>
  <sdf >model.sdf</sdf>

  <author>
    <name>me</name>
    <email>somebody@somewhere.com</email>
  </author>

  <description>
    A simple Box.
  </description>
</model>

실린더 디렉토리로 이동하여 새로운 model.sdf 파일을 생성한다

$ cd ~/gazebo_plugin_tutorial/models/cylinder
$ gedit model.sdf

model.sdf에 아래 내용을 복사한다

<?xml version='1.0'?>
<sdf version ='1.6'>
  <model name ='cylinder'>
    <pose>1 2 0 0 0 0</pose>
    <link name ='link'>
      <pose>0 0 .5 0 0 0</pose>
      <collision name ='collision'>
        <geometry>
          <cylinder><radius>0.5</radius><length>1</length></cylinder>
        </geometry>
      </collision>
      <visual name='visual'>
        <geometry>
          <cylinder><radius>0.5</radius><length>1</length></cylinder>
        </geometry>
      </visual>
    </link>
  </model>
</sdf>

model.config 파일을 생성한다

$ gedit model.config

model.config 파일에 아래 내용을 복사한다

<?xml version='1.0'?>

<model>
  <name>cylinder</name>
  <version>1.0</version>
  <sdf>model.sdf</sdf>

  <author>
    <name>me</name>
    <email>somebody@somewhere.com</email>
  </author>

  <description>
    A simple cylinder.
  </description>
</model>

Run the code

$GAZEBO_MODEL_PATH가 새 모델 디렉토리를 참조하는지 확인한다

$ export GAZEBO_MODEL_PATH=$HOME/gazebo_plugin_tutorial/models:$GAZEBO_MODEL_PATH

GAZEBO_PLUGIN_PATH에 라이브러리를 추가한다:

$ export GAZEBO_PLUGIN_PATH=$HOME/gazebo_plugin_tutorial/build:$GAZEBO_PLUGIN_PATH

world SDF 파일 ~/gazebo_plugin_tutorial/factory.world을 생성한다

$ cd ~/gazebo_plugin_tutorial
$ gedit factory.world

world에 아래 내용을 복사한다

<?xml version="1.0"?>
<sdf version="1.4">
  <world name="default">
    <include>
      <uri>model://ground_plane</uri>
    </include>

    <include>
      <uri>model://sun</uri>
    </include>

    <plugin name="factory" filename="libfactory.so"/>
  </world>
</sdf>

가제보 실행

$ gazebo ~/gazebo_plugin_tutorial/factory.world

가제보 창에는 구, 상자, 실린더가 연속으로 배치된 환경이 보여야 한다.

Table of Contents




Clone this wiki locally
0