]> git.smokeofanarchy.ru Git - space-station-14.git/commitdiff
Add UI click sounds (#22410)
authormetalgearsloth <31366439+metalgearsloth@users.noreply.github.com>
Fri, 29 Dec 2023 04:43:36 +0000 (15:43 +1100)
committerGitHub <noreply@github.com>
Fri, 29 Dec 2023 04:43:36 +0000 (15:43 +1100)
* Add UI click sounds

* tweaks

* Significant cleanup

* Audio options and numerous fixes

* Fix the remaining UI elements

* new click sound

---------

Co-authored-by: Kara <lunarautomaton6@gmail.com>
19 files changed:
Content.Client/Audio/AudioUIController.cs [new file with mode: 0644]
Content.Client/Audio/ContentAudioSystem.cs
Content.Client/Construction/UI/ConstructionMenuPresenter.cs
Content.Client/Options/UI/Tabs/AudioTab.xaml
Content.Client/Options/UI/Tabs/AudioTab.xaml.cs
Content.Client/UserInterface/Systems/Actions/ActionUIController.cs
Content.Client/UserInterface/Systems/Actions/Controls/ActionButton.cs
Content.Client/UserInterface/Systems/Admin/AdminUIController.cs
Content.Client/UserInterface/Systems/Bwoink/AHelpUIController.cs
Content.Client/UserInterface/Systems/Character/CharacterUIController.cs
Content.Client/UserInterface/Systems/EscapeMenu/EscapeUIController.cs
Content.Client/UserInterface/Systems/Guidebook/GuidebookUIController.cs
Content.Client/UserInterface/Systems/Inventory/InventoryUIController.cs
Content.Client/UserInterface/Systems/Sandbox/SandboxUIController.cs
Content.Shared/CCVar/CCVars.cs
Resources/Audio/UserInterface/attributions.yml [new file with mode: 0644]
Resources/Audio/UserInterface/click.ogg [new file with mode: 0644]
Resources/Audio/UserInterface/hover.ogg [new file with mode: 0644]
Resources/Locale/en-US/escape-menu/ui/options-menu.ftl

diff --git a/Content.Client/Audio/AudioUIController.cs b/Content.Client/Audio/AudioUIController.cs
new file mode 100644 (file)
index 0000000..ef90367
--- /dev/null
@@ -0,0 +1,98 @@
+using Content.Shared.CCVar;
+using Robust.Client.Audio;
+using Robust.Client.ResourceManagement;
+using Robust.Client.UserInterface.Controllers;
+using Robust.Shared.Audio.Sources;
+using Robust.Shared.Configuration;
+
+namespace Content.Client.Audio;
+
+public sealed class AudioUIController : UIController
+{
+    [Dependency] private readonly IAudioManager _audioManager = default!;
+    [Dependency] private readonly IConfigurationManager _configManager = default!;
+    [Dependency] private readonly IResourceCache _cache = default!;
+
+    private float _interfaceGain;
+    private IAudioSource? _clickSource;
+    private IAudioSource? _hoverSource;
+
+    private const float ClickGain = 0.25f;
+    private const float HoverGain = 0.05f;
+
+    public override void Initialize()
+    {
+        base.Initialize();
+
+        /*
+         * This exists to load UI sounds outside of the game sim.
+         */
+
+        // No unsub coz never shuts down until program exit.
+        _configManager.OnValueChanged(CCVars.UIClickSound, SetClickSound, true);
+        _configManager.OnValueChanged(CCVars.UIHoverSound, SetHoverSound, true);
+
+        _configManager.OnValueChanged(CCVars.InterfaceVolume, SetInterfaceVolume, true);
+    }
+
+    private void SetInterfaceVolume(float obj)
+    {
+        _interfaceGain = obj;
+
+        if (_clickSource != null)
+        {
+            _clickSource.Gain = ClickGain * _interfaceGain;
+        }
+
+        if (_hoverSource != null)
+        {
+            _hoverSource.Gain = HoverGain * _interfaceGain;
+        }
+    }
+
+    private void SetClickSound(string value)
+    {
+        if (!string.IsNullOrEmpty(value))
+        {
+            var resource = _cache.GetResource<AudioResource>(value);
+            var source =
+                _audioManager.CreateAudioSource(resource);
+
+            if (source != null)
+            {
+                source.Gain = ClickGain * _interfaceGain;
+                source.Global = true;
+            }
+
+            _clickSource = source;
+            UIManager.SetClickSound(source);
+        }
+        else
+        {
+            UIManager.SetClickSound(null);
+        }
+    }
+
+    private void SetHoverSound(string value)
+    {
+        if (!string.IsNullOrEmpty(value))
+        {
+            var hoverResource = _cache.GetResource<AudioResource>(value);
+            var hoverSource =
+                _audioManager.CreateAudioSource(hoverResource);
+
+            if (hoverSource != null)
+            {
+                hoverSource.Gain = HoverGain * _interfaceGain;
+                hoverSource.Global = true;
+            }
+
+            _hoverSource = hoverSource;
+            UIManager.SetHoverSound(hoverSource);
+        }
+        else
+        {
+            UIManager.SetHoverSound(null);
+        }
+    }
+}
index 603b1086d8b1bce6174e33633205706f541f5dd0..b5d2d4bcdc58dda51cba74c0778f01e21791facb 100644 (file)
@@ -1,15 +1,18 @@
 using Content.Shared.Audio;
-using Content.Shared.CCVar;
 using Content.Shared.GameTicking;
-using Robust.Client.GameObjects;
-using Robust.Shared;
-using Robust.Shared.Audio;
+using Robust.Client.Audio;
+using Robust.Client.ResourceManagement;
+using Robust.Client.UserInterface;
 using AudioComponent = Robust.Shared.Audio.Components.AudioComponent;
 
 namespace Content.Client.Audio;
 
 public sealed partial class ContentAudioSystem : SharedContentAudioSystem
 {
+    [Dependency] private readonly IAudioManager _audioManager = default!;
+    [Dependency] private readonly IResourceCache _cache = default!;
+    [Dependency] private readonly IUserInterfaceManager _uiManager = default!;
+
     // Need how much volume to change per tick and just remove it when it drops below "0"
     private readonly Dictionary<EntityUid, float> _fadingOut = new();
 
@@ -32,6 +35,7 @@ public sealed partial class ContentAudioSystem : SharedContentAudioSystem
     public const float AmbienceMultiplier = 3f;
     public const float AmbientMusicMultiplier = 3f;
     public const float LobbyMultiplier = 3f;
+    public const float InterfaceMultiplier = 2f;
 
     public override void Initialize()
     {
index 28cf3ba16c0d54bfdc5f6b996404e6947c023985..9a09436176652ee659a60b85bb078e660cbc121b 100644 (file)
@@ -394,7 +394,7 @@ namespace Content.Client.Construction.UI
                 if (IsAtFront)
                 {
                     WindowOpen = false;
-                    _uiManager.GetActiveUIWidget<GameTopMenuBar>().CraftingButton.Pressed = false; // This does not call CraftingButtonToggled
+                    _uiManager.GetActiveUIWidget<GameTopMenuBar>().CraftingButton.SetClickPressed(false); // This does not call CraftingButtonToggled
                 }
                 else
                     _constructionView.MoveToFront();
@@ -402,7 +402,7 @@ namespace Content.Client.Construction.UI
             else
             {
                 WindowOpen = true;
-                _uiManager.GetActiveUIWidget<GameTopMenuBar>().CraftingButton.Pressed = true; // This does not call CraftingButtonToggled
+                _uiManager.GetActiveUIWidget<GameTopMenuBar>().CraftingButton.SetClickPressed(true); // This does not call CraftingButtonToggled
             }
         }
 
index 528b0ac136c6c3ddf5d2419a1a4c734d673e23ab..e54b0dc34ee845da5bb2d0d54a7f633b695cd64a 100644 (file)
                     <Label Name="LobbyVolumeLabel" MinSize="48 0" Align="Right" />
                     <Control MinSize="4 0"/>
                 </BoxContainer>
+                <BoxContainer Orientation="Horizontal" Margin="5 0 0 0">
+                    <Label Text="{Loc 'ui-options-interface-volume'}" HorizontalExpand="True" />
+                    <Control MinSize="8 0" />
+                    <Slider Name="InterfaceVolumeSlider"
+                            MinValue="0"
+                            MaxValue="100"
+                            HorizontalExpand="True"
+                            MinSize="80 0"
+                            Rounded="True" />
+                    <Control MinSize="8 0" />
+                    <Label Name="InterfaceVolumeLabel" MinSize="48 0" Align="Right" />
+                    <Control MinSize="4 0"/>
+                </BoxContainer>
                 <BoxContainer Orientation="Horizontal" Margin="5 0 0 0">
                     <Label Text="{Loc 'ui-options-ambience-max-sounds'}" HorizontalExpand="True" />
                     <Control MinSize="8 0" />
index 80e13d4a43ed355a981f9a9fd613b7fc70bac55d..470ca7d799d8f67779eec1967382b716b523a2e0 100644 (file)
@@ -2,13 +2,10 @@ using Content.Client.Audio;
 using Content.Shared.CCVar;
 using Robust.Client.Audio;
 using Robust.Client.AutoGenerated;
-using Robust.Client.GameObjects;
-using Robust.Client.Graphics;
 using Robust.Client.UserInterface;
 using Robust.Client.UserInterface.Controls;
 using Robust.Client.UserInterface.XAML;
 using Robust.Shared;
-using Robust.Shared.Audio.Systems;
 using Robust.Shared.Configuration;
 using Range = Robust.Client.UserInterface.Controls.Range;
 
@@ -39,6 +36,7 @@ namespace Content.Client.Options.UI.Tabs
             AmbienceVolumeSlider.OnValueChanged += OnAmbienceVolumeSliderChanged;
             AmbienceSoundsSlider.OnValueChanged += OnAmbienceSoundsSliderChanged;
             LobbyVolumeSlider.OnValueChanged += OnLobbyVolumeSliderChanged;
+            InterfaceVolumeSlider.OnValueChanged += OnInterfaceVolumeSliderChanged;
             LobbyMusicCheckBox.OnToggled += OnLobbyMusicCheckToggled;
             RestartSoundsCheckBox.OnToggled += OnRestartSoundsCheckToggled;
             EventMusicCheckBox.OnToggled += OnEventMusicCheckToggled;
@@ -59,6 +57,7 @@ namespace Content.Client.Options.UI.Tabs
             AmbientMusicVolumeSlider.OnValueChanged -= OnAmbientMusicVolumeSliderChanged;
             AmbienceVolumeSlider.OnValueChanged -= OnAmbienceVolumeSliderChanged;
             LobbyVolumeSlider.OnValueChanged -= OnLobbyVolumeSliderChanged;
+            InterfaceVolumeSlider.OnValueChanged -= OnInterfaceVolumeSliderChanged;
             base.Dispose(disposing);
         }
 
@@ -67,6 +66,11 @@ namespace Content.Client.Options.UI.Tabs
             UpdateChanges();
         }
 
