Пример #1
0
        void InvertSub()
        {
            Queue <List <PolygonTreeNode> > queue = new Queue <List <PolygonTreeNode> >();

            queue.Enqueue(new List <PolygonTreeNode>()
            {
                this
            });

            while (queue.Count > 0)
            {
                List <PolygonTreeNode> children = queue.Dequeue();
                int l = children.Count;

                for (int j = 0; j < l; j++)
                {
                    PolygonTreeNode node = children[j];
                    if (node.Polygon != null)
                    {
                        node.Polygon = node.Polygon.Flipped();
                    }
                    queue.Enqueue(node.Children);
                }
            }
        }
Пример #2
0
        public List <Polygon> GetPolygons()
        {
            List <Polygon> result = new List <Polygon>();
            Queue <List <PolygonTreeNode> > queue = new Queue <List <PolygonTreeNode> >();

            queue.Enqueue(new List <PolygonTreeNode>()
            {
                this
            });

            while (queue.Count > 0)
            {
                List <PolygonTreeNode> children = queue.Dequeue();
                int l = children.Count;

                for (int j = 0; j < l; j++)
                {
                    PolygonTreeNode node = children[j];
                    if (node.Polygon != null)
                    {
                        result.Add(node.Polygon);
                    }
                    else
                    {
                        queue.Enqueue(node.Children);
                    }
                }
            }

            return(result);
        }
Пример #3
0
        public PolygonTreeNode AddChild(Polygon polygon)
        {
            PolygonTreeNode NewChildNode = new PolygonTreeNode();

            NewChildNode.Parent  = this;
            NewChildNode.Polygon = polygon;
            Children.Add(NewChildNode);
            return(NewChildNode);
        }
Пример #4
0
 public Tree(List <Polygon> polygons)
 {
     PolygonTree = new PolygonTreeNode();
     _RootNode   = new Node(null);
     if (polygons != null)
     {
         AddPolygons(polygons);
     }
 }
Пример #5
0
        void RecursivelyInvalidatePolygon()
        {
            PolygonTreeNode node = this;

            while (node.Polygon != null)
            {
                node.Polygon = null;
                if (node.Parent != null)
                {
                    node = node.Parent;
                }
            }
        }
Пример #6
0
        public PolygonTreeNode[] AddChildren(Polygon[] ArrayNewPolygon)
        {
            PolygonTreeNode[] ArrayAddedNode = new PolygonTreeNode[ArrayNewPolygon.Length];

            for (int P = 0; P < ArrayNewPolygon.Length; P++)
            {
                PolygonTreeNode NewChildNode = new PolygonTreeNode();
                NewChildNode.Parent  = this;
                NewChildNode.Polygon = ArrayNewPolygon[P];
                Children.Add(NewChildNode);
                ArrayAddedNode[P] = NewChildNode;
            }
            return(ArrayAddedNode);
        }
Пример #7
0
        public void SplitByPlane(Plane plane,
                                 ref List <PolygonTreeNode> coplanarfrontnodes, out PolygonTreeNode CoplanarBackNode,
                                 out PolygonTreeNode FrontNode, out PolygonTreeNode BackNode)
        {
            CoplanarBackNode = null;
            FrontNode        = null;
            BackNode         = null;

            if (Children.Count > 0)
            {
                Queue <List <PolygonTreeNode> > QueueNodeList  = null;
                List <PolygonTreeNode>          ActiveNodeList = Children;
                while (true)
                {
                    int l = ActiveNodeList.Count;
                    for (int j = 0; j < l; j++)
                    {
                        PolygonTreeNode node = ActiveNodeList[j];
                        if (node.Children.Count > 0)
                        {
                            if (QueueNodeList == null)
                            {
                                QueueNodeList = new Queue <List <PolygonTreeNode> >(node.Children.Count);
                            }
                            QueueNodeList.Enqueue(node.Children);
                        }
                        else
                        {
                            node.SplitPolygonByPlane(plane, ref coplanarfrontnodes, out CoplanarBackNode, out FrontNode, out BackNode);
                        }
                    }
                    if (QueueNodeList != null && QueueNodeList.Count > 0)
                    {
                        ActiveNodeList = QueueNodeList.Dequeue();
                    }
                    else
                    {
                        break;
                    }
                }
            }
            else
            {
                SplitPolygonByPlane(plane, ref coplanarfrontnodes, out CoplanarBackNode, out FrontNode, out BackNode);
            }
        }
