基于 ArcGIS Maps SDK for JavaScript 如何对接 WMS / WMTS 服务?

641 阅读5分钟

前言

为了应对波诡云谲的国际形势,国家大力推进信创平台建设,国内各大地理信息软件开发企业的国产化服务数据已经趋于多元化。对于使用以ArcGIS Maps SDK for JavaScript为地图框架的项目,将不得不对其进行国产化的数据兼容加载。
最近在做第三方系统地图服务数据对接中,就遇到了要兼容超图众智宏图等厂商提供的WMS服务 / WMTS服务。以下就对于这些国产化数据平台服务的对接进行总结归纳。

ArcGIS Enterprise 支持 OGC

开放地理空间联盟 (OGC) Web 服务使地图和数据以国际公认的开放格式在 Web 上可用。 OGC 用于定义相关规范,可使具有受支持客户端应用程序的任何人均可在 Web 上使用地图和数据,无论该应用程序是基于 Web(例如,位于 ArcGIS Enterprise 门户的 Map Viewer 中)还是富桌面客户端(例如 ArcGIS Pro)。

OGC 用于定义多种服务类型,分别用于提供不同类型的数据和地图。 ArcGIS Enterprise 支持以下 OGC 服务类型:

  • Web 地图服务 (WMS),用于以地图图像的方式提供一组图层
  • Web 地图切片服务 (WMTS),用于以缓存地图切片的形式提供地图图层
  • Web 要素服务 (WFS),用于以矢量要素的形式提供数据
  • 网络覆盖服务 (WCS),用于以栅格 coverage 的形式提供数据(不要与 ESRI 的 ArcInfo coverage 格式相混淆)
  • 网络处理服务 (WPS),用于提供地理空间处理功能

具体的内容可以参考ArcGIS官网提供的 ArcGIS Enterprise 支持 OGC

超图

超图是一款专业的GIS软件,提供多种数据格式和服务类型,包括WMS和WMTS服务。
它具有强大的数据处理和分析能力,可以用于城市规划、土地利用、资源管理等领域。
在arcgis api中,可以通过使用WMSLayer和WMTSLayer类来加载超图的WMS和WMTS服务。

html文件

通用的前端html页面,下同。

<html lang="en">
  <head>
    <meta charset="utf-8" />
    <meta name="viewport" content="initial-scale=1,maximum-scale=1,user-scalable=no" />
    <title>WMTSLayer | WMTSLayer | ArcGIS Maps SDK for JavaScript 4.26</title>
    <link rel="stylesheet" href="https://js.arcgis.com/4.26/esri/themes/light/main.css" />
    <style>
      html,
      body,
      #viewDiv {
        padding: 0;
        margin: 0;
        height: 100%;
        width: 100%;
      }
      .esri-layer-list {
        width: 310px;
      }
    </style>
    <script src="https://js.arcgis.com/4.26/"></script>
    <script src="./index.js"></script>
  </head>
  <body>
    <div id="viewDiv"></div>
  </body>
</html>

示例地址

WMSLayer加载

完整代码

下面为index.js文件的完整代码,自此之后展示的代码为关键代码,可以以此做参考。

require([
  "esri/Map",
  "esri/views/MapView",
  "esri/layers/WMTSLayer"
], (Map, MapView, WMTSLayer) => {
  const layer = new WMSLayer({
    url: "https://iserver.supermap.io/iserver/services/maps/wms130",
    sublayers: [
      {
        name: "长春市区图"
      }
    ]
  });

  const map = new Map({
    layers: [layer],
  });
  view = new SceneView({
    container: "viewDiv",
    map: map,
  });
  view.when(function () {
    view.extent = layer.fullExtent;
    var layerList = new LayerList({
      view: view,
    });
    view.ui.add(layerList, "bottom-left");
  });
});
加载效果

image.png

WMTSLayer加载

示例地址: iserver.supermap.io/iserver/ser…

const layer = new WMTSLayer({
  url: "https://iserver.supermap.io/iserver/services/map-china400/wmts-china",
  activeLayer: { id: "China", tileMatrixSetId: "ChinaPublicServices_China" },
});
加载效果

image.png

航天宏图

该说不说,航天宏图、众智软件的国产化服务,我还是第一次见🤣

WMSLayer加载

image.png

关键代码
// 保密需要,ip和port根据需求加载
const layer = new WMSLayer({
  id: `wms-dltb4528`,
  title: 'dltb4528',
  url: `http://${ip}:${port}/mapserver/layer/WMS/1.1.1/dltb4528/dltb4528/getCapabilities`,
  version: '1.1.0',
  sublayers: [
      {
        title: 'dltb4528',
        name: 'dltb4528'
      }
  ],
  imageFormat: 'image/png',
  spatialReference: { wkid: 4528 }
});
加载效果

1679394806909.png

注意

