Skip to content

Commit 4cd9ed7

Browse files
committed
Merge branch 'kinfu-rgb'
2 parents e02e8fb + 7e5bb02 commit 4cd9ed7

File tree

13 files changed

+412
-201
lines changed

13 files changed

+412
-201
lines changed

CMakeLists.txt

+1-1
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,7 @@ list(APPEND CMAKE_MODULE_PATH ${CMAKE_SOURCE_DIR}/cmake
3939
# Hard dependencies.
4040
find_package(YCM 0.11 REQUIRED)
4141
find_package(YARP 3.4 REQUIRED COMPONENTS os dev sig
42-
OPTIONAL_COMPONENTS cv pcl)
42+
OPTIONAL_COMPONENTS cv idl_tools pcl)
4343

4444
# Soft dependencies.
4545
find_package(OpenCV QUIET)

examples/cpp/CMakeLists.txt

+4-1
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,10 @@ if(ENABLE_examples)
1212
add_subdirectory(exampleMeshFromCloud)
1313
add_subdirectory(exampleMeshFromLiveRGBD)
1414
add_subdirectory(exampleProcessCloud)
15-
add_subdirectory(exampleSceneReconstructionClient)
15+
16+
if(TARGET ROBOTICSLAB::VisionIDL)
17+
add_subdirectory(exampleSceneReconstructionClient)
18+
endif()
1619
endif()
1720

1821
add_subdirectory(exampleRemoteGrabber)

examples/cpp/exampleSceneReconstructionClient/CMakeLists.txt

+3-2
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ if(NOT YARP_FOUND)
66
find_package(YARP 3.4 REQUIRED COMPONENTS os sig)
77
endif()
88

9-
if(NOT TARGET ROBOTICSLAB::YarpCloudUtils)
9+
if(NOT TARGET ROBOTICSLAB::YarpCloudUtils OR NOT TARGET ROBOTICSLAB::VisionIDL)
1010
find_package(ROBOTICSLAB_VISION REQUIRED)
1111
endif()
1212

@@ -15,4 +15,5 @@ add_executable(exampleSceneReconstructionClient main.cpp)
1515
target_link_libraries(exampleSceneReconstructionClient YARP::YARP_os
1616
YARP::YARP_init
1717
YARP::YARP_sig
18-
ROBOTICSLAB::YarpCloudUtils)
18+
ROBOTICSLAB::YarpCloudUtils
19+
ROBOTICSLAB::VisionIDL)

examples/cpp/exampleSceneReconstructionClient/main.cpp

+11-16
Original file line numberDiff line numberDiff line change
@@ -4,29 +4,22 @@
44
* @brief Sample usage of @ref sceneReconstruction.
55
*/
66

7-
#include <yarp/conf/version.h>
8-
97
#include <yarp/os/LogStream.h>
108
#include <yarp/os/Network.h>
119
#include <yarp/os/ResourceFinder.h>
1210
#include <yarp/os/RpcClient.h>
1311
#include <yarp/os/SystemClock.h>
1412
#include <yarp/os/Value.h>
15-
#include <yarp/os/Vocab.h>
13+
1614
#include <yarp/sig/PointCloud.h>
1715

1816
#include <YarpCloudUtils.hpp>
17+
#include <SceneReconstructionIDL.h>
1918

2019
constexpr auto DEFAULT_REMOTE = "/sceneReconstruction";
2120
constexpr auto DEFAULT_PREFIX = "/exampleSceneReconstructionClient";
2221
constexpr auto DEFAULT_COLLECTION = "meshPipeline";
2322

24-
#if YARP_VERSION_MINOR >= 5
25-
constexpr auto VOCAB_GET_POINTS = yarp::os::createVocab32('g','p','c');
26-
#else
27-
constexpr auto VOCAB_GET_POINTS = yarp::os::createVocab('g','p','c');
28-
#endif
29-
3023
int main(int argc, char * argv[])
3124
{
3225
yarp::os::Network yarp;
@@ -69,20 +62,22 @@ int main(int argc, char * argv[])
6962
return 1;
7063
}
7164

72-
yarp::os::Bottle cmd {yarp::os::Value(VOCAB_GET_POINTS, true)};
73-
yarp::sig::PointCloudXYZ cloud;
65+
roboticslab::SceneReconstructionIDL sceneReconstruction;
66+
sceneReconstruction.yarp().attachAsClient(rpc);
67+
68+
auto result = sceneReconstruction.getPointsWithNormals();
7469

75-
if (!rpc.write(cmd, cloud))
70+
if (!result.ret)
7671
{
7772
yError() << "Unable to send remote command";
7873
return 1;
7974
}
8075

81-
yInfo() << "Got cloud of" << cloud.size() << "points";
76+
yInfo() << "Got cloud of" << result.pointsWithNormals.size() << "points";
8277

