就如各位所見,使用ROS之后,一般的循環(huán)函數(shù)就會變得相當簡單。循環(huán)函數(shù)只會訂閱(subscribe)數(shù)據(jù),任何Arduino循環(huán)都一樣。設定時要將ROS初始化,將各個ROS訊息訂閱者的訂閱叫出來。每個訂閱者會占據(jù)Arduino的RAM,數(shù)量取決于要用程序代碼做什么,以6個到12個為限。
Servo servo;
void servo_cb( const std_msgs::Float32& msg )
{
const float min = 45;
const float range = 90;
float v = msg.data;
if( v > 1 ) v = 1;
if( v < 0 ) v = 0;
float angle = min + (range * v);
servo.write(angle);
}
ros::Subscriber
ros::NodeHandle nh;
void setup()
{
servo.attach(SERVOPIN);
nh.initNode();
nh.subscribe(sub);
void loop()
{
nh.spinOnce();
delay(1); }
接下來要設法透過Arduino在ROS的世界說話。簡單的方法是使用機器人啟動檔。雖然以下的檔案內(nèi)容非常簡單,但是這里要追加啟動檔,如此一來即使是非常復雜的機器人,也能用一個指令啟動。
$ cat rosservo.launch
$ roslaunch ./rosservo.lanch
rostopic指令可以看出ROS訊息傳送到機器人的哪個部位。看了下面的程序代碼就會發(fā)現(xiàn),「/head/tilt」可以透過Arduino使用。訊息要使用「rostopic」傳送。-1的選項只會發(fā)布(publish)訊息一次,通知/head/tilt傳送一個浮點數(shù)。
$ rostopic list
/diagnostics
/head/tilt
/rosout
/rosout_agg
$ rostopic pub -1 /head/tiltstd_msgs/Float32 0.4
$ rostopic pub -1 /head/tilt std_msgs/Float320.9
這個階段當中,能夠?qū)⑺邪l(fā)布數(shù)值到ROS的已知方法用在控制伺服機上。假如從0改成1,伺服機就會全速運行。這本來并沒有問題,但實際上我們想要逐漸加速以達到全速,然后再逐漸減速,停在目標角度上。假如伺服機驟然運轉,機器人的動作就會變得僵硬,讓周圍的人嚇一跳。
Terry和Houndbot都是ROS機器人,以6061個鋁合金零件制造而成。項目的目標是要盡量讓這些機器人自主運動。
以下的Python腳本程序會監(jiān)聽「/head/tilt/smooth」的訊息,朝「/head/tilt」發(fā)布許多訊息,好讓伺服機轉到目標角度之前慢慢加速,再慢慢延遲旋轉。當訊息抵達「/head/tilt/smooth」時一定會呼叫「moveServo_cb」。這個回調(diào)函式會從-90到+90度之間每10度產(chǎn)生1個數(shù)值,追加到角度數(shù)組當中。「sin()」會取這個角度,數(shù)值從-1到+1慢慢增加。該數(shù)值加1之后,范圍就會變成0到+2,再除以2之后, 0到+1的曲線數(shù)值數(shù)組就完成了。然后再看看m數(shù)組當中,每當發(fā)布訊息時,就會稍微前進一點,范圍在r之內(nèi),直到1*r或是全范圍為止。
#!/usr/bin/env python
from time import sleep
import numpy as np
import rospy
from std_msgs.msg import Float32
currentPosition = 0.5
pub = None
def moveServo_cb(data):
global currentPosition, pub
targetPosition = data.data
r = targetPosition - currentPosition
angles = np.array( (range(190)) [0::10]) -90
m = ( np.sin( angles * np.pi/ 180. ) + 1 )/2
for mi in np.nditer(m):
pos = currentPosition + mi*r
A06B-0128-B075 A06B-0502-B751 A06B-6079-H208
A06B-0128-B076 A06B-0502-B855 A06B-6079-H301
A06B-0128-B077 A06B-0503-B006 A06B-6079-H304
A06B-0128-B175 A06B-0503-B202 A06B-6079-H401
A06B-0128-B177 A06B-0503-B251 A06B-6079-K815
A06B-0128-B575 A06B-0503-B304 A06B-6081-H101
A06B-0128-B577 A06B-0505-B001 A06B-6081-H103
A06B-0147-B175 A06B-0514-B504 A06B-6088-H230
A06B-0147-B177 A06B-0521-B052 A06B-6088-H245IC200UDR064完整IC200UDR064完整IC200UDR064完整
A06B-0147-B675 A06B-0521-B541 A06B-6089-H104
A06B-0148-B075 A06B-0532-B001 A06B-6089-H203
A06B-0148-B175 A06B-0572-B003 A06B-6090-H234
A06B-0148-B177 A06B-0572-B004 A06B-6091-H118