public static double Get(bool IsLeftComp, double r, Polyline line, Point2d TheIntersectPoint, int Index, Point2d StartPoint)
        {
            double oldBulge = line.GetBulgeAt(Index - 1);
            if (oldBulge == 0)
                return 0;//这里可能不对,可能有两个交点,而默认为一个交点
            else
            {
                double delta = System.Math.Atan(System.Math.Abs(oldBulge)) * 2;

                //这里计算新的半径时,要考虑方向因素,可能新半径会更小,也可能会更大
                //取决于路径的偏移方向,以及圆心的位置
                double newRadius = line.GetPoint2dAt(Index - 1).GetDistanceTo(line.GetPoint2dAt(Index)) / 2 / System.Math.Sin(delta);//新弧的半径
                if (IsLeftComp)
                {
                    if (oldBulge < 0)
                        newRadius += r;
                    else newRadius -= r;
                }
                else
                {
                    if (oldBulge > 0)
                        newRadius += r;
                    else newRadius -= r;
                }

                double newChord = StartPoint.GetDistanceTo(TheIntersectPoint);
                double newBulge = System.Math.Tan(
                    System.Math.Asin(newChord / 2 / newRadius) / 2
                    )
                    * line.GetBulgeAt(Index - 1) / System.Math.Abs(line.GetBulgeAt(Index - 1));
                return -newBulge;
            }
        }
示例#2
0
        public static LineSegment2d[] GetTangentsTo([NotNull] this CircularArc2d arc, Point2d pt)
        {
            // check if the point is inside the circle
            var center = arc.Center;

            if (pt.GetDistanceTo(center) <= arc.Radius)
            {
                return(null);
            }

            var vec    = center.GetVectorTo(pt) / 2.0;
            var tmp    = new CircularArc2d(center + vec, vec.Length);
            var inters = arc.IntersectWith(tmp);

            if (inters == null)
            {
                return(null);
            }
            var result = new LineSegment2d[2];
            var v1     = inters[0] - center;
            var i      = vec.X * v1.Y - vec.Y - v1.X > 0 ? 0 : 1;
            var j      = i ^ 1;

            result[i] = new LineSegment2d(inters[0], pt);
            result[j] = new LineSegment2d(inters[1], pt);
            return(result);
        }
示例#3
0
        // Sampler函数用于检测用户的输入.
        protected override SamplerStatus Sampler(JigPrompts prompts)
        {
            Database db = HostApplicationServices.WorkingDatabase;
            // 定义一个点拖动交互类.
            JigPromptPointOptions optJigPoint = new JigPromptPointOptions("\n请指定五角星的一个角点:");

            // 设置拖拽光标类型.
            optJigPoint.Cursor = CursorType.RubberBand;
            // 设置拖动光标基点.
            optJigPoint.BasePoint    = mCenterPt;
            optJigPoint.UseBasePoint = true;
            // 用AcquirePoint函数得到用户输入的点.
            PromptPointResult resJigPoint1 = prompts.AcquirePoint(optJigPoint);
            Point3d           curPt        = resJigPoint1.Value;

            if (curPt != peakPt)
            {
                // 重新设置椭圆参数--------------------------------------------.
                // 五角星的中心.
                Point2d p0 = new Point2d(mCenterPt.X, mCenterPt.Y);

                // 计算五角星的第一个顶点坐标.
                Point2d p1 = new Point2d(curPt[0], curPt[1]);

                // 为计算其他9个顶点的坐标进行准备.
                double   d1  = p1.GetDistanceTo(p0);
                double   d2  = d1 * Math.Sin(Rad2Ang(18)) / Math.Sin(Rad2Ang(54));
                Vector2d vec = p1 - p0;
                double   ang = vec.Angle;

                // 计算五角星另外9个顶点的坐标.
                Point2d p2  = PolarPoint(p0, ang + Rad2Ang(36), d2);
                Point2d p3  = PolarPoint(p0, ang + Rad2Ang(72), d1);
                Point2d p4  = PolarPoint(p0, ang + Rad2Ang(108), d2);
                Point2d p5  = PolarPoint(p0, ang + Rad2Ang(144), d1);
                Point2d p6  = PolarPoint(p0, ang + Rad2Ang(180), d2);
                Point2d p7  = PolarPoint(p0, ang + Rad2Ang(216), d1);
                Point2d p8  = PolarPoint(p0, ang + Rad2Ang(252), d2);
                Point2d p9  = PolarPoint(p0, ang + Rad2Ang(288), d1);
                Point2d p10 = PolarPoint(p0, ang + Rad2Ang(324), d2);

                // 更新五角星各个顶点的坐标.
                ent.SetPointAt(0, p1);
                ent.SetPointAt(1, p2);
                ent.SetPointAt(2, p3);
                ent.SetPointAt(3, p4);
                ent.SetPointAt(4, p5);
                ent.SetPointAt(5, p6);
                ent.SetPointAt(6, p7);
                ent.SetPointAt(7, p8);
                ent.SetPointAt(8, p9);
                ent.SetPointAt(9, p10);
                peakPt = curPt;
                return(SamplerStatus.OK);
            }
            else
            {
                return(SamplerStatus.NoChange);
            }
        }
示例#4
0
        private List <Polyline> ArcToPolyline(List <Entity> list)
        {
            List <Polyline> listPoly = new List <Polyline>();

            foreach (var ent in list)
            {
                //如果实体为圆弧
                if (ent is Arc)
                {
                    Arc     arc = ent as Arc;
                    double  R = arc.Radius;
                    Point3d startPoint = arc.StartPoint;
                    Point3d endPoint = arc.EndPoint;
                    Point2d p1, p2;
                    p1 = new Point2d(startPoint.X, startPoint.Y);
                    p2 = new Point2d(endPoint.X, endPoint.Y);
                    Double   L    = p1.GetDistanceTo(p2);
                    double   H    = R - Math.Sqrt(R * R - L * L / 4);
                    Polyline poly = new Polyline();

                    poly.AddVertexAt(0, p1, 2 * H / L, 0, 0);
                    poly.AddVertexAt(1, p2, 0, 0, 0);
                    poly.Color = Autodesk.AutoCAD.Colors.Color.FromColor(System.Drawing.Color.Red);

                    listPoly.Add(poly);
                }
            }
            return(listPoly);
        }
示例#5
0
        /// <summary>
        /// Найти ближайшее ребро, которое пересекает горизонтальный луч, направленный вправо из точки
        /// </summary>
        /// <param name="M"></param>
        /// <param name="ptOnEdge"></param>
        /// <returns></returns>
        private int[] GetEdgeOnHorizontalRay(Point2d M, out Point2d ptOnEdge)
        {
            int[]   edge       = null;
            Point2d?_ptOnEdge  = null;
            double  minDistToM = double.MaxValue;
            int     numVert    = Polygon.Count;

            Action <int[], Point2d, Point2d> onIntersectionFind = (currEdge, vert1, vert2) =>
            {
                Point2d currPtOnEdge = ptOnHorizontalRay(M.Y, vert1, vert2);
                double  currDistToM  = currPtOnEdge.GetDistanceTo(M);
                if (currDistToM < minDistToM)
                {
                    minDistToM = currDistToM;
                    edge       = currEdge;
                    _ptOnEdge  = currPtOnEdge;
                }
            };


            for (int i = 0; i < numVert; i++)
            {
                int[]   currEdge = new int[] { i, (i + 1) % numVert };
                Point2d vert1    = GetPt2DAt(currEdge[0]);
                Point2d vert2    = GetPt2DAt(currEdge[1]);

                double isLeftVal = double.MinValue;
                if (vert1.Y <= M.Y)
                {
                    if (vert2.Y > M.Y)
                    {
                        //Переход снизу вверх
                        isLeftVal = Utils.IsLeft(vert1, vert2, M);
                        if (isLeftVal > 0)
                        {
                            onIntersectionFind.Invoke(currEdge, vert1, vert2);
                        }
                    }
                }
                else if (vert2.Y <= M.Y)
                {
                    //Переход сверху вниз
                    isLeftVal = Utils.IsLeft(vert1, vert2, M);
                    if (isLeftVal < 0)
                    {
                        onIntersectionFind.Invoke(currEdge, vert1, vert2);
                    }
                }
            }
            if (_ptOnEdge.Value != null)
            {
                ptOnEdge = _ptOnEdge.Value;
            }
            else
            {
                ptOnEdge = Point2d.Origin;
            }
            return(edge);
        }
        /// <summary>
        /// Gets the centroid of the circular arc.
        /// </summary>
        /// <param name="arc">The instance to which the method applies.</param>
        /// <returns>The centroid of the arc.</returns>
        public static Point2d Centroid(this CircularArc2d arc)
        {
            Point2d start = arc.StartPoint;
            Point2d end   = arc.EndPoint;
            double  area  = arc.SignedArea();
            double  chord = start.GetDistanceTo(end);
            double  angle = (end - start).Angle;

            return(arc.Center.Polar(angle - (Math.PI / 2.0), (chord * chord * chord) / (12.0 * area)));
        }
示例#7
0
            public int Compare(Point3d pt1_3d, Point3d pt2_3d)
            {
                Point2d pt1 = new Point2d(pt1_3d.X, pt1_3d.Y);
                Point2d pt2 = new Point2d(pt2_3d.X, pt2_3d.Y);

                double dist1 = pt1.GetDistanceTo(basePt);
                double dist2 = pt2.GetDistanceTo(basePt);

                return(dist1.CompareTo(dist2));
            }
示例#8
0
        private static List <Polyline> ArcToPolyline(List <Entity> list)
        {
            List <Polyline> listPoly = new List <Polyline>();

            foreach (var ent in list)
            {
                //如果实体为圆弧
                if (ent is Arc)
                {
                    Arc     arc = ent as Arc;
                    double  R = arc.Radius;
                    Point3d startPoint = arc.StartPoint;
                    Point3d endPoint = arc.EndPoint;
                    Point2d p1, p2;
                    p1 = new Point2d(startPoint.X, startPoint.Y);
                    p2 = new Point2d(endPoint.X, endPoint.Y);
                    Double   L    = p1.GetDistanceTo(p2);
                    double   H    = R - Math.Sqrt(R * R - L * L / 4);
                    Polyline poly = new Polyline();

                    poly.AddVertexAt(0, p1, 2 * H / L, 0, 0);
                    poly.AddVertexAt(1, p2, 0, 0, 0);
                    //poly.Color = Autodesk.AutoCAD.Colors.Color.FromColor(System.Drawing.Color.Red);

                    listPoly.Add(poly);
                }
                else if (ent is Polyline)
                {
                    Polyline p = ent as Polyline;


                    if (p.NumberOfVertices > 2)
                    {
                        for (int i = 0; i < p.NumberOfVertices; i++)
                        {
                            Polyline tempP = new Polyline();

                            tempP.AddVertexAt(0, p.GetPoint2dAt(i), 0, 0, 0);

                            if (i + 1 < p.NumberOfVertices)
                            {
                                tempP.AddVertexAt(1, p.GetPoint2dAt(i + 1), 0, 0, 0);

                                listPoly.Add(tempP);
                            }
                        }
                    }
                    else
                    {
                        listPoly.Add(p);
                    }
                }
            }
            return(listPoly);
        }
