瓦片模式

作者

保罗·拉姆齐

联系

加利福尼亚州克利夫雷普潘的普拉姆西

作者

杰夫麦克纳

联系

jmckenna在gatewaygeomatics.com

最后更新

2021-05-17

介绍

MapServer可以使用CGI的“tile模式”直接为基于tile的地图客户端提供数据。基于图块的地图客户端通过将世界地图分为若干个不连续的缩放级别来工作,每个级别分为若干大小相同的“图块”。而不是通过请求边界框来访问地图,图块客户端通过访问单个图块来构建地图。

配置

“mapserv”cgi程序处理tile请求。为了在正确的投影中返回图块,必须在打开--use proj选项的情况下构建mapserver。通过使用“-v”选项运行它并查找“supports=proj”,可以检查您的“mapserv”版本是否具有投影支持。

例1。在UNIX上::

$ ./mapserv -v
MapServer version 7.7-dev OUTPUT=PNG OUTPUT=JPEG OUTPUT=KML SUPPORTS=PROJ
SUPPORTS=AGG SUPPORTS=FREETYPE SUPPORTS=CAIRO SUPPORTS=SVG_SYMBOLS
SUPPORTS=RSVG SUPPORTS=ICONV SUPPORTS=FRIBIDI SUPPORTS=WMS_SERVER
SUPPORTS=WMS_CLIENT SUPPORTS=WFS_SERVER SUPPORTS=WFS_CLIENT SUPPORTS=WCS_SERVER
SUPPORTS=SOS_SERVER SUPPORTS=GEOS SUPPORTS=POINT_Z_M SUPPORTS=PBF INPUT=JPEG
INPUT=POSTGIS INPUT=OGR INPUT=GDAL INPUT=SHAPEFILE

例2。在Windows上::

C:\ms4w> mapserv -v
MapServer version 7.7.0-dev (MS4W 4.0.4) OUTPUT=PNG OUTPUT=JPEG OUTPUT=KML
SUPPORTS=PROJ SUPPORTS=AGG SUPPORTS=FREETYPE SUPPORTS=CAIRO SUPPORTS=SVG_SYMBOLS
SUPPORTS=SVGCAIRO SUPPORTS=ICONV SUPPORTS=FRIBIDI SUPPORTS=WMS_SERVER
SUPPORTS=WMS_CLIENT SUPPORTS=WFS_SERVER SUPPORTS=WFS_CLIENT SUPPORTS=WCS_SERVER
SUPPORTS=SOS_SERVER SUPPORTS=FASTCGI SUPPORTS=THREADS SUPPORTS=GEOS
SUPPORTS=POINT_Z_M SUPPORTS=PBF INPUT=JPEG INPUT=POSTGIS INPUT=OGR
INPUT=GDAL INPUT=SHAPEFILE

MapServer要求.map文件(或“mapfile”)中的每个层都具有有效的投影块以支持重新投影。由于平铺模式使用重新投影,因此必须确保每个层都有有效的投影块。

备注

The MAP-level projection in the mapfile is not required for mode=tile as the output projection will always be set to the Google Mercator projection EPSG:3857 and its extents, for mode=tile (in other words, the Google Mercator projection is hard-coded in the underlying MapServer source code, always for the mode=tile case). If your mapfile is also serving through an OGC service, such as WMS, your MAP-level projection will obviously be required for the OGC service, but can be any supported EPSG projection (does not have to be 3857).

配置检查表:

  • 使用项目支持编译的MapServer

  • 带有 PROJECTION 为每一项定义 LAYER

从MapServer 6.0开始,有两个额外的参数可用于配置平铺模式,它们可以设置为 Mapfile 的Web对象中的元数据:

  • tile_map_edge_buffer 将瓷砖渲染到缓冲的渲染帧中,然后剪裁出最终的瓷砖。这将减少绘制大符号或宽线时的边缘效果。推荐值:映射文件中最大符号或线宽的大小。

  • tile_metatile_level

如果两者都使用 tile_map_edge_buffertile_metatile_level 同时,缓冲区将在meta-tile级别应用。

MAP
  ..
  WEB
    METADATA
      "tile_map_edge_buffer" "10"
      "tile_metatile_level" "0"
    END #metadata
  END #web

