WebGL 踩坑系列-1
WebGL 中的一些选项
WebGL 中开启颜色混合(透明效果)
gl.enable(gl.BLEND);
gl.blendFunc(gl.SRC_ALPHA, gl.ONE_MINUS_SRC_ALPHA);
设置遮挡剔除有效。生成三角形时,沿着逆时针方向的那面会被生成出来,而另一面就不会生成出来。
gl.enable(gl.CULL_FACE);
gl.cullFace(gl.BACK);
观察球面的效果:

当设置透明效果却不开启遮挡剔除的时候,用 web GL 生成球面,在球外观察球面时就会看到一些奇怪的角。

第二个球就很明显的有一些不同的部分。
在 web GL 中使用矩阵
可以利用矩阵的平移、旋转、缩放实现物体的各种动作。
我在最开始使用 Web GL 绘图的时候,球面上的点都是利用循环得到,但是由于有缩放球面的需求,所以最开始的做法是
1. 创建缓冲区时用的 gl.DYNAMIC_DRAW
2. 当要缩放球面时,重新计算顶点
3. 用 gl.updateBufferData 函数更新定点数据
当缩放的时候就能明显看到画面撕裂,帧率下降。
可能的原因是:
1. 每次重新计算都要使用大量的计算资源,若帧率为 60,那么每秒要计算上千个顶点,如果球面较精细,那么需要计算的顶点数更多。
2. 并且每次计算之后都要将这些顶点传入到 GPU 中,可能会占用一部分的传输带宽
正常的做法是用坐标变换矩阵,将变换后的矩阵通过 gl.uniformMatrix4fv 传入到着色器,就可以轻松的实现平移旋转和缩放。并且不会造成性能严重下降。
但是矩阵的乘法与普通的数乘有所差别,矩阵的乘法一般不满足交换律。
若 pMatrix 表示透视矩阵,vMatrix 表示视图矩阵,mMatrix 表示模型矩阵,aVertex 表示传入的顶点,那么一般的乘式是
gl_Position = pMatrix * vMatrix * mMatrix * aVertex;
如果矩阵的顺序不同,可能最后得到的图形也就不同。
对矩阵先进行旋转操作,再进行平移操作。缩放操作的顺序一般没有影响。
但我在使用 gl-Matrix.js 时,对一个矩阵先进行旋转,再进行平移操作:
mat4.identity(this.mMatrix); mat4.fromRotation(this.mMatrix, angle[1] * Math.PI*2, [0, 0, 1]);
mat4.rotate(this.mMatrix, this.mMatrix, angle[0] * Math.PI, [0, 1, 0]);
mat4.translate(this.mMatrix, this.mMatrix, pos); mat4.multiply(mvpMatrix, pvMatrix, this.mMatrix);
gl.uniformMatrix4fv(uniforms.pmv_matrix, false, mvpMatrix);
和将旋转操作和平移操作放在两个矩阵中进行得到的结果并不相同。
mat4.identity(this.mMatrix); mat4.fromRotation(this.rMatrix, angle[1] * Math.PI*2, [0, 0, 1]);
mat4.rotate(this.rMatrix, this.rMatrix, angle[0] * Math.PI, [0, 1, 0]);
mat4.translate(this.mMatrix, this.mMatrix, pos);
mat4.mul(this.mMatrix, this.mMatrix, this.rMatrix); mat4.multiply(mvpMatrix, pvMatrix, this.mMatrix);
gl.uniformMatrix4fv(uniforms.pmv_matrix, false, mvpMatrix);
注意这里用 pvMatrix 乘 mMatrix 之前先用 mMatrix 乘了一个附加矩阵 rMatrix。
具体的原因并不清楚,但是第二个操作实现的图像符合我的需求。
=========================
这几天又重新测试了下代码,发现上面的旋转平移操作的矩阵还是有些问题,
具体问题在于经过旋转平移后的面上反的,以下矩阵操作可以方便的做到旋转平移,并且得到的面上正的
mat4.fromZRotation(this.rMatrix, this.beta); // 绕 Z 轴旋转 beta 角
mat4.rotateY(this.rMatrix, this.rMatrix, this.theta); // 再绕 Y 轴旋转 theta 角
mat4.fromRotationTranslation(this.mMatrix, this.rMatrix, pos);
mat4.rotateZ(this.mMatrix, this.mMatrix, this.beta);
mat4.rotateY(this.mMatrix, this.mMatrix, this.theta);
最后得到的面就是我想要的
完整的代码可以在我的 GitHub 上查看。
WebGL 踩坑系列-1的更多相关文章
- WebGL 踩坑系列-3
WebGL 踩坑系列-3 绘制球体 在 WebGL 中绘制物体时需要的顶点是以直角坐标表示的, 当然了,gl_Position 是一个四维的向量,一般将顶点赋值给 gl_Position 时,最后一维 ...
- WebGL 踩坑系列-2
需求:绘制斑点在球面上走过的路径 思路:要绘制斑点在球面上走过的路径,首先要记录上一时刻和当前时刻该斑点所在球面的位置,并且实时更新当前时刻的斑点位置和上一时刻的斑点位置. 为了方便,上一时刻斑点所在 ...
- jmeter踩坑系列
1.踩坑系列一: 抓包出来有host的字段,放到jmeter里面一起请求就报错了,去掉就请求正常了 1.踩坑系列二: 从花瓶复制过去 的values 前面有空格,肉眼看起来没有
- python踩坑系列之导入包时下划红线及报错“No module named”问题
python踩坑系列之导入包时下划红线及报错“No module named”问题 使用pycharm编写Python时,自己写了一个包(commontool),在同级另一个路径下(fileshand ...
- 踩坑系列の Oracle dbms_job简单使用
二话不说先上代码 --创建存储过程 create or replace procedure job_truncateState is begin --此处就是要定时执行的sql execute imm ...
- Vue踩坑系列
前言 前端开发对于vue的使用已经越来越多,它的优点就不做介绍了, 本篇是我对vue使用过程中遇到的问题中做的一些总结,帮助大家踩坑.如果喜欢的话可以点波赞,或者关注一下,希望本文可以帮到大家!!! ...
- 踩坑系列:MySql only_full_group_by配置,竟导致所有应用报错?
1. 踩坑经历 一个很平常的下午,大家都在埋头认真写bug呢,突然企业微信群里炸锅了,好多应用都出现大量的Error日志,而且都报同一个错误,就是下面这个: Caused by: com.mysql. ...
- 【踩坑系列】使用long类型处理金额,科学计数法导致金额转大写异常
1. 踩坑经历 上周,一个用户反馈他创建的某个销售单无法打开,但其余销售单都可以正常打开,当时查看了生产环境的ERROR日志,发现抛了这样的异常:java.lang.NumberFormatExcep ...
- electron踩坑系列之一
前言 以electron作为基础框架,已经开发两个项目了.第一个项目,我主要负责用react写页面,第二项目既负责electron部分+UI部分. 做项目,就是踩坑, 一路做项目,一路踩坑,坑多不可怕 ...
随机推荐
- 理解JavaScript普通函数以及箭头函数里使用的this
this 普通函数的this 普通函数的this是由动态作用域决定,它总指向于它的直接调用者.具体可以分为以下四项: this总是指向它的直接调用者, 例如 obj.func() ,那么func()里 ...
- 大佬写的js生成玫瑰(来源网络)
<!DOCTYPE html> <html> <head> <title>js html5渲染的3D玫瑰花(程序员的情人节礼物)</title&g ...
- P1919 【模板】A*B Problem升级版(FFT快速傅里叶)
题目描述 给出两个n位10进制整数x和y,你需要计算x*y. 输入输出格式 输入格式: 第一行一个正整数n. 第二行描述一个位数为n的正整数x. 第三行描述一个位数为n的正整数y. 输出格式: 输出一 ...
- php实现页面跳转的几种方式
PHP中实现页面跳转有一下几种方式,看了几个人写的不是很条理,自己整理一下 在PHP脚本代码中实现 <?php header("location:url地址") ?> ...
- linux1--常用命令
1.目录结构 2./etc:系统配置文件存放地 比如你的wsgi的配置文件,nginx 3./usr 应用程序存放地 比如你的jdk应用程序存放地 4./root 系统管理员root的家目录 4.1像 ...
- Qt 学习之路 2(14):对话框数据传递
Home / Qt 学习之路 2 / Qt 学习之路 2(14):对话框数据传递 Qt 学习之路 2(14):对话框数据传递 豆子 2012年9月15日 Qt 学习之路 2 53条评论 对话框 ...
- N - 嘤嘤嘤 (并查集+枚举)
Our lovely KK has a difficult Social problem. A big earthquake happened in his area. N(2≤N≤2000)N(2≤ ...
- PreparedStatement是如何防止SQL注入的?
为什么在Java中PreparedStatement能够有效防止SQL注入?这可能是每个Java程序员思考过的问题. 首先我们来看下直观的现象(注:需要提前打开mysql的SQL文日志) 1. 不使用 ...
- 使用vlookup函数下拉全部相同解决
菜单“公式”-“计算选项”改为自动 ref: https://zhidao.baidu.com/question/561971299094821004.html
- Ancoda 下的python多版本共存
Ancoda 下的python多版本共存 virtualenv python 多版本共存 Pip, Virtualenv 和Fabric 被称为python 的三大神器,Pip 是包管理工具,Virt ...