diff --git a/examples/wmts-hidpi.html b/examples/wmts-hidpi.html new file mode 100644 index 0000000000..71f31e5648 --- /dev/null +++ b/examples/wmts-hidpi.html @@ -0,0 +1,51 @@ + + + + + + + + + + + WMTS HiDPI example + + + + + +
+ +
+
+
+
+
+ +
+ +
+

WMTS HiDPI example

+

Example of a WMTS based HiDPI layer.

+
+

See the wmts-hidpi.js source to see how this is done.

+
+
hidpi, retina, wmts
+
+ +
+ +
+ + + + + + + diff --git a/examples/wmts-hidpi.js b/examples/wmts-hidpi.js new file mode 100644 index 0000000000..a89a1fbe5a --- /dev/null +++ b/examples/wmts-hidpi.js @@ -0,0 +1,75 @@ +goog.require('ol.BrowserFeature'); +goog.require('ol.Map'); +goog.require('ol.View2D'); +goog.require('ol.layer.Tile'); +goog.require('ol.source.WMTS'); +goog.require('ol.tilegrid.WMTS'); + + +var template = + '{Layer}/{Style}/{TileMatrixSet}/{TileMatrix}/{TileRow}/{TileCol}.jpeg'; +var urls = [ + 'http://maps1.wien.gv.at/basemap/' + template, + 'http://maps2.wien.gv.at/basemap/' + template, + 'http://maps3.wien.gv.at/basemap/' + template, + 'http://maps4.wien.gv.at/basemap/' + template, + 'http://maps.wien.gv.at/basemap/' + template +]; + + +// HiDPI support: +// * Use 'bmaphidpi' layer (pixel ratio 2) for device pixel ratio > 1 +// * Use 'geolandbasemap' layer (pixel ratio 1) for device pixel ratio == 1 +var hiDPI = ol.BrowserFeature.DEVICE_PIXEL_RATIO > 1; + +var source = new ol.source.WMTS({ + extent: [977844.377599999, 5837774.6617, 1915609.8654, 6295560.8122], + projection: 'EPSG:3857', + layer: hiDPI ? 'bmaphidpi' : 'geolandbasemap', + tilePixelRatio: hiDPI ? 2 : 1, + style: 'normal', + matrixSet: 'google3857', + urls: urls, + requestEncoding: /** @type {ol.source.WMTSRequestEncoding} */ ('REST'), + tileGrid: new ol.tilegrid.WMTS({ + origin: [-20037508.3428, 20037508.3428], + resolutions: [ + 559082264.029 * 0.28E-3, + 279541132.015 * 0.28E-3, + 139770566.007 * 0.28E-3, + 69885283.0036 * 0.28E-3, + 34942641.5018 * 0.28E-3, + 17471320.7509 * 0.28E-3, + 8735660.37545 * 0.28E-3, + 4367830.18773 * 0.28E-3, + 2183915.09386 * 0.28E-3, + 1091957.54693 * 0.28E-3, + 545978.773466 * 0.28E-3, + 272989.386733 * 0.28E-3, + 136494.693366 * 0.28E-3, + 68247.3466832 * 0.28E-3, + 34123.6733416 * 0.28E-3, + 17061.8366708 * 0.28E-3, + 8530.91833540 * 0.28E-3, + 4265.45916770 * 0.28E-3, + 2132.72958385 * 0.28E-3, + 1066.36479193 * 0.28E-3 + ], + matrixIds: [ + 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19 + ] + }) +}); + +var map = new ol.Map({ + layers: [ + new ol.layer.Tile({ + source: source + }) + ], + target: 'map', + view: new ol.View2D({ + center: [1823849, 6143760], + zoom: 11 + }) +}); diff --git a/externs/olx.js b/externs/olx.js index 7c87c7bfdf..7efe62290f 100644 --- a/externs/olx.js +++ b/externs/olx.js @@ -2751,6 +2751,7 @@ olx.source.GPXOptions.prototype.urls; * ol.TileLoadFunctionType)|undefined), * tileGrid: (ol.tilegrid.TileGrid|undefined), * tileLoadFunction: (ol.TileLoadFunctionType|undefined), + * tilePixelRatio: (number|undefined), * tileUrlFunction: (ol.TileUrlFunctionType|undefined)}} * @todo api */ @@ -2822,6 +2823,16 @@ olx.source.TileImageOptions.prototype.tileGrid; olx.source.TileImageOptions.prototype.tileLoadFunction; +/** + * The pixel ratio used by the tile service. For example, if the tile + * service advertizes 256px by 256px tiles but actually sends 512px + * by 512px images (for retina/hidpi devices) then `tilePixelRatio` + * should be set to `2`. Default is `1`. + * @type {number|undefined} + */ +olx.source.TileImageOptions.prototype.tilePixelRatio; + + /** * Optional function to get tile URL given a tile coordinate and the projection. * @type {ol.TileUrlFunctionType|undefined} @@ -4176,6 +4187,7 @@ olx.source.StaticVectorOptions.prototype.urls; * requestEncoding: (ol.source.WMTSRequestEncoding|undefined), * layer: string, * style: string, + * tilePixelRatio: (number|undefined), * version: (string|undefined), * format: (string|undefined), * matrixSet: string, @@ -4252,6 +4264,16 @@ olx.source.WMTSOptions.prototype.layer; olx.source.WMTSOptions.prototype.style; +/** + * The pixel ratio used by the tile service. For example, if the tile + * service advertizes 256px by 256px tiles but actually sends 512px + * by 512px images (for retina/hidpi devices) then `tilePixelRatio` + * should be set to `2`. Default is `1`. + * @type {number|undefined} + */ +olx.source.WMTSOptions.prototype.tilePixelRatio; + + /** * WMTS version. Default to `1.0.0`. * @type {string|undefined} diff --git a/src/ol/source/tileimagesource.js b/src/ol/source/tileimagesource.js index e66c4115fd..66de03572d 100644 --- a/src/ol/source/tileimagesource.js +++ b/src/ol/source/tileimagesource.js @@ -30,7 +30,8 @@ ol.source.TileImage = function(options) { logo: options.logo, opaque: options.opaque, projection: options.projection, - tileGrid: options.tileGrid + tileGrid: options.tileGrid, + tilePixelRatio: options.tilePixelRatio }); /** diff --git a/src/ol/source/tilesource.js b/src/ol/source/tilesource.js index dcf6d2c6aa..0e31459b27 100644 --- a/src/ol/source/tilesource.js +++ b/src/ol/source/tilesource.js @@ -16,6 +16,7 @@ goog.require('ol.tilegrid.TileGrid'); * extent: (ol.Extent|undefined), * logo: (string|undefined), * opaque: (boolean|undefined), + * tilePixelRatio: (number|undefined), * projection: ol.proj.ProjectionLike, * tileGrid: (ol.tilegrid.TileGrid|undefined)}} */ @@ -48,6 +49,13 @@ ol.source.Tile = function(options) { */ this.opaque_ = goog.isDef(options.opaque) ? options.opaque : false; + /** + * @private + * @type {number} + */ + this.tilePixelRatio_ = goog.isDef(options.tilePixelRatio) ? + options.tilePixelRatio : 1; + /** * @protected * @type {ol.tilegrid.TileGrid} @@ -185,7 +193,7 @@ ol.source.Tile.prototype.getTileGridForProjection = function(projection) { ol.source.Tile.prototype.getTilePixelSize = function(z, pixelRatio, projection) { var tileGrid = this.getTileGridForProjection(projection); - return tileGrid.getTileSize(z); + return tileGrid.getTileSize(z) * this.tilePixelRatio_; }; diff --git a/src/ol/source/wmtssource.js b/src/ol/source/wmtssource.js index 975039994a..5eb8fe3662 100644 --- a/src/ol/source/wmtssource.js +++ b/src/ol/source/wmtssource.js @@ -186,6 +186,7 @@ ol.source.WMTS = function(options) { projection: options.projection, tileGrid: tileGrid, tileLoadFunction: options.tileLoadFunction, + tilePixelRatio: options.tilePixelRatio, tileUrlFunction: tileUrlFunction });