コード例 #1
0
        public void DrawDelaunay()
        {
            //---获取凸包边界
            GetEdgeList();
            double angleV1V2, angleV2V3, angleMaxV1V2 = 0, angleMaxV2V3 = 0;
            int    newIndex;

            double[] vector1 = new double[2];
            double[] vector2 = new double[2];
            double[] vector3 = new double[2];
            double   lengthV1, lengthV2, lengthV3;
            bool     isTriExist = false; //判断三角形是否存在
            mEdge    edge;

            for (int i = 0; i < EdgeList.Count; i++)
            {
                edge = new mEdge();
                edge = EdgeList[i];

                //------------------------------左三角形不存在时
                if (edge.LeftTri == -1)
                {
                    newIndex     = -1;
                    angleMaxV1V2 = 0; angleMaxV2V3 = 0;
                    vector1[0]   = NodeList[edge.End].X - NodeList[edge.Start].X;
                    vector1[1]   = NodeList[edge.End].Y - NodeList[edge.Start].Y;
                    for (int j = 0; j < NodeList.Count; j++)
                    {
                        if (j != edge.Start && j != edge.End) //排除端点
                        {
                            vector2[0] = NodeList[j].X - NodeList[edge.Start].X;
                            vector2[1] = NodeList[j].Y - NodeList[edge.Start].Y;
                            if (vector1[0] * vector2[1] - vector2[0] * vector1[1] > 0)  //点在vector1左侧
                            {
                                vector3[0] = NodeList[j].X - NodeList[edge.End].X;
                                vector3[1] = NodeList[j].Y - NodeList[edge.End].Y;

                                lengthV1 = Math.Sqrt(vector1[0] * vector1[0] + vector1[1] * vector1[1]);
                                lengthV2 = Math.Sqrt(vector2[0] * vector2[0] + vector2[1] * vector2[1]);
                                lengthV3 = Math.Sqrt(vector3[0] * vector3[0] + vector3[1] * vector3[1]);

                                angleV1V2 = Math.Acos((vector1[0] * vector2[0] + vector1[1] * vector2[1]) / (lengthV1 * lengthV2));
                                angleV2V3 = Math.Acos((vector2[0] * vector3[0] + vector2[1] * vector3[1]) / (lengthV2 * lengthV3));

                                if (angleV2V3 > angleMaxV2V3)
                                {
                                    angleMaxV2V3 = angleV2V3;
                                    angleMaxV1V2 = angleV1V2;
                                    newIndex     = j;
                                }
                                else if (angleV2V3 == angleMaxV2V3 && angleMaxV1V2 >= angleV1V2)
                                {
                                    angleMaxV1V2 = angleV1V2;
                                    newIndex     = j;
                                }
                            }
                        }
                    }
                    if (newIndex != -1) //找到符合要求的点,然后记录
                    {
                        mTriangle triangle = new mTriangle();
                        triangle.NodeA = edge.Start;
                        triangle.NodeB = edge.End;
                        triangle.NodeC = newIndex;

                        edge.LeftTri = TriList.Count;  //三角形索引从0开始
                        isTriExist   = false;

                        //记录第一条边
                        for (int k = 0; k < EdgeList.Count; k++)
                        {
                            mEdge tempEdge = EdgeList[k];
                            if (tempEdge.Start == edge.Start && tempEdge.End == newIndex)
                            {
                                tempEdge.RightTri = TriList.Count;
                                triangle.EdgeB    = k;
                                isTriExist        = true;
                                break;
                            }
                            else if (tempEdge.Start == newIndex && tempEdge.End == edge.Start)
                            {
                                tempEdge.LeftTri = TriList.Count;
                                triangle.EdgeB   = k;
                                isTriExist       = true;
                                break;
                            }
                        }
                        if (isTriExist == false)
                        {
                            mEdge newEdge = new mEdge();
                            newEdge.Start   = newIndex;
                            newEdge.End     = edge.Start;
                            newEdge.LeftTri = TriList.Count;
                            triangle.EdgeB  = EdgeList.Count;
                            EdgeList.Add(newEdge);
                        }

                        isTriExist = false;
                        //记录第二条边
                        for (int k = 0; k < EdgeList.Count; k++)
                        {
                            mEdge tempEdge = EdgeList[k];
                            if (tempEdge.Start == newIndex && tempEdge.End == edge.End)
                            {
                                tempEdge.RightTri = TriList.Count;
                                triangle.EdgeC    = k;
                                isTriExist        = true;
                                break;
                            }
                            else if (tempEdge.Start == edge.End && tempEdge.End == newIndex)
                            {
                                tempEdge.LeftTri = TriList.Count;
                                triangle.EdgeC   = k;
                                isTriExist       = true;
                                break;
                            }
                        }

                        if (isTriExist == false)
                        {
                            mEdge newEdge = new mEdge();
                            newEdge.Start   = edge.End;
                            newEdge.End     = newIndex;
                            newEdge.LeftTri = TriList.Count;
                            triangle.EdgeC  = EdgeList.Count;
                            EdgeList.Add(newEdge);
                        }
                        triangle.EdgeA = i;
                        TriList.Add(triangle);
                    }
                }

                ////////////////////////////////////////////////////////////////////////////右三角形不存在时
                else if (edge.RightTri == -1)
                {
                    newIndex     = -1;
                    angleMaxV1V2 = 0; angleMaxV2V3 = 0;
                    vector1[0]   = NodeList[edge.End].X - NodeList[edge.Start].X;
                    vector1[1]   = NodeList[edge.End].Y - NodeList[edge.Start].Y;

                    for (int j = 0; j < NodeList.Count; j++)
                    {
                        if (j != edge.Start && j != edge.End)
                        {
                            vector2[0] = NodeList[j].X - NodeList[edge.Start].X;
                            vector2[1] = NodeList[j].Y - NodeList[edge.Start].Y;

                            if (vector1[0] * vector2[1] - vector2[0] * vector1[1] < 0)
                            {
                                vector3[0] = NodeList[j].X - NodeList[edge.End].X;
                                vector3[1] = NodeList[j].Y - NodeList[edge.End].Y;

                                lengthV1 = Math.Sqrt(vector1[0] * vector1[0] + vector1[1] * vector1[1]);
                                lengthV2 = Math.Sqrt(vector2[0] * vector2[0] + vector2[1] * vector2[1]);
                                lengthV3 = Math.Sqrt(vector3[0] * vector3[0] + vector3[1] * vector3[1]);

                                angleV1V2 = Math.Acos((vector1[0] * vector2[0] + vector1[1] * vector2[1]) / (lengthV1 * lengthV2));
                                angleV2V3 = Math.Acos((vector2[0] * vector3[0] + vector2[1] * vector3[1]) / (lengthV2 * lengthV3));

                                if (angleV2V3 > angleMaxV2V3)
                                {
                                    angleMaxV2V3 = angleV2V3;
                                    angleMaxV1V2 = angleV1V2;
                                    newIndex     = j;
                                }
                                else if (angleV2V3 == angleMaxV2V3 && angleMaxV1V2 < angleV1V2)
                                {
                                    angleMaxV1V2 = angleV1V2;
                                    newIndex     = j;
                                }
                            }
                        }
                    }

                    if (newIndex != -1)
                    {
                        mTriangle triangle = new mTriangle();
                        triangle.NodeA = edge.Start;
                        triangle.NodeB = edge.End;
                        triangle.NodeC = newIndex;
                        edge.RightTri  = TriList.Count;
                        isTriExist     = false;

                        //记录vector2向量边
                        for (int k = 0; k < EdgeList.Count; k++)
                        {
                            mEdge tempEdge = EdgeList[k];
                            if (tempEdge.Start == newIndex && tempEdge.End == edge.Start)
                            {
                                tempEdge.RightTri = TriList.Count;
                                triangle.EdgeB    = k;
                                isTriExist        = true;
                                break;
                            }
                            else if (tempEdge.Start == edge.Start && tempEdge.End == newIndex)
                            {
                                tempEdge.LeftTri = TriList.Count;
                                triangle.EdgeB   = k;
                                isTriExist       = true;
                                break;
                            }
                        }
                        if (isTriExist == false)
                        {
                            mEdge newEdge = new mEdge();
                            newEdge.Start   = edge.Start;
                            newEdge.End     = newIndex;
                            newEdge.LeftTri = TriList.Count;
                            triangle.EdgeB  = EdgeList.Count;
                            EdgeList.Add(newEdge);
                        }

                        isTriExist = false;

                        //记录Vector3向量边
                        for (int k = 0; k < EdgeList.Count; k++)
                        {
                            mEdge tempEdge = EdgeList[k];
                            if (tempEdge.Start == edge.End && tempEdge.End == newIndex)
                            {
                                tempEdge.RightTri = TriList.Count;
                                triangle.EdgeC    = k;
                                isTriExist        = true;
                                break;
                            }
                            else if (tempEdge.Start == newIndex && tempEdge.End == edge.End)
                            {
                                tempEdge.LeftTri = TriList.Count;
                                triangle.EdgeC   = k;
                                isTriExist       = true;
                                break;
                            }
                        }
                        if (isTriExist == false)
                        {
                            mEdge newEdge = new mEdge();
                            newEdge.Start   = newIndex;
                            newEdge.End     = edge.End;
                            newEdge.LeftTri = TriList.Count;
                            triangle.EdgeC  = EdgeList.Count;
                            EdgeList.Add(newEdge);
                        }
                        triangle.EdgeA = i;
                        TriList.Add(triangle);
                    }
                }
            }

            //////////////////////////////////////////////////////////////////////////
            ///绘图
            //////////////////////////////////////////////////////////////////////////
            Document acDoc = Autodesk.AutoCAD.ApplicationServices.Application.DocumentManager.MdiActiveDocument;
            Database acDb  = acDoc.Database;

            using (Transaction acDelaunayTrans = acDb.TransactionManager.StartTransaction())
            {
                string     layerName = "LineLayer";
                LayerTable acLTable  = acDelaunayTrans.GetObject(acDb.LayerTableId, OpenMode.ForRead) as LayerTable;
                if (acLTable.Has(layerName) == false)
                {
                    using (Transaction acLayerTrans = acDb.TransactionManager.StartTransaction())
                    {
                        LayerTable       acLTable2  = acLayerTrans.GetObject(acDb.LayerTableId, OpenMode.ForRead) as LayerTable;
                        LayerTableRecord acLTRecord = new LayerTableRecord();
                        acLTRecord.Name  = layerName;
                        acLTRecord.Color = Color.FromColorIndex(ColorMethod.ByAci, 7);

                        acLTable2.UpgradeOpen();
                        acLTable2.Add(acLTRecord);
                        acLayerTrans.AddNewlyCreatedDBObject(acLTRecord, true);
                        acLayerTrans.Commit();
                    }
                }

                if (acLTable.Has(layerName) == true)
                {
                    acDb.Clayer = acLTable[layerName];
                }

                BlockTable acBLTable;
                acBLTable = acDelaunayTrans.GetObject(acDb.BlockTableId, OpenMode.ForRead) as BlockTable;
                BlockTableRecord acBTRecord;
                acBTRecord = acDelaunayTrans.GetObject(acBLTable[BlockTableRecord.ModelSpace], OpenMode.ForWrite) as BlockTableRecord;

                int i;
                for (i = 0; i < EdgeList.Count; i++)
                {
                    Point3d startPoint = new Point3d(NodeList[EdgeList[i].Start].X, NodeList[EdgeList[i].Start].Y, NodeList[EdgeList[i].Start].Z);
                    Point3d endPoint   = new Point3d(NodeList[EdgeList[i].End].X, NodeList[EdgeList[i].End].Y, NodeList[EdgeList[i].End].Z);

                    Line acLine = new Line(startPoint, endPoint);
                    acBTRecord.AppendEntity(acLine);
                    acDelaunayTrans.AddNewlyCreatedDBObject(acLine, true);
                }
                DocumentCollection acDC = Autodesk.AutoCAD.ApplicationServices.Application.DocumentManager;
                acDC.MdiActiveDocument.Editor.WriteMessage("\n Delaunay三角网绘制完毕!");

                acDelaunayTrans.Commit();
            }
            //Zoom(new Point3d(), new Point3d(), new Point3d(), 1.01075);
        }