航天宏图发布的WMS服务是完全遵循OGC规范的,但是 ArcGIS Maps SDK for JavaScriptWMSLayer服务比较特殊,在1.3.0版本时,四至范围bboxwkid有关系,wkid在落在如下图一所示的范围时,四至范围bbox会发生改变(如下图二)。

图一:

image.png 图二:

image.png 降版本前:

image.png 降版本后:

image.png

WMTSLayer加载

符合底图的切片方案加载
const layer = new WMTSLayer({
  id: `wmts-测试投影坐标系`,
  title: "测试投影坐标系",
  url: "http://${ip}:${port}/mapserver/layer/WMTS/1.0/测试投影坐标系/测试/getCapabilities",
  version: "1.1.0",
  sublayers: [
    {
      title: "测试投影坐标系",
      name: "测试投影坐标系",
    },
  ],
  spatialReference: { wkid: 4326 },
});
特殊切片方案加载

特殊的方案加载可以利用ArcGIS Maps SDK for JavaScriptwebTileLayer类来定义切片方案。

image.png

// 1. 先从xml文件获取到切片方案数据信息
// 2. 设置切片方案相关信息
const tileInfo = new TileInfo({
  dpi: 96,
  rows: 256,
  cols: 256,
  format: "format/png",
  compressionQuality: 0,
  origin: {
    x: -180,
    y: 90,
  },
  spatialReference: {
    wkid: 4326,
  },
  lods: [
    { level: 1, resolution: 0.703125, scale: 279541132.01425016 },
    { level: 2, resolution: 0.3515625, scale: 139770566.00712565 },
    { level: 3, resolution: 0.17578125, scale: 69885283.00356229 },
    { level: 4, resolution: 0.087890625, scale: 34942641.50178117 },
    { level: 5, resolution: 0.0439453125, scale: 17471320.750890587 },
    { level: 6, resolution: 0.02197265625, scale: 8735660.375445293 },
    { level: 7, resolution: 0.010986328125, scale: 4367830.187722629 },
    { level: 8, resolution: 0.0054931640625, scale: 2183915.093861797 },
    { level: 9, resolution: 0.00274658203125, scale: 1091957.546930427 },
    { level: 10, resolution: 0.001373291015625, scale: 545978.773465685 },
    { level: 11, resolution: 0.0006866455078125, scale: 272989.38673236995 },
    { level: 12, resolution: 0.0003433227539062, scale: 136494.69336618498 },
    { level: 13, resolution: 0.0001716613769531, scale: 68247.34668309249 },
    { level: 14, resolution: 0.0000858306884766, scale: 34123.673341546244 },
    { level: 15, resolution: 0.0000429153442383, scale: 17061.836671245605 },
    { level: 16, resolution: 0.0000214576721191, scale: 8530.918335622784 },
    { level: 17, resolution: 0.0000107288360596, scale: 4265.459167338928 },
    { level: 18, resolution: 0.0000053644180298, scale: 2132.7295841419354 },
    { level: 19, resolution: 0.0000026822090149, scale: 1066.364791598498 },
    { level: 20, resolution: 0.0000013411045074, scale: 533.182395799249 },
    { level: 21, resolution: 0.0000013411045074, scale: 266.5911978996245 },
  ],
});
// 3. 将切片方案赋值给网络切片图层对象
const layer = new WebTileLayer({
  urlTemplate:
    "http://1.119.169.71:10012/mapserver/layer/WMTS/1.0/测试投影坐标系/测试/GetTile/{level}/{row}/{col}.png",
  id: "测试投影坐标系",
  tileInfo,
  spatialReference: { wkid: 4326 },
});
加载效果

image.png

注意

ArcGIS Maps SDK for JavaScriptSceneView模式MapView模式对切片的支持是有区别的,MapView模式可以支持对切片的方案的动态投影矫正,但是SceneView模式并不支持。具体可以看 官方网站 解释。

image.png

众智软件

WMSLayer加载

众智发布的wms服务是兼容ArcGIS Maps SDK for JavaScript加载的,所以ArcGIS Maps SDK for JavaScriptWMSLayer类可以直接加载其wms服务

关键代码
// 保密需要,ip和port根据需求加载
const layer = new WMSLayer({
  id: `wms-dltb`,
  title: 'dltb',
  url: `http://${ip}:${port}/WiseMap/mapagent/mapagent.fcgi?SERVICENAME=dltb&service=wms&request=GetCapabilities`,
  version: '1.1.0',
  sublayers: [
      {
        title: 'dltb',
        name: 'dltb'
      }
  ],
  imageFormat: 'image/png'
});
加载效果

image.png

总结

通过这次数据对接的经历,我对OGC规范有了更深层次的理解。
踩坑了不少,总的来说归纳为:

  • SceneView模式切片方案要注意保持一致。
  • 在加载1.3.0版本的WMS服务时,要注意坐标系的范围,特定的范围会导致四至范围的值变换。

码字不易,希望这次经验对大家有所帮助。

未经本人许可,不得转载本文,谢谢!