示例#9
0
 /// <summary>
 ///     TODO
 /// </summary>
 /// <param name="from"></param>
 /// <param name="to"></param>
 /// <returns></returns>
 public static bool IsEqualTo(this Point2d from, Point2d to)
 {
     try
     {
         return(Math.Abs(from.GetDistanceTo(to)).IsLessThanTol());
     }
     catch (Exception)
     {
         return(from == to);
     }
 }
        private static Entity DrawCircularArc(CircularArc arc, double defaultElevation, Point[] densifiedPoints)
        {
            PointN  pointN      = arc.FromPoint as PointN;
            PointN  pointN2     = arc.ToPoint as PointN;
            PointN  pointN3     = arc.CenterPoint as PointN;
            Point3d point3d     = new Point3d(pointN.X, pointN.Y, pointN.Z);
            Point3d point3d2    = new Point3d(pointN3.X, pointN3.Y, pointN3.Z);
            Point3d point3d3    = new Point3d(pointN2.X, pointN2.Y, pointN2.Z);
            Point2d centerPoint = new Point2d(pointN3.X, pointN3.Y);
            Point2d point2d     = new Point2d(pointN.X, pointN.Y);

            Math.Abs(centerPoint.GetDistanceTo(point2d));
            CircularArc3d circArc;

            if (densifiedPoints != null)
            {
                int    num     = densifiedPoints.Length / 2;
                PointN pointN4 = (PointN)densifiedPoints[num];
                if (arc.IsCounterClockwise)
                {
                    PointN arg_CC_0 = (PointN)densifiedPoints[0];
                    PointN arg_D9_0 = (PointN)densifiedPoints[densifiedPoints.Length - 1];
                }
                else
                {
                    PointN arg_E4_0 = (PointN)densifiedPoints[0];
                    PointN arg_F1_0 = (PointN)densifiedPoints[densifiedPoints.Length - 1];
                }
                Point3d point3d4 = new Point3d(pointN4.X, pointN4.Y, pointN4.Z);
                circArc = new CircularArc3d(point3d, point3d4, point3d3);
            }
            else
            {
                Point2d point2d2 = new Point2d(point3d.X, point3d.Y);
                Point2d point2d3 = new Point2d(point3d3.X, point3d3.Y);
                double  num2     = GIS2CAD.CalcThetaFromVectors(point2d2, point2d3, centerPoint, arc.IsCounterClockwise);
                double  num3     = Math.Tan(num2 / 4.0);
                if (!arc.IsCounterClockwise)
                {
                    num3 *= -1.0;
                }
                CircularArc2d circularArc2d = new CircularArc2d(point2d2, point2d3, num3, false);
                Point2d[]     samplePoints  = circularArc2d.GetSamplePoints(3);
                Point3d       point3d5      = new Point3d(samplePoints[1].X, samplePoints[1].Y, point3d2.Z);
                circArc = new CircularArc3d(point3d, point3d5, point3d3);
            }
            new Point3d(pointN3.X, pointN3.Y, pointN3.Z);
            Arc arc2 = GIS2CAD.CreateFromCircularArc(circArc);

            arc2.ColorIndex = (256);
            return(arc2);
        }
示例#11
0
 public Sierpinski(Point2d a, Point2d b, Point2d c)
 {
     Triangle = new Polyline();
     A = a;
     B = b;
     C = c;
     this.Size = B.GetDistanceTo(A);
     Triangle.AddVertexAt(0, A, 0, 0, 0);
     Triangle.AddVertexAt(1, B, 0, 0, 0);
     Triangle.AddVertexAt(2, C, 0, 0, 0);
     Triangle.Closed = true;
     depth = 0;
 }
 /// <summary>
 /// Inicializa la instancia de la clase <see cref="Sierpinski"/>.
 /// </summary>
 /// <param name="a">El primer punto del triángulo.</param>
 /// <param name="b">El segundo punto del triángulo.</param>
 /// <param name="c">El tercer punto del triángulo.</param>
 public Sierpinski(Point2d a, Point2d b, Point2d c)
 {
     Triangle  = new Polyline();
     A         = a;
     B         = b;
     C         = c;
     this.Size = B.GetDistanceTo(A);
     Triangle.AddVertexAt(0, A, 0, 0, 0);
     Triangle.AddVertexAt(1, B, 0, 0, 0);
     Triangle.AddVertexAt(2, C, 0, 0, 0);
     Triangle.Closed = true;
     depth           = 0;
 }
 public List <Point2d> ConvexHull(List <Point2d> pts)
 {
     _p0 = pts.OrderBy(p => p.Y).ThenBy(p => p.X).First();
     pts = pts.OrderByDescending(p => Cosine(p)).ThenBy(p => _p0.GetDistanceTo(p)).ToList();
     for (int i = 1; i < pts.Count - 1; i++)
     {
         while (i > 0 && Clockwise(pts[i - 1], pts[i], pts[i + 1]))
         {
             pts.RemoveAt(i);
             i--;
         }
     }
     return(pts);
 }
 /// <summary>
 /// Returns the parameter value of point.
 /// </summary>
 /// <param name="pt">The Point 2d whose get the PolylineSegment parameter at.</param>
 /// <returns>A double between 0.0 and 1.0, or -1.0 if the point does not lie on the segment.</returns>
 public double GetParameterOf(Point2d pt)
 {
     if (IsLinear)
     {
         LineSegment2d line = ToLineSegment();
         return(line.IsOn(pt) ? _startPoint.GetDistanceTo(pt) / line.Length : -1.0);
     }
     else
     {
         CircularArc2d arc = ToCircularArc();
         return(arc.IsOn(pt) ?
                arc.GetLength(arc.GetParameterOf(_startPoint), arc.GetParameterOf(pt)) /
                arc.GetLength(arc.GetParameterOf(_startPoint), arc.GetParameterOf(_endPoint)) :
                -1.0);
     }
 }
示例#15
0
        public static double Get(bool IsLeftComp, double r, Polyline line, Point2d TheIntersectPoint, int Index, Point2d StartPoint)
        {
            double oldBulge = line.GetBulgeAt(Index - 1);

            if (oldBulge == 0)
            {
                return(0);//这里可能不对,可能有两个交点,而默认为一个交点
            }
            else
            {
                double delta = System.Math.Atan(System.Math.Abs(oldBulge)) * 2;

                //这里计算新的半径时,要考虑方向因素,可能新半径会更小,也可能会更大
                //取决于路径的偏移方向,以及圆心的位置
                double newRadius = line.GetPoint2dAt(Index - 1).GetDistanceTo(line.GetPoint2dAt(Index)) / 2 / System.Math.Sin(delta);//新弧的半径
                if (IsLeftComp)
                {
                    if (oldBulge < 0)
                    {
                        newRadius += r;
                    }
                    else
                    {
                        newRadius -= r;
                    }
                }
                else
                {
                    if (oldBulge > 0)
                    {
                        newRadius += r;
                    }
                    else
                    {
                        newRadius -= r;
                    }
                }

                double newChord = StartPoint.GetDistanceTo(TheIntersectPoint);
                double newBulge = System.Math.Tan(
                    System.Math.Asin(newChord / 2 / newRadius) / 2
                    )
                                  * line.GetBulgeAt(Index - 1) / System.Math.Abs(line.GetBulgeAt(Index - 1));
                return(-newBulge);
            }
        }
示例#16
0
        /// <summary>
        /// Returns the tangents between the active CircularArc2d instance complete circle and a point.
        /// </summary>
        /// <remarks>
        /// Tangents start points are on the object to which this method applies, end points on the point passed as argument.
        /// Tangents are always returned in the same order: the tangent on the left side of the line from the circular arc center
        /// to the point before the other one. 
        /// </remarks>
        /// <param name="arc">The instance to which this method applies.</param>
        /// <param name="pt">The Point2d to which tangents are searched</param>
        /// <returns>An array of LineSegement2d representing the tangents (2) or null if there is none.</returns>
        public static LineSegment2d[] GetTangentsTo(this CircularArc2d arc, Point2d pt)
        {
            // check if the point is inside the circle
            Point2d center = arc.Center;
            if (pt.GetDistanceTo(center) <= arc.Radius)
                return null;

            Vector2d vec = center.GetVectorTo(pt) / 2.0;
            CircularArc2d tmp = new CircularArc2d(center + vec, vec.Length);
            Point2d[] inters = arc.IntersectWith(tmp);
            if (inters == null)
                return null;
            LineSegment2d[] result = new LineSegment2d[2];
            Vector2d v1 = inters[0] - center;
            Vector2d v2 = inters[1] - center;
            int i = vec.X * v1.Y - vec.Y - v1.X > 0 ? 0 : 1;
            int j = i ^ 1;
            result[i] = new LineSegment2d(inters[0], pt);
            result[j] = new LineSegment2d(inters[1], pt);
            return result;
        }
示例#17
0
        /// <summary>
        /// Если вогнутые вершины попали в треугольник MIP
        /// выбирает видимую точку
        /// </summary>
        /// <param name="M"></param>
        /// <param name="candidateReflexPoints"></param>
        /// <returns></returns>
        private int GetVisiblePtFromReflexPts(Point2d M, List <int> candidateReflexPoints)
        {
            int    ptIndex    = -1;
            double angleToHor = double.MaxValue;
            double distToM    = double.MaxValue;

            foreach (int i in candidateReflexPoints)
            {
                Point2d  pt             = GetPt2DAt(i);
                Vector2d currVector     = pt - M;
                double   currAngleToHor = currVector.GetAngleTo(Vector2d.XAxis);
                double   currDistToM    = pt.GetDistanceTo(M);
                if ((currAngleToHor < angleToHor) || (currAngleToHor == angleToHor && currDistToM < distToM))
                {
                    ptIndex    = i;
                    angleToHor = currAngleToHor;
                    distToM    = currDistToM;
                }
            }
            return(ptIndex);
        }
示例#18
0
        private double GetThickness()
        {
            double rezult = -1.0;
            int    N      = -1;

            #region Search_first_ARC_segment_and_save_index_in_N
            for (int i = 0; i < _basePolyLine.NumberOfVertices; i++)
            {
                if (Math.Abs(_basePolyLine.GetBulgeAt(i) - 0) > Double.Epsilon)
                {
                    N = i; // save indeks i N
                    break; // stop the cycle
                }
            }
            #endregion

            if ((N >= 0) && (N <= (_basePolyLine.NumberOfVertices - 1)))//??? N = 0 is impossible. The first segment. The first segment must be right
            {
                double dist = -1.0;
                int    N1   = GetParalellArc(N, ref dist);

                if ((N1 > 0) && (N1 < (_basePolyLine.NumberOfVertices - 1)))
                {
                    LineSegment2d seg  = _basePolyLine.GetLineSegment2dAt(N);  // find chord
                    LineSegment2d seg1 = _basePolyLine.GetLineSegment2dAt(N1); // find chord

                    //chords are opposite vectors
                    Point2d p1 = seg.StartPoint;
                    Point2d p2 = seg1.EndPoint;

                    rezult = p1.GetDistanceTo(p2);
                }
            }

            return(rezult);
        }
