본문 바로가기
정나우/ROS

URDF, Xacro로 매니퓰레이터 만들기

by 정_나우 2022. 7. 18.

URDF란

Unified Robot Description Format의 준말로, 로봇모델을 표현하기 위한 XML파일이다.

이것을 통해 로봇, 센서, 작업 환경을 정의할 수 있다.

 

Xacro란

XML + Macro로, 복잡한 로봇모델을 만들 때 URDF로 일일이 작업을 하기에는 효율성이 매우 떨어지기 때문에, 기존의 URDF에 단순성, 코드의 재활용성, 모듈화, 프로그램 가능성이 추가된 것이다. 변수, 상수, 수학표현, 조건문을 사용할 수 있다.


사진처럼 3축 매니퓰레이터를 만들어보자.


VScode를 이용한다면 Extensions에서 URDF를 설치하여 파일을 작성하면 훨씬 빠르고 정확하게 작성이 가능하다.

 

또한, Extension에서 ROS를 설치하여 Ctrl+Shift+P를 눌러 URDF Preview를 이용하여 URDF를 작성하면서 동시에 문법이 정확한지 확인할 수 있다. (저장하면 변경내용이 적용된다.)


전문은 다음과 같다.

cd

cd ~/catkin_ws/src
catkin_create_pkg urdf
cd urdf
mkdir robots
cd robots
code manipulator.xacro

vscode가 열리면 다음 내용을 작성한다.

<?xml version="1.0"?>
<robot xmlns:xacro="http://www.ros.org/wiki/xacro" name="dyros_manipulator3r">

<xacro:property name="width" value="0.05"/>
<xacro:property name="height" value="0.2"/>
<xacro:property name="mass" value="0.1"/>

    <link name="base_link">
        <inertial>
            <origin xyz="0.0 0.0 ${height/2}" rpy="0.0 0.0 0.0"/>
            <mass value="${mass}"/>
            <inertia ixx="1.0" ixy="0.0" ixz="0.0" iyy="1.0" iyz="0.0" izz="1.0"/>
        </inertial>
        <visual>
            <origin xyz="0.0 0.0 ${height/2}" rpy="0.0 0.0 0.0"/>
            <geometry>
                <box size="${width} ${width} ${height}"/>
            </geometry>
            <material name="base_link">
                <color rgba="1.0 0.0 0.0 1.0"/>
            </material>
        </visual>
        <collision>
            <origin xyz="0.0 0.0 ${height/2}" rpy="0.0 0.0 0.0"/>
            <geometry>
                <box size="${width} ${width} ${height}"/>
            </geometry>
        </collision>
    </link>

    <joint name="Joint1" type="revolute">
        <origin xyz="0.0 0.0 0.25" rpy="0.0 0.0 0.0"/>
        <parent link="base_link"/>
        <child link="Link1"/>
        <axis xyz="1.0 0.0 0.0"/>
        <limit lower="-3.14" upper="3.14" effort="30" velocity="1"/>
    </joint>

    <link name="Link1">
        <inertial>
            <origin xyz="0.0 0.0 ${height/2}" rpy="0.0 0.0 0.0"/>
            <mass value="${mass}"/>
            <inertia ixx="${mass/12*(width*width+width*width)}" ixy="0.0" ixz="0.0" 
                iyy="${mass/12*(width*width+width*width)}" iyz="0.0" 
                izz="${mass/12*(height*height+height*height)}"/>
        </inertial>
        <visual>
            <origin xyz="0.0 0.0 ${height/2}" rpy="0.0 0.0 0.0"/>
            <geometry>
                <box size="${width} ${width} ${height}"/>
            </geometry>
            <material name="link1">
                <color rgba="0.0 1.0 0.0 1.0"/>
            </material>
        </visual>
        <collision>
            <origin xyz="0.0 0.0 ${height/2}" rpy="0.0 0.0 0.0"/>
            <geometry>
                <box size="${width} ${width} ${height}"/>
            </geometry>
        </collision>
    </link>
    
    <joint name="Joint2" type="revolute">
        <origin xyz="0.0 0.0 0.25" rpy="0.0 0.0 0.0"/>
        <parent link="Link1"/>
        <child link="Link2"/>
        <axis xyz="1.0 0.0 0.0"/>
        <limit lower="-3.14" upper="3.14" effort="30" velocity="1"/>
    </joint>

    <link name="Link2">
        <inertial>
            <origin xyz="0.0 0.0 ${height/2}" rpy="0.0 0.0 0.0"/>
            <mass value="${mass}"/>
            <inertia ixx="${mass/12*(width*width+width*width)}" ixy="0.0" ixz="0.0" 
                iyy="${mass/12*(width*width+width*width)}" iyz="0.0" 
                izz="${mass/12*(height*height+height*height)}"/>
        </inertial>
        <visual>
            <origin xyz="0.0 0.0 ${height/2}" rpy="0.0 0.0 0.0"/>
            <geometry>
                <box size="${width} ${width} ${height}"/>
            </geometry>
            <material name="link2">
                <color rgba="0.0 0.0 1.0 1.0"/>
            </material>
        </visual>
        <collision>
            <origin xyz="0.0 0.0 ${height/2}" rpy="0.0 0.0 0.0"/>
            <geometry>
                <box size="${width} ${width} ${height}"/>
            </geometry>
        </collision>
    </link>

    <joint name="Joint3" type="revolute">
        <origin xyz="0.0 0.0 0.25" rpy="0.0 0.0 0.0"/>
        <parent link="Link2"/>
        <child link="Link3"/>
        <axis xyz="1.0 0.0 0.0"/>
        <limit lower="-3.14" upper="3.14" effort="30" velocity="1"/>
    </joint>

    <link name="Link3">
        <inertial>
            <origin xyz="0.0 0.0 ${height/2}" rpy="0.0 0.0 0.0"/>
            <mass value="${mass}"/>
            <inertia ixx="${mass/12*(width*width+width*width)}" ixy="0.0" ixz="0.0" 
                iyy="${mass/12*(width*width+width*width)}" iyz="0.0" 
                izz="${mass/12*(height*height+height*height)}"/>
        </inertial>
        <visual>
            <origin xyz="0.0 0.0 ${height/2}" rpy="0.0 0.0 0.0"/>
            <geometry>
                <box size="${width} ${width} ${height}"/>
            </geometry>
            <material name="link3">
                <color rgba="0.0 1.0 1.0 1.0"/>
            </material>
        </visual>
        <collision>
            <origin xyz="0.0 0.0 ${height/2}" rpy="0.0 0.0 0.0"/>
            <geometry>
                <box size="${width} ${width} ${height}"/>
            </geometry>
        </collision>
    </link>
