Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • src/vector.cpp

    r7b36fe rb998c3  
    88#include "defs.hpp"
    99#include "helpers.hpp"
    10 #include "info.hpp"
    11 #include "gslmatrix.hpp"
     10#include "memoryallocator.hpp"
    1211#include "leastsquaremin.hpp"
    1312#include "log.hpp"
    14 #include "memoryallocator.hpp"
    1513#include "vector.hpp"
    1614#include "verbose.hpp"
    17 
    18 #include <gsl/gsl_linalg.h>
    19 #include <gsl/gsl_matrix.h>
    20 #include <gsl/gsl_permutation.h>
    21 #include <gsl/gsl_vector.h>
    2215
    2316/************************************ Functions for class vector ************************************/
     
    222215 * \param *Origin first vector of line
    223216 * \param *LineVector second vector of line
    224  * \return true -  \a this contains intersection point on return, false - line is parallel to plane (even if in-plane)
     217 * \return true -  \a this contains intersection point on return, false - line is parallel to plane
    225218 */
    226219bool Vector::GetIntersectionWithPlane(const Vector * const PlaneNormal, const Vector * const PlaneOffset, const Vector * const Origin, const Vector * const LineVector)
    227220{
    228   Info FunctionInfo(__func__);
    229221  double factor;
    230222  Vector Direction, helper;
     
    234226  Direction.SubtractVector(Origin);
    235227  Direction.Normalize();
    236   Log() << Verbose(1) << "INFO: Direction is " << Direction << "." << endl;
    237   //Log() << Verbose(1) << "INFO: PlaneNormal is " << *PlaneNormal << " and PlaneOffset is " << *PlaneOffset << "." << endl;
     228  //Log() << Verbose(4) << "INFO: Direction is " << Direction << "." << endl;
    238229  factor = Direction.ScalarProduct(PlaneNormal);
    239   if (fabs(factor) < MYEPSILON) { // Uniqueness: line parallel to plane?
    240     Log() << Verbose(1) << "BAD: Line is parallel to plane, no intersection." << endl;
     230  if (factor < MYEPSILON) { // Uniqueness: line parallel to plane?
     231    eLog() << Verbose(2) << "Line is parallel to plane, no intersection." << endl;
    241232    return false;
    242233  }
     
    244235  helper.SubtractVector(Origin);
    245236  factor = helper.ScalarProduct(PlaneNormal)/factor;
    246   if (fabs(factor) < MYEPSILON) { // Origin is in-plane
    247     Log() << Verbose(1) << "GOOD: Origin of line is in-plane." << endl;
     237  if (factor < MYEPSILON) { // Origin is in-plane
     238    //Log() << Verbose(2) << "Origin of line is in-plane, simple." << endl;
    248239    CopyVector(Origin);
    249240    return true;
     
    252243  Direction.Scale(factor);
    253244  CopyVector(Origin);
    254   Log() << Verbose(1) << "INFO: Scaled direction is " << Direction << "." << endl;
     245  //Log() << Verbose(4) << "INFO: Scaled direction is " << Direction << "." << endl;
    255246  AddVector(&Direction);
    256247
     
    259250  helper.SubtractVector(PlaneOffset);
    260251  if (helper.ScalarProduct(PlaneNormal) < MYEPSILON) {
    261     Log() << Verbose(1) << "GOOD: Intersection is " << *this << "." << endl;
     252    //Log() << Verbose(2) << "INFO: Intersection at " << *this << " is good." << endl;
    262253    return true;
    263254  } else {
     
    295286
    296287/** Calculates the intersection of the two lines that are both on the same plane.
    297  * This is taken from Weisstein, Eric W. "Line-Line Intersection." From MathWorld--A Wolfram Web Resource. http://mathworld.wolfram.com/Line-LineIntersection.html
     288 * We construct auxiliary plane with its vector normal to one line direction and the PlaneNormal, then a vector
     289 * from the first line's offset onto the plane. Finally, scale by factor is 1/cos(angle(line1,line2..)) = 1/SP(...), and
     290 * project onto the first line's direction and add its offset.
    298291 * \param *out output stream for debugging
    299292 * \param *Line1a first vector of first line
     
    306299bool Vector::GetIntersectionOfTwoLinesOnPlane(const Vector * const Line1a, const Vector * const Line1b, const Vector * const Line2a, const Vector * const Line2b, const Vector *PlaneNormal)
    307300{
    308   Info FunctionInfo(__func__);
    309 
    310   GSLMatrix *M = new GSLMatrix(4,4);
    311 
    312   M->SetAll(1.);
    313   for (int i=0;i<3;i++) {
    314     M->Set(0, i, Line1a->x[i]);
    315     M->Set(1, i, Line1b->x[i]);
    316     M->Set(2, i, Line2a->x[i]);
    317     M->Set(3, i, Line2b->x[i]);
    318   }
    319  
    320   //Log() << Verbose(1) << "Coefficent matrix is:" << endl;
    321   //for (int i=0;i<4;i++) {
    322   //  for (int j=0;j<4;j++)
    323   //    cout << "\t" << M->Get(i,j);
    324   //  cout << endl;
    325   //}
    326   if (fabs(M->Determinant()) > MYEPSILON) {
    327     Log() << Verbose(1) << "Determinant of coefficient matrix is NOT zero." << endl;
     301  bool result = true;
     302  Vector Direction, OtherDirection;
     303  Vector AuxiliaryNormal;
     304  Vector Distance;
     305  const Vector *Normal = NULL;
     306  Vector *ConstructedNormal = NULL;
     307  bool FreeNormal = false;
     308
     309  // construct both direction vectors
     310  Zero();
     311  Direction.CopyVector(Line1b);
     312  Direction.SubtractVector(Line1a);
     313  if (Direction.IsZero())
    328314    return false;
    329   }
    330   Log() << Verbose(1) << "INFO: Line1a = " << *Line1a << ", Line1b = " << *Line1b << ", Line2a = " << *Line2a << ", Line2b = " << *Line2b << "." << endl;
    331 
    332 
    333   // constuct a,b,c
    334   Vector a;
    335   Vector b;
    336   Vector c;
    337   Vector d;
    338   a.CopyVector(Line1b);
    339   a.SubtractVector(Line1a);
    340   b.CopyVector(Line2b);
    341   b.SubtractVector(Line2a);
    342   c.CopyVector(Line2a);
    343   c.SubtractVector(Line1a);
    344   d.CopyVector(Line2b);
    345   d.SubtractVector(Line1b);
    346   Log() << Verbose(1) << "INFO: a = " << a << ", b = " << b << ", c = " << c << "." << endl;
    347   if ((a.NormSquared() < MYEPSILON) || (b.NormSquared() < MYEPSILON)) {
    348    Zero();
    349    Log() << Verbose(1) << "At least one of the lines is ill-defined, i.e. offset equals second vector." << endl;
    350    return false;
    351   }
    352 
    353   // check for parallelity
    354   Vector parallel;
    355   double factor = 0.;
    356   if (fabs(a.ScalarProduct(&b)*a.ScalarProduct(&b)/a.NormSquared()/b.NormSquared() - 1.) < MYEPSILON) {
    357     parallel.CopyVector(Line1a);
    358     parallel.SubtractVector(Line2a);
    359     factor = parallel.ScalarProduct(&a)/a.Norm();
    360     if ((factor >= -MYEPSILON) && (factor - 1. < MYEPSILON)) {
    361       CopyVector(Line2a);
    362       Log() << Verbose(1) << "Lines conincide." << endl;
    363       return true;
     315  OtherDirection.CopyVector(Line2b);
     316  OtherDirection.SubtractVector(Line2a);
     317  if (OtherDirection.IsZero())
     318    return false;
     319
     320  Direction.Normalize();
     321  OtherDirection.Normalize();
     322
     323  //Log() << Verbose(4) << "INFO: Normalized Direction " << Direction << " and OtherDirection " << OtherDirection << "." << endl;
     324
     325  if (fabs(OtherDirection.ScalarProduct(&Direction) - 1.) < MYEPSILON) { // lines are parallel
     326    if ((Line1a == Line2a) || (Line1a == Line2b))
     327      CopyVector(Line1a);
     328    else if ((Line1b == Line2b) || (Line1b == Line2b))
     329        CopyVector(Line1b);
     330    else
     331      return false;
     332    Log() << Verbose(4) << "INFO: Intersection is " << *this << "." << endl;
     333    return true;
     334  } else {
     335    // check whether we have a plane normal vector
     336    if (PlaneNormal == NULL) {
     337      ConstructedNormal = new Vector;
     338      ConstructedNormal->MakeNormalVector(&Direction, &OtherDirection);
     339      Normal = ConstructedNormal;
     340      FreeNormal = true;
     341    } else
     342      Normal = PlaneNormal;
     343
     344    AuxiliaryNormal.MakeNormalVector(&OtherDirection, Normal);
     345    //Log() << Verbose(4) << "INFO: PlaneNormal is " << *Normal << " and AuxiliaryNormal " << AuxiliaryNormal << "." << endl;
     346
     347    Distance.CopyVector(Line2a);
     348    Distance.SubtractVector(Line1a);
     349    //Log() << Verbose(4) << "INFO: Distance is " << Distance << "." << endl;
     350    if (Distance.IsZero()) {
     351      // offsets are equal, match found
     352      CopyVector(Line1a);
     353      result = true;
    364354    } else {
    365       parallel.CopyVector(Line1a);
    366       parallel.SubtractVector(Line2b);
    367       factor = parallel.ScalarProduct(&a)/a.Norm();
    368       if ((factor >= -MYEPSILON) && (factor - 1. < MYEPSILON)) {
    369         CopyVector(Line2b);
    370         Log() << Verbose(1) << "Lines conincide." << endl;
    371         return true;
    372       }
     355      CopyVector(Distance.Projection(&AuxiliaryNormal));
     356      //Log() << Verbose(4) << "INFO: Projected Distance is " << *this << "." << endl;
     357      double factor = Direction.ScalarProduct(&AuxiliaryNormal);
     358      //Log() << Verbose(4) << "INFO: Scaling factor is " << factor << "." << endl;
     359      Scale(1./(factor*factor));
     360      //Log() << Verbose(4) << "INFO: Scaled Distance is " << *this << "." << endl;
     361      CopyVector(Projection(&Direction));
     362      //Log() << Verbose(4) << "INFO: Distance, projected into Direction, is " << *this << "." << endl;
     363      if (this->IsZero())
     364        result = false;
     365      else
     366        result = true;
     367      AddVector(Line1a);
    373368    }
    374     Log() << Verbose(1) << "Lines are parallel." << endl;
    375     Zero();
    376     return false;
    377   }
    378 
    379   // obtain s
    380   double s;
    381   Vector temp1, temp2;
    382   temp1.CopyVector(&c);
    383   temp1.VectorProduct(&b);
    384   temp2.CopyVector(&a);
    385   temp2.VectorProduct(&b);
    386   Log() << Verbose(1) << "INFO: temp1 = " << temp1 << ", temp2 = " << temp2 << "." << endl;
    387   if (fabs(temp2.NormSquared()) > MYEPSILON)
    388     s = temp1.ScalarProduct(&temp2)/temp2.NormSquared();
    389   else
    390     s = 0.;
    391   Log() << Verbose(1) << "Factor s is " << temp1.ScalarProduct(&temp2) << "/" << temp2.NormSquared() << " = " << s << "." << endl;
    392 
    393   // construct intersection
    394   CopyVector(&a);
    395   Scale(s);
    396   AddVector(Line1a);
    397   Log() << Verbose(1) << "Intersection is at " << *this << "." << endl;
    398 
    399   return true;
     369
     370    if (FreeNormal)
     371      delete(ConstructedNormal);
     372  }
     373  if (result)
     374    Log() << Verbose(4) << "INFO: Intersection is " << *this << "." << endl;
     375
     376  return result;
    400377};
    401378
Note: See TracChangeset for help on using the changeset viewer.