示例#19
0
        ///<summary>
        ///Bogenkleinpunkte
        ///</summary>
        public List <Point3d> calcBogenKleinpunkte3d(Point2d ptZentrum, double dRadius, Point3d ptAnfang, Point3d ptEnde, double dStich)
        {
            List <Point3d> lsPunkte   = new List <Point3d>();
            Point2d        ptAnfang2d = new Point2d(ptAnfang.X, ptAnfang.Y);
            Point2d        ptEnde2d   = new Point2d(ptEnde.X, ptEnde.Y);

            //erforderliche Sehnenlänge berechnen
            myAutoCAD.myUtilities objUtil = new myAutoCAD.myUtilities();
            double dSehne = objUtil.calcSehne(dRadius, dStich);

            //Berechnung Bogenlänge
            double dAbstandSE = ptAnfang2d.GetDistanceTo(ptEnde2d);
            double dPhi       = 2 * Math.Asin(dAbstandSE / (2 * dRadius));
            double dBL        = dRadius * dPhi;

            //Berechnung der Bogenlänge für Kleinpunkte
            double dPhi1 = 0;

            dPhi1 = 2 * Math.Asin(dSehne / (2 * dRadius));
            double dBL1 = dRadius * dPhi1;

            //Vorzeichen für Phi1 festlegen (je nach Drehsinn)
            double dAlphaStart = objUtil.RiWi(ptZentrum, ptAnfang2d);
            double dAlphaEnde  = objUtil.RiWi(ptZentrum, ptEnde2d);

            if (dAlphaStart > dAlphaEnde)
            {
                dPhi1 = -dPhi1;
            }

            //Richtungswinkel
            Vector2d v2dRiWi = ptZentrum.GetVectorTo(ptAnfang2d);
            double   dRiWi   = v2dRiWi.Angle;

            dRiWi = objUtil.RiWi(ptZentrum, ptAnfang2d);

            //solange Endpunkt nicht erreicht ist, Kleinpunkte berechnen
            double dStation = dBL1;
            double dWinkel  = dRiWi;

            //dH für Höheninterpolation
            double dH = (ptEnde.Z - ptAnfang.Z) / dBL * dBL1;
            double dz = 0;

            while (dStation < dBL)
            {
                dWinkel += dPhi1;

                //dx, dy und dz berechnen
                double dx = dRadius * Math.Sin(dWinkel);
                double dy = dRadius * Math.Cos(dWinkel);
                dz += dH;

                //Kleinpunkt berechnen
                Point3d ptPunkt = new Point3d(ptZentrum.X + dx, ptZentrum.Y + dy, ptAnfang.Z + dz);

                //Punkt zu Liste hinzufügen
                lsPunkte.Add(ptPunkt);

                dStation += dBL1;
            }

            return(lsPunkte);
        }
