Skip to main content
Summary

로봇을 바닥에 내려놓기 전에

지금까지 우리는 ROS2의 기본 통신 구조를 배웠고, 노드와 토픽이 어떻게 데이터를 주고받는지 살펴보았다. 또 TF로 좌표계를 연결하고, URDF와 xacro로 로봇의 몸을 만들었으며, RViz에서 로봇 모델과 센서 데이터를 확인했다. 이제 다음 질문이 자연스럽게 떠오른다.

"이 로봇, 정말 움직일까?"

실제 로봇이 있다면 바로 바닥에 내려놓고 /cmd_vel을 보내 보고 싶을 것이다. 전진 속도 0.2, 회전 속도 0.5. 터미널에 명령을 입력하는 순간 로봇이 앞으로 나아간다. 멋진 장면이다. 그런데 현실의 로봇은 생각보다 성격이 까다롭다. 바퀴가 헛돌 수도 있고, 책상 다리에 부딪힐 수도 있고, LiDAR 케이블이 빠질 수도 있다. 배터리가 부족하면 주행이 갑자기 느려지고, 누군가 실험실 문을 열고 지나가면 계획한 경로가 순식간에 엉망이 된다.

로봇 개발은 코드만의 문제가 아니다. 코드가 물리 세계와 만나는 순간, 예상하지 못한 일이 폭포처럼 쏟아진다. 그래서 우리는 실제 로봇을 움직이기 전에 가상 세계에서 먼저 움직여 본다. 이것이 로봇 시뮬레이션의 출발점이다.

ROS2에서 시뮬레이션은 단순한 "3D 장난감"이 아니다. 로봇 모델, 센서, 구동계, 월드, 물리 엔진, ROS2 노드, TF, 토픽, 파라미터, launch 파일이 한데 모이는 작은 실험실이다. ROS2 문서에서도 Gazebo, Webots 같은 시뮬레이터가 물리 기반 모델을 이용해 로봇, 센서, 액추에이터, 물체를 비교적 현실적으로 흉내 낼 수 있다고 설명한다1. 우리는 이 가상 실험실에서 로봇을 마음껏 부딪히게 하고, 길을 잃게 하고, 다시 고쳐 보면서 자율주행 시스템을 단단하게 만든다.

로봇 시뮬레이션이 필요한 이유

하드웨어가 없어도 시작할 수 있다는 것

자율주행 로봇을 만들려면 실제 하드웨어가 필요해 보인다. 바퀴 달린 베이스, 모터 드라이버, LiDAR, IMU, 배터리, 컴퓨터, 프레임, 나사, 케이블이 떠오른다. 물론 최종적으로는 실제 로봇이 필요하다. 하지만 처음부터 모든 것을 실제 장비에 의존하면 개발 속도가 급격히 느려진다.

로봇 한 대를 조립하는 데 시간이 걸린다. 고장 나면 부품을 주문해야 한다. 학교나 회사 실험실에서는 로봇을 여러 사람이 함께 쓰기 때문에 원하는 시간에 실험하지 못할 수도 있다. 특히 SLAM이나 Nav2처럼 반복 실험이 많은 기능을 개발할 때는 "로봇을 빌릴 수 있는 시간"이 곧 개발 속도의 한계가 된다.

시뮬레이션은 이 병목을 줄여 준다. 실제 LiDAR가 없어도 가상 LiDAR가 /scan을 발행할 수 있다. 실제 바퀴가 없어도 차동 구동 플러그인이 /cmd_vel을 받아 로봇을 움직일 수 있다. 실제 복도가 없어도 Gazebo 월드 안에 벽, 문, 책상, 장애물을 배치할 수 있다. NVIDIA Isaac Sim 같은 시뮬레이터도 로봇을 배포하기 전에 창고나 공장 같은 물리 기반 디지털 환경에서 로봇 시스템을 학습, 시뮬레이션, 검증할 수 있다는 점을 강조한다2.

