MarmosetInput.cginc:
Input结构定义:
struct Input
{
#if defined(MARMO_PACKED_UV) || defined(MARMO_PACKED_VERTEX_OCCLUSION) || defined(MARMO_PACKED_VERTEX_COLOR)
float4 texcoord;
#else
float2 texcoord;
#endif float3 worldNormal; #if defined(MARMO_SPECULAR_DIRECT) || defined(MARMO_SPECULAR_IBL)
float3 viewDir;
#endif #if defined(MARMO_COMPUTE_WORLD_POS)
#ifdef MARMO_U5_WORLD_POS
float3 worldPos; //this is free in Unity 5
#endif
#else
float4 worldP; //lets write our own
#endif
#if defined(MARMO_VERTEX_COLOR) || defined(MARMO_VERTEX_LAYER_MASK)
half4 color : COLOR;
#elif defined(MARMO_VERTEX_OCCLUSION)
half2 color : COLOR;
#endif #ifdef MARMO_DIFFUSE_VERTEX_IBL
float3 vertexIBL;
#endif
INTERNAL_DATA
};

Output结构定义:

struct MarmosetOutput
{
half3 Albedo; //diffuse map RGB
half Alpha; //diffuse map A
half3 Normal; //world-space normal
half3 Emission; //contains IBL contribution
half Specular; //specular exponent (required by Unity)
#ifdef MARMO_SPECULAR_DIRECT
half3 SpecularRGB; //specular mask
#endif
};

Unity自带的Output结构定义:

struct SurfaceOutput
{
fixed3 Albedo;
fixed3 Normal;
fixed3 Emission;
half Specular;
fixed Gloss;
fixed Alpha;
}; // Metallic workflow
struct SurfaceOutputStandard
{
fixed3 Albedo; // base (diffuse or specular) color
fixed3 Normal; // tangent space normal, if written
half3 Emission;
half Metallic; // 0=non-metal, 1=metal
// Smoothness is the user facing name, it should be perceptual smoothness but user should not have to deal with it.
// Everywhere in the code you meet smoothness it is perceptual smoothness
half Smoothness; // 0=rough, 1=smooth
half Occlusion; // occlusion (default 1)
fixed Alpha; // alpha for transparencies
}; // Specular workflow
struct SurfaceOutputStandardSpecular
{
fixed3 Albedo; // diffuse color
fixed3 Specular; // specular color
fixed3 Normal; // tangent space normal, if written
half3 Emission;
half Smoothness; // 0=rough, 1=smooth
half Occlusion; // occlusion (default 1)
fixed Alpha; // alpha for transparencies
};

