Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use MAVROS for PX4 middleware #44

Merged
merged 12 commits into from
Apr 7, 2023
Merged
Prev Previous commit
Next Next commit
Update PX4 docker compose service
  • Loading branch information
hmakelin committed Apr 5, 2023
commit b67f6f3489e4b1f97a043cd778b7bb22921e0fb2
1 change: 1 addition & 0 deletions docker/docker-compose.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -103,6 +103,7 @@ services:
- driver: nvidia
count: 1
capabilities: [ gpu ]
command: make px4_sitl gazebo_typhoon_h480__ksql_airport

ardupilot:
build:
Expand Down
7 changes: 4 additions & 3 deletions docker/px4/6011_typhoon_h480
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
# SIMULATION USE ONLY
# PX4 mock GPS SITL simulation demo default parameters
# GISNav PX4 mock GPS SITL simulation demo default parameters
# PX4 v1.13
param set-default NAV_ACC_RAD 20.0
param set-default MPC_YAWRAUTO_MAX 22.5.0
param set-default COM_POS_FS_DELAY 5
Expand All @@ -9,5 +10,5 @@ param set-default EKF2_GPS_P_GATE 7
param set-default EKF2_GPS_V_NOISE 3
param set-default SENS_GPS_MASK 4

param set-default EKF2_GPS_CTRL 3
param set-default EKF2_GPS_CHECK 12
#param set-default EKF2_GPS_CTRL 3
#param set-default EKF2_GPS_CHECK 12
61 changes: 21 additions & 40 deletions docker/px4/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -2,52 +2,33 @@ FROM px4io/px4-dev-ros2-foxy

LABEL maintainer="Harri Makelin <hmakelin@protonmail.com>"

ARG USERNAME=gisnav
ARG UID=1000
ARG GID=$UID

ARG ROS_DOMAIN_ID=0
ENV ROS_DOMAIN_ID=${ROS_DOMAIN_ID}

# Set 'gisnav' as default user and add it to sudo'ers
# QGroundControl will not run as 'root'
RUN apt-get update --fix-missing && \
apt-get install sudo && \
groupadd --gid $GID $USERNAME && useradd --uid $UID --gid $GID -m $USERNAME && \
echo "${USERNAME} ALL=(ALL) NOPASSWD:ALL" > /etc/sudoers.d/$USERNAME
USER $USERNAME

# gstreamer and Gazebo plugins for getting video stream out of gazebo
RUN sudo apt-get -y install ros-foxy-gazebo-ros-pkgs gstreamer1.0-plugins-bad gstreamer1.0-libav gstreamer1.0-gl
RUN apt-get update && \
apt-get -y dist-upgrade && \
apt-get -y install ros-foxy-gazebo-ros-pkgs gstreamer1.0-plugins-bad \
gstreamer1.0-libav gstreamer1.0-gl

# Install PX4-Autopilot, pull latest commit from PX4-SITL_gazebo submodule fork
# Install PX4-Autopilot
RUN sudo apt-get -y install -o Dpkg::Options::="--force-overwrite" \
libignition-common3-core-dev libignition-common3-av-dev expect && \
git clone --branch hmakelin-v1.14.0-beta1 \
https://github.com/hmakelin/PX4-Autopilot.git $HOME/PX4-Autopilot --recursive && \
cd $HOME/PX4-Autopilot && \
git fetch --all --tags && \
git checkout tags/v1.14.0-1.0.1-beta1 -b gisnav && \
git submodule update --init --recursive && \
cd Tools/simulation/gazebo/sitl_gazebo && \
git pull origin hmakelin-v1.14.0-beta1 && \
cd $HOME/PX4-Autopilot && \
git clone --branch v1.13.3 --single-branch \
https://github.com/PX4/PX4-Autopilot.git --recursive && \
cd PX4-Autopilot && \
bash Tools/setup/ubuntu.sh --no-nuttx

# Add ROS camera plugin
COPY * /
RUN pip install lxml && \
python3 merge_xml.py ros_camera.xml PX4-Autopilot/Tools/sitl_gazebo/models/typhoon_h480/typhoon_h480.sdf.jinja

# Make initial PX4 build (for faster startup in the future)
RUN cd $HOME/PX4-Autopilot && \
yes | DONT_RUN=1 make px4_sitl gazebo_typhoon_h480__ksql_airport
RUN cd PX4-Autopilot && \
DONT_RUN=1 make px4_sitl gazebo_typhoon_h480__ksql_airport

# Apply configuration files
COPY * /
RUN sudo mv -t $HOME/ /6011_typhoon_h480 && \
cat $HOME/6011_typhoon_h480 >> $HOME/PX4-Autopilot/ROMFS/px4fmu_common/init.d-posix/airframes/6011_typhoon_h480

