前言
地图的渲染其实可以分解为线、面、纹理、文字的渲染。为了了解地图渲染的实现原理并实际练习WebGL,进行了这个系列的练习,线是第一步。
本文不赘述WebGL的基本知识,只对运用到的知识点进行一下简单的回顾:
着色器
WebGL需要两种着色器:顶点着色器和片元着色器,以OpenGL ES着色器语言进行编写,本文中使用的着色器如下:
var VSHADER_SOURCE =
'attribute vec4 a_Position;\n' + // 顶点坐标
'uniform mat4 u_MvpMatrix;\n' + // 模型视图投影矩阵
'void main() {\n' +
' gl_Position = u_MvpMatrix * a_Position;\n' +
'}\n';
var FSHADER_SOURCE =
'precision mediump float;\n' +
'uniform vec4 u_Color;\n' +
'void main() {\n' +
' gl_FragColor = u_Color;\n' + // 颜色
'}\n';
复制代码
考虑到绘制一条线使用同一种颜色,与顶点无关,所以在片元着色器中定义了一个uniform变量u_Color。
三角形
WebGL绘制模型的基本单位是三角形,绘制一条有宽度的线并不能像Canvas2D那样设置strokeStyle之后调用stroke()即可,而是需要将整条线拆分成多个小三角形,这个过程称为三角剖分。
线段本身的三角剖分是很简单的,即矩形剖分为两个三角形。但是折线有拐角(lineJoin)和端头(lineCap),且需要支持不同的样式,这部分的剖分会稍微复杂一点,后文会详细分析。WebGL的drawArrays
方法支持多种模式进行多个三角形的绘制,如下所示:
矢量
三角剖分的计算过程中使用到了矢量和矩阵的一些基本运算,涉及到了矢量的加减法、乘法、单位化、旋转等,这些读者应自行了解和掌握。本文封装了二维矢量的相关计算方法到Vector2
类中。
/**
* Constructor of Vector2
* If opt_src is specified, new vector is initialized by opt_src.
* @param opt_src source vector(option)
*/
function Vector2(opt_src) {
var v = new Float32Array(2);
if (opt_src && typeof opt_src === 'object') {
v[0] = opt_src[0]; v[1] = opt_src[1];
}
this.elements = v;
}
/**
* Vector2.prototype.normalize 单位化
* Vector2.prototype.scalarProduct 与标量相乘
* Vector2.prototype.dotProduct 与矢量点乘
* Vector2.prototype.add 与矢量相加
* Vector2.prototype.minus 与矢量相减
* Vector2.prototype.rotate 旋转角度
* Vector2.prototype.copy 复制
* Vector2.prototype.getVertical 获取单位法向量
* /
复制代码
绘制目标
线这里专指折线,使用线段将一组离散的坐标点依次连接而形成。由于地图是呈现在z=0平面上,本文也只探讨在同一平面上延伸的线(扁平的),所以线的坐标点不用关心z坐标,使用二维矢量(x, y)即可。后文以coords
表示线的坐标数组。
除了coords
,线的样式也是其重要的属性。如下例所示,线可设置宽度、颜色,同时可设置边线的宽度和颜色;端头以canvas为标准,可支持三种样式:butt-平头,square-方头,round-圆头;拐角以canvas为标准,支持三种样式:bevel-平角,miter-尖角,round-圆角。
defaultLineStyle = {
strokeColor: new WebglColor(0.5, 0.5, 1, 1), // 边线颜色
strokeWidth: 5, // 边线宽度
fillColor: new WebglColor(0.9, 0.9, 1, 1), // 线颜色
fillWidth: 20, // 线宽度
lineCap: 'butt', // 端头样式
lineJoin: 'bevel' // 拐角样式
}
复制代码
为了之后的一系列练习,本文封装了一个Shape
类用于WebGL绘制基本图形,抽象出了一个构造的接口和通用的方法、属性如下:
- 构造函数:
new Shape(opts)
,参数说明如下
字段名 | 类型 | 说明 |
---|---|---|
type | String | 图形类型:polyline , polygon , circle |
glCtx | WebGLRenderingContext | WebGL绘图上下文 |
camera | Matrix4 | 视图投影矩阵 |
coords | Array. | 坐标 |
style | Object | 样式 |