여기서 중요한 점은 "시뮬레이션에서 ROS2의 구조를 그대로 연습할 수 있다"는 것이다. 가상 로봇도 결국 토픽을 발행하고 구독한다. 예를 들어 이동 로봇 시뮬레이션에서는 다음과 같은 흐름이 만들어진다.

  • 가상 LiDAR가 /scan 토픽으로 거리 데이터를 발행한다.

  • 가상 바퀴와 엔코더가 /odom 토픽으로 오도메트리를 발행한다.

  • 제어 노드나 키보드 조종 노드가 /cmd_vel 토픽으로 속도 명령을 보낸다.

  • robot_state_publisher가 로봇 모델과 조인트 상태를 바탕으로 /tf를 발행한다.

  • RViz가 /tf, /scan, /odom, 지도, 경로를 시각화한다.

즉, 실제 로봇이 없어도 ROS2 시스템의 뼈대를 먼저 세울 수 있다. 센서 노드, 제어 노드, 위치 추정 노드, 경로 계획 노드를 연결하고, 각 노드가 어떤 토픽을 필요로 하는지 확인할 수 있다. 나중에 실제 하드웨어를 붙일 때도 전체 구조를 새로 만드는 것이 아니라, 가상 센서와 가상 구동계를 실제 드라이버로 바꾸는 방식으로 접근할 수 있다.

물론 모든 것이 자동으로 해결되지는 않는다. 가상 로봇도 URDF나 SDF 모델이 필요하고, 센서 플러그인과 구동 플러그인을 설정해야 하며, Gazebo와 ROS2 사이에 토픽을 연결해야 한다. 최신 Gazebo에서는 ros_gz_bridge 같은 브리지를 통해 Gazebo Transport와 ROS2 토픽 사이에서 메시지를 주고받을 수 있다. 예를 들어 Gazebo의 LiDAR 데이터를 ROS2의 sensor_msgs/msg/LaserScan 타입 /scan 토픽으로 전달하는 식이다3.

하지만 한 번 구성이 잡히면 효과는 크다. 로봇을 책상 위에 올려놓고 케이블을 정리하는 시간 대신, launch 파일 하나로 같은 실험 환경을 반복해서 열 수 있다. 실험실 문이 잠겨 있어도, 새벽에도, 노트북만 켜면 로봇은 가상 복도 위에 다시 나타난다.

위험한 상황을 안전하게 만들기

초보 개발자가 자율주행 로봇을 처음 움직일 때 가장 긴장되는 순간은 "충돌"이다. 로봇이 벽으로 돌진하는데 정지 명령이 먹지 않는다면? 좁은 통로에서 회전하다가 바퀴가 걸린다면? 사람 다리 근처에서 장애물 회피가 늦게 동작한다면?

실제 로봇으로 이런 상황을 반복 테스트하는 것은 부담스럽다. 로봇이 작고 가벼운 TurtleBot이라면 그나마 낫지만, 무거운 AMR이라면 이야기가 달라진다. 충돌은 장비를 망가뜨릴 수도 있고, 주변 물건을 부술 수도 있으며, 무엇보다 사람에게 위험할 수 있다.

시뮬레이션에서는 이런 장면을 마음껏 만들 수 있다. 일부러 벽에 가까운 초기 위치에서 출발시켜 볼 수 있다. 좁은 문을 통과하게 할 수 있다. 복도 중간에 갑자기 박스를 놓을 수 있다. 사람이 옆에서 걸어 나오는 상황을 만들 수도 있다. 로봇이 실패해도 모터 축이 휘지 않고, LiDAR 브래킷이 부러지지 않는다. 실패는 비용이 아니라 데이터가 된다.

특히 자율주행에서는 "평소에는 잘 되지만 가끔 위험한 상황"이 중요하다. 넓은 복도에서 직진하는 것은 어렵지 않다. 문제는 애매한 순간이다. 문틀 근처에서 LiDAR가 벽을 비스듬히 볼 때, 유리문처럼 센서가 잘 인식하지 못하는 물체가 있을 때, 로봇이 회전 중에 장애물이 갑자기 나타날 때, 경로 계획기는 어떤 선택을 해야 할까?

