经纬志
首页 / three.js / 使用示例

地形网格

一张 140 × 140 的规则网格,顶点沿高度函数抬升,颜色按海拔渐变。 同样的流程可以把 DEM 栅格变成可交互的地形面。

three.js 0.160.0 · 更新 2026-10-27
源码与运行效果
运行效果

说明

PlaneGeometry(34, 34, 140, 140) 生成一张水平面,随后 rotateX(-Math.PI/2) 把它放倒,顶点的 Y 就成了高度。 遍历 19881 个顶点,按 heightAt(x, z) 写入高程, 再用 computeVertexNormals() 重算法线,光照才会贴着起伏变化。

颜色写在顶点上,材质开启 vertexColors。低处取深绿,中段过渡到黄褐, 高处偏灰白,用 HSL 的色相与明度连续插值实现,比预设几档色带更平滑。

设置数值说明
平面尺寸34 × 34场景单位,可理解为 34 米或 34 千米
分段140 × 140顶点 19881 个,三角面 39200 个
高度函数两组正弦 + 一峰一谷纯代码生成,不依赖 DEM 文件
高度夸张0.4 – 2.2 倍只改 scale.y,不重建几何
材质Standard,粗糙度 0.94接近自然地表,几乎没有镜面反射
相机上限极角 0.495π禁止转到地下,避免看到网格背面

为什么先放倒再改高度

如果直接在未旋转的平面上改 Z,地形会立起来,像一面墙。把平面绕 X 轴转 −90 度后, 原平面的 Y 方向变成世界的 Z 方向,改顶点的 Y 才是抬升。 这一步顺序不能反,否则法线、纹理坐标与相机朝向都会对不上。

高度夸张的正确做法

示例的夸张滑杆只改网格的 scale.y,几何体不动。 这样切换几乎没有成本,因为顶点缓冲没有重新上传。 但要注意:模型与标注如果与地形同处一个组,会被一起拉伸; 正确做法是把地形放进独立的组,夸张只作用于地形。

在真实项目里,垂直夸张通常设为 1.5 到 3 倍,用于在平面距离远大于高差时突出地形。 如果要做坡度、通视这类量算,必须回到未夸张的真实比例,否则结果没有意义。

换成 DEM 数据

把 heightAt(x, z) 换成从栅格读取的高程即可。需要注意三点: 栅格的行列方向与平面 UV 的对应关系;无效值(如 −9999)要单独处理,不能直接当地形; 高程单位与水平单位要统一,米对米,或千米对千米。

法线不重算,地形会「平」。只改顶点位置而不调用 computeVertexNormals(), 所有法线仍然朝上,光照会均匀铺满整块地形,看起来像一张贴了颜色的纸。