Основным механизмом обмена данными между узлами ROS является отправка и прием сообщений. Сообщения передаются по теме, и каждая тема имеет уникальное имя в сети ROS. Если узел хочет поделиться информацией, он использует издателя для отправки данных в раздел. Узел, который хочет получить эту информацию, использует абонента в той же теме. Помимо своего уникального имени, каждая тема также имеет тип сообщения, который определяет типы сообщений, которые могут передаваться по этой теме.
Данная коммуникация издателя и абонента имеет следующие характеристики:
Темы используются для общения «многие ко многим». Многие издатели могут отправлять сообщения на ту же тему и многие подписчики могут их получать.
Издатели и подписчики разделены на темы и могут быть созданы и уничтожены в любом порядке. Сообщение может быть опубликовано в тему, даже если нет активных подписчиков.
Концепция тем, издателей и подписчиков проиллюстрирована на рисунке:
В этом примере показано, как публиковать и подписываться на темы в сети ROS. Также показано, как:
Подождите получения нового сообщения
Используйте коллбэки для обработки новых сообщений в фоновом режиме
Необходимые условия: Запуск с ROS, подключение к сети ROS
Запустите мастер ROS в MATLAB ® с помощью rosinit
команда.
rosinit
Launching ROS Core... Done in 0.84361 seconds. Initializing ROS master on http://192.168.0.10:49966. Initializing global node /matlab_global_node_39840 with NodeURI http://bat6315glnxa64:41167/
Создайте пример сети ROS с несколькими издателями и подписчиками, используя предоставленную функцию helper exampleHelperROSCreateSampleNetwork.
exampleHelperROSCreateSampleNetwork
Использовать rostopic
list
чтобы увидеть, какие темы доступны.
rostopic list
/pose /rosout /scan /tf
Использование rostopic info
проверить, публикуются ли какие-либо узлы в /scan
тема. Команда ниже показывает, что node_3
публикуется к нему.
rostopic info /scan
Type: sensor_msgs/LaserScan Publishers: * /node_3 (http://bat6315glnxa64:46535/) Subscribers: * /node_1 (http://bat6315glnxa64:39337/) * /node_2 (http://bat6315glnxa64:35615/)
Использовать rossubscriber
подписаться на /scan
тема. Если тема уже существует в сети ROS (как это происходит здесь), rossubscriber
определяет его тип сообщения автоматически, поэтому вам не нужно указывать его.
laser = rossubscriber('/scan');
pause(2)
Использовать receive
чтобы дождаться нового сообщения. (Второй аргумент - тайм-аут в секундах.) Область выхода scandata
содержит полученные данные сообщения.
scandata = receive(laser,10)
scandata = ROS LaserScan message with properties: MessageType: 'sensor_msgs/LaserScan' Header: [1x1 Header] AngleMin: -0.5216 AngleMax: 0.5243 AngleIncrement: 0.0016 TimeIncrement: 0 ScanTime: 0.0330 RangeMin: 0.4500 RangeMax: 10 Ranges: [640x1 single] Intensities: [0x1 single] Use showdetails to show the contents of the message
С некоторыми типами сообщений связаны визуализаторы. Для сообщения LaserScan, rosPlot
строит графики данных скана. The MaximumRange
Пара "имя-значение" задает максимальную область значений графика.
figure
plot(scandata,'MaximumRange',7)
Вместо использования receive
для получения данных можно задать функцию, которая будет вызываться при получении нового сообщения. Это позволяет выполнять другой код MATLAB во время ожидания абонентом новых сообщений. Коллбэки необходимы, если вы хотите использовать несколько абонентов.
Подпишитесь на /pose
topic, использование функции обратного вызова exampleHelperROSPoseCallback
.
robotpose = rossubscriber('/pose',@exampleHelperROSPoseCallback)
robotpose = Subscriber with properties: TopicName: '/pose' LatestMessage: [0x1 Twist] MessageType: 'geometry_msgs/Twist' BufferSize: 1 NewMessageFcn: @exampleHelperROSPoseCallback DataFormat: 'object'
Одним из способов обмена данными между вашей основной рабочей областью и функцией обратного вызова является использование глобальных переменных. Задайте две глобальные переменные pos
и orient
.
global pos global orient
Глобальные переменные pos
и orient
назначаются в exampleHelperROSPoseCallback
функция, когда новые данные сообщения получены на /pose
тема.
Подождите несколько секунд, чтобы убедиться, что абонент может получать сообщения. Самые актуальные данные о положении и ориентации всегда будут храниться в pos
и orient
переменные.
pause(2) pos
pos = 1×3
-0.1612 -0.2381 0.0105
orient
orient = 1×3
-0.2323 0.2905 0.1572
Если вы вводите pos
и orient
несколько раз в командной строке можно увидеть, что значения постоянно обновляются.
Остановите абонента положения путем очистки переменной абонента
clear robotpose
Примечание: Существуют другие способы извлечения информации из функций обратного вызова, помимо использования globals. Для примера можно передать объект указателя в качестве дополнительного аргумента в функцию обратного вызова. Для получения дополнительной информации об определении функций обратного вызова см. документацию «Определение обратного вызова».
Создайте издателя, который отправляет строковые сообщения ROS в /chatter
тема (см. «Работа с базовыми сообщениями ROS»).
chatterpub = rospublisher('/chatter','std_msgs/String')
chatterpub = Publisher with properties: TopicName: '/chatter' NumSubscribers: 0 IsLatching: 1 MessageType: 'std_msgs/String' DataFormat: 'object'
pause(2) % Wait to ensure publisher is registered
Создайте и заполните ROS-сообщение для отправки в /chatter
тема.
chattermsg = rosmessage(chatterpub);
chattermsg.Data = 'hello world'
chattermsg = ROS String message with properties: MessageType: 'std_msgs/String' Data: 'hello world' Use showdetails to show the contents of the message
Использование rostopic list
чтобы проверить, что /chatter
тема доступна в сети ROS.
rostopic list
/chatter /pose /rosout /scan /tf
Определите абонента для /chatter
тема. exampleHelperROSChatterCallback
вызывается при получении нового сообщения и отображает строку содержимое сообщения.
chattersub = rossubscriber('/chatter', @exampleHelperROSChatterCallback)
chattersub = Subscriber with properties: TopicName: '/chatter' LatestMessage: [0x1 String] MessageType: 'std_msgs/String' BufferSize: 1 NewMessageFcn: @exampleHelperROSChatterCallback DataFormat: 'object'
Опубликовать сообщение в /chatter
тема. Строка отображается при коллбэк абонента.
send(chatterpub,chattermsg) pause(2)
ans = 'hello world'
The exampleHelperROSChatterCallback
функция была вызвана сразу после публикации строкового сообщения.
Удалите примеры узлов, издателей и подписчиков из сети ROS. Очистите глобальные переменные pos
и orient.
exampleHelperROSShutDownSampleNetwork clear global pos orient
Завершите работу хозяина ROS и удалите глобальный узел.
rosshutdown
Shutting down global node /matlab_global_node_39840 with NodeURI http://bat6315glnxa64:41167/ Shutting down ROS master on http://192.168.0.10:49966.
Дополнительные сведения о том, как обрабатываются сообщения ROS в MATLAB, см. в разделах Работа с основными сообщениями ROS и Работа со специализированными сообщениями ROS.
Для изучения услуг ROS см. раздел «Вызов и предоставление услуг ROS».