SceneRecog.cpp
Go to the documentation of this file.
00001 /*********************************************************************
00002 *  Software License Agreement (BSD License)
00003 *  Copyright (c) 2013, Intelligent Robotics Lab, DLUT.
00004 *  All rights reserved.
00005 *  Author:Intelligent Robotics Lab, DLUT.
00006 *  Redistribution and use in source and binary forms, with or without
00007 *  modification, are permitted provided that the following conditions
00008 *  are met:
00009 *
00010 *   * Redistributions of source code must retain the above copyright
00011 *     notice, this list of conditions and the following disclaimer.
00012 *   * Redistributions in binary form must reproduce the above
00013 *     copyright notice, this list of conditions and the following
00014 *     disclaimer in the documentation and/or other materials provided
00015 *     with the distribution.
00016 *   * Neither the name of the Intelligent Robotics Lab nor the names of its
00017 *     contributors may be used to endorse or promote products derived
00018 *     from this software without specific prior written permission.
00019 *
00020 *  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
00021 *  "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
00022 *  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
00023 *  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
00024 *  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
00025 *  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
00026 *  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
00027 *  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
00028 *  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
00029 *  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
00030 *  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
00031 *  POSSIBILITY OF SUCH DAMAGE.
00032 *********************************************************************/
00033 #include <stdio.h>
00034 #include <fstream>
00035 #include <iostream>
00036 #include <ctype.h>
00037 #include <ctime>
00038 #include "SceneRecog.h"
00039 
00040 #include <ros/ros.h>
00041 
00042 CSceneRecog *p_plane_display = NULL;
00043 
00044 CSceneRecog::CSceneRecog ()
00045 {
00046   L_width_ = 0;
00047   L_height_ = 0;
00048   p_plane_display = this;
00049   plane_parameters_[0] = 0.0;
00050   plane_parameters_[1] = 0.0;
00051   plane_parameters_[2] = 0.0;
00052   plane_parameters_[3] = 0.0;
00053 
00054 }
00055 
00056 CSceneRecog::~CSceneRecog (void)
00057 {
00058 }
00059 
00060 void CSceneRecog::srProcess (std::vector < std::vector < CPoint3d > >&data)
00061 {
00062   laser_data_.swap (data);      // copy the data
00063   srPlaneExtract ();            // data processing
00064   srStructureExtract ();
00065 }
00066 
00067 void CSceneRecog::srPlaneExtract ()
00068 {
00069   CPoint3d PointInSquare[DIMEN][DIMEN];
00070   CPoint3d Mv;
00071   CPoint3d Nvec;
00072   int flagbuf;
00073   int pnum = -1;
00074   if (laser_data_.size () > 0)
00075   {
00076     L_width_ = (int) laser_data_.size ();
00077     L_height_ = (int) laser_data_[0].size ();
00078 
00079     std::vector < CPointTag > TagVector (L_height_);
00080     std::vector < std::vector < CPointTag > >PTV (L_width_, TagVector);
00081     point_tag_vector_.swap (PTV);
00082 
00083     for (int i = 0; i < L_width_ - DIMEN; i = i + 1)
00084     {
00085       for (int j = 0; j < L_height_ - DIMEN; j = j + 1)
00086       {
00087         Mv.x = Mv.y = Mv.z = 0.0;
00088         for (int k = 0; k < DIMEN; k++) //get the fitting small planes
00089           for (int l = 0; l < DIMEN; l++)
00090           {
00091             PointInSquare[k][l] = laser_data_[i + k][j + l];
00092             Mv.x += PointInSquare[k][l].x;
00093             Mv.y += PointInSquare[k][l].y;
00094             Mv.z += PointInSquare[k][l].z;
00095           }
00096         Mv.x = Mv.x / (DIMEN * DIMEN);  // calculate the barycenter of small planes
00097         Mv.y = Mv.y / (DIMEN * DIMEN);
00098         Mv.z = Mv.z / (DIMEN * DIMEN);
00099 
00100         if (srIsAPlane (PointInSquare, Mv))
00101         {
00102           Nvec =srNormalVec (laser_data_[i + DIMEN - 1][j + DIMEN - 1], laser_data_[i + DIMEN - 1][j],
00103                              laser_data_[i][j + DIMEN - 1], laser_data_[i][j]);
00104 
00105           flagbuf = -1;
00106           for (int f = 0; f <= DIMEN - 1; f++)
00107             for (int g = 0; g <= DIMEN - 1; g++)
00108             {
00109               if (point_tag_vector_[i + f][j + g].pflag != -1)
00110               {
00111                 flagbuf = point_tag_vector_[i + f][j + g].pflag;
00112                 break;
00113               }
00114             }
00115 
00116           if (flagbuf == -1)
00117           {
00118             pnum++;
00119             for (int m = 0; m < DIMEN; m++)
00120             {
00121               for (int n = 0; n < DIMEN; n++)
00122               {
00123                 point_tag_vector_[i + m][j + n].pflag = pnum;
00124               }
00125             }
00126             Plane pTag;
00127             pTag.VecNum = 1;
00128             pTag.VecSum = Nvec;
00129             pTag.VecAve = Nvec;
00130             pTag.MeanVal = Mv;
00131             pTag.MeanSum = Mv;
00132             plane_vector_.push_back (pTag);
00133           }
00134           //there are points coincided in adjacent cells
00135           else
00136           {
00137             if (srAngle (plane_vector_[flagbuf].VecAve, Nvec) < 0.2 /*4*M_PI/180 */ )
00138             {
00139               for (int m2 = 0; m2 < DIMEN; m2++)
00140                 for (int n2 = 0; n2 < DIMEN; n2++)
00141                 {
00142                   point_tag_vector_[i + m2][j + n2].pflag = flagbuf;
00143                 }
00144 
00145               plane_vector_[flagbuf].VecNum++;
00146               //calculate the sum of normals
00147               plane_vector_[flagbuf].VecSum.x += Nvec.x;
00148               plane_vector_[flagbuf].VecSum.y += Nvec.y;
00149               plane_vector_[flagbuf].VecSum.z += Nvec.z;
00150               //calculate the normals
00151               plane_vector_[flagbuf].VecAve.x = plane_vector_[flagbuf].VecSum.x / plane_vector_[flagbuf].VecNum;
00152               plane_vector_[flagbuf].VecAve.y = plane_vector_[flagbuf].VecSum.y / plane_vector_[flagbuf].VecNum;
00153               plane_vector_[flagbuf].VecAve.z = plane_vector_[flagbuf].VecSum.z / plane_vector_[flagbuf].VecNum;
00154               //calculate the sum of barycenter
00155               plane_vector_[flagbuf].MeanSum.x += Mv.x;
00156               plane_vector_[flagbuf].MeanSum.y += Mv.y;
00157               plane_vector_[flagbuf].MeanSum.z += Mv.z;
00158               //calculate the barycenter
00159               plane_vector_[flagbuf].MeanVal.x = plane_vector_[flagbuf].MeanSum.x / plane_vector_[flagbuf].VecNum;
00160               plane_vector_[flagbuf].MeanVal.y = plane_vector_[flagbuf].MeanSum.y / plane_vector_[flagbuf].VecNum;
00161               plane_vector_[flagbuf].MeanVal.z = plane_vector_[flagbuf].MeanSum.z / plane_vector_[flagbuf].VecNum;
00162             }
00163           }
00164         }
00165       }
00166     }
00167   }
00168 }
00169 
00170 void CSceneRecog::srStructureExtract () //recover scene frame in indoor scene
00171 {
00172 
00173   using namespace std;
00174 
00175   for (int i = 0; i < L_height_; i++)
00176   {
00177     for (int j = 0; j < L_width_; j++)
00178     {
00179       int flag = point_tag_vector_[j][i].pflag;
00180       if (flag >= 0)
00181       {
00182         CPointIndex index (i, j);
00183         plane_vector_[flag].InnerPoints.push_back (index);
00184       }
00185     }
00186   }
00187 
00188 
00189   // sort by plane size descending
00190   int PlaneNum = (int) plane_vector_.size ();
00191   for (int i = 0; i < PlaneNum - 1; i++)
00192   {
00193     int pmax = i;
00194     for (int j = i + 1; j < PlaneNum; j++)
00195     {
00196       if (plane_vector_[j].VecNum > plane_vector_[pmax].VecNum)
00197       {
00198         pmax = j;
00199       }
00200     }
00201     if (pmax != i)
00202       std::swap (plane_vector_[i], plane_vector_[pmax]);
00203   }
00204 /*
00205 for(int i = 0; i<PlaneNum; i++)
00206 {
00207         cout<< plane_vector_[i].VecNum<< "  ";
00208         if((i+1)%20 == 0) cout<<endl;
00209 }*/
00210 
00211 
00212   int iterate = 2;
00213   while (iterate-- > 1)
00214   {
00215     //concolidate planes
00216     int cnt = 0;
00217     vector < Plane > Planes;    //save the big plane
00218     vector < Plane > ExcludePlane;
00219     for (int i = 0; i < (int) plane_vector_.size (); i++)
00220     {
00221       cnt++;
00222       if (plane_vector_[i].VecNum < 4)
00223         break;
00224       // calculate the plane equation
00225       plane_vector_[i].A = plane_vector_[i].VecAve.x;
00226       plane_vector_[i].B = plane_vector_[i].VecAve.y;
00227       plane_vector_[i].C = plane_vector_[i].VecAve.z;
00228       plane_vector_[i].D = -(plane_vector_[i].A * plane_vector_[i].MeanVal.x 
00229                            + plane_vector_[i].B * plane_vector_[i].MeanVal.y 
00230                            + plane_vector_[i].C * plane_vector_[i].MeanVal.z);
00231       // consolidate planes to big planes
00232       bool flag = false;
00233       float angle;
00234       for (int j = 0; j < (int) Planes.size (); j++)
00235       {
00236         angle = srAngle (plane_vector_[i].VecAve, Planes[j].VecAve);
00237         angle = angle < (PI - angle) ? angle : (PI - angle);
00238         if (angle < 20 * PI / 180)
00239         {
00240           if (srP2Pl (plane_vector_[i].MeanVal, Planes[j]) < 0.1)
00241           {
00242             Planes[j].VecNum += plane_vector_[i].VecNum;
00243 
00244             //calculate the sum of normals
00245             Planes[j].VecSum += plane_vector_[i].VecSum;
00246 
00247             // calculate the normals
00248             Planes[j].VecAve.x = Planes[j].VecSum.x / Planes[j].VecNum;
00249             Planes[j].VecAve.y = Planes[j].VecSum.y / Planes[j].VecNum;
00250             Planes[j].VecAve.z = Planes[j].VecSum.z / Planes[j].VecNum;
00251 
00252             // calculate the sum of barycenters
00253             Planes[j].MeanSum += plane_vector_[i].MeanSum;
00254 
00255             // calculate the sum of barycenters
00256             Planes[j].MeanVal.x = Planes[j].MeanSum.x / Planes[j].VecNum;
00257             Planes[j].MeanVal.y = Planes[j].MeanSum.y / Planes[j].VecNum;
00258             Planes[j].MeanVal.z = Planes[j].MeanSum.z / Planes[j].VecNum;
00259 
00260             Planes[j].A = Planes[j].VecAve.x;
00261             Planes[j].B = Planes[j].VecAve.y;
00262             Planes[j].C = Planes[j].VecAve.z;
00263             Planes[j].D = -(Planes[j].A * Planes[j].MeanVal.x 
00264                           + Planes[j].B * Planes[j].MeanVal.y 
00265                           + Planes[j].C * Planes[j].MeanVal.z);
00266 
00267             int I = (int) plane_vector_[i].InnerPoints.size ();
00268             for (int k = 0; k < I; k++)
00269             {
00270               Planes[j].InnerPoints.push_back (plane_vector_[i].InnerPoints[k]);
00271             }
00272             flag = true;
00273             break;
00274           }
00275 
00276         }
00277       }
00278       // if any plane don't recruit this small plane
00279       if (!flag)
00280       {
00281         if ((int) Planes.size () < iterate * iterate * MAX_PLANE_NUM)
00282         {
00283           Plane ptemp;
00284           Planes.push_back (ptemp);
00285           std::swap (Planes[Planes.size () - 1], plane_vector_[i]);
00286         }
00287         else
00288         {
00289           Plane ptemp;
00290           ExcludePlane.push_back (ptemp);
00291           std::swap (ExcludePlane[ExcludePlane.size () - 1], plane_vector_[i]);
00292         }
00293       }
00294     }
00295     plane_vector_.swap (Planes);        //save the planes in the vector,and the first element is the biggest plane.
00296   }
00297   //find the boundary of every plane
00298   boundary_vec_.resize (plane_vector_.size ());
00299   for (int i = 0; i < (int) plane_vector_.size (); i++)
00300   {
00301     int flag = 0;
00302     boundary_vec_[i].push_back (plane_vector_[i].InnerPoints[0]);
00303     for (int j = 1; j < (int) plane_vector_[i].InnerPoints.size (); j++)
00304     {
00305       flag = 1;
00306       if (plane_vector_[i].InnerPoints[j - 1].i == plane_vector_[i].InnerPoints[j].i
00307           && plane_vector_[i].InnerPoints[j - 1].j + 1 == plane_vector_[i].InnerPoints[j].j)
00308         continue;
00309       else
00310       {
00311         boundary_vec_[i].push_back (plane_vector_[i].InnerPoints[j - 1]);
00312         boundary_vec_[i].push_back (plane_vector_[i].InnerPoints[j]);
00313         flag = 0;
00314       }
00315     }
00316     if (flag == 1)
00317       boundary_vec_[i].push_back (plane_vector_[i].InnerPoints.back ());
00318   }
00319 
00320   /*for(int i = 0; i<plane_vector_.size(); i++)
00321      {
00322      cout<< plane_vector_[i].InnerPoints.size()<< " --> "<< boundary_vec_[i].size()<< endl;
00323      } */
00324 
00325   // calculate the convex hull of every plane
00326   convex_vec_.resize (boundary_vec_.size ());
00327   for (int i = 0; i < (int) boundary_vec_.size (); i++)
00328   {
00329     int minidx = 0;
00330     for (int j = 1; j < (int) boundary_vec_[i].size (); j++)
00331     {
00332       if (boundary_vec_[i][j].i < boundary_vec_[i][minidx].i
00333           || (boundary_vec_[i][j].i == boundary_vec_[i][minidx].i
00334           && boundary_vec_[i][j].j < boundary_vec_[i][minidx].j))
00335         minidx = j;
00336     }
00337     if (minidx != 0)
00338       std::swap (boundary_vec_[i][0], boundary_vec_[i][minidx]);
00339 
00340     for (int j = 1; j < (int) boundary_vec_[i].size () - 1; j++)
00341     {
00342       int r = j;
00343       for (int k = j + 1; k < (int) boundary_vec_[i].size (); k++)
00344       {
00345         bool res = srCompL1R0bool (boundary_vec_[i][0], boundary_vec_[i][r], boundary_vec_[i][k]);
00346         if (res == 0)
00347           r = k;
00348       }
00349       if (r != j)
00350         std::swap (boundary_vec_[i][j], boundary_vec_[i][r]);
00351     }
00352 
00353     std::vector < CPointIndex > stack;
00354     stack.clear ();
00355     stack.push_back (boundary_vec_[i][0]);
00356     stack.push_back (boundary_vec_[i][1]);
00357     stack.push_back (boundary_vec_[i][2]);
00358 
00359     int top = 2;
00360     for (int j = 3; j < (int) boundary_vec_[i].size (); j++)
00361     {
00362       while (top >= 2 && srCross_Product (stack[top - 1], stack[top], boundary_vec_[i][j]) <= 0)
00363       {
00364         stack.pop_back ();
00365         top--;
00366       }
00367       stack.push_back (boundary_vec_[i][j]);
00368       top++;
00369     }
00370     convex_vec_[i].swap (stack);
00371   }
00372   /*
00373      for(int i = 0; i<boundary_vec_.size(); i++)
00374      {
00375      cout<< boundary_vec_[i].size() << " --> "<< boundary_vec_[i].size() << endl;
00376      }
00377    */
00378   plane_parameters_[0] = plane_vector_[0].A;
00379   plane_parameters_[1] = plane_vector_[0].B;
00380   plane_parameters_[2] = plane_vector_[0].C;
00381   plane_parameters_[3] = plane_vector_[0].D;
00382   //printf("%f,%f,%f,%f\n",planeparameters[0],planeparameters[1],planeparameters[2],planeparameters[3]);
00383 
00384   /*ofstream w("plane.txt");
00385      if (w.is_open())
00386      {
00387      printf("open the file ok\n");
00388      }
00389      else
00390      {
00391      printf("open the file fail\n");
00392      return 0 ;
00393      }
00394      for (int i = 0; i < plane_vector_[0].InnerPoints.size();i++)
00395      {
00396      int x = plane_vector_[0].InnerPoints[i].i;
00397      int y = plane_vector_[0].InnerPoints[i].j;
00398      w<<laser_data_[x][y].x<<"  "<<laser_data_[x][y].y<<"  "<<laser_data_[x][y].z<<"\n";
00399      }
00400      w.close(); */
00401 
00402   //return plane_parameters_;
00403 
00404 }
00405 
00406 float CSceneRecog::srPtopDistan (CPoint3d p1, CPoint3d p2)
00407 {
00408   return ((p1.x - p2.x) * (p1.x - p2.x) + (p1.y - p2.y) * (p1.y - p2.y) + (p1.z - p2.z) * (p1.z - p2.z));
00409 }
00410 
00411 bool CSceneRecog::srIsAPlane (CPoint3d p[][DIMEN], CPoint3d m)
00412 {
00413   CPoint3d Pzero (0, 0, 0);
00414   int n = 3, jt = 100;
00415   float cov[9] = { 0.0 };
00416   float s1, s2, s3, min;
00417   float eps = 0.01f;
00418   CPoint3d sum, ptemp;
00419   int zeronum = 0;
00420   bool booldis = true;
00421   float distemp, maxdis = 0.0;
00422 
00423   ptemp = p[0][0];
00424   for (int i = 0; i < DIMEN; i++)
00425   {
00426     for (int j = 1; j < DIMEN; j++)
00427     {
00428       if (Pzero == p[i][j])
00429       {
00430         zeronum++;
00431       }
00432       else
00433       {
00434         distemp = srPtopDistan (ptemp, p[i][j]);
00435         if (distemp > maxdis)
00436         {
00437           maxdis = distemp;
00438         }
00439         ptemp = p[i][j];
00440       }
00441     }
00442   }
00443 
00444   if (maxdis > MAXDISTH1 * MAXDISTH1)   // || zeronum>DIMEN                
00445   {
00446     booldis = false;
00447     return false;
00448   }
00449   for (int i = 0; i < DIMEN; i++)
00450   {
00451     for (int j = 0; j < DIMEN; j++)
00452     {
00453       float buf[3];
00454       buf[0] = p[i][j].x - m.x;
00455       buf[1] = p[i][j].y - m.y;
00456       buf[2] = p[i][j].z - m.z;
00457       for (int k = 0; k < 3; k++)
00458         for (int l = 0; l < 3; l++)
00459           if (!(p[i][j] == Pzero))
00460           {
00461             cov[k * 3 + l] += buf[k] * buf[l];
00462           }
00463     }
00464   }
00465   // calculate the covariance matrice eigenvalue
00466   srEigenValue (cov, n, eps, jt);
00467   s1 = fabs (cov[0]);
00468   s2 = fabs (cov[4]);
00469   s3 = fabs (cov[8]);
00470   min = s1 < s2 ? s1 : s2;
00471   min = s3 < min ? s3 : min;
00472 
00473   //compare the minimum of eigenvalue with threshold
00474   if (min < THRESH && zeronum < DIMEN && booldis)
00475     return true;
00476   return false;
00477 }
00478 
00479 int CSceneRecog::srEigenValue (float a[], int n, double eps, int jt)
00480 {
00481   int i, j, u, w, t, s, l;
00482   int p = 0;
00483   int q = 0;
00484   float fm, cn, sn, omega, x, y, d, v[30];
00485   l = 1;
00486   for (i = 0; i <= n - 1; i++)
00487   {
00488     v[i * n + i] = 1.0;
00489     for (j = 0; j <= n - 1; j++)
00490     {
00491       if (i != j)
00492       {
00493         v[i * n + j] = 0.0;
00494       }
00495     }
00496   }
00497   while (l == 1)
00498   {
00499     fm = 0.0;
00500     for (i = 0; i <= n - 1; i++)
00501     {
00502       for (j = 0; j <= n - 1; j++)
00503       {
00504         d = fabs (a[i * n + j]);
00505         if ((i != j) && (d > fm))
00506         {
00507           fm = d;
00508           p = i;
00509           q = j;
00510         }
00511       }
00512     }
00513     if (fm < eps)
00514     {
00515       return (1);
00516     }
00517     if (l > jt)
00518     {
00519       return (-1);
00520     }
00521     l = l + 1;
00522     u = p * n + q;
00523     w = p * n + p;
00524     t = q * n + p;
00525     s = q * n + q;
00526     x = -a[u];
00527     y = (a[s] - a[w]) / 2.0;
00528     omega = x / sqrt (x * x + y * y);
00529     if (y < 0.0)
00530     {
00531       omega = -omega;
00532     }
00533     sn = 1.0 + sqrt (1.0 - omega * omega);
00534     sn = omega / sqrt (2.0 * sn);
00535     cn = sqrt (1.0 - sn * sn);
00536     fm = a[w];
00537     a[w] = fm * cn * cn + a[s] * sn * sn + a[u] * omega;
00538     a[s] = fm * sn * sn + a[s] * cn * cn - a[u] * omega;
00539     a[u] = 0.0;
00540     a[t] = 0.0;
00541     for (j = 0; j <= n - 1; j++)
00542     {
00543       if ((j != p) && (j != q))
00544       {
00545         u = p * n + j;
00546         w = q * n + j;
00547         fm = a[u];
00548         a[u] = fm * cn + a[w] * sn;
00549         a[w] = -fm * sn + a[w] * cn;
00550       }
00551     }
00552     for (i = 0; i <= n - 1; i++)
00553     {
00554       if ((i != p) && (i != q))
00555       {
00556         u = i * n + p;
00557         w = i * n + q;
00558         fm = a[u];
00559         a[u] = fm * cn + a[w] * sn;
00560         a[w] = -fm * sn + a[w] * cn;
00561       }
00562     }
00563     for (i = 0; i <= n - 1; i++)
00564     {
00565       u = i * n + p;
00566       w = i * n + q;
00567       fm = v[u];
00568       v[u] = fm * cn + v[w] * sn;
00569       v[w] = -fm * sn + v[w] * cn;
00570     }
00571   }
00572   return 0;
00573 }
00574 
00575 CPoint3d CSceneRecog::srNormalVec (CPoint3d start1, CPoint3d end1, CPoint3d start2, CPoint3d end2)
00576 {
00577   float r1, r2;
00578   CPoint3d point1, point2, point;
00579   point1 = srVecMuti (start1, end1, start1, end2);
00580   point2 = srVecMuti (start2, end1, start2, end2);
00581   r1 = sqrt (point1.x * point1.x + point1.y * point1.y + point1.z * point1.z);
00582   r2 = sqrt (point2.x * point2.x + point2.y * point2.y + point2.z * point2.z);
00583   point.x = (point1.x / r1 + point2.x / r2) / 2;
00584   point.y = (point1.y / r1 + point2.y / r2) / 2;
00585   point.z = (point1.z / r1 + point2.z / r2) / 2;
00586   return point;
00587 }
00588 
00589 CPoint3d CSceneRecog::srVecMuti (CPoint3d start1, CPoint3d end1, CPoint3d start2, CPoint3d end2)
00590 {
00591   float x1, y1, z1;
00592   float x2, y2, z2;
00593   x1 = end1.x - start1.x;
00594   y1 = end1.y - start1.y;
00595   z1 = end1.z - start1.z;
00596   x2 = end2.x - start2.x;
00597   y2 = end2.y - start2.y;
00598   z2 = end2.z - start2.z;
00599   CPoint3d point;
00600   point.x = y1 * z2 - y2 * z1;
00601   point.y = x2 * z1 - x1 * z2;
00602   point.z = x1 * y2 - x2 * y1;
00603   return point;
00604 }
00605 
00606 float CSceneRecog::srAngle (CPoint3d vec1, CPoint3d vec2)
00607 {
00608   float x1, y1, z1, p1, p2, /*r1,r2, */ result, theta;
00609   x1 = vec1.x * vec2.x;
00610   y1 = vec1.y * vec2.y;
00611   z1 = vec1.z * vec2.z;
00612   p1 = vec1.x * vec1.x + vec1.y * vec1.y + vec1.z * vec1.z;
00613   p2 = vec2.x * vec2.x + vec2.y * vec2.y + vec2.z * vec2.z;
00614   result = (x1 + y1 + z1) / sqrt (p1 * p2);
00615   theta = acos (result);
00616   return theta;
00617 }
00618 
00619 float CSceneRecog::srP2Pl (CPoint3d m, const Plane & Plane)
00620 {
00621   float dist;
00622   dist = fabs (Plane.A * m.x + Plane.B * m.y + Plane.C * m.z + Plane.D);
00623   dist = dist / sqrt (Plane.A * Plane.A + Plane.B * Plane.B + Plane.C * Plane.C);
00624   return dist;
00625 }
00626 
00627 void CSceneRecog::srCalColor (int idx, std::vector < float >&rgb)
00628 {
00629   static int preidx = 1000;
00630   float step = 1;
00631   if (idx < 0)
00632   {
00633     rgb[0] = 0.5;
00634     rgb[1] = 0.5;
00635     rgb[2] = 0.5;
00636   }
00637   else if (idx != preidx)
00638   {
00639     float ratio = idx % 8;
00640     ratio = (1 - ratio / 8);
00641     switch (idx % 6)
00642     {
00643       case 0:
00644         rgb[0] = ratio * step;
00645         rgb[1] = 0;
00646         rgb[2] = 0;
00647         break;
00648       case 1:
00649         rgb[0] = 0;
00650         rgb[1] = ratio * step;
00651         rgb[2] = 0;
00652         break;
00653       case 2:
00654         rgb[0] = 0;
00655         rgb[1] = 0;
00656         rgb[2] = ratio * step;
00657         break;
00658       case 3:
00659         rgb[0] = ratio * step;
00660         rgb[1] = ratio * step;
00661         rgb[2] = 0;
00662         break;
00663       case 4:
00664         rgb[0] = ratio * step;
00665         rgb[1] = 0;
00666         rgb[2] = ratio * step;
00667         break;
00668       case 5:
00669         rgb[0] = 0;
00670         rgb[1] = ratio * step;
00671         rgb[2] = ratio * step;
00672         break;
00673     }
00674   }
00675   preidx = idx;
00676 }
00677 
00678 bool CSceneRecog::srCompL1R0bool (const CPointIndex & p1, const CPointIndex & p2, const CPointIndex & p3)
00679 {
00680   bool res = 1;
00681   int temp = (p2.j - p1.j) * (p3.i - p1.i) - (p2.i - p1.i) * (p3.j - p1.j);
00682   if (temp < 0)
00683     res = 0;
00684   else if (temp == 0)
00685   {
00686     int dist1 = (p2.i - p1.i) * (p2.i - p1.i) + (p2.j - p1.j) * (p2.j - p1.j);
00687     int dist2 = (p3.i - p1.i) * (p3.i - p1.i) + (p3.j - p1.j) * (p3.j - p1.j);
00688     if (dist1 > dist2)
00689       res = 0;
00690   }
00691   return res;
00692 }
00693 
00694 inline int CSceneRecog::srCross_Product (const CPointIndex & p1, const CPointIndex & p2, const CPointIndex & p3)
00695 {
00696   return (p2.j - p1.j) * (p3.i - p1.i) - (p2.i - p1.i) * (p3.j - p1.j);
00697 }


camera_laser_calibration
Author(s): Zhao Cilang,Yan Fei,Zhuang Yan/zhuang@dlut.edu.cn
autogenerated on Sun Jan 5 2014 11:05:02