Unity中Shader的BRDF解析(二)

2023-11-28 12:01
文章标签 解析 unity shader brdf

本文主要是介绍Unity中Shader的BRDF解析(二),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

文章目录

  • 前言
  • 一、回顾一下上一篇的结尾
    • 在这里插入图片描述
  • 二、我们来解析一下 UNITY_PBS_USE_BRDF1(高配)
    • 1、迪士尼BRDF原则
    • 2、迪士尼的漫反射函数
    • 3、参数:perceptualRoughness(感性的粗糙度)
    • 4、参数:halfDir (半角向量)
    • 5、参数:nv(法线向量 点积 视线向量)
    • 6、参数:nl、nh、lv、lh


前言

我们在这篇文章中,继续来继续解析BRDF中的高配置情况( UNITY_PBS_USE_BRDF1)下,迪士尼的漫反射计算

  • Unity中Shader的BRDF解析(一)

一、回顾一下上一篇的结尾

  • 在上篇文章中,我们解析到了BRDF的具体计算

在这里插入图片描述

二、我们来解析一下 UNITY_PBS_USE_BRDF1(高配)

1、迪士尼BRDF原则

在这里插入图片描述

我们在该函数的最后能找到与迪士尼BRDF原则对应的程序:

在这里插入图片描述

2、迪士尼的漫反射函数

在这里插入图片描述

在这里插入图片描述

// Specular term
// HACK: theoretically we should divide diffuseTerm by Pi and not multiply specularTerm!
// 理论上漫反射项中应该除以 PI,但是由于以下两个原因没有这样做
// BUT 1) that will make shader look significantly darker than Legacy ones
//原因一:这样会导致最终效果偏暗
// and 2) on engine side “Non-important” lights have to be divided by Pi too in cases when they are injected into ambient SH
//原因二:当引擎光照为 不重要光照 时,进行球谐光照计算,会再除以一个 PI。所以,在Unity计算迪士尼漫反射时,不除以PI

我们主要来看,他用到的参数是什么

3、参数:perceptualRoughness(感性的粗糙度)

//感性的粗糙的 = 1 - smoothness
float perceptualRoughness = SmoothnessToPerceptualRoughness (smoothness);

4、参数:halfDir (半角向量)

//半角向量(一般用 H 表示): H = 光线向量 + 视线向量(此处的 光线向量 和 视线向量 为单位向量,根据向量相加的四边形法则得出半角向量)
float3 halfDir = Unity_SafeNormalize1 (float3(light.dir) + viewDir);

5、参数:nv(法线向量 点积 视线向量)

	//法线 与 视线的点积在可见像素上不应该出现负值,但是他有可能发生在 投影 与 法线 映射 时//所以,可以通过某些方式来修正,但是会产生额外的指令运算//替代方案采用abs的形式,同样可以工作只是正确性少一些    // NdotV should not be negative for visible pixels, but it can happen due to perspective projection and normal mapping// In this case normal should be modified to become valid (i.e facing camera) and not cause weird artifacts.// but this operation adds few ALU and users may not want it. Alternative is to simply take the abs of NdotV (less correct but works too).// Following define allow to control this. Set it to 0 if ALU is critical on your platform.// This correction is interesting for GGX with SmithJoint visibility function because artifacts are more visible in this case due to highlight edge of rough surface// Edit: Disable this code by default for now as it is not compatible with two sided lighting used in SpeedTree.#define UNITY_HANDLE_CORRECTLY_NEGATIVE_NDOTV 0#if UNITY_HANDLE_CORRECTLY_NEGATIVE_NDOTV// The amount we shift the normal toward the view vector is defined by the dot product.half shiftAmount = dot(normal, viewDir);normal = shiftAmount < 0.0f ? normal + viewDir * (-shiftAmount + 1e-5f) : normal;// A re-normalization should be applied here but as the shift is small we don't do it to save ALU.//normal = normalize(normal);float nv = saturate(dot(normal, viewDir)); // TODO: this saturate should no be necessary here#elsehalf nv = abs(dot(normal, viewDir));    // This abs allow to limit artifact#endif

6、参数:nl、nh、lv、lh

