Back to index

salome-med  6.5.0
InterpKernelGeo2DEdge.hxx
Go to the documentation of this file.
00001 // Copyright (C) 2007-2012  CEA/DEN, EDF R&D
00002 //
00003 // This library is free software; you can redistribute it and/or
00004 // modify it under the terms of the GNU Lesser General Public
00005 // License as published by the Free Software Foundation; either
00006 // version 2.1 of the License.
00007 //
00008 // This library is distributed in the hope that it will be useful,
00009 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00010 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00011 // Lesser General Public License for more details.
00012 //
00013 // You should have received a copy of the GNU Lesser General Public
00014 // License along with this library; if not, write to the Free Software
00015 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
00016 //
00017 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
00018 //
00019 
00020 #ifndef __INTERPKERNELGEO2DEDGE_HXX__
00021 #define __INTERPKERNELGEO2DEDGE_HXX__
00022 
00023 #include "INTERPKERNELDefines.hxx"
00024 #include "InterpKernelGeo2DComposedEdge.hxx"
00025 #include "InterpKernelException.hxx"
00026 #include "InterpKernelGeo2DBounds.hxx"
00027 #include "InterpKernelGeo2DNode.hxx"
00028 
00029 #include <iostream>
00030 #include <vector>
00031 #include <list>
00032 #include <map>
00033 
00034 namespace INTERP_KERNEL
00035 {
00036   typedef enum
00037     {
00038       SEG         = 1,
00039       ARC_CIRCLE  = 4,
00040       ARC_PARABOL = 8
00041     } TypeOfFunction;
00042 
00043   typedef enum
00044     {
00045       CIRCLE  = 0 ,
00046       PARABOL = 1
00047     } TypeOfMod4QuadEdge;
00048 
00049   typedef enum
00050     {
00051       START       = 5,
00052       END         = 1,
00053       INSIDE      = 2,
00054       OUT_BEFORE  = 3,
00055       OUT_AFTER   = 4
00056     } TypeOfLocInEdge; //see Edge::OFFSET_FOR_TYPEOFLOCINEDGE
00057   
00058   typedef enum
00059     {
00060       FULL_IN_1    = 1,
00061       FULL_ON_1    = 4,
00062       FULL_OUT_1   = 2,
00063       FULL_UNKNOWN = 3
00064     } TypeOfEdgeLocInPolygon;
00065 
00066   class INTERPKERNEL_EXPORT MergePoints
00067   {
00068   public:
00069     MergePoints();
00070 
00071     //methods called during intersection edge-edge
00072     void start1Replaced();
00073     void end1Replaced();
00074     void start1OnStart2();
00075     void start1OnEnd2();
00076     void end1OnStart2();
00077     void end1OnEnd2();
00078     //methods to be called during aggregation
00079     bool isStart1(unsigned rk) const;
00080     bool isEnd1(unsigned rk) const;
00081     bool isStart2(unsigned rk) const;
00082     bool isEnd2(unsigned rk) const;
00083     void clear();
00084     unsigned getNumberOfAssociations() const;
00085   private:
00086     unsigned _ass1Start1  : 1;
00087     unsigned _ass1End1    : 1;
00088     unsigned _ass1Start2  : 1;
00089     unsigned _ass1End2    : 1;
00090     unsigned _ass2Start1  : 1;
00091     unsigned _ass2End1    : 1;
00092     unsigned _ass2Start2  : 1;
00093     unsigned _ass2End2    : 1;
00094   };
00095 
00100   class INTERPKERNEL_EXPORT IntersectElement
00101   {
00102   public:
00103     IntersectElement(double val1, double val2, bool start1, bool end1, bool start2, bool end2, Node *node, const Edge& e1, const Edge& e2, bool keepOrder);
00104     IntersectElement(const IntersectElement& other);
00106     bool operator<(const IntersectElement& other) const;
00107     IntersectElement& operator=(const IntersectElement& other);
00108     double getVal1() const { return _chararct_val_for_e1; }
00109     double getVal2() const { return _chararct_val_for_e2; }
00111     bool isLowerOnOther(const IntersectElement& other) const;
00112     unsigned isOnExtrForAnEdgeAndInForOtherEdge() const;
00113     void attachLoc() { _node->setLoc(_loc_of_node); }
00114     bool isOnMergedExtremity() const;
00115     bool isIncludedByBoth() const;
00116     void setNode(Node *node) const;
00117     void performMerging(MergePoints& commonNode) const;
00118     Node *getNodeOnly() const { return _node; }
00119     Node *getNodeAndReleaseIt() { Node *tmp=_node; _node=0; return tmp; }
00120     ~IntersectElement();
00121   private:
00122     bool _1S;
00123     bool _1E;
00124     bool _2S;
00125     bool _2E;
00126     double _chararct_val_for_e1;
00127     double _chararct_val_for_e2;
00128     Node *_node;
00129     TypeOfLocInPolygon _loc_of_node;
00130     const Edge& _e1;
00131     const Edge& _e2;
00132   public:
00133     static const unsigned LIMIT_ALONE = 22;
00134     static const unsigned LIMIT_ON = 73;
00135     static const unsigned NO_LIMIT = 19;
00136   };
00137 
00141   class INTERPKERNEL_EXPORT EdgeIntersector
00142   {
00143   protected:
00145     EdgeIntersector(const Edge& e1, const Edge& e2):_e1(e1),_e2(e2) { }
00146   public:
00147     virtual ~EdgeIntersector() { }
00148     virtual bool keepOrder() const = 0;
00150     virtual bool haveTheySameDirection() const = 0;
00152     virtual void getPlacements(Node *start, Node *end, TypeOfLocInEdge& whereStart, TypeOfLocInEdge& whereEnd, MergePoints& commonNode) const = 0;
00154     bool intersect(const Bounds *whereToFind, std::vector<Node *>& newNodes, bool& order, MergePoints& commonNode);
00156     virtual void areOverlappedOrOnlyColinears(const Bounds *whereToFind, bool& obviousNoIntersection, bool& areOverlapped) = 0;
00158     virtual std::list< IntersectElement > getIntersectionsCharacteristicVal() const = 0;
00159   protected:
00160     void obviousCaseForCurvAbscisse(Node *node, TypeOfLocInEdge& where, MergePoints& commonNode, bool& obvious) const;
00161   protected:
00162     const Edge& _e1;
00163     const Edge& _e2;
00164   };
00165 
00166   class INTERPKERNEL_EXPORT SameTypeEdgeIntersector : public EdgeIntersector
00167   {
00168   protected:
00169     SameTypeEdgeIntersector(const Edge& e1, const Edge& e2):EdgeIntersector(e1,e2) { }
00170     bool keepOrder() const { return true; }
00171   };
00172 
00173   class INTERPKERNEL_EXPORT CrossTypeEdgeIntersector : public EdgeIntersector
00174   {
00175   protected:
00176     CrossTypeEdgeIntersector(const Edge& e1, const Edge& e2, bool reverse):EdgeIntersector(e1,e2),_reverse(reverse) { }
00177     bool keepOrder() const { return _reverse; }
00178     bool haveTheySameDirection() const { throw Exception("Cross type intersector is not supposed to deal with overlapped in cross type."); }
00179     const Edge *myE1() { if(_reverse) return &_e1; else return &_e2; }
00180     const Edge *myE2() { if(_reverse) return &_e2; else return &_e1; }
00181   protected:
00183     bool _reverse;
00184   };
00185 
00186   class EdgeLin;
00187   class EdgeInfLin;
00188   class EdgeArcCircle;
00189 
00197   class INTERPKERNEL_EXPORT Edge
00198   {
00199   public:
00200     Edge(Node *start, Node *end, bool direction=true):_cnt(1),_loc(FULL_UNKNOWN) { if(direction) { _start=start; _end=end; } else { _start=end; _end=start; } _start->incrRef(); _end->incrRef(); }
00201     Edge(double sX, double sY, double eX, double eY);
00202     TypeOfEdgeLocInPolygon getLoc() const { return _loc; }
00203     void incrRef() const { _cnt++; }
00204     bool decrRef();
00205     void initLocs() const { _loc=FULL_UNKNOWN; _start->initLocs(); _end->initLocs(); }
00206     void declareOn() const;
00207     void declareIn() const;
00208     void declareOut() const;
00209     const Bounds& getBounds() const { return _bounds; }
00210     void fillXfigStreamForLoc(std::ostream& stream) const;
00211     Node *getNode(TypeOfLocInEdge where) const { if(where==START) return _start; else if(where==END) return _end; else return 0; }
00212     Node *getStartNode() const { return _start; }
00213     Node *getEndNode() const { return _end; }
00214     void setEndNodeWithoutChange(Node *newEnd);
00215     void setStartNodeWithoutChange(Node *newStart);
00216     bool changeStartNodeWith(Node *otherStartNode) const;
00217     bool changeStartNodeWithAndKeepTrack(Node *otherStartNode, std::vector<Node *>& track) const;
00218     bool changeEndNodeWith(Node *otherEndNode) const;
00219     bool changeEndNodeWithAndKeepTrack(Node *otherEndNode, std::vector<Node *>& track) const;
00220     void addSubEdgeInVector(Node *start, Node *end, ComposedEdge& vec) const;
00221     void getNormalVector(double *vectOutput) const;
00222     static EdgeIntersector *BuildIntersectorWith(const Edge *e1, const Edge *e2);
00223     static Edge *BuildFromXfigLine(std::istream& str);
00224     static Edge *BuildEdgeFrom(Node *start, Node *end);
00225     template<TypeOfMod4QuadEdge type>
00226     static Edge *BuildEdgeFrom(Node *start, Node *middle, Node *end);
00227     virtual void update(Node *m) = 0;
00229     virtual double getAreaOfZone() const = 0;
00231     virtual void applySimilarity(double xBary, double yBary, double dimChar);
00233     virtual void unApplySimilarity(double xBary, double yBary, double dimChar);
00235     virtual double getCurveLength() const = 0;
00236     virtual void getBarycenter(double *bary) const = 0;
00237     virtual void getBarycenterOfZone(double *bary) const = 0;
00239     virtual Node *buildRepresentantOfMySelf() const = 0;
00241     virtual bool isIn(double characterVal) const = 0;
00243     virtual bool isLower(double val1, double val2) const = 0;
00245     virtual double getCharactValue(const Node& node) const = 0;
00247     virtual double getCharactValueBtw0And1(const Node& node) const = 0;
00249     virtual double getDistanceToPoint(const double *pt) const = 0;
00251     virtual bool isNodeLyingOn(const double *coordOfNode) const = 0;
00252     virtual TypeOfFunction getTypeOfFunc() const = 0;
00253     virtual void dynCastFunction(const EdgeLin * &seg,
00254                                  const EdgeArcCircle * &arcSeg) const = 0;
00255     bool intersectWith(const Edge *other, MergePoints& commonNode,
00256                        ComposedEdge& outVal1, ComposedEdge& outVal2) const;
00257     static bool IntersectOverlapped(const Edge *f1, const Edge *f2, EdgeIntersector *intersector, MergePoints& commonNode,
00258                                     ComposedEdge& outValForF1, ComposedEdge& outValForF2);
00259     static void Interpolate1DLin(const std::vector<double>& distrib1, const std::vector<double>& distrib2,
00260                                  std::map<int, std::map<int,double> >& result);
00261     virtual void dumpInXfigFile(std::ostream& stream, bool direction, int resolution, const Bounds& box) const = 0;
00262     bool isEqual(const Edge& other) const;
00263   public:
00264     void sortIdsAbs(const std::vector<INTERP_KERNEL::Node *>& addNodes, const std::map<INTERP_KERNEL::Node *, int>& mapp1, const std::map<INTERP_KERNEL::Node *, int>& mapp2, std::vector<int>& edgesThis);
00265     virtual void fillGlobalInfoAbs(bool direction, const std::map<INTERP_KERNEL::Node *,int>& mapThis, const std::map<INTERP_KERNEL::Node *,int>& mapOther, int offset1, int offset2, double fact, double baryX, double baryY,
00266                                    std::vector<int>& edgesThis, std::vector<double>& addCoo, std::map<INTERP_KERNEL::Node *,int> mapAddCoo) const = 0;
00267     virtual void fillGlobalInfoAbs2(const std::map<INTERP_KERNEL::Node *,int>& mapThis, const std::map<INTERP_KERNEL::Node *,int>& mapOther, int offset1, int offset2, double fact, double baryX, double baryY,
00268                                     std::vector<int>& edgesOther, std::vector<double>& addCoo, std::map<INTERP_KERNEL::Node *,int>& mapAddCoo) const = 0;
00269     virtual Edge *buildEdgeLyingOnMe(Node *start, Node *end, bool direction=true) const = 0;
00270   protected:
00271     Edge():_cnt(1),_loc(FULL_UNKNOWN),_start(0),_end(0) { }
00272     virtual ~Edge();
00273     static int CombineCodes(TypeOfLocInEdge code1, TypeOfLocInEdge code2);
00274     static bool Intersect(const Edge *f1, const Edge *f2, EdgeIntersector *intersector, const Bounds *whereToFind, MergePoints& commonNode,
00275                           ComposedEdge& outValForF1, ComposedEdge& outValForF2);
00277     static bool SplitOverlappedEdges(const Edge *e1, const Edge *e2, Node *nS, Node *nE, bool direction, int code,
00278                                      ComposedEdge& outVal1, ComposedEdge& outVal2);
00279   protected:
00280     mutable unsigned char _cnt;
00281     mutable TypeOfEdgeLocInPolygon _loc;
00282     Bounds _bounds;
00283     Node *_start;
00284     Node *_end;
00285   protected:
00286     //In relation with max possible value of TypeOfLocInEdge.
00287     static const int OFFSET_FOR_TYPEOFLOCINEDGE = 8;
00288   };
00289 }
00290 
00291 #endif