MarmosetDirect.cginc:
直接光照的主要代码,去掉deferred lighting相关的代码。
#ifndef MARMOSET_DIRECT_CGINC
#define MARMOSET_DIRECT_CGINC
// Core
inline float3 wrapLighting(float DP, float3 scatter)
{
scatter *= 0.5;
float3 integral = float3(1.0,1.0,1.0)-scatter;
float3 light = saturate(DP * integral + scatter);
float shadow = (DP*0.5+0.5);
shadow *= shadow;
return light * integral * shadow;
}
// NOTE: some intricacy in shader compiler on some GLES2.0 platforms (iOS) needs 'viewDir' & 'h'
// to be mediump instead of lowp, otherwise specular highlight becomes too bright.
inline half4 marmosetLighting (MarmosetOutput s, half3 viewDir, half3 lightDir, half3 lightColor)
{
half4 frag = half4(0.0,0.0,0.0,s.Alpha);
#if defined(MARMO_DIFFUSE_DIRECT) || defined(MARMO_SPECULAR_DIRECT)
half3 L = lightDir;
half3 N = s.Normal;
#ifdef MARMO_HQ
L = normalize(L);
#endif
#endif #ifdef MARMO_DIFFUSE_DIRECT
half dp = saturate(dot(N,L)); #ifdef MARMO_DIFFUSE_SCATTER
float4 scatter = _Scatter * _ScatterColor;
half3 diff = wrapLighting(dp, scatter.rgb);
diff *= 2.0 * s.Albedo.rgb; //*2.0 to match Unity
#else
half3 diff = (2.0 * dp) * s.Albedo.rgb; //*2.0 to match Unity
#endif
frag.rgb = diff * lightColor;
#endif #ifdef MARMO_SPECULAR_DIRECT
half3 H = normalize(viewDir+L);
float specRefl = saturate(dot(N,H));
half3 spec = pow(specRefl, s.Specular*512.0);
#ifdef MARMO_HQ
//self-shadowing blinn
#ifdef MARMO_DIFFUSE_DIRECT
spec *= saturate(10.0*dp);
#else
spec *= saturate(10.0*dot(N,L));
#endif
#endif
spec *= lightColor;
frag.rgb += (0.5 * spec) * s.SpecularRGB; //*0.5 to match Unity
#endif
return frag;
}
//forward lighting
inline half4 LightingMarmosetDirect( MarmosetOutput s, half3 lightDir, half3 viewDir, half atten )
{
return marmosetLighting( s, viewDir, lightDir, _LightColor0 * atten);
}
inline half4 LightingMarmosetDirect( MarmosetOutput s, half3 viewDir, UnityGI gi )
{
fixed4 c;
c = marmosetLighting (s, viewDir, gi.light.dir, gi.light.color); #ifdef UNITY_LIGHT_FUNCTION_APPLY_INDIRECT
c.rgb += s.Albedo * gi.indirect.diffuse;
#endif
return c;
}
inline void LightingMarmosetDirect_GI (MarmosetOutput s, UnityGIInput giInput, inout UnityGI gi)
{
gi = UnityGlobalIllumination(giInput, 1.0, s.Normal);
}
#endif

MarmosetSurf.cginc:
旧版本的surf代码:
#ifndef MARMOSET_SURF_CGINC
#define MARMOSET_SURF_CGINC
void MarmosetSurf(Input IN, inout MarmosetOutput OUT)
{
#define uv_diff IN.uv_MainTex
#define uv_spec IN.uv_MainTex
#define uv_bump IN.uv_MainTex
#define uv_glow IN.uv_MainTex
//DIFFUSE
#if defined(MARMO_DIFFUSE_DIRECT) || defined(MARMO_DIFFUSE_IBL)
half4 diff = tex2D( _MainTex, uv_diff );
diff *= _Color;
//camera exposure is built into OUT.Albedo
diff.rgb *= _ExposureIBL.w;
OUT.Albedo = diff.rgb;
OUT.Alpha = diff.a;
#ifdef MARMO_PREMULT_ALPHA
OUT.Albedo *= diff.a;
#endif
#else
OUT.Albedo = half3(0.0,0.0,0.0);
OUT.Alpha = 1.0;
#endif //NORMALS
#ifdef MARMO_NORMALMAP
float3 N = UnpackNormal(tex2D(_BumpMap,uv_bump));
#ifdef MARMO_HQ
N = normalize(N);
#endif
OUT.Normal = N; //N is in tangent-space
#else
//OUT.Normal is not modified when not normalmapping
float3 N = OUT.Normal; //N is in world-space
#ifdef MARMO_HQ
N = normalize(N);
#endif
#endif //SPECULAR
#if defined(MARMO_SPECULAR_DIRECT) || defined(MARMO_SPECULAR_IBL)
half4 spec = tex2D(_SpecTex, uv_spec);
float3 E = IN.viewDir; //E is in whatever space N is
#ifdef MARMO_HQ
E = normalize(E);
half fresnel = splineFresnel(N, E, _SpecInt, _Fresnel);
#else
half fresnel = fastFresnel(N, E, _SpecInt, _Fresnel);
#endif //camera exposure is built into OUT.Specular
spec.rgb *= _SpecColor.rgb * fresnel * _ExposureIBL.w;
OUT.Specular = spec.rgb;
half glossLod = glossLOD(spec.a, _Shininess);
OUT.Gloss = glossExponent(glossLod);
//conserve energy by dividing out specular integral
OUT.Specular *= specEnergyScalar(OUT.Gloss);
#endif //SPECULAR IBL
#ifdef MARMO_SPECULAR_IBL
#ifdef MARMO_NORMALMAP
float3 R = WorldReflectionVector(IN, OUT.Normal);
#else
float3 R = IN.worldRefl;
#endif
#ifdef MARMO_SKY_ROTATION
R = mulVec3(_SkyMatrix,R); //per-fragment matrix multiply, expensive
#endif
#ifdef MARMO_MIP_GLOSS
half3 specIBL = glossCubeLookup(_SpecCubeIBL, R, glossLod);
#else
half3 specIBL = specCubeLookup(_SpecCubeIBL, R)*spec.a;
#endif
OUT.Emission += specIBL.rgb * spec.rgb * _ExposureIBL.y;
#endif //DIFFUSE IBL
#ifdef MARMO_DIFFUSE_IBL
N = WorldNormalVector(IN,N); //N is in world-space
#ifdef MARMO_SKY_ROTATION
N = mulVec3(_SkyMatrix,N); //per-fragment matrix multiply, expensive
#endif
half3 diffIBL = diffCubeLookup(_DiffCubeIBL, N);
OUT.Emission += diffIBL * diff.rgb * _ExposureIBL.x;
#endif //GLOW
#ifdef MARMO_GLOW
half4 glow = tex2D(_Illum, uv_glow);
glow.rgb *= _GlowColor.rgb;
glow.rgb *= _GlowStrength;
glow.a *= _EmissionLM;
glow.rgb += OUT.Albedo * glow.a;
OUT.Emission += glow.rgb * _ExposureIBL.w;
#endif
}
#endif

