Unity Shader - 高光反射(Phong、Blinn-Phong)

2023-11-06 22:20

本文主要是介绍Unity Shader - 高光反射(Phong、Blinn-Phong),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

高光反射光照模型分为Phong模型Blinn-Phong模型:

Phong 模型公式:

高光反射 = 光源颜色 * 反射颜色 ∗ pow( max(0, 视角v与光反射向量r的余弦值) , 光泽度)

如下图:

Blinn-Phong 模型公式:

高光反射 = 光源颜色 * 反射颜色 ∗ pow( max(0, 半角向量h与法线n的余弦值) , 光泽度)

如下图:

 逐顶点高光反射:

Shader "Unlit/003"
{Properties{_Specular ("_Specular",Color) = (1,1,1,1)// 高光反射值_Gloss ("_Gloss",range(1,100)) = 5}SubShader{Pass{CGPROGRAM#pragma vertex vert#pragma fragment frag#include "UnityCG.cginc"#include "Lighting.cginc"float4 _Specular;half _Gloss;struct v2v{float4 vertex : POSITION;float3 normal : NORMAL;};struct v2f{float4 vertex : POSITION;float3 color : Color;};v2f vert (v2v v){v2f o;// 将对象空间中的点变换到齐次坐标中的摄像机裁剪空间o.vertex = UnityObjectToClipPos(v.vertex);// 光源方向float3 lightDir = normalize(_WorldSpaceLightPos0.xyz);// 将法向量转到世界坐标法向量float3 normal = UnityObjectToWorldNormal(v.normal);// 视野方向float3 viewDir = normalize(_WorldSpaceCameraPos.xyz- UnityObjectToWorldDir(v.vertex));// 反射方向float3 reflectDir = normalize(mul(normal,2) - lightDir);// float3 reflectDir = normalize(reflect(-lightDir,normal));// Phong 模型公式高光反射计算float3 specular = _LightColor0.rab * _Specular.rgb * pow(max(0,dot(reflectDir,viewDir)),_Gloss);// 半角向量float3 _half = normalize(mul(lightDir + viewDir,0.5));      // Blinn-Phong 模型公式高光反射计算//float3 specular = _LightColor0.rab * _Specular.rgb * pow(max(0,dot(_half,normal)),_Gloss);   o.color = specular;return o;   }fixed4 frag (v2f i) : SV_Target{float4 color = float4(i.color,1);return color;}ENDCG}}
}

逐片元:

Shader "Unlit/004"
{Properties{_Specular ("_Specular",Color) = (1,1,1,1)// 高光反射值_Gloss ("_Gloss",range(1,256)) = 5}SubShader{Pass{CGPROGRAM#pragma vertex vert#pragma fragment frag#include "UnityCG.cginc"#include "Lighting.cginc"float4 _Specular;half _Gloss;struct v2v{float4 vertex : POSITION;float3 normal : NORMAL;};struct v2f{float4 vertex : POSITION;float3 normal : TEXCOORD0;float3 worldPos : TEXCOORD1;};v2f vert (v2v v){v2f o;// 将对象空间中的点变换到齐次坐标中的摄像机裁剪空间o.vertex = UnityObjectToClipPos(v.vertex);o.normal = UnityObjectToWorldNormal(v.normal);o.worldPos = UnityObjectToWorldDir(v.vertex);return o;   }fixed4 frag (v2f i) : SV_Target{float3 viewDir = normalize(_WorldSpaceCameraPos.xyz - i.worldPos);float3 reflectDir = normalize(mul(i.normal , 2) - _WorldSpaceLightPos0.xyz);// Phong 模型公式高光反射计算float3 specular = _LightColor0.rgb * _Specular.rgb * pow(max(0,dot(reflectDir,viewDir)),_Gloss);// 半角向量float3 _half = normalize(mul(normalize(_WorldSpaceLightPos0.xyz) + viewDir,0.5));      // Blinn-Phong 模型公式高光反射计算//float3 specular = _LightColor0.rab * _Specular.rgb * pow(max(0,dot(_half,i.normal)),_Gloss);   return float4(specular,1);}ENDCG}}
}

看下效果 左边是逐顶点,右边是逐片源

phong 模型:

 Blinn-Phong 模型:

 可以看到逐顶点渲染和逐像素渲染的区别:逐片元更加细腻

这篇关于Unity Shader - 高光反射(Phong、Blinn-Phong)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



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

相关文章

【Unity Shader】片段着色器(Fragment Shader)的概念及其使用方法

在Unity和图形编程中,片段着色器(Fragment Shader)是渲染管线中的一个阶段,负责计算屏幕上每个像素(片段)的颜色和特性。片段着色器通常在顶点着色器和任何几何处理之后运行,是决定最终像素颜色的关键步骤。 Fragment Shader的概念: 像素处理:片段着色器处理经过顶点着色器和几何着色器处理后,映射到屏幕空间的像素。颜色计算:它计算每个像素的颜色值,这可能包括纹理采样、光

【Unity Shader】Alpha Blend(Alpha混合)的概念及其使用示例

在Unity和图形编程中,Alpha Blend(也称为Alpha混合)是一种用于处理像素透明度的技术。它允许像素与背景像素融合,从而实现透明或半透明的效果。Alpha Blend在渲染具有透明度的物体(如窗户、玻璃、水、雾等)时非常重要。 Alpha Blend的概念: Alpha值:Alpha值是一个介于0(完全透明)和1(完全不透明)的数值,用于表示像素的透明度。混合模式:Alpha B

shader language学习(1)——shader language简介背景

shader language,称为着色语言,shade在英语是阴影、颜色深浅的意思。shader language基于物体本身属性和光照条件,计算美格橡塑的颜色值。 实际上这种解释具有明显的时代局限性,在GPU编程发展的早期,shader language的提出目标是加强对图形处理算法的控制,所以对该语言的定义也针对于此。但随着技术的进步,目前的shader language早已经用于通用计算

Unity Meta Quest 开发:关闭 MR 应用的安全边界

社区链接: SpatialXR社区:完整课程、项目下载、项目孵化宣发、答疑、投融资、专属圈子 📕教程说明 这期教程我将介绍如何在应用中关闭 Quest 系统的安全边界。 视频讲解: https://www.bilibili.com/video/BV1Gm42157Zi 在 Unity 中导入 Meta XR SDK,进行环境配置后,打开 Assets > Plugins > An

Unity 字体创建时候容易导致字体文件不正确的一种情况

上面得到了两种字体格式,一种是TextMeshPro的,另一种是Unity UI系统中默认使用的字体资源。其原因是创建的位置不同导致的。 1.下面是TextMeshPro字体创建的位置 2:下面是Unity UI系统中默认使用的字体资源

摄像头画面显示于unity场景

🐾 个人主页 🐾 🪧阿松爱睡觉,横竖醒不来 🏅你可以不屠龙,但不能不磨剑🗡 目录 一、前言二、UI画面三、显示于场景四、结语 一、前言 由于标题限制,这篇文章主要是讲在unity中调用摄像头,然后将摄像头捕捉到的画面显示到场景中,无论是UI画面还是场景中的某个物体上;至于应用的场景可以用于AR增强现实。 那么话不多说,直接开始今

unity开发 --------- NGUI (UITable)

unity开发 --------- NGUI UITable与UIGrid相似,都是实现自动排序的。但UIGrid的元素大小是由我们来指定的,而Table中的元素的大小是根据元素本身计算出来的。 UITable还保存了元素的顺序List<Transform>。每次重排序,都会更新此List。除了要计算元素的Bound和保存List外,其他基本与UIGrid一致。 unity开发 ---

unity开发 --------- NGUI (UIGrid)

unity开发 --------- NGUI  UIGrid可以实现多个gameobject自动排序。可以设定其排序方向、每个元素的宽度,高度等。 public Arrangement arrangement = Arrangement.Horizontal;public int maxPerLine = 0;public float cellWi

unity开发 --------- NGUI(Localization、UILocalize)

unity开发 --------- NGUI NGUI支持动态加载资源功能。比如语言选择:假如当前语言为中文,当将语言更改为英文时,所有UI上的文字也立即变成了英文。此功能是用Localization和UILocalize两个脚本配合完成的。 Localization中记录多种配置方案,当更改配置方案时,由Localization发送通知,通知各UILocalize更新。 NGU

unity开发 --------- NGUI (UIViewPort、UIDraggableCamera)

unity开发 --------- NGUI 前面提到一种实现ScrollView的方法:unity开发 --------- NGUI (UIDragPanelContents、UIDraggablePanel、UICenterOnChild、UIScollBar、SpringPanel) 但上面那种发放有一个缺陷!它要用到shader。也就是说,对于低端设备,就不能以上面那种方式实现拖