using System.Linq; using Misaki.ShaderGUI; using UnityEditor; using UnityEditor.Rendering; using UnityEngine; using UnityEngine.Rendering; namespace Misaki.HdrpToon.Editor { public class PBRScope : MaterialUIScope { private static class Properties { public static MaterialProperty PbrMode; public static MaterialProperty NormalMap; public static MaterialProperty NormalMapScale; public static MaterialProperty MaskMap; public static MaterialProperty Metallic; public static MaterialProperty MetallicRemapMin; public static MaterialProperty MetallicRemapMax; public static MaterialProperty AORemapMin; public static MaterialProperty AORemapMax; public static MaterialProperty RoughnessRemapMin; public static MaterialProperty RoughnessRemapMax; public static MaterialProperty Smoothness; public static MaterialProperty AnisotropyMap; public static MaterialProperty Anisotropy; public static MaterialProperty KKColor; public static MaterialProperty BSDFContribution; public static MaterialProperty SpecularColorMap; public static MaterialProperty SpecularColor; public static MaterialProperty SpecularFeather; public static MaterialProperty SpecularStep; } private static class Styles { public static readonly GUIContent PbrModeText = new("PBR Mode", "PBR Mode"); public static readonly GUIContent NormalMapText = new("Normal Map", "A texture that dictates the bumpiness of the material."); public static readonly GUIContent MaskMapText = new("Mask Map", "A texture that dictates the physical properties of the material. R: Metallic, G: Occlusion, A: Smoothness"); public static readonly GUIContent MetallicText = new("Metallic", "Specifies the metallicness of the material."); public static readonly GUIContent MetallicRemap = new("Metallic Remap", "Remap the max and min value of metallic"); public static readonly GUIContent AORemap = new GUIContent("AO Remap", "Remap the max and min value of ambient occlusion"); public static readonly GUIContent RoughnessRemap = new GUIContent("Smoothness Remap", "Remap the max and min value of smoothness"); public static readonly GUIContent SmoothnessText = new("Smoothness", "Specifies the smoothness of the material."); public static readonly GUIContent AnisotropyMapText = new("Anisotropy Map", "Specifies the anisotropy map of the material."); public static readonly GUIContent KKColorText = new("KK specular Color", "Specifies the color of KK specular."); public static readonly GUIContent BSDFContributionText = new("BSDF Contribution", "BSDF smoothness contribution, 1 means KK Hair smoothness will fully contribute bsdf calculation"); public static readonly GUIContent SpecularColorMapText = new("Specular Color Map", "Specifies the specular color map of the material."); public static readonly GUIContent SpecRemap = new("Specular Remap", "Feather and step value of Toon Specular"); } public override void LoadMaterialProperties() { Properties.PbrMode = FindProperty("_PBR_Mode"); Properties.NormalMap = FindProperty("_NormalMap"); Properties.NormalMapScale = FindProperty("_NormalScale"); Properties.MaskMap = FindProperty("_MaskMap"); Properties.Metallic = FindProperty("_Metallic"); Properties.MetallicRemapMin = FindProperty("_MetallicRemapMin"); Properties.MetallicRemapMax = FindProperty("_MetallicRemapMax"); Properties.AORemapMin = FindProperty("_AORemapMin"); Properties.AORemapMax = FindProperty("_AORemapMax"); Properties.RoughnessRemapMin = FindProperty("_SmoothnessRemapMin"); Properties.RoughnessRemapMax = FindProperty("_SmoothnessRemapMax"); Properties.Smoothness = FindProperty("_Smoothness"); Properties.AnisotropyMap = FindProperty("_AnisotropyMap"); Properties.Anisotropy = FindProperty("_Anisotropy"); Properties.KKColor = FindProperty("_KKColor"); Properties.BSDFContribution = FindProperty("_BSDFContribution"); Properties.SpecularColorMap = FindProperty("_SpecularColorMap"); Properties.SpecularColor = FindProperty("_SpecularColor"); Properties.SpecularFeather = FindProperty("_ToonSpecularFeather"); Properties.SpecularStep = FindProperty("_ToonSpecularStep"); } protected override void DrawContent() { editor.ShaderProperty(Properties.PbrMode, Styles.PbrModeText); EditorGUILayout.Space(); editor.TexturePropertySingleLine(Styles.NormalMapText, Properties.NormalMap, Properties.NormalMapScale); var materials = GetMaterials().ToList(); foreach (Material material in materials) { material.SetKeyword(new LocalKeyword(material.shader, "_NORMAL_MAP"), Properties.NormalMap.textureValue != null); } PBRMode pbrMode = (PBRMode)Properties.PbrMode.floatValue; if (pbrMode != PBRMode.Off) { editor.TexturePropertySingleLine(Styles.MaskMapText, Properties.MaskMap); if (Properties.MaskMap.textureValue == null) { foreach (Material material in materials) { material.DisableKeyword(new LocalKeyword(material.shader, "_MASK_MAP")); } if (pbrMode != PBRMode.KKHair) editor.ShaderProperty(Properties.Metallic, Styles.MetallicText); editor.ShaderProperty(Properties.Smoothness, Styles.SmoothnessText); } else { foreach (Material material in materials) { material.EnableKeyword(new LocalKeyword(material.shader, "_MASK_MAP")); } editor.MinMaxShaderProperty(Properties.MetallicRemapMin, Properties.MetallicRemapMax, 0, 1, Styles.MetallicRemap); editor.MinMaxShaderProperty(Properties.AORemapMin, Properties.AORemapMax, 0, 1, Styles.AORemap); editor.MinMaxShaderProperty(Properties.RoughnessRemapMin, Properties.RoughnessRemapMax, 0, 1, Styles.RoughnessRemap); } } else { foreach (Material material in materials) { material.DisableKeyword(new LocalKeyword(material.shader, "_MASK_MAP")); material.DisableKeyword(new LocalKeyword(material.shader, "_ANISOTROPY_MAP")); material.DisableKeyword(new LocalKeyword(material.shader, "_SPECULAR_COLOR_MAP")); } } switch (pbrMode) { case PBRMode.Anisotropy or PBRMode.KKHair: { editor.TexturePropertySingleLine(Styles.AnisotropyMapText, Properties.AnisotropyMap, Properties.Anisotropy); if (pbrMode == PBRMode.KKHair) { editor.ShaderProperty(Properties.KKColor, Styles.KKColorText); editor.ShaderProperty(Properties.BSDFContribution, Styles.BSDFContributionText); } EditorGUILayout.Space(); EditorGUILayout.LabelField("Anisotropy Map only ST"); editor.TextureScaleOffsetProperty(Properties.AnisotropyMap); if (Properties.AnisotropyMap.textureValue == null) { foreach (Material material in materials) { material.DisableKeyword(new LocalKeyword(material.shader, "_ANISOTROPY_MAP")); } } else { foreach (Material material in materials) { material.EnableKeyword(new LocalKeyword(material.shader, "_ANISOTROPY_MAP")); } } break; } case PBRMode.Toon: { editor.TexturePropertySingleLine(Styles.SpecularColorMapText, Properties.SpecularColorMap, Properties.SpecularColor); if (Properties.SpecularColorMap.textureValue == null) { foreach (Material material in materials) { material.DisableKeyword(new LocalKeyword(material.shader, "_SPECULAR_COLOR_MAP")); } } else { foreach (Material material in materials) { material.EnableKeyword(new LocalKeyword(material.shader, "_SPECULAR_COLOR_MAP")); } } editor.MinMaxShaderProperty(Properties.SpecularFeather, Properties.SpecularStep, 0, 1, Styles.SpecRemap); break; } } } private enum PBRMode { Off, Standard, Anisotropy, KKHair, Toon } protected override ShaderGUIExpandable ExpandableBit => ShaderGUIExpandable.PBR; protected override GUIContent Header => new("PBR Settings"); } }