Point Cloud Library (PCL)  1.11.1-dev
color_coding.h
1 /*
2  * Software License Agreement (BSD License)
3  *
4  * Point Cloud Library (PCL) - www.pointclouds.org
5  * Copyright (c) 2010-2012, Willow Garage, Inc.
6  *
7  * All rights reserved.
8  *
9  * Redistribution and use in source and binary forms, with or without
10  * modification, are permitted provided that the following conditions
11  * are met:
12  *
13  * * Redistributions of source code must retain the above copyright
14  * notice, this list of conditions and the following disclaimer.
15  * * Redistributions in binary form must reproduce the above
16  * copyright notice, this list of conditions and the following
17  * disclaimer in the documentation and/or other materials provided
18  * with the distribution.
19  * * Neither the name of Willow Garage, Inc. nor the names of its
20  * contributors may be used to endorse or promote products derived
21  * from this software without specific prior written permission.
22  *
23  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
24  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
25  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
26  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
27  * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
28  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
29  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
30  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
31  * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
32  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
33  * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
34  * POSSIBILITY OF SUCH DAMAGE.
35  *
36  */
37 
38 #pragma once
39 
40 #include <iostream>
41 #include <vector>
42 
43 namespace pcl
44 {
45 
46 namespace octree
47 {
48 
49 /** \brief @b ColorCoding class
50  * \note This class encodes 8-bit color information for octree-based point cloud compression.
51  * \note
52  * \note typename: PointT: type of point used in pointcloud
53  * \author Julius Kammerl (julius@kammerl.de)
54  */
55 template<typename PointT>
57 {
58  // public typedefs
60  using PointCloudPtr = typename PointCloud::Ptr;
61  using PointCloudConstPtr = typename PointCloud::ConstPtr;
62 
63 public:
64  /** \brief Constructor.
65  *
66  * */
69  {
70  }
71 
72  /** \brief Empty class constructor. */
73  virtual
75  {
76  }
77 
78  /** \brief Define color bit depth of encoded color information.
79  * \param bitDepth_arg: amounts of bits for representing one color component
80  */
81  inline
82  void
83  setBitDepth (unsigned char bitDepth_arg)
84  {
85  colorBitReduction_ = static_cast<unsigned char> (8 - bitDepth_arg);
86  }
87 
88  /** \brief Retrieve color bit depth of encoded color information.
89  * \return amounts of bits for representing one color component
90  */
91  inline unsigned char
93  {
94  return (static_cast<unsigned char> (8 - colorBitReduction_));
95  }
96 
97  /** \brief Set amount of voxels containing point color information and reserve memory
98  * \param voxelCount_arg: amounts of voxels
99  */
100  inline void
101  setVoxelCount (unsigned int voxelCount_arg)
102  {
103  pointAvgColorDataVector_.reserve (voxelCount_arg * 3);
104  }
105 
106  /** \brief Set amount of points within point cloud to be encoded and reserve memory
107  * \param pointCount_arg: amounts of points within point cloud
108  * */
109  inline
110  void
111  setPointCount (unsigned int pointCount_arg)
112  {
113  pointDiffColorDataVector_.reserve (pointCount_arg * 3);
114  }
115 
116  /** \brief Initialize encoding of color information
117  * */
118  void
120  {
121  pointAvgColorDataVector_.clear ();
122 
123  pointDiffColorDataVector_.clear ();
124  }
125 
126  /** \brief Initialize decoding of color information
127  * */
128  void
130  {
132 
134  }
135 
136  /** \brief Get reference to vector containing averaged color data
137  * */
138  std::vector<char>&
140  {
142  }
143 
144  /** \brief Get reference to vector containing differential color data
145  * */
146  std::vector<char>&
148  {
150  }
151 
152  /** \brief Encode averaged color information for a subset of points from point cloud
153  * \param indexVector_arg indices defining a subset of points from points cloud
154  * \param rgba_offset_arg offset to color information
155  * \param inputCloud_arg input point cloud
156  * */
157  void
158  encodeAverageOfPoints (const typename std::vector<int>& indexVector_arg, unsigned char rgba_offset_arg, PointCloudConstPtr inputCloud_arg)
159  {
160  unsigned int avgRed = 0;
161  unsigned int avgGreen = 0;
162  unsigned int avgBlue = 0;
163 
164  // iterate over points
165  std::size_t len = indexVector_arg.size ();
166  for (std::size_t i = 0; i < len; i++)
167  {
168  // get color information from points
169  const int& idx = indexVector_arg[i];
170  const char* idxPointPtr = reinterpret_cast<const char*> (&(*inputCloud_arg)[idx]);
171  const int& colorInt = *reinterpret_cast<const int*> (idxPointPtr+rgba_offset_arg);
172 
173  // add color information
174  avgRed += (colorInt >> 0) & 0xFF;
175  avgGreen += (colorInt >> 8) & 0xFF;
176  avgBlue += (colorInt >> 16) & 0xFF;
177 
178  }
179 
180  // calculated average color information
181  if (len > 1)
182  {
183  avgRed /= static_cast<unsigned int> (len);
184  avgGreen /= static_cast<unsigned int> (len);
185  avgBlue /= static_cast<unsigned int> (len);
186  }
187 
188  // remove least significant bits
189  avgRed >>= colorBitReduction_;
190  avgGreen >>= colorBitReduction_;
191  avgBlue >>= colorBitReduction_;
192 
193  // add to average color vector
194  pointAvgColorDataVector_.push_back (static_cast<char> (avgRed));
195  pointAvgColorDataVector_.push_back (static_cast<char> (avgGreen));
196  pointAvgColorDataVector_.push_back (static_cast<char> (avgBlue));
197  }
198 
199  /** \brief Encode color information of a subset of points from point cloud
200  * \param indexVector_arg indices defining a subset of points from points cloud
201  * \param rgba_offset_arg offset to color information
202  * \param inputCloud_arg input point cloud
203  * */
204  void
205  encodePoints (const typename std::vector<int>& indexVector_arg, unsigned char rgba_offset_arg, PointCloudConstPtr inputCloud_arg)
206  {
207  unsigned int avgRed;
208  unsigned int avgGreen;
209  unsigned int avgBlue;
210 
211  // initialize
212  avgRed = avgGreen = avgBlue = 0;
213 
214  // iterate over points
215  std::size_t len = indexVector_arg.size ();
216  for (std::size_t i = 0; i < len; i++)
217  {
218  // get color information from point
219  const int& idx = indexVector_arg[i];
220  const char* idxPointPtr = reinterpret_cast<const char*> (&(*inputCloud_arg)[idx]);
221  const int& colorInt = *reinterpret_cast<const int*> (idxPointPtr+rgba_offset_arg);
222 
223  // add color information
224  avgRed += (colorInt >> 0) & 0xFF;
225  avgGreen += (colorInt >> 8) & 0xFF;
226  avgBlue += (colorInt >> 16) & 0xFF;
227 
228  }
229 
230  if (len > 1)
231  {
232  unsigned char diffRed;
233  unsigned char diffGreen;
234  unsigned char diffBlue;
235 
236  // calculated average color information
237  avgRed /= static_cast<unsigned int> (len);
238  avgGreen /= static_cast<unsigned int> (len);
239  avgBlue /= static_cast<unsigned int> (len);
240 
241  // iterate over points for differential encoding
242  for (std::size_t i = 0; i < len; i++)
243  {
244  const int& idx = indexVector_arg[i];
245  const char* idxPointPtr = reinterpret_cast<const char*> (&(*inputCloud_arg)[idx]);
246  const int& colorInt = *reinterpret_cast<const int*> (idxPointPtr+rgba_offset_arg);
247 
248  // extract color components and do XOR encoding with predicted average color
249  diffRed = (static_cast<unsigned char> (avgRed)) ^ static_cast<unsigned char> (((colorInt >> 0) & 0xFF));
250  diffGreen = (static_cast<unsigned char> (avgGreen)) ^ static_cast<unsigned char> (((colorInt >> 8) & 0xFF));
251  diffBlue = (static_cast<unsigned char> (avgBlue)) ^ static_cast<unsigned char> (((colorInt >> 16) & 0xFF));
252 
253  // remove least significant bits
254  diffRed = static_cast<unsigned char> (diffRed >> colorBitReduction_);
255  diffGreen = static_cast<unsigned char> (diffGreen >> colorBitReduction_);
256  diffBlue = static_cast<unsigned char> (diffBlue >> colorBitReduction_);
257 
258  // add to differential color vector
259  pointDiffColorDataVector_.push_back (static_cast<char> (diffRed));
260  pointDiffColorDataVector_.push_back (static_cast<char> (diffGreen));
261  pointDiffColorDataVector_.push_back (static_cast<char> (diffBlue));
262  }
263  }
264 
265  // remove least significant bits from average color information
266  avgRed >>= colorBitReduction_;
267  avgGreen >>= colorBitReduction_;
268  avgBlue >>= colorBitReduction_;
269 
270  // add to differential color vector
271  pointAvgColorDataVector_.push_back (static_cast<char> (avgRed));
272  pointAvgColorDataVector_.push_back (static_cast<char> (avgGreen));
273  pointAvgColorDataVector_.push_back (static_cast<char> (avgBlue));
274 
275  }
276 
277  /** \brief Decode color information
278  * \param outputCloud_arg output point cloud
279  * \param beginIdx_arg index indicating first point to be assigned with color information
280  * \param endIdx_arg index indicating last point to be assigned with color information
281  * \param rgba_offset_arg offset to color information
282  */
283  void
284  decodePoints (PointCloudPtr outputCloud_arg, std::size_t beginIdx_arg, std::size_t endIdx_arg, unsigned char rgba_offset_arg)
285  {
286  assert (beginIdx_arg <= endIdx_arg);
287 
288  // amount of points to be decoded
289  unsigned int pointCount = static_cast<unsigned int> (endIdx_arg - beginIdx_arg);
290 
291  // get averaged color information for current voxel
292  unsigned char avgRed = *(pointAvgColorDataVector_Iterator_++);
293  unsigned char avgGreen = *(pointAvgColorDataVector_Iterator_++);
294  unsigned char avgBlue = *(pointAvgColorDataVector_Iterator_++);
295 
296  // invert bit shifts during encoding
297  avgRed = static_cast<unsigned char> (avgRed << colorBitReduction_);
298  avgGreen = static_cast<unsigned char> (avgGreen << colorBitReduction_);
299  avgBlue = static_cast<unsigned char> (avgBlue << colorBitReduction_);
300 
301  // iterate over points
302  for (std::size_t i = 0; i < pointCount; i++)
303  {
304  unsigned int colorInt;
305  if (pointCount > 1)
306  {
307  // get differential color information from input vector
308  unsigned char diffRed = static_cast<unsigned char> (*(pointDiffColorDataVector_Iterator_++));
309  unsigned char diffGreen = static_cast<unsigned char> (*(pointDiffColorDataVector_Iterator_++));
310  unsigned char diffBlue = static_cast<unsigned char> (*(pointDiffColorDataVector_Iterator_++));
311 
312  // invert bit shifts during encoding
313  diffRed = static_cast<unsigned char> (diffRed << colorBitReduction_);
314  diffGreen = static_cast<unsigned char> (diffGreen << colorBitReduction_);
315  diffBlue = static_cast<unsigned char> (diffBlue << colorBitReduction_);
316 
317  // decode color information
318  colorInt = ((avgRed ^ diffRed) << 0) |
319  ((avgGreen ^ diffGreen) << 8) |
320  ((avgBlue ^ diffBlue) << 16);
321  }
322  else
323  {
324  // decode color information
325  colorInt = (avgRed << 0) | (avgGreen << 8) | (avgBlue << 16);
326  }
327 
328  char* idxPointPtr = reinterpret_cast<char*> (&(*outputCloud_arg)[beginIdx_arg + i]);
329  int& pointColor = *reinterpret_cast<int*> (idxPointPtr+rgba_offset_arg);
330  // assign color to point from point cloud
331  pointColor=colorInt;
332  }
333  }
334 
335  /** \brief Set default color to points
336  * \param outputCloud_arg output point cloud
337  * \param beginIdx_arg index indicating first point to be assigned with color information
338  * \param endIdx_arg index indicating last point to be assigned with color information
339  * \param rgba_offset_arg offset to color information
340  * */
341  void
342  setDefaultColor (PointCloudPtr outputCloud_arg, std::size_t beginIdx_arg, std::size_t endIdx_arg, unsigned char rgba_offset_arg)
343  {
344  assert (beginIdx_arg <= endIdx_arg);
345 
346  // amount of points to be decoded
347  unsigned int pointCount = static_cast<unsigned int> (endIdx_arg - beginIdx_arg);
348 
349  // iterate over points
350  for (std::size_t i = 0; i < pointCount; i++)
351  {
352  char* idxPointPtr = reinterpret_cast<char*> (&(*outputCloud_arg)[beginIdx_arg + i]);
353  int& pointColor = *reinterpret_cast<int*> (idxPointPtr+rgba_offset_arg);
354  // assign color to point from point cloud
355  pointColor = defaultColor_;
356  }
357  }
358 
359 protected:
360  /** \brief Pointer to output point cloud dataset. */
361  PointCloudPtr output_;
362 
363  /** \brief Vector for storing average color information */
364  std::vector<char> pointAvgColorDataVector_;
365 
366  /** \brief Iterator on average color information vector */
367  std::vector<char>::const_iterator pointAvgColorDataVector_Iterator_;
368 
369  /** \brief Vector for storing differential color information */
370  std::vector<char> pointDiffColorDataVector_;
371 
372  /** \brief Iterator on differential color information vector */
373  std::vector<char>::const_iterator pointDiffColorDataVector_Iterator_;
374 
375  /** \brief Amount of bits to be removed from color components before encoding */
376  unsigned char colorBitReduction_;
377 
378  // frame header identifier
379  static const int defaultColor_;
380 };
381 
382 // define default color
383 template<typename PointT>
384 const int ColorCoding<PointT>::defaultColor_ = ((255) << 0) |
385  ((255) << 8) |
386  ((255) << 16);
387 
388 } // namespace octree
389 } // namespace pcl
390 
391 #define PCL_INSTANTIATE_ColorCoding(T) template class PCL_EXPORTS pcl::octree::ColorCoding<T>;
392 
pcl::octree::ColorCoding::pointAvgColorDataVector_
std::vector< char > pointAvgColorDataVector_
Vector for storing average color information
Definition: color_coding.h:364
pcl::octree::ColorCoding::pointDiffColorDataVector_
std::vector< char > pointDiffColorDataVector_
Vector for storing differential color information
Definition: color_coding.h:370
pcl::octree::ColorCoding::pointAvgColorDataVector_Iterator_
std::vector< char >::const_iterator pointAvgColorDataVector_Iterator_
Iterator on average color information vector.
Definition: color_coding.h:367
pcl
Definition: convolution.h:46
pcl::octree::ColorCoding::encodeAverageOfPoints
void encodeAverageOfPoints(const typename std::vector< int > &indexVector_arg, unsigned char rgba_offset_arg, PointCloudConstPtr inputCloud_arg)
Encode averaged color information for a subset of points from point cloud.
Definition: color_coding.h:158
pcl::octree::ColorCoding::output_
PointCloudPtr output_
Pointer to output point cloud dataset.
Definition: color_coding.h:361
pcl::octree::ColorCoding::initializeEncoding
void initializeEncoding()
Initialize encoding of color information.
Definition: color_coding.h:119
pcl::PointCloud
PointCloud represents the base class in PCL for storing collections of 3D points.
Definition: distances.h:55
pcl::octree::ColorCoding::encodePoints
void encodePoints(const typename std::vector< int > &indexVector_arg, unsigned char rgba_offset_arg, PointCloudConstPtr inputCloud_arg)
Encode color information of a subset of points from point cloud.
Definition: color_coding.h:205
pcl::octree::ColorCoding
ColorCoding class
Definition: color_coding.h:56
pcl::octree::ColorCoding::pointDiffColorDataVector_Iterator_
std::vector< char >::const_iterator pointDiffColorDataVector_Iterator_
Iterator on differential color information vector.
Definition: color_coding.h:373
pcl::octree::ColorCoding::initializeDecoding
void initializeDecoding()
Initialize decoding of color information.
Definition: color_coding.h:129
pcl::octree::ColorCoding::getDifferentialDataVector
std::vector< char > & getDifferentialDataVector()
Get reference to vector containing differential color data.
Definition: color_coding.h:147
pcl::octree::ColorCoding::setBitDepth
void setBitDepth(unsigned char bitDepth_arg)
Define color bit depth of encoded color information.
Definition: color_coding.h:83
pcl::octree::ColorCoding::getAverageDataVector
std::vector< char > & getAverageDataVector()
Get reference to vector containing averaged color data.
Definition: color_coding.h:139
pcl::octree::ColorCoding::setDefaultColor
void setDefaultColor(PointCloudPtr outputCloud_arg, std::size_t beginIdx_arg, std::size_t endIdx_arg, unsigned char rgba_offset_arg)
Set default color to points.
Definition: color_coding.h:342
pcl::octree::ColorCoding::ColorCoding
ColorCoding()
Constructor.
Definition: color_coding.h:67
pcl::PointCloud::Ptr
shared_ptr< PointCloud< PointT > > Ptr
Definition: point_cloud.h:406
pcl::octree::ColorCoding::defaultColor_
static const int defaultColor_
Definition: color_coding.h:379
pcl::octree::ColorCoding::colorBitReduction_
unsigned char colorBitReduction_
Amount of bits to be removed from color components before encoding.
Definition: color_coding.h:376
pcl::octree::ColorCoding::setVoxelCount
void setVoxelCount(unsigned int voxelCount_arg)
Set amount of voxels containing point color information and reserve memory.
Definition: color_coding.h:101
pcl::PointCloud::ConstPtr
shared_ptr< const PointCloud< PointT > > ConstPtr
Definition: point_cloud.h:407
pcl::octree::ColorCoding::setPointCount
void setPointCount(unsigned int pointCount_arg)
Set amount of points within point cloud to be encoded and reserve memory.
Definition: color_coding.h:111
pcl::octree::ColorCoding::decodePoints
void decodePoints(PointCloudPtr outputCloud_arg, std::size_t beginIdx_arg, std::size_t endIdx_arg, unsigned char rgba_offset_arg)
Decode color information.
Definition: color_coding.h:284
pcl::octree::ColorCoding::getBitDepth
unsigned char getBitDepth()
Retrieve color bit depth of encoded color information.
Definition: color_coding.h:92
pcl::octree::ColorCoding::~ColorCoding
virtual ~ColorCoding()
Empty class constructor.
Definition: color_coding.h:74