diff --git a/README.md b/README.md
index c60436a..02df642 100644
--- a/README.md
+++ b/README.md
@@ -63,7 +63,6 @@ A general overview can be found in the paper [RapidPoseTriangulation: Multi-view
## Extras
-- For usage in combination with ROS2 see [ros](extras/ros/README.md) directory.
diff --git a/bindings/rpt_module.cpp b/bindings/rpt_module.cpp
index 8f94f47..a83934c 100644
--- a/bindings/rpt_module.cpp
+++ b/bindings/rpt_module.cpp
@@ -167,6 +167,11 @@ NB_MODULE(_core, m)
return camera.to_string();
});
+ nb::class_(m, "TriangulationOptions")
+ .def(nb::init<>())
+ .def_rw("min_match_score", &TriangulationOptions::min_match_score)
+ .def_rw("min_group_size", &TriangulationOptions::min_group_size);
+
nb::class_(m, "PairCandidate")
.def(nb::init<>())
.def_rw("view1", &PairCandidate::view1)
@@ -268,12 +273,14 @@ NB_MODULE(_core, m)
const PoseArray3DConst &previous_poses_3d,
float min_match_score)
{
+ TriangulationOptions options;
+ options.min_match_score = min_match_score;
return filter_pairs_with_previous_poses(
pose_batch_view_from_numpy(poses_2d, person_counts),
cameras,
joint_names,
pose_batch3d_view_from_numpy(previous_poses_3d),
- min_match_score);
+ options);
},
"poses_2d"_a,
"person_counts"_a,
@@ -292,14 +299,16 @@ NB_MODULE(_core, m)
float min_match_score,
size_t min_group_size)
{
+ TriangulationOptions options;
+ options.min_match_score = min_match_score;
+ options.min_group_size = min_group_size;
return triangulate_debug(
pose_batch_view_from_numpy(poses_2d, person_counts),
cameras,
roomparams_from_numpy(roomparams),
joint_names,
nullptr,
- min_match_score,
- min_group_size);
+ options);
},
"poses_2d"_a,
"person_counts"_a,
@@ -321,14 +330,16 @@ NB_MODULE(_core, m)
size_t min_group_size)
{
const PoseBatch3DView previous_view = pose_batch3d_view_from_numpy(previous_poses_3d);
+ TriangulationOptions options;
+ options.min_match_score = min_match_score;
+ options.min_group_size = min_group_size;
return triangulate_debug(
pose_batch_view_from_numpy(poses_2d, person_counts),
cameras,
roomparams_from_numpy(roomparams),
joint_names,
&previous_view,
- min_match_score,
- min_group_size);
+ options);
},
"poses_2d"_a,
"person_counts"_a,
@@ -349,14 +360,16 @@ NB_MODULE(_core, m)
float min_match_score,
size_t min_group_size)
{
+ TriangulationOptions options;
+ options.min_match_score = min_match_score;
+ options.min_group_size = min_group_size;
const PoseBatch3D poses_3d = triangulate_poses(
pose_batch_view_from_numpy(poses_2d, person_counts),
cameras,
roomparams_from_numpy(roomparams),
joint_names,
nullptr,
- min_match_score,
- min_group_size);
+ options);
return pose_batch_to_numpy(poses_3d);
},
"poses_2d"_a,
@@ -379,14 +392,16 @@ NB_MODULE(_core, m)
size_t min_group_size)
{
const PoseBatch3DView previous_view = pose_batch3d_view_from_numpy(previous_poses_3d);
+ TriangulationOptions options;
+ options.min_match_score = min_match_score;
+ options.min_group_size = min_group_size;
const PoseBatch3D poses_3d = triangulate_poses(
pose_batch_view_from_numpy(poses_2d, person_counts),
cameras,
roomparams_from_numpy(roomparams),
joint_names,
&previous_view,
- min_match_score,
- min_group_size);
+ options);
return pose_batch_to_numpy(poses_3d);
},
"poses_2d"_a,
diff --git a/extras/ros/README.md b/extras/ros/README.md
deleted file mode 100644
index e1b3d11..0000000
--- a/extras/ros/README.md
+++ /dev/null
@@ -1,22 +0,0 @@
-# ROS Wrapper
-
-Run the 3D triangulator with ROS topics as inputs and publish detected poses.
-
-
-
-- Build container:
-
- ```bash
- docker build --progress=plain -t rapidposetriangulation_ros3d -f extras/ros/dockerfile_3d .
- ```
-
-- Update or remove the `ROS_DOMAIN_ID` in the `docker-compose.yml` files to fit your environment
-
-- Run and test:
-
- ```bash
- xhost + && docker compose -f extras/ros/docker-compose-3d.yml up
-
- docker exec -it ros-test_node-1 bash
- export ROS_DOMAIN_ID=18
- ```
diff --git a/extras/ros/docker-compose-3d.yml b/extras/ros/docker-compose-3d.yml
deleted file mode 100644
index 7989b27..0000000
--- a/extras/ros/docker-compose-3d.yml
+++ /dev/null
@@ -1,70 +0,0 @@
-services:
-
- test_node:
- image: rapidposetriangulation_ros3d
- network_mode: "host"
- ipc: "host"
- privileged: true
- volumes:
- - ../../:/RapidPoseTriangulation/
- - /tmp/.X11-unix:/tmp/.X11-unix
- - /dev/shm:/dev/shm
- environment:
- - DISPLAY
- - QT_X11_NO_MITSHM=1
- - "PYTHONUNBUFFERED=1"
- command: /bin/bash -i -c 'sleep infinity'
-
- triangulator:
- image: rapidposetriangulation_ros3d
- network_mode: "host"
- ipc: "host"
- privileged: true
- volumes:
- - ../../:/RapidPoseTriangulation/
- - /tmp/.X11-unix:/tmp/.X11-unix
- - /dev/shm:/dev/shm
- environment:
- - DISPLAY
- - QT_X11_NO_MITSHM=1
- - "PYTHONUNBUFFERED=1"
- command: /bin/bash -i -c 'export ROS_DOMAIN_ID=18 && ros2 run rpt3d_wrapper_cpp rpt3d_wrapper'
-
- skeleton_markers:
- image: rapidposetriangulation_ros3d
- network_mode: "host"
- ipc: "host"
- privileged: true
- volumes:
- - ../../:/RapidPoseTriangulation/
- - /tmp/.X11-unix:/tmp/.X11-unix
- - /dev/shm:/dev/shm
- environment:
- - "PYTHONUNBUFFERED=1"
- command: /bin/bash -i -c 'export ROS_DOMAIN_ID=18 && ros2 run marker_publishers skeleton_markers'
-
- cube_markers:
- image: rapidposetriangulation_ros3d
- network_mode: "host"
- ipc: "host"
- privileged: true
- volumes:
- - ../../:/RapidPoseTriangulation/
- - /tmp/.X11-unix:/tmp/.X11-unix
- - /dev/shm:/dev/shm
- environment:
- - "PYTHONUNBUFFERED=1"
- command: /bin/bash -i -c 'export ROS_DOMAIN_ID=18 && ros2 run marker_publishers cube_markers'
-
- skeleton_tfs:
- image: rapidposetriangulation_ros3d
- network_mode: "host"
- ipc: "host"
- privileged: true
- volumes:
- - ../../:/RapidPoseTriangulation/
- - /tmp/.X11-unix:/tmp/.X11-unix
- - /dev/shm:/dev/shm
- environment:
- - "PYTHONUNBUFFERED=1"
- command: /bin/bash -i -c 'export ROS_DOMAIN_ID=18 && ros2 run marker_publishers skeleton_tfs'
diff --git a/extras/ros/dockerfile_3d b/extras/ros/dockerfile_3d
deleted file mode 100644
index 1196e69..0000000
--- a/extras/ros/dockerfile_3d
+++ /dev/null
@@ -1,46 +0,0 @@
-FROM ros:humble-ros-base-jammy
-ARG DEBIAN_FRONTEND=noninteractive
-
-# Set the working directory to /project
-WORKDIR /project/
-
-# Update and install basic tools
-RUN apt-get update && apt-get upgrade -y
-RUN apt-get update && apt-get install -y --no-install-recommends git nano wget
-RUN apt-get update && apt-get install -y --no-install-recommends python3-pip
-RUN pip3 install --upgrade pip
-
-# Fix ros package building error
-RUN pip3 install --no-cache-dir "setuptools<=58.2.0"
-
-# Add ROS2 sourcing by default
-RUN echo "source /opt/ros/humble/setup.bash" >> ~/.bashrc
-
-# Create ROS2 workspace for project packages
-RUN mkdir -p /project/dev_ws/src/
-RUN cd /project/dev_ws/; colcon build
-RUN echo "source /project/dev_ws/install/setup.bash" >> ~/.bashrc
-
-# Copy modules
-COPY ./extras/include/ /RapidPoseTriangulation/extras/include/
-COPY ./rpt/ /RapidPoseTriangulation/rpt/
-COPY ./extras/ros/marker_publishers/ /RapidPoseTriangulation/extras/ros/marker_publishers/
-COPY ./extras/ros/rpt_msgs/ /RapidPoseTriangulation/extras/ros/rpt_msgs/
-COPY ./extras/ros/rpt3d_wrapper_cpp/ /RapidPoseTriangulation/extras/ros/rpt3d_wrapper_cpp/
-
-# Link and build as ros package
-RUN ln -s /RapidPoseTriangulation/extras/ros/marker_publishers/ /project/dev_ws/src/
-RUN ln -s /RapidPoseTriangulation/extras/ros/rpt_msgs/ /project/dev_ws/src/
-RUN ln -s /RapidPoseTriangulation/extras/ros/rpt3d_wrapper_cpp/ /project/dev_ws/src/
-RUN /bin/bash -i -c 'cd /project/dev_ws/; colcon build --symlink-install --cmake-args -DCMAKE_BUILD_TYPE=Release'
-
-# Update ros packages -> autocompletion and check
-RUN /bin/bash -i -c 'ros2 pkg list'
-
-# Clear cache to save space, only has an effect if image is squashed
-RUN apt-get autoremove -y \
- && apt-get clean \
- && rm -rf /var/lib/apt/lists/*
-
-WORKDIR /RapidPoseTriangulation/
-CMD ["/bin/bash"]
diff --git a/extras/ros/marker_publishers/CMakeLists.txt b/extras/ros/marker_publishers/CMakeLists.txt
deleted file mode 100644
index bd51c83..0000000
--- a/extras/ros/marker_publishers/CMakeLists.txt
+++ /dev/null
@@ -1,63 +0,0 @@
-cmake_minimum_required(VERSION 3.5)
-project(marker_publishers)
-
-# Default to C99
-if(NOT CMAKE_C_STANDARD)
- set(CMAKE_C_STANDARD 99)
-endif()
-
-# Default to C++14
-if(NOT CMAKE_CXX_STANDARD)
- set(CMAKE_CXX_STANDARD 14)
-endif()
-
-if(CMAKE_COMPILER_IS_GNUCXX OR CMAKE_CXX_COMPILER_ID MATCHES "Clang")
- add_compile_options(-Wall -Wextra -Wpedantic)
-endif()
-
-# find dependencies
-find_package(ament_cmake REQUIRED)
-find_package(rclcpp REQUIRED)
-find_package(rpt_msgs REQUIRED)
-find_package(geometry_msgs REQUIRED)
-find_package(tf2_ros REQUIRED)
-find_package(visualization_msgs REQUIRED)
-
-add_executable(cube_markers src/cube_markers.cpp)
-ament_target_dependencies(cube_markers rclcpp geometry_msgs visualization_msgs)
-target_include_directories(cube_markers PUBLIC
- $
- $)
-
-add_executable(skeleton_markers src/skeleton_markers.cpp)
-ament_target_dependencies(skeleton_markers rclcpp rpt_msgs geometry_msgs visualization_msgs)
-target_include_directories(skeleton_markers PUBLIC
- $
- $)
-
-add_executable(skeleton_tfs src/skeleton_tfs.cpp)
-ament_target_dependencies(skeleton_tfs rclcpp rpt_msgs geometry_msgs tf2_ros)
-target_include_directories(skeleton_tfs PUBLIC
- $
- $)
-
-install(TARGETS cube_markers
- DESTINATION lib/${PROJECT_NAME})
-
-install(TARGETS skeleton_markers
- DESTINATION lib/${PROJECT_NAME})
-
-install(TARGETS skeleton_tfs
- DESTINATION lib/${PROJECT_NAME})
-if(BUILD_TESTING)
- find_package(ament_lint_auto REQUIRED)
- # the following line skips the linter which checks for copyrights
- # uncomment the line when a copyright and license is not present in all source files
- #set(ament_cmake_copyright_FOUND TRUE)
- # the following line skips cpplint (only works in a git repo)
- # uncomment the line when this package is not in a git repo
- #set(ament_cmake_cpplint_FOUND TRUE)
- ament_lint_auto_find_test_dependencies()
-endif()
-
-ament_package()
diff --git a/extras/ros/marker_publishers/package.xml b/extras/ros/marker_publishers/package.xml
deleted file mode 100644
index 2ca1087..0000000
--- a/extras/ros/marker_publishers/package.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-
-
-
- marker_publishers
- 0.0.0
- TODO: Package description
- root
- TODO: License declaration
-
- ament_cmake
-
- rclcpp
- rpt_msgs
- geometry_msgs
- tf2_ros
- visualization_msgs
-
- ament_lint_auto
- ament_lint_common
-
-
- ament_cmake
-
-
diff --git a/extras/ros/marker_publishers/src/cube_markers.cpp b/extras/ros/marker_publishers/src/cube_markers.cpp
deleted file mode 100644
index 403f2fd..0000000
--- a/extras/ros/marker_publishers/src/cube_markers.cpp
+++ /dev/null
@@ -1,122 +0,0 @@
-#include
-#include
-
-#include
-#include
-#include
-#include
-
-// =================================================================================================
-
-const std::string output_topic = "/markers_cube";
-static const std::array, 2> roomparams = {{
- {4.0, 5.0, 2.2},
- {1.0, 0.0, 1.1},
-}};
-
-// =================================================================================================
-// =================================================================================================
-
-class CubePublisher : public rclcpp::Node
-{
-public:
- CubePublisher() : Node("cube_publisher")
- {
- publisher_ = this->create_publisher(output_topic, 1);
- timer_ = this->create_wall_timer(
- std::chrono::seconds(1), std::bind(&CubePublisher::timer_callback, this));
-
- cube_edges = generate_cube_edges();
- }
-
-private:
- visualization_msgs::msg::MarkerArray cube_edges;
- rclcpp::Publisher::SharedPtr publisher_;
- rclcpp::TimerBase::SharedPtr timer_;
-
- void timer_callback()
- {
- publisher_->publish(cube_edges);
- }
- visualization_msgs::msg::MarkerArray generate_cube_edges();
-};
-
-// =================================================================================================
-
-visualization_msgs::msg::MarkerArray CubePublisher::generate_cube_edges()
-{
- visualization_msgs::msg::MarkerArray marker_array;
- visualization_msgs::msg::Marker marker;
-
- marker.header.frame_id = "world";
- marker.type = visualization_msgs::msg::Marker::LINE_LIST;
- marker.action = visualization_msgs::msg::Marker::ADD;
- marker.scale.x = 0.05;
- marker.id = 0;
-
- marker.color.a = 1.0;
- marker.color.r = 1.0;
-
- std::vector> corners = {
- {-1, -1, -1},
- {1, -1, -1},
- {1, 1, -1},
- {-1, 1, -1},
- {-1, -1, 1},
- {1, -1, 1},
- {1, 1, 1},
- {-1, 1, 1},
- };
-
- for (auto &corner : corners)
- {
- for (size_t i = 0; i < corner.size(); ++i)
- {
- corner[i] = 0.5 * roomparams[0][i] * corner[i] + roomparams[1][i];
- }
- }
-
- std::vector> edge_indices = {
- {0, 1},
- {1, 2},
- {2, 3},
- {3, 0},
- {4, 5},
- {5, 6},
- {6, 7},
- {7, 4},
- {0, 4},
- {1, 5},
- {2, 6},
- {3, 7},
- };
-
- for (const auto &edge : edge_indices)
- {
- geometry_msgs::msg::Point p1, p2;
- p1.x = corners[edge.first][0];
- p1.y = corners[edge.first][1];
- p1.z = corners[edge.first][2];
-
- p2.x = corners[edge.second][0];
- p2.y = corners[edge.second][1];
- p2.z = corners[edge.second][2];
-
- marker.points.push_back(p1);
- marker.points.push_back(p2);
- }
-
- marker_array.markers.push_back(marker);
- return marker_array;
-}
-
-// =================================================================================================
-// =================================================================================================
-
-int main(int argc, char *argv[])
-{
- rclcpp::init(argc, argv);
- rclcpp::spin(std::make_shared());
- rclcpp::shutdown();
- return 0;
-}
diff --git a/extras/ros/marker_publishers/src/skeleton_markers.cpp b/extras/ros/marker_publishers/src/skeleton_markers.cpp
deleted file mode 100644
index c4c3448..0000000
--- a/extras/ros/marker_publishers/src/skeleton_markers.cpp
+++ /dev/null
@@ -1,255 +0,0 @@
-#include
-#include
-#include
-
-#include
-#include
-#include
-#include
-#include
-
-#include "rpt_msgs/msg/poses.hpp"
-
-// =================================================================================================
-
-const std::string input_topic = "/poses/humans3d";
-const std::string output_topic = "/markers_skeleton";
-
-// =================================================================================================
-// =================================================================================================
-
-std::array hue_to_rgb(double hue)
-{
- double r, g, b;
- int h = static_cast(hue * 6);
- double f = hue * 6 - h;
- double q = 1 - f;
-
- switch (h % 6)
- {
- case 0:
- r = 1;
- g = f;
- b = 0;
- break;
- case 1:
- r = q;
- g = 1;
- b = 0;
- break;
- case 2:
- r = 0;
- g = 1;
- b = f;
- break;
- case 3:
- r = 0;
- g = q;
- b = 1;
- break;
- case 4:
- r = f;
- g = 0;
- b = 1;
- break;
- case 5:
- r = 1;
- g = 0;
- b = q;
- break;
- default:
- r = g = b = 0;
- break;
- }
-
- std::array rgb = {
- static_cast(r * 255),
- static_cast(g * 255),
- static_cast(b * 255)};
-
- return rgb;
-}
-
-// =================================================================================================
-// =================================================================================================
-
-class SkeletonPublisher : public rclcpp::Node
-{
-public:
- SkeletonPublisher() : Node("skeleton_publisher")
- {
- publisher_ = this->create_publisher(output_topic, 1);
- subscriber_ = this->create_subscription(
- input_topic, 1,
- std::bind(&SkeletonPublisher::listener_callback, this, std::placeholders::_1));
-
- connections = {
- {"shoulder_middle", "head"},
- {"head", "nose"},
- {"nose", "eye_left"},
- {"nose", "eye_right"},
- {"eye_left", "ear_left"},
- {"eye_right", "ear_right"},
- {"shoulder_left", "shoulder_right"},
- {"hip_middle", "shoulder_left"},
- {"hip_middle", "shoulder_right"},
- {"shoulder_left", "elbow_left"},
- {"elbow_left", "wrist_left"},
- {"hip_middle", "hip_left"},
- {"hip_left", "knee_left"},
- {"knee_left", "ankle_left"},
- {"shoulder_right", "elbow_right"},
- {"elbow_right", "wrist_right"},
- {"hip_middle", "hip_right"},
- {"hip_right", "knee_right"},
- {"knee_right", "ankle_right"},
- };
- }
-
-private:
- std::vector> connections;
- rclcpp::Publisher::SharedPtr publisher_;
- rclcpp::Subscription::SharedPtr subscriber_;
-
- void listener_callback(const rpt_msgs::msg::Poses::SharedPtr msg);
- visualization_msgs::msg::MarkerArray generate_msg(
- const std::vector>> &poses,
- const std::vector &joint_names);
-};
-
-// =================================================================================================
-
-void SkeletonPublisher::listener_callback(const rpt_msgs::msg::Poses::SharedPtr msg)
-{
- std::vector>> poses;
- const std::vector &joint_names = msg->joint_names;
-
- // Unflatten poses
- size_t idx = 0;
- std::vector &bshape = msg->bodies_shape;
- for (int32_t i = 0; i < bshape[0]; ++i)
- {
- std::vector> body;
- for (int32_t j = 0; j < bshape[1]; ++j)
- {
- std::array joint;
- for (int32_t k = 0; k < bshape[2]; ++k)
- {
- joint[k] = msg->bodies_flat[idx];
- ++idx;
- }
- body.push_back(std::move(joint));
- }
- poses.push_back(std::move(body));
- }
-
- auto skelmsg = generate_msg(poses, joint_names);
- publisher_->publish(skelmsg);
-}
-
-// =================================================================================================
-
-visualization_msgs::msg::MarkerArray SkeletonPublisher::generate_msg(
- const std::vector>> &poses,
- const std::vector &joint_names)
-{
- visualization_msgs::msg::MarkerArray marker_array;
- visualization_msgs::msg::Marker marker;
-
- marker.header.frame_id = "world";
- marker.type = visualization_msgs::msg::Marker::LINE_LIST;
- marker.action = visualization_msgs::msg::Marker::ADD;
- marker.scale.x = 0.02;
- marker.id = 0;
-
- size_t num_bodies = poses.size();
- for (size_t i = 0; i < num_bodies; ++i)
- {
- std_msgs::msg::ColorRGBA color;
- double hue = static_cast(i) / num_bodies;
- auto rgb = hue_to_rgb(hue);
- color.r = rgb[0] / 255.0;
- color.g = rgb[1] / 255.0;
- color.b = rgb[2] / 255.0;
- color.a = 1.0;
-
- for (size_t j = 0; j < connections.size(); ++j)
- {
- std::string joint1 = connections[j][0];
- std::string joint2 = connections[j][1];
-
- int sidx = -1;
- int eidx = -1;
- for (size_t k = 0; k < joint_names.size(); ++k)
- {
- if (joint_names[k] == joint1)
- {
- sidx = k;
- }
- if (joint_names[k] == joint2)
- {
- eidx = k;
- }
- }
- if (sidx == -1 || eidx == -1)
- {
- continue;
- }
-
- if (poses[i][sidx][3] <= 0 || poses[i][eidx][3] <= 0)
- {
- continue;
- }
-
- geometry_msgs::msg::Point p1, p2;
- p1.x = poses[i][sidx][0];
- p1.y = poses[i][sidx][1];
- p1.z = poses[i][sidx][2];
- p2.x = poses[i][eidx][0];
- p2.y = poses[i][eidx][1];
- p2.z = poses[i][eidx][2];
-
- marker.points.push_back(p1);
- marker.points.push_back(p2);
- marker.colors.push_back(color);
- marker.colors.push_back(color);
- }
- }
-
- if (num_bodies == 0)
- {
- // Create an invisible line to remove any old skeletons
- std_msgs::msg::ColorRGBA color;
- color.r = 0.0;
- color.g = 0.0;
- color.b = 0.0;
- color.a = 0.0;
-
- geometry_msgs::msg::Point p1, p2;
- p1.x = 0.0;
- p1.y = 0.0;
- p1.z = 0.0;
- p2.x = 0.0;
- p2.y = 0.0;
- p2.z = 0.001;
-
- marker.points.push_back(p1);
- marker.points.push_back(p2);
- marker.colors.push_back(color);
- marker.colors.push_back(color);
- }
-
- marker_array.markers.push_back(marker);
- return marker_array;
-}
-
-// =================================================================================================
-// =================================================================================================
-
-int main(int argc, char *argv[])
-{
- rclcpp::init(argc, argv);
- rclcpp::spin(std::make_shared());
- rclcpp::shutdown();
- return 0;
-}
diff --git a/extras/ros/marker_publishers/src/skeleton_tfs.cpp b/extras/ros/marker_publishers/src/skeleton_tfs.cpp
deleted file mode 100644
index 2444b56..0000000
--- a/extras/ros/marker_publishers/src/skeleton_tfs.cpp
+++ /dev/null
@@ -1,335 +0,0 @@
-#include
-#include
-#include