Пример #1
0
        public void UpdateNodeOctant(OctreeZoneData zoneData)
        {
            AxisAlignedBox box = zoneData.OctreeWorldAABB;

            if (box.IsNull)
            {
                return;
            }

            // Skip if octree has been destroyed (shutdown conditions)
            if (null == this.rootOctree)
            {
                return;
            }

            PCZSceneNode node = zoneData.mAssociatedNode;

            if (null == zoneData.Octant)
            {
                //if outside the octree, force into the root node.
                if (!zoneData._isIn(this.rootOctree.Box))
                {
                    this.rootOctree.AddNode(node);
                }
                else
                {
                    AddNodeToOctree(node, this.rootOctree, 0);
                }
                return;
            }

            if (!zoneData._isIn(zoneData.Octant.Box))
            {
                //if outside the octree, force into the root node.
                if (!zoneData._isIn(this.rootOctree.Box))
                {
                    // skip if it's already in the root node.
                    if (((OctreeZoneData)node.GetZoneData(this)).Octant == this.rootOctree)
                    {
                        return;
                    }

                    RemoveNodeFromOctree(node);
                    this.rootOctree.AddNode(node);
                }
                else
                {
                    AddNodeToOctree(node, this.rootOctree, 0);
                }
            }
        }
Пример #2
0
        public void RemoveNode(PCZSceneNode node)
        {
            //PCZSceneNode check;
            //int i;
            //int Index;

            //Index = NodeList.Count - 1;

            //for ( i = Index; i >= 0; i-- )
            //{
            //    check = ( PCZSceneNode ) NodeList.Values[ i ];

            //    if ( check == node )
            //    {
            //        ( ( OctreeZoneData ) node.GetZoneData( zone ) ).Octant = null;
            //        NodeList.RemoveAt( i );
            //        UnRef();
            //    }
            //}

            ((OctreeZoneData)node.GetZoneData(this.zone)).Octant = null;
            NodeList.Remove(node);
            UnRef();
        }
Пример #3
0
        private void AddNodeToOctree(PCZSceneNode n, Octree octant, int depth)
        {
            // Skip if octree has been destroyed (shutdown conditions)
            if (null == this.rootOctree)
            {
                return;
            }

            AxisAlignedBox bx = n.WorldAABB;


            //if the octree is twice as big as the scene node,
            //we will add it to a child.
            if ((depth < this.maxDepth) && octant.IsTwiceSize(bx))
            {
                int x = 0, y = 0, z = 0;
                octant._getChildIndexes(bx, ref x, ref y, ref z);

                if (octant.Children[x, y, z] == null)
                {
                    octant.Children[x, y, z] = new Octree(this, octant);
                    Vector3 octantMin = octant.Box.Minimum;
                    Vector3 octantMax = octant.Box.Maximum;
                    Vector3 min, max;

                    if (x == 0)
                    {
                        min.x = octantMin.x;
                        max.x = (octantMin.x + octantMax.x) / 2;
                    }

                    else
                    {
                        min.x = (octantMin.x + octantMax.x) / 2;
                        max.x = octantMax.x;
                    }

                    if (y == 0)
                    {
                        min.y = octantMin.y;
                        max.y = (octantMin.y + octantMax.y) / 2;
                    }

                    else
                    {
                        min.y = (octantMin.y + octantMax.y) / 2;
                        max.y = octantMax.y;
                    }

                    if (z == 0)
                    {
                        min.z = octantMin.z;
                        max.z = (octantMin.z + octantMax.z) / 2;
                    }

                    else
                    {
                        min.z = (octantMin.z + octantMax.z) / 2;
                        max.z = octantMax.z;
                    }

                    octant.Children[x, y, z].Box.SetExtents(min, max);
                    octant.Children[x, y, z].HalfSize = (max - min) / 2;
                }

                AddNodeToOctree(n, octant.Children[x, y, z], ++depth);
            }
            else
            {
                if (((OctreeZoneData)n.GetZoneData(this)).Octant == octant)
                {
                    return;
                }

                RemoveNodeFromOctree(n);
                octant.AddNode(n);
            }
        }