示例#20
0
        public void ExtractSpillwayPositions()
        {
            Document adoc = Application.DocumentManager.MdiActiveDocument;

            if (adoc == null)
            {
                return;
            }

            Database db = adoc.Database;

            Editor ed = adoc.Editor;

            List <Polyline3d> highlighted = new List <Polyline3d>();

            try
            {
                Plane horizontalPlane = new Plane(Point3d.Origin, Vector3d.ZAxis);


                //Указать линию КПЧ и линии перелома откоса (они должны быть в соответствующих слоях)
                TypedValue[]           tv   = new TypedValue[] { new TypedValue(0, "POLYLINE"), new TypedValue(8, "КПЧ,ОТК") };//ограничение по слоям
                SelectionFilter        flt  = new SelectionFilter(tv);
                PromptSelectionOptions opts = new PromptSelectionOptions();
                opts.MessageForAdding = "\nВыберите 3d-полилинии, обозначающие край проезжей части"
                                        + "и переломы откоса (только с одной стороны дороги). Линии должны быть в слоях КПЧ и ОТК";
                PromptSelectionResult res = ed.GetSelection(opts, flt);
                if (res.Status == PromptStatus.OK)
                {
                    SelectionSet sset = res.Value;
                    //Отобрать только полилинии в нужных слоях
                    Dictionary <string, List <Polyline3dInfo> > slopeLines = new Dictionary <string, List <Polyline3dInfo> >();



                    //Считать направление полилинии соответствующим направлению дороги
                    bool?          toTheRight = null;//водосброс справа от КПЧ
                    Polyline3dInfo baseLine   = null;
                    using (Transaction tr = db.TransactionManager.StartTransaction())
                    {
                        WrongPolylinesException wrongPolylinesException = new WrongPolylinesException();



                        //Отбор линий в служебных слоях
                        foreach (SelectedObject acSSObj in sset)
                        {
                            Polyline3d currPoly = tr.GetObject(acSSObj.ObjectId, OpenMode.ForRead) as Polyline3d;
                            if (currPoly != null)
                            {
                                if (currPoly.Layer.Equals("КПЧ") || currPoly.Layer.Equals("ОТК"))
                                {
                                    List <Polyline3dInfo> polylines = null;
                                    slopeLines.TryGetValue(currPoly.Layer, out polylines);
                                    if (polylines == null)
                                    {
                                        polylines = new List <Polyline3dInfo>();
                                        slopeLines.Add(currPoly.Layer, polylines);
                                    }
                                    polylines.Add(new Polyline3dInfo(currPoly.Layer, currPoly));
                                }
                            }
                        }

                        //Проверить, что есть весь набор слоев - КПЧ, ОТК
                        if (!slopeLines.ContainsKey("КПЧ") || !slopeLines.ContainsKey("ОТК"))
                        {
                            wrongPolylinesException.Mistakes = wrongPolylinesException.Mistakes | Mistake.NotEnoughLayers;
                        }

                        //Проверить, что в слое КПЧ находится только 1 полилиния
                        List <Polyline3dInfo> checkList1 = null;
                        slopeLines.TryGetValue("КПЧ", out checkList1);
                        if (checkList1 == null || checkList1.Count != 1)
                        {
                            wrongPolylinesException.Mistakes = wrongPolylinesException.Mistakes | Mistake.TooManyLinesInOneLayer;
                        }

                        #region Проперка непересечения линий
                        //Проверить что линии откоса не пересекают друг друга в плане
                        //TODO: ВРЕМЕННО отказался от проверки взаимного пересечения линий откоса. Нужно учесть возможность частичного совпадения линий

                        /*
                         * List<Polyline3dInfo> slopeLinesList = slopeLines.Values.ToList().Aggregate((l1, l2) =>
                         * {
                         *  return l1.Concat(l2).ToList();
                         * });
                         * bool exitLoop = false;
                         * for (int i = 0; i < slopeLinesList.Count; i++)
                         * {
                         *  for (int j = i + 1; j < slopeLinesList.Count; j++)
                         *  {
                         *      Polyline3d poly1 = slopeLinesList[i].Poly3d;
                         *      Polyline3d poly2 = slopeLinesList[j].Poly3d;
                         *      Point3dCollection intersectPts = new Point3dCollection();
                         *      poly1.IntersectWith(poly2, Intersect.OnBothOperands,
                         *          horizontalPlane, intersectPts,
                         *          new IntPtr(0), new IntPtr(0));
                         *
                         *      //TODO!!!!! Не считать точки пересечения если в точках пересечения происходит полное совпадение вершин двух полилиний
                         *      //В это случае скорее всего полилинии просто сливаются в одну. Это допустимо для коридора
                         *
                         *
                         *
                         *      if (intersectPts.Count > 0)
                         *      {
                         *
                         *
                         *
                         *          wrongPolylinesException.Mistakes = wrongPolylinesException.Mistakes | Mistake.LinesAreIntersecting;
                         *          exitLoop = true;
                         *          break;
                         *      }
                         *  }
                         *  if (exitLoop)
                         *      break;
                         * }
                         */
                        #endregion

                        //Проверить, что все точки откоса расположены с одной стороны от КПЧ
                        //Определить водосброс направо или налево
                        //TODO: Проверить сонаправленность линий! (низкий приоритет)



                        //Для всех кодов определить участки КПЧ. Параметры взаимного расположения расчитываются в горизонтальной проекции
                        //По начальным точкам линий определить расположение линии справа или слева от КПЧ

                        //базовая линия - КПЧ
                        List <Polyline3dInfo> list = null;
                        slopeLines.TryGetValue("КПЧ", out list);

                        if (list != null && list.Count > 0)
                        {
                            baseLine = list.First();

                            foreach (KeyValuePair <string, List <Polyline3dInfo> > kvp in slopeLines)
                            {
                                if (!kvp.Key.Equals("КПЧ"))
                                {
                                    foreach (Polyline3dInfo poly3dInfo in kvp.Value)
                                    {
                                        poly3dInfo.BaseLine = baseLine.Poly2d;
                                        poly3dInfo.ComputeParameters();
                                        poly3dInfo.ComputeOrientation();
                                        //проверка, что все линии с одной стороны от базовой
                                        if (toTheRight != null)
                                        {
                                            if (toTheRight != poly3dInfo.ToTheRightOfBaseLine)
                                            {
                                                wrongPolylinesException.Mistakes = wrongPolylinesException.Mistakes | Mistake.WrongOrientation;
                                            }
                                        }
                                        else
                                        {
                                            toTheRight = poly3dInfo.ToTheRightOfBaseLine;
                                        }
                                    }
                                }
                            }
                        }


                        if (wrongPolylinesException.Mistakes != Mistake.None)
                        {
                            throw wrongPolylinesException;
                        }

                        #region Test
                        //ed.WriteMessage("\nОшибок нет\ntoTheRight = " + toTheRight);
                        ////Начертить круги в точках начала и конца полилиний
                        //BlockTable bt = tr.GetObject(db.BlockTableId, OpenMode.ForRead) as BlockTable;
                        //BlockTableRecord ms
                        //        = (BlockTableRecord)tr.GetObject(bt[BlockTableRecord.ModelSpace], OpenMode.ForWrite);
                        //foreach (KeyValuePair<string, List<Polyline3dInfo>> kvp in slopeLines)
                        //{
                        //    if (!kvp.Key.Equals("КПЧ"))
                        //    {
                        //        foreach (Polyline3dInfo poly3dInfo in kvp.Value)
                        //        {
                        //            Point3d pt1 = poly3dInfo.Poly3d.GetPointAtParameter(poly3dInfo.StartParameter);
                        //            Point3d pt2 = poly3dInfo.Poly3d.GetPointAtParameter(poly3dInfo.EndParameter);
                        //            Point3d pt3 = baseLine.Poly3d.GetPointAtParameter(poly3dInfo.StartParameterBase);
                        //            Point3d pt4 = baseLine.Poly3d.GetPointAtParameter(poly3dInfo.EndParameterBase);

                        //            foreach (Point3d pt in new Point3d[] { pt1, pt2, pt3, pt4 })
                        //            {
                        //                using (Circle circle = new Circle(pt, Vector3d.ZAxis, 1))
                        //                {
                        //                    circle.Color = Color.FromColorIndex(ColorMethod.ByAci, 1);
                        //                    ms.AppendEntity(circle);
                        //                    tr.AddNewlyCreatedDBObject(circle, true);
                        //                }
                        //            }
                        //            using (Line line = new Line(pt1, pt3))
                        //            {
                        //                line.Color = Color.FromColorIndex(ColorMethod.ByAci, 1);
                        //                ms.AppendEntity(line);
                        //                tr.AddNewlyCreatedDBObject(line, true);
                        //            }
                        //            using (Line line = new Line(pt2, pt4))
                        //            {
                        //                line.Color = Color.FromColorIndex(ColorMethod.ByAci, 1);
                        //                ms.AppendEntity(line);
                        //                tr.AddNewlyCreatedDBObject(line, true);
                        //            }


                        //        }
                        //    }
                        //}
                        #endregion

                        tr.Commit();
                    }

                    //Включать подсветку 3d полилиний, которые участвуют в расчете
                    highlighted.Clear();
                    foreach (KeyValuePair <string, List <Polyline3dInfo> > kvp in slopeLines)
                    {
                        foreach (Polyline3dInfo p3dI in kvp.Value)
                        {
                            p3dI.Poly3d.Highlight();
                            highlighted.Add(p3dI.Poly3d);
                        }
                    }

                    int          spillwayNum  = 1;
                    PositionData positionData = new PositionData();
                    while (true)
                    {
                        //Указать точку расположения водосброса
                        PromptPointResult  pPtRes;
                        PromptPointOptions pPtOpts = new PromptPointOptions("");
                        pPtOpts.Message = "\nУкажите точку расположения водосброса: ";
                        pPtRes          = adoc.Editor.GetPoint(pPtOpts);
                        if (pPtRes.Status == PromptStatus.OK)
                        {
                            Point3d pickedPt = new Point3d(pPtRes.Value.X, pPtRes.Value.Y, 0);

                            Point3d nearestPtOnBase = baseLine.Poly2d.GetClosestPointTo(pickedPt, true);       //найти ближайшую точку базовой линии

                            double pickedParameterBase = baseLine.Poly2d.GetParameterAtPoint(nearestPtOnBase); //параметр базовой линии в этой точке
                            //Найти все линии откоса, которые расположены в районе данного параметра
                            //Предполагается, что для каждого кода есть только одна такая
                            List <Polyline3dInfo> pickedPtSlopeLines =
                                slopeLines["ОТК"].FindAll(l => l.StartParameterBase <= pickedParameterBase && l.EndParameterBase >= pickedParameterBase);


                            if (pickedPtSlopeLines.Count > 1)//Проверить, что найдены минимум 2 линии перелома откоса
                            {
                                //Найти ближайшую линию к базовой линии - это бровка
                                Polyline3dInfo edgeLine = null;
                                double         minDist  = double.MaxValue;
                                foreach (Polyline3dInfo p3dI in pickedPtSlopeLines)
                                {
                                    Point3d ptOnLine = p3dI.Poly2d.GetClosestPointTo(nearestPtOnBase, false);
                                    double  distance = ptOnLine.DistanceTo(nearestPtOnBase);
                                    if (distance < minDist)
                                    {
                                        minDist  = distance;
                                        edgeLine = p3dI;
                                    }
                                }



                                Point3d nearestPtOnEdge = edgeLine.Poly2d.GetClosestPointTo(pickedPt, true);       //найти ближайшую точку бровки

                                double pickedParameterEdge = edgeLine.Poly2d.GetParameterAtPoint(nearestPtOnEdge); //параметр бровки в этой точке

                                //Найти касательную к бровке
                                Vector3d tangentVector = edgeLine.Poly2d.GetFirstDerivative(pickedParameterEdge);

                                double rotateAngle = toTheRight.Value ? -Math.PI / 2 : Math.PI / 2;

                                Vector3d          spillWayVector = tangentVector.RotateBy(rotateAngle, Vector3d.ZAxis).GetNormal();//вектор водосброса, перпендикулярный бровке
                                Line              spillWayAxis   = new Line(nearestPtOnEdge, nearestPtOnEdge + spillWayVector);
                                Point3dCollection intersections  = new Point3dCollection();
                                baseLine.Poly2d.IntersectWith(spillWayAxis, Intersect.ExtendArgument,
                                                              horizontalPlane, intersections,
                                                              new IntPtr(0), new IntPtr(0));
                                if (intersections.Count > 0)
                                {
                                    Point3d basePt = intersections[0];//Точка пересечения оси водосброса с КПЧ
                                    //Найти точки пересечения перпендикуляра к ОТК0 и остальными линиями откоса
                                    //Отсортировать все линии по удаленности от КПЧ в этой точке
                                    SortedDictionary <Point3d, Polyline3dInfo> intersectionPts
                                        = new SortedDictionary <Point3d, Polyline3dInfo>(new PtsSortComparer(basePt));
                                    pickedPtSlopeLines.Add(baseLine);
                                    foreach (Polyline3dInfo p3dI in pickedPtSlopeLines)
                                    {
                                        intersections.Clear();
                                        p3dI.Poly2d.IntersectWith(spillWayAxis, Intersect.ExtendArgument,
                                                                  horizontalPlane, intersections,
                                                                  new IntPtr(0), new IntPtr(0));
                                        if (intersections.Count > 0)
                                        {
                                            intersectionPts.Add(intersections[0], p3dI);
                                        }
                                    }

                                    if (intersectionPts.Count == pickedPtSlopeLines.Count)//Проверить, что все пересечения найдены
                                    {
                                        //intersectionPts содержит все линии с точками пересечения в нужном порядке,
                                        //но все точки пересечения лежат на плоскости XY
                                        //Расчитать трехмерные точки
                                        Point3dCollection pts = new Point3dCollection();
                                        foreach (KeyValuePair <Point3d, Polyline3dInfo> kvp in intersectionPts)
                                        {
                                            Point3d pt2d = kvp.Key;
                                            pt2d = kvp.Value.Poly2d.GetClosestPointTo(pt2d, false);//по какой-то причине в некоторых случаях без этой строки вылетала ошибка при получении параметра
                                            double  param = kvp.Value.Poly2d.GetParameterAtPoint(pt2d);
                                            Point3d pt3d  = kvp.Value.Poly3d.GetPointAtParameter(param);
                                            pts.Add(pt3d);
                                        }


                                        using (Transaction tr = db.TransactionManager.StartTransaction())
                                        {
                                            //Регистрация приложения
                                            Utils.RegisterApp(db, tr);


                                            ObjectId layerId = Utils.CreateLayerIfNotExists("ВОДОСБРОС", db, tr, null,
                                                                                            Color.FromColorIndex(ColorMethod.ByAci, 150), LineWeight.LineWeight030);


                                            BlockTable       bt = tr.GetObject(db.BlockTableId, OpenMode.ForRead) as BlockTable;
                                            BlockTableRecord ms
                                                = (BlockTableRecord)tr.GetObject(bt[BlockTableRecord.ModelSpace], OpenMode.ForWrite);

                                            //Вычерчивание 3d полилинии по линии водосброса
                                            using (Polyline3d poly3d = new Polyline3d())
                                            {
                                                poly3d.LayerId  = layerId;
                                                poly3d.PolyType = Poly3dType.SimplePoly;
                                                ms.AppendEntity(poly3d);
                                                tr.AddNewlyCreatedDBObject(poly3d, true);

                                                foreach (Point3d pt in pts)
                                                {
                                                    PolylineVertex3d vertex = new PolylineVertex3d(pt);
                                                    poly3d.AppendVertex(vertex);
                                                    tr.AddNewlyCreatedDBObject(vertex, true);
                                                }


                                                //В расширенные данные записать название водосброса
                                                poly3d.XData = new ResultBuffer(
                                                    new TypedValue(1001, Constants.AppName),
                                                    new TypedValue(1000, spillwayNum.ToString()));
                                            }

                                            tr.Commit();
                                        }


                                        Vector3d baseVector = Vector3d.YAxis;
                                        int      sign       = Math.Sign(baseVector.CrossProduct(spillWayVector).Z);
                                        double   rotation   = spillWayVector.GetAngleTo(baseVector) * sign; //в радианах
                                        rotation = rotation * 180 / (Math.PI);                              //в градусах
                                        List <Slope> slopes = new List <Slope>();
                                        //Сохраниение расположения водосброса и всех уклонов
                                        for (int i = 0; i < pts.Count - 1; i++)
                                        {
                                            Point3d pt1    = pts[i];
                                            Point3d pt2    = pts[i + 1];
                                            Point2d pt1_2d = new Point2d(pt1.X, pt1.Y);
                                            Point2d pt2_2d = new Point2d(pt2.X, pt2.Y);

                                            double len = pt1_2d.GetDistanceTo(pt2_2d);
                                            if (len > 0)
                                            {
                                                double s = (pt2.Z - pt1.Z) / len;
                                                slopes.Add(new Slope()
                                                {
                                                    S = s, Len = len
                                                });
                                            }
                                        }

                                        SpillwayPosition spillwayPosition = new SpillwayPosition()
                                        {
                                            Name       = spillwayNum.ToString(),
                                            X          = pts[0].X,
                                            Y          = pts[0].Y,
                                            Z          = pts[0].Z,
                                            Z_Rotation = rotation,
                                            ToTheRight = toTheRight.Value,
                                            Slopes     = slopes
                                        };
                                        spillwayNum++;
                                        positionData.SpillwayPositions.Add(spillwayPosition);
                                    }
                                }
                            }
                        }
                        else
                        {
                            //ed.WriteMessage("\nвыбор закончен");

                            break;
                        }
                    }



                    //ed.WriteMessage("\nпродолжение выполнения");
                    //Сериализация расположений. Сохранить xml в папку рядом с файлом
                    if (positionData.SpillwayPositions.Count > 0)
                    {
                        //TODO: Учесть возможные ошибки из-за отсутствия прав
                        string filename = null;
                        int    n        = 0;
                        do
                        {
                            filename = Path.Combine(Path.GetDirectoryName(adoc.Name),
                                                    Path.GetFileNameWithoutExtension(adoc.Name) /*"SpillwayPositions"*/ + "_" + n + ".xml");
                            n++;
                        } while (File.Exists(filename));


                        XmlSerializer xmlSerializer = new XmlSerializer(typeof(PositionData));
                        using (StreamWriter sw = new StreamWriter(filename))
                        {
                            xmlSerializer.Serialize(sw, positionData);
                        }
                        //Cообщение о том, что все выполнено
                        ed.WriteMessage("\nПоложение водосбросов сохранено в файле " + filename);
                    }
                }
            }
            catch (System.Exception ex)
            {
                //Utils.ErrorToCommandLine(ed, "Ошибка при извлечении расположений водосбросов", ex);
                CommonException(ex, "Ошибка при извлечении расположений водосбросов");
            }
            finally
            {
                foreach (Polyline3d p3d in highlighted)
                {
                    p3d.Unhighlight();
                }
            }
        }
        private double Cosine(Point2d pt)
        {
            double d = _p0.GetDistanceTo(pt);

            return(d == 0.0 ? 1.0 : Math.Round((pt.X - _p0.X) / d, 9));
        }
