Paweł Budziszewski Jan 31, 2024 - Robotics

Open 3D Engine (O3DE): Off-Road Vehicle Simulation in Desert Conditions

Introduction

The work described in this article was inspired by the article of Alexander Kalmykov and further elaborated on this article. My intention is not to make an extensive comparison of O3DE with other tools. While I have used Unity and Unreal in various simulation projects in the past and have a superficial knowledge of Gazebo, I do not feel competent to make such comparisons. However, I would not be myself if I did not make some references to other software based on my experience. I work in O3DE daily, so there might be some bias.

Project Overview

Objective

The aim of this project was to create a desert terrain scene featuring a model of the Polaris Dagor A1 vehicle. The primary objectives included:

  • Ensuring the functionality of the vehicle with the Ackermann controller.
  • Equipping the vehicle with a camera, lidar, and IMU sensors.
  • Making everything accessible and controllable via ROS 2.

An additional assumption was that I aimed to complete the project within a limited timeframe, and it took approximately 2 days.

Model Preparation Challenges

My usual workflow for such projects begins with finding, preparing, and importing all necessary models into the O3DE. Often, this involves some preparation of files before they can be used in the engine. However, in simpler cases, this task is as straightforward as downloading FBX files and dragging them into the scene. Even in these instances, it’s advisable to check the mesh, materials, and Level of Details (LOD) in a tool like Blender.

O3DE tip: O3DE automatically recognizes LOD meshes if they are stored as separate objects in a single FBX file, with mesh names ending with “_LOD0,” “_LOD1,” etc.

Special Case: Polaris Dagor A1 Model

Still, there are cases requiring investing much more work in the preparation of models or textures. The only available free model of the Polaris Dagor A1 was in CAD format (STEP .stp file). The initial plan was to convert the entire model into Collada (.dae) files for use in O3DE. In general, importing such models without pre-processing is not the best idea, since CAD models are never optimized for a real-time simulation. However, since O3DE typically handles them well, I gave it a try without pre-processing first.

Challenges faced:

  • Unoptimized CAD Model: The CAD model was huge, with an overwhelming 2,987,122 faces for a single wheel, a figure more suited to CAD applications than real-time simulations.
  • Software Limitations: Possibly working on this model would be easier if using professional, paid CAD software. However, without access to any of these tools, I had to rely on FreeCAD and Blender, and it led to frustration and crashes (note to self: avoid importing 2GB .ply files into Blender).

Solution
I resorted to converting selected parts of the model to PLY in FreeCAD, performing decimation in Blender to reduce size, and ultimately exporting as FBX. Although the resultant mesh was not aesthetically pleasing, remeshing the entire model would have required more time and expertise.

O3DE tip: O3DE mandates UV maps for all meshes, even if unused in materials. (e.g., no textures). CAD-based DAE files often lack UV maps. Keep this in mind when you work with the model in Blender.

I had to spend some time and effort to do this, and thus, the model preparation phase consumed nearly half of the total time.

Vehicle Model Creation

The subsequent phase of creating the vehicle model in O3DE proved to be relatively straightforward. O3DE has a physics abstraction system with PhysX 4 and 5 implementations. I used PhysX 5, which stands out for its performance, essential features for robotic simulation, and active development. The interface, resembling Unity’s, facilitates easy setup. The only thing I am missing is integration with the PhysX vehicle model. While manual creation of elements like suspension can be enjoyable, a dedicated, well-tuned model would be a valuable addition. It is especially true for aspects like the physics material model of the tire, where the standard model sometimes falls short of producing satisfactory results. The good news is that the integration of the vehicle model in O3DE is on the roadmap.

A functional vehicle model necessitates a multibody structure with rigid bodies interconnected by joints. O3DE simplifies this process through its GUI editor, allowing the addition of relevant components to entities representing each segment.

O3DE Tip: The most straightforward approach to set up a multi-body segment is to consolidate all components (rigid body, colliders, joints, and visualization) into one entity. However, I often prefer to separate the visualization part (mesh and material components) into a distinct child entity. This approach offers several advantages:

  • Independent Transformation and Scaling: You can transform or scale visualization independently of colliders. This is particularly useful when mesh files have strange scaling factors, and you typically don’t want to alter the physical body’s scale.
  • Multiple Mesh Assets: It allows pinning multiple mesh assets to one physical body. This proves beneficial when dealing with a robot imported as multiple small files.
  • Clarity: Having fewer components in one entity enhances clarity.

Suspension System

Setting up an Ackermann-type vehicle with a simple, rigid suspension is straightforward in O3DE, especially with helpful examples. This basic configuration would suffice for driving over the scene. However, given the context of creating an off-road vehicle simulation, a robust suspension system becomes a crucial element. In this case, springs and dampers are essential.

The simplest approach might involve connecting each wheel (or steering knuckle for front wheels) to the chassis using a prismatic joint with stiffness and damping. However, the Polaris model features two rigid axles with control arms, and off-road conditions necessitate accounting for substantial axle articulations. To achieve a reasonable approximation, I opted to connect each axle to the chassis using a single central swing arm. This arm connects to the chassis through a hinge joint, featuring stiffness and damping to emulate actual suspension behavior. The axle, in turn, links to the arm through another hinge joint, incorporating a longitudinal axis of rotation for axle articulations, along with stiffness and damping parameters.

