Hi!
I am implementing CustomMapTileDataSource feature. So far I can draw custom Tiles on fly with some shapes (see image below).
Now I need to draw lines on each Tile which UWP MapControl provides.
All my lines are precalculated with WGS82 coordinates and well tested.
I use this MSDN manual https://zcusa.951200.xyz/en-us/windows/uwp/maps-and-location/overlay-tiled-images
And here I can get WGS83 rect to filter lines I have to draw.
private async void customDataSource_BitmapRequestedAsync(CustomMapTileDataSource sender, MapTileBitmapRequestedEventArgs args)
{
var deferral = args.Request.GetDeferral();
const int tileSide = 256;
TileSystem.TileXYToPixelXY(args.X, args.Y, out int pixelX, out int pixelY);
var rect = new List<BasicGeoposition>();
// Add Top Left Geo Point
TileSystem.PixelXYToLatLong(pixelX, pixelY, args.ZoomLevel, out double latTopLeft, out double lngTopLeft);
rect.Add(new BasicGeoposition() { Latitude = latTopLeft, Longitude = lngTopLeft });
// Add Top Right Geo Point
TileSystem.PixelXYToLatLong(pixelX + tileSide, pixelY, args.ZoomLevel, out double latTopRight, out double lngTopRight);
rect.Add(new BasicGeoposition() { Latitude = latTopRight, Longitude = lngTopRight });
// Add Bottom Right Geo Point
TileSystem.PixelXYToLatLong(pixelX + tileSide, pixelY + tileSide, args.ZoomLevel, out double latBottomRight, out double lngBottomRight);
rect.Add(new BasicGeoposition() { Latitude = latBottomRight, Longitude = lngBottomRight });
// Add Bottom Left Geo Point
TileSystem.PixelXYToLatLong(pixelX, pixelY + tileSide, args.ZoomLevel, out double latBottomLeft, out double lngBottomLeft);
rect.Add(new BasicGeoposition() { Latitude = latBottomLeft, Longitude = lngBottomLeft });
var filterdLines = GetLinesByGeoRect(rect);
args.Request.PixelData = await CreateBitmapAsStreamAsync(filterdLines, args.ZoomLevel);
deferral.Complete();
}
And this event is particular fit to draw a concrete Tile that you can see in image up (I have used ds.DrawCircle to do test drawing).
private async Task<RandomAccessStreamReference> CreateBitmapAsStreamAsync(List<MyLine> lines, int zoom)
{
int pixelHeight = 256;
int pixelWidth = 256;
var randomAccessStream = new InMemoryRandomAccessStream();
var outputStream = randomAccessStream.GetOutputStreamAt(0);
var softwareBitmap = new SoftwareBitmap(BitmapPixelFormat.Bgra8, pixelHeight, pixelWidth, BitmapAlphaMode.Premultiplied);
var resourceCreator = CanvasDevice.GetSharedDevice();
var canvasBitmap = CanvasBitmap.CreateFromSoftwareBitmap(resourceCreator, softwareBitmap);
var canvasRenderTarget = new CanvasRenderTarget(resourceCreator, softwareBitmap.PixelWidth, softwareBitmap.PixelHeight, 96);
using (var ds = canvasRenderTarget.CreateDrawingSession())
{
ds.Antialiasing = CanvasAntialiasing.Antialiased;
foreach (var line in lines)
{
// Try to convert WGS84 Lat Long to Screen coordinates for this Tile
TileSystem.LatLongToPixelXY(line.latt, line.longt, zoom, out int startX, out int startY);
TileSystem.LatLongToPixelXY(line.latt, line.longt, zoom, out int endX, out int endY);
/*
50.016952, 8.772860 zoom 1 X: 268 Y: 174
50.016952, 8.772860 zoom 11 X: 274920 Y: 177771
*/
ds.DrawLine(startX, startY, endX, endY, Colors.Black, 1);
}
// ds.DrawCircle(new Vector2(100, 100), 100, Colors.Blue); // just to test drawing in Tile
// ds.DrawRectangle(1, 1, 255, 255, Colors.Black, 2); // just to test drawing in Tile
}
await canvasRenderTarget.SaveAsync(randomAccessStream, CanvasBitmapFileFormat.Png);
await randomAccessStream.FlushAsync();
return RandomAccessStreamReference.CreateFromStream(randomAccessStream);
}
The problem starts here TileSystem.LatLongToPixelXY As you see in my example for the same coordinates and different level of details (1-20) it gives weird X and Y
50.016952, 8.772860 zoom 1 X: 268 Y: 174
50.016952, 8.772860 zoom 11 X: 274920 Y: 177771
It is impossible to apply the value 177771 for the Tile 256 x 256 pixels do draw something!
So I have no clue how to apply it for the current Tile?
It seems like Microsoft should provide more clear explanation:
How to convert Latitude Longitude for current Tile is under drawing?
Thank you!