시뮬레이션은 이런 경계 상황을 의도적으로 반복하게 해 준다. 실제 환경에서는 드물게 발생하는 사건도 가상 세계에서는 버튼 한 번으로 다시 만들 수 있다. OSRF의 다중 로봇 시뮬레이션 문서에서도 시뮬레이션은 하드웨어 준비 시간, 로봇 다운타임, 실험 사이의 재설정 시간을 줄이고, 충돌이나 배터리 같은 현실적 부담 없이 긴 시간 동안 시나리오를 반복하며 견고성을 검증할 수 있다고 설명한다4.

물론 "안전하다"는 말이 "대충 해도 된다"는 뜻은 아니다. 시뮬레이션에서 로봇이 벽을 통과하거나, 바퀴가 바닥에 닿지 않았는데 움직이거나, LiDAR가 실제보다 지나치게 깨끗한 데이터를 준다면 잘못된 자신감을 얻게 된다. 그래서 시뮬레이션은 위험을 줄이는 도구이면서 동시에 세심한 설정이 필요한 도구다.

반복 실험이 알고리즘을 키운다

자율주행 알고리즘은 한 번에 완성되지 않는다. SLAM 파라미터를 조금 바꾸면 지도 품질이 달라진다. Costmap의 inflation radius를 바꾸면 로봇이 벽에서 떨어지는 거리가 달라진다. Controller의 속도 제한을 바꾸면 로봇이 더 빠르게 움직이지만 코너에서 흔들릴 수 있다. 어떤 설정이 좋은지 알려면 비교해야 한다.

문제는 비교가 공정해야 한다는 것이다. 오늘은 로봇이 복도 왼쪽에서 출발했고, 내일은 오른쪽에서 출발했다면 결과를 직접 비교하기 어렵다. 오늘은 사람이 지나가지 않았고, 내일은 누군가 중간에 걸어 들어왔다면 장애물 회피 성능을 비교하기 애매하다. 실험 조건이 매번 달라지면, 알고리즘이 좋아진 것인지 운이 좋았던 것인지 알기 어렵다.

시뮬레이션은 실험 조건을 고정하기 쉽다. 같은 월드, 같은 초기 위치, 같은 목표 지점, 같은 파라미터, 같은 센서 설정으로 여러 번 실행할 수 있다. 그리고 하나씩만 바꿔 볼 수 있다. 예를 들어 SLAM 실험에서는 다음처럼 조건을 나눌 수 있다.

  • 같은 방 구조에서 로봇 주행 속도만 바꿔 지도 품질을 비교한다.

  • 같은 주행 경로에서 LiDAR 노이즈 설정만 바꿔 SLAM의 안정성을 확인한다.

  • 같은 지도에서 Nav2의 costmap 파라미터만 바꿔 벽과의 안전거리를 비교한다.

  • 같은 목표 지점에서 controller 파라미터만 바꿔 도착 시간과 경로 흔들림을 비교한다.

이런 반복이 쌓이면 감이 아니라 근거로 튜닝할 수 있다. "이 값이 왠지 좋아 보여서"가 아니라 "같은 조건에서 실패율이 줄었기 때문에" 선택할 수 있다.

여기에 rosbag이 더해지면 실험은 더 강력해진다. rosbag은 ROS2 토픽 데이터를 기록하고 다시 재생하는 도구다. 예를 들어 시뮬레이션 주행 중 /scan, /odom, /tf, /cmd_vel을 기록해 두면, 나중에 같은 데이터를 다시 재생하면서 SLAM 노드나 장애물 회피 노드의 동작을 분석할 수 있다. 이 책의 20장에서 rosbag을 더 자세히 다루겠지만, 지금은 "로봇이 겪은 일을 녹화해 두는 블랙박스"라고 생각하면 된다.

