Skip to content

Image Tiles

Overview

MapServer can serve out image tiles using Tile Mode. This example uses a countries dataset from Natural Earth.

Tiles will always be in the Web Mercator (EPSG:3857) projection, and can easily be added to client JavaScript applications such as OpenLayers and Leaflet. Tiles are also easy to cache using software such as MapCache.

Mapfile Notes

There are no specific changes required to allow Mapfile layers to be accessed using Tile Mode. However there are some METADATA settings that can be used to configure tile mode. See tile mode configuration in the docs.

WEB
    METADATA
        "tile_map_edge_buffer" "10"
        "tile_metatile_level" "0"
    END
END

Tip

It is good practice to always set a PROJECTION block on the LAYER - even if it is in the same projection as the MAP.

Requesting Tiles in OpenLayers

A TileLayer is simple to add to an OpenLayers map. We simply provide a template URL as the XYZ source, and add &MODE=tile:

new TileLayer({
    source: new XYZ({
        url: mapserverUrl + mapfilesPath + 'tiles.map&MODE=tile&TILE={x}+{y}+{z}&LAYERS=countries',
    }),
}),

Code

tiles.js
import '../css/style.css';
import Map from 'ol/Map.js';
import TileLayer from 'ol/layer/Tile.js';
import View from 'ol/View.js';
import XYZ from 'ol/source/XYZ.js';

const mapserverUrl = import.meta.env.VITE_MAPSERVER_BASE_URL;
const mapfilesPath = import.meta.env.VITE_MAPFILES_PATH;

const map = new Map({
    target: 'map',
    layers: [
        new TileLayer({
            source: new XYZ({
                url: mapserverUrl + mapfilesPath + 'tiles.map&MODE=tile&TILE={x}+{y}+{z}&LAYERS=countries',
            }),
        }),
    ],
    view: new View({
        center: [-472202, 7530279],
        zoom: 3,
    }),
});
tiles.map
MAP
    NAME "Tiles"
    EXTENT -180 -90 180 90
    SIZE 400 400 #
    PROJECTION
        "init=epsg:4326"
    END
    WEB
        METADATA
            "tile_map_edge_buffer" "10"
            "tile_metatile_level" "0"
        END
    END
    IMAGECOLOR "#ADD8E6"
    LAYER
        NAME "countries"
        TYPE POLYGON

        STATUS OFF
        CONNECTIONTYPE OGR
        CONNECTION "data/naturalearth"
        DATA "ne_110m_admin_0_countries"
        EXTENT -180.0 -90.0 180.0 90
        CLASS
            STYLE
                COLOR 60 179 113
                OUTLINECOLOR 255 255 255
                OUTLINEWIDTH 0.1
            END
            #LABEL
            #    TEXT "[name]"
            #END
        END
    END
END

Exercises

  1. Change the background colour of the MAP and tiles by modifying the IMAGECOLOR "#ADD8E6" setting. #ADD8E6 is "LightBlue".
  2. Uncomment the LABEL block in the Mapfile to add labels to the tiles. You will notice that the country names are repeated several times, as they are shown for each tile. Try setting the tile_metatile_level value to "1" and then "2". This will reduce label repetition, but take longer to render.

    METADATA
        "tile_map_edge_buffer" "10"
        "tile_metatile_level" "0"
    END
    

Possible Errors

  • "mapserv(): Web application error. No way to generate map extent. "
    

    Resolution: ensure the parameter order in the JS client is in the format &TILE={x}+{y}+{z}&LAYERS. Other tile services often use the zoom level as the first parameter, for example {z}/{x}/{y}.