arcgis三维球中加载2000坐标系出现错误(The tiling scheme of this layer is not supported by SceneView)

      目前我们国家测绘地理信息的坐标体系基准是国家2000坐标系CGCS2000.各类地图组件如OpenLayers、Mapbox、Cesuim和ArcGIS Javascrip等都主要是支持WGS84(wkid=4326)和墨卡托投影坐标系(wkid=102100)两种,对CGCS2000坐标系基本上都不支持。特别是在三维地球展示中基本上都是以WGS84球面坐标系加载,因为三维球是个球,当然是要加载球面坐标系了。(但我知道以前科澜三维是平面的!)所以三维地球都加载不了国内的2000坐标系,要加载也是通过扩展和定制WebTileLayer类进行特殊处理。

    ArcGIS Javascript Api 4.*系列一直在朝着二三维一体化的方向发展,其开发商ESRI一直专攻GIS领域,而且是全球头部GIS软件平台,特别是随着ArcGIS 10.1后,其软件产品迭代更新的速度极快。三维产品也是其重点发展对象之一。在今年中旬发布的ArcGIS Javascript Api 4.12版本,不仅性能提升,增加了一些牛逼的功能,更重要的是支持CGCS2000坐标系!!!支持CGCS2000坐标系!!!支持CGCS2000坐标系!!!重要的事情说三遍!

     这正是一个喜大普奔的事情,可能是因为ESRI的三维软件开发团队在北京的缘故吧,爱国注意情怀和中国市场总得发挥点作用。但我看到这个信息后,一直想试试,因为我对他支持2000坐标系还是存有疑惑,加载应该没那么容易!咱天朝的标准规范永远是跟着参考国际标准,但必须在上面进行小幅修改,开发人员蛋疼的事情太多了!

 1         
 2         var arcgisUrl = 'http://myserver.net/hserver/rest/services/imageserver2000/MapServer';
 3 
 4         Layer.fromArcGISServerUrl({
 5           url: arcgisUrl
 6          
 7         }).then(function(layer){
 8 
 9             var customBasemap = new Basemap({
10                 baseLayers: [layer],
11                 title: "ArcGIS REST Service",
12                 id: "切片"
13             });
14             
15             var map = new Map({
16                 //basemap: "topo-vector"
17                 basemap:customBasemap
18               });
19 
20             var view = new SceneView({
21                 container: "viewDiv",
22                 map: map,
23                 spatialReference: {
24                     "wkid": 4490,
25                     "latestWkid": 4490
26                 }
27             });
28         });

 

上述代码就是我想用我自己的影像地图作为三维球的底图,满怀期待,但最后还是出现我预料中的事情,没有那么简单!

球出来了,提示“The tiling scheme of this layer is not supported by SceneView”,当时没注意看这个信息,以为是坐标系统还是继续不支持,但官方明明说了支持2000坐标系啊,不能够啊!

 

继续发挥Chrome强大的调试功能,在SceneViewer.js文件中调试出三块关键代码行数,checkIfTileInfoSupportedForViewSR,makeGCSWithTileSize,ompatibleWith。经过调试和研究发现,2000坐标系确实是支持的,但是切片规则(Tiling Scheme)必须跟esri规定的要一样。

 

天地图切片规则

级别

比例尺

分辨率(/像素)

7

4617149.9776692898246525792559     

0.010986328125

8

2308574.9888346449123262896279     

0.0054931640625

9

1154287.494417322456163144814

0.00274658203125

10

577143.74720866122808157240698

0.001373291015625

11

288571.87360433061404078620349

0.0006866455078125

12

144285.93680216530702039310175

0.00034332275390625

13

72142.968401082653510196550873

0.000171661376953125

14

36071.484200541326755098275436

0.0000858306884765625

15

18035.742100270663377549137718

0.00004291534423828125

16

9017.871050135331688774568859

0.000021457672119140625

17

4508.9355250676658443872844296

0.0000107288360595703125

18

2254.4677625338329221936422148

0.00000536441802978515625

19

1127.2338812669164610968211074

0.000002682209014892578125

20

563.61694063345823054841055369

0.0000013411045074462890625

esri脚本代码里第一级分辨率固定了 res[0] = 0.703125,下面以及都是一半的比例尺进行处理。下面是两个切片规则的比较。

                  

        arcgis javascript api 规定的切片规则                                                                                               天地图服务切片规则

 

可以看出我的服务的切片规则和arcgis的恰好错开一个层级,我怀疑是因为我们是从0级开始算,arcgis是从第1级开始算导致的吧。但仔细看看其实两个瓦片规则的分辨率还是有细微的差别的。

 

 

 

q.prototype.compatibleWith = function(a) {
    if (! (a instanceof q)) {
        if (q._checkUnsupported(a)) return ! 1;
        a = new q(a)
    }
    if (!a.spatialReference.equals(this.spatialReference) || a.pixelSize[0] !== this.pixelSize[0] || a.pixelSize[1] !== this.pixelSize[1]) return ! 1;
    var c = Math.min(this.levels.length, a.levels.length) - 1,
    f = this.levels[c].resolution,
    b = .5 * f;
    if (!e.floatEqualAbsolute(a.origin[0], this.origin[0], b) || !e.floatEqualAbsolute(a.origin[1], this.origin[1], b)) return ! 1;
    b = .5 * f / Math.pow(2, c) / Math.max(this.pixelSize[0], this.pixelSize[1]) * 12;
    return e.floatEqualAbsolute(f, a.levels[c].resolution, b)
}

  

问题如何处理呢?我的服务是用的已有的缓存切片进行发布的啊!下一步就是操作ArcGIS Server 的信息了,强制去掉一个层级,让其从第1级开始算瓦片吧,这样我猜应该能加载了吧。

请听下会demo汇报......

posted @ 2019-08-23 17:00  cehui0303  阅读(...)  评论(... 编辑 收藏