재현 가능성은 디버깅에서 특히 중요하다. 로봇이 어떤 순간에 벽으로 붙는 문제가 있다고 하자. 실제 로봇만으로 디버깅하면 그 순간을 다시 만들기 어렵다. 하지만 같은 월드와 같은 bag 데이터를 가지고 있다면, 문제 상황을 여러 번 되감아 볼 수 있다. 지도 좌표가 흔들렸는지, /scan이 끊겼는지, /cmd_vel이 갑자기 커졌는지, TF가 순간적으로 사라졌는지 하나씩 확인할 수 있다.

좋은 로봇 개발자는 로봇을 많이 움직이는 사람이기도 하지만, 같은 상황을 다시 만들 줄 아는 사람이기도 하다. 시뮬레이션은 그 능력을 크게 높여 준다.

Gazebo, RViz, launch는 서로 다른 일을 한다

처음 ROS2 시뮬레이션을 접하면 도구 이름이 한꺼번에 쏟아져 혼란스럽다. Gazebo를 켰는데 RViz도 켜야 한다고 하고, launch 파일도 만들라고 한다. 파라미터 파일도 있고, 브리지 설정도 있다. 모두 "시뮬레이션"이라는 말 아래 묶이지만 실제 역할은 다르다.

Gazebo 같은 시뮬레이터는 가상 세계를 담당한다. 월드 안에 바닥, 벽, 장애물, 조명, 중력, 마찰, 로봇 모델, 센서가 들어간다. 바퀴가 돌면 로봇이 움직이고, 로봇이 벽에 닿으면 충돌이 발생한다. LiDAR는 주변 물체를 스캔하고, 카메라는 가상 이미지를 만든다. 즉 Gazebo는 "로봇이 살아 움직이는 물리 무대"에 가깝다.

RViz는 물리 시뮬레이터가 아니다. RViz의 핵심 역할은 ROS2 데이터를 시각화하는 것이다. TF 트리가 제대로 연결되어 있는지, /scan이 어느 방향으로 뿌려지는지, 로봇 모델이 base_link를 기준으로 올바른 위치에 있는지, 지도 위에서 경로가 어떻게 생성되는지 확인한다. Gazebo가 영화 세트장이라면, RViz는 로봇의 머릿속을 보여 주는 관제 화면에 가깝다.

ROS2 launch 파일은 여러 노드를 한 번에 실행하는 실험 버튼이다. 시뮬레이션 하나를 실행하려면 생각보다 많은 프로그램이 필요하다. Gazebo 서버, 로봇 spawn 노드, robot_state_publisher, 브리지 노드, teleop 노드, RViz, SLAM 노드, Nav2 노드가 함께 실행될 수 있다. 이들을 매번 터미널 여러 개에 손으로 입력하면 실수가 잦다. launch 파일은 이 실행 순서와 설정을 코드로 묶어 준다.

파라미터 파일은 실험 조건표다. 로봇의 최대 속도, LiDAR 토픽 이름, frame 이름, costmap 크기, SLAM 설정, controller 설정을 코드와 분리해서 관리한다. 같은 노드라도 파라미터를 바꾸면 전혀 다른 동작을 할 수 있다. 그래서 실험을 재현하려면 launch 파일뿐 아니라 파라미터 파일도 함께 관리해야 한다.

Gazebo와 ROS2 사이의 연결도 중요하다. 최신 Gazebo는 자체 메시지 체계를 사용하고, ROS2는 ROS2 메시지 체계를 사용한다. 이 둘을 이어 주는 것이 ros_gz_bridge 같은 브리지다. Gazebo 공식 문서는 이 브리지를 통해 joint state, TF, 센서 데이터, 명령을 Gazebo와 ROS2 사이에서 주고받고, RViz가 Gazebo에서 시뮬레이션 중인 로봇 모델을 동시에 시각화할 수 있다고 설명한다5.