# Run SITL simulation - answer 'y' to prompt about custom commit in submodule (temp fix until 1.14 stable comes out)
CMD cd ${HOME}/PX4-Autopilot && \
expect -c \
"set timeout -1; \
spawn make px4_sitl gazebo_typhoon_h480__ksql_airport; \
expect \"Hit 'y' and <ENTER> to continue the build with this version. Hit <ENTER> to resolve manually.\"; \
send \"y\n\"; \
interact"
RUN cat 6011_typhoon_h480 >> PX4-Autopilot/ROMFS/px4fmu_common/init.d-posix/airframes/6011_typhoon_h480

RUN rm -rf /var/lib/apt/lists/* && \
apt clean

WORKDIR PX4-Autopilot
83 changes: 83 additions & 0 deletions docker/px4/merge_xml.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,83 @@
"""
This script merges an XML file containing a Gazebo plugin definition with a
typhoon_h480.sdf.jinja file, which is part of the PX4 SITL Gazebo plugin. The
XML file should include a plugin definition that needs to be placed under the
camera sensor element in the typhoon_h480.sdf.jinja file.

Usage:
python merge_xml.py path/to/xml_file.xml path/to/typhoon_h480.sdf.jinja

Arguments:
xml_file: Path to the XML file containing the plugin definition.
sdf_jinja_file: Path to the typhoon_h480.sdf.jinja file.

The script will merge the plugin definition from the provided XML file into the
typhoon_h480.sdf.jinja file "in-place". If the camera sensor element is not
found in the typhoon_h480.sdf.jinja file, the script will print an error
message and exit.
"""
import argparse
import os

from lxml import etree


def merge_xml(xml_file, sdf_jinja_file):
"""
Merge an XML file containing a Gazebo plugin definition into a
typhoon_h480.sdf.jinja file.

This function reads the plugin definition from the provided XML file and
inserts it under the camera sensor element in the typhoon_h480.sdf.jinja file.
The modified content is then written back to the typhoon_h480.sdf.jinja file.

Args:
xml_file (str): Path to the XML file containing the plugin definition.
sdf_jinja_file (str): Path to the typhoon_h480.sdf.jinja file.

If the camera sensor element is not found in the typhoon_h480.sdf.jinja file,
an error message is printed and the function returns without modifying the file.
"""
# Parse the provided XML file
with open(xml_file, "r") as file:
xml_content = file.read()
snippet_tree = etree.fromstring(xml_content)

# Parse the typhoon_h480.sdf.jinja file
with open(sdf_jinja_file, "r") as file:
sdf_jinja_content = file.read()
sdf_jinja_tree = etree.fromstring(sdf_jinja_content)

# Find the camera sensor in the typhoon_h480.sdf.jinja file
camera_sensor = sdf_jinja_tree.xpath("//sensor[@name='camera']")

if camera_sensor:
# Insert the plugin from the XML file under the camera sensor element
camera_sensor[0].append(snippet_tree.find(".//plugin"))

# Write the modified content back to the typhoon_h480.sdf.jinja file
with open(sdf_jinja_file, "wb") as file:
file.write(etree.tostring(sdf_jinja_tree, pretty_print=True))
else:
print("Camera sensor not found in the typhoon_h480.sdf.jinja file.")


if __name__ == "__main__":
parser = argparse.ArgumentParser(description="Merge XML files.")
parser.add_argument(
"xml_file", type=str, help="Path to the XML file with the plugin data."
)
parser.add_argument(
"sdf_jinja_file", type=str, help="Path to the typhoon_h480.sdf.jinja file."
)

args = parser.parse_args()

if os.path.exists(args.xml_file) and os.path.exists(args.sdf_jinja_file):
merge_xml(args.xml_file, args.sdf_jinja_file)
print("XML snippet merged successfully!")
else:
if not os.path.exists(args.xml_file):
print(f"File '{args.xml_file}' not found.")
if not os.path.exists(args.sdf_jinja_file):
print(f"File '{args.sdf_jinja_file}' not found.")
13 changes: 13 additions & 0 deletions docker/px4/ros_camera.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
<sdf version='1.5'>
<model name='typhoon_h480'>
<link name="cgo3_camera_link">
<sensor name="camera" type="camera">
<plugin name="camera_plugin" filename="libgazebo_ros_camera.so">
<alwaysOn>true</alwaysOn>
<imageTopicName>image_raw</imageTopicName>
<cameraInfoTopicName>camera_info</cameraInfoTopicName>
</plugin>
</sensor>
</link>
</model>
</sdf>