Unity中Shader反射环境

文章目录

  • 前言
  • 一、制作反射环境的两种办法
    • 法1:属性面板接收一个 Cubemap 作为反射环境
    • 法2:把环境烘焙成一张Cubemap
  • 二、在Unity中实现把环境烘焙成一张Cubemap
    • 1、先创建一个反射探针(可以直接创建,也可以空物体增加组件)
    • 2、计算得到模型顶点指向摄像头的 视线向量
    • 3、计算视线向量的反射向量
    • 4、对反射探针的Cubemap进行纹理采样
    • 5、对采样后的结果进行解码处理
  • 三、最终效果


前言

Unity中Shader的反射环境,本质就是把环境烘焙成一张Cubemap。

继续使用上一篇文章的代码测试:

  • Unity中Shader法线贴图(下)实现篇

我们修改一下,把Cubemap采样时,使用的 世界空间下的模型法线替换成法线贴图转化后的世界空间下的法线

在这里插入图片描述

可以看到物体反射的基础效果:

请添加图片描述


一、制作反射环境的两种办法

法1:属性面板接收一个 Cubemap 作为反射环境

  • Unity中Shader立方体纹理Cubemap

法2:把环境烘焙成一张Cubemap


二、在Unity中实现把环境烘焙成一张Cubemap

1、先创建一个反射探针(可以直接创建,也可以空物体增加组件)

在这里插入图片描述

在这里插入图片描述

反射探针中当前激活的CubeMap存储在unity_SpecCube0当中,必须要用UNITY_SAMPLE_TEXCUBE进行采样,然后需要对其进行解码

2、计算得到模型顶点指向摄像头的 视线向量

half3 worldView = normalize (UnityWorldSpaceViewDir (i.worldPos));

计算需要提前准备 世界空间下的模型顶点

3、计算视线向量的反射向量

half3 R = reflect (-worldView, N);
计算需要提前准备 世界空间下的模型法线

4、对反射探针的Cubemap进行纹理采样

half4 cubemap = UNITY_SAMPLE_TEXCUBE (unity_SpecCube0, R);

5、对采样后的结果进行解码处理

half3 skyColor = DecodeHDR (cubemap, unity_SpecCube0_HDR);


三、最终效果

请添加图片描述

最终代码:

