Skip to content

Commit

Permalink
New Material Feature: Vertex Color Blend Modes and New Material Featu…
Browse files Browse the repository at this point in the history
…re: Vertex Color Mode: Split Color And Lighting. Also bump package.json version to 1.5.0.
  • Loading branch information
pastasfuture committed Aug 2, 2021
1 parent 66ac6ff commit 5419a00
Show file tree
Hide file tree
Showing 10 changed files with 147 additions and 24 deletions.
13 changes: 13 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,16 @@
---------------------------------------------------------------------------------------------------------------------------
New Material Feature: **Vertex Color Blend Modes**
---------------------------------------------------------------------------------------------------------------------------
Controls how vertex colors are blended with MainColor|MainTex.
**Multiply** The standard vertex color blend mode, the vertexColor.rgba channels are multiplied against the MainColor.rgba channels.
**Additive** adds the vertexColor.rgb * vertexColor.a result to the MainColor.rgb channels. vertexColor.a is multiplied against MainColor.a to support alpha fade out.
**Subtractive** subtracts the vertexColor.rgb * vertexColor.a result from the MainColor.rgb channels. vertexColor.a is multiplied against MainColor.a to support alpha fade out.

---------------------------------------------------------------------------------------------------------------------------
New Material Feature: **Vertex Color Mode: Split Color And Lighting**
---------------------------------------------------------------------------------------------------------------------------
**Split Color And Lighting**: A hybrid of VertexColorMode.Color and VertexColorMode.Lighting. Vertex colors >= 0.5 are rescaled and treated as VertexColorMode.Lighting. Vertex colors < 0.5 are rescaled and treated as VertexColorMode.Color. This mode is experimental. Looking for feedback from users. Expect potential modifications to the underlying implementation in future releases.

---------------------------------------------------------------------------------------------------------------------------
New Precision Volume Feature: **Dither Size**
---------------------------------------------------------------------------------------------------------------------------
Expand Down
5 changes: 4 additions & 1 deletion Editor/Material/BaseShaderGUI.cs
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,8 @@ public abstract class BaseShaderGUI : ShaderGUI

protected MaterialProperty vertexColorModeProp { get; set; }

protected MaterialProperty vertexColorBlendModeProp { get; set; }

protected MaterialProperty renderQueueCategoryProp { get; set; }

