WebGL入门教程 - 高光计算模型

techbrood 发表于 2019-08-09 18:06:06

标签: webgl, tutorials, specular, light

- +

现实物体在光源的照射下,会出现吸收和反射。物体的颜色主要由漫反射决定,但局部高光效果则主要由镜面反射来决定。

从表面反射出的光线与入射角成相等但相反的角度,称为“镜面反射”。

如果镜面反射光线直接进入相机,就好像相机直接看到光源一样,即使它已经从物体上反弹出来。相机看到的是光源的光,而不是物体的颜色。如果你有一个白色光源,镜面反射将是白色的。如果您有一个红色光源,镜面反射将是红色的。因此,要对镜面反射进行建模,需要在照明模型中指定光源的颜色。

specular_angle.png

通常相机位置和反射光之间存在一个角度,如果角度很大,我们将看不到反射光,如果角度为0,那么在不考虑光线被吸收和衰减的情况下,我们看到了全部的反射光。可以用余弦函数来计算百分比,但是对于高聚焦的镜面反射来说,一般我们的直观体验是角度为0及其附近处光线陡然变亮,而超过某个角度后光线迅速变暗,因此普通余弦函数的曲线太平缓了,所以我们把余弦函数提高一个n次幂,曲线就会在边缘处(偏离角度较大处)快速下降。你可以自行测试下cos函数的指数函数的变化曲线,通过引入额外的指数参数,我们可以模拟在镜面反射矢量周围的各种光散射量。如果指数较大,例如100,则cos(a)exp将向y轴塌缩,只有非常小的角度才会返回一个有效的百分比值,即高光区域很小;而如果指数很小,如1.0,则会模拟反射光线周围的大量光线,即高光区域较大。

高光反射数学模型

如果我们用n表示片段法线(N)方向上的正规化向量(长度为1),如下图所示:

reflection_vectors2.png

在已知入射光位置、入射光L、片段点位置和片段点法向量的情况下,我们可以通过简单的几何计算推导反射光R如下:

R = N + P
=> R = n*dot_product(n,-L) + (L + N)
=> R = n*dot_product(n,-L) + (L + n*dot_product(n,-L))
=> R = 2*n*dot_product(n,-L) + L
其中L = fragment_position - light_position

得到反射光后,根据相机位置,我们可以进一步计算反射光和相机夹角,然后算上我们刚才提到的指数参数以及额外的一个高光强度调节参数,推导过程如下:

reflection = normalize( R );
to_camera = normalize( fragment_position - camera_position );
cos_angle = dot(reflection, to_camera);
cos_angle = clamp(cos_angle, 0.0, 1.0);
cos_angle = specular_factor*(pow(cos_angle, specular_gloss)); // 这里specular_gloss代表上面所提到的指数参数,表示shiness
specular_color = u_Light_color * cos_angle;

根据上面的公式,我们可以很容易的实现一个webgl shader程序。

possitive(7) views4615 comments1

发送私信

最新评论

iefreer 2019-08-12 14:42:01

一个参考实现:https://wow.techbrood.com/fiddle/53585


请先 登录 再评论.
相关文章
  • CentOS6 Apache2.2多站点HTTPS配置

    可以使用letsencrypt(certbot)免费证书服务。支持多系统、多站点和多目录,支持wildcard(通配符域名),90天生效,可用定时任务自动更新。需要注意一点的是apache2.4以下版本需要在默认的ssl配置中添加如下的指令:NameVirtualHost

  • 增强现实引擎ARToolKit工作原理简介

    ARToolkit是一个基于CV(计算机视觉)和Marker(标识)的开源增强现实引擎。其具备如下功能特性:A. 鲁棒跟踪,包括基于标记的跟踪与基于特征的跟踪;

  • JavaScript事件模型图解

    在JavaScript中用户交互的核心部分就是事件处理。本文为对事件模型和处理机制的总体性描述。Event是什么?
    event是用户操作网页时发生的交互动作,比如clic...

  • 常见面试题JavaScript闭包(ES5语法)

    JavaScript闭包(Closure)是常见的JS面试题,是否理解闭包是一个简单的区分JS初级和高级程序员的判例。几乎每个JS程序员都在使用闭包,有意或无意间。比如编写一个jQuery鼠标点击处理函数:$(function()

  • Web界面编程状态变化和JS开发框架(React/Angular/Ember)

    UI编程中的一个关键课题就是界面组件化(可复用)以及组件状态管理。稍早一些的windows程序员可能接触过MFC,其界面编程中有一个DDX(DoDataExchange)的机制,...

  • 使用SVG和CSS3创建圆形进度条动画

    圆形进度条是一个经典的控制面板元素,常用于显示任务进度,比如用户档案的完整程度,或者升级状态。有很多方法来实现圆形进度条,比如用JS, CSS3, Canvas, SVG...

  • 深入理解Three.js(WebGL)贴图(纹理映射)和UV映射

    本文将详细描述如何使用Three.js给3D对象添加贴图(Texture Map,也译作纹理映射,“贴图”的翻译要更直观,而“纹理映射”更准确。)。为了能够查看在线演示效...

  • 三维向量的简单运算和实用意义

    在WebGL的实际应用中我们广泛使用向量的几何运算来计算角度、距离,判断点线、点面之间的关系,比如物体之间的碰撞检测。本文简要介绍三维计算机图形学中常用的...

  • 粒子运动模拟 - Verlet积分算法简介

    Verlet算法是经典力学(牛顿力学)中的一种最为普遍的积分方法,被广泛运用在分子运动模拟(Molecular Dynamics Simulation),行星运动以及织物变形模拟等领域...

  • S3TC(S3 Texture Compression)纹理压缩格式详解

    使用S3TC格式存储的压缩纹理是以4X4的纹理单元块(texel blocks)为基本单位存储的,每纹理单元块(texel blocks)有64bit或者128bit的纹理单元数据(texel data)。这...

  • 如何实现SVG clipPath自适应被裁剪对象

    CSS3中引入的clip-path(裁剪路径)属性是一个很强大的特性。
    clip-path的含义如下图所示,好比剪纸一样,你用剪刀沿着某条路径把目标对象(图像或元素)裁...

  • HTML网页布局:静态、自适应、流式、响应式

    静态布局(Static Layout)即传统Web设计,对于PC设计一个Layout,在屏幕宽高有调整时,使用横向和竖向的滚动条来查阅被遮掩部分;对于移动设备,单独设计一个布...

  • 更多...