결국 시뮬레이션 실험은 여러 층으로 이루어진다. 아래에는 물리 세계를 흉내 내는 Gazebo가 있고, 가운데에는 ROS2 토픽과 TF가 흐르며, 위에는 RViz와 CLI 도구가 상태를 보여 준다. launch와 파라미터는 이 모든 것을 한 번에 재현 가능한 형태로 묶는다.

가상 로봇도 ROS2 그래프 안에 있다

시뮬레이션을 제대로 이해하려면 "가상 로봇도 ROS2 그래프의 일부"라는 관점이 필요하다. Gazebo 창에 보이는 로봇은 단순한 그림이 아니다. ROS2 입장에서 보면 여러 토픽과 서비스, TF를 가진 시스템이다.

예를 들어 TurtleBot 계열 이동 로봇을 시뮬레이션한다고 생각해 보자. 키보드 조종 노드가 /cmd_vel을 발행한다. 시뮬레이터는 이 속도 명령을 받아 왼쪽 바퀴와 오른쪽 바퀴의 회전으로 바꾼다. 바퀴가 돌면서 로봇 위치가 변하고, 시뮬레이터는 오도메트리와 조인트 상태를 발행한다. LiDAR 플러그인은 주변 벽까지의 거리를 계산해 /scan으로 내보낸다. robot_state_publisher는 조인트 상태와 로봇 모델을 이용해 TF를 만든다.

이 구조는 실제 로봇과 놀라울 정도로 닮아 있다. 실제 로봇에서는 모터 드라이버가 /cmd_vel을 바퀴 속도로 바꾸고, 실제 LiDAR 드라이버가 /scan을 발행한다. 시뮬레이션에서는 그 역할을 가상 플러그인과 브리지가 대신한다.

이 닮음 덕분에 우리는 같은 ROS2 도구를 사용할 수 있다.

ros2 node list
ros2 topic list
ros2 topic echo /scan
ros2 topic echo /odom
ros2 run tf2_ros tf2_echo odom base_link

이 명령들은 실제 로봇에서도, 시뮬레이션에서도 유용하다. RViz에서 Fixed Frame을 odom이나 map으로 바꾸고 LaserScan, RobotModel, TF를 확인하는 방법도 같다. 앞 장에서 배운 RViz 디버깅 습관은 시뮬레이션 장에서도 그대로 이어진다.

여기서 중요한 감각이 하나 있다. 시뮬레이션이 잘 안 될 때도 문제를 화면의 로봇 모양만 보고 판단하면 안 된다. 로봇이 움직이지 않는다면 Gazebo 화면만 바라볼 것이 아니라 /cmd_vel이 발행되는지, 브리지가 연결되어 있는지, 바퀴 조인트 이름이 맞는지, TF가 끊기지 않았는지 확인해야 한다. 시뮬레이션도 결국 ROS2 시스템이기 때문이다.

AI 학습과 대규모 테스트의 출발점

이 책의 중심은 SLAM과 Nav2로 이동 로봇을 만드는 것이지만, 시뮬레이션은 더 넓은 세계로 이어진다. 최근 로봇 개발에서는 AI 모델을 학습하거나, 여러 대의 로봇을 동시에 검증하거나, 실제로 만들기 어려운 상황을 대량으로 생성하는 데 시뮬레이션을 활용한다.

예를 들어 카메라 기반 인식 모델을 학습하려면 다양한 이미지가 필요하다. 낮, 밤, 그림자, 반사, 다른 색의 물체, 다른 위치의 장애물을 모두 실제로 촬영하려면 많은 시간이 든다. 시뮬레이션에서는 조명, 색상, 물체 배치, 배경을 바꾸며 합성 데이터를 만들 수 있다. Isaac Sim은 센서 시뮬레이션과 도메인 랜덤화, 즉 조명·색상·텍스처·배경 등을 바꿔 다양한 학습 데이터를 생성하는 기능을 제공한다고 설명한다6.

