Venue Maps API Developer's Guide

# Key Concepts

This section provides insights into the key concepts used throughout the HERE Venue Maps API.

## The Mercator Projection

The Venue Maps API serves map tiles obtained by mapping points on the surface of a sphere (the globe) to points on a plane, using the normalized Mercator projection.

The basic Mercator projection formula is this:

{λ, φ} -> x[-1, 1] y [-1, 1]

In this formula:

 λ = longitude φ = latitude x = λ / π y = ln(tan(π/4 + φ/2)) / π

The plane represents the globe as a square grid of map tiles. The size of the grid depends on the map zoom level. At the lowest zoom level, the world is contained in one map tile. At the next higher zoom level, the world is two tiles wide and two tiles high (2x2), at the next level above that, the grid is 4x4, then 8x8, 16x16, and so on up to the maximum zoom for a particular region. In other words, at each zoom level the tiles that make up the complete map of the world form a grid in which the number of tiles is equal to two to the power of two multiplied by the zoom level (2(2*zoom)).

The relationship between tiles at two consecutive zoom levels can be expressed as follows:

col1,z+1 = (2*colz) + 1row1,z+1 = (2*rowz) + 1

In this formula:

 col = column number in the tile grid row = row number in the tile grid z = zoom level

The diagram below demonstrates this graphically:

You can use this information to obtain the grid coordinates (row and column) of the map tile for a particular geographic location in your application. The following pseudo code contains the complete algorithm:
``````--- javascript ---
var lat = 52.525439, // Latitude
lon = 13.38727,    // Longitude
z = 12,        // Zoom level
n,
xTile,
yTile;

latRad = lat * Math.PI / 180;
n = Math.pow(2, z);
xTile = n * ((lon + 180) / 360);
Math.PI)) / 2;

--- output ---
n = 4096
xTile = 2200.31 // Column
yTile = 1343.20 // Row
``````

The zoom level and tile row and column can be used as URL variables separated by the '/' character in map tile requests. Note that they must be provided in this order: `zoom/column/row`. This is the [Z]/[X]/[Y] addressing scheme.

The map tile specification is typically preceded by other path variables and may be followed either by further path variables and/or query parameters.

Specifying the grid location of a map tile in terms of zoom level, column and row as described under The Mercator Projection is easy to understand and intuitive in practise. However, the grid is a two-dimensional array and as such does not offer efficient storage and retrieval. A better solution is a one-dimensional array, where each item is uniquely addressable by a single value. This is made possible by quadkeys, which combine the zoom level, column and row information for a tile in a one value.

In fact, a quadkey is a string containing a numeric value. The value is obtained by interleaving the bits of the row and column coordinates of a tile in the grid at the given zoom level, then converting the result to a base-4 number (the leading zeros are retained). The length of a quadkey string (the number of digits/characters) equals the zoom level of the tile.

For example, we can obtain the quadkey for a map tile in column 3 and row 5 at zoom level 5 as follows:

``````// Convert the column (x) and row (y) values
// to their binary (b) equivalents:
x = 3 -> 011b

y = 5 -> 101b

// Interleave the binary values (b), convert the
// combined result to a base-4 (q) number and
// finally convert that to a string:
quadkey = 100111b -> 213q -> "213"
``````

The code below shows a JavaScript implementation of the algorithm that calculates quadkeys. The inputs are the coordinates of the a map tile and the zoom level. The return value is a string containing the quadkey. The lower part of the code block shows the function called to calculate a quadkey for zoom level 16, which is also the length of the output string shown on the last line.

``````--- input ---
xTile: 35210  // Column
yTile: 21493  // Row
z: 16     // Zoom Level

--- JavaScript ---
for (var i = z; i > 0; i--) {
var digit = "0",
mask = 1 << (i - 1);
if ((xTile & mask) != 0) {
digit++;
}

if ((yTile & mask) != 0) {
digit = digit + 2;
}
} // for i return quadKey;

}

--- output ---

Note that when using a quadkey address, you cannot specify the size or format of the map tile image. The response always includes an image that measures 256 x 256 pixels and the format is `png32`.

``````--- JavaScript ---
PI = Math.PI,
lat = 52.519067, //latitude
lon = 13.415851, //longitude
z = 16; //zoom level
n = Math.pow(2, z);
xTile = n * ((lon + 180)/360);

--- Output ---
n = 65536
xTile = 35210.28114204445
yTile = 21493.148547728106
``````

xTile and yTile are used as an input for the following step to generate their corresponding quadkey.

Venue Maps API uses Bing Maps Tile System to encode xTile, yTile and Zoom Level into a quadkey. Each quadkey is prefixed with floor level.

We continue with the tile coordinates we calculated in Example Calculate Tile Address

``````--- Input ---
xTile: 35210
yTile: 21493
zoom level: 16

--- JavaScript ---
for (var i = z; i > 0; i--) {
var digit = "0",
mask = 1 << (i - 1);
if ((xTile & mask) != 0) {
digit++;
}
if ((yTile & mask) != 0) {
digit++;
digit++;
}

}

--- Output ---
``````

Example of Venue Maps API URL using the calculated QuadKey:

``````http://static-3.venue.maps.api.here.com
/0/tiles-png
/L0/1202102332221212.png?
Policy=<Policy-value>
&Signature=<Signature-value>
&Key-Pair-Id=<Key-Pair-Id-value>
&app_id={YOUR_APP_ID}
&app_code={YOUR_APP_CODE}``````

Resulting Venue Maps API tile:

You cannot use this account to purchase a commercial plan on Developer Portal, as it is already associated to plans with different payment methods.

To purchase a commercial plan on Developer Portal, please register for or sign in with a different HERE Account.

Something took longer than expected.

The project should be available soon under your projects page.

Sorry, our services are not available in this region.

Something seems to have gone wrong. Please try again later.

We've detected that your account is set to Australian Dollars (AUD).
Unfortunately, we do not offer checkouts in AUD anymore.
You can continue using your current plan as normal, but to subscribe to one of our new plans,