// Copyright (C), 1998-2007, Beijing Tangent Engineering Software Co. Ltd. // = FileName: Road.h // = Version: 8.5 // = Author: lgh // = Date: 2010-9-27 9:30:22 // = Description: 道路结构,包含道路道路所有信息, // = Maintainers: #pragma once #include "InterStruct.h" // 道路被多条线截断,需要判断其过滤模式,哪段保留,哪段删除 class CFilterMode { public: BOOL KeepFirst() const {return m_bFirstKeep;} void KeepFirst(BOOL bKeepFirst) {m_bFirstKeep = bKeepFirst;} private: BOOL m_bFirstKeep; }; class CRoad { public: CRoad(double dLeftWid, double dRightWid, BOOL bDrawMid, BOOL bDrawCorner, double dCornerRadius, EFilletStyle cornerType); virtual ~CRoad(void); double HalfWid() const {return (m_dLeftWid + m_dRightWid)*0.5;} BOOL IsDrawMid() const{return m_bDrawMid;} // // 道路的区域 void ToRegionSys(AcGePoint2d &ptLeftDown, AcGePoint2d &ptRightUp) const; virtual void ToRegion(AcGePoint2d &ptLeftDown, AcGePoint2d &ptRightUp) const = 0; // 道路发生截取的误差长度。(删除短线) double TolLen() const {return HalfWid() * 1.2;} // 道路相交拆分的时候,使用的误差。该范围内,可以认为道路相交 double TolForSplit() const{return HalfWid() * 4.0;} // 获取道路所在的近似区域 double TolForRegion( ) const {return HalfWid() * 10.0;}; // 是否需要倒角 BOOL NeedInterCircle() const{return m_bCorner;} // 是否需要同圆心倒角 BOOL NeedSameCenter() const{return m_eCornerType == eSameCenter;} // 倒角半径 double CirRadius() const{return m_dRaidus; } BOOL NeedDrawMid() const {return m_bDrawMid;} virtual EPointAtRoadPerp PointAtRoadPerp(const AcGePoint2d &pt, double dTol = 1.0) const = 0; virtual EPointAtRoadInDir PointAtRoadInDir(const AcGePoint2d &pt, double dTol = 1.0) const = 0; // 检测点相对于延伸的道路的关系,用于中线的测试。 virtual EPointAtRoadInDir PointAtExtendRoadInDir(const AcGePoint2d &pt, double dTol = 1.0) const = 0; // 以下为道路的四个方向,对圆弧来说,会取point点的切线方向 // 道路左(上)方向,右(下)方向。起点到终点的方向,终点到起点的方向。 // 对于直线道路来说,参数点无意义。 virtual AcGeVector2d LeftDirection(const AcGePoint2d &point) const = 0; virtual AcGeVector2d RightDirection(const AcGePoint2d &point) const = 0; virtual AcGeVector2d StartDirection(const AcGePoint2d &point) const = 0; virtual AcGeVector2d EndDirection(const AcGePoint2d &point) const = 0; // 检测ArcSplit或者lineSplit的方向是否跟vec相同。 static EVecDirection SameDirection(const AcGeVector2d &vec, const AcGeCircArc2d &arcSplit, bool bStart); static EVecDirection SameDirection(const AcGeVector2d &vec, const AcGeLineSeg2d &lineSplit, bool bStart); // 拆分中线,当然,如果当前道路不需要回执中线,则不执行拆分 virtual void SplitMid(const AcGeLineSeg2d &lineseg, AcAryInterStructPointer &arLeftDump, AcAryInterStructPointer &arRightDump, CLineCADEntEdgeAdapter &ent)const = 0; virtual void SplitMid(const AcGeCircArc2d &arc, AcAryInterStructPointer &arLeftDump, AcAryInterStructPointer &arRightDump, CArcCADEntEdgeAdapter &ent)const = 0; // 检测线段或者弧线是否在道路内部。 BOOL IsInExtendRoad(CInterStruct *pInter) const ; virtual TGGeCurveSegment ToCurveSeg(int nFlag) const = 0; // 0,中线;1,左边线;2,右边线 protected: // 拆分线段,或者圆弧,arInterPoint:按照线段或者圆弧有序的点的集合 static void SplitLineEdge(const AcGeLineSeg2d &lineseg, AcArray &arInterPoint, AcAryLineSeg2d &arLines); static void SplitArcEdge(const AcGeCircArc2d &arc, AcArray &arInterPoint, AcAryCircArc2d &arArcs); // 同向检测 static EVecDirection VecSameDirection(AcGeVector2d vec1, AcGeVector2d vec2, double dTol); protected: double m_dLeftWid; // 左宽 double m_dRightWid; // 右宽 BOOL m_bDrawMid; // 是否绘制中线 BOOL m_bCorner;// 是否需要倒角 double m_dRaidus; // 倒角半径 EFilletStyle m_eCornerType;// 倒角方式 static AcGeTol m_sGeTol; }; class CLineRoad : public CRoad { public: CLineRoad(double dLeftWid, double dRightWid, BOOL bDrawMid, BOOL bDrawCorner, double dCornerRadius, EFilletStyle cornerType, const AcGeLineSeg2d &midLine); virtual ~CLineRoad(void); virtual void ToRegion(AcGePoint2d &ptLeftDown, AcGePoint2d &ptRightUp) const; AcGeLineSeg2d LeftLine() const; AcGeLineSeg2d RightLine() const; AcGeLineSeg2d MidLine() const; virtual TGGeCurveSegment ToCurveSeg(int nFlag) const ; // 0,中线;1,左边线;2,右边线 // 把直线和圆弧拆分为interStruct数组。 void SplitEdge(const AcGeLineSeg2d &lineEdge, AcAryInterStructPointer &leftInters, AcAryInterStructPointer &rightInters, CLineCADEntEdgeAdapter &ent, AcAryInterStructPointer &arInterOri) const; void SplitEdge(const AcGeCircArc2d &arcEdge, AcAryInterStructPointer &leftInters, AcAryInterStructPointer &rightInters, CArcCADEntEdgeAdapter &ent, AcAryInterStructPointer &arInterOri) const; // 拆分中线,当然,如果当前道路不需要回执中线,则不执行拆分 virtual void SplitMid(const AcGeLineSeg2d &lineseg, AcAryInterStructPointer &arLeftDump, AcAryInterStructPointer &arRightDump, CLineCADEntEdgeAdapter &ent)const ; virtual void SplitMid(const AcGeCircArc2d &arc, AcAryInterStructPointer &arLeftDump, AcAryInterStructPointer &arRightDump, CArcCADEntEdgeAdapter &ent)const ; EPointAtRoadPerp PointAtRoadPerp(const AcGePoint2d &pt, double dTol = 1.0) const; EPointAtRoadInDir PointAtRoadInDir(const AcGePoint2d &pt, double dTol = 1.0) const; // 检测点相对于延伸的道路的关系,用于中线的测试。 EPointAtRoadInDir PointAtExtendRoadInDir(const AcGePoint2d &pt, double dTol = 1.0) const; virtual AcGeVector2d LeftDirection(const AcGePoint2d &point) const ; virtual AcGeVector2d RightDirection(const AcGePoint2d &point) const; virtual AcGeVector2d StartDirection(const AcGePoint2d &point) const; virtual AcGeVector2d EndDirection(const AcGePoint2d &point) const; protected: private: AcGeLineSeg2d m_midLine; }; class CArcRoad : public CRoad { public: CArcRoad(double dLeftWid, double dRightWid, BOOL bDrawMid, BOOL bDrawCorner, double dCornerRadius, EFilletStyle cornerType, const AcGeCircArc2d &midArc); virtual ~CArcRoad(void); virtual void ToRegion(AcGePoint2d &ptLeftDown, AcGePoint2d &ptRightUp) const; AcGeCircArc2d LeftArc() const; AcGeCircArc2d RightArc() const; AcGeCircArc2d MidArc() const; virtual TGGeCurveSegment ToCurveSeg(int nFlag) const; // 0,中线;1,左边线;2,右边线 // 把直线和圆弧拆分为interStruct数组。 void SplitEdge(const AcGeLineSeg2d &lineEdge, AcAryInterStructPointer &leftInters, AcAryInterStructPointer &rightInters, CLineCADEntEdgeAdapter &ent, AcAryInterStructPointer &arInterOri) const; void SplitEdge(const AcGeCircArc2d &arcEdge, AcAryInterStructPointer &leftInters, AcAryInterStructPointer &rightInters, CArcCADEntEdgeAdapter &ent, AcAryInterStructPointer &arInterOri) const; virtual void SplitMid(const AcGeLineSeg2d &lineseg, AcAryInterStructPointer &arLeftDump, AcAryInterStructPointer &arRightDump, CLineCADEntEdgeAdapter &ent)const ; virtual void SplitMid(const AcGeCircArc2d &arc, AcAryInterStructPointer &arLeftDump, AcAryInterStructPointer &arRightDump, CArcCADEntEdgeAdapter &ent)const ; EPointAtRoadPerp PointAtRoadPerp(const AcGePoint2d &pt, double dTol = 1.0) const; EPointAtRoadInDir PointAtRoadInDir(const AcGePoint2d &pt, double dTol = 1.0) const; // 检测点相对于延伸的道路的关系,用于中线的测试。 EPointAtRoadInDir PointAtExtendRoadInDir(const AcGePoint2d &pt, double dTol = 1.0) const; virtual AcGeVector2d LeftDirection(const AcGePoint2d &point) const ; virtual AcGeVector2d RightDirection(const AcGePoint2d &point) const; virtual AcGeVector2d StartDirection(const AcGePoint2d &point) const; virtual AcGeVector2d EndDirection(const AcGePoint2d &point) const; protected: private: AcGeCircArc2d m_midArc; };