IBL实现的两个关键函数:

half3 diffCubeLookup(samplerCUBE diffCube, float3 worldNormal)
{
half4 diff = texCUBE(diffCube, worldNormal);
return fromRGBM(diff);
}
half3 specCubeLookup(samplerCUBE specCube, float3 worldRefl)
{
half4 spec = texCUBE(specCube, worldRefl);
return fromRGBM(spec);
}

    IBL.diffuse使用world normal查询,IBL.specular使用world reflection查询。

宏定义解析:
MARMO_DIFFUSE_SPECULAR_COMBINED 
    Diffuse/Specular合并
    _MainTex.RGBA = RGB表示Diffuse,A表示Specular强度和Gloss
MARMO_PACKED_UV
    UV打包
#ifdef MARMO_PACKED_UV
o.texcoord.zw = v.texcoord1.xy;
#endif

MARMO_PACKED_VERTEX_COLOR
    顶点色打包
#ifdef MARMO_PACKED_VERTEX_COLOR
o.texcoord.zw = v.color.rg;
o.worldP.w = v.color.b;
#endif

Skyshop.代码解析的更多相关文章

  1. VBA常用代码解析

    031 删除工作表中的空行 如果需要删除工作表中所有的空行,可以使用下面的代码. Sub DelBlankRow() DimrRow As Long DimLRow As Long Dimi As L ...

  2. [nRF51822] 12、基础实验代码解析大全 · 实验19 - PWM

    一.PWM概述: PWM(Pulse Width Modulation):脉冲宽度调制技术,通过对一系列脉冲的宽度进行调制,来等效地获得所需要波形. PWM 的几个基本概念: 1) 占空比:占空比是指 ...

  3. [nRF51822] 11、基础实验代码解析大全 · 实验16 - 内部FLASH读写

     一.实验内容: 通过串口发送单个字符到NRF51822,NRF51822 接收到字符后将其写入到FLASH 的最后一页,之后将其读出并通过串口打印出数据. 二.nRF51822芯片内部flash知识 ...

  4. [nRF51822] 10、基础实验代码解析大全 · 实验15 - RTC

    一.实验内容: 配置NRF51822 的RTC0 的TICK 频率为8Hz,COMPARE0 匹配事件触发周期为3 秒,并使能了TICK 和COMPARE0 中断. TICK 中断中驱动指示灯D1 翻 ...

  5. [nRF51822] 9、基础实验代码解析大全 · 实验12 - ADC

    一.本实验ADC 配置 分辨率:10 位. 输入通道:5,即使用输入通道AIN5 检测电位器的电压. ADC 基准电压:1.2V. 二.NRF51822 ADC 管脚分布 NRF51822 的ADC ...

  6. java集合框架之java HashMap代码解析

     java集合框架之java HashMap代码解析 文章Java集合框架综述后,具体集合类的代码,首先以既熟悉又陌生的HashMap开始. 源自http://www.codeceo.com/arti ...

  7. Kakfa揭秘 Day8 DirectKafkaStream代码解析

    Kakfa揭秘 Day8 DirectKafkaStream代码解析 今天让我们进入SparkStreaming,看一下其中重要的Kafka模块DirectStream的具体实现. 构造Stream ...

  8. linux内存管理--slab及其代码解析

    Linux内核使用了源自于 Solaris 的一种方法,但是这种方法在嵌入式系统中已经使用了很长时间了,它是将内存作为对象按照大小进行分配,被称为slab高速缓存. 内存管理的目标是提供一种方法,为实 ...

  9. MYSQL常见出错mysql_errno()代码解析

    如题,今天遇到怎么一个问题, 在理论上代码是不会有问题的,但是还是报了如上的错误,把sql打印出來放到DB中却可以正常执行.真是郁闷,在百度里面 渡 了很久没有相关的解释,到时找到几个没有人回复的 & ...