示例#22
0
        public void BD2()
        {
            Document doc        = Application.DocumentManager.MdiActiveDocument;
            Database db         = HostApplicationServices.WorkingDatabase;
            Editor   ed         = doc.Editor;
            string   clayername = db.GetCurrentLayerName();
            string   xckPath    = Tools.GetCurrentPath() + @"\BaseDwgs\常用图块.dwg";
            string   blkname    = "LED筒灯";

            ed.WriteMessage("\n百福工具箱——快速通道照明灯具");

            //输入天花灯具的起始点和终止点
            PromptPointResult ppr1 = ed.GetPoint("\n请选择起始点");

            if (ppr1.Status == PromptStatus.OK)
            {
                Point2d            spt = new Point2d(ppr1.Value.X, ppr1.Value.Y);
                PromptPointOptions ppo = new PromptPointOptions("\n请选择终止点")
                {
                    BasePoint    = ppr1.Value,
                    UseBasePoint = true
                };
                PromptPointResult ppr2 = ed.GetPoint(ppo);
                if (ppr2.Status == PromptStatus.OK)
                {
                    Point2d ept = new Point2d(ppr2.Value.X, ppr2.Value.Y);
                    double  dis = spt.GetDistanceTo(ept);

                    PromptDoubleOptions pdo = new PromptDoubleOptions("\n请输入间距,默认为1200mm")
                    {
                        AllowNegative = false, //不允许输入负数
                        DefaultValue  = 1200   //设置默认值
                    };
                    PromptDoubleResult pdr = ed.GetDouble(pdo);
                    if (pdr.Status == PromptStatus.OK)
                    {
                        double jj = pdr.Value;
                        int    n  = (int)(dis / jj);
                        jj = dis / n;

                        while (jj >= 1200)
                        {
                            n++;
                            jj = dis / n;
                        }

                        Vector2d vec         = (ept - spt) / n;
                        Point3d  insertPoint = new Point3d(spt.X, spt.Y, 0);

                        db.SetCurrentLayer("BF-灯具");

                        for (int i = 1; i <= n; i++)
                        {
                            insertPoint = new Point3d(insertPoint.X + vec.X, insertPoint.Y + vec.Y, 0);
                            using (Transaction trans = db.TransactionManager.StartTransaction())
                            {
                                LayerTable lt = (LayerTable)trans.GetObject(db.LayerTableId, OpenMode.ForRead);
                                db.ImportBlocksFromDWG(xckPath, blkname);
                                ObjectId spaceId = db.CurrentSpaceId;//获取当前空间(模型空间或图纸空间)

                                spaceId.InsertBlockReference("BF-灯具", blkname, insertPoint, new Scale3d(1), 0);
                                trans.Commit();
                            }
                        }
                        ed.WriteMessage($"\n筒灯间距是{string.Format("{0:F2}", jj)}mm");
                    }
                }
            }
            db.SetCurrentLayer(clayername);
        }
示例#23
0
        public void TcJianTou()
        {
            this.point2dCollection_0 = new Point2dCollection();
            this.point3d_1           = CAD.GetPoint("选择插入点: ");
            Point3d point3d;

            if (!(this.point3d_1 == point3d))
            {
                Point2dCollection point2dCollection = this.point2dCollection_0;
                Point2d           point2d;
                point2d..ctor(this.point3d_1.X, this.point3d_1.Y);
                point2dCollection.Add(point2d);
                Polyline polyline = new Polyline();
                short    num;
                for (;;)
                {
                    num = checked ((short)(this.point2dCollection_0.Count - 1));
                    if (num >= 1)
                    {
                        Class36.smethod_64(polyline.ObjectId);
                        polyline = new Polyline();
                        polyline.SetDatabaseDefaults();
                        short num2 = 0;
                        short num3 = num;
                        short num4 = num2;
                        for (;;)
                        {
                            short num5 = num4;
                            short num6 = num3;
                            if (num5 > num6)
                            {
                                break;
                            }
                            polyline.AddVertexAt((int)num4, this.point2dCollection_0[(int)num4], 0.0, 0.0, 0.0);
                            num4 += 1;
                        }
                        CAD.AddEnt(polyline);
                    }
                    short num7 = this.GangJin();
                    if (num7 != 1)
                    {
                        break;
                    }
                    this.point3d_1 = this.point3d_2;
                    Point2dCollection point2dCollection2 = this.point2dCollection_0;
                    point2d..ctor(this.point3d_2.X, this.point3d_2.Y);
                    point2dCollection2.Add(point2d);
                }
                num = checked ((short)(this.point2dCollection_0.Count - 1));
                if (num >= 1)
                {
                    Class36.smethod_64(polyline.ObjectId);
                    polyline = new Polyline();
                    polyline.SetDatabaseDefaults();
                    short num8  = 0;
                    short num9  = num;
                    short num10 = num8;
                    for (;;)
                    {
                        short num11 = num10;
                        short num6  = num9;
                        if (num11 > num6)
                        {
                            break;
                        }
                        polyline.AddVertexAt((int)num10, this.point2dCollection_0[(int)num10], 0.0, 0.0, 0.0);
                        num10 += 1;
                    }
                    Point2d p        = this.point2dCollection_0[(int)num];
                    Point2d point2d2 = this.point2dCollection_0[(int)(checked (num - 1))];
                    double  angle    = p.GetVectorTo(point2d2).Angle;
                    double  num12    = p.GetDistanceTo(point2d2);
                    num12 = Math.Min(num12, 400.0);
                    Point2d point2dAngle = CAD.GetPoint2dAngle(p, num12, angle * 180.0 / 3.1415926535897931);
                    polyline.AddVertexAt((int)num, this.point2dCollection_0[(int)num], 0.0, 0.0, 90.0);
                    polyline.AddVertexAt((int)(checked (num + 1)), point2dAngle, 0.0, 90.0, 0.0);
                    CAD.AddEnt(polyline);
                }
            }
        }
