using GFramework.Core.extensions; using GFramework.Core.system; using Godot; namespace GFramework.Core.Godot.system; /// /// 音频管理器抽象基类,提供音频播放的基础实现 /// public abstract class AbstractAudioManagerSystem : AbstractSystem, IAudioManagerSystem { /// /// 音频资源加载系统依赖 /// protected IResourceLoadSystem? ResourceLoadSystem; /// /// 资源目录系统依赖 /// protected IAssetCatalogSystem? AssetCatalogSystem; /// /// 背景音乐播放器 /// protected AudioStreamPlayer? MusicPlayer; /// /// 音效播放器列表 /// protected readonly List SoundPlayers = []; /// /// 可用音效播放器队列 /// protected readonly Queue AvailableSoundPlayers = new(); /// /// 3D音效播放器列表 /// protected readonly List Sound3DPlayers = []; /// /// 可用3D音效播放器队列 /// protected readonly Queue AvailableSound3DPlayers = new(); /// /// 资源工厂系统依赖 /// protected IResourceFactorySystem? ResourceFactorySystem; /// /// 背景音乐音量 /// protected float MusicVolume = 1.0f; /// /// 音效音量 /// protected float SoundVolume = 1.0f; /// /// 主音量 /// protected float MasterVolume = 1.0f; /// /// 特效音量 /// protected float SfxVolume = 1.0f; /// /// 语音音量 /// protected float VoiceVolume = 1.0f; /// /// 环境音量 /// protected float AmbientVolume = 1.0f; /// /// 音乐淡入淡出动画 /// protected Tween? MusicFadeTween; /// /// 最大同时播放的音效数量 /// protected const int MaxSoundPlayers = 10; /// /// 最大同时播放的3D音效数量 /// protected const int MaxSound3DPlayers = 5; /// /// 所有者节点的抽象属性 /// protected abstract Node Owner { get; } /// /// 系统初始化方法 /// protected override void OnInit() { // 获取依赖的系统 ResourceLoadSystem = this.GetSystem(); AssetCatalogSystem = this.GetSystem(); ResourceFactorySystem = this.GetSystem(); // 初始化背景音乐播放器 MusicPlayer = new AudioStreamPlayer(); Owner.AddChild(MusicPlayer); // 预创建音效播放器池 for (var i = 0; i < MaxSoundPlayers; i++) { var soundPlayer = new AudioStreamPlayer(); Owner.AddChild(soundPlayer); soundPlayer.Finished += () => OnSoundFinished(soundPlayer); SoundPlayers.Add(soundPlayer); AvailableSoundPlayers.Enqueue(soundPlayer); } // 预创建3D音效播放器池 for (var i = 0; i < MaxSound3DPlayers; i++) { var sound3DPlayer = new AudioStreamPlayer3D(); Owner.AddChild(sound3DPlayer); sound3DPlayer.Finished += () => OnSound3DFinished(sound3DPlayer); Sound3DPlayers.Add(sound3DPlayer); AvailableSound3DPlayers.Enqueue(sound3DPlayer); } } /// /// 当音效播放完成时的回调 /// /// 完成播放的音频播放器 private void OnSoundFinished(AudioStreamPlayer player) { // 将播放器放回可用队列 AvailableSoundPlayers.Enqueue(player); } /// /// 当3D音效播放完成时的回调 /// /// 完成播放的3D音频播放器 private void OnSound3DFinished(AudioStreamPlayer3D player) { // 将播放器放回可用队列 AvailableSound3DPlayers.Enqueue(player); } /// /// 播放背景音乐 /// /// 音频文件路径 /// 音量大小,范围0-1 /// 是否循环播放 public virtual void PlayMusic(string audioPath, float volume = 1.0f, bool loop = true) { var audioStream = ResourceLoadSystem?.LoadResource(audioPath); if (audioStream == null || MusicPlayer == null) return; // 停止当前正在进行的淡入淡出效果 MusicFadeTween?.Kill(); MusicPlayer.Stream = audioStream; MusicPlayer.VolumeDb = LinearToDb(volume * MusicVolume * MasterVolume); MusicPlayer.Play(); } /// /// 通过资源ID播放背景音乐 /// /// 音乐资源ID /// 音量大小,范围0-1 /// 是否循环播放 public virtual void PlayMusic(AssetCatalog.ResourceId musicId, float volume = 1.0f, bool loop = true) { PlayMusic(musicId.Path, volume, loop); } /// /// 播放音效 /// /// 音频文件路径 /// 音量大小,范围0-1 /// 音调调整 public virtual void PlaySound(string audioPath, float volume = 1.0f, float pitch = 1.0f) { if (AvailableSoundPlayers.Count == 0) return; var audioStream = ResourceLoadSystem?.LoadResource(audioPath); if (audioStream == null) return; var player = AvailableSoundPlayers.Dequeue(); player.Stream = audioStream; player.VolumeDb = LinearToDb(volume * SoundVolume * MasterVolume); player.Play(); } /// /// 通过资源ID播放音效 /// /// 音效资源ID /// 音量大小,范围0-1 /// 音调调整 public virtual void PlaySound(AssetCatalog.ResourceId soundId, float volume = 1.0f, float pitch = 1.0f) { PlaySound(soundId.Path, volume, pitch); } /// /// 播放3D音效 /// /// 音频文件路径 /// 3D空间中的位置 /// 音量大小,范围0-1 public virtual void PlaySound3D(string audioPath, Vector3 position, float volume = 1.0f) { if (AvailableSound3DPlayers.Count == 0) return; var audioStream = ResourceLoadSystem?.LoadResource(audioPath); if (audioStream == null) return; var player = AvailableSound3DPlayers.Dequeue(); player.Stream = audioStream; player.VolumeDb = LinearToDb(volume * SoundVolume * MasterVolume); player.Position = position; player.Play(); } /// /// 停止背景音乐 /// public virtual void StopMusic() { MusicFadeTween?.Kill(); MusicPlayer?.Stop(); } /// /// 暂停背景音乐 /// public virtual void PauseMusic() { MusicFadeTween?.Kill(); // todo 需要记录音乐播放位置,以便恢复播放时从正确位置开始 } /// /// 恢复背景音乐播放 /// public virtual void ResumeMusic() { MusicPlayer?.Play(); } /// /// 设置背景音乐音量 /// /// 音量大小,范围0-1 public virtual void SetMusicVolume(float volume) { MusicVolume = volume; if (MusicPlayer != null) { MusicPlayer.VolumeDb = LinearToDb(MusicVolume * MasterVolume); } } /// /// 设置音效音量 /// /// 音量大小,范围0-1 public virtual void SetSoundVolume(float volume) { SoundVolume = volume; } /// /// 设置主音量 /// /// 音量大小,范围0-1 public virtual void SetMasterVolume(float volume) { MasterVolume = volume; // 更新音乐音量 if (MusicPlayer != null) { MusicPlayer.VolumeDb = LinearToDb(MusicVolume * MasterVolume); } } /// /// 设置SFX音量 /// /// 音量大小,范围0-1 public virtual void SetSfxVolume(float volume) { SfxVolume = volume; } /// /// 设置语音音量 /// /// 音量大小,范围0-1 public virtual void SetVoiceVolume(float volume) { VoiceVolume = volume; } /// /// 设置环境音量 /// /// 音量大小,范围0-1 public virtual void SetAmbientVolume(float volume) { AmbientVolume = volume; } /// /// 检查背景音乐是否正在播放 /// /// 正在播放返回true,否则返回false public virtual bool IsMusicPlaying() { return MusicPlayer?.Playing ?? false; } /// /// 淡入背景音乐 /// /// 音频文件路径 /// 淡入持续时间(秒) /// 目标音量 public virtual void FadeInMusic(string audioPath, float duration, float volume = 1.0f) { var audioStream = ResourceLoadSystem?.LoadResource(audioPath); if (audioStream == null || MusicPlayer == null) return; // 停止当前正在进行的淡入淡出效果 MusicFadeTween?.Kill(); MusicPlayer.Stream = audioStream; MusicPlayer.VolumeDb = LinearToDb(0.0f); // 初始音量为0 MusicPlayer.Play(); // 创建淡入动画 MusicFadeTween = Owner.CreateTween(); MusicFadeTween.TweenProperty(MusicPlayer, "volume_db", LinearToDb(volume * MusicVolume * MasterVolume), duration); } /// /// 淡出背景音乐 /// /// 淡出持续时间(秒) public virtual void FadeOutMusic(float duration) { if (MusicPlayer == null) return; // 停止当前正在进行的淡入淡出效果 MusicFadeTween?.Kill(); // 创建淡出动画 MusicFadeTween = Owner.CreateTween(); MusicFadeTween.TweenProperty(MusicPlayer, "volume_db", LinearToDb(0.0f), duration); MusicFadeTween.TweenCallback(Callable.From(() => MusicPlayer.Stop())); } /// /// 设置低通滤波器强度 /// /// 滤波器强度,范围0-1 public virtual void SetLowPassFilter(float amount) { // TODO: 实现低通滤波器效果 // 可以通过AudioEffectLowPassFilter实现 } /// /// 设置音频混响效果 /// /// 房间大小 /// 阻尼 /// 湿声级别 public virtual void SetReverb(float roomSize, float damping, float wetLevel) { // TODO: 实现音频混响效果 // 可以通过AudioEffectReverb实现 } /// /// 将线性音量值转换为分贝值 /// /// 线性音量值(0-1) /// 分贝值 protected static float LinearToDb(float linear) { return linear > 0 ? 20 * Mathf.Log(linear) : -100; } /// /// 将分贝值转换为线性音量值 /// /// 分贝值 /// 线性音量值(0-1) protected static float DbToLinear(float db) { return db > -100 ? Mathf.Exp(db / 20) : 0; } /// /// 系统销毁时清理资源 /// protected override void OnDestroy() { // 停止并清理淡入淡出动画 MusicFadeTween?.Kill(); // 清理音乐播放器 MusicPlayer?.QueueFree(); // 清理音效播放器池 foreach (var player in SoundPlayers) { player.QueueFree(); } // 清理3D音效播放器池 foreach (var player in Sound3DPlayers) { player.QueueFree(); } SoundPlayers.Clear(); AvailableSoundPlayers.Clear(); Sound3DPlayers.Clear(); AvailableSound3DPlayers.Clear(); } }