While the optimal method would involve fine-tuning these suspension parameters based on real-world vehicle recordings, I didn’t have access to such data and opted not to invest additional time in this aspect. Instead, I tuned the parameters to achieve behavior that looks realistic and performs well. Undoubtedly, with proper validation data, these parameters could be further refined for increased accuracy.

ROS 2 Integration

Integrating the vehicle controller into the simulation is a straightforward process that involves incorporating a few additional components. O3DE includes an official ROS 2 Gem (module) with seamless ROS 2 support (no need for a ROS bridge!). Leveraging this built-in support streamlines the creation of all necessary ROS nodes, showcasing the power of out-of-the-box functionality.

The ROS 2 Gem includes components catering to various control aspects, such as Ackermann and Twist control. Additionally, it provides support for a range of sensors, including IMU, lidar (including a GPU-based and exceptionally fast), cameras, and more. For an overview of these components, check out the robotics documentation.

O3DE streamlines ROS 2 integration by offering URDF/XACRO import functionality. This feature makes the process easier by automatically creating a multi-body structure, pinning visualizations (with support for DAE and STL files), and configuring the necessary ROS 2 components. This becomes particularly convenient if the URDF description is correct and provides all necessary information, and if you use DAE meshes, typically converted directly from CAD models.

Environment Creation

The final element to be crafted is the environment, and O3DE, being a comprehensive game engine, boasts a robust set of features, including a powerful, highly modular terrain system. While it might seem intricate at first glance, the availability of excellent tutorials that guide through key features makes the process accessible.

Having some prior experience with the terrain system, creating the necessary components proved to be a swift task for me. However, the same cannot be said for preparing height maps, masks, and textures. Despite my ambition to handle these aspects by myself, the results were not entirely successful. On a side note, am I the only one who thinks that naming all the components for creating and modifying height or mask maps “gradients” in O3DE is a bit misleading?

Update: I had a fruitful discussion with one of the leading experts on the O3DE terrain system, and it seems that the name “gradient” has a much deeper meaning than I originally thought. It should be understood similarly to a mathematical gradient, which is a function that maps out rates of change, or gradients in image processing, mapping directional changes in intensity or color. The gradient components in O3DE are meant to describe similar types of changes but with the values mapped into world space so that they can be referenced by position. These components may have a wide range of applications. Height and mask maps in the terrain system are only one of them. You could write an audio component that uses the gradient to adjust volume or a robotics component that uses the gradient to define safe maximum speeds. You can in fact use the same gradient for ALL of those simultaneously.

Besides the terrain system, there are other useful features I used in the project, including:

  • Vegetation system – it is powerful as well but seems less intuitive to set up on first use.
  • Camera postprocessing FX – a typical set containing SSAO, Bloom, and many more features I did not need to use in this project
  • Atmosphere and distant fog
  • Environmental lighting
  • Sky box
  • Diffuse probe grid (works much better than the one I remember from Unity)And that is all, the simulation was ready!

Conclusions

This project has solidified my belief that O3DE is an excellent tool for robotic simulations. Its ability to create photorealistic scenes that run efficiently is noteworthy. While in terms of photorealism, it may not surpass the capabilities of Unreal Engine 5, which stands in a class of its own, O3DE can readily compete with Unity, often yielding superior results—such as more effective shadow rendering and a more user-friendly diffuse probe grid, contributing to a high level of photorealism.

A significant advantage is O3DE’s built-in ROS 2 support, simplifying the setup of the simulation environment. While it may take some time to configure everything correctly, the availability of examples and tutorials facilitates the process. An important highlight is O3DE’s open-source nature, coupled with a convenient Apache license. You do not have to worry, that one day you will wake up only to find out that the license fee for your favorite simulation platform has been doubled.

However, it’s essential to acknowledge certain drawbacks. O3DE, being less mature compared to Unreal Engine or Unity, may exhibit bugs and crashes, especially on Linux. I have experienced such things when working in Unreal and Unity, especially on Linux, but O3DE’s relative novelty may make such instances more frustrating. Fortunately, the project boasts an active community and adheres to a strict release cycle, consistently improving over time.

O3DE’s Strengths

  • Built-in ROS 2 support, with a lot of useful components.
  • Fast, feature-rich, GPU-based lidar simulation.
  • URDF/XACRO import with support for CAD models (.dae and .stl).
  • Nice terrain and vegetation systems. Both are powerful, yet easy to use.
  • Apache license.

Limitations 

  • Occasional bugs and crushes.
  • Not all the features that could be useful in the robotic simulation are yet implemented in O3DE, e.g., the PhysX vehicle model.

Final thoughts

O3DE is highly competent for robotic simulations, balancing photorealism with performance. It competes effectively with platforms like Unreal Engine 5 and Unity, particularly in shadow rendering and diffuse probe grid performance. Its open-source nature and active community support add to its appeal for simulation projects.

Interested in our latest projects? Follow us on  LinkedIn to always stay updated!
You can also visit our page on GitHub to discover more of our open-source projects.

Authors:
Paweł Budziszewski, Simulation Engineer (the Simulation Engines department) at Robotec.ai
Adam Dąbrowski, VP of Robotics and Simulation at Robotec.ai

Share post: