DCS/ruiyiweiUX/Assets/Scripts/Components/MaterialRenderModeHelper.cs

112 lines
4.8 KiB
C#
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

using UnityEngine;
/// <summary>
/// 材质渲染模式助手类
/// 用于设置材质的正确渲染模式以支持透明度
/// </summary>
public static class MaterialRenderModeHelper
{
public enum BlendMode
{
Opaque,
Cutout,
Fade, // Traditional transparency (ZWrite OFF)
Transparent, // Physically based transparency (ZWrite OFF)
AlphaBlendWithDepth // Alpha blend with depth write (ZWrite ON) - 解决Body显示问题
}
/// <summary>
/// 设置材质的渲染模式
/// </summary>
/// <param name="material">要设置的材质</param>
/// <param name="blendMode">渲染模式</param>
public static void SetMaterialRenderMode(Material material, BlendMode blendMode)
{
switch (blendMode)
{
case BlendMode.Opaque:
material.SetInt("_SrcBlend", (int)UnityEngine.Rendering.BlendMode.One);
material.SetInt("_DstBlend", (int)UnityEngine.Rendering.BlendMode.Zero);
material.SetInt("_ZWrite", 1);
material.DisableKeyword("_ALPHATEST_ON");
material.DisableKeyword("_ALPHABLEND_ON");
material.DisableKeyword("_ALPHAPREMULTIPLY_ON");
material.renderQueue = -1;
break;
case BlendMode.Cutout:
material.SetInt("_SrcBlend", (int)UnityEngine.Rendering.BlendMode.One);
material.SetInt("_DstBlend", (int)UnityEngine.Rendering.BlendMode.Zero);
material.SetInt("_ZWrite", 1);
material.EnableKeyword("_ALPHATEST_ON");
material.DisableKeyword("_ALPHABLEND_ON");
material.DisableKeyword("_ALPHAPREMULTIPLY_ON");
material.renderQueue = (int)UnityEngine.Rendering.RenderQueue.AlphaTest;
break;
case BlendMode.Fade:
material.SetInt("_SrcBlend", (int)UnityEngine.Rendering.BlendMode.SrcAlpha);
material.SetInt("_DstBlend", (int)UnityEngine.Rendering.BlendMode.OneMinusSrcAlpha);
material.SetInt("_ZWrite", 0);
material.DisableKeyword("_ALPHATEST_ON");
material.EnableKeyword("_ALPHABLEND_ON");
material.DisableKeyword("_ALPHAPREMULTIPLY_ON");
material.renderQueue = (int)UnityEngine.Rendering.RenderQueue.Transparent;
break;
case BlendMode.Transparent:
material.SetInt("_SrcBlend", (int)UnityEngine.Rendering.BlendMode.One);
material.SetInt("_DstBlend", (int)UnityEngine.Rendering.BlendMode.OneMinusSrcAlpha);
material.SetInt("_ZWrite", 0);
material.DisableKeyword("_ALPHATEST_ON");
material.DisableKeyword("_ALPHABLEND_ON");
material.EnableKeyword("_ALPHAPREMULTIPLY_ON");
material.renderQueue = (int)UnityEngine.Rendering.RenderQueue.Transparent;
break;
case BlendMode.AlphaBlendWithDepth:
// 关键修复:保持深度写入的透明混合模式
material.SetInt("_SrcBlend", (int)UnityEngine.Rendering.BlendMode.SrcAlpha);
material.SetInt("_DstBlend", (int)UnityEngine.Rendering.BlendMode.OneMinusSrcAlpha);
material.SetInt("_ZWrite", 1); // 保持深度写入这样Body即使单独存在也能正确显示
material.DisableKeyword("_ALPHATEST_ON");
material.EnableKeyword("_ALPHABLEND_ON");
material.DisableKeyword("_ALPHAPREMULTIPLY_ON");
// 使用较早的渲染队列,确保在其他透明物体之前渲染
material.renderQueue = (int)UnityEngine.Rendering.RenderQueue.Geometry + 450;
break;
}
}
/// <summary>
/// 自动检测并设置合适的渲染模式
/// </summary>
/// <param name="material">材质</param>
/// <param name="alpha">透明度值</param>
public static void AutoSetRenderMode(Material material, float alpha)
{
if (alpha >= 1.0f)
{
SetMaterialRenderMode(material, BlendMode.Opaque);
}
else
{
SetMaterialRenderMode(material, BlendMode.AlphaBlendWithDepth);
}
}
/// <summary>
/// 专门为Body设置渲染模式
/// 确保Body在单独显示时也能正确显示
/// </summary>
/// <param name="material">Body材质</param>
/// <param name="alpha">透明度值</param>
public static void SetBodyRenderMode(Material material, float alpha)
{
if (alpha >= 1.0f)
{
SetMaterialRenderMode(material, BlendMode.Opaque);
}
else
{
// 对于Body始终使用保持深度写入的透明模式
SetMaterialRenderMode(material, BlendMode.AlphaBlendWithDepth);
}
}
}