+        private void OnInterfaceVolumeSliderChanged(Range obj)
+        {
+            UpdateChanges();
+        }
+
         private void OnAmbientMusicVolumeSliderChanged(Range obj)
         {
             UpdateChanges();
@@ -120,6 +124,7 @@ namespace Content.Client.Options.UI.Tabs
             _cfg.SetCVar(CCVars.AmbienceVolume, AmbienceVolumeSlider.Value / 100f * ContentAudioSystem.AmbienceMultiplier);
             _cfg.SetCVar(CCVars.AmbientMusicVolume, AmbientMusicVolumeSlider.Value / 100f * ContentAudioSystem.AmbientMusicMultiplier);
             _cfg.SetCVar(CCVars.LobbyMusicVolume, LobbyVolumeSlider.Value / 100f * ContentAudioSystem.LobbyMultiplier);
+            _cfg.SetCVar(CCVars.InterfaceVolume, InterfaceVolumeSlider.Value / 100f * ContentAudioSystem.InterfaceMultiplier);
 
             _cfg.SetCVar(CCVars.MaxAmbientSources, (int)AmbienceSoundsSlider.Value);
 
@@ -143,6 +148,7 @@ namespace Content.Client.Options.UI.Tabs
             AmbienceVolumeSlider.Value = _cfg.GetCVar(CCVars.AmbienceVolume) * 100f / ContentAudioSystem.AmbienceMultiplier;
             AmbientMusicVolumeSlider.Value = _cfg.GetCVar(CCVars.AmbientMusicVolume) * 100f / ContentAudioSystem.AmbientMusicMultiplier;
             LobbyVolumeSlider.Value = _cfg.GetCVar(CCVars.LobbyMusicVolume) * 100f / ContentAudioSystem.LobbyMultiplier;
+            InterfaceVolumeSlider.Value = _cfg.GetCVar(CCVars.InterfaceVolume) * 100f / ContentAudioSystem.InterfaceMultiplier;
 
             AmbienceSoundsSlider.Value = _cfg.GetCVar(CCVars.MaxAmbientSources);
 
@@ -166,6 +172,8 @@ namespace Content.Client.Options.UI.Tabs
                 Math.Abs(AmbientMusicVolumeSlider.Value - _cfg.GetCVar(CCVars.AmbientMusicVolume) * 100f / ContentAudioSystem.AmbientMusicMultiplier) < 0.01f;
             var isLobbyVolumeSame =
                 Math.Abs(LobbyVolumeSlider.Value - _cfg.GetCVar(CCVars.LobbyMusicVolume) * 100f / ContentAudioSystem.LobbyMultiplier) < 0.01f;
+            var isInterfaceVolumeSame =
+                Math.Abs(InterfaceVolumeSlider.Value - _cfg.GetCVar(CCVars.InterfaceVolume) * 100f / ContentAudioSystem.InterfaceMultiplier) < 0.01f;
 
             var isAmbientSoundsSame = (int)AmbienceSoundsSlider.Value == _cfg.GetCVar(CCVars.MaxAmbientSources);
             var isLobbySame = LobbyMusicCheckBox.Pressed == _cfg.GetCVar(CCVars.LobbyMusicEnabled);
@@ -173,7 +181,7 @@ namespace Content.Client.Options.UI.Tabs
             var isEventSame = EventMusicCheckBox.Pressed == _cfg.GetCVar(CCVars.EventMusicEnabled);
             var isAdminSoundsSame = AdminSoundsCheckBox.Pressed == _cfg.GetCVar(CCVars.AdminSoundsEnabled);
             var isEverythingSame = isMasterVolumeSame && isMidiVolumeSame && isAmbientVolumeSame && isAmbientMusicVolumeSame && isAmbientSoundsSame && isLobbySame && isRestartSoundsSame && isEventSame
-                                   && isAdminSoundsSame && isLobbyVolumeSame;
+                                   && isAdminSoundsSame && isLobbyVolumeSame && isInterfaceVolumeSame;
             ApplyButton.Disabled = isEverythingSame;
             ResetButton.Disabled = isEverythingSame;
             MasterVolumeLabel.Text =
@@ -186,6 +194,8 @@ namespace Content.Client.Options.UI.Tabs
                 Loc.GetString("ui-options-volume-percent", ("volume", AmbienceVolumeSlider.Value / 100));
             LobbyVolumeLabel.Text =
                 Loc.GetString("ui-options-volume-percent", ("volume", LobbyVolumeSlider.Value / 100));
+            InterfaceVolumeLabel.Text =
+                Loc.GetString("ui-options-volume-percent", ("volume", InterfaceVolumeSlider.Value / 100));
             AmbienceSoundsLabel.Text = ((int)AmbienceSoundsSlider.Value).ToString();
         }
     }
