ndt_frame_tools.h
Go to the documentation of this file.
00001 /*
00002  * Software License Agreement (BSD License)
00003  *
00004  *  Copyright (c) 2010, AASS Research Center, Orebro University.
00005  *  All rights reserved.
00006  *
00007  *  Redistribution and use in source and binary forms, with or without
00008  *  modification, are permitted provided that the following conditions
00009  *  are met:
00010  *
00011  *   * Redistributions of source code must retain the above copyright
00012  *     notice, this list of conditions and the following disclaimer.
00013  *   * Redistributions in binary form must reproduce the above
00014  *     copyright notice, this list of conditions and the following
00015  *     disclaimer in the documentation and/or other materials provided
00016  *     with the distribution.
00017  *   * Neither the name of AASS Research Center nor the names of its
00018  *     contributors may be used to endorse or promote products derived
00019  *     from this software without specific prior written permission.
00020  *
00021  *  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
00022  *  "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
00023  *  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
00024  *  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
00025  *  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
00026  *  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
00027  *  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
00028  *  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
00029  *  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
00030  *  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
00031  *  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
00032  *  POSSIBILITY OF SUCH DAMAGE.
00033  *
00034  */
00035 #ifndef NDTFRAMETOOLS_HH
00036 #define NDTFRAMETOOLS_HH
00037 
00038 //#include <ndt_feature_reg/NDTFrame.hh>
00039 #include <pcl/point_types.h>
00040 
00041 namespace ndt_feature_reg
00042 {
00043 template<class T> std::string toString (const T& x)
00044 {
00045     std::ostringstream o;
00046 
00047     if (!(o << x))
00048         throw std::runtime_error ("::toString()");
00049 
00050     return o.str ();
00051 }
00052 
00053 inline void scaleKeyPointSize(std::vector<cv::KeyPoint> &keypoints, const float &factor)
00054 {
00055     for( std::vector<cv::KeyPoint>::iterator i = keypoints.begin(), ie = keypoints.end(); i != ie; ++i )
00056     {
00057         i->size *= factor;
00058     }
00059 }
00060 
00061 inline void scaleKeyPointPosition(std::vector<cv::KeyPoint> &keypoints, const float &factor)
00062 {
00063     for( std::vector<cv::KeyPoint>::iterator i = keypoints.begin(), ie = keypoints.end(); i != ie; ++i )
00064     {
00065         i->pt.x *= factor;
00066         i->pt.y *= factor;
00067     }
00068 }
00069 
00070 /*
00071      inline void convertMatches(const std::vector<cv::DMatch> &in, std::vector<std::pair<int,int> > &out)
00072      {
00073           out.resize(in.size());
00074           for (size_t i = 0; i < in.size(); i++)
00075           {
00076                out[i].first = in[i].queryIdx;
00077                out[i].second = in[i].trainIdx;
00078           }
00079      }
00080 
00081      inline std::vector<std::pair<int,int> > convertMatches(const std::vector<cv::DMatch> &in)
00082      {
00083           std::vector<std::pair<int,int> > out;
00084           convertMatches(in,out);
00085           return out;
00086      }
00087 
00088      inline pcl::PointXYZRGB getPCLColor(int r, int g, int b)
00089      {
00090           pcl::PointXYZRGB ret;
00091           ret.r = r;
00092           ret.g = g;
00093           ret.b = b;
00094           return ret;
00095      }
00096 
00097      inline pcl::PointXYZRGB getPCLColor(size_t i)
00098      {
00099           pcl::PointXYZRGB ret;
00100 
00101           switch (i)
00102           {
00103           case 0:
00104                ret.r = 255; ret.g = 0; ret.b = 0;
00105                return ret;
00106           case 1:
00107                ret.r = 0; ret.g = 255; ret.b = 0;
00108                return ret;
00109           case 2:
00110                ret.r = 0; ret.g = 0; ret.b = 255;
00111                return ret;
00112           default:
00113                ret.r = 0; ret.g = 0; ret.b = 0;
00114           }
00115           return ret;
00116      }
00117 
00118      inline cv::Mat getCameraMatrix(double fx, double fy, double cx, double cy)
00119      {
00120           cv::Mat ret = cv::Mat::zeros(3,3, CV_64F);
00121           ret.at<double>(0,0) = fx;
00122           ret.at<double>(1,1) = fy;
00123           ret.at<double>(0,2) = cx;
00124           ret.at<double>(1,2) = cy;
00125           ret.at<double>(2,2) = 1.;
00126           return ret;
00127      }
00128 
00129      inline cv::Mat getDistVector(double d0, double d1, double d2, double d3, double d4)
00130      {
00131           cv::Mat ret = cv::Mat(5,1, CV_64F);
00132           ret.at<double>(0) = d0;
00133           ret.at<double>(1) = d1;
00134           ret.at<double>(2) = d2;
00135           ret.at<double>(3) = d3;
00136           ret.at<double>(4) = d4;
00137           return ret;
00138      }
00139 
00140      inline cv::Mat getDepthPointCloudLookUpTable(const cv::Size &size, const cv::Mat &camMat, const cv::Mat &distVec, const double &dsFactor)
00141      {
00142           cv::Mat pixels = cv::Mat(size.height * size.width,1, CV_64FC2);
00143           // Fill the tmp values simply with the image coordinates
00144 
00145           {
00146                cv::Mat_<cv::Vec2d> _I = pixels;
00147                size_t iter = 0;
00148                for (int y = 0; y < size.height; y++)
00149                {
00150                     for (int x = 0; x < size.width; x++)
00151                     {
00152                          _I(iter)[0] = x;
00153                          _I(iter)[1] = y;
00154                          iter++;
00155                     }
00156                }
00157           }
00158           cv::Mat normpixels = cv::Mat(pixels.size(), CV_64FC2); // normalized undistorted pixels
00159           cv::undistortPoints(pixels, normpixels, camMat, distVec);
00160 
00161           cv::Mat ret = cv::Mat(normpixels.size(), CV_64FC3); // "normpixelsxyz"
00162           {
00163                cv::Mat_<cv::Vec2d> _J = normpixels;
00164                cv::Mat_<cv::Vec3d> _I = ret;
00165                size_t iter = 0;
00166                for (int y = 0; y < size.height; y++)
00167                {
00168                     for (int x = 0; x < size.width; x++)
00169                     {
00170                          _I(iter)[0] = _J(iter)[0]*dsFactor;
00171                          _I(iter)[1] = _J(iter)[1]*dsFactor;
00172                          _I(iter)[2] = dsFactor;
00173                          iter++;
00174                     }
00175                }
00176           }
00177           return ret;
00178      }
00179 
00180      inline void colorKeyPointsInPointCloud(pcl::PointCloud<pcl::PointXYZRGB> &pc, const std::vector<std::vector<size_t> > &kptsIndices, const pcl::PointXYZRGB &color)
00181      {
00182           for (size_t i = 0; i < kptsIndices.size(); i++)
00183           {
00184                for (size_t j = 0; j < kptsIndices[i].size(); j++)
00185                {
00186                     pcl::PointXYZRGB& pt = (pc)[kptsIndices[i][j]];
00187                     pt.rgb = color.rgb;
00188                }
00189           }
00190      }
00191 
00192      inline void createColoredPointCloud(const cv::Mat &img, const pcl::PointCloud<pcl::PointXYZ> &pc, pcl::PointCloud<pcl::PointXYZRGB> &out)
00193      {
00194           // Assume 1 to 1 mapping...
00195           size_t width = pc.width;
00196           size_t height = pc.height;
00197           size_t size = pc.size();
00198           out.resize(size);
00199           out.width = width;
00200           out.height = height;
00201           out.is_dense = pc.is_dense;
00202 
00203           //      cv::Mat_<cv::Vec3b> _I = img;
00204           if (img.channels() == 1)
00205           {
00206                for (size_t i = 0; i < size; i++)
00207                {
00208                     out[i].x = pc[i].x;
00209                     out[i].y = pc[i].y;
00210                     out[i].z = pc[i].z;
00211                     out[i].r = img.data[i];
00212                     out[i].g = img.data[i];
00213                     out[i].b = img.data[i];
00214                }
00215           }
00216           if (img.channels() == 3)
00217           {
00218                for (size_t i = 0; i < size; i++)
00219                {
00220                     out[i].x = pc[i].x;
00221                     out[i].y = pc[i].y;
00222                     out[i].z = pc[i].z;
00223                     out[i].r = img.data[3*i];
00224                     out[i].g = img.data[3*i+1];
00225                     out[i].b = img.data[3*i+2];
00226                }
00227           }
00228      }
00229 */
00230 
00231 /*
00232      inline size_t convertDepthImageToPointCloud(const cv::Mat &depthImg, const cv::Mat &lookUpTable, pcl::PointCloud<pcl::PointXYZ> &pc)
00233      {
00234           if (depthImg.depth() != CV_16U)
00235                return 0;
00236           size_t width = depthImg.size().width;
00237           size_t height = depthImg.size().height;
00238           size_t size = width*height;
00239           if (pc.size() != size || pc.width != width || pc.height != height || pc.is_dense != true)
00240           {
00241                pc.resize(size);
00242                pc.is_dense = true;
00243                pc.width = width;
00244                pc.height = height;
00245           }
00246 
00247           cv::Mat_<cv::Vec3d> _I = lookUpTable;
00248 
00249           const double* plt = lookUpTable.ptr<double>(0);
00250           const unsigned short* pd = depthImg.ptr<unsigned short>(0);
00251           for (size_t i = 0; i < size; i++)
00252           {
00253                if (*pd == 0)
00254                {
00255                     float nan = std::numeric_limits<float>::quiet_NaN();
00256                     pc[i] = pcl::PointXYZ(nan,nan,nan);
00257                }
00258                else
00259                {
00260                     double depth = *pd;
00261                     pc[i] = pcl::PointXYZ(depth * _I(i)[0],
00262                                           depth * _I(i)[1],
00263                                           depth * _I(i)[2]);
00264                }
00265                pd++;
00266                plt += 3;
00267           }
00268           return size;
00269      }
00270 
00271 
00272      inline bool insideBoarder(const cv::KeyPoint &keyPoint, const pcl::PointCloud<pcl::PointXYZ> &in, int boarderSize)
00273      {
00274           int u = static_cast<int>(keyPoint.pt.x+0.5);
00275           int v = static_cast<int>(keyPoint.pt.y+0.5);
00276           if ((u >= boarderSize) &&
00277               (u < (int)in.width-boarderSize) &&
00278                (v >= boarderSize) && v <
00279                ((int)in.height-boarderSize))
00280                {
00281                     return true;
00282                }
00283               return false;
00284 
00285               }
00286 
00287      inline void selectIndicesAroundKeyPoint(const cv::KeyPoint &keyPoint, const pcl::PointCloud<pcl::PointXYZ> &in, int nbPoints, std::vector<size_t> &out)
00288      {
00289           int u = static_cast<int>(keyPoint.pt.x+0.5);
00290           int v = static_cast<int>(keyPoint.pt.y+0.5);
00291           int index = v * in.width + u;
00292           out.push_back(index);
00293           switch (nbPoints)
00294           {
00295           case 21:
00296           {
00297                if (insideBoarder(keyPoint, in, 3))
00298                {
00299                     out.push_back(index-3);
00300                     out.push_back(index+3);
00301                     out.push_back(index+3*in.width);
00302                     out.push_back(index-3*in.width);
00303                }
00304           }
00305           case 17:
00306           {
00307                if (insideBoarder(keyPoint, in, 2))
00308                {
00309                     out.push_back(index-in.width-2);
00310                     out.push_back(index-in.width+2);
00311                     out.push_back(index+in.width-2);
00312                     out.push_back(index+in.width+2);
00313                }
00314           }
00315           case 13:
00316           {
00317                if (insideBoarder(keyPoint, in, 2))
00318                {
00319                     out.push_back(index-2);
00320                     out.push_back(index+2);
00321                     out.push_back(index+2*in.width);
00322                     out.push_back(index-2*in.width);
00323                }
00324           }
00325           case 9:
00326           {
00327                if (insideBoarder(keyPoint, in, 1))
00328                {
00329                     out.push_back(index-in.width-1);
00330                     out.push_back(index-in.width+1);
00331                     out.push_back(index+in.width-1);
00332                     out.push_back(index+in.width+1);
00333                }
00334           }
00335           case 5:
00336           {
00337                if (insideBoarder(keyPoint, in, 1))
00338                {
00339                     out.push_back(index-1);
00340                     out.push_back(index+1);
00341                     out.push_back(index+in.width);
00342                     out.push_back(index-in.width);
00343                }
00344           }
00345           default:
00346                // Nothing
00347                break;
00348           }
00349      }
00350 */
00351 } // namespace
00352 
00353 #endif


ndt_feature_reg
Author(s): Henrik Andreasson, Todor Stoyanov, Jari Saarinen
autogenerated on Wed Aug 26 2015 15:25:07