protected MaterialProperty lightingModeProp { get; set; }
Expand Down Expand Up @@ -106,6 +108,7 @@ public virtual void FindProperties(MaterialProperty[] properties)
{
textureFilterModeProp = FindProperty(PropertyNames._TextureFilterMode, properties);
vertexColorModeProp = FindProperty(PropertyNames._VertexColorMode, properties);
vertexColorBlendModeProp = FindProperty(PropertyNames._VertexColorBlendMode, properties);
renderQueueCategoryProp = FindProperty(PropertyNames._RenderQueueCategory, properties);
lightingModeProp = FindProperty(PropertyNames._LightingMode, properties);
lightingBakedProp = FindProperty(PropertyNames._LightingBaked, properties);
Expand Down Expand Up @@ -219,7 +222,7 @@ public virtual void DrawSurfaceOptions(Material material)
{
PSXMaterialUtils.DrawRenderQueueCategory(materialEditor, renderQueueCategoryProp);
PSXMaterialUtils.DrawTextureFilterMode(materialEditor, textureFilterModeProp);
PSXMaterialUtils.DrawVertexColorMode(materialEditor, vertexColorModeProp);
PSXMaterialUtils.DrawVertexColorMode(materialEditor, vertexColorModeProp, vertexColorBlendModeProp);
PSXMaterialUtils.DrawLightingMode(material, materialEditor, lightingModeProp, lightingBakedProp, lightingDynamicProp);
PSXMaterialUtils.DrawShadingEvaluationMode(materialEditor, shadingEvaluationModeProp);
PSXMaterialUtils.DrawBRDFMode(materialEditor, brdfModeProp);
Expand Down
35 changes: 32 additions & 3 deletions Editor/Material/PSXMaterialUtils.cs
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,15 @@ public enum VertexColorMode
ColorBackground,
AlphaOnly,
Emission,
EmissionAndAlphaOnly
EmissionAndAlphaOnly,
SplitColorAndLighting
}

public enum VertexColorBlendMode
{
Multiply = 0,
Additive,
Subtractive
}

public enum RenderFace
Expand Down Expand Up @@ -137,6 +145,7 @@ public static class PropertyNames
{
public static readonly string _TextureFilterMode = "_TextureFilterMode";
public static readonly string _VertexColorMode = "_VertexColorMode";
public static readonly string _VertexColorBlendMode = "_VertexColorBlendMode";
public static readonly string _RenderQueueCategory = "_RenderQueueCategory";
public static readonly string _LightingMode = "_LightingMode";
public static readonly string _LightingBaked = "_LightingBaked";
Expand Down Expand Up @@ -186,6 +195,7 @@ public static class PropertyIDs
{
public static readonly int _TextureFilterMode = Shader.PropertyToID(PropertyNames._TextureFilterMode);
public static readonly int _VertexColorMode = Shader.PropertyToID(PropertyNames._VertexColorMode);
public static readonly int _VertexColorBlendMode = Shader.PropertyToID(PropertyNames._VertexColorBlendMode);
public static readonly int _RenderQueueCategory = Shader.PropertyToID(PropertyNames._RenderQueueCategory);
public static readonly int _LightingMode = Shader.PropertyToID(PropertyNames._LightingMode);
public static readonly int _LightingBaked = Shader.PropertyToID(PropertyNames._LightingBaked);
Expand Down Expand Up @@ -257,6 +267,7 @@ public static class Keywords
public static readonly string _VERTEX_COLOR_MODE_ALPHA_ONLY = "_VERTEX_COLOR_MODE_ALPHA_ONLY";
public static readonly string _VERTEX_COLOR_MODE_EMISSION = "_VERTEX_COLOR_MODE_EMISSION";
public static readonly string _VERTEX_COLOR_MODE_EMISSION_AND_ALPHA_ONLY = "_VERTEX_COLOR_MODE_EMISSION_AND_ALPHA_ONLY";
public static readonly string _VERTEX_COLOR_MODE_SPLIT_COLOR_AND_LIGHTING = "_VERTEX_COLOR_MODE_SPLIT_COLOR_AND_LIGHTING";
public static readonly string _LIGHTING_BAKED_ON = "_LIGHTING_BAKED_ON";
public static readonly string _LIGHTING_DYNAMIC_ON = "_LIGHTING_DYNAMIC_ON";
public static readonly string _SHADING_EVALUATION_MODE_PER_VERTEX = "_SHADING_EVALUATION_MODE_PER_VERTEX";
Expand Down Expand Up @@ -291,7 +302,10 @@ public static class Styles
"Controls how MainTex and EmissionTex are filtered.\nTextureFilterMode.TextureImportSettings is the standard unity behavior. Textures will be filtered using the texture's import settings.\nTextureFilterMode.Point will force PSX era nearest neighbor point sampling, regardless of texture import settings.\nTextureFilterMode.PointMipmaps is the same as TextureFilterMode.Point but supports supports point sampled lods via the texture's mipmap chain.\nTextureFilterMode.N64 will force N64 era 3-point barycentric texture filtering.\nTextureFilterMode.N64MipMaps is the same as TextureFilterMode.N64 but supports N64 sampled lods via the texture's mipmap chain.");

public static readonly GUIContent VertexColorMode = new GUIContent("Vertex Color Mode",
"Controls how vertex colors are interpreted by the shader. VertexColorMode.Color multiplies the vertex color data with the MainTex value. This is useful for adding variation to the MainTex color per vertex, such as in a particle sim. VertexColorMode.Lighting interprets the vertexColor data as per-vertex lighting. The result will be added to other lighting that may be present. VertexColorMode.ColorBackground blends between the vertex color data and the MainTex color based on the MainTex alpha. VertexColorMode.AlphaOnly multiplies only the alpha channel of the vertex color against the alpha of MainTex. VertexColorMode.Emission multiplies the vertex color with the Emission value. VertexColorMode.EmissionAndAlphaOnly multiplies the vertex color with the Emission value and multiplies the vertex color alpha channel with the MainTex alpha.");
"Controls how vertex colors are interpreted by the shader. VertexColorMode.Color multiplies the vertex color data with the MainTex value. This is useful for adding variation to the MainTex color per vertex, such as in a particle sim. VertexColorMode.Lighting interprets the vertexColor data as per-vertex lighting. The result will be added to other lighting that may be present. VertexColorMode.ColorBackground blends between the vertex color data and the MainTex color based on the MainTex alpha. VertexColorMode.AlphaOnly multiplies only the alpha channel of the vertex color against the alpha of MainTex. VertexColorMode.Emission multiplies the vertex color with the Emission value. VertexColorMode.EmissionAndAlphaOnly multiplies the vertex color with the Emission value and multiplies the vertex color alpha channel with the MainTex alpha.\nVertexColorMode.SplitColorAndLighting is a hybrid of VertexColorMode.Color and VertexColorMode.Lighting. Vertex colors >= 0.5 are rescaled and treated as VertexColorMode.Lighting. Vertex colors < 0.5 are rescaled and treated as VertexColorMode.Color.");

public static readonly GUIContent VertexColorBlendMode = new GUIContent("Vertex Color Blend Mode",
"Controls how vertex colors are blended with MainColor|MainTex.\nMultiply is the standard vertex color blend mode, the vertexColor.rgba channels are multiplied against the MainColor.rgba channels.\nAdditive adds the vertexColor.rgb * vertexColor.a result to the MainColor.rgb channels. vertexColor.a is multiplied against MainColor.a to support alpha fade out.\nSubtractive subtracts the vertexColor.rgb * vertexColor.a result from the MainColor.rgb channels. vertexColor.a is multiplied against MainColor.a to support alpha fade out.");

public static readonly GUIContent RenderQueueCategory =
new GUIContent("Render Queue Category", "Controls when this object is rendered.\nMaterials set to Background are rendered first.\nMaterials set to Main are rendered second.\nMaterials set to UIOverlay are rendered last.\nThe CameraVolume override controls whether or not the depth buffer will be cleared between these stages.");
Expand Down Expand Up @@ -649,6 +663,15 @@ public static void SetupMaterialLightingMode(Material material, bool vertexColor
material.DisableKeyword(Keywords._VERTEX_COLOR_MODE_EMISSION_AND_ALPHA_ONLY);
}

if (vertexColorMode == VertexColorMode.SplitColorAndLighting)
{
material.EnableKeyword(Keywords._VERTEX_COLOR_MODE_SPLIT_COLOR_AND_LIGHTING);
}
else
{
material.DisableKeyword(Keywords._VERTEX_COLOR_MODE_SPLIT_COLOR_AND_LIGHTING);
}

switch (lightingMode)
{
case LightingMode.Unlit:
Expand Down Expand Up @@ -1083,9 +1106,15 @@ public static void DrawTextureFilterMode(MaterialEditor materialEditor, Material
DoPopup(Styles.TextureFilterMode, textureFilterModeProp, Enum.GetNames(typeof(TextureFilterMode)), materialEditor);
}

public static void DrawVertexColorMode(MaterialEditor materialEditor, MaterialProperty vertexColorModeProp)
public static void DrawVertexColorMode(MaterialEditor materialEditor, MaterialProperty vertexColorModeProp, MaterialProperty vertexColorBlendModeProp)
{
DoPopup(Styles.VertexColorMode, vertexColorModeProp, Enum.GetNames(typeof(VertexColorMode)), materialEditor);

VertexColorMode vertexColorMode = (VertexColorMode)(int)vertexColorModeProp.floatValue;
if (vertexColorMode == VertexColorMode.Color)
{
DoPopup(Styles.VertexColorBlendMode, vertexColorBlendModeProp, Enum.GetNames(typeof(VertexColorBlendMode)), materialEditor);
}
}

public static void DrawLightingMode(Material material, MaterialEditor materialEditor, MaterialProperty lightingModeProp, MaterialProperty lightingBakedProp, MaterialProperty lightingDynamicProp)
Expand Down
5 changes: 3 additions & 2 deletions Runtime/Material/PSXLit/PSXLit.shader
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
_UVAnimationMode("_UVAnimationMode", Float) = 0.0
_UVAnimationParametersFrameLimit("_UVAnimationParametersFrameLimit", Vector) = (0, 60, 0, 0)
_UVAnimationParameters("_UVAnimationParameters", Vector) = (1, 1, 0, 0)
_VertexColorBlendMode("_VertexColorBlendMode", Float) = 0.0

// C# side material state tracking.
[HideInInspector] _TextureFilterMode("__textureFilterMode", Float) = 0.0
Expand Down Expand Up @@ -79,7 +80,7 @@
// -------------------------------------
// Material Keywords
#pragma shader_feature _TEXTURE_FILTER_MODE_TEXTURE_IMPORT_SETTINGS _TEXTURE_FILTER_MODE_POINT _TEXTURE_FILTER_MODE_POINT_MIPMAPS _TEXTURE_FILTER_MODE_N64 _TEXTURE_FILTER_MODE_N64_MIPMAPS
#pragma shader_feature _ _VERTEX_COLOR_MODE_COLOR _VERTEX_COLOR_MODE_LIGHTING _VERTEX_COLOR_MODE_COLOR_BACKGROUND _VERTEX_COLOR_MODE_ALPHA_ONLY _VERTEX_COLOR_MODE_EMISSION _VERTEX_COLOR_MODE_EMISSION_AND_ALPHA_ONLY
#pragma shader_feature _ _VERTEX_COLOR_MODE_COLOR _VERTEX_COLOR_MODE_LIGHTING _VERTEX_COLOR_MODE_COLOR_BACKGROUND _VERTEX_COLOR_MODE_ALPHA_ONLY _VERTEX_COLOR_MODE_EMISSION _VERTEX_COLOR_MODE_EMISSION_AND_ALPHA_ONLY _VERTEX_COLOR_MODE_SPLIT_COLOR_AND_LIGHTING
#pragma shader_feature _LIGHTING_BAKED_ON
#pragma shader_feature _LIGHTING_DYNAMIC_ON
#pragma shader_feature _SHADING_EVALUATION_MODE_PER_VERTEX _SHADING_EVALUATION_MODE_PER_PIXEL _SHADING_EVALUATION_MODE_PER_OBJECT
Expand Down Expand Up @@ -126,7 +127,7 @@

// -------------------------------------
// Material Keywords
#pragma shader_feature _ _VERTEX_COLOR_MODE_COLOR _VERTEX_COLOR_MODE_LIGHTING _VERTEX_COLOR_MODE_COLOR_BACKGROUND _VERTEX_COLOR_MODE_ALPHA_ONLY
#pragma shader_feature _ _VERTEX_COLOR_MODE_COLOR _VERTEX_COLOR_MODE_LIGHTING _VERTEX_COLOR_MODE_COLOR_BACKGROUND _VERTEX_COLOR_MODE_ALPHA_ONLY _VERTEX_COLOR_MODE_SPLIT_COLOR_AND_LIGHTING
#pragma shader_feature _EMISSION
#pragma shader_feature _ALPHATEST_ON
#pragma shader_feature _ _ALPHAPREMULTIPLY_ON _ALPHAMODULATE_ON
Expand Down
1 change: 1 addition & 0 deletions Runtime/Material/PSXLit/PSXLitInput.hlsl
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ float4 _DoubleSidedConstants;
int _UVAnimationMode;
float2 _UVAnimationParametersFrameLimit;
float4 _UVAnimationParameters;
int _VertexColorBlendMode;

// Following two variables are feeded by the C++ Editor for Scene selection
int _ObjectId;
Expand Down
21 changes: 18 additions & 3 deletions Runtime/Material/PSXLit/PSXLitMetaPass.hlsl
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@

#include "Packages/com.hauntedpsx.render-pipelines.psx/Runtime/ShaderLibrary/ShaderVariables.hlsl"
#include "Packages/com.hauntedpsx.render-pipelines.psx/Runtime/ShaderLibrary/ShaderFunctions.hlsl"
#include "Packages/com.hauntedpsx.render-pipelines.psx/Runtime/ShaderLibrary/MaterialFunctions.hlsl"
#include "Packages/com.hauntedpsx.render-pipelines.psx/Runtime/ShaderLibrary/BakedLighting.hlsl"

CBUFFER_START(UnityMetaPass)
Expand All @@ -25,7 +26,7 @@ struct Attributes
float2 uv0 : TEXCOORD0;
float2 uv1 : TEXCOORD1;
float2 uv2 : TEXCOORD2;
#if defined(_VERTEX_COLOR_MODE_COLOR) || defined(_VERTEX_COLOR_MODE_COLOR_BACKGROUND)
#if defined(_VERTEX_COLOR_MODE_COLOR) || defined(_VERTEX_COLOR_MODE_COLOR_BACKGROUND) || defined(_VERTEX_COLOR_MODE_SPLIT_COLOR_AND_LIGHTING)
float4 color : COLOR;
#endif
};
Expand All @@ -34,7 +35,7 @@ struct Varyings
{
float4 positionCS : SV_POSITION;
float2 uv : TEXCOORD0;
#if defined(_VERTEX_COLOR_MODE_COLOR) || defined(_VERTEX_COLOR_MODE_COLOR_BACKGROUND)
#if defined(_VERTEX_COLOR_MODE_COLOR) || defined(_VERTEX_COLOR_MODE_COLOR_BACKGROUND) || defined(_VERTEX_COLOR_MODE_SPLIT_COLOR_AND_LIGHTING)
float4 color : TEXCOORD1;
#endif
};
Expand Down Expand Up @@ -110,10 +111,24 @@ half4 LitMetaPassFragment(Varyings i) : SV_Target
half4 color = _MainColor * SAMPLE_TEXTURE2D(_MainTex, sampler_MainTex, colorUV);

#if defined(_VERTEX_COLOR_MODE_COLOR)
color *= i.color;
float4 vertexColorNormalized = i.color;
color = ApplyVertexColorPerPixelColorVertexColorModeColor(color, vertexColorNormalized, vertexColorBlendMode);
#elif defined(_VERTEX_COLOR_MODE_COLOR_BACKGROUND)
color.rgb = lerp(i.color.rgb, color.rgb, color.a);
color.a = 1.0f;
#elif defined(_VERTEX_COLOR_MODE_SPLIT_COLOR_AND_LIGHTING)
if (ComputeVertexColorModeSplitColorAndLightingIsLighting(i.color))
{
// Lighting mode, still need to apply alpha to support alpha fade.
color.a *= i.color.a;
}
else
{
float4 vertexColorNormalized = i.color;
vertexColorNormalized.rgb = saturate(lerp(0.5f, vertexColorNormalized.rgb, vertexColorNormalized.a) * 2.0f);
color *= vertexColorNormalized;
}

#endif

#if _ALPHATEST_ON
Expand Down
2 changes: 1 addition & 1 deletion Runtime/Material/PSXLit/PSXLitPass.hlsl
Original file line number Diff line number Diff line change
Expand Up @@ -89,7 +89,7 @@ half4 LitPassFragment(Varyings i, FRONT_FACE_TYPE cullFace : FRONT_FACE_SEMANTIC

float4 color = _MainColor * SampleTextureWithFilterMode(TEXTURE2D_ARGS(_MainTex, sampler_MainTex), uvColor, texelSizeLod, lod);

color = ApplyVertexColorPerPixelColor(color, i.color, interpolatorNormalization);
color = ApplyVertexColorPerPixelColor(color, i.color, interpolatorNormalization, _VertexColorBlendMode);

#if _ALPHATEST_ON
// Perform alpha cutoff transparency (i.e: discard pixels in the holes of a chain link fence texture, or in the negative space of a leaf texture).
Expand Down
Loading

0 comments on commit 5419a00

Please sign in to comment.