/// <summary> /// Read a heightmap report /// </summary> /// <param name="from">Origin</param> /// <param name="map">Deserialized heightmap</param> /// <returns>Number of bytes read</returns> public static int ReadHeightMap(ReadOnlySpan <byte> from, out Heightmap map) { HeightMapHeader header = MemoryMarshal.Cast <byte, HeightMapHeader>(from)[0]; map = new Heightmap { XMin = header.XMin, XMax = header.XMax, XSpacing = header.XSpacing, YMin = header.YMin, YMax = header.YMax, YSpacing = header.YSpacing, Radius = header.Radius, NumX = header.NumX, NumY = header.NumY }; if (from.Length > Marshal.SizeOf(header)) { ReadOnlySpan <byte> zCoordinates = from.Slice(Marshal.SizeOf(header), Marshal.SizeOf <float>() * map.NumX * map.NumY); map.ZCoordinates = MemoryMarshal.Cast <byte, float>(zCoordinates).ToArray(); } else { map.NumX = map.NumY = 0; map.ZCoordinates = Array.Empty <float>(); } return(Marshal.SizeOf(header) + map.ZCoordinates.Length * Marshal.SizeOf <float>()); }
/// <summary> /// Write a heightmap as read by G29 S1 /// </summary> /// <param name="to">Destination</param> /// <param name="map">Heightmap to write</param> /// <returns>Number of bytes written</returns> public static int WriteHeightMap(Span <byte> to, Heightmap map) { HeightMapHeader header = new HeightMapHeader { XMin = map.XMin, XMax = map.XMax, XSpacing = map.XSpacing, YMin = map.YMin, YMax = map.YMax, YSpacing = map.YSpacing, Radius = map.Radius, NumX = (ushort)map.NumX, NumY = (ushort)map.NumY }; MemoryMarshal.Write(to, ref header); Span <float> coords = MemoryMarshal.Cast <byte, float>(to.Slice(Marshal.SizeOf(header))); for (int i = 0; i < map.NumX * map.NumY; i++) { coords[i] = map.ZCoordinates[i]; } return(Marshal.SizeOf(header) + Marshal.SizeOf <float>() * map.NumX * map.NumY); }
/// <summary> /// Read a heightmap report /// </summary> /// <param name="from">Origin</param> /// <param name="map">Deserialized heightmap</param> /// <returns>Number of bytes read</returns> public static int ReadHeightMap(ReadOnlySpan <byte> from, out Heightmap map) { HeightMapHeader header = MemoryMarshal.Read <HeightMapHeader>(from); map = new Heightmap { XMin = header.XMin, XMax = header.XMax, XSpacing = header.XSpacing, YMin = header.YMin, YMax = header.YMax, YSpacing = header.YSpacing, Radius = header.Radius, NumX = header.NumX, NumY = header.NumY }; int headerSize = Marshal.SizeOf <HeightMapHeader>(), dataLength = Marshal.SizeOf <float>() * map.NumX * map.NumY; if (from.Length > headerSize) { ReadOnlySpan <byte> zCoordinates = from.Slice(headerSize, dataLength); map.ZCoordinates = MemoryMarshal.Cast <byte, float>(zCoordinates).ToArray(); } else { map.NumX = map.NumY = dataLength = 0; map.ZCoordinates = Array.Empty <float>(); } return(headerSize + dataLength); }