Arduino Uno R4 Minima & WiFiをROS2と繋いでみる
はじめに
はじめまして。初めてブログ執筆をさせていただきます伊藤です。
今回は、新型のArduinoであるArduino Uno R4とロボット開発用のミドルウェアであるROS 2を、マイコン用のROS 2であるmicro-ROSを使用して接続し、サーボモーターを制御してみました。Arduino Uno R3は性能不足からmicro-ROSには対応していませんでしたが、性能が向上したArduino Uno R4はmicro-ROSに対応できるのかを検証してみます。
Arduino Uno R4にはWiFi非搭載モデルのArduino Uno R4 MinimaとWiFi搭載モデルのArduino Uno R4 WiFiの2モデルがあります。今回はまずArduino Uno R4 Minimaでサンプルコードを動かし、Arduino Uno R4 WiFiでサーボモータを制御してみます。
下が今回使用するArduino Uno R4 Minimaです。(以下、R4 Minimaと書きます)
(ご購入はこちらから)
全体的な形状はR3から引き継がれていますが、コネクタ形状や表面実装部品等、様々な部分が変更されています。最大の特徴として、メインプロセッサがATMega328Pからルネサス製のRA4M1に変更されており、クロック周波数やメモリ容量が大きく向上しています。
ROS 2のインストール
ROS 2はロボット制御用のミドルウェアで、主にロボットやIoTの研究用途で使用されています。最大の特徴は分散処理システムを構築するための通信機能が備わっていることで、ノードと呼ばれる実行ファイル同士が通信し互いにメッセ―ジを送り合い、様々な処理を実行します。
今回使用しているOSはUbuntu 22.04、ROS 2のディストリビューションはHumbleです。ROS 2をインストールする場合は、使用しているUbuntuのバージョンに合わせたディストリビューションをインストールして下さい。
まずはROS 2のGPGキーを取得します。ターミナルを開いて以下のコマンドを入力してください。
sudo apt update && sudo apt install curl -y
sudo curl -sSL https://raw.githubusercontent.com/ros/rosdistro/master/ros.key -o /usr/share/keyrings/ros-archive-keyring.gpg
次にリポジトリをsource.listに追加します。
echo "deb [arch=$(dpkg --print-architecture) signed-by=/usr/share/keyrings/ros-archive-keyring.gpg] http://packages.ros.org/ros2/ubuntu $(. /etc/os-release && echo $UBUNTU_CODENAME) main" | sudo tee /etc/apt/sources.list.d/ros2.list > /dev/null
続いてROS 2と必要なツールをインストールします。他のディストリビューションをインストールする場合はこのあとのコマンドの”humble”をインストールするディストリビューションの名前に置き換えて下さい。
sudo apt update && sudo apt upgrade
sudo apt install ros-humble-desktop python3-colcon-common-extensions python3-rosdep
最後にsetupファイルを読み込みます。毎回読み込むのは面倒なので、ターミナルを開くたびに実行されるスクリプトに記述しておきます。
source /opt/ros/humble/setup.bash
echo "source /opt/ros/humble/setup.bash" >> ~/.bashrc
micro-ROSをセットアップする
Arduino Uno R4とROS 2間で通信を行うために、micro-ros-arduinoとmicro-ROSエージェントをセットアップします。micro-ros-arduinoはArduinoでmicro-ROSを使用するためのライブラリです。micro-ROSエージェントを介してROS 2と通信し、ArduinoをROS 2のノードの1つとしてROS 2に統合する事ができます。
はじめに、ワークスペースの作成とmicro-ROSセットアップパッケージのダウンロードをします。
mkdir -p ~/ros2_ws/src
cd ~/ros2_ws/src/
git clone -b humble https://github.com/micro-ROS/micro_ros_setup.git src/micro_ros_setup
ダウンロードが完了したらros2_wsに戻り、依存関係の確認を行います。
cd ~/ros2_ws/
rosdep install -i --from-path src --rosdistro humble -y
続いてワークスペースのビルドを行います。
colcon build
source /opt/ros/humble/setup.bash
source ~/ros2_ws/install/setup.bash
echo "source ~/ros2_ws/install/setup.bash" >> ~/.bashrc
最後にmicro-ROSエージェントのセットアップ用のコードを実行して完了です。
ros2 run micro_ros_setup create_agent_ws.sh
ros2 run micro_ros_setup build_agent.sh
source ~/ros2_ws/install/setup.bash
micro-ROSエージェントのセットアップが完了したらmicro-ros-arduinoをダウンロードします。ここをクリックすると、自動的にファイルがダウンロードされます。
humble以外のディストリビューションを使用する場合は以下のURLのリンク先から適当なバージョンをダウンロードして下さい。
https://github.com/micro-ROS/micro_ros_arduino/releases
Arduino IDEを開き、スケッチ→ライブラリをインクルード→.ZIP形式のライブラリをインストール
の順に選択し、先程ダウンロードしたzipファイルを選択します。
micro-ros-arduinoはまだR4 Minimaに対応していないので、使うにはコードの修正が必要です。/Arduino/libraries/micro_ros_arduino/src/default_transport.cpp
の7行目を#include <sys/time.h>
から#include <time.h>
に書き換えます。
これでmicro-ros-arduinoのインストールも完了です。
R4 Minimaでサンプルコードを動かす
まずはmicro-ros-arduinoに入っているサンプルコードを動かしてみます。このときR4 Minimaのシリアルポート名を確認しておきます。ボード名の下に書かれている文字列です。今回の場合は「/dev/ttyACM0」となっています。
ファイル→スケッチ例→micro_ros_arduino→micro-ros_publisherを順番に選択し、ボードにスケッチを書き込みます。
書き込みが完了したら下のコマンドをターミナルに入力し、micro-ROSエージェントを起動します。
ros2 run micro_ros_agent micro_ros_agent serial --dev "port_name" -b 921600
"port_name"の部分はR4 Minimaのシリアルポート名に変更してください。
接続が完了すると、このような画面になります。
新しいターミナルを開き、以下のコマンドを入力します。
ros2 topic echo /micro_ros_arduino_node_publisher
ROS 2とR4 Minimaが正常に通信していれば、画像のように連続した整数が表示されます。
R4 WiFiでサーボモーターを動かす
次はR4 WiFiに接続し、無線でサーボモーターを制御してみます。GitHubにてmicro-ros-arduinoをR4 WiFiに対応させるプルリクエストを出してる方が居たので、それを参考にコードを修正します。
参考にしたプルリクエスト
https://github.com/micro-ROS/micro_ros_arduino/pull/1712
下が使用するArduino Uno R4 WiFiです。(以下、R4 WiFiと書きます)
(ご購入はこちらから)
まずは/Arduino/libraries/micro_ros_arduino/src
内のmicro_ros_arduino.h
とwifi_transport.cpp
を以下のように書き換えます。
・micro_ros_arduino.h書き換え前
・micro_ros_arduino.h書き換え後
・wifi_transport.cpp書き換え前
・wifi_transport.cpp書き換え後
次に、Arduino IDEで新規スケッチを開いて以下のコードを記述しR4 WiFiに書き込みます。
#include <stdio.h> //必要なライブラリをインクルードする
#include <micro_ros_arduino.h>
#include <rcl/rcl.h>
#include <rclc/rclc.h>
#include <rclc/executor.h>
#include <std_msgs/msg/int32.h>
#include <Servo.h>
rcl_publisher_t publisher; //変数を定義
rcl_subscription_t subscriber;
rclc_executor_t executor;
rclc_support_t support;
rcl_allocator_t allocator;
rcl_node_t node;
std_msgs__msg__Int32 msg;
Servo myservo;
int deg = 0;
void callback(const void * msgin){ //受け取った角度にサーボを動かす
const std_msgs__msg__Int32 * msg = (const std_msgs__msg__Int32 *)msgin;
deg = int(msg->data);
myservo.write(deg);
}
void setup() {
//使用するWiFiのssid、パスワード、ROS 2が入ったPCのipアドレスを下に入力
set_microros_wifi_transports("WIFI SSID", "WIFI PASS", "IP", 8888);
delay(2000);
allocator = rcl_get_default_allocator();
rclc_support_init(&support, 0, NULL, &allocator);
rclc_node_init_default(&node, "servo", "", &support); //Nodeの作成
rclc_subscription_init_default( //Subscriberの作成
&subscriber, &node,
ROSIDL_GET_MSG_TYPE_SUPPORT(std_msgs, msg, Int32),
"servo/deg");
rclc_executor_init(&executor, &support.context, 1, &allocator); //Executorの作成
rclc_executor_add_subscription(
&executor, &subscriber, &msg, &callback, ON_NEW_DATA);
myservo.attach(3,500,2500);
}
void loop() {
delay(10);
rclc_executor_spin_some(&executor, RCL_MS_TO_NS(100));
}
R4 WiFiにコードを書き込めたら以下のコマンドでmicro-ROSエージェントを起動します。
ros2 run micro_ros_agent micro_ros_agent udp4 --port 8888 -v6
そしてR4 WiFiの5V、GND、3番ピンからサーボモータへジャンパワイヤで配線します。電源はモバイルバッテリーから供給しています。
別のターミナルで以下のコマンドを入力すると、{date:}内に書かれた角度にサーボモーターが動きます。
ros2 topic pub --once /servo/deg std_msgs/msg/Int32 "{data: 180}"
電気スイッチなどに取り付ければ、遠隔で部屋の電灯のオン/オフを制御する事もできます。
おわりに
検証した結果、Arduino Uno R4 MinimaとArduino Uno R4 WiFiはROS 2で動かせる事が分かりました。比較的入手しやすいArduino UnoシリーズがROS 2で使用できるようになった事で、初心者のロボットやIoTへの参入障壁が低くなるかもしれません。
ぜひArduino Uno R4を使った電子工作を楽しんでみてください!