물론 이 책에서 당장 대규모 AI 학습을 하지는 않는다. 하지만 이동 로봇 시스템을 배울 때도 같은 사고방식이 도움이 된다. "한 번 성공했다"보다 "다양한 조건에서 얼마나 안정적인가"가 중요하다. 좁은 복도, 넓은 홀, 장애물이 많은 방, 동적 장애물이 있는 환경을 바꿔 가며 테스트하면 알고리즘의 약점이 더 빨리 드러난다.

시뮬레이션은 로봇에게 연습장을 제공한다. 그리고 좋은 연습장은 단순히 쉬운 문제만 내지 않는다. 일부러 까다로운 코너를 만들고, 센서가 헷갈릴 만한 구조를 만들고, 로봇이 선택을 망설일 만한 상황을 준다. 그 안에서 알고리즘은 조금씩 강해진다.

시뮬레이션이 거짓말을 할 때

시뮬레이션은 강력하지만 완벽하지 않다. 오히려 너무 편리하기 때문에 위험할 때가 있다. 가상 세계에서 잘 움직인 로봇이 실제 바닥에서는 이상하게 움직일 수 있다. 개발자는 이 차이를 반드시 기억해야 한다.

가장 먼저 센서 노이즈가 다르다. 시뮬레이션 LiDAR는 벽까지의 거리를 매우 깨끗하게 줄 수 있다. 하지만 실제 LiDAR는 반사율, 유리, 검은 물체, 먼지, 햇빛, 센서 각도에 영향을 받는다. 카메라도 마찬가지다. 실제 환경에서는 조명이 바뀌고, 렌즈에 먼지가 묻고, 노출이 흔들리고, 모션 블러가 생긴다.

통신 지연도 다르다. 시뮬레이션에서는 모든 노드가 같은 컴퓨터에서 부드럽게 도는 것처럼 보일 수 있다. 실제 로봇에서는 센서 드라이버, 네트워크, DDS 설정, CPU 부하, Wi-Fi 상태 때문에 메시지가 늦게 도착하거나 끊길 수 있다. 특히 원격 PC에서 로봇을 제어한다면 네트워크 상태가 주행 안정성에 영향을 준다.

바퀴와 바닥의 물리도 차이를 만든다. 실제 바퀴는 미끄러진다. 바닥 재질에 따라 마찰이 달라지고, 카펫과 타일에서 움직임이 달라진다. 로봇이 회전할 때 한쪽 바퀴가 살짝 헛돌면 오도메트리가 실제 위치와 어긋난다. 시뮬레이션에서 마찰 계수나 질량, 관성, 조인트 감쇠가 현실과 다르면 로봇의 가속과 정지, 회전이 실제와 다르게 보인다. Isaac Sim의 TurtleBot URDF 가져오기 문서도 바퀴 미끄러짐이 있으면 바퀴와 바닥의 마찰 계수를 조정하고, 질량·관성·조인트의 stiffness와 damping 같은 물리 속성을 튜닝해야 한다고 설명한다7.

배터리 상태도 현실적인 변수다. 배터리가 충분할 때는 모터가 잘 반응하지만, 전압이 떨어지면 속도와 토크가 달라질 수 있다. 시뮬레이션에서는 로봇이 지치지 않는다. 하지만 실제 로봇은 오래 달릴수록 무게중심, 온도, 전원 상태가 영향을 줄 수 있다.

모델 오차도 피할 수 없다. URDF나 SDF에 적은 바퀴 반경이 실제와 조금 다를 수 있다. LiDAR 위치가 모델에서는 정확히 base_link에서 20cm 앞이라고 되어 있지만, 실제 조립에서는 몇 mm 틀어질 수 있다. 작은 오차도 SLAM과 Nav2에서는 누적되어 큰 차이로 나타날 수 있다.

그래서 시뮬레이션 결과를 볼 때는 항상 이렇게 물어야 한다.

