audio manager

godot-4.2
John Montagu, the 4th Earl of Sandvich 2023-09-09 01:00:13 -07:00
parent bd276dffc3
commit eb63e05dd2
Signed by: sandvich
GPG Key ID: 9A39BE37E602B22D
4 changed files with 205 additions and 14 deletions

View File

@ -12,8 +12,8 @@ dest_files=["res://.godot/imported/gillette.mp3-5dd6f93f1f9df01778f80e3dd2caeb1e
[params]
loop=false
loop_offset=0
bpm=0
loop=true
loop_offset=0.0
bpm=0.0
beat_count=0
bar_beats=4

View File

@ -0,0 +1,191 @@
using Godot;
using System.Collections.Generic;
namespace SupaLidlGame.Utils;
public sealed partial class AudioManager : Node
{
public enum Layer
{
Ambient,
BackgroundMusic,
ActiveMusic,
};
//private Array<AudioStreamPlayer> _players;
private Dictionary<Layer, AudioStreamPlayer> _players;
public override void _Ready()
{
_players = new Dictionary<Layer, AudioStreamPlayer>();
_players.Add(Layer.Ambient, null);
_players.Add(Layer.BackgroundMusic, null);
_players.Add(Layer.ActiveMusic, null);
}
public void PlayAmbient(AudioStream stream)
{
StopPlayback(Layer.Ambient);
_players[Layer.Ambient] = CreateAudioStreamPlayer(stream);
FadeIn(_players[Layer.Ambient]);
}
public void PlayBackground(AudioStream stream)
{
StopPlayback(Layer.BackgroundMusic);
_players[Layer.BackgroundMusic] = CreateAudioStreamPlayer(stream);
if (!IsLayerValid(Layer.ActiveMusic))
{
FadeIn(_players[Layer.BackgroundMusic]);
}
}
public void StopBackground()
{
StopPlayback(Layer.BackgroundMusic);
}
public void PlayActive(AudioStream stream)
{
_players[Layer.ActiveMusic] = CreateAudioStreamPlayer(stream);
_players[Layer.ActiveMusic].Play();
if (IsLayerValid(Layer.BackgroundMusic))
{
Pause(Layer.BackgroundMusic);
}
}
public void StopActive()
{
StopPlayback(Layer.ActiveMusic);
if (IsLayerValid(Layer.BackgroundMusic))
{
if (_players[Layer.BackgroundMusic].StreamPaused)
{
Unpause(Layer.BackgroundMusic);
}
else
{
_players[Layer.BackgroundMusic].Play();
}
}
}
public void Play(AudioStream stream, Layer layer)
{
switch (layer)
{
case Layer.Ambient:
PlayAmbient(stream);
break;
case Layer.BackgroundMusic:
PlayBackground(stream);
break;
case Layer.ActiveMusic:
PlayActive(stream);
break;
}
}
public void Stop(Layer layer)
{
switch (layer)
{
case Layer.Ambient:
case Layer.BackgroundMusic:
StopPlayback(layer);
break;
case Layer.ActiveMusic:
StopActive();
break;
}
}
private void Pause(Layer layer)
{
var player = _players[layer];
if (player is null || !IsInstanceValid(player))
{
return;
}
FadeOut(player, pause: true);
}
private void Unpause(Layer layer)
{
var player = _players[layer];
if (player is null || !IsInstanceValid(player))
{
return;
}
FadeIn(player, unpause: true);
}
private void StopPlayback(Layer layer)
{
var player = _players[layer];
if (player is null || !IsInstanceValid(player))
{
return;
}
FadeOut(player, kill: true);
_players[layer] = null;
}
private AudioStreamPlayer CreateAudioStreamPlayer(AudioStream stream)
{
var player = new AudioStreamPlayer();
AddChild(player);
player.Stream = stream;
return player;
}
private void FadeOut(
AudioStreamPlayer player,
double time = 1.0,
bool kill = false,
bool pause = false)
{
var tween = player.GetTree().CreateTween().BindNode(player);
tween.TweenProperty(player, "volume_db", 0, time);
if (kill)
{
tween.TweenCallback(Callable.From(player.QueueFree));
}
else if (pause)
{
tween.TweenCallback(
Callable.From(() => player.StreamPaused = true));
}
}
private void FadeIn(AudioStreamPlayer player,
double time = 1.0,
bool unpause = false)
{
if (unpause)
{
player.StreamPaused = false;
}
else
{
player.Play();
}
player.VolumeDb = 0;
var tween = player.GetTree().CreateTween().BindNode(player);
tween.TweenProperty(player, "volume_db", 1, time);
}
public bool IsLayerValid(Layer layer)
{
var player = _players[layer];
return player is not null && IsInstanceValid(player);
}
}

View File

@ -117,23 +117,19 @@ public partial class World : Node
private void RegisterBoss(Boss boss)
{
if (boss is null)
{
DeregisterBoss(CurrentBoss);
return;
}
CurrentBoss = boss;
MusicPlayer.Stream = boss?.Music;
// TODO: use an audio manager
if (MusicPlayer.Stream is null)
{
MusicPlayer.Stop();
}
else
{
MusicPlayer.Play();
}
GetNode<AudioManager>("/root/AudioManager").PlayActive(boss.Music);
}
private void DeregisterBoss(Boss boss)
{
CurrentBoss = null;
MusicPlayer.Stop();
GetNode<AudioManager>("/root/AudioManager").StopActive();
}
private void LoadMap(Map map)
@ -230,6 +226,9 @@ public partial class World : Node
SpawnPlayer();
};
GlobalState.Stats.DeathCount++;
//EventBus.EmitSignal(EventBus.SignalName.DeregisteredBoss,
// CurrentBoss);
};
return CurrentPlayer;

View File

@ -22,6 +22,7 @@ GlobalState="*res://State/Global/GlobalState.cs"
EventBus="*res://Events/EventBus.cs"
BaseUI="*res://UI/Base.tscn"
World="*res://Scenes/Level.tscn"
AudioManager="*res://Utils/AudioManager.cs"
DebugConsole="*res://Debug/DebugConsole.cs"
Panku="*res://addons/panku_console/console.tscn"