index 0a73943923e8f1f7ea9b04bd460ea74db69eb8e5..09663ba82cd1478ecf58ab2a9b6df471b90ff298 100644 (file)
@@ -285,7 +285,7 @@ public sealed class ActionUIController : UIController, IOnStateChanged<GameplayS
     private void OnWindowOpened()
     {
         if (ActionButton != null)
-            ActionButton.Pressed = true;
+            ActionButton.SetClickPressed(true);
 
         SearchAndDisplay();
     }
@@ -293,7 +293,7 @@ public sealed class ActionUIController : UIController, IOnStateChanged<GameplayS
     private void OnWindowClosed()
     {
         if (ActionButton != null)
-            ActionButton.Pressed = false;
+            ActionButton.SetClickPressed(false);
     }
 
     public void OnStateExited(GameplayState state)
index 3cd172b080219ebda082bd9ed46fdef771d7f3e4..2372d98f8ddbe38da4576956517d68f7d854143e 100644 (file)
@@ -355,6 +355,7 @@ public sealed class ActionButton : Control, IEntityControl
     {
         base.MouseEntered();
 
+        UserInterfaceManager.HoverSound();
         _beingHovered = true;
         DrawModeChanged();
     }
index a7ece3714da588210dbdac20e81314056fa73591..0969a62940ce78fdb57abf4b7bdc0a720164414d 100644 (file)
@@ -127,14 +127,12 @@ public sealed class AdminUIController : UIController, IOnStateEntered<GameplaySt
 
     private void OnWindowOpen()
     {
-        if (AdminButton != null)
-            AdminButton.Pressed = true;
+        AdminButton?.SetClickPressed(true);
     }
 
     private void OnWindowClosed()
     {
-        if (AdminButton != null)
-            AdminButton.Pressed = false;
+        AdminButton?.SetClickPressed(false);
     }
 
     private void OnWindowDisposed()
