public DualContouringTestEnvironment() { cellSize = 0.5f; lines = new LineManager3DLines(TW.Graphics.Device); this.lines.SetMaxLines(1000000); PlaceableObjectGrid = new IntersectableCube(); cameraLightSimulator = new CameraLightSimulator(); surfaceRenderer = VoxelCustomRenderer.CreateDefault(TW.Graphics); TW.Graphics.AcquireRenderer().AddCustomGBufferRenderer(surfaceRenderer); }
/// <summary> /// /// </summary> /// <param name="gridWorldSize">Size of the grid in world space</param> /// <param name="resolution">Aka the subdivision of the grid</param> /// <param name="world">Worldmatrix of the object</param> /// <param name="obj"></param> /// <returns></returns> public static HermiteDataGrid FromIntersectableGeometry(float gridWorldSize, int resolution, Matrix world, IIntersectableObject obj) { var numCubes = new Point3(resolution, resolution, resolution); var grid = new HermiteDataGrid(); var gridToWorld = Matrix.Scaling(1f / resolution, 1f / resolution, 1f / resolution) * Matrix.Scaling(new Vector3(gridWorldSize)); var gridToGeometry = gridToWorld * Matrix.Invert(world); var geometryToGrid = Matrix.Invert(gridToGeometry); // Fill vertices grid.cells = new Array3D <Vertex>(numCubes + new Point3(1, 1, 1)); grid.ForEachGridPoint(cube => { grid.cells[cube] = new Vertex() { Sign = obj.IsInside(Vector3.TransformCoordinate(cube.ToVector3(), gridToGeometry)), EdgeData = new Vector4[3] }; }); // Find changing edges and calculate edge info grid.ForEachGridPoint(cube => { var sign = grid.GetSign(cube); for (int i = 0; i < grid.dirs.Length; i++) { Point3 start = cube; Point3 end = cube + grid.dirs[i]; if (sign == grid.GetSign(end)) { continue; } //sign difference Vector3 startT = Vector3.TransformCoordinate(start, gridToGeometry); Vector3 endT = Vector3.TransformCoordinate(end, gridToGeometry); var vector4 = obj.GetIntersection(startT, endT); var intersectionPoint = Vector3.TransformCoordinate(Vector3.Lerp(startT, endT, vector4.W), geometryToGrid); var realLerp = Vector3.Distance(start, intersectionPoint); // /1 Debug.Assert(Math.Abs(Vector3.Distance(start, end) - 1) < 0.001); // Algo check vector4 = new Vector4(Vector3.Normalize(Vector3.TransformNormal(vector4.TakeXYZ(), geometryToGrid)), realLerp); grid.cells[cube].EdgeData[i] = vector4; } }); return(grid); }