首页 / 浏览问题 / 三维GIS / 问题详情
geojson格式的问题导致使用GeoJsonDataSource加载不出面
14EXP 2023年10月19日

使用产品:超图cesium

操作系统:win10

问题详细描述:我的问题是使用new Cesium.GeoJsonDataSource.load加载行政区划,绘制的面部分出不来。 我目前推测是数据结构的问题,我的数据是

geometry:{
  coordinates:[
   [[数据1],[数据2],[数据3]]
  ]
}

正常来说其中数据1和数据2是面,数据3是孔。 我推测cesium渲染时只拿数据1当作面,其余都当作孔来渲染了。有没有什么办法可以避免这样的问题

2 个回答

您好,
这里值得注意的是:GeoJSON中有一个重要的字段 "type" , 它决定了您的 数据1 数据2 会被当成岛还是洞来进行绘制。特别注意 "Polygon","MultiPolygon"。
这里不能看到您 数据1,数据2,数据3 的内容,无法为您判断数据情况,所以给您以下建议:

1.您可参考https://zhuanlan.zhihu.com/p/539689986 或 https://datatracker.ietf.org/doc/html/rfc7946#section-3.1.6 检查您的GeoJSON数据,(同时注意坐标系

crs)。

2.若您的数据不涉及保密,您可将数据私信给我,我为您进一步查找原因。

3.避免手工编辑GeoJSON数据,使用工具生成GeoJSON。您可将原始数据导入iDesktopX桌面软件,再将数据导出为GeoJSON格式文件。

希望对您有所帮助。

365EXP 2023年10月19日
其实"正常来说"(GeoJSON的协议规则),若您的贴出的geometry类型为 "Polygon", 数据1 会被当初面,其余都会被当成孔来进行绘制。

若您的”数据2“再数据意义上是面,那么可以理解为您的数据错误。可以编写一些JavaScript的代码将 ”数据2“从数据组中提出,放入 "Polygon"的模板,再追加到GeoJSON中
365EXP 2023年10月19日

您说的没错,数据1会被渲染成面,其余的都会被当成孔来进行绘制。其中

coordinates[0]中有5个面数据,其中每一项可能是面可能是孔。通过后端检查正确情况应该是第一第二个是面,其余是孔。问题是我怎么区分是面还是孔

您好,

1. 根据您的数据显示,geometry类型为 MultiPolygon 那么按照"单纯"的GeoJSON协议规则,coordinates[0]将会是一个Polygon对象,即一个面对象,coordinates[0][0]是这个面对象的外环(exterior ring),coordinates[0][1]至 coordinate[0][4] 是这个面对象的内环(interior ring)。外环绘制出来是面,内环绘制出来是孔。

2. 那么结合您的描述:

”coordinates[0]中有5个面数据,其中每一项可能是面可能是孔。通过后端检查正确情况应该是第一第二个是面,其余是孔“。 可以视为后端生成数据时未按照GeoJSON的标准规则。

Cesium或支持GeoJSON的程序将按照协议标准,去识别并使用GeoJSON数据。在标准协议下是用顺序规则区分是面还是孔: 第一个是面,第二个及后面剩余的为孔。在GeoJSON中没有其它数据标识面与孔

3. 以上两点的 GeoJSON原理及您数据情况的分析, 有两个建议给到您,

     a. 从后端根源处解决问题,生成正确的GeoJSON,第一个就是面,其余就是孔,然后您再用Cesium加载

     b.无法改动后端的话,根据您的描述,编写一段代码处理数据:

           第一步:遍历coordinates中每个元素 将 coordinates[i][1]~coordinates[i][coordinates[i].length-1]深拷贝一份 放到一个集合copyCoordinates中

           第二步:将copyCoordinates的元素追加到coordinates

           第三步:用cesium加载geojson 看效果

           但真心的,是数据生成步骤的问题,不是使用时候的问题,以上代码处理后可能还会带来更多的渲染错误情况。


                 

感谢您的解答

我有两点问题不太理解,第一点是您提到这个数据可能不是一个标准的GeoJSON协议规则,我在openlayers中使用new ol.format.GeoJSON().readFeatures(json)加载相同的数据最后结果是没问题的,是不是可以往这方面研究一下openlayers是怎么处理的?

第二点是您提到拷贝出一份copyCoordinates这个集合追加到coordinates,比如有个数据结构是

geometry:{
 coordinates:[[[面],[孔],[孔]],[[面],[孔],[孔]]]
 type: "MultiPolygon"
}

从正常数据角度来说有两个面,两个面中分别有两个孔。

经过您说的处理流程,会不会导致从coordinates[i][1]开始截取把两个孔截取出来了,第一个孔会不会被渲染成面?

最后我推测是不是可以把数据处理成这样

geometry:{
 coordinates:[[[面,面,孔]]]
 type: "MultiPolygon"
}

您好,
请私信我您的远程桌面方式,我帮您远程看一下

GeoJSON标准协议 认为 第一个是用来绘制面,剩余用来绘制孔。 

而我理解您提到的"[面,面,孔]"是您需要数据在业务上的意义需要 第二个数据也画成面。

您看到openlayer显示正常,获取是数据的特殊性 绘制出来后 不能识别,您可以将样式设置边框样式,填充色来一点些透明度再观察数据。

实在不好意思,公司电脑不允许安装远程工具。您邮箱发我一份,我写个demo发您邮箱
zhouyingping@supermap.com
已发送您邮箱
您好,您的数据已收到,开始为您分析中。
使用webstorm右键可以运行,直接双击html好像不行
您好,经过对您数据与代码的分析,为达到您需要的显示效果,请注意以下几点(已通过电子邮件同步发送给您,请查收)

1. GeoJSON 数据错误,存在多余的中括号,请修复数据。

2. 为达到您的显示效果,请添加以下代码关闭深度检测

   viewer.scene.globe.depthTestAgainstTerrain = false;

3.同时 需要移除GeoJsonDataSource.load(json, {})方法中的 clampToGround: true

希望对您有所帮助
感谢解答!
...