小技巧

从MapServer8.0开始, tile_map_edge_buffer 通过添加供应商特定的参数,还可以在WMS GetMap请求中使用元数据 TILED=TRUE 您的GetMap请求。

备注

MapServer 7.6.2版本包含一个内存泄漏修复程序,用于 mode=tile

利用

mapserver tile支持为CGI接口添加了三个新指令:

  • mode=tile

  • tilemode=gmap 告知服务器对切片使用Google Maps切片方案(这是默认的切片模式)

    • tile=x+y+z使用google maps tile寻址系统告诉服务器要检索什么tile

  • tilemode=ve 告知服务器对切片使用Bing地图(以前称为“虚拟地球”)切片命名方案

    • Tile=10231使用Bing地图(以前称为“虚拟地球”)切片寻址系统告诉服务器您要检索的切片

可选的TILESIZE=Width+Height查询参数(在MapServer 8.0中添加)可用于覆盖256x256像素的默认平铺大小,通常是为了获得高DPI平铺。

因此,有效的MODE=TILL请求可能如下所示:

http://127.0.0.1/cgi-bin/mapserv.exe?
    MAP=/ms4w/apps/local-demo/local.map
    &MODE=tile
    &TILEMODE=gmap
    &TILE=0+0+0
    &LAYERS=countries

这会产生256x256的平铺(请注意,它位于Google墨卡托投影中,即使 Mapfile 的输出投影对象为 "init=epsg:4326" ):

../_images/tilemode-gmap.png

关于球形墨卡托

Spherical Mercator (也称为“网络墨卡托”或“谷歌墨卡托”)是世界上所有主要的基于切片的地图界面(谷歌地图、必应地图)的投影 [前身为“虚拟地球”] ,Yahoo Maps,OpenLayers)用来寻址磁贴。相关的官方EPSG代码为 EPSG:3857

球形墨卡托瓷砖集具有以下特性:

  • 利用球面墨卡托算法将地图重新投影到墨卡托。

  • 在顶部缩放级别中有一个图块,缩放级别为零

  • 每个连续缩放级别(Z)沿每个轴具有2^Z平铺

  • 瓷砖尺寸为256x256

谷歌地图和必应地图(以前的“虚拟地球”)都使用球面墨卡托作为底层的瓦片投影,但使用不同的格式来处理单独的瓦片。

谷歌地图使用“x”、“y”、“zoom”格式。缩放指示要从哪个级别拖动瓷砖,“X”和“Y”指示要从哪个缩放级别拖动瓷砖。

必应地图(以前的“虚拟地球”)使用一个单独的字符串来定位每个瓷砖。必应地图的顶级缩放级别有四个磁贴(相当于谷歌的缩放级别1)。必应地图顶部缩放级别中的左上角瓦片被定位为“0”,右上角被定位为“1”,左下角被定位为“2”,右下角被定位为“3”。通过首先引用包含该区块的顶层区块,然后参考其相对于该区块的地址来寻址下一级别的每个区块。因此,在第二个变焦级别中,左上角的瓷砖是“00”,右下角的是“33”。有关更多详细信息,请访问必应地图网站:http://msdn.microsoft.com/en-us/library/bb545006.aspx

使用谷歌地图

这个 Google Maps API 包括支持将可选瓷砖集用作套印格式或备用基础地图。下面是一个例子 GTileLayerOverlay

 1<!DOCTYPE html
 2  PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
 3  "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
 4<html xmlns="http://www.w3.org/1999/xhtml">
 5<head>
 6<meta http-equiv="content-type" content="text/html; charset=utf-8"/>
 7<title>Google/MapServer Tile Example</title>
 8<script src="http://maps.google.com/maps?file=api&v=2&key=[YOUR KEY HERE]"
 9        type="text/javascript"></script>
