1. 이론
1.3토픽 (Topic)
토픽이란?
토픽(Topic)은 노드들이 데이터를 주고받는 이름 붙은 통로입니다.
- 데이터를 보내는 쪽을 퍼블리셔(Publisher), 받는 쪽을 서브스크라이버(Subscriber) 라고 합니다.
- 보내는 쪽은 누가 받는지 모르고 받는 쪽은 누가 보내는지 모릅니다. 토픽 이름과 메시지 타입만 맞으면 연결됩니다.
- 하나의 토픽에 퍼블리셔와 서브스크라이버가 여러 개 있어도 됩니다 (다대다).
둥근 상자 = 노드 · 사각형 = 토픽 · 화살표 = 데이터 방향
메시지에는 타입이 있습니다. 문자열은 std_msgs/msg/String, 속도 명령은 geometry_msgs/msg/Twist 같은 식입니다. 퍼블리셔와 서브스크라이버의 타입이 다르면 서로 통신하지 못합니다.
아래 애니메이션은 토픽의 흐름을 보여 줍니다. 발행하는 노드가 토픽에 메시지를 올리면 그 토픽을 구독한 노드가 계속 받아 갑니다.
해보기 1: 메시지 발행하기
0.5초마다 문자열을 발행하는 talker 노드입니다. ▶ 실행을 눌러 보세요.
1) Publisher: talker
결과 읽는 법
- 출력 탭: 노드가 남긴 로그
- 토픽 탭:
/chatter토픽으로 실제 오간 메시지 (ros2 topic echo와 같은 화면) - 노드 그래프 탭: 노드와 토픽의 연결
직접 바꿔 보기
- 메시지 문장을 바꿔 보세요.
create_timer(0.5, ...)의 주기를0.2로 바꾸면 3초 동안 몇 번 발행될까요? 먼저 예상하고 실행해 보세요.- 위쪽
'chatter'를'news'로 바꾸면 토픽 탭의 이름이 바뀝니다.
해보기 2: 구독하기
이제 listener 노드를 추가합니다. 실제 ROS2에서는 talker와 listener를 터미널 두 개에서 따로 실행합니다. 이 실행기는 파일 하나만 실행하므로 한 프로그램 안에서 두 노드를 함께 돌립니다.
2) Publisher + Subscriber
직접 바꿔 보기
- 노드 그래프 탭을 열어
talker → /chatter → listener연결을 확인하세요. executor.add_node(listener)줄을 지우고 실행해 보세요. 수신 로그가 사라지는 이유는 무엇일까요? (힌트: 콜백은 노드가 spin될 때만 호출됩니다)Listener의 토픽 이름을'news'로 바꿔 보세요. 연결이 끊기는 것이 그래프에 보입니다.Listener의 메시지 타입을Int32로 바꿔 보세요 (from std_msgs.msg import String, Int32). 같은 토픽 이름이라도 타입이 다르면 통신되지 않습니다.
해보기 3: 속도 명령으로 로봇 움직이기
실제 로봇(TIKI-MINI 포함)과 시뮬레이션은 대부분 /cmd_vel 토픽의 Twist 메시지로 속도를 받습니다.
| 필드 | 의미 | 단위 |
|---|---|---|
linear.x | 앞(+)·뒤(-) 이동 속도 | m/s |
angular.z | 왼쪽(+)·오른쪽(-) 회전 속도 | rad/s |
3) /cmd_vel로 로봇 움직이기
직접 바꿔 보기
angular.z = 0.0으로 바꾸면 직진합니다. 벽에 닿으면 어떻게 될까요?angular.z를 음수로 바꾸면 회전 방향이 반대가 됩니다.- 원의 반지름은
linear.x / angular.z입니다. 반지름 1m인 원을 그리려면 값을 어떻게 정해야 할까요? - 슬라이더를 움직이면 원하는 시각의 로봇 위치와 그때까지 찍힌 로그가 표시됩니다.
실제 ROS2에서는 (참고)
개발환경을 구축한 뒤에는 같은 동작을 터미널에서 확인할 수 있습니다.
ros2 topic list # 현재 토픽 목록
ros2 topic echo /chatter # 토픽의 메시지를 계속 출력
ros2 topic info /chatter # 타입, 퍼블리셔/서브스크라이버 수
ros2 topic pub --once /chatter std_msgs/msg/String "{data: 'hello'}"
한눈에 정리
- 토픽은 이름과 메시지 타입으로 연결되는 통로다.
- 퍼블리셔는
create_publisher, 서브스크라이버는create_subscription으로 만든다. - 콜백(타이머, 구독)은
spin중일 때만 호출된다. - 로봇 이동은
/cmd_vel의Twist(linear.x, angular.z)로 명령한다.
확인 문제
Q1. 토픽 이름은 같은데 퍼블리셔는 String, 서브스크라이버는 Int32입니다. 메시지가 전달될까요?
전달되지 않습니다. 토픽 이름뿐 아니라 메시지 타입도 같아야 연결됩니다.
Q2. 서브스크라이버 콜백이 한 번도 호출되지 않습니다. 가장 먼저 확인할 것 두 가지는?
- 토픽 이름과 메시지 타입이 퍼블리셔와 같은지 (
ros2 topic info로 확인) - 구독 노드가
rclpy.spin()또는 executor에 등록되어 실행 중인지
Q3. linear.x = 0.2, angular.z = 0.0 을 계속 발행하면 로봇은 어떻게 움직이나요?
방향을 바꾸지 않고 초속 0.2m로 직진합니다. angular.z가 0이므로 회전하지 않습니다.