Threebox地形与天空层实现:如何打造沉浸式3D地图体验完整指南
【免费下载链接】threeboxA Three.js plugin for Mapbox GL JS, with support for animations and advanced 3D rendering.项目地址: https://gitcode.com/gh_mirrors/thr/threebox
Threebox 是一个面向 Mapbox GL JS 的 Three.js 插件,内置**地形层(terrain)、大气天空层(sky)与真实日照(realSunlight)**三大能力,只需几个配置开关,就能让 2D 地图瞬间变成可交互的沉浸式 3D 地图。本文将从零讲起,带你快速理解地形与天空层的实现原理、同步机制和实战示例,轻松做出"日出日落都会变"的立体地图。
什么是 Threebox?3D 地图插件一句话介绍
Threebox 的核心价值在于让 Three.js 的 3D 场景与 Mapbox 2D 地图共用同一个相机和坐标系,你不需要手动同步相机位置、处理投影变换,插件会自动完成这些脏活累活。
除了加载 3D 模型、射线拾取、拖拽旋转等常见能力外,这个 fork 版本还独家支持:
- 🌄地形层:自动接入 Mapbox DEM 高程数据,生成起伏地形;
- ☀️天空层:大气散射天空盒,随太阳位置实时变化;
- 💡真实日照:按"任意日期 + 经纬度"计算太阳方位,让光照、天空、地形三者保持同步。
三个核心开关:realSunlight、sky、terrain
在创建 Threebox 实例时,通过三个布尔参数即可开启整套沉浸式 3D 体验:
const tb = new Threebox(map, map.getCanvas().getContext('webgl'), { realSunlight: true, // 按日期时间计算真实太阳光照 sky: true, // 开启大气天空层,与日照同步 terrain: true // 开启地形层,模型自动贴合地形高度 });1️⃣ terrain:地形层——让地图"立"起来
开启后,Threebox 会自动完成三件事(源码见 src/Threebox.js 中的createTerrainLayer):
- 添加名为
mapbox-dem的raster-dem高程数据源; - 调用
map.setTerrain()应用地形,默认exaggeration: 1.0(可通过terrainExaggeration属性放大起伏效果); - 场景中的 3D 模型会自动适配地形高度,比如一座雪山上的冰川模型,会稳稳落在山体上而不是浮在半空。
2️⃣ sky:天空层——自带大气散射的天空盒
开启后调用createSkyLayer()创建 id 为sky-layer的天空图层,并写入sky-atmosphere-sun属性。这个属性的值不是写死的颜色,而是由当前日期和地图中心点计算出的太阳高度角与方位角——正午天空湛蓝,清晨呈现暖橙色的低角度光感,效果非常接近真实大气散射。
3️⃣ realSunlight:一切同步的"心脏"
这是整个沉浸式体验的关键。它基于项目内置的天文计算库 src/utils/suncalc.js(SunCalc 算法),根据你给定的Date与经纬度,精确算出太阳的赤纬、方位角、高度角,然后:
- 把平行光(场景主光源)摆到太阳的实际位置;
- 同步更新天空层的
sky-atmosphere-sun; - 并根据太阳高度自动调整地形瓦片的
raster-opacity(夜晚自动压暗,最低保留 0.25)。
一句话:realSunlight 是"大脑",sky 和 terrain 是"执行者",三者一开就是完整的沉浸式 3D 场景。
实战示例:阿尔卑斯冰川地形 + 天空日照
项目中最典型的完整示例是 examples/21-terrain.html,它的实现非常值得借鉴:
- 底图使用 Mapbox 卫星样式
satellite-streets-v9,地形起伏一目了然; - 在法国阿尔卑斯山区加载冰川 3D 模型
examples/models/landmarks/glacier.gltf,模型高度自动贴合山地; - 开启
realSunlight + sky + terrain,并在页面底部放一个时间滑块:拖动滑块改变"当前时刻",渲染回调中调用tb.setSunlight(date, center),就能看到光照方向、天空颜色随之平滑变化——相当于在地图上"回放一天"。
类似的日照效果在建筑阴影示例 examples/14-buildingshadow.html 中也有体现:城市填充拉伸的建筑会投下随时间变化的真实阴影。
⚠️ 注意:天空层和地形层依赖 Mapbox GL JSv2.0 及以上版本,若使用 v1.x,插件会自动降级并关闭这两项功能。
常用 API 一览:手动微调天空与日照
| API | 作用 |
|---|---|
tb.createSkyLayer() | 手动创建/重建天空层 |
tb.createTerrainLayer() | 手动创建/重建地形层 |
tb.setSunlight(date, coords) | 按指定日期时间和经纬度更新太阳位置(场景光 + 天空 + 地形透明度) |
tb.getSunSky(date, sunPos) | 计算某时刻的太阳参数(高度角/方位角) |
tb.updateSunSky(sunPos) | 单独更新天空层的太阳参数 |
如果你不想让天空自动跟随realSunlight,也可以手动控制:先调getSunSky()拿到太阳参数,再调updateSunSky()写入图层,从而实现"固定黄昏色调""夜景模式"等自定义氛围。
新手落地建议:3 步跑通自己的沉浸式 3D 地图
- 准备 Mapbox Token:复制
examples/config_template.js,填入自己的 access token 并保存为config.js; - 打开地形示例:用
npm run start(或直接访问 examples/21-terrain.html)体验完整的地形 + 天空 + 日照效果; - 替换成你的模型:参考示例中的
loadObj写法,把冰川模型换成你的 GLB/GLTF 模型,并设置setCoords到目标经纬度即可。
更多参数说明(如sky、terrain属性的完整定义、terrainExaggeration高度夸张系数)可查阅官方文档 docs/Threebox.md,全部示例清单见 examples/README.md。
小结
Threebox 的地形层与天空层设计得很"省心":一个terrain: true让地图立体化,一个sky: true加上realSunlight: true让天光云影与真实时间对齐。对于想快速做出沉浸式 3D 地图的新手来说,这套内置能力基本可以"零学习成本"直接上手——剩下的,就是把你的 3D 模型放到正确的经纬度上,然后拖动时间滑块,看一场属于地图的日落。🌇
【免费下载链接】threeboxA Three.js plugin for Mapbox GL JS, with support for animations and advanced 3D rendering.项目地址: https://gitcode.com/gh_mirrors/thr/threebox
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考