8378
if (!fileCloud.empty())
8479
{
85-
if (!roboticslab::YarpCloudUtils::savePLY(fileCloud, cloud, binary))
80+
if (!roboticslab::YarpCloudUtils::savePLY(fileCloud, result.pointsWithNormals, binary))
8681
{
8782
yWarning() << "Unable to export cloud to" << fileCloud;
8883
}
@@ -94,12 +89,12 @@ int main(int argc, char * argv[])
9489

9590
if (!fileMesh.empty())
9691
{
97-
yarp::sig::PointCloudXYZ meshPoints;
92+
yarp::sig::PointCloudXYZRGBA meshPoints;
9893
yarp::sig::VectorOf<int> meshIndices;
9994

10095
auto start = yarp::os::SystemClock::nowSystem();
10196

102-
if (!roboticslab::YarpCloudUtils::meshFromCloud(cloud, meshPoints, meshIndices, options, collection))
97+
if (!roboticslab::YarpCloudUtils::meshFromCloud(result.pointsWithNormals, meshPoints, meshIndices, options, collection))
10398
{
10499
yWarning() << "Unable to reconstruct surface from cloud";
105100
}

libraries/CMakeLists.txt

+1-3
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,5 @@
1-
# Copyright: Universidad Carlos III de Madrid (C) 2013
2-
# Authors: Juan G. Victores
3-
41
add_subdirectory(TravisLib)
2+
add_subdirectory(VisionIDL)
53
add_subdirectory(YarpCloudUtils)
64
add_subdirectory(YarpCropCallback)
75
add_subdirectory(YarpPlugins)

libraries/VisionIDL/CMakeLists.txt

+46
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
if(NOT YARP_idl_tools_FOUND AND (NOT DEFINED ENABLE_VisionIDL OR ENABLE_VisionIDL))
2+
message(WARNING "YARP idl_tools component not found, disabling VisionIDL library")
3+
endif()
4+
5+
cmake_dependent_option(ENABLE_VisionIDL "Enable/disable VisionIDL library" ON
6+
YARP_idl_tools_FOUND OFF)
7+
8+
if(ENABLE_VisionIDL)
9+
10+
set(ALLOW_IDL_GENERATION ON CACHE BOOL "Detect changes and rebuild IDL files")
11+
set_property(DIRECTORY APPEND PROPERTY CMAKE_CONFIGURE_DEPENDS vision.thrift)
12+
13+
yarp_idl_to_dir(INPUT_FILES vision.thrift
14+
OUTPUT_DIR ${CMAKE_CURRENT_BINARY_DIR}
15+
SOURCES_VAR idl_sources
16+
HEADERS_VAR idl_headers
17+
INCLUDE_DIRS_VAR idl_include_dirs
18+
PLACEMENT MERGED
19+
THRIFT_NO_NAMESPACE_PREFIX)
20+
21+
add_library(VisionIDL SHARED ${idl_sources} ${idl_headers})
22+
23+
set_target_properties(VisionIDL PROPERTIES PUBLIC_HEADER "${idl_headers}")
24+
25+
target_link_libraries(VisionIDL PUBLIC YARP::YARP_os
26+
YARP::YARP_sig)
27+
28+
target_include_directories(VisionIDL PUBLIC $<BUILD_INTERFACE:${idl_include_dirs}>
29+
$<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}>)
30+
31+
install(TARGETS VisionIDL
32+
EXPORT ROBOTICSLAB_SPEECH
33+
LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
34+
ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR}
35+
RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
36+
PUBLIC_HEADER DESTINATION ${CMAKE_INSTALL_INCLUDEDIR})
37+
38+
set_property(GLOBAL APPEND PROPERTY _exported_targets VisionIDL)
39+
40+
add_library(ROBOTICSLAB::VisionIDL ALIAS VisionIDL)
41+
42+
else()
43+
44+
set(ENABLE_VisionIDL OFF CACHE BOOL "Enable/disable VisionIDL library" FORCE)
45+
46+
endif()

libraries/VisionIDL/vision.thrift