</robot>

 

다음 부분은 자주 사용하는 숫자들을 변수로 설정해둔 것이다.

이는 나중에 밑에서 계산식을 이용할 때 일일이 숫자를 다 안 바꾸고 맨 위에 변수에 해당되는 숫자만 바꾸면 되게 하므로 시간과 오류 발생할 일을 줄여준다.

<xacro:property name="width" value="0.05"/>
<xacro:property name="height" value="0.2"/>
<xacro:property name="mass" value="0.1"/>

 

다음 부분은 변수를 활용한 내용이다.

단순하게 변수만 불러올 수도 있고, 변수에 간단한 계산식을 추가할 수도 있다. 특히 관성모멘트를 일일이 계산하지 않아도 돼서 매우 편하다.

    <link name="Link1">
        <inertial>
            <origin xyz="0.0 0.0 ${height/2}" rpy="0.0 0.0 0.0"/>
            <mass value="${mass}"/>
            <inertia ixx="${mass/12*(width*width+width*width)}" ixy="0.0" ixz="0.0" 
                iyy="${mass/12*(width*width+width*width)}" iyz="0.0" 
                izz="${mass/12*(height*height+height*height)}"/>
        </inertial>

 

이런 식으로 링크를 만들고 링크 사이의 조인트를 만드는 식으로 자신의 입맛에 맞게 작성을 하면 된다.

그리고 visual부분에 material 이름을 설정하지 않으면 나중에 rviz를 실행할 때 오류가 발생하므로 꼭 이름을 설정해줘야 하고, 링크별 material 이름은 다르게 설정해야 한다.

 


rviz로 확인하기 위해 다음 명령어를 입력해준다.

sudo apt-get install ros-melodic-joint-state-publisher-gui
roslaunch urdf_tutorial display.launch model:=robots/dyros_manipulator3r.urdf

 

댓글