示例#24
0
        TP4()
        {
            gp.pnt3d1 = Pub.pnt3dO;
            gp.pnt3d2 = Pub.pnt3dO;
            ps        = PromptStatus.Cancel;
            object mode = 0;

            BaseObjs.acadActivate();
            Vector3d v3d = Vector3d.XAxis;

            try
            {
                elev = UserInput.getCogoPoint("\nPick Cogo Point 1: ", out idCgPnt1, ObjectId.Null, osMode: 8);
                if (elev == "")
                {
                    return;
                }
                else
                {
                    gp.pnt3d1 = idCgPnt1.getCogoPntCoordinates();
                }

                elev = UserInput.getCogoPoint("\nPick Cogo Point 2: ", out idCgPnt2, ObjectId.Null, osMode: 8);
                if (elev == "")
                {
                    return;
                }
                else
                {
                    gp.pnt3d2 = idCgPnt2.getCogoPntCoordinates();
                }

                mode = SnapMode.getOSnap();
                SnapMode.setOSnap(8);

                gp.pnt3dX = Pub.pnt3dO;
                gp.pnt3dT = Pub.pnt3dO;

                System.Windows.Forms.Keys mods = System.Windows.Forms.Control.ModifierKeys;
                bool shift   = (mods & System.Windows.Forms.Keys.Shift) > 0;
                bool control = (mods & System.Windows.Forms.Keys.Control) > 0;
                gp.shift = shift;

                gp.pnt3dT = gPnt.getPoint("\nSelect Target location (CogoPoint for xSlope and distance / pick side to enter xSlope and distance: ", "cmdTP");

                if (gp.pnt3dT == Pub.pnt3dO)
                {
                    return;
                }
                else if (gp.pnt3dT.Z == 0)
                {
                    gp.pnt3dX = gc.calcBasePnt3d(gp.pnt3dT, gp.pnt3d1, gp.pnt3d2);
                    if (gp.pnt3dX == Pub.pnt3dO)
                    {
                        return;
                    }

                    escaped = UserInput.getUserInputDoubleAsString("\nEnter Cross Slope (+ or -): ", out xSlope, xSlope);
                    if (escaped)
                    {
                        return;
                    }

                    escaped = UserInput.getUserInputDoubleAsString("\nEnter Width: ", out width, width);
                    if (escaped)
                    {
                        return;
                    }
                    double dist  = gp.pnt3d1.getDistance(gp.pnt3d2);
                    double distX = gp.pnt3d1.getDistance(gp.pnt3dX);

                    Point2d pnt2dX = gp.pnt3dX.Convert2d(BaseObjs.xyPlane);
                    Point2d pnt2dT = gp.pnt3dT.Convert2d(BaseObjs.xyPlane);
                    double  distT  = pnt2dX.GetDistanceTo(pnt2dT);

                    gp.pnt3dT = new Point3d(gp.pnt3dT.X, gp.pnt3dT.Y, gp.pnt3dX.Z + distT * double.Parse(xSlope));

                    v3d  = gp.pnt3dT - gp.pnt3dX;
                    v3d *= double.Parse(width) / distT;
                }
                else
                {
                    gp.pnt3dX = gc.calcBasePnt3d(gp.pnt3dT, gp.pnt3d1, gp.pnt3d2);
                    if (gp.pnt3dX == Pub.pnt3dO)
                    {
                        return;
                    }

                    CgPnt.setPoint(gp.pnt3dX, out pntNum, "CPNT-ON");

                    v3d = gp.pnt3dT - gp.pnt3dX;
                }
            }
            catch (System.Exception ex)
            {
                BaseObjs.writeDebug(ex.Message + " cmdTP.cs: line: 336");
            }
            finally
            {
                SnapMode.setOSnap((int)mode);
            }

            ObjectId idPoly   = ObjectId.Null;
            Point3d  pnt3d3   = idCgPnt2.getCogoPntCoordinates() + v3d;
            ObjectId idCgPnt3 = pnt3d3.setPoint(out pntNum);
            Point3d  pnt3d4   = idCgPnt1.getCogoPntCoordinates() + v3d;
            ObjectId idCgPnt4 = pnt3d4.setPoint(out pntNum);

            List <ObjectId> idCgPnts = new List <ObjectId> {
                idCgPnt1, idCgPnt2
            };

            BrkLine.makeBreakline(apps.lnkBrks, "cmdTP4", out idPoly, idCgPnts);

            idCgPnts = new List <ObjectId> {
                idCgPnt2, idCgPnt3
            };
            BrkLine.makeBreakline(apps.lnkBrks, "cmdTP4", out idPoly, idCgPnts);

            idCgPnts = new List <ObjectId> {
                idCgPnt3, idCgPnt4
            };
            BrkLine.makeBreakline(apps.lnkBrks, "cmdTP4", out idPoly, idCgPnts);

            idCgPnts = new List <ObjectId> {
                idCgPnt4, idCgPnt1
            };
            BrkLine.makeBreakline(apps.lnkBrks, "cmdTP4", out idPoly, idCgPnts);
        }
        private static Entity DrawPart(Segment[] segs, Point[] points, Point[] densifiedPoints, bool closePart, bool hasZ, double defaultElevation)
        {
            double num = 0.0;

            if (segs != null)
            {
                if (segs.Length == 1)
                {
                    CircularArc        circularArc = segs[0] as CircularArc;
                    EllipticArc        ellipticArc = segs[0] as EllipticArc;
                    BezierCurve        bezierCurve = segs[0] as BezierCurve;
                    ArcGIS10Types.Line line        = segs[0] as ArcGIS10Types.Line;
                    if (circularArc != null)
                    {
                        if (((PointN)circularArc.FromPoint).X == ((PointN)circularArc.ToPoint).X && ((PointN)circularArc.FromPoint).Y == ((PointN)circularArc.ToPoint).Y)
                        {
                            return(GIS2CAD.DrawCircle(circularArc, defaultElevation));
                        }
                        return(GIS2CAD.DrawCircularArc(circularArc, defaultElevation, densifiedPoints));
                    }
                    else if (ellipticArc != null)
                    {
                        if (!ellipticArc.IsCounterClockwise)
                        {
                            return(AGSEllipticalArc.ToCadSpline(ellipticArc, defaultElevation));
                        }
                        return(AGSEllipticalArc.ToCadEllipse(ellipticArc, defaultElevation));
                    }
                    else
                    {
                        if (line != null)
                        {
                            return(GIS2CAD.DrawPolyline(densifiedPoints, false));
                        }
                        if (bezierCurve != null)
                        {
                            return(GIS2CAD.DrawPolyline(densifiedPoints, closePart));
                        }
                    }
                }
                else if (segs.Length > 1)
                {
                    PointN pointN = segs[0].FromPoint as PointN;
                    num = pointN.Z;
                    if (num == 0.0)
                    {
                        num = defaultElevation;
                    }
                    if (GIS2CAD.CanBeDrawnAsPolyline(segs))
                    {
                        var polyline = new Autodesk.AutoCAD.DatabaseServices.Polyline();
                        polyline.ColorIndex = (256);
                        int    num2    = 0;
                        PointN pointN2 = (PointN)segs[0].ToPoint;
                        for (int i = 0; i < segs.Length; i++)
                        {
                            Segment     segment      = segs[i];
                            CircularArc circularArc2 = segment as CircularArc;
                            var         line2        = segment as ArcGIS10Types.Line;
                            if (line2 != null)
                            {
                                PointN pointN3 = (PointN)line2.FromPoint;
                                polyline.AddVertexAt(num2++, new Point2d(pointN3.X, pointN3.Y), 0.0, -1.0, -1.0);
                                pointN2 = (PointN)line2.ToPoint;
                            }
                            else if (circularArc2 != null)
                            {
                                PointN pointN4 = (PointN)circularArc2.CenterPoint;
                                PointN pointN5 = (PointN)circularArc2.FromPoint;
                                PointN pointN6 = (PointN)circularArc2.ToPoint;
                                new Point2d(pointN5.X - pointN4.X, pointN5.Y - pointN4.Y);
                                new Point2d(pointN6.X - pointN4.X, pointN6.Y - pointN4.Y);
                                Point2d point2d     = new Point2d(pointN5.X, pointN5.Y);
                                Point2d centerPoint = new Point2d(pointN4.X, pointN4.Y);
                                Point2d point2d2    = new Point2d(pointN6.X, pointN6.Y);
                                double  num3        = Math.Abs(centerPoint.GetDistanceTo(point2d));
                                double  num4        = Math.Abs(point2d.GetDistanceTo(point2d2));
                                double  num5        = num3;
                                double  num6        = num3;
                                double  d           = (num5 * num5 + num6 * num6 - num4 * num4) / (2.0 * num5 * num6);
                                double  num7        = Math.Acos(d);
                                num7 = GIS2CAD.CalcThetaFromVectors(point2d, point2d2, centerPoint, circularArc2.IsCounterClockwise);
                                double num8 = Math.Tan(num7 / 4.0);
                                if (!circularArc2.IsCounterClockwise)
                                {
                                    num8 *= -1.0;
                                }
                                polyline.AddVertexAt(num2++, point2d, num8, -1.0, -1.0);
                                pointN2 = pointN6;
                            }
                        }
                        polyline.AddVertexAt(num2, new Point2d(pointN2.X, pointN2.Y), 0.0, -1.0, -1.0);
                        if (closePart)
                        {
                            polyline.Closed = (true);
                        }
                        return(polyline);
                    }
                    return(GIS2CAD.Draw3dPline(densifiedPoints, closePart));
                }
            }
            else if (points != null)
            {
                if (points.Length == 2)
                {
                    var line3 = new Autodesk.AutoCAD.DatabaseServices.Line();
                    line3.ColorIndex = (256);
                    GIS2CAD.AdjustZ(ref points, defaultElevation);
                    Point3d startPoint = GIS2CAD.ToCadPoint3d((PointN)points[0]);
                    Point3d endPoint   = GIS2CAD.ToCadPoint3d((PointN)points[1]);
                    line3.StartPoint = (startPoint);
                    line3.EndPoint   = (endPoint);
                    return(line3);
                }
                if (points.Length > 0)
                {
                    if (!GIS2CAD.IsPlanar(points))
                    {
                        try
                        {
                            Document document           = AfaDocData.ActiveDocData.Document;
                            var      database           = document.Database;
                            var      transactionManager = document.TransactionManager;
                            using (document.LockDocument())
                            {
                                using (Transaction transaction = transactionManager.StartTransaction())
                                {
                                    BlockTable       blockTable       = (BlockTable)transaction.GetObject(database.BlockTableId, 0);
                                    BlockTableRecord blockTableRecord = (BlockTableRecord)transaction.GetObject(blockTable[(BlockTableRecord.ModelSpace)], (OpenMode)1);
                                    Polyline3d       polyline3d       = new Polyline3d();
                                    polyline3d.ColorIndex = (256);
                                    blockTableRecord.AppendEntity(polyline3d);
                                    transaction.AddNewlyCreatedDBObject(polyline3d, true);
                                    Point[] array = points;
                                    for (int j = 0; j < array.Length; j++)
                                    {
                                        PointN           srcPt            = (PointN)array[j];
                                        PolylineVertex3d polylineVertex3d = new PolylineVertex3d(GIS2CAD.ToCadPoint3d(srcPt));
                                        polyline3d.AppendVertex(polylineVertex3d);
                                        transaction.AddNewlyCreatedDBObject(polylineVertex3d, true);
                                    }
                                    if (closePart)
                                    {
                                        polyline3d.Closed = (true);
                                    }
                                    document.TransactionManager.QueueForGraphicsFlush();
                                    document.TransactionManager.FlushGraphics();
                                    document.Editor.UpdateScreen();
                                    transaction.Commit();
                                    return(polyline3d);
                                }
                            }
                        }
                        catch (System.Exception ex)
                        {
                            string arg_526_0 = ex.Message;
                        }
                    }
                    var polyline2 = new Autodesk.AutoCAD.DatabaseServices.Polyline();
                    polyline2.ColorIndex = (256);
                    polyline2.Elevation  = (num);
                    num = ((PointN)points[0]).Z;
                    if (num == 0.0)
                    {
                        num = defaultElevation;
                    }
                    int     num9   = 0;
                    Point[] array2 = points;
                    for (int k = 0; k < array2.Length; k++)
                    {
                        PointN pointN7 = (PointN)array2[k];
                        polyline2.AddVertexAt(num9++, new Point2d(pointN7.X, pointN7.Y), 0.0, -1.0, -1.0);
                    }
                    if (closePart)
                    {
                        polyline2.Closed = (true);
                    }
                    return(polyline2);
                }
            }
            return(null);
        }
