unity shader入门(二)语义,结构体,逐顶点光照
下为一个逐顶点漫反射光照shader
Shader "study/Chapter6/vertexShader"{
Properties{
_Diffuse("Diffuse",Color)=(1, 1, 1, 1)//材质的漫反射属性
//声明一个Color类型的属性
}
SubShader{
Pass{
Tags{"LightMode"="ForwardBase"}
CGPROGRAM
#pragma vertex vert
#pragma fragment frag
//unity的内置文件,为了可以使用unity的一些内置变量,如后面的——LightColor0
#include "Lighting.cginc"
//匹配属性的变量,关于属性和变量的匹配,下面有
fixed4 _Diffuse;
//顶点着色器输入结构体,结构体下面有
struct a2v{
float4 vertex:POSITION;//存储模型顶点
float3 normal:NORMAL; //存储模型顶点法线
};
//顶点着色器输出结构体,同时也是片元着色器输入结构体
struct v2f{
float4 pos:SV_POSITION;
fixed3 color:COLOR;//将顶点着色器计算的光照颜色传递给片元着色器
};
//顶点着色器
v2f vert(a2v v){
v2f o;
//将顶点从模型空间转化到裁剪空间
o.pos=UnityObjectToClipPos(v.vertex);
//获取外部项,通过unity内置函数UNITY_LIGHTMODEL_AMBIENT获取环境光部分
fixed3 ambient=UNITY_LIGHTMODEL_AMBIENT.xyz;
//将法线从模型空间转化到世界空间
fixed3 worldNormal=normalize(mul(v.normal,(float3x3)unity_WorldToObject));
//光源方向,_WorldSpaceLightPos0假设场景中只有一个平行光源才能得到正确方向
fixed3 worldLight=normalize(_WorldSpaceLightPos0.xyz);
//_LightColor0为unity内置变量访问该Pass处理的光源的颜色和强度信息
//下面给出漫反射计算公式
fixed3 diffuse=_LightColor0.rgb*_Diffuse.rgb*saturate(dot(worldNormal,worldLight));
o.color=ambient+diffuse;
return o;
}
//片元着色器
fixed4 frag(v2f i):SV_TARGET{
return fixed4(i.color,1.0);
}
ENDCG
}
}
//把这个unity shader的回调设置为内置的Diffuse
FallBack "Diffuse"
}
首先下边是Unity支持的语义
现在来看看顶点输入结构体
struct a2v{
float4 vertex:POSITION;//存储模型顶点
float3 normal:NORMAL; //存储模型顶点法线
};
这个叫a2v的结构体包含了顶点着色器需要的模型数据,a2v表示application to vertex shader,把数据从应用阶段传递到顶点着色器中
一个结构体的格式如下
struct structname{
Type(数据类型) Name(变量名):Semantic(语义);
Type(数据类型) Name(变量名):Semantic(语义);
Type(数据类型) Name(变量名):Semantic(语义);
......
};
我们一般是从顶点着色器输出一些数据比如模型的法线,坐标纹理等给片元着色器就需要通过上述代码中的v2f结构体来实现两者通信。
顶点着色器是逐顶点调用的,片元着色器是逐片元调用的。片元着色器实际上是吧顶点着色器的输出进行差值后得到的结果。
在顶点着色器中做的就是把顶点着色器输入结构体作为(上为a2v)中顶点的一些信息经过一顿操作转换为v2f(就是个函数),然后将这个v2f丢到片元着色器中再
一顿操作,然后输出一个颜色 下面是属性与变量匹配关系
比如你在properties中声明了一个2D属性,在CG中你就要声明一个sample2D变量来匹配这个2D属性,声明的属性名必须与变量名一致,
比如上面都是_Diffuse。取值范围上fixed<half<float,在移动端平台上需要注意下。 我们看到的光=环境光/自发光+漫反射+高光反射
漫反射计算公式
漫反射=(光源颜色*材质的漫反射颜色)max(0,表面法线*光源的单位矢量) 为了防止法线和光源方向点乘的结果为负值,需要使用去最大值函数
将其截取到0,以防止物体被从后面的光源照亮。
得到的材质球效果如下
unity shader入门(二)语义,结构体,逐顶点光照的更多相关文章
- unity shader入门(三)逐像素光照,Blinn-Phong模型
与上篇逐顶点光照很像,只是改为在片元着色器中计算光照,下为逐像素光照shader Shader "study/Chapter6/PixelShader"{ Properties{ ...
- Unity Shader入门精要学习笔记 - 第7章 基础纹理
转自 冯乐乐的 <Unity Shader 入门精要> 纹理最初的目的就是使用一张图片来控制模型的外观.使用纹理映射技术,我们可以把一张图“黏”在模型表面,逐纹素地控制模型的颜色. 在美术 ...
- Unity Shader入门精要学习笔记 - 第6章 开始 Unity 中的基础光照
转自冯乐乐的<Unity Shader入门精要> 通常来讲,我们要模拟真实的光照环境来生成一张图像,需要考虑3种物理现象. 首先,光线从光源中被发射出来. 然后,光线和场景中的一些物体相交 ...
- Unity Shader入门精要学习笔记 - 第4章 学习 Shader 所需的数学基础
摘录自 冯乐乐的<Unity Shader入门精要> 笛卡尔坐标系 1)二维笛卡尔坐标系 在游戏制作中,我们使用的数学绝大部分都是计算位置.距离.角度等变量.而这些计算大部分都是在笛卡尔坐 ...
- unity shader 入门
1.一个简单的顶点/片元着色器基本结构 Shader "Unity Shaders Book/Chapter 5/Simple Shader" { } SubShader { Pa ...
- Unity Shader 入门精要学习 (冯乐乐 著)
第1篇 基础篇 第1章 欢迎来到Shader的世界 第2章 渲染流水线 第3章 Unity Shader 基础 第4章 学习Shader所需的数学基础 第2篇 初级篇 第5章 开始Unity Shad ...
- Unity Shader入门精要学习笔记 - 第17章 Unity的表面着色器探秘
转自 冯乐乐的<Unity Shader 入门精要> 2010年的Unity 3 中,Surface Shader 出现了. 表面着色器的一个例子. 我们先做如下准备工作. 1)新建一个场 ...
- Unity Shader入门精要学习笔记 - 第12章 屏幕后处理效果
建立一个基本的屏幕后处理脚本系统 屏幕后处理,顾名思义,通常指的是在渲染完整个场景得到屏幕图像后,再对这个图像进行一系列操作,实现各种屏幕特效.使用这种技术,可以为游戏画面添加更多艺术效果,例如景深. ...
- Unity Shader入门精要学习笔记 - 第9章 更复杂的光照
转载自 冯乐乐的<Unity Shader入门精要> Unity 的渲染路径 在Unity里,渲染路径决定了光照是如何应该到Unity Shader 中的.因此,如果要和光源打交道,我们需 ...
- Unity Shader入门精要学习笔记 - 第8章 透明效果
转载自 冯乐乐的 <Unity Shader入门精要> 透明是游戏中经常要使用的一种效果.在实时渲染中要实现透明效果,通常会在渲染模型时控制它的透明通道.当开启透明混合后,当一个物体被渲染 ...
随机推荐
- Python之快速排序代码
def quicksort(array): less = [] greater = [] if len(array) <= 1: return array pivot = array.pop() ...
- redis创建集群至少需要几个节点?至少需要几个master节点?
描述: 这也算个思考吧,通过redis-trib.rb可创建redis集群,然后通过--replicas后面接的数字,表示1个主节点对应几个从节点,那么我就做了如下的测试,想要达到的效果就是有6个节点 ...
- pipeline结合jacoco获取自动化测试代码覆盖率
1下载jacoco,并上传至服务器:https://www.eclemma.org/jacoco/ 2.应用服务tomcat的catalina.sh增加jacocoagent #JAVA_OPTS=& ...
- syncronizationcontext
FormDesign.cs 增加变量定义 public string testName { get; set; } TaskWrapper.cs string tmpTest = &qu ...
- EasyNVR摄像机网页无插件直播方案H5前端构建之:使用BootstrapPagination以分页形式展示数据信息
背景介绍 EasyNVR核心在于摄像机的音视频流的获取.转换.转码与高性能分发,同时同步完成对实时直播流的录像存储,在客户端(PC浏览器.Android.iOS.微信)进行录像文件的检索.回放和下载. ...
- 大数据开发工程师面试《一》Shopee虾皮技术面
一.项目问题 1 做了哪些项目2 使用什么技术3 哪个是你主导的项目,一共开发多少个接口,项目多长时间,数据库有多少个表 二.技术问题 1 用自己擅长的语言实现非递归单链表反转 现场手写2 Hadoo ...
- Unable to resolve service for type 'Microsoft.Extensions.Logging.ILogger' while attempting to activate 'xxxxx.Controllers.xxxxController'.
Unable to resolve service for type 'Microsoft.Extensions.Logging.ILogger' while attempting to activa ...
- cookielib模块 for python3
python2 可以直接安装cookielib模块 而py3却不能安装 故需要安装http模块 举例子: from http import cookiejar cookie = cookiejar.C ...
- WebService 与WebAPI的差异性
对于 WebService和 Web API这两个概念, WebService是一个广义的概念,既 包括采用 RPC的 SOAP WebService,也包括直接建立在 Web 上的非 SOAP We ...
- 有关ajax跨域问题
写在前面 JQuery ajax支持get方式的跨域,采用了jsonp来完成.完成跨域请求的有两种方式实现.一种是使用Jquery ajax最底层的Api实现跨域的请求,而另一种则是JQuery aj ...