static void RenderQueueUpgrade(Material material, HDShaderUtils.ShaderID id) { // In order for the ray tracing keyword to be taken into account, we need to make it dirty so that the parameter is created first HDShaderUtils.ResetMaterialKeywords(material); // Replace previous ray tracing render queue for opaque to regular opaque with raytracing if (material.renderQueue == ((int)UnityEngine.Rendering.RenderQueue.GeometryLast + 20)) { material.renderQueue = (int)HDRenderQueue.Priority.Opaque; material.SetFloat(kRayTracing, 1.0f); } // Replace previous ray tracing render queue for transparent to regular transparent with raytracing else if (material.renderQueue == 3900) { material.renderQueue = (int)HDRenderQueue.Priority.Transparent; material.SetFloat(kRayTracing, 1.0f); } // For shader graphs, there is an additional pass we need to do if (material.HasProperty("_RenderQueueType")) { int renderQueueType = (int)material.GetFloat("_RenderQueueType"); switch (renderQueueType) { // This was ray tracing opaque, should go back to opaque case 3: { renderQueueType = 1; } break; // If it was in the transparent range, reduce it by 1 case 4: case 5: case 6: case 7: { renderQueueType = renderQueueType - 1; } break; // If it was in the ray tracing transparent, should go back to transparent case 8: { renderQueueType = renderQueueType - 4; } break; // If it was in overlay should be reduced by 2 case 10: { renderQueueType = renderQueueType - 2; } break; // background, opaque and AfterPostProcessOpaque are not impacted default: break; } // Push it back to the material material.SetFloat("_RenderQueueType", (float)renderQueueType); } HDShaderUtils.ResetMaterialKeywords(material); }
//example migration method: //static void Example(Material material, HDShaderUtils.ShaderID id) //{ // const string kSupportDecals = "_SupportDecals"; // var serializedMaterial = new SerializedObject(material); // if (!TryFindProperty(serializedMaterial, kSupportDecals, SerializedType.Integer, out var property, out _, out _)) // return; // // Caution: order of operation is important, we need to keep the current value of the property (if done after it is 0) // // then we remove it and apply the result // // then we can modify the material (otherwise the material change are lost) // bool supportDecal = property.floatValue == 1.0f; // RemoveSerializedInt(serializedMaterial, kSupportDecals); // serializedMaterial.ApplyModifiedProperties(); // // We need to reset the custom RenderQueue to take into account the move to specific RenderQueue for Opaque with Decal. // // this should be handled correctly with reset below // HDShaderUtils.ResetMaterialKeywords(material); //} //} static void StencilRefactor(Material material, HDShaderUtils.ShaderID id) { HDShaderUtils.ResetMaterialKeywords(material); }
static void OnPostprocessAllAssets(string[] importedAssets, string[] deletedAssets, string[] movedAssets, string[] movedFromAssetPaths) { foreach (var asset in importedAssets) { if (!asset.ToLowerInvariant().EndsWith(".mat")) { continue; } var material = (Material)AssetDatabase.LoadAssetAtPath(asset, typeof(Material)); if (!HDShaderUtils.IsHDRPShader(material.shader, upgradable: true)) { continue; } HDShaderUtils.ShaderID id = HDShaderUtils.GetShaderEnumFromShader(material.shader); var latestVersion = k_Migrations.Length; var wasUpgraded = false; var assetVersions = AssetDatabase.LoadAllAssetsAtPath(asset); AssetVersion assetVersion = null; foreach (var subAsset in assetVersions) { if (subAsset != null && subAsset.GetType() == typeof(AssetVersion)) { assetVersion = subAsset as AssetVersion; break; } } //subasset not found if (!assetVersion) { wasUpgraded = true; assetVersion = ScriptableObject.CreateInstance <AssetVersion>(); assetVersion.hideFlags = HideFlags.HideInHierarchy | HideFlags.HideInInspector | HideFlags.NotEditable; if (s_CreatedAssets.Contains(asset)) { //just created assetVersion.version = latestVersion; s_CreatedAssets.Remove(asset); //[TODO: remove comment once fixed] //due to FB 1175514, this not work. It is being fixed though. //delayed call of the following work in some case and cause infinite loop in other cases. AssetDatabase.AddObjectToAsset(assetVersion, asset); } else { //asset exist prior migration assetVersion.version = 0; AssetDatabase.AddObjectToAsset(assetVersion, asset); } } //upgrade while (assetVersion.version < latestVersion) { k_Migrations[assetVersion.version](material, id); assetVersion.version++; wasUpgraded = true; } if (wasUpgraded) { EditorUtility.SetDirty(assetVersion); s_ImportedAssetThatNeedSaving.Add(asset); s_NeedsSavingAssets = true; } } }
bool IsHDRPShader() { var mat = m_OverrideMaterial.objectReferenceValue as Material; return(HDShaderUtils.IsHDRPShader(mat?.shader)); }
void LogShaderVariants(Shader shader, ShaderSnippetData snippetData, uint prevVariantsCount, uint currVariantsCount, double stripTimeMs) { if (HDRenderPipelineGlobalSettings.instance.shaderVariantLogLevel == ShaderVariantLogLevel.Disabled) { return; } m_TotalVariantsInputCount += prevVariantsCount; m_TotalVariantsOutputCount += currVariantsCount; if (HDRenderPipelineGlobalSettings.instance.shaderVariantLogLevel == ShaderVariantLogLevel.OnlySRPShaders && !HDShaderUtils.IsHDRPShader(shader)) { return; } float percentageCurrent = ((float)currVariantsCount / prevVariantsCount) * 100.0f; float percentageTotal = ((float)m_TotalVariantsOutputCount / m_TotalVariantsInputCount) * 100.0f; string result = string.Format("STRIPPING: {0} ({1} pass) ({2}) -" + " Remaining shader variants = {3}/{4} = {5}% - Total = {6}/{7} = {8}% - Time={9}Ms", shader.name, snippetData.passName, snippetData.shaderType.ToString(), currVariantsCount, prevVariantsCount, percentageCurrent, m_TotalVariantsOutputCount, m_TotalVariantsInputCount, percentageTotal, stripTimeMs); Debug.Log(result); }
static void ExposedDecalInputsFromShaderGraph(Material material, HDShaderUtils.ShaderID id) { if (id == HDShaderUtils.ShaderID.Decal) { // In order for the new properties (kAffectsAlbedo...) to be taken into account, we need to make it dirty so that the parameter is created first HDShaderUtils.ResetMaterialKeywords(material); var serializedMaterial = new SerializedObject(material); // Note: the property must not exist in the .shader for RemoveSerializedFloat to work (otherwise it will be re-added) const string kAlbedoMode = "_AlbedoMode"; float albedoMode = 1.0f; if (TryFindProperty(serializedMaterial, kAlbedoMode, SerializedType.Float, out var propertyAlbedoMode, out _, out _)) { albedoMode = propertyAlbedoMode.floatValue; RemoveSerializedFloat(serializedMaterial, kAlbedoMode); } // For normal map we don't remove the property _NormalMap but just check if there is a texture assign and then enable _AffectNormal const string kNormalMap = "_NormalMap"; float normalMap = 0.0f; if (TryFindProperty(serializedMaterial, kNormalMap, SerializedType.Texture, out var propertyNormalTexture, out _, out _)) { normalMap = propertyNormalTexture.FindPropertyRelative("m_Texture").objectReferenceValue != null ? 1.0f : 0.0f; } // For normal map we don't remove the property _NormalMap but just check if there is a texture assign and then enable _AffectNormal const string kMaskMap = "_MaskMap"; float maskMap = 0.0f; if (TryFindProperty(serializedMaterial, kMaskMap, SerializedType.Texture, out var propertyMaskMapTexture, out _, out _)) { maskMap = propertyMaskMapTexture.FindPropertyRelative("m_Texture").objectReferenceValue != null ? 1.0f : 0.0f; } const string kMaskmapMetal = "_MaskmapMetal"; float maskMapMetal = 0.0f; if (TryFindProperty(serializedMaterial, kMaskmapMetal, SerializedType.Float, out var propertyMaskMapMetal, out _, out _)) { maskMapMetal = propertyMaskMapMetal.floatValue; RemoveSerializedFloat(serializedMaterial, kMaskmapMetal); } const string kMaskmapAO = "_MaskmapAO"; float maskMapAO = 0.0f; if (TryFindProperty(serializedMaterial, kMaskmapAO, SerializedType.Float, out var propertyMaskMapAO, out _, out _)) { maskMapAO = propertyMaskMapAO.floatValue; RemoveSerializedFloat(serializedMaterial, kMaskmapAO); } const string kMaskmapSmoothness = "_MaskmapSmoothness"; float maskMapSmoothness = 0.0f; if (TryFindProperty(serializedMaterial, kMaskmapSmoothness, SerializedType.Float, out var propertyMaskMapSmoothness, out _, out _)) { maskMapSmoothness = propertyMaskMapSmoothness.floatValue; RemoveSerializedFloat(serializedMaterial, kMaskmapSmoothness); } const string kEmissive = "_Emissive"; float emissive = 0.0f; if (TryFindProperty(serializedMaterial, kEmissive, SerializedType.Float, out var propertyEmissive, out _, out _)) { emissive = propertyEmissive.floatValue; RemoveSerializedFloat(serializedMaterial, kEmissive); } // Not used anymore, just removed const string kMaskBlendMode = "_MaskBlendMode"; if (TryFindProperty(serializedMaterial, kMaskBlendMode, SerializedType.Float, out var propertyUnused, out _, out _)) { RemoveSerializedFloat(serializedMaterial, kMaskBlendMode); } serializedMaterial.ApplyModifiedProperties(); // Now apply old value to new properties const string kAffectAlbedo = "_AffectAlbedo"; material.SetFloat(kAffectAlbedo, albedoMode); const string kAffectNormal = "_AffectNormal"; material.SetFloat(kAffectNormal, normalMap); const string kAffectSmoothness = "_AffectSmoothness"; material.SetFloat(kAffectSmoothness, maskMapSmoothness * maskMap); const string kAffectMetal = "_AffectMetal"; material.SetFloat(kAffectMetal, maskMapMetal * maskMap); const string kAffectAO = "_AffectAO"; material.SetFloat(kAffectAO, maskMapAO * maskMap); const string kAffectEmission = "_AffectEmission"; material.SetFloat(kAffectEmission, emissive); // We can't erase obsolete disabled pass from already existing Material, so we need to re-enable all of them const string s_MeshDecalsMStr = "DBufferMesh_M"; const string s_MeshDecalsSStr = "DBufferMesh_S"; const string s_MeshDecalsMSStr = "DBufferMesh_MS"; const string s_MeshDecalsAOStr = "DBufferMesh_AO"; const string s_MeshDecalsMAOStr = "DBufferMesh_MAO"; const string s_MeshDecalsAOSStr = "DBufferMesh_AOS"; const string s_MeshDecalsMAOSStr = "DBufferMesh_MAOS"; const string s_MeshDecals3RTStr = "DBufferMesh_3RT"; const string s_MeshDecalsForwardEmissive = "Mesh_Emissive"; material.SetShaderPassEnabled(s_MeshDecalsMStr, true); material.SetShaderPassEnabled(s_MeshDecalsSStr, true); material.SetShaderPassEnabled(s_MeshDecalsMSStr, true); material.SetShaderPassEnabled(s_MeshDecalsAOStr, true); material.SetShaderPassEnabled(s_MeshDecalsMAOStr, true); material.SetShaderPassEnabled(s_MeshDecalsAOSStr, true); material.SetShaderPassEnabled(s_MeshDecalsMAOSStr, true); material.SetShaderPassEnabled(s_MeshDecals3RTStr, true); material.SetShaderPassEnabled(s_MeshDecalsForwardEmissive, true); } if (id == HDShaderUtils.ShaderID.SG_Decal) { // We can't erase obsolete disabled pass from already existing Material, so we need to re-enable all of them const string s_ShaderGraphMeshDecals4RT = "ShaderGraph_DBufferMesh4RT"; const string s_ShaderGraphMeshDecals3RT = "ShaderGraph_DBufferMesh3RT"; const string s_ShaderGraphMeshDecalForwardEmissive = "ShaderGraph_MeshEmissive"; material.SetShaderPassEnabled(s_ShaderGraphMeshDecals4RT, true); material.SetShaderPassEnabled(s_ShaderGraphMeshDecals3RT, true); material.SetShaderPassEnabled(s_ShaderGraphMeshDecalForwardEmissive, true); } if (id == HDShaderUtils.ShaderID.Decal || id == HDShaderUtils.ShaderID.SG_Decal) { HDShaderUtils.ResetMaterialKeywords(material); } }