コード例 #1
0
ファイル: Polygon.cpp プロジェクト: TacoVox/OpenDaVINCI
            Polygon Polygon::intersectIgnoreZ(const Polygon &other) const {
                // Algorithm:
                // For every pair<Vertex, Vertex> from other determine the intersection point P with every pair<Vertex, Vertex> from this.
                // For every Vertex from other check if the Vertex is inside this.
                // For all resulting Vertices in the overlapping polygon sort vertices to remove all crossings.

                Polygon resultingPolygon;

                vector<Point3> thisPolygon = getVertices();
                vector<Point3> otherPolygon = other.getVertices();

                if ( (thisPolygon.size() > 0) && (otherPolygon.size() > 0) ) {
                    // Modify vertices by adding the first vertex at the end of both lists for closing the polygon.
                    thisPolygon.push_back((*thisPolygon.begin()));
                    otherPolygon.push_back((*otherPolygon.begin()));

                    for(uint32_t i = 0; i < thisPolygon.size() - 1; i++) {
                        Point3 thisA = thisPolygon.at(i);
                        Point3 thisB = thisPolygon.at(i+1);
                        Line thisLine(thisA, thisB);

                        for(uint32_t j = 0; j < otherPolygon.size() - 1; j++) {
                            Point3 otherA = otherPolygon.at(j);
                            Point3 otherB = otherPolygon.at(j+1);
                            Line otherLine(otherA, otherB);

                            Point3 result;
                            if (thisLine.intersectIgnoreZ(otherLine, result)) {
                                // Intersection point found.
                                resultingPolygon.add(result);
                            }
                        }
                    }

                    // Now, check if one vertex from other is within this polygon.
                    for(uint32_t j = 0; j < otherPolygon.size()-1; j++) {
                        Point3 otherVertex = otherPolygon.at(j);

                        if (containsIgnoreZ(otherVertex)) {
                            resultingPolygon.add(otherVertex);
                        }
                    }

                    // Remove crossing lines.
                    resultingPolygon.sort();
                }

                return resultingPolygon;
            }
コード例 #2
0
ol::Collision ol::Shape::
LineStripCollision( const std_container1 &vertices, const std_container2 &otherVertices,
                    const Placement &thisPlacement, const Placement &otherPlacement,
                    bool getResults, bool thisConnectFirstAndLast, bool otherConnectFirstAndLast ) const {
   
   if( vertices.size() < 2 || otherVertices.size() < 2 ) {
      OlError( "An empty shape can't ever collide!" );
      return Collision( false );
   }
   
   Vec2D thisCo = thisPlacement.GetPosition();
   Vec2D otherCo = otherPlacement.GetPosition();
   
   Matrix2D thisTransform = thisPlacement.Get2DMatrix();
   Matrix2D otherTransform = otherPlacement.Get2DMatrix();
   
   typename std_container1::const_iterator thisIter = vertices.begin();
   
   const Vec2D rotationPivot = thisPlacement.GetRotationPivot();
   const Vec2D otherRotationPivot = otherPlacement.GetRotationPivot();
   
   Vec2D thisPrev = thisTransform.Transform( *thisIter - rotationPivot ) + thisCo + rotationPivot;
   
   thisIter++;
   
   std::vector< LinePair * > segmentLists;
   
   // Loop through each vertex //
   while( true ) {
      bool breakNow = false;
      
      // Test if we've reached the last line segment //
      if( thisIter == vertices.end() ) {
         if( !thisConnectFirstAndLast ) {
            break;
         }
         
         breakNow = true;
         thisIter = vertices.begin();
      }
      
      Vec2D thisVertex = thisTransform.Transform( *thisIter - rotationPivot ) + thisCo + rotationPivot;
      thisIter++;

      typename std_container2::const_iterator otherIter = otherVertices.begin();
      Vec2D otherPrev = otherTransform.Transform( *otherIter - otherRotationPivot ) + otherCo + otherRotationPivot;
      otherIter++;
      
      // Loop through each vertex of the other polygon //
      while( true ) {
         bool breakNow = false;
         
         // Test if we've reached the last line segment of the other polygon //
         if( otherIter == otherVertices.end() ) {
            if( !otherConnectFirstAndLast ) {
               break;
            }
            
            breakNow = true;
            otherIter = otherVertices.begin();
         }

         Vec2D otherVertex = otherTransform.Transform( *otherIter - otherRotationPivot )
                             + otherCo + otherRotationPivot;
         otherIter++;
         
         // Test for collision //
         if( IsCounterClockwise( thisPrev, thisVertex, otherPrev )
             != IsCounterClockwise( thisPrev, thisVertex, otherVertex )
             &&
             IsCounterClockwise( otherPrev, otherVertex, thisPrev )
             != IsCounterClockwise( otherPrev, otherVertex, thisVertex )) {
            
            if( !getResults ) {
               return Collision( true );
            }
            else {
               Line thisLine( thisVertex, thisPrev );
               Line otherLine( otherVertex, otherPrev );
               
               segmentLists.push_back( new LinePair( thisLine, otherLine ));
               
               /*
               return Collision( thisLine, otherLine );*/
            }
         }

         // Is last line segment of the other polygon processed? //
         if( breakNow ) {
            break;
         }

         // Advance to the next vertex of the other polygon //
         otherPrev = otherVertex;
      }

      // Is last line segment processed? //
      if( breakNow ) {
         break;
      }

      // Advance to the next vertex //
      thisPrev = thisVertex;
   }
   
   if( !segmentLists.empty() ) {
      return Collision( segmentLists );
   }
   
   return Collision( false );
}