10<script type="text/javascript">
11
12function load() {
13  if (GBrowserIsCompatible()) {
14    var urlTemplate = 'http://localhost/cgi-bin/mapserv?';
15        urlTemplate += 'map=/var/map.map&';
16        urlTemplate += 'layers=layer1 layer2&';
17        urlTemplate += 'mode=tile&';
18        urlTemplate += 'tilemode=gmap&';
19        urlTemplate += 'tile={X}+{Y}+{Z}';
20    var myLayer = new GTileLayer(null,0,18,{
21                                 tileUrlTemplate:urlTemplate,
22                                 isPng:true,
23                                 opacity:1.0 });
24    var map = new GMap2(document.getElementById("map"));
25    map.addControl(new GLargeMapControl());
26    map.addControl(new GMapTypeControl());
27    map.setCenter(new GLatLng(35.35, -80.55), 15);
28    map.addOverlay(new GTileLayerOverlay(myLayer));
29  }
30}
31
32</script>
33</head>
34<body onload="load()" onunload="GUnload()">
35  <div id="map" style="width: 500px; height: 500px"></div>
36</body>
37</html>

请注意tileurltemplate的格式:一个有效的URL,带有x、y和z替换标记,Google地图将替换为平铺坐标和动态缩放级别,以便从您的服务器检索平铺。

您还可以将MapServer平铺层用作备用基础映射:

 1<!DOCTYPE html
 2  PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
 3  "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
 4<html xmlns="http://www.w3.org/1999/xhtml">
 5<head>
 6<meta http-equiv="content-type" content="text/html; charset=utf-8"/>
 7<title>Google/MapServer Tile Example</title>
 8<script src="http://maps.google.com/maps?file=api&v=2&key=[YOUR KEY HERE]"
 9        type="text/javascript"></script>
10<script type="text/javascript">
11
12function load() {
13  if (GBrowserIsCompatible()) {
14    var urlTemplate = 'http://localhost/cgi-bin/mapserv?';
15        urlTemplate += 'map=/var/map.map&';
16        urlTemplate += 'layers=layer1 layer2&';
17        urlTemplate += 'mode=tile&';
18        urlTemplate += 'tilemode=gmap&';
19        urlTemplate += 'tile={X}+{Y}+{Z}';
20    var myLayer = new GTileLayer(null,0,18,{
21                                 tileUrlTemplate:urlTemplate,
22                                 isPng:true,
23                                 opacity:0.3 });
24    var map = new GMap2(document.getElementById("map"));
25    map.addControl(new GLargeMapControl());
26    map.addControl(new GMapTypeControl());
27    map.setCenter(new GLatLng(35.35, -80.55), 15);
28    var myMapType = new GMapType([myLayer], new GMercatorProjection(18), 'MapServer');
29    map.addMapType(myMapType);
30  }
31}
32
33</script>
34</head>
35<body onload="load()" onunload="GUnload()">
36  <div id="map" style="width: 500px; height: 500px"></div>
37</body>
38</html>

与上一个示例相比,唯一的变化是我们不创建gtilelayerOverlay,而是创建一个gmapype,并使用addmapType(),而不是addOverlay()。

使用必应地图(以前称为“虚拟地球”)

这个 Bing Maps API 还包括支持将替代平铺集用作覆盖或替代底图。下面是一个例子:

 1<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
 2<html xmlns="http://www.w3.org/1999/xhtml">
 3<head>
 4  <meta http-equiv="content-type" content="text/html; charset=utf-8"/>
 5  <title>Virtual Earth Example</title>
 6  <script type="text/javascript" src="http://dev.virtualearth.net/mapcontrol/mapcontrol.ashx?v=6.1"></script>
 7  <script type="text/javascript">
 8
 9    var map = null;
10
11    function OnLoadMap () {
12      map = new VEMap("myMap");
13      map.LoadMap();
14
15      var url = "http://localhost/cgi-bin/mapserv?";
16      url += "map=/var/map.map&";
17      url += "mode=tile&";
18      url += "layers=layer1 layer2&";
19      url += "tilemode=ve&";
20      url += "tile=%4";
21
22      var tileSourceSpec = new VETileSourceSpecification( "myLayer", url );
23      tileSourceSpec.Opacity = 0.3;
24      map.AddTileLayer(tileSourceSpec, true);
25    }
26
27  </script>
28</head>
29<body onload="OnLoadMap();">
30  <div id="myMap" style="position:relative; width:500px; height:500px;"></div>
31</body>
32</html>