Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Ignition ros2 control #1

Merged
merged 50 commits into from
Dec 3, 2021
Merged
Show file tree
Hide file tree
Changes from 41 commits
Commits
Show all changes
50 commits
Select commit Hold shift + click to select a range
a512367
Added ignition_ros2_control
ahcorde Mar 13, 2021
2b68d6f
Added ignition_ros2_control demos
ahcorde Mar 13, 2021
c85f448
Added github actions
ahcorde Mar 13, 2021
d7d44ec
udpate github actions
ahcorde Mar 13, 2021
483a973
update github actions
ahcorde Mar 14, 2021
33a888b
update github actions
ahcorde Mar 14, 2021
9f47fe7
update github actions
ahcorde Mar 14, 2021
622614e
update github actions
ahcorde Mar 14, 2021
5df52f9
update github actions
ahcorde Mar 14, 2021
9121427
update github actions
ahcorde Mar 14, 2021
fa457b6
update github actions
ahcorde Mar 14, 2021
4b4c188
update github actions
ahcorde Mar 14, 2021
cb42397
update github actions
ahcorde Mar 14, 2021
52c5a08
update github actions
ahcorde Mar 14, 2021
a1d1da8
Fixed warnings
ahcorde Mar 20, 2021
59baef1
Update CI
ahcorde Mar 20, 2021
3cd82f9
Update CI
ahcorde Mar 21, 2021
55dd076
update README.md
ahcorde Mar 21, 2021
af61b68
Fixed color in xacros
ahcorde Apr 13, 2021
57b34fe
Added missed dependency
ahcorde Apr 15, 2021
d7451ad
Added missed dependency
ahcorde Apr 15, 2021
d7991fe
use string option instaed of topic
ahcorde Apr 16, 2021
a5e0920
Added Dockerfile
ahcorde Apr 16, 2021
7e28cf2
Improved README.md
ahcorde Apr 16, 2021
3efa1a9
Removed ignition-physics dependency and other minor fixes
ahcorde Apr 23, 2021
bfdc61c
Added some of the feedback
ahcorde May 14, 2021
24b07f4
Write joints on each simulation update period
ahcorde Jun 15, 2021
117331d
Ensure that sim_joints_ always has the same number of elements as the…
ahcorde Jun 15, 2021
8207420
Join with the controller manager's executor thread on exit
ahcorde Jun 15, 2021
c917a8c
Forward sdf ros remappings to loaded controllers
ahcorde Jun 15, 2021
5a21c7a
Update ign_ros2_control
ahcorde Jun 15, 2021
6e56564
make linters happy
ahcorde Jun 15, 2021
5f596ec
make linters happy
ahcorde Jun 15, 2021
d50c181
make linters happy
ahcorde Jun 16, 2021
0554ee5
Citadel support (#4)
chapulina Jun 25, 2021
6b8a227
Added some fixes
ahcorde Sep 20, 2021
c157354
fixed IMU
ahcorde Sep 22, 2021
b834eae
Use std instead of boost
ahcorde Nov 25, 2021
766ccad
Fortress support from cmake (#12)
Nov 26, 2021
054d2b5
Pass ROS time instead of SYSTEM time to update function
ahcorde Nov 29, 2021
a11c0c3
Fixed cmake and package
ahcorde Nov 29, 2021
abd6d69
added feedback
ahcorde Nov 30, 2021
6ce4263
Update License
ahcorde Nov 30, 2021
c458ec1
typo
ahcorde Nov 30, 2021
1878091
Added feedback
ahcorde Nov 30, 2021
785cac4
Added feedback
ahcorde Dec 3, 2021
d47b38b
CI
ahcorde Dec 3, 2021
a0ab577
remove fortress from CI
ahcorde Dec 3, 2021
3341771
make linters happy
ahcorde Dec 3, 2021
263a190
make linters happy
ahcorde Dec 3, 2021
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
56 changes: 56 additions & 0 deletions .github/workflows/ci.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
name: Ignition ros2 control CI

on:
pull_request:
push:
branches: [ master ]

jobs:
build:
runs-on: ubuntu-latest
container:
image: ubuntu:20.04
steps:
- uses: actions/checkout@v2
- name: Setup colcon workspace
id: configure
run: |
export DEBIAN_FRONTEND=noninteractive
apt update -qq
apt install -qq -y lsb-release wget curl gnupg2
cd ..
mkdir -p /home/ros2_ws/src
cp -r ign_ros2_control /home/ros2_ws/src/
sh -c 'echo "deb http://packages.osrfoundation.org/gazebo/ubuntu-stable `lsb_release -cs` main" > /etc/apt/sources.list.d/gazebo-stable.list'
ahcorde marked this conversation as resolved.
Show resolved Hide resolved
wget https://packages.osrfoundation.org/gazebo.key -O - | apt-key add -
sh -c 'echo "deb http://packages.ros.org/ros2/ubuntu `lsb_release -cs` main" > /etc/apt/sources.list.d/ros2-latest.list'
curl -s https://raw.githubusercontent.com/ros/rosdistro/master/ros.asc | apt-key add -
IGN_DEPS="libignition-gazebo5-dev libignition-plugin-dev libignition-utils1-cli-dev"
ahcorde marked this conversation as resolved.
Show resolved Hide resolved
apt-get update && apt-get upgrade -q -y
apt-get update && apt-get install -qq -y \
dirmngr \
gnupg2 \
lsb-release \
python3-colcon-ros \
python3-colcon-common-extensions \
python3-rosdep \
build-essential \
$IGN_DEPS
cd /home/ros2_ws/src/
rosdep init
rosdep update
rosdep install --from-paths ./ -i -y --rosdistro foxy \
--ignore-src --skip-keys "ignition-gazebo5"
ahcorde marked this conversation as resolved.
Show resolved Hide resolved
- name: Build project
id: build
run: |
cd /home/ros2_ws/
. /opt/ros/foxy/local_setup.sh
colcon build --packages-up-to ignition_ros2_control_demos
- name: Run tests
id: test
run: |
cd /home/ros2_ws/
. /opt/ros/foxy/local_setup.sh
colcon test --event-handlers console_direct+ --packages-select ignition_ros2_control ignition_ros2_control_demos
colcon test-result
41 changes: 41 additions & 0 deletions Dockerfile/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
FROM osrf/ros:foxy-desktop

# Make sure everything is up to date before building from source
RUN apt-get update \
&& apt-get upgrade -y \
&& apt-get update && apt-get install -q -y --no-install-recommends \
dirmngr \
gnupg2 \
lsb-release \
wget \
curl \
&& apt-get clean

RUN sh -c 'echo "deb http://packages.osrfoundation.org/gazebo/ubuntu-stable `lsb_release -cs` main" > /etc/apt/sources.list.d/gazebo-stable.list' && \
wget https://packages.osrfoundation.org/gazebo.key -O - | apt-key add - && \
sh -c 'echo "deb http://packages.ros.org/ros2/ubuntu `lsb_release -cs` main" > /etc/apt/sources.list.d/ros2-latest.list' && \
curl -s https://raw.githubusercontent.com/ros/rosdistro/master/ros.asc | apt-key add - && \
apt-get update && apt-get install -q -y --no-install-recommends \
python3-colcon-ros \
python3-colcon-common-extensions \
python3-rosdep \
libignition-gazebo5-dev \
ahcorde marked this conversation as resolved.
Show resolved Hide resolved
libignition-plugin-dev \
libignition-utils1-cli-dev \
&& apt-get clean

RUN mkdir -p /home/ros2_ws/src \
&& cd /home/ros2_ws/src \
&& git clone https:/ignitionrobotics/ign_ros2_control/ -b ahcorde/ign_ros2_control \
&& rosdep update \
&& rosdep install --from-paths ./ -i -y --rosdistro foxy \
--ignore-src --skip-keys "ignition-gazebo5"

RUN cd /home/ros2_ws/ \
&& . /opt/ros/foxy/setup.sh \
&& colcon build --merge-install

COPY entrypoint.sh /entrypoint.sh
ENTRYPOINT ["/entrypoint.sh"]

CMD ros2 launch ignition_ros2_control_demos cart_example_position.launch.py
5 changes: 5 additions & 0 deletions Dockerfile/entrypoint.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
#!/bin/sh

. /opt/ros/foxy/setup.sh
. /home/ros2_ws/install/setup.sh
exec "$@"
197 changes: 197 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -1 +1,198 @@
# ign_ros2_control

This is a ROS 2 package for integrating the `ros2_control` controller architecture with the [Ignition Gazebo](http://ignitionrobotics.org/) simulator.
More information about `ros2_control` can be found here: https://ros-controls.github.io/control.ros.org/
ahcorde marked this conversation as resolved.
Show resolved Hide resolved

This package provides an Ignition Gazebo system plugin which instantiates a `ros2_control` controller manager and connects it to a Gazebo model.

Tested on:

- [ROS 2 Foxy](https://docs.ros.org/en/foxy/Installation.html)
- [Ignition Edifice](https://ignitionrobotics.org/docs/edifice)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would it be possible to target the official combinations?

  • Foxy + Citadel (which we can release straight away)
  • Galactic + Edifice (which we can release once ros2_control is in Galactic

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this can be backported: gazebosim/gz-sim#536

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looking closer at the implementation now, you could consider getting the step size from UpdateInfo every iteration.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See #4 for how that could work

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@ahcorde , with #4 in, are you planning to update this PR to target Citadel + Foxy?

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I see the code supports more combinations now. Can we document them here?


# Usage

## Video + Pictures

![](img/ign_ros2_control.gif)

## Running

### Modifying or building your own

```bash
cd Docker
ahcorde marked this conversation as resolved.
Show resolved Hide resolved
docker build -t ignition_ros2_control .
ahcorde marked this conversation as resolved.
Show resolved Hide resolved
```

### To run the demo

#### Using Docker

Docker allows us to run the demo without the GUI if configured properly. The following command runs the demo without the GUI:

```bash
docker run -it --rm --name ignition_ros2_control_demo --net host ignition_ros2_control ros2 launch ignition_ros2_control_demos cart_example_position.launch.py gui:=false
```

Then on your local machine, you can run the Gazebo client:

```bash
ign gazebo -g
```

#### Using Rocker

To run the demo with the GUI, we are going to use [rocker](https:/osrf/rocker/), which is a tool to run docker
images with customized local support injected for things like nvidia support. Rocker also supports user id specific files for cleaner
mounting file permissions. You can install this tool with the following [instructions](https:/osrf/rocker/#installation) (make sure you meet all of the [prerequisites](https:/osrf/rocker/#prerequisites)).

The following command will launch Gazebo:
ahcorde marked this conversation as resolved.
Show resolved Hide resolved

```bash
rocker --x11 --nvidia --name ignition_ros2_control_demo ignition_ros2_control:latest
```

The following commands allow the cart to be moved along the rail:

```bash
docker exec -it ignition_ros2_control_demo bash
source /home/ros2_ws/install/setup.bash
ros2 run ignition_ros2_control_demos example_position
```

## Add ros2_control tag to a URDF
ahcorde marked this conversation as resolved.
Show resolved Hide resolved

To use `ros2_control` with your robot, you need to add some additional elements to your URDF.
You should include the tag `<ros2_control>` to access and control the robot interfaces. We should
include:

- a specific `<plugin>` for our robot
- `<joint>` tag including the robot controllers: commands and states.

```xml
<ros2_control name="GazeboSystem" type="system">
ahcorde marked this conversation as resolved.
Show resolved Hide resolved
<hardware>
<plugin>ignition_ros2_control/GazeboSystem</plugin>
</hardware>
<joint name="slider_to_cart">
<command_interface name="effort">
<param name="min">-1000</param>
<param name="max">1000</param>
</command_interface>
<state_interface name="position"/>
<state_interface name="velocity"/>
<state_interface name="effort"/>
</joint>
</ros2_control>
```

## Add the ignition_ros2_control plugin

In addition to the `ros2_control` tags, a Gazebo plugin needs to be added to your URDF that
actually parses the `ros2_control` tags and loads the appropriate hardware interfaces and
controller manager. By default the `ignition_ros2_control` plugin is very simple, though it is also
extensible via an additional plugin architecture to allow power users to create their own custom
robot hardware interfaces between `ros2_control` and Gazebo.

```xml
<gazebo>
<plugin filename="libignition_ros2_control.so" name="ignition_ros2_control">
<robot_param>robot_description</robot_param>
<robot_param_node>robot_state_publisher</robot_param_node>
<parameters>$(find ignition_ros2_control_demos)/config/cartpole_controller.yaml</parameters>
</plugin>
</gazebo>
```

The `ignition_ros2_control` `<plugin>` tag also has the following optional child elements:

- `<parameters>`: YAML file with the configuration of the controllers

#### Default ignition_ros2_control Behavior

By default, without a `<plugin>` tag, `ignition_ros2_control` will attempt to get all of the information it needs to interface with a ros2_control-based controller out of the URDF. This is sufficient for most cases, and good for at least getting started.

The default behavior provides the following ros2_control interfaces:

- hardware_interface::JointStateInterface
- hardware_interface::EffortJointInterface
- hardware_interface::VelocityJointInterface
Comment on lines +119 to +121

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should we provide something like a link to these interfaces so that users can learn more about them if they'd like?


#### Advanced: custom ignition_ros2_control Simulation Plugins

The `ignition_ros2_control` Gazebo plugin also provides a pluginlib-based interface to implement custom interfaces between Gazebo and `ros2_control` for simulating more complex mechanisms (nonlinear springs, linkages, etc).

These plugins must inherit the `ignition_ros2_control::GazeboSystemInterface`, which implements a simulated `ros2_control`
`hardware_interface::SystemInterface`. SystemInterface provides API-level access to read and command joint properties.

The respective GazeboSystemInterface sub-class is specified in a URDF model and is loaded when the
robot model is loaded. For example, the following XML will load the default plugin:
```xml
<ros2_control name="GazeboSystem" type="system">
ahcorde marked this conversation as resolved.
Show resolved Hide resolved
<hardware>
<plugin>ignition_ros2_control/GazeboSystem</plugin>
ahcorde marked this conversation as resolved.
Show resolved Hide resolved
</hardware>
...
<ros2_control>
<gazebo>
<plugin name="ignition_ros2_control" filename="libignition_ros2_control.so">
...
</plugin>
</gazebo>
```

#### Set up controllers

Use the tag `<parameters>` inside `<plugin>` to set the YAML file with the controller configuration.

```xml
<gazebo>
<plugin name="ignition_ros2_control" filename="libignition_ros2_control.so">
<parameters>$(find ignition_ros2_control_demos)/config/cartpole_controller.yaml</parameters>
</plugin>
<gazebo>
```

This controller publishes the state of all resources registered to a
`hardware_interface::StateInterface` to a topic of type `sensor_msgs/msg/JointState`.
The following is a basic configuration of the controller.

```yaml
joint_state_controller:
ros__parameters:
type: joint_state_controller/JointStateController
```

This controller creates an action called `/cart_pole_controller/follow_joint_trajectory` of type `control_msgs::action::FollowJointTrajectory`.

```yaml
cart_pole_controller:
ros__parameters:
type: joint_trajectory_controller/JointTrajectoryController
joints:
- slider_to_cart
write_op_modes:
- slider_to_cart
```
#### Executing the examples

There are some examples in the `ignition_ros2_control_demos` package. These examples allow to launch a cart in a 30 meter rail.

You can run some of the example configurations by running the following commands:

```bash
ros2 launch ignition_ros2_control_demos cart_example_position.launch.py
ros2 launch ignition_ros2_control_demos cart_example_velocity.launch.py
ros2 launch ignition_ros2_control_demos cart_example_effort.launch.py
Comment on lines +188 to +190

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should we add instructions for building a workspace with the demos first (including installing dependencies) before users try these commands?

```

Send example commands:

When the Gazebo world is launched, you can run some of the following commands to move the cart.

```bash
ros2 run ignition_ros2_control_demos example_position
ros2 run ignition_ros2_control_demos example_velocity
ros2 run ignition_ros2_control_demos example_effort
```
Loading