OpenGL|Android OpenGL ES (七)索引法绘制

前言 之前我们绘制的都是一些简单的基础图形,本章节我们绘制一个复杂些的形状,如下。
OpenGL|Android OpenGL ES (七)索引法绘制
文章图片

索引绘制

图中的数字是后期标注,并非GL绘制。
根据之前学的知识,我们知道,这个图形可以分解为4个三角形,用数字代表顶点序号,分别是
  • 0, 1, 2
  • 0, 2, 3
  • 0, 4, 1
  • 3, 2, 5
在程序中,每个顶点对应x、y坐标,那么我们的顶点数组数据就需要如下声明:
private static final float[] POINT_DATA = https://www.it610.com/article/{ // 0, 1, 2 -0.5f, -0.5f, 0.5f, -0.5f, 0.5f, 0.5f, // 0, 2, 3 -0.5f, -0.5f, 0.5f, 0.5f, -0.5f, 0.5f, // 0, 4, 1 -0.5f, -0.5f, 0f, -1.0f, 0.5f, -0.5f, // 3, 2, 5 -0.5f, 0.5f, 0.5f, 0.5f, 0f, 1.0f, };

所以,实际声明的顶点数是4 * 3 = 12个顶点。而其中有很多顶点是可以重复的,这导致2个问题:
  1. 顶点数据过多,代码的可读性降低,需要隔几行就注释一下
  2. 有重复的顶点数据,造成了内存的浪费
这种绘制方式,叫顶点法绘制。
而本章节会引入一个新的技巧:索引法绘制。
代码实现 1. 定义坐标、索引
/** * 顶点数据 */ private static final float[] POINT_DATA = https://www.it610.com/article/{ -0.5f, -0.5f, 0.5f, -0.5f, 0.5f, 0.5f, -0.5f, 0.5f, 0f, -1.0f, 0f, 1.0f, }; /** * 数组绘制的索引:当前是绘制三角形,所以是3个元素构成一个绘制顺序 */ private static final short[] VERTEX_INDEX = { 0, 1, 2, 0, 2, 3, 0, 4, 1, 3, 2, 5};

这里第一个float类型的数组,定义了每个顶点的坐标位置。
第二个数组是short类型的,定义了上一个数组的绘制顺序。也就是0代表着POINT_DATA数组的第0组的数据(-0.5f, -0.5f)。再解释下,之后我们会声明为2个点为一个顶点,所以索引0并非表示第0位的POINT_DATA[0],而是第0组。
2. 绘制图形
@Override public void onDrawFrame(GL10 glUnused) { GLES20.glClear(GLES20.GL_COLOR_BUFFER_BIT); // 1. 绘制模式; 2. 从数组中读取的数据长度; 3. 加载的数据格式; 4. 读取的数据缓冲区 GLES20.glDrawElements(GLES20.GL_TRIANGLES, VERTEX_INDEX.length, GLES20.GL_UNSIGNED_SHORT, mVertexIndexBuffer); }

这里使用到了一个新的方法GLES20.glDrawElements,方法参数分别是
  1. 图形绘制方式
  2. 绘制的顶点数
  3. 索引的数据格式
  4. 索引的数据Buffer
这里再回顾下顶点法的绘制方法GLES20.glDrawArrays,方法参数分别是
  1. 图形绘制方式
  2. 从顶点数据读取数据的起点位置(以点作为单位,而非向量)
  3. 绘制的顶点数
3. 顶点法、索引法的比较
按照索引的数据声明方式,代码的可读性大大地提高,那么性能上有多大提升呢?
首先,我们知道GL中,一个Float类型的数据占4个Byte,一个Short类型的占2个Byte。
那么在前言中声明的12个顶点的方式,也就是顶点法绘制方式,占的内存空间是:
12(顶点数) * 2(x、y两个向量为一组) * 4(Float格式占的Byte字节) = 96字节
而索引法的占的内存空间是:
6(顶点数) * 2(x、y两个向量为一组) * 4(Float格式占的Byte字节) + 12(索引数) * 2(Short格式占的Byte字节) = 48 + 24 = 72字节
本章节绘制的图形顶点属性比较单一,只有顶点位置,假若包含了颜色等其他顶点信息,那么顶点法占的内存将更大。
【OpenGL|Android OpenGL ES (七)索引法绘制】归纳下两种绘制方式的对比情况。
绘制方式 适用场景 可读性 内存计算方式
顶点法 顶点复用情况少 顶点数 * 顶点属性数 * 顶点数据格式类型
索引法 顶点复用情况多 顶点数 * 顶点属性数 * 顶点数据格式类型 + 索引数 * 索引数据格式类型

    推荐阅读