OpenLayers 实现网格色斑图:WebGL 叠加层方案

气象、环境类业务里常见一种数据:规则经纬度网格(每个格点一个数值)。要在地图上画成色斑图,还要可选网格线、格点数值、鼠标取值------用 OpenLayers 自己从零写 WebGL 图层成本不低。

我开源了一个小库 grid-webgl-openlayers,思路很简单:不替你创建 Map,只往现有 ol/Map 上叠加图层

示例效果图

js 复制代码
ol/Map<br/>底图 + View + 控件
    └── grid-webgl-openlayers 叠加
        ├── ChoroplethLayer   WebGL 色斑图
        └── GridValueLayer    Canvas2D 格点数值

底图、投影、控件仍由业务方管理;库只负责 addLayer

数据格式

JSON 描述一块矩形网格即可

json 复制代码
{
  "startLat": 26,
  "endLat": 34.45,
  "startLon": 97.25,
  "endLon": 108.65,
  "latStep": 0.05,
  "lonStep": 0.05,
  "latCount": 170,
  "lonCount": 229,
  "ds": [[8.37, 9, 9.72], [7.12, 8.01]]
}
  • ds[row][col]:从南往北、从西往东
  • -9999 表示无数据,不参与渲染和拾取

最小示例

js 复制代码
npm install grid-webgl-openlayers ol
js 复制代码
import Map from "ol/Map"
import View from "ol/View"
import TileLayer from "ol/layer/Tile"
import OSM from "ol/source/OSM"
import { GridMapView } from "grid-webgl-openlayers"
import "ol/ol.css"

const map = new Map({
  target: "map",
  view: new View({ projection: "EPSG:4326", center: [105, 30], zoom: 6 }),
  layers: [new TileLayer({ source: new OSM() })],
})

const overlay = await GridMapView.create({
  map,
  dataUrl: "/data/arrayData.json",
  showChoropleth: true,  // 色斑图
  showGrid: false,         // 网格线
  showLabels: true,        // 格点数值
})

// 鼠标悬停取值
overlay.onPointerMove(({ value, lon, lat }) => {
  if (value != null) console.log(value, lon, lat)
})

几行代码就能在 OSM 底图上叠色斑图。

自定义图例(模式分为色带色块)

支持不规则数值-颜色映射:

js 复制代码
const colorRamp = [
  [-9999, [0, 0, 0, 0]],              // 无数据透明
  [0,     [232, 245, 233, 255]],
  [7.5,   [129, 199, 132, 255]],
  [47.6,  [27, 94, 32, 255]],
  [9999,  [0, 0, 0, 0]],
]

await GridMapView.create({ map, dataUrl, colorRamp })

实现要点

  1. WebGL 色斑:ImageCanvas 自定义图层 + Fragment Shader 按经纬度采样格点值,再查 1D 色带纹理上色。
  2. LOD 降采样:缩放级别低时合并格点,避免百万格点拖慢帧率。
  3. 格点标注:Canvas2D 按像素间距稀疏绘制,避免文字堆叠。
  4. 图例面板:双滑块过滤显示数值区间,setDisplayRange(min, max) 即可。

Vue 3 也有组件:GredGridMapGredLegendPanel

在线预览

小结

若你已有 OpenLayers 地图,只需加载规则网格 JSON,用 GridMapView.create() 叠加 WebGL 色斑图和格点标注,比从零写 Shader 省事很多。欢迎 Star 和 Issue。

相关推荐
灵境(虚幻知音)1 天前
WebGL 不支持>1px的线绘制,那 Cesium 的带宽度的线是怎么画出来的?
webgl·cesium·着色器
云登指纹浏览器2 天前
浏览器指纹检测原理演进:从Canvas到WebGL的4轮风控升级
webgl
前端老爷更车5 天前
从 `renderer.render()` 到地面上的阴影:Three.js 阴影渲染全流程源码解析
webgl
Highcharts.js7 天前
Highcharts 渲染方式解析:SVG 默认渲染与 Boost 模块的 WebGL 加速,以及它与其他可视化库的不同
svg·webgl·可视化·canvas·highcharts·渲染方式
UWA10 天前
GPM 2.0 WebGL 监测能力扩容|覆盖 Unity/Cocos/LayaAir 多引擎微信 & 抖音小游戏
unity·微信·性能优化·小游戏·webgl
像我这样帅的人丶你还10 天前
🚀苹果的液态玻璃咋做?🚀
前端·webgl·three.js
用户831348593069811 天前
Cesium实现动态流动火烧云晚霞效果(可用slider调整火烧云浓度)
vue.js·webgl·cesium
IT爱学堂11 天前
Three.js可视化企业实战WEBGL课,2023年全新WEB 3D THREEJS技术
前端·javascript·webgl
智商偏低12 天前
attribute 与 uniform 本质区别(WebGL)
webgl
进哥AI研习社13 天前
WebGL 与视频背景——首屏视觉层的性能博弈
性能优化·webgl·gpu·canvas·shader·帧率·视频背景