Files
Cielonos/Assets/Scripts/MainGame/Characters/Base/Subcontrollers/RenderSubcontrollerBase.cs
SoulliesOfficial 7c1cb7e8e1 Temp FIN
2025-12-14 18:40:00 -05:00

216 lines
7.7 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 System;
using System.Collections.Generic;
using DG.Tweening;
using DG.Tweening.Core;
using DG.Tweening.Plugins.Options;
using Sirenix.OdinInspector;
using TrailsFX;
using UnityEngine;
using UnityEngine.Rendering;
using UnityEngine.Serialization;
namespace Cielonos.MainGame.Characters
{
[ExecuteInEditMode]
public partial class RenderSubcontrollerBase : SubcontrollerBase<CharacterBase>
{
public List<SkinnedMeshRenderer> baseRenderers;
public List<Material> baseRenderMaterials;
public Dictionary<string, GameObject> effectContainers;
[HideInEditorMode]
public Dictionary<string, List<SkinnedMeshRenderer>> effectRenderers;
[HideInEditorMode]
public Dictionary<string, List<Material>> effectRenderMaterials;
public List<TrailEffect> dashTrails;
}
public partial class RenderSubcontrollerBase
{
public override void Initialize()
{
base.Initialize();
baseRenderMaterials = new List<Material>();
foreach (SkinnedMeshRenderer renderer in baseRenderers)
{
baseRenderMaterials.AddRange(renderer.materials);
}
effectRenderers = new Dictionary<string, List<SkinnedMeshRenderer>>();
effectRenderMaterials = new Dictionary<string, List<Material>>();
foreach (KeyValuePair<string, GameObject> container in effectContainers)
{
effectRenderers[container.Key] = new List<SkinnedMeshRenderer>(container.Value.GetComponentsInChildren<SkinnedMeshRenderer>());
}
foreach (var kvp in effectRenderers)
{
List<Material> mats = new List<Material>();
foreach (SkinnedMeshRenderer renderer in kvp.Value)
{
mats.AddRange(renderer.materials);
}
effectRenderMaterials[kvp.Key] = mats;
}
}
}
public partial class RenderSubcontrollerBase
{
public void SetTransparency(bool isTransparent, float alpha)
{
foreach (Material mat in baseRenderMaterials)
{
// 获取当前颜色 (URP Lit Shader 使用 _BaseColor)
// 如果你的材质球使用的是标准颜色属性mat.color 也可以,但在 URP 中显式获取更安全
Color baseColor = mat.HasProperty("_BaseColor") ? mat.GetColor("_BaseColor") : mat.color;
if (isTransparent)
{
// === 1. 设置透明模式 ===
mat.SetFloat("_Surface", 1.0f); // Inspector 显示为 Transparent
mat.SetFloat("_Blend", 0.0f); // Inspector 显示为 Alpha
// === 关键修正:必须手动设置混合因子 ===
// SrcAlpha (5) 和 OneMinusSrcAlpha (10) 是标准透明混合公式
mat.SetInt("_SrcBlend", (int)BlendMode.SrcAlpha);
mat.SetInt("_DstBlend", (int)BlendMode.OneMinusSrcAlpha);
// 关闭深度写入
mat.SetInt("_ZWrite", 0);
// 启用关键字
mat.EnableKeyword("_SURFACE_TYPE_TRANSPARENT");
// 设置渲染队列
mat.renderQueue = (int)RenderQueue.Transparent;
// 设置带透明度的颜色
baseColor.a = alpha;
if (mat.HasProperty("_BaseColor"))
mat.SetColor("_BaseColor", baseColor);
else
mat.color = baseColor;
}
else
{
// === 2. 恢复不透明模式 ===
mat.SetFloat("_Surface", 0.0f); // Inspector 显示为 Opaque
mat.SetFloat("_Blend", 0.0f);
// === 关键修正:恢复不透明混合因子 ===
// One (1) 和 Zero (0) 意味着完全覆盖背景
mat.SetInt("_SrcBlend", (int)BlendMode.One);
mat.SetInt("_DstBlend", (int)BlendMode.Zero);
// 开启深度写入 (这非常重要,否则之前的刀光问题会复发)
mat.SetInt("_ZWrite", 1);
// 禁用关键字
mat.DisableKeyword("_SURFACE_TYPE_TRANSPARENT");
// 恢复默认渲染队列 (通常是 -1代表使用 Shader 默认值 2000)
mat.renderQueue = -1;
// 恢复完全不透明颜色
baseColor.a = 1.0f;
if (mat.HasProperty("_BaseColor"))
mat.SetColor("_BaseColor", baseColor);
else
mat.color = baseColor;
}
}
}
}
public partial class RenderSubcontrollerBase
{
private Sequence getHitBlinkTween;
public void GetHitBlink()
{
getHitBlinkTween?.Kill(true);
getHitBlinkTween = DOTween.Sequence();
getHitBlinkTween.OnPlay(() =>
{
effectContainers["GetHitBlink"].SetActive(true);
});
foreach (Material mat in effectRenderMaterials["GetHitBlink"])
{
TweenerCore<Color, Color, ColorOptions> matTween = mat.DOColor(Color.white * 0.5f, "_EmissionColor", 0.05f)
.OnStart(() => mat.EnableKeyword("_EMISSION"))
.From(Color.black)
.SetEase(Ease.OutQuad)
.OnComplete(() =>
{
mat.SetColor("_EmissionColor", Color.black);
mat.DisableKeyword("_EMISSION");
});
getHitBlinkTween.Join(matTween);
}
getHitBlinkTween.SetLoops(2, LoopType.Yoyo);
getHitBlinkTween.OnComplete(() =>
{
effectContainers["GetHitBlink"].SetActive(false);
});
getHitBlinkTween.Play();
}
}
public partial class RenderSubcontrollerBase
{
private Sequence outlineOnTween;
private Sequence outlineOffTween;
public void OutlineOn(BreakthroughType type, float width, float fadeInDuration)
{
outlineOffTween?.Kill(true);
outlineOnTween?.Kill(true);
outlineOnTween = DOTween.Sequence();
outlineOnTween.OnPlay(() =>
{
effectContainers["Outline"].SetActive(true);
});
foreach (Material mat in effectRenderMaterials["Outline"])
{
mat.SetColor("_Outline_Color", MainGameManager.BasePrefabs.outlineColorCollection[type]);
Tweener matTween = mat.DOFloat(width, "_Outline_Thickness", fadeInDuration)
.From(0.0f)
.SetEase(Ease.OutQuad);
outlineOnTween.Join(matTween);
}
outlineOnTween.Play();
}
public void OutlineOff(float fadeOutDuration)
{
outlineOnTween?.Kill(true);
outlineOffTween?.Kill(true);
outlineOffTween = DOTween.Sequence();
foreach (Material mat in effectRenderMaterials["Outline"])
{
Tweener matTween = mat.DOFloat(0.0f, "_Outline_Thickness", fadeOutDuration)
.SetEase(Ease.OutQuad);
outlineOffTween.Join(matTween);
}
outlineOffTween.OnComplete(() =>
{
effectContainers["Outline"].SetActive(false);
});
outlineOffTween.Play();
}
}
}