Reputation: 3979
Hello I work on a game that is based on a map generation with BING.
The problem is: The card is generated based on address given by the user, after which I would like to generate a 1km2 card (1000m wide and 1000m long).
Unfortunately I found no bing API to retrieve a map with defined size in meters. I can only define a "level zoom" and a resolution.
Here's what I use now (from Microsoft Bing Api Tile code library example):
// Get a bing Map (resolution max. 834 pixel) with zoom level 16
var stream = await httpClient.GetStreamAsync("api/newmap/?latitude=46.6052284&longitude=7.0967002&mapSizeHeight=834&mapSizeWidth=834&zoomLevel=16");
// Calculated from "latitudeCentre" and "zoom level" , i get like 0.8 meter/pixel
double meterPerPixel = TileSystem.GroundResolution(latitudeCentre, 16);
For example (834/834 pixel) and zoom level 16 => which gives me about a scale of 0.8 meter / pixel. I can not generate a 1 meter / pixel map. Do you think a solution to my problem exist?
I really hope so if yes ^^ :-)
Upvotes: 1
Views: 395
Reputation: 3979
Ok , YES It's possible !! I take time for make a function for finally i solve it by myself . But i am shocked , nobody has never ask this question , and Microsoft never post the code for that . I think this function can be really usefull .
private void SetBoundingBoxLocationAndZoom(double latitudeCentre)
{
// 1024/1024 meters
double desiredMapSize = 1024.0;
int bestMatchMapSize = 0;
int bestMatchMapResolution = 0;
int bestMatchMapZoom = 0;
//Starts with the largest zoom and ending with the smallest (remote) (min zoomLevel [1])
// 1 - 21
for (int zoom = 21; zoom >= 1; zoom--)
{
//Starts with the highest resolution and ending with the smallest (min pixel 80/80)
// 80 - 834
for (int resolution = 834; resolution >= 80; resolution--)
{
double meterPerPixel = TileSystem.GroundResolution(latitudeCentre, zoom);
double mapSize = meterPerPixel * resolution;
if(Math.Abs(desiredMapSize - mapSize) < Math.Abs(desiredMapSize - bestMatchMapSize))
{
bestMatchMapSize = (int)mapSize;
bestMatchMapResolution = resolution;
bestMatchMapZoom = zoom;
}
}
}
zoomLevel = bestMatchMapZoom;
sizeMapInMeter = bestMatchMapSize;
resolutionMap = bestMatchMapResolution;
}
/// <summary>
/// Determines the ground resolution (in meters per pixel) at a specified
/// latitude and level of detail.
/// </summary>
/// <param name="latitude">Latitude (in degrees) at which to measure the
/// ground resolution.</param>
/// <param name="levelOfDetail">Level of detail, from 1 (lowest detail)
/// to 23 (highest detail).</param>
/// <returns>The ground resolution, in meters per pixel.</returns>
public static double GroundResolution(double latitude, int levelOfDetail)
{
latitude = Clip(latitude, MinLatitude, MaxLatitude);
return Math.Cos(latitude * Math.PI / 180) * 2 * Math.PI * EarthRadius / MapSize(levelOfDetail);
}
Upvotes: 1