public BoundingVolumeHierarchy(List<Boundable> boundables) { _logNumBoundables = (int)Math.Ceiling(Math.Log(boundables.Count)); var time = DateTime.UtcNow; Console.WriteLine($"Building BVH for {boundables.Count} boundables..."); Root = Construct(new BVHNode(boundables)); Console.WriteLine($"Constuction done in {DateTime.UtcNow - time}"); }
public BoundingVolumeHierarchy(List <Boundable> boundables) { _logNumBoundables = (int)Math.Ceiling(Math.Log(boundables.Count)); var time = DateTime.UtcNow; Console.WriteLine($"Building BVH for {boundables.Count} boundables..."); Root = Construct(new BVHNode(boundables)); Console.WriteLine($"Constuction done in {DateTime.UtcNow - time}"); }
public BVHNode Construct(BVHNode leaf) { if (leaf.Boundables.Count == 0) { return(leaf); } var bb = BoundingBox.FromBoundables(leaf.Boundables); var xLen = bb.Max.X - bb.Min.X; var yLen = bb.Max.Y - bb.Min.Y; var zLen = bb.Max.Z - bb.Min.Z; List <Boundable> sorted; if (xLen > yLen && xLen > zLen) { sorted = leaf.Boundables.OrderBy(x => x.BoundingBox.Centroid.X).ToList(); } else if (yLen > xLen && yLen > zLen) { sorted = leaf.Boundables.OrderBy(x => x.BoundingBox.Centroid.Y).ToList(); } else { sorted = leaf.Boundables.OrderBy(x => x.BoundingBox.Centroid.Z).ToList(); } var bestPlane = CalculateBestSplitPlane(sorted); //don't split further if (bestPlane.Cost > leaf.BoundingBox.Area * leaf.Boundables.Count) { return(leaf); } var left = new BVHNode(bestPlane.Left); var right = new BVHNode(bestPlane.Right); var parent = new BVHNode(Construct(left), Construct(right)); return(parent); }
public BVHNode Construct(BVHNode leaf) { if (leaf.Boundables.Count == 0) { return leaf; } var bb = BoundingBox.FromBoundables(leaf.Boundables); var xLen = bb.Max.X - bb.Min.X; var yLen = bb.Max.Y - bb.Min.Y; var zLen = bb.Max.Z - bb.Min.Z; List<Boundable> sorted; if (xLen > yLen && xLen > zLen) { sorted = leaf.Boundables.OrderBy(x => x.BoundingBox.Centroid.X).ToList(); } else if (yLen > xLen && yLen > zLen) { sorted = leaf.Boundables.OrderBy(x => x.BoundingBox.Centroid.Y).ToList(); } else { sorted = leaf.Boundables.OrderBy(x => x.BoundingBox.Centroid.Z).ToList(); } var bestPlane = CalculateBestSplitPlane(sorted); //don't split further if (bestPlane.Cost > leaf.BoundingBox.Area*leaf.Boundables.Count) { return leaf; } var left = new BVHNode(bestPlane.Left); var right = new BVHNode(bestPlane.Right); var parent = new BVHNode(Construct(left), Construct(right)); return parent; }
public BVHNode(BVHNode left, BVHNode right) { _left = left; _right = right; BoundingBox = BoundingBox.Combine(left.BoundingBox, right.BoundingBox); }
public BVHNode(BVHNode left) { _left = left; BoundingBox = left.BoundingBox; }