"이 성공은 현실에서도 버틸 수 있는 성공인가?"

이 질문을 잊지 않으면 시뮬레이션은 훌륭한 도구가 된다. 잊는 순간, 시뮬레이션은 예쁜 착각이 된다.

Sim-to-Real, 한 번에 건너뛰지 않기

시뮬레이션에서 실제 로봇으로 옮기는 과정을 흔히 Sim-to-Real이라고 부른다. 말은 간단하지만 실제로는 다리를 하나씩 놓는 작업에 가깝다.

첫 번째 다리는 인터페이스를 맞추는 것이다. 시뮬레이션에서도 실제 로봇에서도 가능하면 같은 토픽 이름과 메시지 타입을 사용한다. 예를 들어 이동 명령은 /cmd_vel, LiDAR는 /scan, 오도메트리는 /odom, 기본 프레임은 base_link로 맞춘다. 이렇게 하면 Nav2나 SLAM 노드는 시뮬레이션인지 실제인지 크게 신경 쓰지 않고 동작할 수 있다.

두 번째 다리는 파라미터를 분리하는 것이다. 시뮬레이션용 최대 속도와 실제 로봇용 최대 속도는 다를 수 있다. 센서 노이즈, costmap 범위, controller 제한도 다를 수 있다. 따라서 코드에 값을 박아 넣기보다 YAML 파라미터 파일로 관리하는 편이 좋다. 같은 노드 구조를 유지하되 실행 환경에 따라 파라미터를 바꾸는 방식이다.

세 번째 다리는 단계적 검증이다. 시뮬레이션에서 전체 Nav2 주행이 성공했다고 해서 바로 실제 로봇에게 긴 복도 끝까지 가라고 명령하지 않는다. 먼저 바퀴가 명령대로 도는지 확인한다. 그다음 /scan과 /odom이 정상인지 확인한다. RViz에서 TF가 맞는지 본다. 짧은 직진, 짧은 회전, 작은 목표 이동을 거쳐 점차 어려운 실험으로 넘어간다.

네 번째 다리는 로그를 남기는 것이다. 실제 로봇에서 문제가 생겼을 때 "방금 이상했는데?"로 끝나면 디버깅이 어렵다. rosbag으로 데이터를 기록해 두면 시뮬레이션이나 오프라인 환경에서 다시 분석할 수 있다. 어떤 센서가 튀었는지, 경로 계획이 왜 바뀌었는지, controller가 어떤 속도 명령을 냈는지 추적할 수 있다.

시뮬레이션과 실제 로봇은 경쟁 관계가 아니다. 시뮬레이션은 먼저 넘어져 보는 곳이고, 실제 로봇은 마지막으로 증명하는 곳이다.

시뮬레이션 실험을 설계하는 습관

좋은 시뮬레이션은 그냥 실행하는 것이 아니라 설계하는 것이다. 월드를 하나 띄우고 로봇을 움직여 보는 것도 시작으로는 충분하지만, 자율주행 알고리즘을 개선하려면 실험 조건을 의식적으로 정해야 한다.

먼저 목표를 정한다. "SLAM 지도가 덜 흔들리게 만들겠다", "좁은 통로에서 벽에 덜 붙게 만들겠다", "동적 장애물을 만났을 때 멈춤과 회피를 안정적으로 만들겠다"처럼 실험 질문이 있어야 한다. 질문이 없으면 결과도 흐릿하다.

다음으로 기준 조건을 고정한다. 월드 파일, 초기 위치, 목표 위치, 파라미터 파일, 사용한 ROS2 배포판, Gazebo 버전, launch 명령을 기록한다. 그래야 나중에 같은 실험을 다시 실행할 수 있다.

그다음 하나씩만 바꾼다. SLAM 파라미터도 바꾸고, 속도도 바꾸고, costmap도 바꾸고, 월드도 바꾸면 무엇이 결과를 바꿨는지 알 수 없다. 실험은 요리와 비슷하다. 소금, 불 세기, 조리 시간을 한꺼번에 바꾸면 무엇 때문에 맛이 달라졌는지 모른다.

