diff --git a/src/audio.rs b/src/audio.rs index ecb2c08..e0b2e4c 100644 --- a/src/audio.rs +++ b/src/audio.rs @@ -166,8 +166,8 @@ pub fn setup( pub fn respawn_sinks( mut commands: Commands, asset_server: Res, - settings: Res, q_audiosinks: Query, With)>, + mut ew_togglemusic: EventWriter, ) { for sink in &q_audiosinks { commands.entity(sink).despawn(); @@ -182,7 +182,7 @@ pub fn respawn_sinks( source, settings: PlaybackSettings { mode: PlaybackMode::Loop, - paused: settings.mute_music || !settings.hud_active, + paused: true, ..default() }, }, @@ -195,7 +195,7 @@ pub fn respawn_sinks( source, settings: PlaybackSettings { mode: PlaybackMode::Loop, - paused: settings.mute_music || settings.hud_active, + paused: true, ..default() }, }, @@ -218,6 +218,7 @@ pub fn respawn_sinks( SfxType::OneOff => (), } } + ew_togglemusic.send(ToggleMusicEvent()); } pub fn play_sfx( @@ -242,16 +243,16 @@ pub fn play_sfx( pub fn toggle_music(q_audiosinks: Query<(&AudioSink, &Sfx)>, settings: Res) { for (bgm_sink, sfx) in &q_audiosinks { let play = match *sfx { - Sfx::BGM => settings.hud_active, - Sfx::BGMActualJupiterRecording => !settings.hud_active, + Sfx::BGM => settings.radio_mode == 1, + Sfx::BGMActualJupiterRecording => settings.radio_mode == 2, _ => { continue; } }; - if settings.mute_music || !play { - bgm_sink.pause(); - } else { + if play { bgm_sink.play(); + } else { + bgm_sink.pause(); } } } diff --git a/src/game.rs b/src/game.rs index 57102d6..7fe545b 100644 --- a/src/game.rs +++ b/src/game.rs @@ -80,7 +80,7 @@ pub enum AchievementEvent { #[derive(Event)] pub enum GameEvent { SetAR(Turn), - SetMusic(Turn), + SetMusic(Cycle), SetSound(Turn), SetMap(Turn), SetFullscreen(Turn), @@ -107,9 +107,43 @@ impl Turn { } } +pub enum Cycle { + First, + Last, + Next, + Previous, +} + +impl Cycle { + pub fn to_index(&self, current_index: usize, vector: &Vec) -> Option { + if vector.is_empty() { + return None; + } + match self { + Cycle::First => Some(0), + Cycle::Last => Some(vector.len() - 1), + Cycle::Next => { + let index = current_index.saturating_add(1); + if index >= vector.len() { + Some(0) + } else { + Some(index) + } + } + Cycle::Previous => { + if current_index == 0 { + Some(vector.len() - 1) + } else { + Some(current_index - 1) + } + } + } + } +} + pub fn setup(mut settings: ResMut, prefs: Res) { settings.hud_active = prefs.augmented_reality; - settings.mute_music = !prefs.music; + settings.radio_mode = prefs.radio_station; settings.mute_sfx = !prefs.sound; settings.third_person = prefs.third_person; settings.shadows_sun = prefs.shadows_sun; @@ -139,10 +173,14 @@ pub fn handle_game_event( prefs.save(); } GameEvent::SetMusic(turn) => { - // TODO invert "mute_music" to "music_active" - settings.mute_music = turn.to_bool(settings.mute_music); + match turn.to_index(settings.radio_mode, &settings.radio_modes) { + Some(radio_mode) => { + settings.radio_mode = radio_mode; + } + None => {} + } ew_togglemusic.send(audio::ToggleMusicEvent()); - prefs.music = !settings.mute_music; + prefs.radio_station = settings.radio_mode; prefs.save(); } GameEvent::SetSound(turn) => { diff --git a/src/main.rs b/src/main.rs index 297e3dc..c707c94 100644 --- a/src/main.rs +++ b/src/main.rs @@ -35,6 +35,7 @@ pub mod prelude { actor, audio, camera, chat, cmd, common, game, hud, load, menu, nature, var, visual, world, }; pub use game::Turn::Toggle; + pub use game::Cycle::Next; pub use game::{GameEvent, Turn}; } diff --git a/src/menu.rs b/src/menu.rs index 190d166..01fe741 100644 --- a/src/menu.rs +++ b/src/menu.rs @@ -462,8 +462,13 @@ pub fn update_menu( text.sections[i].value = format!("Sound: {onoff}\n"); } MenuAction::ToggleMusic => { - let onoff = bool2string(!settings.mute_music); - text.sections[i].value = format!("Music: {onoff}\n"); + let station = + if let Some(station) = settings.radio_modes.get(settings.radio_mode) { + station + } else { + &settings.radio_modes[0] + }; + text.sections[i].value = format!("Radio: {station}\n"); } MenuAction::ToggleAR => { let onoff = bool2string(settings.hud_active); @@ -566,7 +571,7 @@ pub fn handle_input( ew_updatemenu.send(UpdateMenuEvent); } MenuAction::ToggleMusic => { - ew_game.send(GameEvent::SetMusic(Toggle)); + ew_game.send(GameEvent::SetMusic(Next)); ew_updatemenu.send(UpdateMenuEvent); } MenuAction::ToggleSound => { diff --git a/src/var.rs b/src/var.rs index 7b96684..dcfd0a2 100644 --- a/src/var.rs +++ b/src/var.rs @@ -14,7 +14,7 @@ use crate::prelude::*; use bevy::prelude::*; use bevy::window::WindowMode; -use serde::{Serialize, Deserialize}; +use serde::{Deserialize, Serialize}; use std::collections::{HashMap, HashSet}; use std::env; use std::fs; @@ -40,7 +40,8 @@ pub struct Settings { pub version: String, pub alive: bool, pub mute_sfx: bool, - pub mute_music: bool, + pub radio_mode: usize, + pub radio_modes: Vec, pub volume_sfx: u8, pub volume_music: u8, pub mouse_sensitivity: f32, @@ -156,7 +157,6 @@ impl Default for Settings { fn default() -> Self { let dev_mode = cfg!(feature = "dev_mode") && env::var("CARGO").is_ok(); let default_mute_sfx = false; - let default_mute_music = dev_mode; let version = if let Some(version) = option_env!("CARGO_PKG_VERSION") { version.to_string() } else { @@ -169,7 +169,12 @@ impl Default for Settings { version, alive: true, mute_sfx: default_mute_sfx, - mute_music: default_mute_music, + radio_mode: 1, + radio_modes: vec![ + "Off".to_string(), + "Cinematic".to_string(), + "Vibration Sensor Readings".to_string(), + ], volume_sfx: 100, volume_music: 100, mouse_sensitivity: 0.4, @@ -418,7 +423,7 @@ pub struct Preferences { pub fullscreen_on: bool, pub render_mode: String, pub augmented_reality: bool, - pub music: bool, + pub radio_station: usize, pub sound: bool, pub third_person: bool, pub shadows_sun: bool,