Search code examples
openlayers

Requesting and caching WMTS/ tiled WMS tiles outside of the current viewport in Openlayers


I'm working on an application that needs to request multiple WMTS/ tiled WMS layers simultaneously. I understand that this will always incur performance overheads, but the ability to do this is core to the functionality of the application. I'm looking at ways of improving performance, and a method I would like to try is to pre-load and cache tiles outside the current viewport extent. My thinking is that the application can use time in which the user is stationary to prepare the surrounding tiles, which can be rendered from a cache when the map is moved.

Openlayers appears to do this by default for WMTS and tiled WMS layers to a minor degree, but I would like to control the extent to which this occurs. I understand that for WMS layers the ratio and buffer parameters can be used to manipulate the size of the BBOX used to request WMS layers, but have been unable to locate any information on parameters that allow this to occur for WMTS/ tiled WMS layers. Does this functionality exist out of the box in Openlayers? If not, is it be possible to supply a custom tile indices (i.e dervied from the viewport + a buffer) to the request, or would this require something completely custom to make requests? Thanks.


Solution

  • You could use a bigger viewport, but hide the overflow and reposition the controls so it appears the required size. It would affect how operations such as fit() work.

    <!doctype html>
    <html lang="en">
    
    <head>
      <link rel="stylesheet" href="https://cdn.rawgit.com/openlayers/openlayers.github.io/master/en/v5.3.0/css/ol.css" type="text/css">
      <style>
        html, body {
            margin: 0;
            padding: 0;
            width: 100%;
            height: 100%;
            overflow: hidden;
        }
        .map {
            position: absolute;
            width: 200%;
            height: 200%;
            left: -50%;
            top: -50%;
        }
        .map div.ol-zoom {
            left: calc(25% + .5em);
            top: calc(25% + .5em);
        }
        .map div.ol-attribution {
            right: calc(25% + .5em);
            bottom: calc(25% + .5em);
        }
        .map div.ol-rotate {
            right: calc(25% + .5em);
            top: calc(25% + .5em);
        }
      </style>
      <script src="https://cdn.rawgit.com/openlayers/openlayers.github.io/master/en/v5.3.0/build/ol.js"></script>
      <title>OpenLayers View on View example</title>
    </head>
    
    <body>
      <div id="map" class="map"></div>
      <script type="text/javascript">
    
        var source = new ol.source.OSM();
    
        var map = new ol.Map({
            target: 'map',
            layers: [new ol.layer.Tile({ source: source })],
            view: new ol.View({
                center: ol.proj.fromLonLat([2.3442, 48.8635]),
                zoom: 10
            })
        });
    
      </script>
    </body>
    
    </html>