Пример #8
0
        void SplitPolygonByPlane(Plane plane,
                                 ref List <PolygonTreeNode> CoplanarFrontNodes, out PolygonTreeNode CoplanarBackNode,
                                 out PolygonTreeNode FrontNode, out PolygonTreeNode BackNode)
        {
            Polygon ActivePolygon = this.Polygon;

            CoplanarBackNode = null;
            FrontNode        = null;
            BackNode         = null;

            if (ActivePolygon != null)
            {
                BoundingSphere Sphere       = ActivePolygon.BoundingSphere;
                double         SphereRadius = Sphere.Radius + 1.0e-4;
                Vector3        PlaneNormal  = plane.Normal;
                Vector3        SphereCenter = Sphere.Center;
                float          d            = PlaneNormal.Dot(SphereCenter) - plane.D;

                if (d > SphereRadius)
                {
                    FrontNode = this;
                }
                else if (d < -SphereRadius)
                {
                    BackNode = this;
                }
                else
                {
                    SplitPolygonResult splitresult;
                    plane.SplitPolygon(ActivePolygon, out splitresult);
                    switch (splitresult.Type)
                    {
                    case 0:
                        CoplanarFrontNodes.Add(this);
                        break;

                    case 1:
                        CoplanarBackNode = this;
                        break;

                    case 2:
                        FrontNode = this;
                        break;

                    case 3:
                        BackNode = this;
                        break;

                    default:
                        if (splitresult.Front != null)
                        {
                            FrontNode = AddChild(splitresult.Front);
                        }
                        if (splitresult.Back != null)
                        {
                            BackNode = AddChild(splitresult.Back);
                        }
                        break;
                    }
                }
            }
        }
Пример #9
0
        public void ClipPolygons(List <PolygonTreeNode> clippolygontreenodes, bool alsoRemoveCoplanarFront)
        {
            Args         args  = new Args(node: this, polygonTreeNodes: clippolygontreenodes);
            Stack <Args> stack = new Stack <Args>();

            while (true)
            {
                var clippingNode     = args.Node;
                var polygontreenodes = args.PolygonTreeNodes;

                if (clippingNode.ActivePlane != null)
                {
                    List <PolygonTreeNode> ListBackNodes = new List <PolygonTreeNode>();
                    PolygonTreeNode        BackNode;
                    List <PolygonTreeNode> ListFrontNodes = new List <PolygonTreeNode>();
                    PolygonTreeNode        FrontNode;
                    PolygonTreeNode        CoplanarBackNode;

                    Plane plane = clippingNode.ActivePlane;
                    int   numpolygontreenodes = polygontreenodes.Count;

                    for (var i = 0; i < numpolygontreenodes; i++)
                    {
                        PolygonTreeNode polyNode = polygontreenodes[i];

                        if (!polyNode.IsRemoved)
                        {
                            if (alsoRemoveCoplanarFront)
                            {
                                polyNode.SplitByPlane(plane, ref ListBackNodes, out CoplanarBackNode, out FrontNode, out BackNode);
                            }
                            else
                            {
                                polyNode.SplitByPlane(plane, ref ListFrontNodes, out CoplanarBackNode, out FrontNode, out BackNode);
                            }

                            if (FrontNode != null)
                            {
                                ListFrontNodes.Add(FrontNode);
                            }

                            if (BackNode != null)
                            {
                                ListBackNodes.Add(BackNode);
                            }

                            if (CoplanarBackNode != null)
                            {
                                ListBackNodes.Add(CoplanarBackNode);
                            }
                        }
                    }

                    if (clippingNode.Front != null && ListFrontNodes.Count > 0)
                    {
                        stack.Push(new Args(node: clippingNode.Front, polygonTreeNodes: ListFrontNodes));
                    }

                    int numbacknodes = ListBackNodes.Count;

                    if (clippingNode.Back != null && numbacknodes > 0)
                    {
                        stack.Push(new Args(node: clippingNode.Back, polygonTreeNodes: ListBackNodes));
                    }
                    else if (numbacknodes > 0)
                    {
                        // there's nothing behind this plane. Delete the nodes behind this plane:
                        for (int i = 0; i < numbacknodes; i++)
                        {
                            ListBackNodes[i].Remove();
                        }
                    }
                }
                if (stack.Count > 0)
                {
                    args = stack.Pop();
                }
                else
                {
                    break;
                }
            }
        }