/** Walks through the octree, adding any visible objects to the render queue. @remarks If any octant in the octree if completely within the the view frustum, all subchildren are automatically added with no visibility tests. */ public void WalkOctree(OctreeCamera camera, RenderQueue queue, Octree octant, VisibleObjectsBoundsInfo visibleBounds, bool onlyShadowCasters, bool foundVisible) { //return immediately if nothing is in the node. if(octant.NumNodes == 0) { return; } Visibility v = Visibility.None; if(foundVisible) { v = Visibility.Full; } else if(octant == octree) { v = Visibility.Partial; } else { AxisAlignedBox box = octant.CullBounds; v = camera.GetVisibility(box); } // if the octant is visible, or if it's the root node... if(v != Visibility.None) { if(this.ShowBoundingBoxes) { // TODO: Implement Octree.WireBoundingBox //boxList.Add(octant.WireBoundingBox); } bool vis = true; for(int i = 0; i < octant.NodeList.Count; i++) { OctreeNode node = (OctreeNode)octant.NodeList[i]; // if this octree is partially visible, manually cull all // scene nodes attached directly to this level. if(v == Visibility.Partial) { vis = camera.IsObjectVisible(node.WorldAABB); } if(vis) { numObjects++; node.AddToRenderQueue(camera, queue, onlyShadowCasters, visibleBounds); visible.Add(node); if(DisplayNodes) { GetRenderQueue().AddRenderable(node); } // check if the scene manager or this node wants the bounding box shown. if(node.ShowBoundingBox || this.ShowBoundingBoxes) { node.AddBoundingBoxToQueue(queue); } } } if(octant.Children[0,0,0] != null ) WalkOctree(camera, queue, octant.Children[0,0,0], visibleBounds, onlyShadowCasters, ( v == Visibility.Full ) ); if(octant.Children[1,0,0] != null ) WalkOctree(camera, queue, octant.Children[1,0,0], visibleBounds, onlyShadowCasters, ( v == Visibility.Full ) ); if(octant.Children[0,1,0] != null ) WalkOctree(camera, queue, octant.Children[0,1,0], visibleBounds, onlyShadowCasters, ( v == Visibility.Full ) ); if(octant.Children[1,1,0] != null ) WalkOctree(camera, queue, octant.Children[1,1,0], visibleBounds, onlyShadowCasters, ( v == Visibility.Full ) ); if(octant.Children[0,0,1] != null ) WalkOctree(camera, queue, octant.Children[0,0,1], visibleBounds, onlyShadowCasters, ( v == Visibility.Full ) ); if(octant.Children[1,0,1] != null ) WalkOctree(camera, queue, octant.Children[1,0,1], visibleBounds, onlyShadowCasters, ( v == Visibility.Full ) ); if(octant.Children[0,1,1] != null ) WalkOctree(camera, queue, octant.Children[0,1,1], visibleBounds, onlyShadowCasters, ( v == Visibility.Full ) ); if(octant.Children[1,1,1] != null ) WalkOctree(camera, queue, octant.Children[1,1,1], visibleBounds, onlyShadowCasters, ( v == Visibility.Full ) ); } }