随机推荐

  1. itestpdf

    itestpdf jar pdf

  2. scrapy 爬取视频

    利用FilesPipeline 下载视频 1.setting.py # 保存log信息的文件名 LOG_LEVEL = "INFO" # LOG_STDOUT = True # L ...

  3. Redis windows版本资源与安装

    这里提供一个windows版本的Redis百度云资源 链接: https://pan.baidu.com/s/19JY_d_J87n98OeAHK9qI4A 密码: d6dq 1,GitHub下载地址 ...

  4. 【Eureka篇三】Eureka如何管理服务调用(6)

    在Eureka Client启动时,将自身的服务的信息发送到Eureka Server.然后进行2调用当前服务器节点中的其他服务信息,保存到Eureka Client中.当服务间相互调用其它服务时,在 ...

  5. 舒服的MarkDown软件Mark Text

  6. Unity 插件宝典 (张忠喜 廖一庭 著)

    第1章 模型类插件 第2章 特效类插件 第3章 动画插件 第4章 编辑器插件 第5章 脚本类插件 第6章 GUI插件 第7章 Shaders插件 第8章 优化类插件 第9章 综合应用----卡通版赛车 ...

  7. mysql 实现经纬度排序查找功能

    需求如下: 商品有多个门店,用户使用App时需要查找附近门店的商品,商品要进行去重分页. 思路: 1.确认mysql自带经纬度查询函数可以使用. 2.该需求需要利用分组排序,取每个商品最近门店的商品i ...

  8. 初探云原生应用管理(二): 为什么你必须尽快转向 Helm v3

    系列介绍:这个系列是介绍如何用云原生技术来构建.测试.部署.和管理应用的内容专辑.做这个系列的初衷是为了推广云原生应用管理的最佳实践,以及传播开源标准和知识.在这个系列文章的开篇初探云原生应用管理(一 ...

  9. 使用 Xbox Game 录制桌面视频(录制音频)

    使用 Xbox Game 录制桌面视频(附带音频) 前言:可能自己音频输出的问题,一直无法用工具录制桌面的音频,而最后发现利用 Xbox Game 录制游戏视频的功能很好地解决我们的问题. 1)打开游 ...

  10. C# NuGet常用命令

    命令执行位置:工具=〉Nuget包管理器=〉程序包管理器控制台 一.安装 1.安装指定版本类库install-package <程序包名> -version <版本号> 2.安 ...