마지막으로 결과를 관찰 가능한 값으로 남긴다. 도착 성공 여부, 충돌 여부, 목표까지 걸린 시간, 경로 길이, 벽과의 최소 거리, 재계획 횟수, CPU 사용량, 노드 경고 로그 등을 기록한다. RViz 화면을 보는 것도 중요하지만, 숫자와 로그가 있어야 비교할 수 있다.

이 습관은 나중에 Nav2를 다룰 때 큰 힘을 발휘한다. Nav2는 planner, controller, costmap, behavior tree가 함께 움직이는 시스템이다. 문제가 생겼을 때 감으로 파라미터를 뒤섞으면 더 복잡해진다. 반대로 실험 조건을 잘 관리하면 문제를 하나씩 좁혀 갈 수 있다.

이 장에서 기억할 것

로봇 시뮬레이션은 실제 테스트를 대체하는 마법이 아니다. 하지만 실제 테스트에 도달하기 전까지 수많은 시행착오를 빠르고 안전하게 겪게 해 주는 강력한 도구다.

하드웨어가 없어도 로봇 모델, 센서, 구동계, ROS2 노드를 먼저 연결할 수 있다. 벽 충돌, 좁은 통로, 동적 장애물처럼 실제 장비로 반복하기 위험한 상황을 안전하게 재현할 수 있다. 같은 월드와 같은 파라미터로 SLAM, 경로 계획, 장애물 회피 성능을 비교할 수 있고, rosbag을 이용하면 실험을 다시 재생하며 디버깅할 수 있다.

Gazebo는 물리 기반 가상 세계를 만들고, RViz는 ROS2 데이터와 로봇의 내부 상태를 보여 준다. launch 파일과 파라미터는 여러 노드를 일관되게 실행하고 실험 조건을 관리하게 해 준다. 이 네 가지가 함께 움직일 때 시뮬레이션은 단순한 화면이 아니라 자율주행 로봇 개발 환경이 된다.

동시에 시뮬레이션의 한계도 분명히 알아야 한다. 센서 노이즈, 통신 지연, 바퀴 미끄러짐, 마찰, 조명, 배터리, 모델 오차는 실제 로봇에서 결과를 바꿀 수 있다. 따라서 시뮬레이션에서 성공한 설정은 실제 로봇에서 다시 검증해야 한다.

이제 우리는 로봇을 가상 세계에 내려놓을 준비가 되었다. 다음 장에서는 Gazebo의 기본 개념을 살펴본다. 월드란 무엇인지, 로봇 모델은 어떻게 들어가는지, 물리 엔진과 센서 시뮬레이션은 어떤 역할을 하는지 하나씩 확인해 보자. 화면 속 로봇이 단순한 그림에서 "실험 가능한 로봇"으로 바뀌는 순간이 곧 시작된다.

참고

1ROS 2 Simulators documentation

2NVIDIA Isaac Sim ROS 2 simulation guide

3Gazebo ROS 2 integration

4Programming Multiple Robots with ROS 2 - Simulation

5Gazebo ROS 2 integration and RViz visualization

6NVIDIA Isaac Sim synthetic data and domain randomization

7Isaac Sim URDF Import: TurtleBot

책 목록

ROS2로 완성하는 자율주행 로봇: 노드·TF·SLAM·Nav2 실전 설계

전체 목차 보기

이 노트는 보도·비평·교육·연구 목적으로 작성되었습니다. 저작권 문의가 있으시면 에서 알려주세요.

틸노트는 사용자가 AI를 활용해 노트를 쉽게 작성하거나 편집할 수 있는 서비스입니다.

AI 스퀘어 단톡방에 함께해요

AI 활용과 틸노트 사용 팁을 나누는 오픈채팅방입니다. 입장 비밀번호는 tilnote입니다.

참여하기