コード例 #2
0
        /// <summary>
        /// 绘点
        /// </summary>
        /// <param name="nodeList"></param>


        public void DrawTubao(List <mNode> nodeList, List <mEdge> edgeList)
        {
            List <mNode> tempNodeList = new List <mNode>();

            if (edgeList.Count != 0)
            {
                edgeList.Clear();
            }
            double[] vectorA = new double[2];
            double[] vectorB = new double[2];
            vectorA[0] = 0; vectorA[1] = 100;    //用于计算两边夹角,且夹角始终小于或等于180°
            double minX = nodeList[0].X;
            int    startIndex = 0, endIndex, tempIndex;

            for (int i = 1; i < nodeList.Count; i++)
            {
                if (minX > nodeList[i].X)
                {
                    minX       = nodeList[i].X;
                    startIndex = i;
                }
            }
            tempNodeList.Add(new mNode(nodeList[startIndex].N, nodeList[startIndex].X, nodeList[startIndex].Y, nodeList[startIndex].Z));    //最左边的点
            mEdge edge = new mEdge();

            edge.Start = startIndex;
            endIndex   = -1;
            tempIndex  = startIndex;

            double VALength, VBLength, tempCos, minCos = 1, minLength = double.MaxValue;

            while (endIndex != startIndex)
            {
                int j = 0;
                VALength  = Math.Sqrt(vectorA[0] * vectorA[0] + vectorA[1] * vectorA[1]);
                minLength = double.MaxValue;
                for (j = 0; j < nodeList.Count; j++)  //边界
                {
                    if (j != edge.Start)
                    {
                        vectorB[0] = nodeList[j].X - nodeList[tempIndex].X;
                        vectorB[1] = nodeList[j].Y - nodeList[tempIndex].Y;
                        VBLength   = Math.Sqrt(vectorB[0] * vectorB[0] + vectorB[1] * vectorB[1]);

                        tempCos = (vectorA[0] * vectorB[0] + vectorA[1] * vectorB[1]) / (VALength * VBLength);

                        if (minCos > tempCos)
                        {
                            minCos    = tempCos;
                            edge.End  = j;
                            minLength = VBLength;
                        }
                        else if (tempCos == minCos && VBLength < minLength)
                        {
                            edge.End  = j;
                            minLength = VBLength;
                        }
                    }
                }
                edgeList.Add(edge);
                tempNodeList.Add(new mNode(edge.End, nodeList[edge.End].X, nodeList[edge.End].Y, nodeList[edge.End].Z));
                endIndex   = edge.End;
                edge       = new mEdge();
                edge.Start = endIndex;
                minCos     = 1;
                vectorA[0] = nodeList[tempIndex].X - nodeList[endIndex].X;
                vectorA[1] = nodeList[tempIndex].Y - nodeList[endIndex].Y;
                tempIndex  = endIndex;
            }

            //画凸包
            Document acDoc = Autodesk.AutoCAD.ApplicationServices.Application.DocumentManager.MdiActiveDocument;
            Database acDb  = acDoc.Database;

            using (Transaction acTransLine = acDb.TransactionManager.StartTransaction())
            {
                string layerName = "LineLayer";
                using (Transaction acTransLineLayer = acDb.TransactionManager.StartTransaction())
                {
                    //创建线图层
                    LayerTable acLTable = acTransLineLayer.GetObject(acDb.LayerTableId, OpenMode.ForRead) as LayerTable;
                    if (acLTable.Has(layerName) == false)
                    {
                        LayerTableRecord acLTRecord = new LayerTableRecord();
                        acLTRecord.Name  = layerName;
                        acLTRecord.Color = Color.FromColorIndex(ColorMethod.ByAci, 7);  //7表示白色

                        acLTable.UpgradeOpen();
                        acLTable.Add(acLTRecord);
                        acTransLineLayer.AddNewlyCreatedDBObject(acLTRecord, true);
                    }
                    acTransLineLayer.Commit();
                }

                LayerTable acLTable2 = acTransLine.GetObject(acDb.LayerTableId, OpenMode.ForRead) as LayerTable;
                if (acLTable2.Has(layerName) == true)
                {
                    acDb.Clayer = acLTable2[layerName];
                }
                BlockTable acBlkTbl;
                acBlkTbl = acTransLine.GetObject(acDb.BlockTableId, OpenMode.ForRead) as BlockTable;
                BlockTableRecord acBlkTblRec;
                acBlkTblRec = acTransLine.GetObject(acBlkTbl[BlockTableRecord.ModelSpace], OpenMode.ForWrite) as BlockTableRecord;
                int i, j;
                for (i = 0; i < tempNodeList.Count; i++)
                {
                    j = i + 1;
                    if (j == tempNodeList.Count)
                    {
                        j = 0;
                    }
                    Point3d StartPoint = new Point3d(tempNodeList[i].X, tempNodeList[i].Y, tempNodeList[i].Z);
                    Point3d EndPoint   = new Point3d(tempNodeList[j].X, tempNodeList[j].Y, tempNodeList[j].Z);
                    Line    acLine     = new Line(StartPoint, EndPoint);
                    acBlkTblRec.AppendEntity(acLine);
                    acTransLine.AddNewlyCreatedDBObject(acLine, true);
                }
                acTransLine.Commit();
            }
            Zoom(new Point3d(), new Point3d(), new Point3d(), 1.01075);
        }
