PointCloudToArViz.cpp
Go to the documentation of this file.
1 /*
2  * This file is part of ArmarX.
3  *
4  * ArmarX is free software; you can redistribute it and/or modify
5  * it under the terms of the GNU General Public License version 2 as
6  * published by the Free Software Foundation.
7  *
8  * ArmarX is distributed in the hope that it will be useful, but
9  * WITHOUT ANY WARRANTY; without even the implied warranty of
10  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11  * GNU General Public License for more details.
12  *
13  * You should have received a copy of the GNU General Public License
14  * along with this program. If not, see <http://www.gnu.org/licenses/>.
15  *
16  * @package VisionX::ArmarXObjects::PointCloudToArViz
17  * @author Rainer Kartmann ( rainer dot kartmann at kit dot edu )
18  * @date 2020
19  * @copyright http://www.gnu.org/licenses/gpl-2.0.txt
20  * GNU General Public License
21  */
22 
23 #include "PointCloudToArViz.h"
24 
25 #include <pcl/impl/point_types.hpp>
26 #include <pcl/point_types.h>
27 #include <pcl/common/transforms.h>
31 
35 
36 
37 namespace visionx
38 {
39 
42  {
43  defineOptionalProperty<int>("ProviderWaitMs", 100,
44  "Time to wait for each point cloud provider [ms].");
45  }
46 
48  {
50 
51  defs->optional(params.pointSizeInPixels, "viz.pointSizeInPixels", "The point size in pixels.");
52  defs->optional(params.checkFinite, "viz.checkFinite",
53  "Enable to check points for being finite. "
54  "\nEnable this option if the drawn point cloud causes the screen to become purely white.");
55  defs->optional(params.labeled, "viz.labeled",
56  "If true and point cloud is labeled, draw colors according to labels.");
57 
58  defs->optional(params.robotName, "robotName", "");
59  defs->optional(params.pointCloudNodeName, "pointCloudNodeName", " If the point cloud header does not provide a frame id, this info is used.");
60 
61  return defs;
62  }
63 
65  {
66  addPlugin(virtualRobotReaderPlugin);
67  }
68 
69 
71  {
72  return "PointCloudToArViz";
73  }
74 
75 
77  {
78  params.providerWaitTime = IceUtil::Time::milliSeconds(getProperty<int>("ProviderWaitMs").getValue());
79  }
80 
81 
83  {
84  if(virtualRobotReaderPlugin->isAvailable())
85  {
86  robot = virtualRobotReaderPlugin->get().getSynchronizedRobot(params.robotName, armarx::Clock::Now());
87  }
88 
91  }
92 
93 
95  {
96  }
97 
99  {
100  }
101 
102 
104  {
105  // Fetch input clouds.
106  for (const std::string& providerName : getPointCloudProviderNames())
107  {
108  if (waitForPointClouds(providerName, static_cast<int>(params.providerWaitTime.toMilliSeconds())))
109  {
110  auto it = cache.find(providerName);
111  if (it == cache.end())
112  {
113  it = cache.emplace(providerName, armarx::viz::PointCloud(providerName)).first;
114  }
115  armarx::viz::PointCloud& vizCloud = it->second;
116 
117  Parameters params;
118  {
119  std::scoped_lock lock(paramMutex);
120  params = this->params;
121  }
122 
123  vizCloud.checkFinite(params.checkFinite);
124  vizCloud.pointSizeInPixels(params.pointSizeInPixels);
125 
126  const PointContentType type = getPointCloudFormat(providerName)->type;
127  if (visionx::tools::isLabeled(type))
128  {
129  pcl::PointCloud<pcl::PointXYZRGBL>::Ptr inputCloud(new pcl::PointCloud<pcl::PointXYZRGBL>);
130  getPointClouds(providerName, inputCloud);
131  applyCustomTransform(*inputCloud);
132  vizCloud.pointCloud(*inputCloud, params.labeled);
133  }
134  else
135  {
136  pcl::PointCloud<pcl::PointXYZRGBA>::Ptr inputCloud(new pcl::PointCloud<pcl::PointXYZRGBA>);
137  getPointClouds(providerName, inputCloud);
138  applyCustomTransform(*inputCloud);
139  vizCloud.pointCloud(*inputCloud);
140  }
141 
142  armarx::viz::Layer layer = arviz.layer(providerName);
143  layer.add(vizCloud);
144  arviz.commit({layer});
145  }
146  else
147  {
148  ARMARX_VERBOSE << "Timeout waiting for point cloud provider " << providerName << ".";
149  }
150  }
151  }
152 
153  void PointCloudToArViz::setPointSizeInPixels(float pointSizeInPixels, const Ice::Current&)
154  {
155  std::scoped_lock lock(paramMutex);
156  params.pointSizeInPixels = pointSizeInPixels;
157  }
158 
159  void PointCloudToArViz::setCustomTransform(const armarx::PoseBasePtr& transformPtr, const Ice::Current&)
160  {
161  return;
162 
163  // std::scoped_lock lock(paramMutex);
164  // params.customTransform = armarx::PosePtr::dynamicCast(transformPtr)->toEigen();
165  // if (params.customTransform->isIdentity())
166  // {
167  // params.customTransform = std::nullopt;
168  // }
169  }
170 
171  template<class PointT>
172  void PointCloudToArViz::applyCustomTransform(pcl::PointCloud<PointT>& pointCloud)
173  {
174  ARMARX_CHECK_NOT_NULL(virtualRobotReaderPlugin);
175  if(not virtualRobotReaderPlugin->isAvailable())
176  {
177  ARMARX_INFO << deactivateSpam(100) << "The robot reader plugin is deactivated. Won't transform point cloud";
178  return;
179  }
180 
181  ARMARX_CHECK_NOT_NULL(robot);
182  ARMARX_CHECK(virtualRobotReaderPlugin->get().synchronizeRobot(*robot, armarx::core::time::Duration::MicroSeconds(pointCloud.header.stamp)));
183 
184  const auto pointCloudNodeName = [&]() -> std::string {
185 
186  // highest prio: use frame id of point cloud.
187  if(not pointCloud.header.frame_id.empty())
188  {
189  return pointCloud.header.frame_id;
190  }
191 
192  // check if fallback solution is available
193  ARMARX_INFO << deactivateSpam(100)
194  << "The point cloud header does not provide a frame_id. Using property instead";
195 
196  ARMARX_CHECK_NOT_EMPTY(params.pointCloudNodeName)
197  << "The `pointCloudNodeName` property must be provided as the point cloud header frame id is not set!";
198 
199  return params.pointCloudNodeName;
200  }();
201 
202  if(not robot)
203  {
204  ARMARX_INFO << deactivateSpam(100) << "The robot is not available. Won't transform point cloud";
205  return;
206  }
207 
208  ARMARX_CHECK_NOT_NULL(robot);
209  const auto node = robot->getRobotNode(pointCloudNodeName);
210  ARMARX_CHECK_NOT_NULL(node) << "No robot node with name `" << pointCloudNodeName << "`";
211 
212  const auto globalSensorPose = node->getGlobalPose();
213 
214  pcl::transformPointCloud(pointCloud, pointCloud, globalSensorPose);
215  pointCloud.header.frame_id = armarx::GlobalFrame;
216  }
217 
218 
220  {
221  using namespace armarx::RemoteGui::Client;
222 
223  GridLayout grid;
224  int row = 0;
225 
226  tab.checkFinite.setName("Check Finite");
227  tab.checkFinite.setValue(params.checkFinite);
228 
229  tab.pointSizeInPixels.setName("Point Size [pixels]");
230  tab.pointSizeInPixels.setDecimals(2);
231  tab.pointSizeInPixels.setRange(0, 100);
232  tab.pointSizeInPixels.setSteps(100);
233  tab.pointSizeInPixels.setValue(params.pointSizeInPixels);
234 
235  tab.labeled.setName("Color by Labels");
236  tab.labeled.setValue(params.labeled);
237 
238  grid.add(Label(tab.checkFinite.getName()), {row, 0}).add(tab.checkFinite, {row, 1});
239  row++;
240  grid.add(Label(tab.pointSizeInPixels.getName()), {row, 0}).add(tab.pointSizeInPixels, {row, 1});
241  row++;
242  grid.add(Label(tab.labeled.getName()), {row, 0}).add(tab.labeled, {row, 1});
243  row++;
244 
245  VBoxLayout root = {grid, VSpacer()};
246  RemoteGui_createTab(getName(), root, &tab);
247  }
248 
250  {
251  std::scoped_lock lock(paramMutex);
252  if (tab.checkFinite.hasValueChanged())
253  {
254  params.checkFinite = tab.checkFinite.getValue();
255  }
256  if (tab.pointSizeInPixels.hasValueChanged())
257  {
258  params.pointSizeInPixels = tab.pointSizeInPixels.getValue();
259  }
260  if (tab.labeled.hasValueChanged())
261  {
262  params.labeled = tab.labeled.getValue();
263  }
264  }
265 
266 
267 }
armarx::armem::client::plugins::ReaderWriterPlugin::isAvailable
bool isAvailable() const
Definition: ReaderWriterPlugin.h:81
PointCloudToArViz.h
armarx::viz::Client::commit
CommitResult commit(StagedCommit const &commit)
Definition: Client.cpp:71
ARMARX_VERBOSE
#define ARMARX_VERBOSE
Definition: Logging.h:180
visionx::PointCloudToArViz::createPropertyDefinitions
armarx::PropertyDefinitionsPtr createPropertyDefinitions() override
Definition: PointCloudToArViz.cpp:47
visionx::PointCloudToArViz::setPointSizeInPixels
virtual void setPointSizeInPixels(float pointSizeInPixels, const Ice::Current &=Ice::emptyCurrent) override
Definition: PointCloudToArViz.cpp:153
visionx::PointCloudProcessor::getPointCloudFormat
MetaPointCloudFormatPtr getPointCloudFormat(std::string providerName)
Definition: PointCloudProcessor.cpp:506
visionx
ArmarX headers.
Definition: OpenPoseStressTest.h:38
visionx::PointCloudToArViz::process
void process() override
Definition: PointCloudToArViz.cpp:103
visionx::PointCloudToArVizPropertyDefinitions
Property definitions of PointCloudToArViz.
Definition: PointCloudToArViz.h:56
armarx::RemoteGui::Client::VBoxLayout
Definition: Widgets.h:167
Pose.h
ARMARX_CHECK_NOT_NULL
#define ARMARX_CHECK_NOT_NULL(ptr)
This macro evaluates whether ptr is not null and if it turns out to be false it will throw an Express...
Definition: ExpressionException.h:204
armarx::RemoteGui::Client::GridLayout::add
GridLayout & add(Widget const &child, Pos pos, Span span=Span{1, 1})
Definition: Widgets.cpp:412
armarx::GlobalFrame
const std::string GlobalFrame
Definition: FramedPose.h:62
armarx::RemoteGui::Client::Widget::setName
void setName(std::string const &name)
Definition: Widgets.cpp:19
visionx::tools::isLabeled
bool isLabeled(PointContentType type)
Definition: PointCloudConversions.cpp:108
ARMARX_CHECK_NOT_EMPTY
#define ARMARX_CHECK_NOT_EMPTY(c)
Definition: ExpressionException.h:222
armarx::ManagedIceObject::addPlugin
PluginT * addPlugin(const std::string prefix="", ParamsT &&...params)
Definition: ManagedIceObject.h:184
visionx::PointCloudToArVizPropertyDefinitions::PointCloudToArVizPropertyDefinitions
PointCloudToArVizPropertyDefinitions(std::string prefix)
Definition: PointCloudToArViz.cpp:40
armarx::viz::Layer::add
void add(ElementT const &element)
Definition: Layer.h:29
armarx::RemoteGui::Client::VSpacer
Definition: Widgets.h:204
ARMARX_CHECK
#define ARMARX_CHECK(expression)
Shortcut for ARMARX_CHECK_EXPRESSION.
Definition: ExpressionException.h:80
Clock.h
visionx::voxelgrid::Label
uint32_t Label
Type of an object label.
Definition: types.h:7
armarx::RemoteGui::Client::GridLayout
Definition: Widgets.h:186
visionx::PointCloudToArViz::PointCloudToArViz
PointCloudToArViz()
Definition: PointCloudToArViz.cpp:64
FramedPose.h
armarx::viz::PointCloud::pointSizeInPixels
PointCloud & pointSizeInPixels(float s)
Definition: PointCloud.h:55
visionx::PointCloudToArViz::RemoteGui_update
void RemoteGui_update() override
Definition: PointCloudToArViz.cpp:249
visionx::PointCloudProcessor::waitForPointClouds
bool waitForPointClouds(int milliseconds=1000)
Wait for new PointClouds.
Definition: PointCloudProcessor.cpp:433
armarx::viz::PointCloud
Definition: PointCloud.h:21
VirtualRobotReader.h
visionx::PointCloudToArViz::getDefaultName
std::string getDefaultName() const override
Definition: PointCloudToArViz.cpp:70
visionx::PointCloudToArViz::onDisconnectPointCloudProcessor
void onDisconnectPointCloudProcessor() override
Definition: PointCloudToArViz.cpp:94
visionx::PointCloudProcessorPropertyDefinitions
Properties of PointCloudProcessor.
Definition: PointCloudProcessor.h:173
armarx::armem::robot_state::VirtualRobotReader::getSynchronizedRobot
VirtualRobot::RobotPtr getSynchronizedRobot(const std::string &name, const VirtualRobot::RobotIO::RobotDescription &loadMode=VirtualRobot::RobotIO::RobotDescription::eStructure, bool blocking=true)
visionx::PointCloudProcessor::getPointClouds
int getPointClouds(const PointCloudPtrT &pointCloudPtr)
Poll PointClouds from provider.
Definition: PointCloudProcessor.h:373
visionx::PointCloudToArViz::onInitPointCloudProcessor
void onInitPointCloudProcessor() override
Definition: PointCloudToArViz.cpp:76
armarx::armem::client::plugins::ReaderWriterPlugin::get
T & get()
Definition: ReaderWriterPlugin.h:88
armarx::LightweightRemoteGuiComponentPluginUser::RemoteGui_startRunningTask
void RemoteGui_startRunningTask()
Definition: LightweightRemoteGuiComponentPlugin.cpp:110
ExpressionException.h
armarx::Component::getConfigIdentifier
std::string getConfigIdentifier()
Retrieve config identifier for this component as set in constructor.
Definition: Component.cpp:70
ARMARX_INFO
#define ARMARX_INFO
Definition: Logging.h:174
armarx::ArVizComponentPluginUser::arviz
armarx::viz::Client arviz
Definition: ArVizComponentPlugin.h:43
visionx::PointCloudToArViz::createRemoteGuiTab
void createRemoteGuiTab()
Definition: PointCloudToArViz.cpp:219
armarx::LightweightRemoteGuiComponentPluginUser::RemoteGui_createTab
void RemoteGui_createTab(std::string const &name, RemoteGui::Client::Widget const &rootWidget, RemoteGui::Client::Tab *tab)
Definition: LightweightRemoteGuiComponentPlugin.cpp:95
IceUtil::Handle< class PropertyDefinitionContainer >
armarx::core::time::Clock::Now
static DateTime Now()
Current time on the virtual clock.
Definition: Clock.cpp:97
armarx::Logging::deactivateSpam
SpamFilterDataPtr deactivateSpam(float deactivationDurationSec=10.0f, const std::string &identifier="", bool deactivate=true) const
disables the logging for the current line for the given amount of seconds.
Definition: Logging.cpp:92
armarx::ManagedIceObject::getName
std::string getName() const
Retrieve name of object.
Definition: ManagedIceObject.cpp:107
armarx::armem::robot_state::VirtualRobotReader::synchronizeRobot
bool synchronizeRobot(VirtualRobot::Robot &robot, const armem::Time &timestamp)
Definition: VirtualRobotReader.cpp:39
visionx::PointCloudToArViz::onConnectPointCloudProcessor
void onConnectPointCloudProcessor() override
Definition: PointCloudToArViz.cpp:82
Logging.h
armarx::viz::Client::layer
Layer layer(std::string const &name) const
Definition: Client.h:133
visionx::PointCloudToArViz::onExitPointCloudProcessor
void onExitPointCloudProcessor() override
Definition: PointCloudToArViz.cpp:98
armarx::core::time::Duration::MicroSeconds
static Duration MicroSeconds(std::int64_t microSeconds)
Constructs a duration in microseconds.
Definition: Duration.cpp:27
armarx::RemoteGui::Client
Definition: EigenWidgets.cpp:8
armarx::viz::PointCloud::pointCloud
PointCloud & pointCloud(const PointCloudT &cloud)
Draw a point cloud.
Definition: PointCloud.h:194
armarx::viz::Layer
Definition: Layer.h:12
armarx::viz::PointCloud::checkFinite
PointCloud & checkFinite(bool enabled=true)
Enable or disable checking whether points are finite when adding them (disabled by default).
Definition: PointCloud.h:41
visionx::PointCloudProcessor::getPointCloudProviderNames
std::vector< std::string > getPointCloudProviderNames() const
Get the names of providers for which usingPointCloudProvider() has been called.
Definition: PointCloudProcessor.cpp:381
visionx::PointCloudToArViz::setCustomTransform
virtual void setCustomTransform(const armarx::PoseBasePtr &transform, const Ice::Current &=Ice::emptyCurrent) override
Definition: PointCloudToArViz.cpp:159