index 43789bb228e40fff1d2cc2b8e3b1db4ada86f65e..a8c4a2b1b41231ff5a96094a30df6fb619c53b11 100644 (file)
@@ -121,6 +121,7 @@ public sealed class AHelpUIController: UIController, IOnSystemChanged<BwoinkSyst
             LobbyAHelpButton.Pressed = pressed;
         }
 
+        UIManager.ClickSound();
         UnreadAHelpRead();
     }
 
index 45bdada6e7af322fc7c775cf688439e1e851f9ea..5c085b19664481dfb9745bb2c238db6174f695a2 100644 (file)
@@ -184,7 +184,7 @@ public sealed class CharacterUIController : UIController, IOnStateEntered<Gamepl
 
         if (CharacterButton != null)
         {
-            CharacterButton.Pressed = !_window.IsOpen;
+            CharacterButton.SetClickPressed(!_window.IsOpen);
         }
 
         if (_window.IsOpen)
index a6a8b01022edd5274ef7c27b2e7e9f1130418b9d..85c4af767238692f1bdf60eefbb8bd7320808502 100644 (file)
@@ -51,8 +51,8 @@ public sealed class EscapeUIController : UIController, IOnStateEntered<GameplayS
         EscapeButton.OnPressed += EscapeButtonOnOnPressed;
     }
 