示例#26
0
        // overload no scale factor or set the view - just make the layout
        public void LayoutAndViewport(Database db, string layoutName, out ObjectId rvpid, string deviceName, string mediaName, out ObjectId id)
        {
            // set default values
            rvpid = new ObjectId();
            bool          flagVp        = false; // flag to create a new floating view port
            double        viewSize      = (double)Application.GetSystemVariable("VIEWSIZE");
            double        height        = viewSize;
            double        width         = viewSize;
            Point2d       loCenter      = new Point2d(); // layout center point
            Point2d       vpLowerCorner = new Point2d();
            Point2d       vpUpperCorner = new Point2d();
            Document      doc           = Application.DocumentManager.MdiActiveDocument;
            LayoutManager lm            = LayoutManager.Current;

            id = lm.CreateLayout(layoutName);

            using (Transaction tr = db.TransactionManager.StartTransaction())
            {
                Layout lo = tr.GetObject(id, OpenMode.ForWrite, false) as Layout;
                if (lo != null)
                {
                    lm.CurrentLayout = lo.LayoutName; // make it current!

                    #region do some plotting settings here for the paper size...
                    ObjectId loid = lm.GetLayoutId(lo.LayoutName);

                    PlotInfo pi = new PlotInfo();
                    pi.Layout = loid;

                    PlotSettings          ps  = new PlotSettings(false);
                    PlotSettingsValidator psv = PlotSettingsValidator.Current;

                    psv.RefreshLists(ps);
                    psv.SetPlotConfigurationName(ps, deviceName, mediaName);
                    psv.SetPlotType(ps, Autodesk.AutoCAD.DatabaseServices.PlotType.Layout);
                    psv.SetPlotPaperUnits(ps, PlotPaperUnit.Inches);
                    psv.SetUseStandardScale(ps, true);
                    psv.SetStdScaleType(ps, StdScaleType.ScaleToFit); // use this as default

                    pi.OverrideSettings = ps;

                    PlotInfoValidator piv = new PlotInfoValidator();
                    piv.Validate(pi);

                    lo.CopyFrom(ps);

                    PlotConfig pc = PlotConfigManager.CurrentConfig;
                    // returns data in millimeters...
                    MediaBounds mb = pc.GetMediaBounds(mediaName);

                    Point2d p1 = mb.LowerLeftPrintableArea;
                    Point2d p3 = mb.UpperRightPrintableArea;
                    Point2d p2 = new Point2d(p3.X, p1.Y);
                    Point2d p4 = new Point2d(p1.X, p3.Y);

                    // convert millimeters to inches
                    double mm2inch = 25.4;
                    height = p1.GetDistanceTo(p4) / mm2inch;
                    width  = p1.GetDistanceTo(p2) / mm2inch;

                    vpLowerCorner = lo.PlotOrigin;
                    vpUpperCorner = new Point2d(vpLowerCorner.X + width, vpLowerCorner.Y + height);
                    LineSegment2d seg = new LineSegment2d(vpLowerCorner, vpUpperCorner);
                    loCenter = seg.MidPoint;
                    #endregion

                    if (lo.GetViewports().Count == 1) // Viewport was not created by default
                    {
                        // the create by default view ports on new layouts it
                        // is off we need to mark a flag to generate a new one
                        // in another transaction - out of this one
                        flagVp = true;
                    }
                    else if (lo.GetViewports().Count == 2) // create Viewports by default it is on
                    {
                        // extract the last item from the collection
                        // of view ports inside of the layout
                        int      i    = lo.GetViewports().Count - 1;
                        ObjectId vpId = lo.GetViewports()[i];

                        if (!vpId.IsNull)
                        {
                            Viewport vp = tr.GetObject(vpId, OpenMode.ForWrite, false) as Viewport;
                            if (vp != null)
                            {
                                vp.Height      = height;                                   // change height
                                vp.Width       = width;                                    // change width
                                vp.CenterPoint = new Point3d(loCenter.X, loCenter.Y, 0.0); // change center
                                //vp.ColorIndex = 1; // debug

                                // zoom to the Viewport extents
                                Zoom(new Point3d(vpLowerCorner.X, vpLowerCorner.Y, 0.0),
                                     new Point3d(vpUpperCorner.X, vpUpperCorner.Y, 0.0), new Point3d(), 1.0);

                                rvpid = vp.ObjectId; // return the output ObjectId to out...
                            }
                        }
                    }
                }
                tr.Commit();
            } // end of transaction

            // we need another transaction to create a new paper space floating Viewport
            if (flagVp)
            {
                using (Transaction tr = db.TransactionManager.StartTransaction())
                {
                    BlockTable       bt     = (BlockTable)tr.GetObject(db.BlockTableId, OpenMode.ForRead);
                    BlockTableRecord btr_ps = (BlockTableRecord)tr.GetObject(bt[BlockTableRecord.PaperSpace], OpenMode.ForWrite);

                    Viewport vp = new Viewport();
                    vp.Height      = height;                                   // set the height
                    vp.Width       = width;                                    // set the width
                    vp.CenterPoint = new Point3d(loCenter.X, loCenter.Y, 0.0); // set the center
                    //vp.ColorIndex = 2; // debug

                    btr_ps.AppendEntity(vp);
                    tr.AddNewlyCreatedDBObject(vp, true);

                    vp.On = true; // make it accessible!

                    // zoom to the Viewport extents
                    Zoom(new Point3d(vpLowerCorner.X, vpLowerCorner.Y, 0.0),
                         new Point3d(vpUpperCorner.X, vpUpperCorner.Y, 0.0), new Point3d(), 1.0);

                    rvpid = vp.ObjectId; // return the ObjectId to the out...

                    tr.Commit();
                } // end of transaction
            }
        }
示例#27
0
        public override bool WorldDraw(
            Autodesk.AutoCAD.GraphicsInterface.Drawable drawable,
            Autodesk.AutoCAD.GraphicsInterface.WorldDraw wd)
        {
            base.WorldDraw(drawable, wd);

            Polyline pline = (Polyline)drawable;

            double length         = pline.Length;
            int    numberOfLabels = (int)(length / labelDist);

            if (numberOfLabels == 0)
            {
                numberOfLabels = 1;
            }

            for (int i = 0; i < numberOfLabels + 1; i++)
            {
                #region Size label
                double dist = labelDist * i;
                if (numberOfLabels == 1)
                {
                    dist = length / 2;
                }
                Point3d pt     = pline.GetPointAtDist(dist);
                int     dn     = IntersectUtilities.PipeSchedule.GetPipeDN(pline);
                string  system =
                    IntersectUtilities.PipeSchedule.GetPipeType(pline) == IntersectUtilities.PipeSchedule.PipeTypeEnum.Twin ?
                    "T" : "E";
                string label = $"DN{dn}-{system}";

                Vector3d deriv = pline.GetFirstDerivative(pt);
                deriv = deriv.GetNormal();

                Vector3d perp = deriv.GetPerpendicularVector();

                wd.Geometry.Text(
                    pt + perp * labelOffset, Vector3d.ZAxis, deriv, label, true, style);
                //pt + perp * labelOffset, Vector3d.ZAxis, deriv, labelHeight, 1.0, 0.0, label);

                //wd.Geometry.Text(
                //    pt + perp * labelOffset, Vector3d.ZAxis, deriv, labelHeight, 1.0, 0.0, label);
                #endregion
            }

            #region Buerør label
            int nrOfVertices = pline.NumberOfVertices;

            for (int j = 0; j < pline.NumberOfVertices - 1; j++)
            {
                //Guard against already cut out curves
                double b = pline.GetBulgeAt(j);
                if (b == 0)
                {
                    continue;
                }
                Point2d fP = pline.GetPoint2dAt(j);
                Point2d sP = pline.GetPoint2dAt(j + 1);

                double u           = fP.GetDistanceTo(sP);
                double radius      = u * ((1 + b.Pow(2)) / (4 * Math.Abs(b)));
                double minRadius   = IntersectUtilities.PipeSchedule.GetPipeMinElasticRadius(pline, false);
                bool   isInSituBuk = IntersectUtilities.PipeSchedule.IsInSituBent(pline);
                //If radius is less than minRadius a buerør is detected
                //Split the pline in segments delimiting buerør and append

                Point3d fP3d = new Point3d(fP.X, fP.Y, 0);
                Point3d sP3d = new Point3d(sP.X, sP.Y, 0);

                double fL = pline.GetDistAtPoint(fP3d);
                double sL = pline.GetDistAtPoint(sP3d);

                Vector3d vec = pline.GetFirstDerivative(fP3d);
                vec = vec.GetNormal();
                vec = vec.GetPerpendicularVector();
                Point3d pt1 = fP3d + vec;
                Point3d pt2 = fP3d - vec;
                wd.Geometry.WorldLine(pt1, pt2);

                vec = pline.GetFirstDerivative(sP3d);
                vec = vec.GetNormal();
                vec = vec.GetPerpendicularVector();
                pt1 = sP3d + vec;
                pt2 = sP3d - vec;
                wd.Geometry.WorldLine(pt1, pt2);

                string label;
                if (radius > minRadius)
                {
                    label = $"Elastisk R{radius.ToString("0.##")}";
                }
                else
                {
                    double arcLength = sL - fL;

                    if (isInSituBuk)
                    {
                        label = $"In-situ buk R{radius.ToString("0.##")} L{arcLength.ToString("0.##")}";
                    }
                    else
                    {
                        double angle = arcLength / ((Math.PI / 180) * radius);
                        label = $"Buerør R{radius.ToString("0.##")} L{arcLength.ToString("0.##")} A{angle.ToString("0.##")}";
                    }
                }

                CircularArc2d arc     = pline.GetArcSegment2dAt(j);
                Point2d[]     samples = arc.GetSamplePoints(3);
                Point3d       midPt   = new Point3d(samples[1].X, samples[1].Y, 0);

                Vector3d deriv = pline.GetFirstDerivative(midPt);
                deriv = deriv.GetNormal();

                Vector3d perp = deriv.GetPerpendicularVector();
                if (b > 0)
                {
                    perp = -perp;
                }

                //wd.Geometry.Text(
                //    midPt + perp * (labelOffset + labelHeight + 0.7), Vector3d.ZAxis, deriv, labelHeight, 1.0, 0.0, label);
                wd.Geometry.Text(
                    midPt + perp * (labelOffset + labelHeight + 0.7), Vector3d.ZAxis, deriv, label, true, style);
            }
            #endregion

            return(true);
        }
示例#28
0
        public static void AddSpline()
        {
            if (!Ativacao())
            {
                MessageBox.Show("Esta API não está ativada. Entre em contato com a SELTTE!");
                return;
            }

            pt1x = GetPoint();

            // Caso não se clique em lugar algum, o comando é finalizado
            if (pt1x.X == 0.0 && pt1x.Y == 0.0)
            {
                Editor editor = Autodesk.AutoCAD.ApplicationServices.Application.DocumentManager.MdiActiveDocument.Editor;

                editor.WriteMessage("\n-> Cancelado!\n");
                return;
            }

            pt2x = GetPoint();

            // Caso não se clique em lugar algum, o comando é finalizado
            if (pt2x.X == 0.0 && pt2x.Y == 0.0)
            {
                Editor editor = Autodesk.AutoCAD.ApplicationServices.Application.DocumentManager.MdiActiveDocument.Editor;

                editor.WriteMessage("\n-> Cancelado!\n");
                return;
            }

            pt1 = new Point2d(pt1x.X, pt1x.Y);
            pt2 = new Point2d(pt2x.X, pt2x.Y);

            if (pt1.X > pt2.X || pt1.Y > pt2.Y)
            {
                Point2d ptx = pt1;

                pt1 = pt2;
                pt2 = ptx;
            }

            // Get the current document and database
            Document acDoc   = Autodesk.AutoCAD.ApplicationServices.Application.DocumentManager.MdiActiveDocument;
            Database acCurDb = acDoc.Database;
            Editor   ed      = acDoc.Editor;

            // Start a transaction
            using (Transaction acTrans = acCurDb.TransactionManager.StartTransaction())
            {
                // Open the Block table for read
                BlockTable acBlkTbl = acTrans.GetObject(acCurDb.BlockTableId, OpenMode.ForRead) as BlockTable;

                // Open the Block table record Model space for write
                BlockTableRecord acBlkTblRec = acTrans.GetObject(acBlkTbl[BlockTableRecord.ModelSpace], OpenMode.ForWrite) as BlockTableRecord;

                double anglePt1Pt2 = pt1.GetVectorTo(pt2).Angle;

                if (anglePt1Pt2 > Math.PI)
                {
                    anglePt1Pt2 -= Math.PI;
                }


                //PolarPoints(pt1.Add((pt2.Subtract(pt1.GetAsVector()) / 4).GetAsVector()), pt1.GetVectorTo(pt2).GetAngleTo(pt2.GetAsVector()) + Math.PI / 2, 10);
                Point2d pt3 = PolarPoints(pt1.Add(pt1.GetVectorTo(pt2) / 4), anglePt1Pt2 + Math.PI / 2, pt1.GetDistanceTo(pt2) * 0.1);
                Point2d pt4 = PolarPoints(pt2.Subtract((pt2.Subtract(pt1.GetAsVector()) / 4).GetAsVector()), anglePt1Pt2 - Math.PI / 2, pt1.GetDistanceTo(pt2) * 0.1);

                Point3d pt5 = new Point3d(pt1.X, pt1.Y, 0); // pt1 em 3d
                Point3d pt6 = new Point3d(pt3.X, pt3.Y, 0); // pt3 em 3d
                Point3d pt7 = new Point3d(pt4.X, pt4.Y, 0); // pt4 em 3d
                Point3d pt8 = new Point3d(pt2.X, pt2.Y, 0); // pt2 em 3d

                // Define the fit points for the spline
                Point3dCollection ptColl = new Point3dCollection
                {
                    pt5,
                    pt6,
                    pt7,
                    pt8
                };

                // Create a spline through (0, 0, 0), (5, 5, 0), and (10, 0, 0) with a
                // start and end tangency of (0.5, 0.5, 0.0)
                using (Spline acSpline = new Spline(ptColl, new Point3d(0.0000, 0.0000, 0.0000).GetAsVector(), new Point3d(0.0000, 0.0000, 0.0000).GetAsVector(), 0, 0.0))
                {
                    // Add the new object to the block table record and the transaction
                    acBlkTblRec.AppendEntity(acSpline);
                    acTrans.AddNewlyCreatedDBObject(acSpline, true);
                }

                acDoc.SendStringToExecute("Trim  ", true, false, false);

                // Save the new line to the database
                acTrans.Commit();
            }
        }
        /// <summary>
        /// 判断2d点是否在线段上
        /// </summary>
        /// <param name="p"></param>
        /// <param name="line"></param>
        /// <returns></returns>
        public bool IsPointOnLine(Point2d p, Line line)
        {
            var flag = p.GetDistanceTo(line.StartPoint.toPoint2d()) + p.GetDistanceTo(line.EndPoint.toPoint2d()) - line.Length < 0.00001;

            return(flag);
        }
