注册 登录
明经CAD社区 返回首页

sieben的个人空间 http://www.mjtd.com/?43121 [收藏] [复制] [分享] [RSS]

日志

一个很晚的晚上和一个很早的早上

已有 2456 次阅读2006-8-31 22:28 |系统分类:开发

C#打断曲线的方法

一直就不喜欢在程序里用AutoCAD命令,在.Net里还有AutoCAD命令与Editor及事务提交之间纠缠不清的关系,特别是三者的次序我实在搞不清楚,托管类里没有打断曲线的方法,AutoCAD的Break命令用起来不顺手,而且还担心不可靠.只好自己写一个打断曲线的方法,各位或许会用得上.花了一个很晚的晚上和一个很早的早上.可以打断直线,圆弧,圆,椭圆,椭圆弧,轻型多义线(封闭和开口的),Xline及射线.

源代码 : 叶开.Sieben
        /// <summary>
        /// curveid Object must have existed in Database
        /// Can break Line | Arc | Circle | Ellipse | Polyline | Xline | Ray
        /// </summary>
        /// <param name="p1">第一个打断点 </param>
        /// <param name="p2">第二个打断点</param>
        /// <param name="curveid">要打断曲线的ObjectId</param>
        /// <returns></returns>
        public static bool BreakCurve(Point3d p1, Point3d p2, ObjectId curveid)
        {
            //pcm.WriteLine("BreakCurve start", 0);
            try
            {
                Database cdb = curveid.Database;
                using (Transaction ctrans = cdb.TransactionManager.StartTransaction())
                {
                    Curve cur = (Curve)ctrans.GetObject(curveid, OpenMode.ForWrite);
                    Point3d p11 = cur.GetClosestPointTo(p1, false);
                    Point3d p21 = cur.GetClosestPointTo(p2, false);
                    #region Break Line
                    if (cur is Line)
                    {
                        //pcm.WriteLine("Break Line start ", 1);
                        Line l1 = (Line)cur;
                        Line l2 = (Line)l1.Clone();
                        if (l1.GetDistAtPoint(p11) < l1.GetDistAtPoint(p21))
                        {
                            l2.StartPoint = p21;
                            l1.EndPoint = p11;
                        }
                        else
                        {
                            l2.StartPoint = p11;
                            l1.EndPoint = p21;
                        }
                        DrawEntity(l2);
                    }
                    #endregion Break Line
                    #region Break Arc
                    if (cur is Arc)
                    {//pcm.WriteLine("Break Arc start ", 1);
                        Arc arc1 = (Arc)cur;
                        Arc arc2 = (Arc)arc1.Clone();
                        Vector3d v11 = arc1.StartPoint.GetVectorTo(arc1.Center);
                        Vector3d v12 = arc1.EndPoint.GetVectorTo(arc1.Center);
                        Vector3d v21 = p11.GetVectorTo(arc1.Center);
                        Vector3d v22 = p21.GetVectorTo(arc1.Center);
                        if (v11.GetAngleTo(v21, Vector3d.ZAxis) < v11.GetAngleTo(v22, Vector3d.ZAxis))
                        {
                            arc2.EndAngle = arc1.StartAngle + v11.GetAngleTo(v21, Vector3d.ZAxis);
                            arc1.StartAngle += v11.GetAngleTo(v22, Vector3d.ZAxis);
                        }
                        else
                        {
                            arc2.EndAngle = arc1.StartAngle + v11.GetAngleTo(v22, Vector3d.ZAxis);
                            arc1.StartAngle += v11.GetAngleTo(v21, Vector3d.ZAxis);
                        }
                        DrawEntity(arc2);
                    }
                    #endregion Break Arc
                    #region Break Circle
                    if (cur is Circle)
                    {//pcm.WriteLine("Break Circle start ", 1);
                        Circle c1 = (Circle)cur;
                        Vector3d v1 = p11.GetVectorTo(c1.Center);
                        Vector3d v2 = p21.GetVectorTo(c1.Center);
                        Arc arc1 = new Arc();
                        arc1.Center = c1.Center;
                        arc1.SetPropertiesFrom(c1);
                        arc1.Radius = c1.Radius;
                        arc1.StartAngle = Vector3d.XAxis.GetAngleTo(v2, Vector3d.ZAxis);
                        arc1.EndAngle = arc1.StartAngle + v2.GetAngleTo(v1, Vector3d.ZAxis);
                        c1.Erase();
                        DrawEntity(arc1);
                    }
                    #endregion Break Circle
                    #region Break Ellipse
                    if (cur is Ellipse)
                    {
                        //pcm.WriteLine("Break Ellipse start ", 1);
                        Ellipse ell1 = (Ellipse)cur;
                        if (ell1.Closed)
                        {
                            // pcm.WriteLine("Ellipse closed ", 1);
                            Vector3d v1 = p11.GetVectorTo(ell1.Center);
                            Vector3d v2 = p21.GetVectorTo(ell1.Center);
                            ell1.StartAngle = ell1.MajorAxis.GetAngleTo(v2, Vector3d.ZAxis);
                            ell1.EndAngle = ell1.StartAngle + v2.GetAngleTo(v1, Vector3d.ZAxis);
                        }
                        else
                        {
                            //pcm.WriteLine("Ellipse opened ", 1);
                            Ellipse ell2 = (Ellipse)ell1.Clone();
                            Vector3d v11 = ell1.StartPoint.GetVectorTo(ell1.Center);
                            Vector3d v12 = ell1.EndPoint.GetVectorTo(ell1.Center);
                            Vector3d v21 = p11.GetVectorTo(ell1.Center);
                            Vector3d v22 = p21.GetVectorTo(ell1.Center);
                            if (v11.GetAngleTo(v21, Vector3d.ZAxis) < v11.GetAngleTo(v22, Vector3d.ZAxis))
                            {
                                ell2.EndAngle = ell1.StartAngle + v11.GetAngleTo(v21, Vector3d.ZAxis);
                                ell1.StartAngle += v11.GetAngleTo(v22, Vector3d.ZAxis);
                            }
                            else
                            {
                                ell2.EndAngle = ell1.StartAngle + v11.GetAngleTo(v22, Vector3d.ZAxis);
                                ell1.StartAngle += v11.GetAngleTo(v21, Vector3d.ZAxis);
                            }
                            DrawEntity(ell2);
                        }
                    }
                    #endregion Break Ellipse
                    #region Break Polyline
                    if (cur is Polyline)
                    {
                        //pcm.WriteLine("Break PolyLine start ", 1);
                        Polyline pl1 = (Polyline)cur;
                        double param11 = pl1.GetParameterAtPoint(p11);
                        double param12 = pl1.GetParameterAtPoint(p21);
                        double param21 = Math.Min(param11, param12);
                        double param22 = Math.Max(param11, param12);
                        if (pl1.Closed)
                        {
                            #region Polyline closed
                           pcm.WriteLine("PolyLine closed ", 1);
                            Polyline pl2 = new Polyline();
                            pl2.SetPropertiesFrom(pl1);
                            double len11 = pl1.GetDistanceAtParameter(param21) + pl1.GetDistanceAtParameter(pl1.EndParam) - pl1.GetDistanceAtParameter(param22);
                            double len12 = pl1.GetDistanceAtParameter(param22) - pl1.GetDistanceAtParameter(param21);
                            int param31 = (int)Math.Floor(param21);
                            int param32 = (int)Math.Floor(param22) + 1;
                            Point3d p31;
                            if (len11 > len12)
                            {
                                if ((double)param32 != param22)
                                {
                                    double bul12 = pl1.GetBulgeAt(param32 - 1);
                                    double bul22 = 0;
                                    if (bul12 != 0.0)
                                    {
                                        double len22 = pl1.GetDistanceAtParameter(param32) - pl1.GetDistanceAtParameter(param32 - 1);
                                        double len32 = pl1.GetDistanceAtParameter(param32) - pl1.GetDistanceAtParameter(param22);
                                        bul22 = Math.Tan(len32 * Math.Atan(bul12) / len22);
                                    }
                                    p31 = pl1.GetPointAtParameter(param22);
                                    pl2.AddVertexAt(0, new Point2d(p31.X, p31.Y), bul22, 0, 0);
                                }
                                for (int i = param32; i < pl1.EndParam; i++)
                                {
                                    p31 = pl1.GetPointAtParameter(i);
                                    pl2.AddVertexAt(pl2.NumberOfVertices, new Point2d(p31.X, p31.Y), pl1.GetBulgeAt(i), 0, 0);
                                }
                                for (int i = 0; i <= param31; i++)
                                {
                                    p31 = pl1.GetPointAtParameter(i);
                                    pl2.AddVertexAt(pl2.NumberOfVertices, new Point2d(p31.X, p31.Y), pl1.GetBulgeAt(i), 0, 0);
                                }
                                if ((double)param31 != param21)
                                {
                                    p31 = pl1.GetPointAtParameter(param21);
                                    pl2.AddVertexAt(pl2.NumberOfVertices, new Point2d(p31.X, p31.Y), 0, 0, 0);
                                    double bul11 = pl1.GetBulgeAt(param31);
                                    if (bul11 != 0.0)
                                    {
                                        double len21 = pl1.GetDistanceAtParameter(param31 + 1) - pl1.GetDistanceAtParameter(param31);
                                        double len31 = pl1.GetDistanceAtParameter(param21) - pl1.GetDistanceAtParameter(param31);
                                        if (pl2.NumberOfVertices == 2)
                                            len31 = pl1.GetDistanceAtParameter(param22) - pl1.GetDistanceAtParameter(param21);
                                        double bul21 = Math.Tan(len31 * Math.Atan(bul11) / len21);
                                        pl2.SetBulgeAt(pl2.NumberOfVertices - 2, bul21);
                                    }
                                }
                            }
                            else
                            {
                                if ((double)param31 != param21)
                                {
                                    double bul11 = pl1.GetBulgeAt(param31);
                                    double bul21 = 0;
                                    if (bul11 != 0.0)
                                    {
                                        double len21 = pl1.GetDistanceAtParameter(param31 + 1) - pl1.GetDistanceAtParameter(param31);
                                        double len31 = pl1.GetDistanceAtParameter(param31 + 1) - pl1.GetDistanceAtParameter(param21);
                                        bul21 = Math.Tan(len31 * Math.Atan(bul11) / len21);
                                    }
                                    p31 = pl1.GetPointAtParameter(param21);
                                    pl2.AddVertexAt(0, new Point2d(p31.X, p31.Y), bul21, 0, 0);
                                }
                                for (int i = param31 + 1; i <= param32 - 1; i++)
                                {
                                    p31 = pl1.GetPointAtParameter(i);
                                    pl2.AddVertexAt(pl2.NumberOfVertices, new Point2d(p31.X, p31.Y), pl1.GetBulgeAt(i), 0, 0);
                                }
                                if ((double)param32 != param22)
                                {
                                    p31 = pl1.GetPointAtParameter(param22);
                                    pl2.AddVertexAt(pl2.NumberOfVertices, new Point2d(p31.X, p31.Y), 0, 0, 0);
                                    double bul12 = pl1.GetBulgeAt(param32 - 1);
                                    if (bul12 != 0.0)
                                    {
                                        double len22 = pl1.GetDistanceAtParameter(param32) - pl1.GetDistanceAtParameter(param32 - 1);
                                        double len32 = pl1.GetDistanceAtParameter(param22) - pl1.GetDistanceAtParameter(param32 - 1);
                                        if (pl2.NumberOfVertices == 2)
                                            len32 = pl1.GetDistanceAtParameter(param22) - pl1.GetDistanceAtParameter(param21);
                                        double bul22 = Math.Tan(len32 * Math.Atan(bul12) / len22);
                                        pl2.SetBulgeAt(pl2.NumberOfVertices - 2, bul22);
                                    }
                                }
                            }
                            #endregion Polyline closed
                            DrawEntity(pl2);
                        }
                        else
                        {
                            #region Polyline opened
                            //pcm.WriteLine("PolyLine opend ", 1);
                            Polyline pl2 = new Polyline();
                            pl2.SetPropertiesFrom(pl1);
                            double len11 = pl1.GetDistanceAtParameter(param21) + pl1.GetDistanceAtParameter(pl1.EndParam) - pl1.GetDistanceAtParameter(param22);
                            double len12 = pl1.GetDistanceAtParameter(param22) - pl1.GetDistanceAtParameter(param21);
                            int param31 = (int)Math.Floor(param21);
                            int param32 = (int)Math.Floor(param22) + 1;
                            Point3d p31;
                            for (int i = 0; i < param21; i++)
                            {
                                p31 = pl1.GetPointAtParameter(i);
                                pl2.AddVertexAt(pl2.NumberOfVertices, new Point2d(p31.X, p31.Y), pl1.GetBulgeAt(i), 0, 0);
                            }
                            if ((double)param31 != param21)
                            {
                                p31 = pl1.GetPointAtParameter(param21);
                                pl2.AddVertexAt(pl2.NumberOfVertices, new Point2d(p31.X, p31.Y), 0, 0, 0);
                                double bul11 = pl1.GetBulgeAt(param31);
                                if (bul11 != 0.0)
                                {
                                    double len21 = pl1.GetDistanceAtParameter(param31 + 1) - pl1.GetDistanceAtParameter(param31);
                                    double len31 = pl1.GetDistanceAtParameter(param21) - pl1.GetDistanceAtParameter(param31);
                                    if (pl2.NumberOfVertices == 2)
                                        len31 = pl1.GetDistanceAtParameter(param22) - pl1.GetDistanceAtParameter(param21);
                                    double bul21 = Math.Tan(len31 * Math.Atan(bul11) / len21);
                                    pl2.SetBulgeAt(pl2.NumberOfVertices - 2, bul21);
                                }
                            }
                            Polyline pl3 = new Polyline();
                            pl3.SetPropertiesFrom(pl1);
                            if ((double)param32 != param22)
                            {
                                double bul12 = pl1.GetBulgeAt(param32 - 1);
                                double bul22 = 0;
                                if (bul12 != 0.0)
                                {
                                    double len22 = pl1.GetDistanceAtParameter(param32) - pl1.GetDistanceAtParameter(param32 - 1);
                                    double len32 = pl1.GetDistanceAtParameter(param32) - pl1.GetDistanceAtParameter(param22);
                                    bul22 = Math.Tan(len32 * Math.Atan(bul12) / len22);
                                }
                         


路过

雷人

握手

鲜花

鸡蛋

发表评论 评论 (2 个评论)

回复 wl_207 2006-9-2 08:33
高手,鉴定完毕。
flicker 彩虹炫 | Passbyer 2006-9-5 20:37
因为不喜欢AutoCAD命令,就自己写一个,楼主果然是高手,呵呵。

facelist doodle 涂鸦板

您需要登录后才可以评论 登录 | 注册

小黑屋|手机版|CAD论坛|CAD教程|CAD下载|联系我们|关于明经|明经通道 ( 粤ICP备05003914号 )  
©2000-2023 明经通道 版权所有 本站代码,在未取得本站及作者授权的情况下,不得用于商业用途

GMT+8, 2024-3-29 23:53 , Processed in 0.138909 second(s), 16 queries , Gzip On.

Powered by Discuz! X3.4

Copyright © 2001-2021, Tencent Cloud.

返回顶部