Tekkotsu Homepage
Demos
Overview
Downloads
Dev. Resources
Reference
Credits

TargetData.cc

Go to the documentation of this file.
00001 //-*-c++-*-
00002 
00003 #include "BaseData.h"    // superclass
00004 #include "Point.h"       // Point data member
00005 #include "ShapeTypes.h"  // TargetDataType
00006 
00007 #include "SketchSpace.h"
00008 #include "Sketch.h"
00009 #include "visops.h"
00010 
00011 #include "ShapeSpace.h"  // required by DATASTUFF_CC
00012 #include "ShapeRoot.h"   // required by DATASTUFF_CC
00013 
00014 #include "TargetData.h"
00015 #include "ShapeTarget.h"
00016 
00017 #include "BlobData.h"
00018 #include "ShapeBlob.h"
00019 #include "VRmixin.h"
00020 
00021 using namespace std;
00022 
00023 namespace DualCoding {
00024 
00025 TargetData::TargetData(ShapeSpace& _space, const EndPoint &_frontLeftPt, const EndPoint &_frontRightPt, const EndPoint &_backLeftPt, const EndPoint &_backRightPt, const EndPoint &_frontIntersect, const EndPoint &_backIntersect, const float _height)
00026                      : BaseData(_space, getStaticType()),
00027                        frontLine(_space, _frontLeftPt, _frontRightPt),
00028                        backLine(_space, _backLeftPt, _backRightPt),
00029                        frontValid((_frontLeftPt != Point(0, 0, 0)) && (_frontRightPt != Point(0, 0, 0))),
00030                        backValid((_backLeftPt != Point(0, 0, 0)) && (_backRightPt != Point(0, 0, 0))),
00031                        frontIntersect(_frontIntersect),
00032                        backIntersect(_backIntersect),
00033                        orientation(0),
00034                        length(0),
00035                        width(0),
00036                        height(_height) {
00037   update_derived_properties();
00038 }
00039 
00040 DATASTUFF_CC(TargetData);
00041 
00042 BoundingBox2D TargetData::getBoundingBox() const {
00043   BoundingBox2D result(frontLine.getBoundingBox());
00044   result.expand(backLine.getBoundingBox());
00045   return result;
00046 }
00047 
00048 bool TargetData::isMatchFor(const ShapeRoot& other) const {
00049   if (!(isSameTypeAs(other) && isSameColorAs(other))) {
00050     return false;
00051   }
00052   else {
00053     const Shape<TargetData>& other_target = ShapeRootTypeConst(other,TargetData);
00054     return isMatchFor(other_target.getData());
00055   }
00056 }
00057 
00058 bool TargetData::isMatchFor(const TargetData& other_target) const {
00059   // 2 targets match if either of their lines match
00060   if (frontValid && !frontLine.isMatchFor(other_target.frontLine) && backValid && !backLine.isMatchFor(other_target.backLine))
00061     return false;
00062   return true;
00063 }
00064 
00065 void TargetData::update_derived_properties() {
00066   EndPoint &frontLeftPt  = getFrontLeftPt();
00067   EndPoint &frontRightPt = getFrontRightPt();
00068   EndPoint &backLeftPt   = getBackLeftPt();
00069   EndPoint &backRightPt  = getBackRightPt();
00070   
00071   // Determine if the front and back lines are valid
00072   frontValid  = true;
00073   backValid   = true;
00074   if ((frontLeftPt == Point(0, 0, 0)) || (frontRightPt == Point(0, 0, 0))) {
00075     frontValid = false;
00076   }
00077   if ((backLeftPt == Point(0, 0, 0)) || (backRightPt == Point(0, 0, 0))) {
00078     backValid = false;
00079   }
00080   if (frontValid && backValid && (getRefFrameType() != camcentric)) {
00081     // Lines should not be in the negative z plane
00082     if (frontLine.getCentroid().coordZ() < 0) {
00083       frontValid = false;
00084     }
00085     if (backLine.getCentroid().coordZ() < 0) {
00086       backValid = false;
00087     }
00088     // Remove short lines if the other line is long
00089     if ((frontLine.getLength() < 50.0f) && backValid && (backLine.getLength() > 50.0f)) {
00090       frontValid = false;
00091     }
00092     else if ((backLine.getLength() < 50.0f) && frontValid && (frontLine.getLength() > 50.0f)) {
00093       backValid = false;
00094     }
00095   }
00096   
00097   // Reset the front/back lines if they are invalid
00098   if (!frontValid) {
00099     frontLeftPt  = Point(0, 0, 0);
00100     frontRightPt = Point(0, 0, 0);
00101     frontLeftPt.setValid(false);
00102     frontRightPt.setValid(false);
00103     frontLine.update_derived_properties();
00104     
00105     frontIntersect = Point(0, 0, 0);
00106     frontIntersect.setValid(false);
00107   }
00108   if (!backValid) {
00109     backLeftPt  = Point(0, 0, 0);
00110     backRightPt = Point(0, 0, 0);
00111     backLeftPt.setValid(false);
00112     backRightPt.setValid(false);
00113     backLine.update_derived_properties();
00114     
00115     backIntersect = Point(0, 0, 0);
00116     backIntersect.setValid(false);
00117   }
00118   
00119   // Determine if the front/back intersection points are valid
00120   if (frontIntersect == Point(0, 0, 0)) {
00121     frontIntersect.setValid(false);
00122   }
00123   if (backIntersect == Point(0, 0, 0)) {
00124     backIntersect.setValid(false);
00125   }
00126   
00127   // Check left/right points based on intersection points
00128   if (frontIntersect.isValid() || backIntersect.isValid()) {
00129     if (frontIntersect.isValid()) {
00130       bool swap = false;
00131       
00132       // The right point will be closer to the intersection if both points are valid/invalid
00133       if (frontValid && (frontLeftPt.isValid() == frontRightPt.isValid())
00134        && (frontLeftPt.distanceFrom(frontIntersect) < frontRightPt.distanceFrom(frontIntersect))) {
00135         swap = true;
00136       }
00137       // Assumption: the right point will be the valid point otherwise
00138       else if (frontValid && frontLeftPt.isValid() && !frontRightPt.isValid()) {
00139         swap = true;
00140       }
00141       
00142       
00143       if (swap) {
00144         // Front left and right are reversed
00145         EndPoint temp = frontLeftPt;
00146         frontLeftPt = frontRightPt;
00147         frontRightPt = temp;
00148         frontLine.update_derived_properties();
00149       }
00150       
00151       // If back intersection is invalid, then determine back left/right based on distance from front left/right
00152       if (backValid && !backIntersect.isValid()) {
00153         float leftMax  = max(frontLeftPt.distanceFrom(backLeftPt), frontRightPt.distanceFrom(backLeftPt));
00154         float rightMax = max(frontLeftPt.distanceFrom(backRightPt), frontRightPt.distanceFrom(backRightPt));
00155         
00156         // Look at the point that's further away
00157         swap = false;
00158         if (leftMax > rightMax) {
00159           if (frontLeftPt.distanceFrom(backLeftPt) > frontRightPt.distanceFrom(backLeftPt)) {
00160             swap = true;
00161           }
00162         }
00163         else {
00164           if (frontRightPt.distanceFrom(backRightPt) > frontLeftPt.distanceFrom(backRightPt)) {
00165             swap = true;
00166           }
00167         }
00168         
00169         if (swap) {
00170           // Back left and right are reversed
00171           EndPoint temp = backLeftPt;
00172           backLeftPt = backRightPt;
00173           backRightPt = temp;
00174           backLine.update_derived_properties();
00175         }
00176       }
00177     }
00178     if (backIntersect.isValid()) {
00179       bool swap = false;
00180       
00181       // The right point will be closer to the intersection if both points are valid/invalid
00182       if (backValid && (backLeftPt.isValid() == backRightPt.isValid())
00183        && (backLeftPt.distanceFrom(backIntersect) < backRightPt.distanceFrom(backIntersect))) {
00184         swap = true;
00185       }
00186       // Assumption: the right point will be the valid point otherwise
00187       else if (backValid && backLeftPt.isValid() && !backRightPt.isValid()) {
00188         swap = true;
00189       }
00190       
00191       
00192       if (swap) {
00193         // Back left and right are reversed
00194         EndPoint temp = backLeftPt;
00195         backLeftPt = backRightPt;
00196         backRightPt = temp;
00197         backLine.update_derived_properties();
00198       }
00199       
00200       // If front intersection is invalid, then determine front left/right based on distance from back left/right
00201       if (frontValid && !frontIntersect.isValid()) {
00202         float leftMax  = max(backLeftPt.distanceFrom(frontLeftPt), backRightPt.distanceFrom(frontLeftPt));
00203         float rightMax = max(backLeftPt.distanceFrom(frontRightPt), backRightPt.distanceFrom(frontRightPt));
00204         
00205         // Look at the point that's further away
00206         swap = false;
00207         if (leftMax > rightMax) {
00208           if (backLeftPt.distanceFrom(frontLeftPt) > backRightPt.distanceFrom(frontLeftPt)) {
00209             swap = true;
00210           }
00211         }
00212         else {
00213           if (backRightPt.distanceFrom(frontRightPt) > backLeftPt.distanceFrom(frontRightPt)) {
00214             swap = true;
00215           }
00216         }
00217         
00218         if (swap) {
00219           // Front left and right are reversed
00220           EndPoint temp = frontLeftPt;
00221           frontLeftPt = frontRightPt;
00222           frontRightPt = temp;
00223           frontLine.update_derived_properties();
00224         }
00225       }
00226     }
00227   }
00228   
00229   float front_dx = frontRightPt.coordX() - frontLeftPt.coordX();
00230   float front_dy = frontRightPt.coordY() - frontLeftPt.coordY();
00231   float back_dx  = backRightPt.coordX() - backLeftPt.coordX();
00232   float back_dy  = backRightPt.coordY() - backLeftPt.coordY();
00233   
00234   if (frontValid && backValid) {
00235     // Calculate the length/width
00236     length = max(frontLine.getLength(), backLine.getLength());
00237     width  = max(frontLine.perpendicularDistanceFrom( backLine.getCentroid() ), backLine.perpendicularDistanceFrom( frontLine.getCentroid() ));
00238 
00239     // Calculate the orientation based on the front and back line
00240     AngSignPi front_orientation = AngSignPi(std::atan2(front_dy, front_dx) + (direction_t)M_PI / 2);
00241     AngSignPi back_orientation  = AngSignPi(std::atan2(back_dy, back_dx) + (direction_t)M_PI / 2);
00242     
00243     // Check left/right of line by coming up with a point that's 1000mm away,
00244     // and if the point is closer to the other line, then orientation should be flipped
00245     float dist = 1000.0f;
00246     Point frontPt( getCentroid().coordX() + dist * cos(front_orientation), getCentroid().coordY() + dist * sin(front_orientation), getCentroid().coordZ() );
00247     if ((width > 50.0f) && (frontLine.perpendicularDistanceFrom( frontPt ) > backLine.perpendicularDistanceFrom( frontPt ))) {
00248       // Front left and right are reversed
00249       EndPoint temp = frontLeftPt;
00250       frontLeftPt = frontRightPt;
00251       frontRightPt = temp;
00252       frontLine.update_derived_properties();
00253       
00254       front_dx = frontRightPt.coordX() - frontLeftPt.coordX();
00255       front_dy = frontRightPt.coordY() - frontLeftPt.coordY();
00256       front_orientation = AngSignPi(std::atan2(front_dy, front_dx) + (direction_t)M_PI / 2);
00257     }
00258     
00259     Point backPt( getBackCentroid().coordX() - dist * cos(back_orientation), getBackCentroid().coordY() - dist * sin(back_orientation), getBackCentroid().coordZ() );
00260     if ((width > 50.0f) && (backLine.perpendicularDistanceFrom( backPt ) > frontLine.perpendicularDistanceFrom( backPt ))) {
00261       // Back left and right are reversed
00262       EndPoint temp = backLeftPt;
00263       backLeftPt = backRightPt;
00264       backRightPt = temp;
00265       backLine.update_derived_properties();
00266       
00267       back_dx  = backRightPt.coordX() - backLeftPt.coordX();
00268       back_dy  = backRightPt.coordY() - backLeftPt.coordY();
00269       back_orientation  = AngSignPi(std::atan2(back_dy, back_dx) + (direction_t)M_PI / 2);
00270     }
00271     
00272     // Use the orientation of the line with most valid points
00273     int frontValidCount = 0, backValidCount = 0;
00274     if (frontLeftPt.isValid()) frontValidCount++;
00275     if (frontRightPt.isValid()) frontValidCount++;
00276     if (backLeftPt.isValid()) backValidCount++;
00277     if (backRightPt.isValid()) backValidCount++;
00278     
00279     if (frontValidCount == backValidCount) {
00280       // Take the average of the 2 orientations
00281       orientation = AngSignPi(std::atan2(std::sin((direction_t)front_orientation) + std::sin((direction_t)back_orientation), std::cos((direction_t)front_orientation) + std::cos((direction_t)back_orientation)));
00282     }
00283     else if (frontValidCount > backValidCount) {
00284       orientation = front_orientation;
00285     }
00286     else {
00287       orientation = back_orientation;
00288     }
00289   }
00290   // If only one line is valid, obtain the length/orientation from it
00291   else if (frontValid) {
00292     length = frontLine.getLength();
00293     width = 0;
00294     orientation = AngSignPi(std::atan2(front_dy, front_dx) + (direction_t)M_PI / 2);
00295   }
00296   else if (backValid) {
00297     length = backLine.getLength();
00298     width = 0;
00299     orientation = AngSignPi(std::atan2(back_dy, back_dx) + (direction_t)M_PI / 2);
00300   }
00301   else {
00302     length = 0;
00303     width = 0;
00304     orientation = 0;
00305   }
00306   
00307 }
00308 
00309 bool TargetData::updateParams(const ShapeRoot& other, bool force) {
00310   const Shape<TargetData>& other_target = ShapeRootTypeConst(other,TargetData);
00311   if (other_target->confidence <= 0)
00312     return false;
00313     
00314   const int other_conf = other_target->confidence;
00315   confidence += other_conf;
00316   
00317   height = (height*confidence + other_target->getHeight()*other_conf) / (confidence+other_conf);
00318   
00319   // Update front line
00320   EndPoint &frontLeftPt  = getFrontLeftPt();
00321   EndPoint &frontRightPt = getFrontRightPt();
00322   if (!frontValid) {
00323     frontLeftPt  = other_target->getFrontLeftPt();
00324     frontRightPt = other_target->getFrontRightPt();
00325   }
00326   else if (other_target->isFrontValid()) {
00327     NEW_SHAPE(otherFrontLine, LineData, other_target->frontLine);
00328     frontLine.updateParams(otherFrontLine, force);
00329     otherFrontLine.getSpace().deleteShape(otherFrontLine);
00330   }
00331   
00332   // Update back line
00333   EndPoint &backLeftPt  = getBackLeftPt();
00334   EndPoint &backRightPt = getBackRightPt();
00335   if (!backValid) {
00336     backLeftPt  = other_target->getBackLeftPt();
00337     backRightPt = other_target->getBackRightPt();
00338   }
00339   else if (other_target->isBackValid()) {
00340     NEW_SHAPE(otherBackLine, LineData, other_target->backLine);
00341     backLine.updateParams(otherBackLine, force);
00342     otherBackLine.getSpace().deleteShape(otherBackLine);
00343   }
00344   
00345   // Update front intersection point
00346   if (frontIntersect == Point(0, 0, 0)) {
00347     frontIntersect = other_target->getFrontIntersect();
00348   }
00349   else if (other_target->getFrontIntersect() != Point(0, 0, 0)) {
00350     if (frontIntersect.isValid() == other_target->getFrontIntersect().isValid()) {
00351       frontIntersect.updateParams(other_target->getFrontIntersect());
00352     }
00353     else if (other_target->getFrontIntersect().isValid()) {
00354       frontIntersect = other_target->getFrontIntersect();
00355     }
00356   }
00357   
00358   // Update back intersection point
00359   if (backIntersect == Point(0, 0, 0)) {
00360     backIntersect = other_target->getBackIntersect();
00361   }
00362   else if (other_target->getBackIntersect() != Point(0, 0, 0)) {
00363     if (backIntersect.isValid() == other_target->getBackIntersect().isValid()) {
00364       backIntersect.updateParams(other_target->getBackIntersect());
00365     }
00366     else if (other_target->getBackIntersect().isValid()) {
00367       backIntersect = other_target->getBackIntersect();
00368     }
00369   }
00370   
00371   update_derived_properties();
00372   
00373   return true;
00374 }
00375 
00376 void TargetData::mergeWith(const ShapeRoot& other) {
00377   const Shape<TargetData>& other_target = ShapeRootTypeConst(other,TargetData);
00378   if (other_target->confidence <= 0)
00379     return;
00380   const int other_conf = other_target->confidence;
00381   confidence += other_conf;
00382   
00383   height = (height*confidence + other_target->height*other_conf) / (confidence+other_conf);
00384   NEW_SHAPE(otherFrontLine, LineData, other_target->frontLine);
00385   NEW_SHAPE(otherBackLine, LineData, other_target->backLine);
00386   frontLine.mergeWith(otherFrontLine);
00387   backLine.mergeWith(otherBackLine);
00388   otherFrontLine.getSpace().deleteShape(otherFrontLine);
00389   otherBackLine.getSpace().deleteShape(otherBackLine);
00390   
00391   frontIntersect.updateParams(other_target->getFrontIntersect());
00392   backIntersect.updateParams(other_target->getBackIntersect());
00393   
00394   update_derived_properties();
00395 }
00396 
00397 void TargetData::printParams() const {
00398   cout << "Type = " << getTypeName() << endl;
00399   cout << "Shape ID = " << getId() << endl;
00400   cout << "Parent ID = " << getParentId() << endl;
00401   
00402   // Print all parameters.
00403   const EndPoint frontLeftPt  = getFrontLeftPt();
00404   const EndPoint frontRightPt = getFrontRightPt();
00405   const EndPoint backLeftPt   = getBackLeftPt();
00406   const EndPoint backRightPt  = getBackRightPt();
00407   const Point centroid = getCentroid();
00408   
00409   cout << endl;
00410   cout << "centroid = (" << centroid.coordX() << ", " << centroid.coordY() << ", " << centroid.coordZ() << ")" << endl;
00411   cout << "front left pt = (" << frontLeftPt.coordX() << ", " << frontLeftPt.coordY() << ", " << frontLeftPt.coordZ() << "), valid = " << frontLeftPt.isValid() << endl;
00412   cout << "front right pt = (" << frontRightPt.coordX() << ", " << frontRightPt.coordY() << ", " << frontRightPt.coordZ() << "), valid = " << frontRightPt.isValid() << endl;
00413   cout << "back left pt = (" << backLeftPt.coordX() << ", " << backLeftPt.coordY() << ", " << backLeftPt.coordZ() << "), valid = " << backLeftPt.isValid() << endl;
00414   cout << "back right pt = (" << backRightPt.coordX() << ", " << backRightPt.coordY() << ", " << backRightPt.coordZ() << "), valid = " << backRightPt.isValid() << endl;
00415   cout << "front intersect = (" << frontIntersect.coordX() << ", " << frontIntersect.coordY() << ", " << frontIntersect.coordZ() << "), valid = " << frontIntersect.isValid() << endl;
00416   cout << "back intersect = (" << backIntersect.coordX() << ", " << backIntersect.coordY() << ", " << backIntersect.coordZ() << "), valid = " << backIntersect.isValid() << endl;
00417   cout << "front valid = " << frontValid << endl;
00418   cout << "back valid = " << backValid << endl;
00419   cout << "orientation = " << (float)orientation * 180.0 / M_PI << " deg" << endl;
00420   cout << "length = " << length << endl;
00421   cout << "width = " << width << endl;
00422   cout << "height = " << height << endl;
00423 }
00424 
00425 void TargetData::applyTransform(const fmat::Transform& Tmat, const ReferenceFrameType_t newref) {
00426   if (frontValid)
00427     frontLine.applyTransform(Tmat, newref);
00428   if (backValid)
00429     backLine.applyTransform(Tmat, newref);
00430   if (frontIntersect != Point(0, 0, 0))
00431     frontIntersect.applyTransform(Tmat, newref);
00432   if (backIntersect != Point(0, 0, 0))
00433     backIntersect.applyTransform(Tmat, newref);
00434   update_derived_properties();
00435 }
00436 
00437 void TargetData::projectToGround(const fmat::Transform& camToBase, const PlaneEquation& groundplane) {
00438   // project the lines to elevated ground space
00439   PlaneEquation target_plane = groundplane;
00440   float const new_displacement = target_plane.getDisplacement() + target_plane.getZsign()*height;
00441   target_plane.setDisplacement(new_displacement);
00442   
00443   if (frontValid)
00444     frontLine.projectToGround(camToBase, target_plane);
00445   if (backValid)
00446     backLine.projectToGround(camToBase, target_plane);
00447   if (frontIntersect != Point(0, 0, 0))
00448     frontIntersect.projectToGround(camToBase, target_plane);
00449   if (backIntersect != Point(0, 0, 0))
00450     backIntersect.projectToGround(camToBase, target_plane);
00451   update_derived_properties();
00452 }
00453 
00454 // Doesn't actually render a target to sketch space
00455 Sketch<bool>* TargetData::render() const {
00456   SketchSpace &SkS = space->getDualSpace();
00457   
00458   Sketch<bool>& draw_result = 
00459     *new Sketch<bool>(SkS, "render("+getName()+")");
00460   draw_result->setParentId(getViewableId());
00461   draw_result->setColor(getColor());
00462   
00463   fmat::Column<3> ctr(getCentroid().getCoords());
00464   SkS.applyTmat(ctr);
00465   int const cx = int(ctr[0]);
00466   int const cy = int(ctr[1]);
00467   draw_result = false;
00468   draw_result(cx, cy) = true;  
00469   return &draw_result;
00470 }
00471 
00472 TargetData& TargetData::operator=(const TargetData& other) {
00473   if (&other == this)
00474     return *this;
00475   BaseData::operator=(other);
00476   
00477   frontLine      = other.frontLine;
00478   backLine       = other.backLine;
00479   frontValid     = other.frontValid;
00480   backValid      = other.backValid;
00481   frontIntersect = other.frontIntersect;
00482   backIntersect  = other.backIntersect;
00483   orientation    = other.orientation;
00484   length         = other.length;
00485   width          = other.width;
00486   height         = other.height;
00487   
00488   return *this;
00489 }
00490 
00491 float TargetData::perpendicularDistanceFrom(Point point) {
00492   if (frontValid && backValid)
00493     return min(frontLine.perpendicularDistanceFrom(point), backLine.perpendicularDistanceFrom(point));
00494   else if (frontValid)
00495     return frontLine.perpendicularDistanceFrom(point);
00496   else if (backValid)
00497     return backLine.perpendicularDistanceFrom(point);
00498   else
00499     return 0;
00500 }
00501 
00502 Shape<TargetData> TargetData::extractLineTarget(std::string frontColor, std::string backColor, std::string rightColor, std::string occluderColor, const float height) {
00503   // get the front, back and right stuff
00504   NEW_SKETCH(camFrame, uchar, VRmixin::sketchFromSeg());    
00505   NEW_SKETCH(frontStuff, bool, visops::colormask(camFrame, frontColor));
00506   NEW_SKETCH(backStuff, bool, visops::colormask(camFrame, backColor));
00507   NEW_SKETCH(rightStuff, bool, visops::colormask(camFrame, rightColor));
00508   NEW_SKETCH(occluders, bool, visops::colormask(camFrame, occluderColor));
00509 
00510   NEW_SHAPEVEC(frontBlobs, BlobData, BlobData::extractBlobs(frontStuff, 100));
00511   NEW_SHAPEVEC(backBlobs, BlobData, BlobData::extractBlobs(backStuff, 100));
00512   NEW_SHAPEVEC(rightBlobs, BlobData, BlobData::extractBlobs(rightStuff, 100));
00513   
00514   // assume the biggest blob forms the front line
00515   NEW_SKETCH(frontSketch, bool, frontBlobs.size() > 0 ? frontBlobs[0]->getRendering() : visops::zeros(camFrame));
00516   // assume the biggest blob forms the back line
00517   NEW_SKETCH(backSketch, bool, backBlobs.size() > 0 ? backBlobs[0]->getRendering() : visops::zeros(camFrame));
00518   // assume the biggest blob forms the right line
00519   NEW_SKETCH(rightSketch, bool, rightBlobs.size() > 0 ? rightBlobs[0]->getRendering() : visops::zeros(camFrame));
00520   
00521   Shape<TargetData> result = extractLineTarget(frontSketch, backSketch, rightSketch, occluders, height);
00522   
00523   // delete temporary camera shapes
00524   //camShS.deleteShapes(horBlobs);
00525   //camShS.deleteShapes(vertBlobs);
00526   
00527   return result;
00528 }
00529 
00530 Shape<TargetData> TargetData::extractLineTarget(Sketch<bool>& frontSketch, Sketch<bool>& backSketch, Sketch<bool>& rightSketch, Sketch<bool>& occluders, const float height) {
00531   NEW_SHAPE(frontLine, LineData, LineData::extractLine(frontSketch, occluders | rightSketch));
00532   NEW_SHAPE(backLine, LineData, LineData::extractLine(backSketch, occluders | rightSketch));
00533   NEW_SHAPE(rightLine, LineData, LineData::extractLine(rightSketch, occluders));
00534 
00535   Shape<TargetData> result = extractLineTarget(frontLine, backLine, rightLine, frontSketch->getColor(), height);
00536   
00537   // delete temporary camera shapes
00538   if (frontLine.isValid())
00539     frontLine.getSpace().deleteShape(frontLine);
00540   if (backLine.isValid())
00541     backLine.getSpace().deleteShape(backLine);
00542   if (rightLine.isValid())
00543     rightLine.getSpace().deleteShape(rightLine);
00544   
00545   return result;
00546 }
00547 
00548 Shape<TargetData> TargetData::extractLineTarget(Shape<LineData>& frontLine, Shape<LineData>& backLine, Shape<LineData>& rightLine, rgb color, const float height) {
00549   
00550   // create the target using the front and back lines
00551   if (frontLine.isValid() && backLine.isValid()) {
00552     EndPoint frontIntersect = Point(0, 0, 0);
00553     EndPoint backIntersect = Point(0, 0, 0);
00554     if (rightLine.isValid()) {
00555       frontIntersect = frontLine->intersectionWithLine(rightLine);
00556       backIntersect  = backLine->intersectionWithLine(rightLine);
00557       frontIntersect.setValid(frontLine->pointOnLine(frontIntersect));
00558       backIntersect.setValid(backLine->pointOnLine(backIntersect));
00559     }
00560     else {
00561       frontIntersect.setValid(false);
00562       backIntersect.setValid(false);
00563     }
00564   
00565     Shape<TargetData> result(frontLine.getSpace(), frontLine->leftPt(), frontLine->rightPt(), backLine->leftPt(), backLine->rightPt(), frontIntersect, backIntersect, height);
00566     result->setColor(color);
00567     return result;
00568   }
00569   else if (frontLine.isValid()) {
00570     EndPoint left = Point(0, 0, 0);
00571     EndPoint right = Point(0, 0, 0);
00572     left.setValid(false);
00573     right.setValid(false);
00574     
00575     EndPoint frontIntersect = Point(0, 0, 0);
00576     EndPoint backIntersect = Point(0, 0, 0);
00577     frontIntersect.setValid(false);
00578     backIntersect.setValid(false);
00579     
00580     if (rightLine.isValid()) {
00581       frontIntersect = frontLine->intersectionWithLine(rightLine);
00582       frontIntersect.setValid(frontLine->pointOnLine(frontIntersect));
00583     }
00584     
00585     Shape<TargetData> result(frontLine.getSpace(), frontLine->rightPt(), frontLine->leftPt(), right, left, frontIntersect, backIntersect, height);
00586     result->setColor(color);
00587     return result;
00588   }
00589   else if (backLine.isValid()) {
00590     EndPoint left = Point(0, 0, 0);
00591     EndPoint right = Point(0, 0, 0);
00592     left.setValid(false);
00593     right.setValid(false);
00594     
00595     EndPoint frontIntersect = Point(0, 0, 0);
00596     EndPoint backIntersect = Point(0, 0, 0);
00597     frontIntersect.setValid(false);
00598     backIntersect.setValid(false);
00599     
00600     if (rightLine.isValid()) {
00601       backIntersect = backLine->intersectionWithLine(rightLine);
00602       backIntersect.setValid(backLine->pointOnLine(backIntersect));
00603     }
00604     
00605     Shape<TargetData> result(backLine.getSpace(), right, left, backLine->rightPt(), backLine->leftPt(), frontIntersect, backIntersect, height);
00606     result->setColor(color);
00607     return result;
00608   }
00609   else {
00610     ShapeRoot invalid; // need to define a named variable to avoid warning on next line
00611     return ShapeRootType(invalid, TargetData);
00612   }
00613 
00614 }
00615 
00616 } // namespace

DualCoding 5.1CVS
Generated Mon May 9 04:56:28 2016 by Doxygen 1.6.3