DeckGL MVTLayer+Mapbox注入shader实现简单效果

1.数据获取与处理

可以从OSM下载相应的带高度的矢量建筑物轮廓数据,下载后进行数据处理,保留高度字段,其他字段根据需求选择(比如说想实现选中建筑物弹出相应建筑物的信息,就把这些信息字段保留下来),然后将shp(如果为shp数据)转为GeoJson(注意如果不是说3857投影的先转为3867投影),接着就是进行矢量切片为MVT格式的xyz数据(我看DecKGL好像并不支持mbtiles数据,不过可以使用一个服务端比如node解析mbties数据为xyz给前端调用,那样估计性能会好些),这里推荐使用tippecanoe,性能好而且自定义切片程度高。下面为我这次切片的参数选择:

tippecanoe --no-tile-compression -s EPSG:3857 -ad -an -Z10 -z16 -e gl-3857 -ai gl_3857.geojson

在缩放级别 10-15 时,相对较小的建筑物被稀疏化,矢量切片500K 大小限制以下

  • pC:–no-tile-compression不要压缩 PBF 矢量切片数据(这个DeckGL的issue上有人提我看了,默认压缩了会会出现问题)
  • ador--drop-fraction-as-needed :在每个缩放级别下动态删除部分要素,以将大图块保持在 500K 大小限制以下
  • anor--drop-smallest-as-needed:从每个缩放级别动态删除最小的要素(如最小的多边形),以将大图块保持在 500K 大小限制以下
  • e:将 tiles 写入指定目录而不是 mbtiles 文件
  • ai:如果要素 ID 是数字的字符串表示形式,请将其转换为纯数字以用作要素 ID
  • s:指定投影,默认为3857

这里使用的数据为桂林的建筑物矢量数据,并且将其切片文件放到nginx http服务器上进行调用,当然也有更好的方案,如弄个全国的建筑物数据的话,并且需求更新及时,就可有采用在Postgresql/postgis中动态矢量切片来弄。

2.注入shader添加自定义效果

DeckGL比较有有意思也比较难的便是注入shader代码实现各种自定义效果了,这样一来就可以借鉴网络上(如shadertoy)各种有意思的shader demo来结合实现更多的地理信息可视化效果。

因为MVTLayer为TileLayer的派生类图层,而TileLayer又为CompositeLayer,所以这里就采用Layer Extensions来添加自定义效果,而不是采用Subclassed Layers(不过也可以采用这种方式,会更灵活,可以传递attribute、uniform数据到着色器中使用)

通过查看源码层层查找可以发现,其着色其代码继承的是soilpolygonLayer的,所以只需要去看看其着色器代码中有些上面变量可以使用(觉得难找的话还有一个小技巧可以快速定位到相应的着色器代码,就是先随便注入些东西,然后控制台会报错对于的着色器文件编译错误。。。)

class Custom extends deck.LayerExtension{
    getShaders(){
      return {
        inject: {
          'vs:#decl':`
              varying vec2 vPosition;
          `,
          'vs:#main-end':`
              vPosition = vertexPositions;
          `,
          'fs:#decl': `
              varying vec2 vPosition;
          `,
          //重写颜色绘制函数
          'fs:DECKGL_FILTER_COLOR': `
              color = vec4(color.rgb, color.a * pow(1.0-vPosition.y,2.0));
          `
        }
      }
    }
}

//使用
const mvtLayer = new MapboxLayer({
  id: "gl-building-mtv",
  type: MVTLayer,
  data: `your mvt url /{z}/{x}/{y}.pbf`,
  minZoom: 2,
  maxZoom: 16,
  getFillColor: [17, 179, 68, 150],
  lineWidthMinPixels: 0.5,
  pickable: true,
  extruded: true,
  autoHighlight: true,
  highlightColor: [0, 245, 255, 100],
  getElevation: d => d.properties.Elevation,
  wireframe: false,
  getLineColor: [105, 160, 126, 1],
  // material: {
  //   ambient: 0.1,
  //   diffuse: 0.9,
  //   shininess: 32,
  //   specularColor: [30, 30, 30]
  // },
  extensions: [new Custom()]
});

在这里插入图片描述

在这里插入图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
Vue.js 和 Mapbox 是两个非常流行的工具,用于构建用户界面和提供强大的地图功能。Vue 是一个轻量级的前端框架,以其组件化开发和易于上手的特点受到开发者喜爱。Mapbox 则是一个提供了丰富的地图服务、地图样式和交互功能的平台。 当你将 Vue 与 Mapbox 结合使用时,可以实现以下几个关键点: 1. 安装依赖:首先,你需要在 Vue 项目中安装 `@vuegis/vue-mapbox-gl` 或者直接使用 Mapbox GL JS(原生库),这是官方推荐的 Vue 组件化解决方案。 2. 创建地图组件:创建一个 Vue 组件,例如 `Map.vue`,引入 Mapbox GL JS,并设置初始化地图的方法,包括设置中心位置、比例尺、地图样式等。 ```html <template> <div ref="map"></div> </template> <script> import { mapboxgl, Map } from '@vuegis/vue-mapbox-gl' export default { components: { MapboxGL: mapboxgl.Map, }, mounted() { this.createMap() }, methods: { createMap() { this.$refs.map .el .style = 'width: 100%; height: 400px;'; // 设置样式 const map = new Map(this.$refs.map, { center: [51.505, -0.09], // 地图中心点 zoom: 13, // 初始缩放级别 style: 'mapbox://styles/mapbox/streets-v11', // 使用预设样式 }); }, }, } </script> ``` 3. 动态数据绑定:Vue 的响应式系统使得地图可以根据数据变化动态调整,比如根据用户的输入改变地图视图或添加标记。 4. 图层和交互:Mapbox 提供了各种图层(如矢量图层、影像图层等)和交互元素(如点击事件、鼠标悬停事件),可以在 Vue 中轻松使用。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

seeooco

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值