-    private void ActivateButton() => EscapeButton!.Pressed = true;
-    private void DeactivateButton() => EscapeButton!.Pressed = false;
+    private void ActivateButton() => EscapeButton!.SetClickPressed(true);
+    private void DeactivateButton() => EscapeButton!.SetClickPressed(false);
 
     public void OnStateEntered(GameplayState state)
     {
index 20e3158f748ea9fda86b0c16efdbe15e1f500f9f..6f20393b7f240eae30ac9f627f00c8fd4889c1d0 100644 (file)
@@ -139,12 +139,13 @@ public sealed class GuidebookUIController : UIController, IOnStateEntered<LobbyS
 
         if (_guideWindow.IsOpen)
         {
+            UIManager.ClickSound();
             _guideWindow.Close();
             return;
         }
 
         if (GuidebookButton != null)
-            GuidebookButton.Pressed = !_guideWindow.IsOpen;
+            GuidebookButton.SetClickPressed(!_guideWindow.IsOpen);
 
         if (guides == null)
         {
index 73040e9932fdbb26dfc0c0adc6f5fb05a803f08f..b20f926761fa3c6ad8780ce1e40dc0f6e4ffb11f 100644 (file)
@@ -243,7 +243,9 @@ public sealed class InventoryUIController : UIController, IOnStateEntered<Gamepl
         }
 
         UpdateInventoryHotbar(_playerInventory);
-        _inventoryHotbar.Visible = !_inventoryHotbar.Visible;
+        var shouldBeVisible = !_inventoryHotbar.Visible;
+        _inventoryHotbar.Visible = shouldBeVisible;
+
     }
 
     // Neuron Activation