+65
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,65 @@
1+
namespace yarp roboticslab
2+
3+
struct yarp_sig_Matrix {
4+
} (
5+
yarp.name = "yarp::sig::Matrix"
6+
yarp.includefile = "yarp/sig/Matrix.h"
7+
)
8+
9+
struct yarp_sig_PointCloudXYZ {
10+
} (
11+
yarp.name = "yarp::sig::PointCloudXYZ"
12+
yarp.includefile = "yarp/sig/PointCloud.h"
13+
)
14+
15+
struct yarp_sig_PointCloudXYZNormalRGBA {
16+
} (
17+
yarp.name = "yarp::sig::PointCloudXYZNormalRGBA"
18+
yarp.includefile = "yarp/sig/PointCloud.h"
19+
)
20+
21+
struct return_pose {
22+
1: bool ret = false;
23+
2: yarp_sig_Matrix pose;
24+
}
25+
26+
struct return_points {
27+
1: bool ret = false;
28+
2: yarp_sig_PointCloudXYZ points;
29+
}
30+
31+
struct return_points_with_normals {
32+
1: bool ret = false;
33+
2: yarp_sig_PointCloudXYZNormalRGBA pointsWithNormals;
34+
}
35+
36+
service SceneReconstructionIDL
37+
{
38+
/**
39+
* pause the scene reconstruction process
40+
*/
41+
void pause();
42+
43+
/**
44+
* start/resume the scene reconstruction process
45+
*/
46+
void resume();
47+
48+
/**
49+
* get current camera pose
50+
* @return struct {bool ret, yarp_sig_Matrix pose}
51+
*/
52+
return_pose getPose();
53+
54+
/**
55+
* get the resulting point cloud
56+
* @return struct {bool ret, yarp_sig_PointCloudXYZ points}
57+
*/
58+
return_points getPoints();
59+
60+
/**
61+
* get the resulting point cloud with normals and color data (if available)
62+
* @return struct {bool ret, yarp_sig_PointCloudXYZNormalRGBA pointsWithNormals}
63+
*/
64+
return_points_with_normals getPointsWithNormals();
65+
}

programs/sceneReconstruction/CMakeLists.txt

+4-3
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ if(NOT DEFINED ENABLE_sceneReconstruction OR ENABLE_sceneReconstruction)
1212
endif()
1313

1414
cmake_dependent_option(ENABLE_sceneReconstruction "Enable/disable sceneReconstruction program" ON
15-
"TARGET opencv_rgbd;OpenCV_VERSION VERSION_GREATER_EQUAL 4.0;_opencv_nonfree;YARP_cv_FOUND" OFF)
15+
"TARGET opencv_rgbd;OpenCV_VERSION VERSION_GREATER_EQUAL 4.0;_opencv_nonfree;YARP_cv_FOUND;ENABLE_VisionIDL" OFF)
1616

1717
if(ENABLE_sceneReconstruction)
1818

@@ -31,7 +31,8 @@ if(ENABLE_sceneReconstruction)
3131
YARP::YARP_dev
3232
YARP::YARP_sig
3333
YARP::YARP_cv
34-
opencv_rgbd)
34+
opencv_rgbd
35+
ROBOTICSLAB::VisionIDL)
3536

3637
if(OpenCV_VERSION VERSION_GREATER_EQUAL 4.2)
3738
target_sources(sceneReconstruction PRIVATE DynaFu.cpp)
@@ -43,7 +44,7 @@ if(ENABLE_sceneReconstruction)
4344
target_compile_definitions(sceneReconstruction PRIVATE HAVE_KINFU_LS)
4445
endif()
4546

46-
if(OpenCV_VERSION VERSION_GREATER_EQUAL 4.5.3)
47+
if(OpenCV_VERSION VERSION_GREATER_EQUAL 4.5.5)
4748
target_sources(sceneReconstruction PRIVATE ColoredKinFu.cpp)
4849
target_compile_definitions(sceneReconstruction PRIVATE HAVE_COLORED_KINFU)
4950
endif()

programs/sceneReconstruction/ColoredKinFu.cpp

+44-16
Original file line numberDiff line numberDiff line change
@@ -10,21 +10,49 @@
1010

1111
using namespace roboticslab;
1212

13+
template <>
14+
void KinectFusionImpl<cv::colored_kinfu::ColoredKinFu>::getCloud(yarp::sig::PointCloudXYZNormalRGBA & cloudWithNormals) const
15+
{
16+
cv::Mat points, normals, colors;
17+
18+
mtx.lock();
19+
handle->getCloud(points, normals, colors);
20+
mtx.unlock();
21+
22+
cloudWithNormals.resize(points.rows);
23+
24+
for (auto i = 0; i < points.rows; i++)
25+
{
26+
using color_t = unsigned char;
27+
const auto & point = points.at<cv::Vec4f>(i);
28+
const auto & normal = normals.at<cv::Vec4f>(i);
29+
const auto & color = colors.at<cv::Vec4f>(i);
30+
31+
cloudWithNormals(i) = {
32+
{point[0], point[1], point[2]},
33+
{normal[0], normal[1], normal[2]},
34+
{static_cast<color_t>(color[0]), static_cast<color_t>(color[1]), static_cast<color_t>(color[2]), static_cast<color_t>(color[3])}
35+
};
36+
}
37+
}
38+
1339
template <>
1440
bool KinectFusionImpl<cv::colored_kinfu::ColoredKinFu>::update(const yarp::sig::ImageOf<yarp::sig::PixelFloat> & depthFrame,
15-
const yarp::sig::FlexImage & rgbFrame)
41+
const yarp::sig::FlexImage & colorFrame)
1642
{
1743
// Cast away constness so that toCvMat accepts the YARP image. This function
1844
// does not alter the inner structure of PixelFloat images anyway.
1945
auto & nonConstDepthFrame = const_cast<yarp::sig::ImageOf<yarp::sig::PixelFloat> &>(depthFrame);
2046
cv::Mat depthMat = yarp::cv::toCvMat(nonConstDepthFrame);
2147

2248
yarp::sig::ImageOf<yarp::sig::PixelBgr> bgrFrame;
23-
bgrFrame.copy(rgbFrame);
49+
bgrFrame.copy(colorFrame); // convert to BGR (probably from RGB)
2450
cv::Mat bgrMat = yarp::cv::toCvMat(bgrFrame);
2551

2652
cv::UMat depthUmat;
2753
depthMat.convertTo(depthUmat, depthMat.type(), 1000.0); // OpenCV uses milimeters
54+
55+
std::lock_guard<std::mutex> lock(mtx);
2856
return handle->update(depthUmat, bgrMat);
2957
}
3058