示例#30
0
            //private bool joinedEdge = false;//test

            public void CalcPipePosition(Transaction tr, ObjectId tinSurfId, double defaultDepth, bool sameDepthEveryPt, BlockTableRecord ms)
            {
                //Нужно учитывать размеры колодцев при расчете положения ребра!
                //Колодцы бывают просто цилиндрические и просто коробчатые
                //Учитывать Rotation, BoundingShape, InnerDiameterOrWidth, InnerLength
                //Уточнить кривую в плане по которой идет труба с учетом размеров колодца

                //TODO: Как учесть, что блок прямоугольного колодца может не соответствовать колодцу по направлениям длины и ширины????

                PointOnCurve2d startSplitPt = null;
                PointOnCurve2d endSplitPt   = null;

                CivilDB.Structure strStart = null;
                CivilDB.Structure strEnd   = null;
                if (!StartNode.StructId.IsNull)
                {
                    strStart = (CivilDB.Structure)tr.GetObject(StartNode.StructId, OpenMode.ForRead);
                    //уточнить положение начала кривой в начале с учетом размеров колодца!
                    startSplitPt = GetSplitPt(strStart, true);
                }
                if (!EndNode.StructId.IsNull)
                {
                    strEnd = (CivilDB.Structure)tr.GetObject(EndNode.StructId, OpenMode.ForRead);
                    //уточнить положение конца кривой в начале с учетом размеров колодца!
                    endSplitPt = GetSplitPt(strEnd, false);
                }

                if (startSplitPt != null && endSplitPt != null && startSplitPt.Parameter >= endSplitPt.Parameter)
                {
                    //колодцы стоят вплотную друг к другу или залезают друг на друга. Места для трубы на остается
                    return;
                }

                //проход по составляющим кривой с отбрасыванием частей, отсекаемых колодцами
                //Curve2d.GetSplitCurves работает неправильно
                //Curve2d.Explode тоже не помогает
                if (startSplitPt == null)
                {
                    AddPtToPipePositionList(new XYZ(PositionCurve.StartPoint));
                }
                Curve2d[] segments  = PositionCurve.GetCurves();
                double    currParam = 0;

                foreach (Curve2d seg in segments)
                {
                    Interval interval = seg.GetInterval();
                    double   len      = seg.GetLength(interval.LowerBound, interval.UpperBound);

                    currParam += len;

                    //Если есть точка разбиения в начале и она еще не достигнута
                    if (startSplitPt != null)
                    {
                        if (startSplitPt.Parameter < currParam)
                        {
                            //точка разбиения находится на этой кривой. Ее нужно добавить в список
                            AddPtToPipePositionList(new XYZ(startSplitPt.Point));
                            startSplitPt = null;
                        }
                        else
                        {
                            //точка отсечения начала еще не достигнута, переход к следующей кривой
                            continue;
                        }
                    }


                    if (endSplitPt != null && endSplitPt.Parameter < currParam)
                    {
                        //точка разбиения находится на этой кривой. Ее нужно добавить в список
                        AddPtToPipePositionList(new XYZ(endSplitPt.Point));
                        endSplitPt = null;
                        break;//обход точек заканчивается
                    }

                    AddPtToPipePositionList(new XYZ(seg.EndPoint));
                }


                //Задание глубин заложения ребер по концам
                //- если не задана глубина заложения на одном из концов, сделать их равными
                //- если не задана глубина на обоих концах задать обоим концам глубину по умолчанию согласно вводу в окне
                CivilDB.TinSurface tinSurf         = (CivilDB.TinSurface)tr.GetObject(tinSurfId, OpenMode.ForRead);
                double             startElevByData = double.NegativeInfinity;
                double             endElevByData   = double.NegativeInfinity;

                if (StartPipeJunctionData != null && StartPipeJunctionData.JunctionLevel != double.NegativeInfinity)
                {
                    startElevByData = StartPipeJunctionData.JunctionLevel;
                    XYZ xyz = PipePositionList.First();
                    xyz.Z = startElevByData;
                }
                if (EndPipeJunctionData != null && EndPipeJunctionData.JunctionLevel != double.NegativeInfinity)
                {
                    endElevByData = EndPipeJunctionData.JunctionLevel;
                    XYZ xyz = PipePositionList.Last();
                    xyz.Z = endElevByData;
                }



                if (startElevByData != double.NegativeInfinity && endElevByData == double.NegativeInfinity)
                {
                    XYZ xyz = PipePositionList.Last();
                    xyz.Z = startElevByData;
                }
                else if (startElevByData == double.NegativeInfinity && endElevByData != double.NegativeInfinity)
                {
                    XYZ xyz = PipePositionList.First();
                    xyz.Z = endElevByData;
                }
                else if (startElevByData == double.NegativeInfinity && endElevByData == double.NegativeInfinity)
                {
                    XYZ xyz1 = PipePositionList.First();
                    SetElevBySurf(defaultDepth, tinSurf, xyz1);

                    XYZ xyz2 = PipePositionList.Last();
                    SetElevBySurf(defaultDepth, tinSurf, xyz2);
                }


                //- но не допускать, чтобы труба опускалась ниже дна колодца
                double sartElevByStr = double.NegativeInfinity;
                double endElevByStr  = double.NegativeInfinity;

                if (strStart != null && strStart.SumpElevation > PipePositionList.First().Z)
                {
                    sartElevByStr = strStart.SumpElevation;
                    PipePositionList.First().Z = sartElevByStr;
                }

                if (strEnd != null && strEnd.SumpElevation > PipePositionList.Last().Z)
                {
                    endElevByStr = strEnd.SumpElevation;
                    PipePositionList.Last().Z = endElevByStr;
                }
                //после корректировки уточнить отметку соседней точки если по ней нет данных
                if (sartElevByStr != double.NegativeInfinity &&
                    endElevByData == double.NegativeInfinity)
                {
                    XYZ xyz = PipePositionList.Last();
                    xyz.Z = sartElevByStr;
                }
                else if (startElevByData == double.NegativeInfinity &&
                         endElevByStr != double.NegativeInfinity)
                {
                    XYZ xyz = PipePositionList.First();
                    xyz.Z = endElevByStr;
                }


                //Убедиться, что если в одном узле без колодца стыкуются несколько ребер,
                //то в месте стыковки обязательно у всех ребер должна быть одинаковая отметка
                double neighborJunctElev = GetNeigborJuncElev(StartNode);
                XYZ    startPos          = PipePositionList.First();

                if (neighborJunctElev != double.NegativeInfinity && startPos.Z != neighborJunctElev)
                {
                    startPos.Z = neighborJunctElev;
                }

                neighborJunctElev = GetNeigborJuncElev(EndNode);
                XYZ endPos = PipePositionList.Last();

                if (neighborJunctElev != double.NegativeInfinity && endPos.Z != neighborJunctElev)
                {
                    endPos.Z = neighborJunctElev;
                }


                //Задание отметок промежуточных точек на ребрах сети (интерполяция либо относительно поверхности)
                if (PipePositionList.Count > 2)
                {
                    if (sameDepthEveryPt)
                    {
                        //одинаковая глубина относительно поверхности земли
                        //метод TinSurface.SampleElevations работает не так как надо! Он не дает подробного учета рельефа!
                        //точки полилинии
                        for (int i = 1; i < PipePositionList.Count - 1; i++)
                        {
                            XYZ xyz = PipePositionList[i];
                            SetElevBySurf(defaultDepth, tinSurf, xyz);
                        }


                        //Помимо углов поворотов нужно добавить промежуточные точки через 1 м для учета рельефа!


                        List <XYZ> positionListExtended = new List <XYZ>();
                        positionListExtended.Add(PipePositionList.First());
                        for (int i = 1; i < PipePositionList.Count; i++)
                        {
                            XYZ      xyz0    = PipePositionList[i - 1];
                            XYZ      xyz1    = PipePositionList[i];
                            double   len     = xyz1.Position2d.GetDistanceTo(xyz0.Position2d);
                            Vector2d vector  = (xyz1.Position2d - xyz0.Position2d).GetNormal();
                            double   currLen = 1;
                            while (currLen < len)
                            {
                                //добавление промежуточных точек
                                Point2d pt = xyz0.Position2d + vector * currLen;
                                XYZ     intermediateXYZ = new XYZ(pt);
                                SetElevBySurf(defaultDepth, tinSurf, intermediateXYZ);
                                positionListExtended.Add(intermediateXYZ);

                                currLen += 1;
                            }
                            positionListExtended.Add(xyz1);
                        }
                        PipePositionList = positionListExtended;
                    }
                    else
                    {
                        //интерполяция между началом и концом
                        double startElev  = startPos.Z;
                        double endElev    = endPos.Z;
                        double elevDiff   = endElev - startElev;
                        double currLength = 0;
                        for (int i = 1; i < PipePositionList.Count - 1; i++)
                        {
                            XYZ xyz = PipePositionList[i];

                            Point2d prevPt = PipePositionList[i - 1].Position2d;
                            currLength += prevPt.GetDistanceTo(xyz.Position2d);


                            xyz.Z = startElev + (elevDiff * currLength / pipeHorizontalLength);
                        }
                    }
                }
            }