index 778de82210a8f3fe9832396b58cb764b2af92fc8..3ab36a9166a3eef69b6742bf52f1ed6f68679684 100644 (file)
@@ -172,10 +172,12 @@ public sealed class SandboxUIController : UIController, IOnStateChanged<Gameplay
             return;
         if (_sandbox.SandboxAllowed && _window.IsOpen != true)
         {
+            UIManager.ClickSound();
             _window.OpenCentered();
         }
         else
         {
+            UIManager.ClickSound();
             _window.Close();
         }
     }
index b18ab14262387f96108a1243f268b05d34a80ee4..e23df3d936bb7022798bbdaa9ec1555fd2940d79 100644 (file)
@@ -81,6 +81,12 @@ namespace Content.Shared.CCVar
         public static readonly CVarDef<float> LobbyMusicVolume =
             CVarDef.Create("ambience.lobby_music_volume", 0.50f, CVar.ARCHIVE | CVar.CLIENTONLY);
 
+        /// <summary>
+        /// UI volume.
+        /// </summary>
+        public static readonly CVarDef<float> InterfaceVolume =
+            CVarDef.Create("audio.interface_volume", 0.50f, CVar.ARCHIVE | CVar.CLIENTONLY);
+
         /*
          * Status
          */
@@ -573,6 +579,16 @@ namespace Content.Shared.CCVar
         public static readonly CVarDef<bool> DatabaseSynchronous =
             CVarDef.Create("database.sync", false, CVar.SERVERONLY);
 
+        /*
+         * Interface
+         */
+
+        public static readonly CVarDef<string> UIClickSound =
+            CVarDef.Create("interface.click_sound", "/Audio/UserInterface/click.ogg", CVar.REPLICATED);
+
+        public static readonly CVarDef<string> UIHoverSound =
+            CVarDef.Create("interface.hover_sound", "/Audio/UserInterface/hover.ogg", CVar.REPLICATED);
+
         /*
          * Outline
          */
diff --git a/Resources/Audio/UserInterface/attributions.yml b/Resources/Audio/UserInterface/attributions.yml
new file mode 100644 (file)
index 0000000..f0d3612
--- /dev/null
@@ -0,0 +1,11 @@
+- files:
+  - click.ogg
+  license: "CC0-1.0"
+  copyright: "Made by el_boss, edited by mirrorcult"
+  source: "https://freesound.org/people/el_boss/sounds/677861/"
+
+- files:
+  - hover.ogg
+  license: "CC0-1.0"
+  copyright: "Made by MATRIXXX_, edited by metalgearsloth"
+  source: "https://freesound.org/people/MATRIXXX_/sounds/703884/"
\ No newline at end of file
diff --git a/Resources/Audio/UserInterface/click.ogg b/Resources/Audio/UserInterface/click.ogg
new file mode 100644 (file)
index 0000000..63f5ef8
Binary files /dev/null and b/Resources/Audio/UserInterface/click.ogg differ
diff --git a/Resources/Audio/UserInterface/hover.ogg b/Resources/Audio/UserInterface/hover.ogg
new file mode 100644 (file)
index 0000000..7fb8d98
Binary files /dev/null and b/Resources/Audio/UserInterface/hover.ogg differ
index b850d29b4c877e42eac70f1e866a231ae3340b35..d0b16e91b2d42743f0775dfe57ad061756776e94 100644 (file)
@@ -27,6 +27,7 @@ ui-options-midi-volume = MIDI (Instrument) Volume:
 ui-options-ambient-music-volume = Ambient music volume:
 ui-options-ambience-volume = Ambience volume:
 ui-options-lobby-volume = Lobby & Round-end volume:
+ui-options-interface-volume = Interface volume:
 ui-options-ambience-max-sounds = Ambience simultaneous sounds:
 ui-options-lobby-music = Lobby & Round-end Music
 ui-options-restart-sounds = Round Restart Sounds