Unity3d 如何将曲面着色器转换为Unity中的顶点/片段代码?
我想知道如何将此曲面着色器代码转换为顶点/片段杂注:Unity3d 如何将曲面着色器转换为Unity中的顶点/片段代码?,unity3d,shader,fragment-shader,vertex-shader,Unity3d,Shader,Fragment Shader,Vertex Shader,我想知道如何将此曲面着色器代码转换为顶点/片段杂注: Shader "Custom/Diamond Opaque Test" { Properties { _Color ("Main Color", Color) = (1,1,1,1) _SpecColor ("Specular Color", Color) = (0.5,0.5,0.5,1) _Shininess ("Shininess", Range (0.01, 1)) = 0.07
Shader "Custom/Diamond Opaque Test" {
Properties {
_Color ("Main Color", Color) = (1,1,1,1)
_SpecColor ("Specular Color", Color) = (0.5,0.5,0.5,1)
_Shininess ("Shininess", Range (0.01, 1)) = 0.078125
_RimPower ("Rim Power", Range(0,8.0)) = 3.0
_ReflectColor ("Reflection Color", Color) = (1,1,1,0.5)
[NoScaleOffset] _Cube ("Cubemap", CUBE) = "" {}
}
SubShader {
CGPROGRAM
#pragma surface surf BlinnPhong
struct Input {
float3 worldRefl;
float3 viewDir;
};
samplerCUBE _Cube;
fixed4 _Color;
fixed4 _ReflectColor;
half _Shininess;
half _RimPower;
void surf (Input IN, inout SurfaceOutput o) {
o.Albedo = _Color.rgb;
o.Gloss = _Color.a;
o.Specular = _Shininess;
half rim = saturate(dot (normalize(IN.viewDir), o.Normal));
o.Emission = texCUBE (_Cube, IN.worldRefl).rgb * _ReflectColor.rgb * pow(rim,_RimPower);;
}
ENDCG
}
FallBack "Mobile/Diffuse"
}
上面的着色器代码是下图左侧的红色宝石:
我的目标是看起来像右边的宝石。在此过程中,我面临着一些挑战。左边的宝石是不透明的,可以接受阴影。右边的宝石正面透明,背面透明。但是,这不接受阴影。我必须在let Blinnfong上制作宝石,这样它才能投射和接收阴影
是否可以为正面和背面透明度创建不同的控件?还有一种透明对象接受阴影的方法吗?我想给宝石添加轮廓,这样它就可以被看得更远。有没有办法在同一关卡中添加轮廓,还是必须有自己的单独关卡?此外,如何使接收到的阴影变暗?所有这些要求会对GPU征税吗?该游戏适用于移动平台
我是CG编程的初学者。我的第一步是找出将曲面编程转换为顶点/片段的方法。任何例子都将不胜感激
我确实在资产商店购买了一些宝石资产,但其中一些可以投射阴影,但不能接收或根本不能投射或接收。有什么好处?右侧的gem着色器来自从资产存储购买的资产之一。我不想在未经他们允许的情况下在此网站上共享他们的着色器脚本。这实际上是一个相当复杂的过程,不过我建议您从他们的网站下载unity着色器源代码开始。大多数实际着色是在UNITYSTANDBRDF.cginc、UNITYPBSLIGHT.cginc和UNITYSTANDCORE.cginc中完成的。如果你用谷歌搜索这些文件,你也可以在github上找到它们 基本上,前向添加着色器的基本结构如下所示:
Shader "MyForwardAddShader"
{
Properties
{
_MainTex("Some texture", 2D) = "white"{}
}
SubShader
{
Tags {"RenderType"="Geometry" "Queue" = "Geometry"}
Pass
{
// Forward Base pass - this applies main directional light and ambient
Name "FORWARD"
Tags { "LightMode" = "ForwardBase" }
CGPROGRAM
#pragma target 3.5
#pragma multi_compile_fwdbase
#pragma multi_compile_fog
#pragma multi_compile_instancing
#pragma vertex vert
#pragma fragment frag
// I Like to keep these in separate include files
#include "MyForwardBase.cginc"
ENDCG
}
Pass
{
// Forward Add pass - this is added once per extra light source
Name "FORWARD_DELTA"
Tags { "LightMode" = "ForwardAdd" }
Blend SrcAlpha One
Fog { Color (0,0,0,0) } // in additive pass fog should be black
ZWrite Off
ZTest LEqual
CGPROGRAM
#pragma target 3.5
#pragma multi_compile_fwdadd_fullshadows
#pragma multi_compile_fog
#pragma vertex vert
#pragma fragment frag
#include "MyForwardAdd.cginc"
ENDCG
}
}
}
UNITY_LIGHT_ATTENUATION(atten, i, i.worldPos.xyz); // Here, worldPos is stored in the vertex output struct and calculated per vertex
half3 lightColor = _LightColor0.rgb * atten;
请注意,您还需要阴影投射器过程来投射阴影(您可以只复制标准着色器源代码中使用的过程),如果要使用烘焙照明,还需要元过程
像“MyForwardBase.cginc”这样的文件应该包括顶点输入和输出结构的定义,以及过程的顶点和片段函数。使用此设置,还需要在其中定义统一(属性变量)。灯光计算可能需要的一些变量:
// Calculate this in the vertex shader and normalize per fragment
o.worldPos = mul(unity_ObjectToWorld, v.vertex).xyz;
float3 viewDir = _WorldSpaceCameraPos.xyz - o.worldPos;
// In the ForwardBase pass, _WorldSPaceLightPos0.xyz stores the direction of the main directional light, instead of position.
// Use this in the vertex function:
half3 mainLightColor = _LightColor0.rgb;
half3 mainLightDir = _WorldSpaceLightPos0.xyz;
对于ForwardBase过程,您需要包括“AutoLight.cginc”,并在vertex函数中使用此宏:
COMPUTE_LIGHT_COORDS(o);
这反过来要求您在VertexOutput结构中具有此宏:
UNITY_LIGHTING_COORDS(6,7) // 6, 7 can be any texture interpolator IDs, they will translate to TEXCOORD6 and TEXCOORD7 in this case
ForwardAdd灯光衰减的工作原理如下:
Shader "MyForwardAddShader"
{
Properties
{
_MainTex("Some texture", 2D) = "white"{}
}
SubShader
{
Tags {"RenderType"="Geometry" "Queue" = "Geometry"}
Pass
{
// Forward Base pass - this applies main directional light and ambient
Name "FORWARD"
Tags { "LightMode" = "ForwardBase" }
CGPROGRAM
#pragma target 3.5
#pragma multi_compile_fwdbase
#pragma multi_compile_fog
#pragma multi_compile_instancing
#pragma vertex vert
#pragma fragment frag
// I Like to keep these in separate include files
#include "MyForwardBase.cginc"
ENDCG
}
Pass
{
// Forward Add pass - this is added once per extra light source
Name "FORWARD_DELTA"
Tags { "LightMode" = "ForwardAdd" }
Blend SrcAlpha One
Fog { Color (0,0,0,0) } // in additive pass fog should be black
ZWrite Off
ZTest LEqual
CGPROGRAM
#pragma target 3.5
#pragma multi_compile_fwdadd_fullshadows
#pragma multi_compile_fog
#pragma vertex vert
#pragma fragment frag
#include "MyForwardAdd.cginc"
ENDCG
}
}
}
UNITY_LIGHT_ATTENUATION(atten, i, i.worldPos.xyz); // Here, worldPos is stored in the vertex output struct and calculated per vertex
half3 lightColor = _LightColor0.rgb * atten;
还有一些宏用于确定像素是否在阴影中,您可以在AutoLight.cginc中找到它们。在ForwardAdd过程中,灯光方向按顶点计算,如下所示:
o.lightDir = _WorldSpaceLightPos0.xyz - o.worldPos.xyz * _WorldSpaceLightPos0.w;
就我个人而言,我喜欢为每个特征创建小的CGInclude,例如反射、折射、三平面贴图等,并且只要我需要它们,就可以包含它们。我还倾向于在自己的include文件中保留一个名为“Lighting”的单独函数,因为照明计算在通道之间共享。此函数将所有变量(如lightDir、viewDir、反照率、粗糙度等)作为参数,并返回片段的着色颜色
正如我所说,这是一个相当复杂的过程,这只是一个入门。实现照明功能本身就是一个故事,尽管查看UnityStandardBRDF.cginc可以有所帮助。我建议您从基本的blinn phong模型开始进行调试,并从中改进 我很困惑你的问题中有很多问题?1-曲面到碎片2-双面透明为什么要将此着色器转换为碎片着色器?最好使用曲面着色器,因为它易于编辑。@SeyedMortezaKamali 1)。我所购买的资产中有一些我喜欢的功能,但它是由vertex/fragment编写的。我想把代码的一些部分添加到我的代码中。我想将曲面转换为顶点/碎片,以便了解如何操作它。2). 我想通过控制正面和背面的alpha来控制宝石中的雾量。为整个宝石设置alpha使其看起来更像玻璃或塑料。例如,我想将白色宝石的背面alpha设置为更接近纯色,而不是更暗的颜色。我希望这是有意义的。编写片段着色器并不容易,但如果您喜欢这样做,您应该学习片段着色器,但无论如何,每个灯光建模都有片段着色器