//其他向量之间的点积
float nl = saturate(dot(normal, light.dir));//法线 点积 光线
float nh = saturate(dot(normal, halfDir));//法线 点积 半角
half lv = saturate(dot(light.dir, viewDir));//光线 点积 视线
half lh = saturate(dot(light.dir, halfDir));//光线 点积 半角

这篇关于Unity中Shader的BRDF解析(二)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/429670

相关文章

Golang HashMap实现原理解析

《GolangHashMap实现原理解析》HashMap是一种基于哈希表实现的键值对存储结构,它通过哈希函数将键映射到数组的索引位置,支持高效的插入、查找和删除操作,:本文主要介绍GolangH... 目录HashMap是一种基于哈希表实现的键值对存储结构,它通过哈希函数将键映射到数组的索引位置,支持

Python使用getopt处理命令行参数示例解析(最佳实践)

《Python使用getopt处理命令行参数示例解析(最佳实践)》getopt模块是Python标准库中一个简单但强大的命令行参数处理工具,它特别适合那些需要快速实现基本命令行参数解析的场景,或者需要... 目录为什么需要处理命令行参数?getopt模块基础实际应用示例与其他参数处理方式的比较常见问http

Python利用ElementTree实现快速解析XML文件

《Python利用ElementTree实现快速解析XML文件》ElementTree是Python标准库的一部分,而且是Python标准库中用于解析和操作XML数据的模块,下面小编就来和大家详细讲讲... 目录一、XML文件解析到底有多重要二、ElementTree快速入门1. 加载XML的两种方式2.

Java的栈与队列实现代码解析

《Java的栈与队列实现代码解析》栈是常见的线性数据结构,栈的特点是以先进后出的形式,后进先出,先进后出,分为栈底和栈顶,栈应用于内存的分配,表达式求值,存储临时的数据和方法的调用等,本文给大家介绍J... 目录栈的概念(Stack)栈的实现代码队列(Queue)模拟实现队列(双链表实现)循环队列(循环数组

java解析jwt中的payload的用法

《java解析jwt中的payload的用法》:本文主要介绍java解析jwt中的payload的用法,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录Java解析jwt中的payload1. 使用 jjwt 库步骤 1:添加依赖步骤 2:解析 JWT2. 使用 N

Python中__init__方法使用的深度解析

《Python中__init__方法使用的深度解析》在Python的面向对象编程(OOP)体系中,__init__方法如同建造房屋时的奠基仪式——它定义了对象诞生时的初始状态,下面我们就来深入了解下_... 目录一、__init__的基因图谱二、初始化过程的魔法时刻继承链中的初始化顺序self参数的奥秘默认

Java 正则表达式URL 匹配与源码全解析

《Java正则表达式URL匹配与源码全解析》在Web应用开发中,我们经常需要对URL进行格式验证,今天我们结合Java的Pattern和Matcher类,深入理解正则表达式在实际应用中... 目录1.正则表达式分解:2. 添加域名匹配 (2)3. 添加路径和查询参数匹配 (3) 4. 最终优化版本5.设计思

使用Java将DOCX文档解析为Markdown文档的代码实现

《使用Java将DOCX文档解析为Markdown文档的代码实现》在现代文档处理中,Markdown(MD)因其简洁的语法和良好的可读性,逐渐成为开发者、技术写作者和内容创作者的首选格式,然而,许多文... 目录引言1. 工具和库介绍2. 安装依赖库3. 使用Apache POI解析DOCX文档4. 将解析

Java字符串处理全解析(String、StringBuilder与StringBuffer)

《Java字符串处理全解析(String、StringBuilder与StringBuffer)》:本文主要介绍Java字符串处理全解析(String、StringBuilder与StringBu... 目录Java字符串处理全解析:String、StringBuilder与StringBuffer一、St

Spring Boot循环依赖原理、解决方案与最佳实践(全解析)

《SpringBoot循环依赖原理、解决方案与最佳实践(全解析)》循环依赖指两个或多个Bean相互直接或间接引用,形成闭环依赖关系,:本文主要介绍SpringBoot循环依赖原理、解决方案与最... 目录一、循环依赖的本质与危害1.1 什么是循环依赖?1.2 核心危害二、Spring的三级缓存机制2.1 三