コード例 #3
0
        public void GetEdgeList()
        {
            double[] vectorA = new double[2];
            double[] vectorB = new double[2];
            vectorA[0] = 0; vectorA[1] = 100;    //用于计算两边夹角,且夹角始终小于或等于180°
            double minX = NodeList[0].X;
            int    startIndex = 0, endIndex, tempIndex;

            for (int i = 1; i < NodeList.Count; i++)
            {
                if (minX > NodeList[i].X)
                {
                    minX       = NodeList[i].X;
                    startIndex = i;
                }
            }
            mEdge edge = new mEdge();

            edge.Start = startIndex;
            endIndex   = startIndex - 1;
            tempIndex  = startIndex;

            double VALength, VBLength, tempCos, minCos = 1, minLength = double.MaxValue;

            while (endIndex != startIndex)
            {
                int j = 0;
                VALength  = Math.Sqrt(vectorA[0] * vectorA[0] + vectorA[1] * vectorA[1]);
                minLength = double.MaxValue;
                for (j = 0; j < NodeList.Count; j++)  //边界
                {
                    if (j != edge.Start)
                    {
                        vectorB[0] = NodeList[j].X - NodeList[tempIndex].X;
                        vectorB[1] = NodeList[j].Y - NodeList[tempIndex].Y;
                        VBLength   = Math.Sqrt(vectorB[0] * vectorB[0] + vectorB[1] * vectorB[1]);

                        tempCos = (vectorA[0] * vectorB[0] + vectorA[1] * vectorB[1]) / (VALength * VBLength);

                        if (minCos > tempCos)
                        {
                            minCos    = tempCos;
                            edge.End  = j;
                            minLength = VBLength;
                        }
                        else if (tempCos == minCos && VBLength < minLength)
                        {
                            edge.End  = j;
                            minLength = VBLength;
                        }
                    }
                }
                EdgeList.Add(edge);
                endIndex   = edge.End;
                edge       = new mEdge();
                edge.Start = endIndex;
                minCos     = 1;
                vectorA[0] = NodeList[tempIndex].X - NodeList[endIndex].X;
                vectorA[1] = NodeList[tempIndex].Y - NodeList[endIndex].Y;
                tempIndex  = endIndex;
            }

            /*
             * //画凸包
             * Document acDoc = Autodesk.AutoCAD.ApplicationServices.Application.DocumentManager.MdiActiveDocument;
             * Database acDb = acDoc.Database;
             *
             * using (Transaction acTransLine = acDb.TransactionManager.StartTransaction())
             * {
             *  string layerName = "LineLayer";
             *  using (Transaction acTransLineLayer = acDb.TransactionManager.StartTransaction())
             *  {
             *      //创建线图层
             *      LayerTable acLTable = acTransLineLayer.GetObject(acDb.LayerTableId, OpenMode.ForRead) as LayerTable;
             *      if (acLTable.Has(layerName) == false)
             *      {
             *          LayerTableRecord acLTRecord = new LayerTableRecord();
             *          acLTRecord.Name = layerName;
             *          acLTRecord.Color = Color.FromColorIndex(ColorMethod.ByAci, 7);  //7表示白色
             *
             *          acLTable.UpgradeOpen();
             *          acLTable.Add(acLTRecord);
             *          acTransLineLayer.AddNewlyCreatedDBObject(acLTRecord, true);
             *      }
             *      acTransLineLayer.Commit();
             *  }
             *
             *  LayerTable acLTable2 = acTransLine.GetObject(acDb.LayerTableId, OpenMode.ForRead) as LayerTable;
             *  if (acLTable2.Has(layerName) == true)
             *  {
             *      acDb.Clayer = acLTable2[layerName];
             *  }
             *  BlockTable acBlkTbl;
             *  acBlkTbl = acTransLine.GetObject(acDb.BlockTableId, OpenMode.ForRead) as BlockTable;
             *  BlockTableRecord acBlkTblRec;
             *  acBlkTblRec = acTransLine.GetObject(acBlkTbl[BlockTableRecord.ModelSpace], OpenMode.ForWrite) as BlockTableRecord;
             *  int i, j;
             *  for (i = 0; i < EdgeList.Count; i++)
             *  {
             *      j = i + 1;
             *      if (j == EdgeList.Count)
             *          j = 0;
             *      Point3d StartPoint = new Point3d(NodeList[EdgeList[i].Start].X, NodeList[EdgeList[i].Start].Y, NodeList[EdgeList[i].Start].Z);
             *      Point3d EndPoint = new Point3d(NodeList[EdgeList[i].End].X, NodeList[EdgeList[i].End].Y, NodeList[EdgeList[i].End].Z);
             *      Line acLine = new Line(StartPoint, EndPoint);
             *      acBlkTblRec.AppendEntity(acLine);
             *      acTransLine.AddNewlyCreatedDBObject(acLine, true);
             *  }
             *  acTransLine.Commit();
             * }
             * Zoom(new Point3d(), new Point3d(), new Point3d(), 1.01075);
             */
        }