WebGL顶点索引绘制gl.drawElements()

WebGL顶点索引绘制gl.drawElements()

本文是WebGL电子书的1.6节内容

上一节课绘制的一个案例是线框立方体,不知大家是否注意到,立方体有8个顶点,但是数组列举顶点的时候,因为绘制直线的时候一个点是三条直线公用, 如果绘制函数gl.drawArrays()绘制模式mode使用gl.LINES模式,每绘制一条直线就需要定义两个顶点。在这种情况下一个点可能在顶点数组中多次列举出来,造成数据重复, 这时候要解决数据的复用,大家应该会想到数据库、索引等概念,也就是说把立方体的8个顶点声明在一个数组中,再声明一个索引数组可以多次调用同一个顶点, 这样可以复用数据,节约空间,上节课案例的立方体的数据是比较少的,实际开发中一个曲面顶点数据量往往比较大,三维模型通过建立顶点的索引来复用顶点数据,可以节约一定的存储空间。

WebGL为了复用顶点数据新引入了一个新的绘制函数gl.drawElements()gl.drawElements()gl.drawArrays()方法一样都是命令浏览器WebGL图形系统开始处理顶点绘制渲染出像素并显示在屏幕Canvas画布上。 区别是gl.drawArrays()方法直接调用顶点数组数据,gl.drawElements()是通过一个索引数组访问使用顶点数组中的顶点数据。

本节课的代码是在上节课的基础上进行更改,使用顶点索引法实现一样的渲染结果。下面的代码只列举新增和修改的部分,其余代码不变,着色器程序更不用修改。

  1. 只需要把所有的顶点列举一次即可,不用重复枚举。
//   8个顶点坐标数组
var data=new Float32Array([
   0.5,  0.5,  0.5,//顶点0
   -0.5,  0.5,  0.5,//顶点1
   -0.5, -0.5,  0.5,//顶点2
   0.5, -0.5,  0.5,//顶点3
   0.5,  0.5, -0.5,//顶点4
   -0.5,  0.5, -0.5,//顶点5
   -0.5, -0.5, -0.5,//顶点6
   0.5, -0.5, -0.5,//顶点7
]);
  1. 顶点的索引数组

在这里插入图片描述

索引值索引值对应顶点坐标
0(0.5, 0.5, 0.5)
1(-0.5, 0.5, 0.5)
2(-0.5, -0.5, 0.5)
3(0.5, -0.5, 0.5)
4(0.5, 0.5, -0.5)
5(-0.5, 0.5, -0.5)
6(-0.5, -0.5, -0.5)
7(0.5, -0.5, -0.5)

下面代码中表示的顶点索引如上图所示。

// 顶点索引数组
var indexes = new Uint8Array([
  //前四个点对应索引值
  0, 1, 2, 3,//gl.LINE_LOOP模式四个点绘制一个矩形框
  //后四个顶点对应索引值
  4, 5, 6, 7,//gl.LINE_LOOP模式四个点绘制一个矩形框
  //前后对应点对应索引值  
  0, 4,//两个点绘制一条直线
  1, 5,//两个点绘制一条直线
  2, 6,//两个点绘制一条直线
  3, 7//两个点绘制一条直线
]);
  1. 索引数组的数据传入显存缓冲区,注意与顶点数据传入缓冲区方法参数的对比,传入索引数据时,bindBuffer()bufferData()方法的第一个参数是gl.ELEMENT_ARRAY_BUFFER,传入顶点数据时是gl.ARRAY_BUFFER
//创建缓冲区对象
var indexesBuffer=gl.createBuffer();
//绑定缓冲区对象
gl.bindBuffer(gl.ELEMENT_ARRAY_BUFFER,indexesBuffer);
//索引数组indexes数据传入缓冲区
gl.bufferData(gl.ELEMENT_ARRAY_BUFFER,indexes,gl.STATIC_DRAW);
  1. 使用方法drawElements()替换drawArrays()方法,参数设置基本一致,方法drawElements()只是新增了一个数据类型设置参数gl.UNSIGNED_BYTE
//LINE_LOOP模式绘制前四个点
gl.drawElements(gl.LINE_LOOP,4,gl.UNSIGNED_BYTE,0);
//LINE_LOOP模式从第五个点开始绘制四个点
gl.drawElements(gl.LINE_LOOP,4,gl.UNSIGNED_BYTE,4);
//LINES模式绘制后8个点
gl.drawElements(gl.LINES, 8, gl.UNSIGNED_BYTE, 8);
WebGL API gl.drawElements()

参数格式:drawElements(mode, count, type, offset)

参数含义
mode绘制模式gl.LINE_LOOP、gl.LINES、gl.TRIANGLES等
count绘制顶点个数整型数
type数据类型gl.UNSIGNED_BYTE对应Uint8Array,gl.UNSIGNED_SHORT对应Uint16Array
offset从第几个点开始绘制整型数,以字节为单位

countoffset组合可以确定绘制众多顶点中的连续一段,通过顶点索引关联顶点数据,countoffset指的是顶点的索引数组。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Threejs可视化

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值