@@ -42,9 +70,9 @@ namespace roboticslab
4270

4371
std::unique_ptr<KinectFusion> makeColoredKinFu(const yarp::os::Searchable & config,
4472
const yarp::sig::IntrinsicParams & depthIntrinsic,
45-
const yarp::sig::IntrinsicParams & rgbIntrinsic,
73+
const yarp::sig::IntrinsicParams & colorIntrinsic,
4674
int depthWidth, int depthHeight,
47-
int rgbWidth, int rgbHeight)
75+
int colorWidth, int colorHeight)
4876
{
4977
using Params = cv::colored_kinfu::Params;
5078

@@ -65,20 +93,20 @@ std::unique_ptr<KinectFusion> makeColoredKinFu(const yarp::os::Searchable & conf
6593
yCInfo(KINFU) << "principal point (X):" << depthIntrinsic.principalPointX;
6694
yCInfo(KINFU) << "principal point (Y):" << depthIntrinsic.principalPointY;
6795

68-
yCInfo(KINFU) << "--- CAMERA PARAMETERS (RGB) ---";
96+
yCInfo(KINFU) << "--- CAMERA PARAMETERS (color) ---";
6997

70-
params->rgb_frameSize = cv::Size(rgbWidth, rgbHeight);
71-
yCInfo(KINFU) << "width:" << rgbWidth;
72-
yCInfo(KINFU) << "height:" << rgbHeight;
98+
params->rgb_frameSize = cv::Size(colorWidth, colorHeight);
99+
yCInfo(KINFU) << "width:" << colorWidth;
100+
yCInfo(KINFU) << "height:" << colorHeight;
73101

74-
params->rgb_intr = cv::Matx33f(rgbIntrinsic.focalLengthX, 0, rgbIntrinsic.principalPointX,
75-
0, rgbIntrinsic.focalLengthY, rgbIntrinsic.principalPointY,
76-
0, 0, 1);
102+
params->rgb_intr = cv::Matx33f(colorIntrinsic.focalLengthX, 0, colorIntrinsic.principalPointX,
103+
0, colorIntrinsic.focalLengthY, colorIntrinsic.principalPointY,
104+
0, 0, 1);
77105

78-
yCInfo(KINFU) << "focal length (X):" << rgbIntrinsic.focalLengthX;
79-
yCInfo(KINFU) << "focal length (Y):" << rgbIntrinsic.focalLengthY;
80-
yCInfo(KINFU) << "principal point (X):" << rgbIntrinsic.principalPointX;
81-
yCInfo(KINFU) << "principal point (Y):" << rgbIntrinsic.principalPointY;
106+
yCInfo(KINFU) << "focal length (X):" << colorIntrinsic.focalLengthX;
107+
yCInfo(KINFU) << "focal length (Y):" << colorIntrinsic.focalLengthY;
108+
yCInfo(KINFU) << "principal point (X):" << colorIntrinsic.principalPointX;
109+
yCInfo(KINFU) << "principal point (Y):" << colorIntrinsic.principalPointY;
82110

83111
yCInfo(KINFU) << "--- ALGORITHM PARAMETERS ---";
84112

@@ -203,7 +231,7 @@ std::unique_ptr<KinectFusion> makeColoredKinFu(const yarp::os::Searchable & conf
203231
yCInfo(KINFU) << "volumePoseTransl (DEFAULT):" << transl[0] << transl[1] << transl[2];
204232
}
205233

206-
if (config.check("volumeType", "type of voxel volume (tsdf, hashtsdf)"))
234+
if (config.check("volumeType", "type of voxel volume (tsdf, hashtsdf, coloredtsdf)"))
207235
{
208236
std::string volumeType = config.find("volumeType").asString();
209237

0 commit comments

Comments
 (0)