<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"> <html><head><meta http-equiv="Content-Type" content="text/html;charset=iso-8859-1"> <title>CObservation3DRangeScan.h Source File</title> <link href="doxygen.css" rel="stylesheet" type="text/css"> <link href="tabs.css" rel="stylesheet" type="text/css"> </head><body> <div align="left"><a href="http://www.mrpt.org/">Main MRPT website</a> > <b>C++ reference</b> </div> <div align="right"> <a href="index.html"><img border="0" src="mrpt_logo.png" alt="MRPT logo"></a> </div> <!-- Generated by Doxygen 1.7.5 --> <script type="text/javascript"> var searchBox = new SearchBox("searchBox", "search",false,'Search'); </script> <div id="navrow1" class="tabs"> <ul class="tablist"> <li><a href="index.html"><span>Main Page</span></a></li> <li><a href="pages.html"><span>Related Pages</span></a></li> <li><a href="modules.html"><span>Modules</span></a></li> <li><a href="namespaces.html"><span>Namespaces</span></a></li> <li><a href="annotated.html"><span>Classes</span></a></li> <li class="current"><a href="files.html"><span>Files</span></a></li> <li> <div id="MSearchBox" class="MSearchBoxInactive"> <div class="left"> <form id="FSearchBox" action="search.php" method="get"> <img id="MSearchSelect" src="search/mag.png" alt=""/> <input type="text" id="MSearchField" name="query" value="Search" size="20" accesskey="S" onfocus="searchBox.OnSearchFieldFocus(true)" onblur="searchBox.OnSearchFieldFocus(false)"/> </form> </div><div class="right"></div> </div> </li> </ul> </div> <div id="navrow2" class="tabs2"> <ul class="tablist"> <li><a href="files.html"><span>File List</span></a></li> <li><a href="globals.html"><span>File Members</span></a></li> </ul> </div> <div class="header"> <div class="headertitle"> <div class="title">CObservation3DRangeScan.h</div> </div> </div> <div class="contents"> <a href="_c_observation3_d_range_scan_8h.html">Go to the documentation of this file.</a><div class="fragment"><pre class="fragment"><a name="l00001"></a>00001 <span class="comment">/* +---------------------------------------------------------------------------+</span> <a name="l00002"></a>00002 <span class="comment"> | The Mobile Robot Programming Toolkit (MRPT) C++ library |</span> <a name="l00003"></a>00003 <span class="comment"> | |</span> <a name="l00004"></a>00004 <span class="comment"> | http://www.mrpt.org/ |</span> <a name="l00005"></a>00005 <span class="comment"> | |</span> <a name="l00006"></a>00006 <span class="comment"> | Copyright (C) 2005-2011 University of Malaga |</span> <a name="l00007"></a>00007 <span class="comment"> | |</span> <a name="l00008"></a>00008 <span class="comment"> | This software was written by the Machine Perception and Intelligent |</span> <a name="l00009"></a>00009 <span class="comment"> | Robotics Lab, University of Malaga (Spain). |</span> <a name="l00010"></a>00010 <span class="comment"> | Contact: Jose-Luis Blanco <jlblanco@ctima.uma.es> |</span> <a name="l00011"></a>00011 <span class="comment"> | |</span> <a name="l00012"></a>00012 <span class="comment"> | This file is part of the MRPT project. |</span> <a name="l00013"></a>00013 <span class="comment"> | |</span> <a name="l00014"></a>00014 <span class="comment"> | MRPT is free software: you can redistribute it and/or modify |</span> <a name="l00015"></a>00015 <span class="comment"> | it under the terms of the GNU General Public License as published by |</span> <a name="l00016"></a>00016 <span class="comment"> | the Free Software Foundation, either version 3 of the License, or |</span> <a name="l00017"></a>00017 <span class="comment"> | (at your option) any later version. |</span> <a name="l00018"></a>00018 <span class="comment"> | |</span> <a name="l00019"></a>00019 <span class="comment"> | MRPT is distributed in the hope that it will be useful, |</span> <a name="l00020"></a>00020 <span class="comment"> | but WITHOUT ANY WARRANTY; without even the implied warranty of |</span> <a name="l00021"></a>00021 <span class="comment"> | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |</span> <a name="l00022"></a>00022 <span class="comment"> | GNU General Public License for more details. |</span> <a name="l00023"></a>00023 <span class="comment"> | |</span> <a name="l00024"></a>00024 <span class="comment"> | You should have received a copy of the GNU General Public License |</span> <a name="l00025"></a>00025 <span class="comment"> | along with MRPT. If not, see <http://www.gnu.org/licenses/>. |</span> <a name="l00026"></a>00026 <span class="comment"> | |</span> <a name="l00027"></a>00027 <span class="comment"> +---------------------------------------------------------------------------+ */</span> <a name="l00028"></a>00028 <span class="preprocessor">#ifndef CObservation3DRangeScan_H</span> <a name="l00029"></a>00029 <span class="preprocessor"></span><span class="preprocessor">#define CObservation3DRangeScan_H</span> <a name="l00030"></a>00030 <span class="preprocessor"></span> <a name="l00031"></a>00031 <span class="preprocessor">#include <<a class="code" href="_c_serializable_8h.html">mrpt/utils/CSerializable.h</a>></span> <a name="l00032"></a>00032 <span class="preprocessor">#include <<a class="code" href="_c_image_8h.html">mrpt/utils/CImage.h</a>></span> <a name="l00033"></a>00033 <span class="preprocessor">#include <<a class="code" href="_c_observation_8h.html">mrpt/slam/CObservation.h</a>></span> <a name="l00034"></a>00034 <span class="preprocessor">#include <<a class="code" href="_c_pose3_d_8h.html">mrpt/poses/CPose3D.h</a>></span> <a name="l00035"></a>00035 <span class="preprocessor">#include <<a class="code" href="_c_pose2_d_8h.html">mrpt/poses/CPose2D.h</a>></span> <a name="l00036"></a>00036 <a name="l00037"></a>00037 <span class="preprocessor">#include <<a class="code" href="_c_polygon_8h.html">mrpt/math/CPolygon.h</a>></span> <a name="l00038"></a>00038 <a name="l00039"></a>00039 <a name="l00040"></a>00040 <span class="keyword">namespace </span>mrpt <a name="l00041"></a>00041 { <a name="l00042"></a>00042 <span class="keyword">namespace </span>slam <a name="l00043"></a>00043 { <a name="l00044"></a>00044 <a name="l00045"></a><a class="code" href="structmrpt_1_1slam_1_1_c_observation3_d_range_scan_ptr.html#a770cc45b23e61f6984f16b592ae2df92">00045</a> <a class="code" href="_c_serializable_8h.html#a9ef523d787f6cb837a0585b790882588" title="This declaration must be inserted in all CSerializable classes definition, before the class declarati...">DEFINE_SERIALIZABLE_PRE_CUSTOM_BASE_LINKAGE</a>( <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html" title="Declares a class derived from "CObservation" that encapsules a 3D range scan measurement (e...">CObservation3DRangeScan</a>, <a class="code" href="classmrpt_1_1slam_1_1_c_observation.html" title="Declares a class that represents any robot's observation.">CObservation</a>,<a class="code" href="obs_2include_2mrpt_2obs_2link__pragmas_8h.html#ae8bb1b2647c58d6ae2eb30ca31fcf5a1">OBS_IMPEXP</a> ) <a name="l00046"></a>00046 <a name="l00047"></a>00047 <span class="comment">/** Declares a class derived from "CObservation" that</span> <a name="l00048"></a>00048 <span class="comment"> * encapsules a 3D range scan measurement (e.g. from a time of flight range camera).</span> <a name="l00049"></a>00049 <span class="comment"> * This kind of observations can carry one or more of these data fields:</span> <a name="l00050"></a>00050 <span class="comment"> * - 3D point cloud (as float's).</span> <a name="l00051"></a>00051 <span class="comment"> * - 2D range image (as a matrix): Each entry in the matrix "rangeImage(ROW,COLUMN)" contains a distance or a depth (in meters), depending on \a range_is_depth.</span> <a name="l00052"></a>00052 <span class="comment"> * - 2D intensity (grayscale or RGB) image (as a mrpt::utils::CImage): For SwissRanger cameras, a logarithmic A-law compression is used to convert the original 16bit intensity to a more standard 8bit graylevel.</span> <a name="l00053"></a>00053 <span class="comment"> * - 2D confidence image (as a mrpt::utils::CImage): For each pixel, a 0x00 and a 0xFF mean the lowest and highest confidence levels, respectively.</span> <a name="l00054"></a>00054 <span class="comment"> *</span> <a name="l00055"></a>00055 <span class="comment"> * The coordinates of the 3D point cloud are in meters with respect to the depth camera origin of coordinates</span> <a name="l00056"></a>00056 <span class="comment"> * (in SwissRanger, the front face of the camera: a small offset ~1cm in front of the physical focal point),</span> <a name="l00057"></a>00057 <span class="comment"> * with the +X axis pointing forward, +Y pointing left-hand and +Z pointing up.</span> <a name="l00058"></a>00058 <span class="comment"> * The field CObservation3DRangeScan::relativePoseIntensityWRTDepth describes the change of coordinates from</span> <a name="l00059"></a>00059 <span class="comment"> * the depth camera to the intensity (RGB or grayscale) camera. In a SwissRanger camera both cameras coincide,</span> <a name="l00060"></a>00060 <span class="comment"> * so this pose is just a rotation (0,0,0,-90deg,0,-90deg). But in</span> <a name="l00061"></a>00061 <span class="comment"> * Microsoft Kinect there is also an offset, as shown in this figure:</span> <a name="l00062"></a>00062 <span class="comment"> *</span> <a name="l00063"></a>00063 <span class="comment"> * <div align=center></span> <a name="l00064"></a>00064 <span class="comment"> * <img src="CObservation3DRangeScan_figRefSystem.png"></span> <a name="l00065"></a>00065 <span class="comment"> * </div></span> <a name="l00066"></a>00066 <span class="comment"> *</span> <a name="l00067"></a>00067 <span class="comment"> * In any case, check the field \a relativePoseIntensityWRTDepth, or the method \a doDepthAndIntensityCamerasCoincide()</span> <a name="l00068"></a>00068 <span class="comment"> * to determine if both frames of reference coincide, since even for Kinect cameras both can coincide if the images</span> <a name="l00069"></a>00069 <span class="comment"> * have been rectified.</span> <a name="l00070"></a>00070 <span class="comment"> *</span> <a name="l00071"></a>00071 <span class="comment"> * The 2D images and matrices are stored as common images, with an up->down rows order and left->right, as usual.</span> <a name="l00072"></a>00072 <span class="comment"> * Optionally, the intensity and confidence channels can be set to delayed-load images for off-rawlog storage so it saves</span> <a name="l00073"></a>00073 <span class="comment"> * memory by having loaded in memory just the needed images. See the methods load() and unload().</span> <a name="l00074"></a>00074 <span class="comment"> * Due to the intensive storage requirements of this kind of observations, this observation is the only one in MRPT</span> <a name="l00075"></a>00075 <span class="comment"> * for which it's recommended to always call "load()" and "unload()" before and after using the observation, *ONLY* when</span> <a name="l00076"></a>00076 <span class="comment"> * the observation was read from a rawlog dataset, in order to make sure that all the externally stored data fields are</span> <a name="l00077"></a>00077 <span class="comment"> * loaded and ready in memory.</span> <a name="l00078"></a>00078 <span class="comment"> *</span> <a name="l00079"></a>00079 <span class="comment"> * Classes that grab observations of this type are:</span> <a name="l00080"></a>00080 <span class="comment"> * - mrpt::hwdrivers::CSwissRanger3DCamera</span> <a name="l00081"></a>00081 <span class="comment"> * - mrpt::hwdrivers::CKinect</span> <a name="l00082"></a>00082 <span class="comment"> *</span> <a name="l00083"></a>00083 <span class="comment"> * There are two sets of calibration parameters:</span> <a name="l00084"></a>00084 <span class="comment"> * - cameraParams: Projection parameters of the depth camera.</span> <a name="l00085"></a>00085 <span class="comment"> * - cameraParamsIntensity: Projection parameters of the intensity (gray-level or RGB) camera.</span> <a name="l00086"></a>00086 <span class="comment"> *</span> <a name="l00087"></a>00087 <span class="comment"> * In some cameras, like SwissRanger, both are the same. Also, it is possible in Kinect to rectify the range images such both cameras</span> <a name="l00088"></a>00088 <span class="comment"> * seem to coincide and then both sets of camera parameters will be identical.</span> <a name="l00089"></a>00089 <span class="comment"> *</span> <a name="l00090"></a>00090 <span class="comment"> * Range data can be interpreted in two different ways depending on the 3D camera (this field is already set to the</span> <a name="l00091"></a>00091 <span class="comment"> * correct setting when grabbing observations from an mrpt::hwdrivers sensor):</span> <a name="l00092"></a>00092 <span class="comment"> * - range_is_depth=true -> Kinect-like ranges: entries of \a rangeImage are distances along the +X axis</span> <a name="l00093"></a>00093 <span class="comment"> * - range_is_depth=false -> Ranges in \a rangeImage are actual distances in 3D.</span> <a name="l00094"></a>00094 <span class="comment"> *</span> <a name="l00095"></a>00095 <span class="comment"> * 3D point clouds can be generated at any moment after grabbing with CObservation3DRangeScan::project3DPointsFromDepthImage()</span> <a name="l00096"></a>00096 <span class="comment"> *</span> <a name="l00097"></a>00097 <span class="comment"> * \note Starting at serialization version 2 (MRPT 0.9.1+), the confidence channel is stored as an image instead of a matrix to optimize memory and disk space.</span> <a name="l00098"></a>00098 <span class="comment"> * \note Starting at serialization version 3 (MRPT 0.9.1+), the 3D point cloud and the rangeImage can both be stored externally to save rawlog space.</span> <a name="l00099"></a>00099 <span class="comment"> * \note Starting at serialization version 5 (MRPT 0.9.5+), the new field \a range_is_depth.</span> <a name="l00100"></a>00100 <span class="comment"> *</span> <a name="l00101"></a>00101 <span class="comment"> * \sa mrpt::hwdrivers::CSwissRanger3DCamera, mrpt::hwdrivers::CKinect, CObservation</span> <a name="l00102"></a>00102 <span class="comment"> * \ingroup mrpt_obs_grp</span> <a name="l00103"></a>00103 <span class="comment"> */</span> <a name="l00104"></a>00104 class <a class="code" href="obs_2include_2mrpt_2obs_2link__pragmas_8h.html#ae8bb1b2647c58d6ae2eb30ca31fcf5a1">OBS_IMPEXP</a> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html" title="Declares a class derived from "CObservation" that encapsules a 3D range scan measurement (e...">CObservation3DRangeScan</a> : public <a class="code" href="classmrpt_1_1slam_1_1_c_observation.html" title="Declares a class that represents any robot's observation.">CObservation</a> <a name="l00105"></a>00105 { <a name="l00106"></a>00106 <span class="comment">// This must be added to any CSerializable derived class:</span> <a name="l00107"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#ab6e3fbd5783a4a5e7320cef562606bb6">00107</a> <a class="code" href="_c_serializable_8h.html#a72ab55bf7ae009c89b75715cfa21e84d" title="This declaration must be inserted in all CSerializable classes definition, within the class declarati...">DEFINE_SERIALIZABLE</a>( <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html" title="Declares a class derived from "CObservation" that encapsules a 3D range scan measurement (e...">CObservation3DRangeScan</a> ) <a name="l00108"></a>00108 <a name="l00109"></a>00109 protected: <a name="l00110"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a6f603c7774754227a45075217914d74c">00110</a> <span class="keywordtype">bool</span> m_points3D_external_stored; <span class="comment">//!< If set to true, m_points3D_external_file is valid.</span> <a name="l00111"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#af89ce19a39ecdbdddfd68fbb87016f58">00111</a> <span class="comment"></span> std::<span class="keywordtype">string</span> m_points3D_external_file; <span class="comment">//!< 3D points are in CImage::IMAGES_PATH_BASE+<this_file_name></span> <a name="l00112"></a>00112 <span class="comment"></span> <a name="l00113"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a345e4f41854e3602d707b0f8653533aa">00113</a> <span class="keywordtype">bool</span> m_rangeImage_external_stored; <span class="comment">//!< If set to true, m_rangeImage_external_file is valid.</span> <a name="l00114"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a0102da2b4d3621f5111e888a93227352">00114</a> <span class="comment"></span> std::<span class="keywordtype">string</span> m_rangeImage_external_file; <span class="comment">//!< rangeImage is in CImage::IMAGES_PATH_BASE+<this_file_name></span> <a name="l00115"></a>00115 <span class="comment"></span> <a name="l00116"></a>00116 public: <a name="l00117"></a>00117 <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html" title="Declares a class derived from "CObservation" that encapsules a 3D range scan measurement (e...">CObservation3DRangeScan</a>( ); <span class="comment">//!< Default constructor</span> <a name="l00118"></a>00118 <span class="comment"></span> virtual ~CObservation3DRangeScan( ); <span class="comment">//!< Destructor</span> <a name="l00119"></a>00119 <span class="comment"></span><span class="comment"></span> <a name="l00120"></a>00120 <span class="comment"> /** @name Delayed-load manual control methods.</span> <a name="l00121"></a>00121 <span class="comment"> @{ */</span><span class="comment"></span> <a name="l00122"></a>00122 <span class="comment"> /** Makes sure all images and other fields which may be externally stored are loaded in memory.</span> <a name="l00123"></a>00123 <span class="comment"> * Note that for all CImages, calling load() is not required since the images will be automatically loaded upon first access, so load() shouldn't be needed to be called in normal cases by the user.</span> <a name="l00124"></a>00124 <span class="comment"> * If all the data were alredy loaded or this object has no externally stored data fields, calling this method has no effects.</span> <a name="l00125"></a>00125 <span class="comment"> * \sa unload</span> <a name="l00126"></a>00126 <span class="comment"> */</span> <a name="l00127"></a>00127 virtual <span class="keywordtype">void</span> load() const;<span class="comment"></span> <a name="l00128"></a>00128 <span class="comment"> /** Unload all images, for the case they being delayed-load images stored in external files (othewise, has no effect).</span> <a name="l00129"></a>00129 <span class="comment"> * \sa load</span> <a name="l00130"></a>00130 <span class="comment"> */</span> <a name="l00131"></a>00131 virtual <span class="keywordtype">void</span> unload();<span class="comment"></span> <a name="l00132"></a>00132 <span class="comment"> /** @} */</span> <a name="l00133"></a>00133 <span class="comment"></span> <a name="l00134"></a>00134 <span class="comment"> /** Compute the 3D points coordinates from the depth image (\a rangeImage) and the depth camera camera parameters (\a cameraParams).</span> <a name="l00135"></a>00135 <span class="comment"> * There exist two set of formulas for projecting the i'th point, depending on the value of "range_is_depth".</span> <a name="l00136"></a>00136 <span class="comment"> * In all formulas below, "rangeImage" is the matrix of ranges and the pixel coordinates are (r,c).</span> <a name="l00137"></a>00137 <span class="comment"> *</span> <a name="l00138"></a>00138 <span class="comment"> * 1) [range_is_depth=true] With "range equals depth" or "Kinect-like depth mode": the range values</span> <a name="l00139"></a>00139 <span class="comment"> * are in fact distances along the "+X" axis, not real 3D ranges (this is the way Kinect reports ranges):</span> <a name="l00140"></a>00140 <span class="comment"> *</span> <a name="l00141"></a>00141 <span class="comment"> * \code</span> <a name="l00142"></a>00142 <span class="comment"> * x(i) = rangeImage(r,c)</span> <a name="l00143"></a>00143 <span class="comment"> * y(i) = (r_cx - c) * x(i) / r_fx</span> <a name="l00144"></a>00144 <span class="comment"> * z(i) = (r_cy - r) * x(i) / r_fy</span> <a name="l00145"></a>00145 <span class="comment"> * \endcode</span> <a name="l00146"></a>00146 <span class="comment"> *</span> <a name="l00147"></a>00147 <span class="comment"> *</span> <a name="l00148"></a>00148 <span class="comment"> * 2) [range_is_depth=false] With "normal ranges": range means distance in 3D. This must be set when</span> <a name="l00149"></a>00149 <span class="comment"> * processing data from the SwissRange 3D camera, among others.</span> <a name="l00150"></a>00150 <span class="comment"> *</span> <a name="l00151"></a>00151 <span class="comment"> * \code</span> <a name="l00152"></a>00152 <span class="comment"> * Ky = (r_cx - c)/r_fx</span> <a name="l00153"></a>00153 <span class="comment"> * Kz = (r_cy - r)/r_fy</span> <a name="l00154"></a>00154 <span class="comment"> *</span> <a name="l00155"></a>00155 <span class="comment"> * x(i) = rangeImage(r,c) / sqrt( 1 + Ky^2 + Kz^2 )</span> <a name="l00156"></a>00156 <span class="comment"> * y(i) = Ky * x(i)</span> <a name="l00157"></a>00157 <span class="comment"> * z(i) = Kz * x(i)</span> <a name="l00158"></a>00158 <span class="comment"> * \endcode</span> <a name="l00159"></a>00159 <span class="comment"> *</span> <a name="l00160"></a>00160 <span class="comment"> * \param[in] PROJ3D_USE_LUT (Only when range_is_depth=true) Whether to use a Look-up-table (LUT) to speed up the conversion. It's thread safe in all situations <b>except</b> when you call this method from different threads <b>and</b> with different camera parameter matrices. In all other cases, it's a good idea to left it enabled.</span> <a name="l00161"></a>00161 <span class="comment"> *</span> <a name="l00162"></a>00162 <span class="comment"> * \note In MRPT < 0.9.5, this method always assumes that ranges were in Kinect-like format.</span> <a name="l00163"></a>00163 <span class="comment"> */</span> <a name="l00164"></a>00164 <span class="keywordtype">void</span> project3DPointsFromDepthImage(const <span class="keywordtype">bool</span> PROJ3D_USE_LUT=true); <a name="l00165"></a>00165 <a name="l00166"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a626fce1290e5964bb11dce414f3404ed">00166</a> <span class="keywordtype">bool</span> hasPoints3D; <span class="comment">//!< true means the field points3D contains valid data.</span> <a name="l00167"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a076786d89b432044134849557fe87069">00167</a> <span class="comment"></span> std::<a class="code" href="classstd_1_1vector.html" title="STL class.">vector</a><<span class="keywordtype">float</span>> points3D_x; <span class="comment">//!< If hasPoints3D=true, the X coordinates of the 3D point cloud detected by the camera. \sa resizePoints3DVectors</span> <a name="l00168"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a914792f38dac9d7a15098ebe1991c09b">00168</a> <span class="comment"></span> std::<a class="code" href="classstd_1_1vector.html" title="STL class.">vector</a><<span class="keywordtype">float</span>> points3D_y; <span class="comment">//!< If hasPoints3D=true, the Y coordinates of the 3D point cloud detected by the camera. \sa resizePoints3DVectors</span> <a name="l00169"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a20aec97d07425273f1522f14a256c51c">00169</a> <span class="comment"></span> std::<a class="code" href="classstd_1_1vector.html" title="STL class.">vector</a><<span class="keywordtype">float</span>> points3D_z; <span class="comment">//!< If hasPoints3D=true, the Z coordinates of the 3D point cloud detected by the camera. \sa resizePoints3DVectors</span> <a name="l00170"></a>00170 <span class="comment"></span><span class="comment"></span> <a name="l00171"></a>00171 <span class="comment"> /** Use this method instead of resizing all three \a points3D_x, \a points3D_y & \a points3D_z to allow the usage of the internal memory pool. */</span> <a name="l00172"></a>00172 <span class="keywordtype">void</span> resizePoints3DVectors(const <span class="keywordtype">size_t</span> nPoints); <a name="l00173"></a>00173 <a name="l00174"></a>00174 <span class="comment">// 3D points external storage functions ---------</span> <a name="l00175"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a138047831d773ed925b2c06064b47f85">00175</a> inline <span class="keywordtype">bool</span> points3D_isExternallyStored()<span class="keyword"> const </span>{ <span class="keywordflow">return</span> m_points3D_external_stored; } <a name="l00176"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a2ab4653a696310c4be207c515c69fb53">00176</a> <span class="keyword">inline</span> std<a class="code" href="classstd_1_1string.html" title="STL class.">::string</a> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a2ab4653a696310c4be207c515c69fb53">points3D_getExternalStorageFile</a>()<span class="keyword"> const </span>{ <span class="keywordflow">return</span> m_points3D_external_file; } <a name="l00177"></a>00177 <span class="keywordtype">void</span> points3D_getExternalStorageFileAbsolutePath(<a class="code" href="classstd_1_1string.html" title="STL class.">std::string</a> &out_path) <span class="keyword">const</span>; <a name="l00178"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a0725dfa2db806283300eabed03f15b03">00178</a> <span class="keyword">inline</span> std<a class="code" href="classstd_1_1string.html" title="STL class.">::string</a> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a0725dfa2db806283300eabed03f15b03">points3D_getExternalStorageFileAbsolutePath</a>()<span class="keyword"> const </span>{ <a name="l00179"></a>00179 std<a class="code" href="classstd_1_1string.html" title="STL class.">::string</a> tmp; <a name="l00180"></a>00180 points3D_getExternalStorageFileAbsolutePath(tmp); <a name="l00181"></a>00181 <span class="keywordflow">return</span> tmp; <a name="l00182"></a>00182 } <a name="l00183"></a>00183 <span class="keywordtype">void</span> points3D_convertToExternalStorage( <span class="keyword">const</span> <a class="code" href="classstd_1_1string.html" title="STL class.">std::string</a> &fileName, <span class="keyword">const</span> <a class="code" href="classstd_1_1string.html" title="STL class.">std::string</a> &use_this_base_dir ); <span class="comment">//!< Users won't normally want to call this, it's only used from internal MRPT programs.</span> <a name="l00184"></a>00184 <span class="comment"></span> <span class="comment">// ---------</span> <a name="l00185"></a>00185 <a name="l00186"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a0559c84e0a67864e4ce59348678436b4">00186</a> <span class="keywordtype">bool</span> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a0559c84e0a67864e4ce59348678436b4" title="true means the field rangeImage contains valid data">hasRangeImage</a>; <span class="comment">//!< true means the field rangeImage contains valid data</span> <a name="l00187"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a0f98cea47186bd07f1f1716952f75c22">00187</a> <span class="comment"></span> mrpt<a class="code" href="classmrpt_1_1math_1_1_c_matrix.html" title="This class is a "CSerializable" wrapper for "CMatrixFloat".">::math::CMatrix</a> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a0f98cea47186bd07f1f1716952f75c22" title="If hasRangeImage=true, a matrix of floats with the range data as captured by the camera (in meters)...">rangeImage</a>; <span class="comment">//!< If hasRangeImage=true, a matrix of floats with the range data as captured by the camera (in meters) \sa range_is_depth</span> <a name="l00188"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a77518e0cd9ce4cc8db949da58ef18ad7">00188</a> <span class="comment"></span> <span class="keywordtype">bool</span> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a77518e0cd9ce4cc8db949da58ef18ad7" title="true: Kinect-like ranges: entries of rangeImage are distances along the +X axis; false: Ranges in ran...">range_is_depth</a>; <span class="comment">//!< true: Kinect-like ranges: entries of \a rangeImage are distances along the +X axis; false: Ranges in \a rangeImage are actual distances in 3D.</span> <a name="l00189"></a>00189 <span class="comment"></span> <a name="l00190"></a>00190 <span class="keywordtype">void</span> rangeImage_setSize(<span class="keyword">const</span> <span class="keywordtype">int</span> HEIGHT, <span class="keyword">const</span> <span class="keywordtype">int</span> WIDTH); <span class="comment">//!< Similar to calling "rangeImage.setSize(H,W)" but this method provides memory pooling to speed-up the memory allocation.</span> <a name="l00191"></a>00191 <span class="comment"></span> <a name="l00192"></a>00192 <span class="comment">// Range Matrix external storage functions ---------</span> <a name="l00193"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a52de1b42c080cdd0ee6508a8e274f8d9">00193</a> <span class="keyword">inline</span> <span class="keywordtype">bool</span> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a52de1b42c080cdd0ee6508a8e274f8d9">rangeImage_isExternallyStored</a>()<span class="keyword"> const </span>{ <span class="keywordflow">return</span> m_rangeImage_external_stored; } <a name="l00194"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a28896385f2ec4d74d16160e7f053582b">00194</a> <span class="keyword">inline</span> std<a class="code" href="classstd_1_1string.html" title="STL class.">::string</a> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a28896385f2ec4d74d16160e7f053582b">rangeImage_getExternalStorageFile</a>()<span class="keyword"> const </span>{ <span class="keywordflow">return</span> m_rangeImage_external_file; } <a name="l00195"></a>00195 <span class="keywordtype">void</span> rangeImage_getExternalStorageFileAbsolutePath(<a class="code" href="classstd_1_1string.html" title="STL class.">std::string</a> &out_path) <span class="keyword">const</span>; <a name="l00196"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#ae0f1526dd694e84d4dc149003328beb0">00196</a> <span class="keyword">inline</span> std<a class="code" href="classstd_1_1string.html" title="STL class.">::string</a> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#ae0f1526dd694e84d4dc149003328beb0">rangeImage_getExternalStorageFileAbsolutePath</a>()<span class="keyword"> const </span>{ <a name="l00197"></a>00197 std<a class="code" href="classstd_1_1string.html" title="STL class.">::string</a> tmp; <a name="l00198"></a>00198 rangeImage_getExternalStorageFileAbsolutePath(tmp); <a name="l00199"></a>00199 <span class="keywordflow">return</span> tmp; <a name="l00200"></a>00200 } <a name="l00201"></a>00201 <span class="keywordtype">void</span> rangeImage_convertToExternalStorage( <span class="keyword">const</span> <a class="code" href="classstd_1_1string.html" title="STL class.">std::string</a> &fileName, <span class="keyword">const</span> <a class="code" href="classstd_1_1string.html" title="STL class.">std::string</a> &use_this_base_dir ); <span class="comment">//!< Users won't normally want to call this, it's only used from internal MRPT programs.</span> <a name="l00202"></a>00202 <span class="comment"></span><span class="comment"> /** Forces marking this observation as non-externally stored - it doesn't anything else apart from reseting the corresponding flag (Users won't normally want to call this, it's only used from internal MRPT programs) */</span> <a name="l00203"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a995f374e9b7cb6276cf1af9169162b17">00203</a> <span class="keywordtype">void</span> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a995f374e9b7cb6276cf1af9169162b17" title="Forces marking this observation as non-externally stored - it doesn't anything else apart from reseti...">rangeImage_forceResetExternalStorage</a>() { m_rangeImage_external_stored=<span class="keyword">false</span>; } <a name="l00204"></a>00204 <span class="comment">// ---------</span> <a name="l00205"></a>00205 <a name="l00206"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#ac21c65855e699cb8997333123694f06a">00206</a> <span class="keywordtype">bool</span> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#ac21c65855e699cb8997333123694f06a" title="true means the field intensityImage contains valid data">hasIntensityImage</a>; <span class="comment">//!< true means the field intensityImage contains valid data</span> <a name="l00207"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#ad80a6bb04bb9075c9a94a337baab8c44">00207</a> <span class="comment"></span> mrpt<a class="code" href="classmrpt_1_1utils_1_1_c_image.html" title="A class for storing images as grayscale or RGB bitmaps.">::utils::CImage</a> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#ad80a6bb04bb9075c9a94a337baab8c44" title="If hasIntensityImage=true, a color or gray-level intensity image of the same size than "rangeImage"...">intensityImage</a>; <span class="comment">//!< If hasIntensityImage=true, a color or gray-level intensity image of the same size than "rangeImage"</span> <a name="l00208"></a>00208 <span class="comment"></span> <a name="l00209"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a2cf64e2a0c320cb4e234d8c37e6ba8bd">00209</a> <span class="keywordtype">bool</span> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a2cf64e2a0c320cb4e234d8c37e6ba8bd" title="true means the field confidenceImage contains valid data">hasConfidenceImage</a>; <span class="comment">//!< true means the field confidenceImage contains valid data</span> <a name="l00210"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a4a0f22e324e555efc64bc795fcf052a1">00210</a> <span class="comment"></span> mrpt<a class="code" href="classmrpt_1_1utils_1_1_c_image.html" title="A class for storing images as grayscale or RGB bitmaps.">::utils::CImage</a> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a4a0f22e324e555efc64bc795fcf052a1" title="If hasConfidenceImage=true, an image with the "confidence" value [range 0-255] as estimated by the ca...">confidenceImage</a>; <span class="comment">//!< If hasConfidenceImage=true, an image with the "confidence" value [range 0-255] as estimated by the capture drivers.</span> <a name="l00211"></a>00211 <span class="comment"></span> <a name="l00212"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#ada5fceaf82d7863dd261a727db1e4c68">00212</a> mrpt<a class="code" href="classmrpt_1_1utils_1_1_t_camera.html" title="Structure to hold the parameters of a pinhole camera model.">::utils::TCamera</a> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#ada5fceaf82d7863dd261a727db1e4c68" title="Projection parameters of the depth camera.">cameraParams</a>; <span class="comment">//!< Projection parameters of the depth camera.</span> <a name="l00213"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#ad32223901eb22ce06859d8f5bce75c0e">00213</a> <span class="comment"></span> mrpt<a class="code" href="classmrpt_1_1utils_1_1_t_camera.html" title="Structure to hold the parameters of a pinhole camera model.">::utils::TCamera</a> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#ad32223901eb22ce06859d8f5bce75c0e" title="Projection parameters of the intensity (graylevel or RGB) camera.">cameraParamsIntensity</a>; <span class="comment">//!< Projection parameters of the intensity (graylevel or RGB) camera.</span> <a name="l00214"></a>00214 <span class="comment"></span><span class="comment"></span> <a name="l00215"></a>00215 <span class="comment"> /** Relative pose of the intensity camera wrt the depth camera (which is the coordinates origin for this observation).</span> <a name="l00216"></a>00216 <span class="comment"> * In a SwissRanger camera, this will be (0,0,0,-90deg,0,-90deg) since both cameras coincide.</span> <a name="l00217"></a>00217 <span class="comment"> * In a Kinect, this will include a small lateral displacement and a rotation, according to the drawing on the top of this page.</span> <a name="l00218"></a>00218 <span class="comment"> * \sa doDepthAndIntensityCamerasCoincide</span> <a name="l00219"></a>00219 <span class="comment"> */</span> <a name="l00220"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a3fc0f19191d7d741ab3832081befe020">00220</a> mrpt<a class="code" href="classmrpt_1_1poses_1_1_c_pose3_d.html" title="A class used to store a 3D pose (a 3D translation + a rotation in 3D).">::poses::CPose3D</a> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a3fc0f19191d7d741ab3832081befe020" title="Relative pose of the intensity camera wrt the depth camera (which is the coordinates origin for this ...">relativePoseIntensityWRTDepth</a>; <a name="l00221"></a>00221 <span class="comment"></span> <a name="l00222"></a>00222 <span class="comment"> /** Return true if \a relativePoseIntensityWRTDepth equals the pure rotation (0,0,0,-90deg,0,-90deg) (with a small comparison epsilon)</span> <a name="l00223"></a>00223 <span class="comment"> * \sa relativePoseIntensityWRTDepth</span> <a name="l00224"></a>00224 <span class="comment"> */</span> <a name="l00225"></a>00225 <span class="keywordtype">bool</span> doDepthAndIntensityCamerasCoincide() <span class="keyword">const</span>; <a name="l00226"></a>00226 <a name="l00227"></a>00227 <a name="l00228"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a421de2b6c46d2d93bb36382bf2e69e02">00228</a> <span class="keywordtype">float</span> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a421de2b6c46d2d93bb36382bf2e69e02" title="The maximum range allowed by the device, in meters (e.g. 8.0m, 5.0m,...)">maxRange</a>; <span class="comment">//!< The maximum range allowed by the device, in meters (e.g. 8.0m, 5.0m,...)</span> <a name="l00229"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#ace5f7375d556d1e6f6ed7750cbb1cccd">00229</a> <span class="comment"></span> <a class="code" href="classmrpt_1_1poses_1_1_c_pose3_d.html" title="A class used to store a 3D pose (a 3D translation + a rotation in 3D).">CPose3D</a> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#ace5f7375d556d1e6f6ed7750cbb1cccd" title="The 6D pose of the sensor on the robot.">sensorPose</a>; <span class="comment">//!< The 6D pose of the sensor on the robot.</span> <a name="l00230"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a67242543caa5ca865a4d1eea634d241a">00230</a> <span class="comment"></span> <span class="keywordtype">float</span> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a67242543caa5ca865a4d1eea634d241a" title="The "sigma" error of the device in meters, used while inserting the scan in an occupancy grid...">stdError</a>; <span class="comment">//!< The "sigma" error of the device in meters, used while inserting the scan in an occupancy grid.</span> <a name="l00231"></a>00231 <span class="comment"></span> <a name="l00232"></a>00232 <span class="comment"></span> <a name="l00233"></a>00233 <span class="comment"> /** A general method to retrieve the sensor pose on the robot.</span> <a name="l00234"></a>00234 <span class="comment"> * Note that most sensors will return a full (6D) CPose3D, but see the derived classes for more details or special cases.</span> <a name="l00235"></a>00235 <span class="comment"> * \sa setSensorPose</span> <a name="l00236"></a>00236 <span class="comment"> */</span> <a name="l00237"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a524e4c3856223448a0a3eeb9b2982b29">00237</a> <span class="keywordtype">void</span> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a524e4c3856223448a0a3eeb9b2982b29" title="A general method to retrieve the sensor pose on the robot.">getSensorPose</a>( <a class="code" href="classmrpt_1_1poses_1_1_c_pose3_d.html" title="A class used to store a 3D pose (a 3D translation + a rotation in 3D).">CPose3D</a> &out_sensorPose )<span class="keyword"> const </span>{ out_sensorPose = sensorPose; } <a name="l00238"></a>00238 <span class="comment"></span> <a name="l00239"></a>00239 <span class="comment"> /** A general method to change the sensor pose on the robot.</span> <a name="l00240"></a>00240 <span class="comment"> * Note that most sensors will use the full (6D) CPose3D, but see the derived classes for more details or special cases.</span> <a name="l00241"></a>00241 <span class="comment"> * \sa getSensorPose</span> <a name="l00242"></a>00242 <span class="comment"> */</span> <a name="l00243"></a><a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a25e8f59e7eb41650c51007371aed30c9">00243</a> <span class="keywordtype">void</span> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html#a25e8f59e7eb41650c51007371aed30c9" title="A general method to change the sensor pose on the robot.">setSensorPose</a>( <span class="keyword">const</span> <a class="code" href="classmrpt_1_1poses_1_1_c_pose3_d.html" title="A class used to store a 3D pose (a 3D translation + a rotation in 3D).">CPose3D</a> &newSensorPose ) { sensorPose = newSensorPose; } <a name="l00244"></a>00244 <a name="l00245"></a>00245 <span class="keywordtype">void</span> swap(<a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html" title="Declares a class derived from "CObservation" that encapsules a 3D range scan measurement (e...">CObservation3DRangeScan</a> &o); <span class="comment">//!< Very efficient method to swap the contents of two observations.</span> <a name="l00246"></a>00246 <span class="comment"></span> <a name="l00247"></a>00247 <span class="keywordtype">void</span> getZoneAsObs( <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html" title="Declares a class derived from "CObservation" that encapsules a 3D range scan measurement (e...">CObservation3DRangeScan</a> &obs, <span class="keyword">const</span> <span class="keywordtype">unsigned</span> <span class="keywordtype">int</span> &r1, <span class="keyword">const</span> <span class="keywordtype">unsigned</span> <span class="keywordtype">int</span> &r2, <span class="keyword">const</span> <span class="keywordtype">unsigned</span> <span class="keywordtype">int</span> &c1, <span class="keyword">const</span> <span class="keywordtype">unsigned</span> <span class="keywordtype">int</span> &c2 ); <a name="l00248"></a>00248 <span class="comment"></span> <a name="l00249"></a>00249 <span class="comment"> /** A Levenberg-Marquart-based optimizer to recover the calibration parameters of a 3D camera given a range (depth) image and the corresponding 3D point cloud.</span> <a name="l00250"></a>00250 <span class="comment"> * \param camera_offset The offset (in meters) in the +X direction of the point cloud. It's 1cm for SwissRanger SR4000.</span> <a name="l00251"></a>00251 <span class="comment"> * \return The final average reprojection error per pixel (typ <0.05 px)</span> <a name="l00252"></a>00252 <span class="comment"> */</span> <a name="l00253"></a>00253 <span class="keyword">static</span> <span class="keywordtype">double</span> recoverCameraCalibrationParameters( <a name="l00254"></a>00254 <span class="keyword">const</span> <a class="code" href="classmrpt_1_1slam_1_1_c_observation3_d_range_scan.html" title="Declares a class derived from "CObservation" that encapsules a 3D range scan measurement (e...">CObservation3DRangeScan</a> &in_obs, <a name="l00255"></a>00255 <a class="code" href="classmrpt_1_1utils_1_1_t_camera.html" title="Structure to hold the parameters of a pinhole camera model.">mrpt::utils::TCamera</a> &out_camParams, <a name="l00256"></a>00256 <span class="keyword">const</span> <span class="keywordtype">double</span> camera_offset = 0.01 ); <a name="l00257"></a>00257 <a name="l00258"></a>00258 <a name="l00259"></a>00259 }; <span class="comment">// End of class def.</span> <a name="l00260"></a>00260 <a name="l00261"></a>00261 <a name="l00262"></a>00262 } <span class="comment">// End of namespace</span> <a name="l00263"></a>00263 <a name="l00264"></a>00264 <span class="keyword">namespace </span>utils <a name="l00265"></a>00265 { <a name="l00266"></a>00266 <span class="keyword">using namespace </span>::mrpt::slam; <a name="l00267"></a>00267 <span class="comment">// Specialization must occur in the same namespace</span> <a name="l00268"></a>00268 <a class="code" href="_c_serializable_8h.html#a81695246461c7c04018786a6b6e75b6d">MRPT_DECLARE_TTYPENAME_PTR</a>(CObservation3DRangeScan) <a name="l00269"></a>00269 } <a name="l00270"></a>00270 <a name="l00271"></a>00271 } <span class="comment">// End of namespace</span> <a name="l00272"></a>00272 <a name="l00273"></a>00273 <span class="preprocessor">#endif</span> </pre></div></div> </div> <br><hr><br> <table border="0" width="100%"> <tr> <td> Page generated by <a href="http://www.doxygen.org" target="_blank">Doxygen 1.7.5</a> for MRPT 0.9.5 SVN: at Sun Sep 25 17:20:18 UTC 2011</td><td></td> <td width="100"> </td> <td width="150"> </td></tr> </table> </body></html>