Files
zeling_v2/Assets/Scripts/Audio/CombatSFXController.cs
2026-05-08 11:04:00 +08:00

86 lines
2.9 KiB
C#

using UnityEngine;
using BaseGames.Core.Events;
using BaseGames.Combat;
namespace BaseGames.Audio
{
/// <summary>
/// 订阅战斗/死亡事件,通过 AudioManager 播放对应 SFX。
/// 挂载在 Persistent 场景的 [Systems] GameObject 上。
/// </summary>
public class CombatSFXController : MonoBehaviour
{
[Header("Event Channels")]
[SerializeField] private HitConfirmedEventChannelSO _onHitConfirmed;
[SerializeField] private VoidEventChannelSO _onPlayerDied;
[Header("Default Hit SFX")]
[SerializeField] private AudioClip _defaultHitSFX;
[Header("Per-Type Hit SFX (optional, overrides default)")]
[SerializeField] private AudioClip _sparkHitSFX;
[SerializeField] private AudioClip _slashHitSFX;
[SerializeField] private AudioClip _bloodHitSFX;
[SerializeField] private AudioClip _magicHitSFX;
[SerializeField] private AudioClip _heavyHitSFX;
[SerializeField] private AudioClip _critHitSFX;
[SerializeField] private AudioClip _parryHitSFX;
[SerializeField] private AudioClip _fireHitSFX;
[SerializeField] private AudioClip _iceHitSFX;
[Header("Death SFX")]
[SerializeField] private AudioClip _playerDeathSFX;
private void OnEnable()
{
if (_onHitConfirmed != null)
_onHitConfirmed.OnEventRaised += HandleHit;
if (_onPlayerDied != null)
_onPlayerDied.OnEventRaised += HandlePlayerDied;
}
private void OnDisable()
{
if (_onHitConfirmed != null)
_onHitConfirmed.OnEventRaised -= HandleHit;
if (_onPlayerDied != null)
_onPlayerDied.OnEventRaised -= HandlePlayerDied;
}
private void HandleHit(HitInfo info)
{
AudioClip clip = ResolveHitClip(info.DamageInfo.FxType);
if (clip == null) return;
AudioManager.Instance.PlaySFXAtPosition(clip, info.HitPoint);
}
private void HandlePlayerDied()
{
if (_playerDeathSFX == null) return;
AudioManager.Instance.PlaySFX(_playerDeathSFX);
}
private AudioClip ResolveHitClip(HitFxType fxType)
{
AudioClip perType = fxType switch
{
HitFxType.Spark => _sparkHitSFX,
HitFxType.Slash => _slashHitSFX,
HitFxType.Blood => _bloodHitSFX,
HitFxType.Magic => _magicHitSFX,
HitFxType.Heavy => _heavyHitSFX,
HitFxType.Crit => _critHitSFX,
HitFxType.Parry => _parryHitSFX,
HitFxType.Fire => _fireHitSFX,
HitFxType.Ice => _iceHitSFX,
_ => null
};
return perType != null ? perType : _defaultHitSFX;
}
}
}