public TerrainTileHeader CalculateHeaderInfo(ref Vector3[] ecefPoints, Boolean lightingRequired) { BoundingSphere.FromPoints(ecefPoints); var hdr = new TerrainTileHeader(); hdr.CenterX = BoundingSphere.Center.X; hdr.CenterY = BoundingSphere.Center.Y; hdr.CenterZ = BoundingSphere.Center.Z; hdr.BoundingSphereRadius = BoundingSphere.Radius; return(hdr); }
private void MakeHeader(TerrainTileHeader headerRec) { MeshHeader = new TerrainTileHeader() { CenterX = headerRec.CenterX, CenterY = headerRec.CenterY, CenterZ = headerRec.CenterZ, MinimumHeight = headerRec.MinimumHeight, MaximumHeight = headerRec.MaximumHeight, BoundingSphereCenterX = headerRec.BoundingSphereCenterX, BoundingSphereCenterY = headerRec.BoundingSphereCenterY, BoundingSphereCenterZ = headerRec.BoundingSphereCenterZ, BoundingSphereRadius = headerRec.BoundingSphereRadius, HorizonOcclusionPointX = headerRec.HorizonOcclusionPointX, HorizonOcclusionPointY = headerRec.HorizonOcclusionPointY, HorizonOcclusionPointZ = headerRec.HorizonOcclusionPointZ }; }
/// <summary> /// Make tile header record /// </summary> private void MakeHeader(ref ElevationData evData) { // todo fill in all fields correctly Header = new TerrainTileHeader() { CenterX = -4869750.60295, CenterY = 517839.417383868, CenterZ = -4005385.98852821, MinimumHeight = evData.MinElevation, MaximumHeight = evData.MaxElevation, BoundingSphereCenterX = -4869750.60295, BoundingSphereCenterY = 517839.417383868, BoundingSphereCenterZ = -4005385.98852821, BoundingSphereRadius = 832547.176047396, HorizonOcclusionPointX = -0.775337351286795, HorizonOcclusionPointY = 0.0824478037997883, HorizonOcclusionPointZ = -0.639862876673674 }; }
/// <summary> /// Temp class /// </summary> /// <param name="minElevation"></param> /// <param name="maxElevation"></param> private void MakeFakeHeader(float minElevation, float maxElevation) { // todo fill in all fields correctly MeshHeader = new TerrainTileHeader() { CenterX = -4869750.60295, CenterY = 517839.417383868, CenterZ = -4005385.98852821, MinimumHeight = minElevation, MaximumHeight = maxElevation, BoundingSphereCenterX = -4869750.60295, BoundingSphereCenterY = 517839.417383868, BoundingSphereCenterZ = -4005385.98852821, BoundingSphereRadius = 832547.176047396, HorizonOcclusionPointX = 0.5, HorizonOcclusionPointY = 0.5, HorizonOcclusionPointZ = 0.5 }; }
/// <summary> /// Generate quantized mesh tile from the supplied grid /// </summary> /// <returns></returns> public bool BuildQuantizedMeshTile() { try { ComputeHeaderInfo(); // Turn grid into a quantized mesh var vertices = MeshBuilder.MakeQuantizedMesh(ref TileData); var tileHeader = new TerrainTileHeader() { MaximumHeight = TileData.MaximumHeight, MinimumHeight = TileData.MinimumHeight, CenterX = TileData.CenterX, CenterY = TileData.CenterY, CenterZ = TileData.CenterZ, BoundingSphereCenterX = TileData.BoundingSphereCenterX, BoundingSphereCenterY = TileData.BoundingSphereCenterY, BoundingSphereCenterZ = TileData.BoundingSphereCenterZ, BoundingSphereRadius = TileData.BoundingSphereRadius, HorizonOcclusionPointX = TileData.HorizonOcclusionPointX, HorizonOcclusionPointY = TileData.HorizonOcclusionPointY, HorizonOcclusionPointZ = TileData.HorizonOcclusionPointZ }; // This class constructs a tile from the computed mesh var tileBuilder = new TileBuilder(); var tile = tileBuilder.MakeTile(vertices, ref TileData.VertexNormals, tileHeader, MapUtils.GridSizeToTriangleCount(TileData.GridSize), TileData.GridSize, TileData.HasLighting); QuantizedMeshTile = CompressTile ? MapUtils.Compress(tile) : tile; BuildTileFaultCode = RequestErrorStatus.OK; } catch (Exception E) { Log.LogError(E, "BuildQuantizedMeshTile: Exception:"); return(false); } return(true); }
/// <summary> /// From the vertices passed in make quantized mesh tile /// </summary> /// <param name="vertices"></param> /// <param name="headerRec"></param> /// <param name="trianglesCount"></param> /// <param name="tileSize"></param> /// <returns></returns> public byte[] MakeTile(VertexData vertices, TerrainTileHeader headerRec, int trianglesCount, int gridSize) { // Assemble tile data _TriangleCount = trianglesCount; _GridSize = gridSize; MakeHeader(headerRec); EncodeVertices(ref vertices); MakeTriangleIndices(); MakeEdgeIndicesData(); // We are now ready to assemble the tile into a byte array var ms = new MemoryStream(); using (BinaryWriter writer = new BinaryWriter(ms)) // using (BinaryWriter writer = new BinaryWriter(File.Open(outFile, FileMode.Create))) { // write header writer.Write(MeshHeader.CenterX); writer.Write(MeshHeader.CenterY); writer.Write(MeshHeader.CenterZ); writer.Write(MeshHeader.MinimumHeight); writer.Write(MeshHeader.MaximumHeight); writer.Write(MeshHeader.BoundingSphereCenterX); writer.Write(MeshHeader.BoundingSphereCenterY); writer.Write(MeshHeader.BoundingSphereCenterZ); writer.Write(MeshHeader.BoundingSphereRadius); writer.Write(MeshHeader.HorizonOcclusionPointX); writer.Write(MeshHeader.HorizonOcclusionPointY); writer.Write(MeshHeader.HorizonOcclusionPointZ); // write vertex data in order. count, long array, lat array, height array writer.Write(MeshVertexData.vertexCount); for (int i = 0; i < MeshVertexData.vertexCount; i++) { writer.Write(MeshVertexData.u[i]); // longitude } for (int i = 0; i < MeshVertexData.vertexCount; i++) { writer.Write(MeshVertexData.v[i]); // latitude } for (int i = 0; i < MeshVertexData.vertexCount; i++) { writer.Write(MeshVertexData.height[i]); //heights } // write triangle indices writer.Write(MeshIndexData16.triangleCount); for (int i = 0; i < MeshIndexData16.triangleCount * 3; i++) // three indices to a triangle { writer.Write(MeshIndexData16.indices[i]); } // write west indices writer.Write(MeshEdgeIndices16.westVertexCount); for (int i = 0; i < MeshEdgeIndices16.westVertexCount; i++) { writer.Write(MeshEdgeIndices16.westIndices[i]); } // write south indices writer.Write(MeshEdgeIndices16.southVertexCount); for (int i = 0; i < MeshEdgeIndices16.southVertexCount; i++) { writer.Write(MeshEdgeIndices16.southIndices[i]); } // write east indices writer.Write(MeshEdgeIndices16.eastVertexCount); for (int i = 0; i < MeshEdgeIndices16.eastVertexCount; i++) { writer.Write(MeshEdgeIndices16.eastIndices[i]); } // write north indices writer.Write(MeshEdgeIndices16.northVertexCount); for (int i = 0; i < MeshEdgeIndices16.northVertexCount; i++) { writer.Write(MeshEdgeIndices16.northIndices[i]); } // todo normals return(ms.ToArray()); } }
/// <summary> /// Full Test on Bitmap tiler /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private async void btnMakeBMTile_Click(object sender, EventArgs e) { int x = Convert.ToInt32(txtX2.Text); int y = Convert.ToInt32(txtY2.Text); int zoom = Convert.ToInt32(txtZ2.Text); listBox1.Items.Add("Fetching DEM..."); // class to get digital elevation models(DEM) //BitmapDEMSource demSrc = new BitmapDEMSource(); TRexDEMSource demSrc = new TRexDEMSource(); demSrc.Initalize(new MapHeader() { GridSize = Convert.ToInt32(txtGridSizeBM.Text), MinElevation = 0, MaxElevation = 1000 }); var elevData = await demSrc.GetDemXYZ(x, y, zoom); listBox1.Items.Add($"DEM length {elevData.Elev.Length}"); listBox1.Items.Add("Making Mesh..."); // This class constructs a cesium quantized mesh from the dem var vertices = new Mesh().MakeFakeMesh(ref elevData); listBox1.Items.Add("Making Tile..."); // This class constructs a quantized mesh tile mesh from the original mesh var hdr = new TerrainTileHeader() { BoundingSphereCenterX = elevData.BoundingSphereCenterX, BoundingSphereCenterY = elevData.BoundingSphereCenterY, BoundingSphereCenterZ = elevData.BoundingSphereCenterZ, CenterX = elevData.CenterX, CenterY = elevData.CenterY, CenterZ = elevData.CenterZ, HorizonOcclusionPointX = elevData.HorizonOcclusionPointX, HorizonOcclusionPointY = elevData.HorizonOcclusionPointY, HorizonOcclusionPointZ = elevData.HorizonOcclusionPointZ, BoundingSphereRadius = elevData.BoundingSphereRadius, MinimumHeight = elevData.MinimumHeight, MaximumHeight = elevData.MaximumHeight }; var tile = new Tiler().MakeTile(vertices, hdr, MapUtil.GridSizeToTriangleCount(elevData.GridSize), elevData.GridSize); listBox1.Items.Add($"Tile Ready. Size:{tile.Length} . Saving to {txtBMPath.Text}"); var ms = new MemoryStream(tile); using (FileStream fs = new FileStream(txtBMPath.Text, FileMode.Create)) using (GZipStream zipStream = new GZipStream(fs, CompressionMode.Compress, false)) { zipStream.Write(ms.ToArray(), 0, ms.ToArray().Length); // .Write(bytes, 0, bytes.Length); } // Open View txtView.Text = txtBMPath.Text; btnView_Click(sender, e); }
public async Task <IActionResult> GetStaticTile(int x, int y, int z, string formatExtension, [FromQuery] Guid projectUid, [FromQuery] Guid filterUid) { // todo for now default values. these will be passed in eventually var testDataPath = _configuration["TestDataPath"]; Guid projectId = projectUid; Guid filterid = filterUid; bool isValid = Guid.TryParse(_configuration["DefaultProjectUid"], out projectId); if (!isValid) { return(NotFound()); // todo } if (z < 1) // root level { // these two tiles are standard. Use tiler to fetch the correct tile var basicTile = await new Tiler.Tiler().FetchTile(testDataPath, x, y, z); if (basicTile != null) { HttpContext.Response.Headers.Add("Content-Encoding", "gzip"); // already compressed on disk HttpContext.Response.Headers.Add("Content-Length", basicTile.Length.ToString()); HttpContext.Response.Headers.Add("Content-Type", "application/octet-stream"); HttpContext.Response.Headers.Add("Content-Disposition", $"attachment;filename={y}.terrain"); return(File(basicTile, _TerrainDataQM)); } Console.WriteLine($"*** Tile x:{x},y:{y},z:{z} was found ***"); return(NotFound()); } var elevData = await _demSource.GetDemXYZ(x, y, z); // DI injected for single instance // This class constructs a cesium quantized mesh from the dem var vertices = new Mesh.Mesh().MakeFakeMesh(ref elevData); var tempHeadr = new TerrainTileHeader() { MaximumHeight = elevData.MaximumHeight, MinimumHeight = elevData.MinimumHeight, CenterX = elevData.CenterX, CenterY = elevData.CenterY, CenterZ = elevData.CenterZ, BoundingSphereCenterX = elevData.BoundingSphereCenterX, BoundingSphereCenterY = elevData.BoundingSphereCenterY, BoundingSphereCenterZ = elevData.BoundingSphereCenterZ, BoundingSphereRadius = elevData.BoundingSphereRadius, HorizonOcclusionPointX = elevData.HorizonOcclusionPointX, HorizonOcclusionPointY = elevData.HorizonOcclusionPointY, HorizonOcclusionPointZ = elevData.HorizonOcclusionPointZ }; // This class constructs a quantized mesh tile mesh from the original mesh var tile = new Tiler.Tiler().MakeTile(vertices, tempHeadr, MapUtil.GridSizeToTriangleCount(elevData.GridSize), elevData.GridSize); if (tile != null) { var compressed = MapUtil.Compress(tile); HttpContext.Response.Headers.Add("Content-Encoding", "gzip"); // already compressed on disk HttpContext.Response.Headers.Add("Content-Length", compressed.Length.ToString()); HttpContext.Response.Headers.Add("Content-Type", "application/octet-stream"); HttpContext.Response.Headers.Add("Content-Disposition", $"attachment;filename={y}.terrain"); return(File(compressed, _TerrainDataQM)); } return(NotFound()); }
public async Task <IActionResult> GetBitmapTile(int x, int y, int z, string formatExtension) { // todo for now default values. these will be passed in eventually var testDataPath = _configuration["TestDataPath"]; Guid projectId; bool isValid = Guid.TryParse(_configuration["DefaultProjectUid"], out projectId); if (!isValid) { return(NotFound()); // todo } if (z < 1) { // these two tiles are standard // Use tiler to fetch the correct tile var basicTile = await new Tiler.Tiler().FetchTile(testDataPath, x, y, z); if (basicTile != null) { HttpContext.Response.Headers.Add("Content-Encoding", "gzip"); // already compressed on disk // HttpContext.Response.Headers.Add("Access-Control-Allow-Origin","*"); // already compressed on disk HttpContext.Response.Headers.Add("Content-Length", basicTile.Length.ToString()); HttpContext.Response.Headers.Add("Content-Type", "application/octet-stream"); HttpContext.Response.Headers.Add("Content-Disposition", $"attachment;filename={y}.terrain"); return(File(basicTile, _TerrainDataQM)); } Console.WriteLine($"*** Tile x:{x},y:{y},z:{z} was found ***"); return(NotFound()); // todo } // Bitmap tiler BitmapDEMSource demSrc = new BitmapDEMSource(); var elevData = await demSrc.GetDemXYZ(x, y, z); // DI injected for single instance // This class constructs a cesium quantized mesh from the dem var vertices = new Mesh.Mesh().MakeFakeMesh(ref elevData); // todo fill in header details var tempHeadr = new TerrainTileHeader() { MaximumHeight = elevData.MaximumHeight, MinimumHeight = elevData.MinimumHeight, CenterX = elevData.CenterX, CenterY = elevData.CenterY, CenterZ = elevData.CenterZ, BoundingSphereCenterX = elevData.BoundingSphereCenterX, BoundingSphereCenterY = elevData.BoundingSphereCenterY, BoundingSphereCenterZ = elevData.BoundingSphereCenterZ, BoundingSphereRadius = elevData.BoundingSphereRadius, HorizonOcclusionPointX = elevData.HorizonOcclusionPointX, HorizonOcclusionPointY = elevData.HorizonOcclusionPointY, HorizonOcclusionPointZ = elevData.HorizonOcclusionPointZ }; // This class constructs a quantized mesh tile mesh from the original mesh var tile = new Tiler.Tiler().MakeTile(vertices, tempHeadr, MapUtil.GridSizeToTriangleCount(elevData.GridSize), elevData.GridSize); // Debugging code string file = $"c:\\temp\\Test-{x}-{y}-{z}.terrain"; FileInfo fi = new FileInfo(file); if (!fi.Exists && z == 8 && x == 501) { var ms = new MemoryStream(tile); using (FileStream fs = new FileStream(file, FileMode.Create)) using (GZipStream zipStream = new GZipStream(fs, CompressionMode.Compress, false)) { zipStream.Write(ms.ToArray(), 0, ms.ToArray().Length); // .Write(bytes, 0, bytes.Length); } } if (tile != null) { var compressed = MapUtil.Compress(tile); HttpContext.Response.Headers.Add("Content-Encoding", "gzip"); // already compressed on disk HttpContext.Response.Headers.Add("Content-Length", compressed.Length.ToString()); HttpContext.Response.Headers.Add("Content-Type", "application/octet-stream"); HttpContext.Response.Headers.Add("Content-Disposition", $"attachment;filename={y}.terrain"); return(File(compressed, _TerrainDataQM)); // return Ok(MapUtil.Compress(tile)); } else { return(NotFound()); } }
public async Task <IActionResult> GetFakeTile(int x, int y, int z, string formatExtension) { // todo for now default values. these will be passed in eventually var testDataPath = _configuration["TestDataPath"]; Guid projectId; bool isValid = Guid.TryParse(_configuration["DefaultProjectUid"], out projectId); if (!isValid) { return(NotFound()); // todo } if (z < 1) { // these two tiles are standard // Use tiler to fetch the correct tile var basicTile = await new Tiler.Tiler().FetchTile(testDataPath, x, y, z); if (basicTile != null) { HttpContext.Response.Headers.Add("Content-Encoding", "gzip"); // already compressed on disk // HttpContext.Response.Headers.Add("Access-Control-Allow-Origin","*"); // already compressed on disk HttpContext.Response.Headers.Add("Content-Length", basicTile.Length.ToString()); HttpContext.Response.Headers.Add("Content-Type", "application/octet-stream"); HttpContext.Response.Headers.Add("Content-Disposition", $"attachment;filename={y}.terrain"); Console.WriteLine($"*** Tile x:{x},y:{y},z:{z} was found ***"); return(File(basicTile, _TerrainDataQM)); } return(NotFound()); } FakeDEMSource demSrc = new FakeDEMSource(); demSrc.Initalize(new MapHeader() { GridSize = _GridSize }); // todo x,y,z to lat lon var elevData = await demSrc.GetDemLL(1, 1, 1, 1); // just the same tile always for now // This class constructs a cesium quantized mesh from the dem var vertices = new Mesh.Mesh().MakeFakeMesh(ref elevData); // todo fill in header details var tempHeadr = new TerrainTileHeader() { MaximumHeight = elevData.MaximumHeight, MinimumHeight = elevData.MinimumHeight }; // This class constructs a quantized mesh tile mesh from the original mesh var tile = new Tiler.Tiler().MakeTile(vertices, tempHeadr, MapUtil.GridSizeToTriangleCount(elevData.GridSize), elevData.GridSize); if (tile != null) { var compressed = MapUtil.Compress(tile); HttpContext.Response.Headers.Add("Content-Encoding", "gzip"); // already compressed on disk // HttpContext.Response.Headers.Add("Access-Control-Allow-Origin","*"); // already compressed on disk HttpContext.Response.Headers.Add("Content-Length", compressed.Length.ToString()); HttpContext.Response.Headers.Add("Content-Type", "application/octet-stream"); HttpContext.Response.Headers.Add("Content-Disposition", $"attachment;filename={y}.terrain"); return(File(compressed, _TerrainDataQM)); } else { return(NotFound()); } }