//纹理的多级渐远 Mipmap
//纹理的环绕方式
//法线贴图
//反射环境
Shader "MyShader/P2_1_9"
{Properties{_MainTex ("Texture", 2D) = "white" {}[KeywordEnum (Repeat,Clamp)]_WrapMode("WrapMode",int) = 0[IntRange]_Mipmap ("Mipmap",Range(0,10)) = 0//法线贴图[Normal]_NormalTex("NormalTex",2D) = "bump" {}//在属性面板定义立方体纹理_CubeMap("CubeMap",Cube) = "white" {}}SubShader{Tags { "RenderType"="Opaque" }LOD 100Pass{CGPROGRAM#pragma vertex vert#pragma fragment frag#pragma shader_feature _WRAPMODE_REPEAT _WRAPMODE_CLAMP#include "UnityCG.cginc"struct appdata{float4 vertex : POSITION;float2 uv : TEXCOORD0;half3 normal : NORMAL;float4 tangent : TANGENT;};struct v2f{float2 uv : TEXCOORD0;float4 vertex : SV_POSITION;float3 localPos : TEXCOORD1;float3 worldPos : TEXCOORD2;half3 worldNormal : TEXCOORD3;float3 tSpace0:TEXCOORD4;float3 tSpace1:TEXCOORD5;float3 tSpace2:TEXCOORD6;};sampler2D _MainTex;float4 _MainTex_ST;half _Mipmap;samplerCUBE _CubeMap;sampler2D _NormalTex;v2f vert (appdata v){v2f o;o.vertex = UnityObjectToClipPos(v.vertex);o.uv = TRANSFORM_TEX(v.uv, _MainTex);o.localPos = v.vertex.xyz;o.worldPos = mul(unity_ObjectToWorld,v.vertex);o.worldNormal = UnityObjectToWorldNormal(v.normal);half3 worldTangent = UnityObjectToWorldDir(v.tangent);//v.tangent.w:DCC软件中顶点UV值中的V值翻转情况.//unity_WorldTransformParams.w:模型缩放是否有奇数负值. half tangentSign = v.tangent.w * unity_WorldTransformParams.w;half3 worldBinormal = cross(o.worldNormal, worldTangent) * tangentSign;o.tSpace0 = float3(worldTangent.x,worldBinormal.x,o.worldNormal.x);o.tSpace1 = float3(worldTangent.y,worldBinormal.y,o.worldNormal.y);o.tSpace2 = float3(worldTangent.z,worldBinormal.z,o.worldNormal.z);return o;}fixed4 frag (v2f i) : SV_Target{//WrapMode#if _WRAPMODE_REPEATi.uv = frac(i.uv);#elif _WRAPMODE_CLAMP//法一://i.uv = clamp(i.uv,0,1);//法二:i.uv = saturate(i.uv);#endiffloat4 uvMipmap = fixed4(i.uv,0,_Mipmap);fixed4 col = tex2Dlod(_MainTex, uvMipmap);//法线纹理fixed3 normalTex = UnpackNormal(tex2D(_NormalTex,i.uv));//max(0,dot(N,L))fixed3 N1 = normalize(normalTex);fixed3 L = _WorldSpaceLightPos0.xyz;//return fixed4(normalTex,1);//计算出世界空间下的法线half3 worldNormal = half3(dot(i.tSpace0,normalTex),dot(i.tSpace1,normalTex),dot(i.tSpace2,normalTex));//return max(0,dot(worldNormal,L));//CubeMap//fixed4 cubemap = texCUBE(_CubeMap,i.localPos);//V,N,Rfixed3 V = normalize(i.worldPos - _WorldSpaceCameraPos);fixed3 N = normalize(worldNormal);fixed3 R = reflect(V,N);fixed4 cubemap = texCUBE(_CubeMap,R);//return cubemap;//反射探针中当前激活的CubeMap存储在unity_SpecCube0当中,必须要用UNITY_SAMPLE_TEXCUBE进行采样,然后需要对其进行解码//half3 worldView = normalize (UnityWorldSpaceViewDir (i.worldPos));//half3 R = reflect (-worldView, N);cubemap = UNITY_SAMPLE_TEXCUBE (unity_SpecCube0, R);half3 skyColor = DecodeHDR (cubemap, unity_SpecCube0_HDR);return fixed4(skyColor,1);return col;}ENDCG}}
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/153863.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【Linux】:进程间通信和日志模拟

进程间通信 一.基本概念二.简单的通信-管道(匿名管道)1.建立通信信道2.通信接口 三.命名管道三.模拟命名管道通信(加上日志)1.完整代码2.基本使用 一.基本概念 是什么 两个或多个进程实现数据层面的交互。 因为进程独立性的存在,导致进程间…

广度优先算法(BFS)

广度优先算法(Breadth-First Search)是在图和树领域的搜索方法,其核心思想是从一个起始点开始,访问其所有的临近节点,然后再按照相同的方式访问这些临近节点的节点,这种访问方式类似涟漪泛起,一…

HINSTANCE是什么?

HINSTANCE 就是 HMODULE:

队列OJ--循环队列

目录 题目链接:622. 设计循环队列 - 力扣(LeetCode)​​​​​ 题解: ​编辑 代码实现: 完整代码: 题目链接:622. 设计循环队列 - 力扣(LeetCode)​​​​​ 题解&#x…

jenkins传参给robotframework

在做自动化的时候,需要使用jenkins传参给rf,rf根据传来的变量运行,在将变量传递给py脚本文件。特此记录。 一、配置jenkins 构建的命令使用如下格式即可(注意空格): cd D:\xxx\test call pybot --variabl…

砖家测评:腾讯云标准型S5服务器和s6性能差异和租用价格

腾讯云服务器CVM标准型S5和S6有什么区别?都是标准型云服务器,标准型S5是次新一代云服务器规格,标准型S6是最新一代的云服务器,S6实例的CPU处理器主频性能要高于S5实例,同CPU内存配置下的标准型S6实例要比S5实例性能更好…

视频剪辑技巧:批量剪辑新篇章,AI智剪来领航

随着数字媒体的飞速发展,视频剪辑已经成为一项重要的工作。在繁忙的工作中,如何高效、准确地完成批量剪辑是一项具有挑战性的任务。近年来,AI智剪的出现为视频剪辑工作带来了新的解决方案,引领着批量剪辑的新篇章。在AI智剪的帮助…

为了摆脱 Android ,亚马逊开发基于Linux的操作系统

导读亚马逊一直在开发一种新的操作系统 —— 内部代号为 “Vega”,以便在 Fire TV、智能显示器和其他联网设备上取代 Android 系统。 亚马逊一直在开发一种新的操作系统 —— 内部代号为 “Vega”,以便在 Fire TV、智能显示器和其他联网设备上取代 Andr…

终于有人把数据资产入表知识地图总结出来了,轻松看懂

在当前数字化的浪潮下,数据已经成为劳动、土地、知识、技术以后的第五大生产要素,“数据就是资源”已成为共识。如今数据资产“入表”已成定局,数据资产化迫在眉睫。 2023年8月21日,财政部正式印发《企业数据资源相关会计处理暂行…

什么样的企业可以使用免费版的CRM?

市面上大部分的免费CRM不需要付费即可使用,但是对于使用人数和功能进行了部分限制。下面我们就来说说,免费CRM的适用对象是谁? 1、初创/小微企业 这种小微企业没有太多的资金,也没有复杂的客户管理需求,仅仅需要一款…

生产环境_移动目标轨迹压缩应用和算法处理-Douglas-Peucker轨迹压缩算法

场景: 我目前设计到的场景是:以路面上行驶的汽车为例,即在地图应用中,对GPS轨迹数据进行压缩,减少数据传输和存储开销,因为轨迹点太频繁了,占用空间太大,运行节点太慢了&#xff0c…

姿态估计 手势动作实时识别项目(基于mediapipe、keras进行实现)

姿态估计 手势动作实时识别项目(基于mediapipe、keras进行实现) 0、功能展示1、项目原理介绍2、数据集采集脚本3、将采集到的动作数据集利用mediapipe库检测手部关键点信息,转换成数据信息保存到本地4、训练一个效果一般的随机森林分类器5、使用Kreas训练一个效果好点的全连…

提高软件测试覆盖率的5个重点

软件测试覆盖率是软件测试中的一个重要指标,它有利于保障软件质量、提高软件可靠性和可维护性。软件测试覆盖率能够发现并修复代码缺陷,确保代码的正确性,提高软件的稳定性,降低成本和风险。 因此进一步提高软件测试覆盖率对于软件…

Oauth2认证及Spring Security Oauth2授权码模式

Oauth2认证 Oauth2简介 简介 第三方认证技术方案最主要是解决认证协议的通用标准问题,因为要实现跨系统认证,各系统之间要遵循一定的接口协议。 OAUTH协议为用户资源的授权提供了一个安全的、开放而又简易的标准。同时,任何第三方都可以使…

ICCV 23丨3D-VisTA:用于 3D 视觉和文本对齐的预训练Transformer

来源:投稿 作者:橡皮 编辑:学姐 论文链接:https://arxiv.org/abs/2308.04352 开源代码:http://3d-vista.github.io 摘要: 3D视觉语言标定(3D-VL)是一个新兴领域,旨在将…

centos7安装mysql8

打开Mysql下载页面 https://downloads.mysql.com/archives/community/ 选择版本号: centos选择Red Hat版本,复制地址 复制地址后,链接ssh,添加储存库 yum install 粘贴地址; yum install https://downloads.mysql…

人工智能基础_机器学习044_使用逻辑回归模型计算逻辑回归概率_以及_逻辑回归代码实现与手动计算概率对比---人工智能工作笔记0084

上面我们已经把逻辑回归的公式,以及,公式对应的图形都画画出来了,然后我们再来看看 如何用代码实现 可以看到上面是代码,咱们自己去写一下 import numpy as np from sklearn.linear_model import LogistieRegression from sklearn import datasets # 训练数据和测试数据拆分…

人工智能时代下的程序员核心竞争力:构建专属护城河

选题建议:《人工智能时代下的程序员核心竞争力:构建你的护城河》 大纲: I. 引言 A. 人工智能时代的发展趋势B. 程序员面临的挑战与机遇 I. 引言 A. 人工智能时代的发展趋势 随着科技的飞速进步,我们已经踏入了一个日新月异的人工…

Leetcode—2216.美化数组的最少删除数【中等】

2023每日刷题&#xff08;三十六&#xff09; Leetcode—2216.美化数组的最少删除数 实现代码 int minDeletion(int* nums, int numsSize) {int last nums[0], flag 1, ans 0;for(int i 1; i < numsSize; i) {if(flag) { // 前一个下标为偶数if(nums[i] last) {…

Linux C 线程

线程 概述线程和进程的异同如何选择使用进程还是线程 函数获取进程自身ID  pthread_self创建线程  pthread_create退出线程  pthread_exit线程等待  pthread_join 四种线程模型1 &#xff09;单线程2 &#xff09;单线程3 &#xff09;双线程4 &#xff09;三线程 概述…