问题起源

在计算漫反射关照时,需要用到法线,通过法线和光线的点乘值,计算漫反射的产生的光线强度,所以需要从顶点着色器中将法线数据传递到片源着色器中,但是片源着色器中的顶点坐标是经过了模型矩阵变化过的世界坐标.所以二者很可能已经不匹配了,当然模型矩阵是单位矩阵的特殊情况下,就没有影响.

对法线进行mv变换

因此,需要对法线也应用mv矩阵变换.这样,模型的在旋转和缩放后,法线才能也与之匹配,如下图这样:

去掉对法线的偏移效果

但有个问题,就是偏移,如果法线跟着一起偏移,方向就会出问题了,加入模型矩阵沿x方向偏移一点,法线的x也相应的增加一点,就会出现下面这样的情况:



这种情况可以通过将法线的齐次坐标设置为0,来解决,因为偏移的原理就是矩阵最后一列的值乘以其次坐标产生的影响:

不等比缩放

大部分情况下,上面的处理就可以得到想要的效果了,但是,如果mv矩阵中存在不等比缩放,那么会出现法线与原来的面不垂直的问题,虽然在很多情况下这个效果可能不会太明显,因为法线偏差一点点,关照计算并不会有特别明显的区别:



但是当不等比缩放的不同轴之间的差距很大时,这个效果就会更明显了.像下面这样:



这个时候计算出来的光照就会和预期的有很明显的区别,给人很怪异的感觉了.

法线矩阵

这个时候,需要使用发现矩阵,其实就是模型矩阵逆矩阵的转置矩阵,用上效果立马就对了.

模型矩阵逆矩阵的转置矩阵作用原理

用法很简单,原理还是需要点时间来理解的.

首先我们的目标是法线最终需要与顶点的切线垂直.

定义:原法线为n,变换后法线为N,原来顶点处切线为t,变换后切线为T,模型矩阵为M,要计算的结果法线矩阵为X.

.表示点乘,表示矩阵乘以向量(也可以省略),或者向量间叉乘,`代表:

n . t = 0; //法线与切线垂直,所以点乘为0

N . T = 0; //最终结果亦垂直

N = X * n

T = M * t

将第三,四个方程带入第二个方程:

(X * n) . (M * t) = 0

点乘变换成叉乘

(X * n) . (M * t) => (X * n)T * (M * t) => 省略* => (Xn)T * Mt

=> nTXT * Mt

由于n . t = 0

XTM = I

n . t = N . T = 0

XTM = I => X = (M-1)T

OpenGL光照计算中法线矩阵原理及推到过程的更多相关文章

  1. OpenGL光照1:颜色和基础光照

    本文是个人学习记录,学习建议看教程 https://learnopengl-cn.github.io/ 非常感谢原作者JoeyDeVries和多为中文翻译者提供的优质教程 的内容为插入注释,可以先跳过 ...

  2. Deferred Shading,延迟渲染(提高渲染效率,减少多余光照计算)【转】

    Deferred Shading,看过<Gems2> 的应该都了解了.最近很火的星际2就是使用了Deferred Shading. 原帖位置:   http://blog.csdn.net ...

  3. OpenGL光照3:光源

    本文是个人学习记录,学习建议看教程 https://learnopengl-cn.github.io/ 非常感谢原作者JoeyDeVries和多为中文翻译者提供的优质教程 的内容为插入注释,可以先跳过 ...

  4. GLSL 中的光照计算

    理论知识转载地址:http://blog.csdn.net/ym19860303/article/details/25545933 1.Lambert模型(漫反射) 环境光: Iambdiff = K ...

  5. 关于opengl中的矩阵平移,矩阵旋转,推导过程理解 OpenGL计算机图形学的一些必要矩阵运算知识

    原文作者:aircraft 原文链接:https://www.cnblogs.com/DOMLX/p/12166896.html 为什么引入齐次坐标的变换矩阵可以表示平移呢? - Yu Mao的回答 ...

  6. OpenGL中的矩阵相乘

    OpenGL中的矩阵相乘 1, 在OpenGL中所有的视图变换,模型变换 都是4×4矩阵,每个后续的glMultiMatrix*(N),或者变换函数,glTranslate* (),glRotate* ...

  7. 043——VUE中组件之使用.sync修饰符与computed计算属性实现购物车原理

    <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...

  8. OpenGL光照2:材质和光照贴图

    本文是个人学习记录,学习建议看教程 https://learnopengl-cn.github.io/ 非常感谢原作者JoeyDeVries和多为中文翻译者提供的优质教程 的内容为插入注释,可以先跳过 ...

  9. OpenGL的glPushMatrix和glPopMatrix矩阵栈顶操作函数详解

    OpenGL中图形绘制后,往往需要一系列的变换来达到用户的目的,而这种变换实现的原理是又通过矩阵进行操作的.opengl中的变换一般包括视图变换.模型变换.投影变换等,在每次变换后,opengl将会呈 ...

随机推荐

  1. 在利用手背扫描图像+K因子 对室内温度进行回归预测时碰到的问题

    1. 关于多输入流: 由于本Mission是双输入, 导师要求尽量能使用Inception之诸, 于是输入便成了问题. 思考: 在Github上找到了keras-inceptionV4进行对网络头尾的 ...

  2. OKR vs KPI

    OKR vs KPI refs xgqfrms 2012-2020 www.cnblogs.com 发布文章使用:只允许注册用户才可以访问!

  3. TypeScript 4.1 Quick Start Tutorials

    TypeScript 4.1 Quick Start Tutorials TypeScript 4.1 快速上手教程 https://typescript-41-quick-start-tutoria ...

  4. React Hooks: useReducer All In One

    React Hooks: useReducer All In One useReducer https://reactjs.org/docs/hooks-reference.html#usereduc ...

  5. React Suspense All In One

    React Suspense All In One 挂起让组件在渲染之前"等待"某些东西. 如今,Suspense仅支持一种用例:使用React.lazy动态加载组件. 将来,它将 ...

  6. Redis 大 key 问题 & 问题分析 & 解决方案

    Redis 大 key 问题 & 问题分析 & 解决方案 Redis 什么是 Redis 大 key 单个key 存储的 value 很大 hash, set,zset,list 结构 ...

  7. hackr.io & Programming Courses & Programming Tutorials

    hackr.io & Programming Courses & Programming Tutorials the Best Programming Courses & Tu ...

  8. H5 APP 页面移动端适配方案

    H5 APP 页面移动端适配方案 https://segmentfault.com/a/1190000011586301 https://juejin.im/post/5cbdee71f265da03 ...

  9. c++ 使用PID获取可执行文件路径

    注意看备注 https://docs.microsoft.com/en-us/windows/win32/api/psapi/nf-psapi-getmodulefilenameexa #includ ...

  10. app启动速度怎么提升?

    简介: APP 启动速度的重要性不言而喻.高德地图是一个有着上亿用户的超级 APP,本文从唤端技术.H5 启动页.下载速度.APP加载.线程调度和任务编排等方面,详解相关技术原理和实现方案,分享高德在 ...