basic/geometry/geo_rangesensor/MgcContBox.cpp

Go to the documentation of this file.
00001 // Magic Software, Inc.
00002 // http://www.magic-software.com
00003 // Copyright (c) 2000, All Rights Reserved
00004 //
00005 // Source code from Magic Software is supplied under the terms of a license
00006 // agreement and may not be copied or disclosed except in accordance with the
00007 // terms of that agreement.  The various license agreements may be found at
00008 // the Magic Software web site.  This file is subject to the license
00009 //
00010 // FREE SOURCE CODE
00011 // http://www.magic-software.com/License.html/free.pdf
00012 
00013 #include "MgcContBox.h"
00014 #include "MgcGaussPointsFit.h"
00015 //#include "MgcQuaternion.h"
00016 
00017 //----------------------------------------------------------------------------
00018 /*void MgcContAlignedBox (int iQuantity, const MgcVector2* akPoint,
00019     MgcVector2& rkMin, MgcVector2& rkMax)
00020 {
00021     rkMin = akPoint[0];
00022     rkMax = rkMin;
00023 
00024     for (int i = 1; i < iQuantity; i++)
00025     {
00026         if ( akPoint[i].x < rkMin.x )
00027             rkMin.x = akPoint[i].x;
00028         else if ( akPoint[i].x > rkMax.x )
00029             rkMax.x = akPoint[i].x;
00030 
00031         if ( akPoint[i].y < rkMin.y )
00032             rkMin.y = akPoint[i].y;
00033         else if ( akPoint[i].y > rkMax.y )
00034             rkMax.y = akPoint[i].y;
00035     }
00036 }*/
00037 //----------------------------------------------------------------------------
00038 void MgcContAlignedBox (int iQuantity, const MgcVector3* akPoint,
00039     MgcVector3& rkMin, MgcVector3& rkMax)
00040 {
00041     rkMin = akPoint[0];
00042     rkMax = rkMin;
00043 
00044     for (int i = 1; i < iQuantity; i++)
00045     {
00046         if ( akPoint[i].x < rkMin.x )
00047             rkMin.x = akPoint[i].x;
00048         else if ( akPoint[i].x > rkMax.x )
00049             rkMax.x = akPoint[i].x;
00050 
00051         if ( akPoint[i].y < rkMin.y )
00052             rkMin.y = akPoint[i].y;
00053         else if ( akPoint[i].y > rkMax.y )
00054             rkMax.y = akPoint[i].y;
00055 
00056         if ( akPoint[i].z < rkMin.z )
00057             rkMin.z = akPoint[i].z;
00058         else if ( akPoint[i].z > rkMax.z )
00059             rkMax.z = akPoint[i].z;
00060     }
00061 }
00062 //----------------------------------------------------------------------------
00063 /*MgcBox2 MgcContOrientedBox (int iQuantity, const MgcVector2* akPoint)
00064 {
00065     MgcBox2 kBox;
00066 
00067     MgcGaussPointsFit(iQuantity,akPoint,kBox.Center(),kBox.Axes(),
00068         kBox.Extents());
00069 
00070     // Let C be the box center and let U0 and U1 be the box axes.  Each input
00071     // point is of the form X = C + y0*U0 + y1*U1.  The following code
00072     // computes min(y0), max(y0), min(y1), and max(y1).  The box center is
00073     // then adjusted to be
00074     //   C' = C + 0.5*(min(y0)+max(y0))*U0 + 0.5*(min(y1)+max(y1))*U1
00075 
00076     MgcVector2 kDiff = akPoint[0] - kBox.Center();
00077     MgcReal fY0Min = kDiff.Dot(kBox.Axis(0)), fY0Max = fY0Min;
00078     MgcReal fY1Min = kDiff.Dot(kBox.Axis(1)), fY1Max = fY1Min;
00079 
00080     for (int i = 1; i < iQuantity; i++)
00081     {
00082         kDiff = akPoint[i] - kBox.Center();
00083 
00084         MgcReal fY0 = kDiff.Dot(kBox.Axis(0));
00085         if ( fY0 < fY0Min )
00086             fY0Min = fY0;
00087         else if ( fY0 > fY0Max )
00088             fY0Max = fY0;
00089 
00090         MgcReal fY1 = kDiff.Dot(kBox.Axis(1));
00091         if ( fY1 < fY1Min )
00092             fY1Min = fY1;
00093         else if ( fY1 > fY1Max )
00094             fY1Max = fY1;
00095     }
00096 
00097     kBox.Center() += (0.5*(fY0Min+fY0Max))*kBox.Axis(0) +
00098         (0.5*(fY1Min+fY1Max))*kBox.Axis(1);
00099 
00100     kBox.Extent(0) = 0.5*(fY0Max - fY0Min);
00101     kBox.Extent(1) = 0.5*(fY1Max - fY1Min);
00102 
00103     return kBox;
00104 }*/
00105 //----------------------------------------------------------------------------
00106 MgcBox3 MgcContOrientedBox (int iQuantity, const MgcVector3* akPoint)
00107 {
00108     MgcBox3 kBox;
00109 
00110     MgcGaussPointsFit(iQuantity,akPoint,kBox.Center(),kBox.Axes(),
00111         kBox.Extents());
00112 
00113     // Let C be the box center and let U0, U1, and U2 be the box axes.  Each
00114     // input point is of the form X = C + y0*U0 + y1*U1 + y2*U2.  The
00115     // following code computes min(y0), max(y0), min(y1), max(y1), min(y2),
00116     // and max(y2).  The box center is then adjusted to be
00117     //   C' = C + 0.5*(min(y0)+max(y0))*U0 + 0.5*(min(y1)+max(y1))*U1 +
00118     //        0.5*(min(y2)+max(y2))*U2
00119 
00120     MgcVector3 kDiff = akPoint[0] - kBox.Center();
00121     MgcReal fY0Min = kDiff.Dot(kBox.Axis(0)), fY0Max = fY0Min;
00122     MgcReal fY1Min = kDiff.Dot(kBox.Axis(1)), fY1Max = fY1Min;
00123     MgcReal fY2Min = kDiff.Dot(kBox.Axis(2)), fY2Max = fY2Min;
00124 
00125     for (int i = 1; i < iQuantity; i++)
00126     {
00127         kDiff = akPoint[i] - kBox.Center();
00128 
00129         MgcReal fY0 = kDiff.Dot(kBox.Axis(0));
00130         if ( fY0 < fY0Min )
00131             fY0Min = fY0;
00132         else if ( fY0 > fY0Max )
00133             fY0Max = fY0;
00134 
00135         MgcReal fY1 = kDiff.Dot(kBox.Axis(1));
00136         if ( fY1 < fY1Min )
00137             fY1Min = fY1;
00138         else if ( fY1 > fY1Max )
00139             fY1Max = fY1;
00140 
00141         MgcReal fY2 = kDiff.Dot(kBox.Axis(2));
00142         if ( fY2 < fY2Min )
00143             fY2Min = fY2;
00144         else if ( fY2 > fY2Max )
00145             fY2Max = fY2;
00146     }
00147 
00148     kBox.Center() += (0.5*(fY0Min+fY0Max))*kBox.Axis(0) +
00149         (0.5*(fY1Min+fY1Max))*kBox.Axis(1) +
00150         (0.5*(fY2Min+fY2Max))*kBox.Axis(2);
00151 
00152     kBox.Extent(0) = 0.5*(fY0Max - fY0Min);
00153     kBox.Extent(1) = 0.5*(fY1Max - fY1Min);
00154     kBox.Extent(2) = 0.5*(fY2Max - fY2Min);
00155 
00156     return kBox;
00157 }
00158 //----------------------------------------------------------------------------
00159 /*bool MgcContOrientedBox (int iQuantity, const MgcVector2* akPoint,
00160     const bool* abValid, MgcBox2& rkBox)
00161 {
00162     if ( !MgcGaussPointsFit(iQuantity,akPoint,abValid,rkBox.Center(),
00163          rkBox.Axes(),rkBox.Extents()) )
00164     {
00165         return false;
00166     }
00167 
00168     // Let C be the box center and let U0 and U1 be the box axes.  Each input
00169     // point is of the form X = C + y0*U0 + y1*U1.  The following code
00170     // computes min(y0), max(y0), min(y1), and max(y1).  The box center is
00171     // then adjusted to be
00172     //   C' = C + 0.5*(min(y0)+max(y0))*U0 + 0.5*(min(y1)+max(y1))*U1
00173 
00174     // get first valid vertex
00175     MgcVector2 kDiff;
00176     MgcReal fY0Min, fY0Max, fY1Min, fY1Max;
00177     int i;
00178     for (i = 0; i < iQuantity; i++)
00179     {
00180         if ( abValid[i] )
00181         {
00182             kDiff = akPoint[i] - rkBox.Center();
00183             fY0Min = kDiff.Dot(rkBox.Axis(0));
00184             fY0Max = fY0Min;
00185             fY1Min = kDiff.Dot(rkBox.Axis(1));
00186             fY1Max = fY1Min;
00187             break;
00188         }
00189     }
00190 
00191     for (i++; i < iQuantity; i++)
00192     {
00193         if ( abValid[i] )
00194         {
00195             kDiff = akPoint[i] - rkBox.Center();
00196 
00197             MgcReal fY0 = kDiff.Dot(rkBox.Axis(0));
00198             if ( fY0 < fY0Min )
00199                 fY0Min = fY0;
00200             else if ( fY0 > fY0Max )
00201                 fY0Max = fY0;
00202 
00203             MgcReal fY1 = kDiff.Dot(rkBox.Axis(1));
00204             if ( fY1 < fY1Min )
00205                 fY1Min = fY1;
00206             else if ( fY1 > fY1Max )
00207                 fY1Max = fY1;
00208         }
00209     }
00210 
00211     rkBox.Center() += (0.5*(fY0Min+fY0Max))*rkBox.Axis(0)
00212         + (0.5*(fY1Min+fY1Max))*rkBox.Axis(1);
00213 
00214     rkBox.Extent(0) = 0.5*(fY0Max - fY0Min);
00215     rkBox.Extent(1) = 0.5*(fY1Max - fY1Min);
00216 
00217     return true;
00218 }*/
00219 //----------------------------------------------------------------------------
00220 /*bool MgcContOrientedBox (int iQuantity, const MgcVector3* akPoint,
00221     const bool* abValid, MgcBox3& rkBox)
00222 {
00223     if ( !MgcGaussPointsFit(iQuantity,akPoint,abValid,rkBox.Center(),
00224          rkBox.Axes(),rkBox.Extents()) )
00225     {
00226         return false;
00227     }
00228 
00229     // Let C be the box center and let U0, U1, and U2 be the box axes.  Each
00230     // input point is of the form X = C + y0*U0 + y1*U1 + y2*U2.  The
00231     // following code computes min(y0), max(y0), min(y1), max(y1), min(y2),
00232     // and max(y2).  The box center is then adjusted to be
00233     //   C' = C + 0.5*(min(y0)+max(y0))*U0 + 0.5*(min(y1)+max(y1))*U1 +
00234     //        0.5*(min(y2)+max(y2))*U2
00235 
00236     // get first valid vertex
00237     MgcVector3 kDiff;
00238     MgcReal fY0Min, fY0Max, fY1Min, fY1Max, fY2Min, fY2Max;
00239     int i;
00240     for (i = 0; i < iQuantity; i++)
00241     {
00242         if ( abValid[i] )
00243         {
00244             kDiff = akPoint[i] - rkBox.Center();
00245             fY0Min = kDiff.Dot(rkBox.Axis(0));
00246             fY0Max = fY0Min;
00247             fY1Min = kDiff.Dot(rkBox.Axis(1));
00248             fY1Max = fY1Min;
00249             fY2Min = kDiff.Dot(rkBox.Axis(2));
00250             fY2Max = fY2Min;
00251             break;
00252         }
00253     }
00254 
00255     for (i++; i < iQuantity; i++)
00256     {
00257         if ( abValid[i] )
00258         {
00259             kDiff = akPoint[i] - rkBox.Center();
00260 
00261             MgcReal fY0 = kDiff.Dot(rkBox.Axis(0));
00262             if ( fY0 < fY0Min )
00263                 fY0Min = fY0;
00264             else if ( fY0 > fY0Max )
00265                 fY0Max = fY0;
00266 
00267             MgcReal fY1 = kDiff.Dot(rkBox.Axis(1));
00268             if ( fY1 < fY1Min )
00269                 fY1Min = fY1;
00270             else if ( fY1 > fY1Max )
00271                 fY1Max = fY1;
00272 
00273             MgcReal fY2 = kDiff.Dot(rkBox.Axis(2));
00274             if ( fY2 < fY2Min )
00275                 fY2Min = fY2;
00276             else if ( fY2 > fY2Max )
00277                 fY2Max = fY2;
00278         }
00279     }
00280 
00281     rkBox.Center() += (0.5*(fY0Min+fY0Max))*rkBox.Axis(0)
00282         + (0.5*(fY1Min+fY1Max))*rkBox.Axis(1) +
00283         (0.5*(fY2Min+fY2Max))*rkBox.Axis(2);
00284 
00285     rkBox.Extent(0) = 0.5*(fY0Max - fY0Min);
00286     rkBox.Extent(1) = 0.5*(fY1Max - fY1Min);
00287     rkBox.Extent(2) = 0.5*(fY2Max - fY2Min);
00288 
00289     return true;
00290 }
00291 //----------------------------------------------------------------------------
00292 MgcBox3 MgcMergeBoxes (const MgcBox3& rkBox0, const MgcBox3& rkBox1)
00293 {
00294     MgcBox3 kBox;
00295     kBox.Center() = 0.5*(rkBox0.Center() + rkBox1.Center());
00296 
00297     MgcQuaternion kQ0, kQ1;
00298     kQ0.FromAxes(rkBox0.Axes());
00299     kQ1.FromAxes(rkBox1.Axes());
00300     if ( kQ0.Dot(kQ1) < 0.0 )
00301         kQ1 = -kQ1;
00302 
00303     MgcQuaternion kQ = kQ0 + kQ1;
00304     MgcReal fInvLength = 1.0/MgcMath::Sqrt(kQ.Norm());
00305     kQ = fInvLength*kQ;
00306     kQ.ToAxes(kBox.Axes());
00307 
00308     int i, j;
00309     MgcVector3 akVertex[8], kDiff;
00310     MgcReal fADot;
00311 
00312     kBox.Extent(0) = 0.0;
00313     kBox.Extent(1) = 0.0;
00314     kBox.Extent(2) = 0.0;
00315 
00316     rkBox0.ComputeVertices(akVertex);
00317     for (i = 0; i < 8; i++)
00318     {
00319         kDiff = akVertex[i] - kBox.Center();
00320         for (j = 0; j < 3; j++)
00321         {
00322             fADot = MgcMath::Abs(kDiff.Dot(rkBox0.Axis(j)));
00323             if ( fADot > kBox.Extent(j) )
00324                 kBox.Extent(j) = fADot;
00325         }
00326     }
00327 
00328     rkBox1.ComputeVertices(akVertex);
00329     for (i = 0; i < 8; i++)
00330     {
00331         kDiff = akVertex[i] - kBox.Center();
00332         for (j = 0; j < 3; j++)
00333         {
00334             fADot = MgcMath::Abs(kDiff.Dot(rkBox1.Axis(j)));
00335             if ( fADot > kBox.Extent(j) )
00336                 kBox.Extent(j) = fADot;
00337         }
00338     }
00339 
00340     return kBox;
00341 }*/
00342 //----------------------------------------------------------------------------

Generated on Sat Apr 1 21:30:31 2006 for Motion Planning Kernel by  doxygen 1.4.6-NO