Buffering the layer data to improve the map navigation

Map navigation is an important factor to take into account to make the user experience better.

When we pan the map, many times we get to see blank areas (meaning that the content is loading) and after a few seconds the image appears.

On gridded layers and WMS layers working in single tile mode, we can improve this at the cost of increasing the requests number or increasing the computation time at the server side.

Note

Most of the raster layers inherit from the base class OpenLayers.Layer.Grid, which is responsible for dividing each zoom level into tiles.

For WMS layers working in single tile mode, the grid is formed only by one tile, which fills the whole map view.

The idea behind improving map navigation is simple; load the tiles outside the map view so that they are loaded before the user pans the map view in that direction.

This recipe shows you how to preload content outside the map view, both for gridded layers and also for WMS layers working in single tile mode, so that you can improve the navigation experience of the users.

How to do it...

  1. Create an HTML file and include the OpenLayers dependencies.
  2. We are going to create two maps side by side and on top of each one we are going to add a spinner control, from the Dojo Toolkit framework (http://dojotoolkit.org), to control the properties buffer and singleTile values:
    <table style="width: 100%; height: 95%;"> 
        <tr> 
            <td style="width: 50%;"> 
                <p> 
                    WMS layer with <em>buffer</em>: <input id="buffer_a" dojoType="dijit.form.NumberSpinner" onChange="changeBufferA" 
                                                           intermediateChanges="true" style="width:100px" value="0" smallDelta="1" constraints="{min:0,max:5}" /> 
                </p> 
                <div id="ch02_wms_buffer" style="width: 100%; height: 100%;"></div> 
            </td> 
            <td style="width: 50%;"> 
                <p> 
                    WMS using <em>singleTile</em> property and <em>ratio</em>: <input id="buffer_b" dojoType="dijit.form.NumberSpinner" onChange="changeBufferB" 
                                                                                      intermediateChanges="true" style="width:100px" value="1.0" smallDelta="0.1" constraints="{min:0.0,max:2.0}" /> 
                </p> 
                <div id="ch02_wms_ratio" style="width: 100%; height: 100%;"></div> 
            </td> 
        </tr> 
    </table>
  3. The left-hand side panel will show how to control the number of tiles that can be loaded outside the map view:
    <script type="text/javascript"> 
        // Create the map using the specified DOM element 
        var map_a = new OpenLayers.Map("ch02_wms_buffer");    
        
        // Add a WMS layer 
        var wms_a = new OpenLayers.Layer.WMS("Basic", "http://vmap0.tiles.osgeo.org/wms/vmap0", 
        { 
            layers: 'basic' 
        }, 
        { 
            buffer: 0 
        }); 
        map_a.addLayer(wms_a); 
        
        // Set the center of the view 
        map_a.setCenter(new OpenLayers.LonLat(-90,0), 3);
  4. The right-hand side panel shows how to control the amount of data you can preload in a WMS layer working in single tile mode.
        // Create the map using the specified DOM element 
        var map_b = new OpenLayers.Map("ch02_wms_ratio");    
        
        // Add a WMS layer 
        var wms_b = new OpenLayers.Layer.WMS("Basic", "http://vmap0.tiles.osgeo.org/wms/vmap0", 
        { 
            layers: 'basic' 
        }, 
        { 
            singleTile: true, 
            ratio: 1 
        }); 
        map_b.addLayer(wms_b); 
        
        // Set the center of the view 
        map_b.setCenter(new OpenLayers.LonLat(-90,0), 3);
  5. Finally, there is the code responsible for changes on the spinner controls, shown as follows:
        // Handle events 
        function changeBufferA(value) { 
            wms_a.addOptions({buffer: value}); 
        } 
        function changeBufferB(value) { 
            map_b.removeLayer(wms_b); 
            wms_b.destroy(); 
            wms_b = new OpenLayers.Layer.WMS("Basic", "http:// vmap0.tiles.osgeo.org/wms/vmap0", 
            { 
                layers: 'basic' 
            }, 
            { 
                singleTile: true, 
                ratio: value 
            }); 
            map_b.addLayer(wms_b); 
        } 
    </script>
    

How it works...

The left-hand side map contains a WMS layer working in the default tiled mode. In this mode, the buffer property from the base class OpenLayers.Layer.Grid specifies how many tiles must be loaded outside the map view.

When a user changes the spinner value for the buffer property, we simply update it with the following line of code:

    function changeBufferA(value) { 
        wms_a.addOptions({buffer: value}); 
    } 

The right-hand side map, on the other hand, has a WMS layer working in single tile mode (see the singleTile property set to true). In this mode, only one request is made to get an image, which fills the whole map view.

We can control the size of the image with the ratio property, which belongs to the OpenLayers.Layer.WMS class. A ratio of value 1.0 means an image with exact dimensions of the map view. By default the ratio value is 1.5, which means we are requesting an image with the map view dimensions plus a half.

In this case, the ratio value is set once while creating the layer and to update it we need to delete the previous layer and create a new one with the new value. This is done as follows:

    function changeBufferB(value) { 
        map_b.removeLayer(wms_b); 
        wms_b.destroy(); 
        wms_b = new OpenLayers.Layer.WMS("Basic", "http://vmap0.tiles.osgeo.org/wms/vmap0", 
        { 
            layers: 'basic' 
        }, 
        { 
            singleTile: true, 
            ratio: value 
        }); 
        map_b.addLayer(wms_b); 
    } 

Note

We first remove the layer from the map and later invoke the destroy() method to free internal resources used by the layer and avoid memory leaks.

There's more...

Remember, the more tiles we load the more requests to the server. The same goes for a WMS layer in single tile mode; the greater the bounding box you request, the greater the computation time on the server results.

Because of this, increasing the buffer or ratio values too much is not always the best solution.

Think about your data and how the user will explore it. If your data is probably better to explore in its extension—a great area in the same zoom level—then a buffer of one or two can be a good idea. If your data is mainly zoomed but the user is not interested in exploring large areas, then the default values are fine.

See also

  • The Using WMS with single tile mode recipe
  • The Setting the tile size in WMS layers recipe
  • The Adding WMS layer recipe
..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
3.21.248.162