mirror of
https://gitlab.com/veloren/veloren.git
synced 2024-08-30 18:12:32 +00:00
Split settings.rs into multiple files
This commit is contained in:
parent
8effdb1773
commit
685eeb42d8
42
voxygen/src/settings/audio.rs
Normal file
42
voxygen/src/settings/audio.rs
Normal file
@ -0,0 +1,42 @@
|
||||
use serde::{Deserialize, Serialize};
|
||||
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
pub enum AudioOutput {
|
||||
/// Veloren's audio system wont work on some systems,
|
||||
/// so you can use this to disable it, and allow the
|
||||
/// game to function
|
||||
// If this option is disabled, functions in the rodio
|
||||
// library MUST NOT be called.
|
||||
Off,
|
||||
#[serde(other)]
|
||||
Automatic,
|
||||
}
|
||||
|
||||
impl AudioOutput {
|
||||
pub fn is_enabled(&self) -> bool { !matches!(self, Self::Off) }
|
||||
}
|
||||
/// `AudioSettings` controls the volume of different audio subsystems and which
|
||||
/// device is used.
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct AudioSettings {
|
||||
pub master_volume: f32,
|
||||
pub music_volume: f32,
|
||||
pub sfx_volume: f32,
|
||||
pub max_sfx_channels: usize,
|
||||
|
||||
/// Audio Device that Voxygen will use to play audio.
|
||||
pub output: AudioOutput,
|
||||
}
|
||||
|
||||
impl Default for AudioSettings {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
master_volume: 1.0,
|
||||
music_volume: 0.4,
|
||||
sfx_volume: 0.6,
|
||||
max_sfx_channels: 30,
|
||||
output: AudioOutput::Automatic,
|
||||
}
|
||||
}
|
||||
}
|
185
voxygen/src/settings/control.rs
Normal file
185
voxygen/src/settings/control.rs
Normal file
@ -0,0 +1,185 @@
|
||||
use crate::window::{GameInput, KeyMouse};
|
||||
use hashbrown::{HashMap, HashSet};
|
||||
use serde::{Deserialize, Serialize};
|
||||
use winit::event::{MouseButton, VirtualKeyCode};
|
||||
|
||||
// ControlSetting-like struct used by Serde, to handle not serializing/building
|
||||
// post-deserializing the inverse_keybindings hashmap
|
||||
#[derive(Serialize, Deserialize)]
|
||||
struct ControlSettingsSerde {
|
||||
keybindings: HashMap<GameInput, KeyMouse>,
|
||||
}
|
||||
|
||||
impl From<ControlSettings> for ControlSettingsSerde {
|
||||
fn from(control_settings: ControlSettings) -> Self {
|
||||
let mut user_bindings: HashMap<GameInput, KeyMouse> = HashMap::new();
|
||||
// Do a delta between default() ControlSettings and the argument, and let
|
||||
// keybindings be only the custom keybindings chosen by the user.
|
||||
for (k, v) in control_settings.keybindings {
|
||||
if ControlSettings::default_binding(k) != v {
|
||||
// Keybinding chosen by the user
|
||||
user_bindings.insert(k, v);
|
||||
}
|
||||
}
|
||||
ControlSettingsSerde {
|
||||
keybindings: user_bindings,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// `ControlSettings` contains keybindings.
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(from = "ControlSettingsSerde", into = "ControlSettingsSerde")]
|
||||
pub struct ControlSettings {
|
||||
pub keybindings: HashMap<GameInput, KeyMouse>,
|
||||
pub inverse_keybindings: HashMap<KeyMouse, HashSet<GameInput>>, // used in event loop
|
||||
}
|
||||
|
||||
impl From<ControlSettingsSerde> for ControlSettings {
|
||||
fn from(control_serde: ControlSettingsSerde) -> Self {
|
||||
let user_keybindings = control_serde.keybindings;
|
||||
let mut control_settings = ControlSettings::default();
|
||||
for (k, v) in user_keybindings {
|
||||
control_settings.modify_binding(k, v);
|
||||
}
|
||||
control_settings
|
||||
}
|
||||
}
|
||||
|
||||
/// Since Macbook trackpads lack middle click, on OS X we default to LShift
|
||||
/// instead It is an imperfect heuristic, but hopefully it will be a slightly
|
||||
/// better default, and the two places we default to middle click currently
|
||||
/// (roll and wall jump) are both situations where you cannot glide (the other
|
||||
/// default mapping for LShift).
|
||||
#[cfg(target_os = "macos")]
|
||||
const MIDDLE_CLICK_KEY: KeyMouse = KeyMouse::Key(VirtualKeyCode::LShift);
|
||||
#[cfg(not(target_os = "macos"))]
|
||||
const MIDDLE_CLICK_KEY: KeyMouse = KeyMouse::Mouse(MouseButton::Middle);
|
||||
|
||||
impl ControlSettings {
|
||||
pub fn get_binding(&self, game_input: GameInput) -> Option<KeyMouse> {
|
||||
self.keybindings.get(&game_input).copied()
|
||||
}
|
||||
|
||||
pub fn get_associated_game_inputs(&self, key_mouse: &KeyMouse) -> Option<&HashSet<GameInput>> {
|
||||
self.inverse_keybindings.get(key_mouse)
|
||||
}
|
||||
|
||||
pub fn insert_binding(&mut self, game_input: GameInput, key_mouse: KeyMouse) {
|
||||
self.keybindings.insert(game_input, key_mouse);
|
||||
self.inverse_keybindings
|
||||
.entry(key_mouse)
|
||||
.or_default()
|
||||
.insert(game_input);
|
||||
}
|
||||
|
||||
pub fn modify_binding(&mut self, game_input: GameInput, key_mouse: KeyMouse) {
|
||||
// For the KeyMouse->GameInput hashmap, we first need to remove the GameInput
|
||||
// from the old binding
|
||||
if let Some(old_binding) = self.get_binding(game_input) {
|
||||
self.inverse_keybindings
|
||||
.entry(old_binding)
|
||||
.or_default()
|
||||
.remove(&game_input);
|
||||
}
|
||||
// then we add the GameInput to the proper key
|
||||
self.inverse_keybindings
|
||||
.entry(key_mouse)
|
||||
.or_default()
|
||||
.insert(game_input);
|
||||
// For the GameInput->KeyMouse hashmap, just overwrite the value
|
||||
self.keybindings.insert(game_input, key_mouse);
|
||||
}
|
||||
|
||||
/// Return true if this key is used for multiple GameInputs that aren't
|
||||
/// expected to be safe to have bound to the same key at the same time
|
||||
pub fn has_conflicting_bindings(&self, key_mouse: KeyMouse) -> bool {
|
||||
if let Some(game_inputs) = self.inverse_keybindings.get(&key_mouse) {
|
||||
for a in game_inputs.iter() {
|
||||
for b in game_inputs.iter() {
|
||||
if !GameInput::can_share_bindings(*a, *b) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
false
|
||||
}
|
||||
|
||||
pub fn default_binding(game_input: GameInput) -> KeyMouse {
|
||||
// If a new GameInput is added, be sure to update GameInput::iterator() too!
|
||||
match game_input {
|
||||
GameInput::Primary => KeyMouse::Mouse(MouseButton::Left),
|
||||
GameInput::Secondary => KeyMouse::Mouse(MouseButton::Right),
|
||||
GameInput::ToggleCursor => KeyMouse::Key(VirtualKeyCode::Comma),
|
||||
GameInput::Escape => KeyMouse::Key(VirtualKeyCode::Escape),
|
||||
GameInput::Chat => KeyMouse::Key(VirtualKeyCode::Return),
|
||||
GameInput::Command => KeyMouse::Key(VirtualKeyCode::Slash),
|
||||
GameInput::MoveForward => KeyMouse::Key(VirtualKeyCode::W),
|
||||
GameInput::MoveLeft => KeyMouse::Key(VirtualKeyCode::A),
|
||||
GameInput::MoveBack => KeyMouse::Key(VirtualKeyCode::S),
|
||||
GameInput::MoveRight => KeyMouse::Key(VirtualKeyCode::D),
|
||||
GameInput::Jump => KeyMouse::Key(VirtualKeyCode::Space),
|
||||
GameInput::Sit => KeyMouse::Key(VirtualKeyCode::K),
|
||||
GameInput::Dance => KeyMouse::Key(VirtualKeyCode::J),
|
||||
GameInput::Glide => KeyMouse::Key(VirtualKeyCode::LShift),
|
||||
GameInput::Climb => KeyMouse::Key(VirtualKeyCode::Space),
|
||||
GameInput::ClimbDown => KeyMouse::Key(VirtualKeyCode::LControl),
|
||||
GameInput::SwimUp => KeyMouse::Key(VirtualKeyCode::Space),
|
||||
GameInput::SwimDown => KeyMouse::Key(VirtualKeyCode::LShift),
|
||||
GameInput::Fly => KeyMouse::Key(VirtualKeyCode::H),
|
||||
GameInput::Sneak => KeyMouse::Key(VirtualKeyCode::LControl),
|
||||
GameInput::ToggleLantern => KeyMouse::Key(VirtualKeyCode::G),
|
||||
GameInput::Mount => KeyMouse::Key(VirtualKeyCode::F),
|
||||
GameInput::Map => KeyMouse::Key(VirtualKeyCode::M),
|
||||
GameInput::Bag => KeyMouse::Key(VirtualKeyCode::B),
|
||||
GameInput::Trade => KeyMouse::Key(VirtualKeyCode::R),
|
||||
GameInput::Social => KeyMouse::Key(VirtualKeyCode::O),
|
||||
GameInput::Crafting => KeyMouse::Key(VirtualKeyCode::C),
|
||||
GameInput::Spellbook => KeyMouse::Key(VirtualKeyCode::P),
|
||||
GameInput::Settings => KeyMouse::Key(VirtualKeyCode::N),
|
||||
GameInput::Help => KeyMouse::Key(VirtualKeyCode::F1),
|
||||
GameInput::ToggleInterface => KeyMouse::Key(VirtualKeyCode::F2),
|
||||
GameInput::ToggleDebug => KeyMouse::Key(VirtualKeyCode::F3),
|
||||
GameInput::Fullscreen => KeyMouse::Key(VirtualKeyCode::F11),
|
||||
GameInput::Screenshot => KeyMouse::Key(VirtualKeyCode::F4),
|
||||
GameInput::ToggleIngameUi => KeyMouse::Key(VirtualKeyCode::F6),
|
||||
GameInput::Roll => MIDDLE_CLICK_KEY,
|
||||
GameInput::Respawn => KeyMouse::Key(VirtualKeyCode::Space),
|
||||
GameInput::Interact => KeyMouse::Key(VirtualKeyCode::E),
|
||||
GameInput::ToggleWield => KeyMouse::Key(VirtualKeyCode::T),
|
||||
GameInput::FreeLook => KeyMouse::Key(VirtualKeyCode::L),
|
||||
GameInput::AutoWalk => KeyMouse::Key(VirtualKeyCode::Period),
|
||||
GameInput::CameraClamp => KeyMouse::Key(VirtualKeyCode::Apostrophe),
|
||||
GameInput::CycleCamera => KeyMouse::Key(VirtualKeyCode::Key0),
|
||||
GameInput::Slot1 => KeyMouse::Key(VirtualKeyCode::Key1),
|
||||
GameInput::Slot2 => KeyMouse::Key(VirtualKeyCode::Key2),
|
||||
GameInput::Slot3 => KeyMouse::Key(VirtualKeyCode::Key3),
|
||||
GameInput::Slot4 => KeyMouse::Key(VirtualKeyCode::Key4),
|
||||
GameInput::Slot5 => KeyMouse::Key(VirtualKeyCode::Key5),
|
||||
GameInput::Slot6 => KeyMouse::Key(VirtualKeyCode::Key6),
|
||||
GameInput::Slot7 => KeyMouse::Key(VirtualKeyCode::Key7),
|
||||
GameInput::Slot8 => KeyMouse::Key(VirtualKeyCode::Key8),
|
||||
GameInput::Slot9 => KeyMouse::Key(VirtualKeyCode::Key9),
|
||||
GameInput::Slot10 => KeyMouse::Key(VirtualKeyCode::Q),
|
||||
GameInput::SwapLoadout => KeyMouse::Key(VirtualKeyCode::Tab),
|
||||
GameInput::Select => KeyMouse::Key(VirtualKeyCode::Y),
|
||||
GameInput::AcceptGroupInvite => KeyMouse::Key(VirtualKeyCode::U),
|
||||
GameInput::DeclineGroupInvite => KeyMouse::Key(VirtualKeyCode::I),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Default for ControlSettings {
|
||||
fn default() -> Self {
|
||||
let mut new_settings = Self {
|
||||
keybindings: HashMap::new(),
|
||||
inverse_keybindings: HashMap::new(),
|
||||
};
|
||||
// Sets the initial keybindings for those GameInputs.
|
||||
for game_input in GameInput::iterator() {
|
||||
new_settings.insert_binding(game_input, ControlSettings::default_binding(game_input));
|
||||
}
|
||||
new_settings
|
||||
}
|
||||
}
|
231
voxygen/src/settings/gamepad.rs
Normal file
231
voxygen/src/settings/gamepad.rs
Normal file
@ -0,0 +1,231 @@
|
||||
use hashbrown::HashMap;
|
||||
use serde::{Deserialize, Serialize};
|
||||
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct GamepadSettings {
|
||||
pub game_buttons: con_settings::GameButtons,
|
||||
pub menu_buttons: con_settings::MenuButtons,
|
||||
pub game_axis: con_settings::GameAxis,
|
||||
pub menu_axis: con_settings::MenuAxis,
|
||||
pub game_analog_buttons: con_settings::GameAnalogButton,
|
||||
pub menu_analog_buttons: con_settings::MenuAnalogButton,
|
||||
pub pan_sensitivity: u32,
|
||||
pub pan_invert_y: bool,
|
||||
pub axis_deadzones: HashMap<crate::controller::Axis, f32>,
|
||||
pub button_deadzones: HashMap<crate::controller::AnalogButton, f32>,
|
||||
pub mouse_emulation_sensitivity: u32,
|
||||
pub inverted_axes: Vec<crate::controller::Axis>,
|
||||
}
|
||||
|
||||
impl Default for GamepadSettings {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
game_buttons: con_settings::GameButtons::default(),
|
||||
menu_buttons: con_settings::MenuButtons::default(),
|
||||
game_axis: con_settings::GameAxis::default(),
|
||||
menu_axis: con_settings::MenuAxis::default(),
|
||||
game_analog_buttons: con_settings::GameAnalogButton::default(),
|
||||
menu_analog_buttons: con_settings::MenuAnalogButton::default(),
|
||||
pan_sensitivity: 10,
|
||||
pan_invert_y: false,
|
||||
axis_deadzones: HashMap::new(),
|
||||
button_deadzones: HashMap::new(),
|
||||
mouse_emulation_sensitivity: 12,
|
||||
inverted_axes: Vec::new(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub mod con_settings {
|
||||
use crate::controller::*;
|
||||
use gilrs::{Axis as GilAxis, Button as GilButton};
|
||||
use serde::{Deserialize, Serialize};
|
||||
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct GameButtons {
|
||||
pub primary: Button,
|
||||
pub secondary: Button,
|
||||
pub toggle_cursor: Button,
|
||||
pub escape: Button,
|
||||
pub enter: Button,
|
||||
pub command: Button,
|
||||
pub move_forward: Button,
|
||||
pub move_left: Button,
|
||||
pub move_back: Button,
|
||||
pub move_right: Button,
|
||||
pub jump: Button,
|
||||
pub sit: Button,
|
||||
pub dance: Button,
|
||||
pub glide: Button,
|
||||
pub climb: Button,
|
||||
pub climb_down: Button,
|
||||
pub swimup: Button,
|
||||
pub swimdown: Button,
|
||||
pub sneak: Button,
|
||||
pub toggle_lantern: Button,
|
||||
pub mount: Button,
|
||||
pub map: Button,
|
||||
pub bag: Button,
|
||||
pub quest_log: Button,
|
||||
pub character_window: Button,
|
||||
pub social: Button,
|
||||
pub crafting: Button,
|
||||
pub spellbook: Button,
|
||||
pub settings: Button,
|
||||
pub help: Button,
|
||||
pub toggle_interface: Button,
|
||||
pub toggle_debug: Button,
|
||||
pub fullscreen: Button,
|
||||
pub screenshot: Button,
|
||||
pub toggle_ingame_ui: Button,
|
||||
pub roll: Button,
|
||||
pub respawn: Button,
|
||||
pub interact: Button,
|
||||
pub toggle_wield: Button,
|
||||
pub swap_loadout: Button,
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct MenuButtons {
|
||||
pub up: Button,
|
||||
pub down: Button,
|
||||
pub left: Button,
|
||||
pub right: Button,
|
||||
pub scroll_up: Button,
|
||||
pub scroll_down: Button,
|
||||
pub scroll_left: Button,
|
||||
pub scroll_right: Button,
|
||||
pub home: Button,
|
||||
pub end: Button,
|
||||
pub apply: Button,
|
||||
pub back: Button,
|
||||
pub exit: Button,
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct GameAxis {
|
||||
pub movement_x: Axis,
|
||||
pub movement_y: Axis,
|
||||
pub camera_x: Axis,
|
||||
pub camera_y: Axis,
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct MenuAxis {
|
||||
pub move_x: Axis,
|
||||
pub move_y: Axis,
|
||||
pub scroll_x: Axis,
|
||||
pub scroll_y: Axis,
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct GameAnalogButton {}
|
||||
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct MenuAnalogButton {}
|
||||
|
||||
impl Default for GameButtons {
|
||||
fn default() -> Self {
|
||||
// binding to unknown = getting skipped from processing
|
||||
Self {
|
||||
primary: Button::Simple(GilButton::RightTrigger2),
|
||||
secondary: Button::Simple(GilButton::LeftTrigger2),
|
||||
toggle_cursor: Button::Simple(GilButton::Unknown),
|
||||
escape: Button::Simple(GilButton::Start),
|
||||
enter: Button::Simple(GilButton::Unknown),
|
||||
command: Button::Simple(GilButton::Unknown),
|
||||
move_forward: Button::Simple(GilButton::Unknown),
|
||||
move_left: Button::Simple(GilButton::Unknown),
|
||||
move_back: Button::Simple(GilButton::Unknown),
|
||||
move_right: Button::Simple(GilButton::Unknown),
|
||||
jump: Button::Simple(GilButton::South),
|
||||
sit: Button::Simple(GilButton::Unknown),
|
||||
dance: Button::Simple(GilButton::Unknown),
|
||||
glide: Button::Simple(GilButton::LeftTrigger),
|
||||
climb: Button::Simple(GilButton::South),
|
||||
climb_down: Button::Simple(GilButton::East),
|
||||
swimup: Button::Simple(GilButton::South),
|
||||
swimdown: Button::Simple(GilButton::East),
|
||||
sneak: Button::Simple(GilButton::East),
|
||||
toggle_lantern: Button::Simple(GilButton::DPadLeft),
|
||||
mount: Button::Simple(GilButton::North),
|
||||
map: Button::Simple(GilButton::Select),
|
||||
bag: Button::Simple(GilButton::DPadRight),
|
||||
quest_log: Button::Simple(GilButton::Unknown),
|
||||
character_window: Button::Simple(GilButton::Unknown),
|
||||
social: Button::Simple(GilButton::Unknown),
|
||||
crafting: Button::Simple(GilButton::DPadDown),
|
||||
spellbook: Button::Simple(GilButton::Unknown),
|
||||
settings: Button::Simple(GilButton::Unknown),
|
||||
help: Button::Simple(GilButton::Unknown),
|
||||
toggle_interface: Button::Simple(GilButton::Unknown),
|
||||
toggle_debug: Button::Simple(GilButton::Unknown),
|
||||
fullscreen: Button::Simple(GilButton::Unknown),
|
||||
screenshot: Button::Simple(GilButton::Unknown),
|
||||
toggle_ingame_ui: Button::Simple(GilButton::Unknown),
|
||||
roll: Button::Simple(GilButton::RightTrigger),
|
||||
respawn: Button::Simple(GilButton::South),
|
||||
interact: Button::Simple(GilButton::North),
|
||||
toggle_wield: Button::Simple(GilButton::West),
|
||||
swap_loadout: Button::Simple(GilButton::LeftThumb),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Default for MenuButtons {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
up: Button::Simple(GilButton::Unknown),
|
||||
down: Button::Simple(GilButton::Unknown),
|
||||
left: Button::Simple(GilButton::Unknown),
|
||||
right: Button::Simple(GilButton::Unknown),
|
||||
scroll_up: Button::Simple(GilButton::Unknown),
|
||||
scroll_down: Button::Simple(GilButton::Unknown),
|
||||
scroll_left: Button::Simple(GilButton::Unknown),
|
||||
scroll_right: Button::Simple(GilButton::Unknown),
|
||||
home: Button::Simple(GilButton::DPadUp),
|
||||
end: Button::Simple(GilButton::DPadDown),
|
||||
apply: Button::Simple(GilButton::South),
|
||||
back: Button::Simple(GilButton::East),
|
||||
exit: Button::Simple(GilButton::Mode),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Default for GameAxis {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
movement_x: Axis::Simple(GilAxis::LeftStickX),
|
||||
movement_y: Axis::Simple(GilAxis::LeftStickY),
|
||||
camera_x: Axis::Simple(GilAxis::RightStickX),
|
||||
camera_y: Axis::Simple(GilAxis::RightStickY),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Default for MenuAxis {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
move_x: Axis::Simple(GilAxis::RightStickX),
|
||||
move_y: Axis::Simple(GilAxis::RightStickY),
|
||||
scroll_x: Axis::Simple(GilAxis::LeftStickX),
|
||||
scroll_y: Axis::Simple(GilAxis::LeftStickY),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Default for GameAnalogButton {
|
||||
fn default() -> Self { Self {} }
|
||||
}
|
||||
|
||||
impl Default for MenuAnalogButton {
|
||||
fn default() -> Self { Self {} }
|
||||
}
|
||||
}
|
37
voxygen/src/settings/gameplay.rs
Normal file
37
voxygen/src/settings/gameplay.rs
Normal file
@ -0,0 +1,37 @@
|
||||
use crate::hud::PressBehavior;
|
||||
use serde::{Deserialize, Serialize};
|
||||
|
||||
/// `GameplaySettings` contains sensitivity and gameplay options.
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct GameplaySettings {
|
||||
pub pan_sensitivity: u32,
|
||||
pub zoom_sensitivity: u32,
|
||||
pub camera_clamp_angle: u32,
|
||||
pub zoom_inversion: bool,
|
||||
pub mouse_y_inversion: bool,
|
||||
pub smooth_pan_enable: bool,
|
||||
pub free_look_behavior: PressBehavior,
|
||||
pub auto_walk_behavior: PressBehavior,
|
||||
pub camera_clamp_behavior: PressBehavior,
|
||||
pub stop_auto_walk_on_input: bool,
|
||||
pub auto_camera: bool,
|
||||
}
|
||||
|
||||
impl Default for GameplaySettings {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
pan_sensitivity: 100,
|
||||
zoom_sensitivity: 100,
|
||||
camera_clamp_angle: 45,
|
||||
zoom_inversion: false,
|
||||
mouse_y_inversion: false,
|
||||
smooth_pan_enable: false,
|
||||
free_look_behavior: PressBehavior::Toggle,
|
||||
auto_walk_behavior: PressBehavior::Toggle,
|
||||
camera_clamp_behavior: PressBehavior::Toggle,
|
||||
stop_auto_walk_on_input: true,
|
||||
auto_camera: false,
|
||||
}
|
||||
}
|
||||
}
|
65
voxygen/src/settings/graphics.rs
Normal file
65
voxygen/src/settings/graphics.rs
Normal file
@ -0,0 +1,65 @@
|
||||
use crate::{render::RenderMode, window::FullScreenSettings};
|
||||
use serde::{Deserialize, Serialize};
|
||||
use std::fmt;
|
||||
|
||||
#[derive(Copy, Clone, Serialize, Deserialize, Debug, PartialEq)]
|
||||
pub enum Fps {
|
||||
Max(u32),
|
||||
Unlimited,
|
||||
}
|
||||
|
||||
pub fn get_fps(max_fps: Fps) -> u32 {
|
||||
match max_fps {
|
||||
Fps::Max(x) => x,
|
||||
Fps::Unlimited => u32::MAX,
|
||||
}
|
||||
}
|
||||
|
||||
impl fmt::Display for Fps {
|
||||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
||||
match *self {
|
||||
Fps::Max(x) => write!(f, "{}", x),
|
||||
Fps::Unlimited => write!(f, "Unlimited"),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// `GraphicsSettings` contains settings related to framerate and in-game
|
||||
/// visuals.
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct GraphicsSettings {
|
||||
pub view_distance: u32,
|
||||
pub sprite_render_distance: u32,
|
||||
pub particles_enabled: bool,
|
||||
pub figure_lod_render_distance: u32,
|
||||
pub max_fps: Fps,
|
||||
pub fov: u16,
|
||||
pub gamma: f32,
|
||||
pub exposure: f32,
|
||||
pub ambiance: f32,
|
||||
pub render_mode: RenderMode,
|
||||
pub window_size: [u16; 2],
|
||||
pub fullscreen: FullScreenSettings,
|
||||
pub lod_detail: u32,
|
||||
}
|
||||
|
||||
impl Default for GraphicsSettings {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
view_distance: 10,
|
||||
sprite_render_distance: 100,
|
||||
particles_enabled: true,
|
||||
figure_lod_render_distance: 300,
|
||||
max_fps: Fps::Max(60),
|
||||
fov: 70,
|
||||
gamma: 1.0,
|
||||
exposure: 1.0,
|
||||
ambiance: 10.0,
|
||||
render_mode: RenderMode::default(),
|
||||
window_size: [1280, 720],
|
||||
fullscreen: FullScreenSettings::default(),
|
||||
lod_detail: 250,
|
||||
}
|
||||
}
|
||||
}
|
75
voxygen/src/settings/interface.rs
Normal file
75
voxygen/src/settings/interface.rs
Normal file
@ -0,0 +1,75 @@
|
||||
use crate::{
|
||||
hud::{BarNumbers, BuffPosition, CrosshairType, Intro, ShortcutNumbers, XpBar},
|
||||
ui::ScaleMode,
|
||||
};
|
||||
use serde::{Deserialize, Serialize};
|
||||
use vek::*;
|
||||
|
||||
/// `InterfaceSettings` contains UI, HUD and Map options.
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct InterfaceSettings {
|
||||
pub toggle_debug: bool,
|
||||
pub sct: bool,
|
||||
pub sct_player_batch: bool,
|
||||
pub sct_damage_batch: bool,
|
||||
pub speech_bubble_dark_mode: bool,
|
||||
pub speech_bubble_icon: bool,
|
||||
pub crosshair_transp: f32,
|
||||
pub chat_transp: f32,
|
||||
pub chat_character_name: bool,
|
||||
pub crosshair_type: CrosshairType,
|
||||
pub intro_show: Intro,
|
||||
pub xp_bar: XpBar,
|
||||
pub shortcut_numbers: ShortcutNumbers,
|
||||
pub buff_position: BuffPosition,
|
||||
pub bar_numbers: BarNumbers,
|
||||
pub ui_scale: ScaleMode,
|
||||
pub map_zoom: f64,
|
||||
pub map_drag: Vec2<f64>,
|
||||
pub map_show_topo_map: bool,
|
||||
pub map_show_difficulty: bool,
|
||||
pub map_show_towns: bool,
|
||||
pub map_show_dungeons: bool,
|
||||
pub map_show_castles: bool,
|
||||
pub loading_tips: bool,
|
||||
pub map_show_caves: bool,
|
||||
pub map_show_trees: bool,
|
||||
pub minimap_show: bool,
|
||||
pub minimap_face_north: bool,
|
||||
}
|
||||
|
||||
impl Default for InterfaceSettings {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
toggle_debug: false,
|
||||
sct: true,
|
||||
sct_player_batch: false,
|
||||
sct_damage_batch: false,
|
||||
speech_bubble_dark_mode: false,
|
||||
speech_bubble_icon: true,
|
||||
crosshair_transp: 0.6,
|
||||
chat_transp: 0.4,
|
||||
chat_character_name: true,
|
||||
crosshair_type: CrosshairType::Round,
|
||||
intro_show: Intro::Show,
|
||||
xp_bar: XpBar::Always,
|
||||
shortcut_numbers: ShortcutNumbers::On,
|
||||
buff_position: BuffPosition::Bar,
|
||||
bar_numbers: BarNumbers::Values,
|
||||
ui_scale: ScaleMode::RelativeToWindow([1920.0, 1080.0].into()),
|
||||
map_zoom: 10.0,
|
||||
map_drag: Vec2 { x: 0.0, y: 0.0 },
|
||||
map_show_topo_map: false,
|
||||
map_show_difficulty: true,
|
||||
map_show_towns: true,
|
||||
map_show_dungeons: true,
|
||||
map_show_castles: true,
|
||||
loading_tips: true,
|
||||
map_show_caves: true,
|
||||
map_show_trees: true,
|
||||
minimap_show: true,
|
||||
minimap_face_north: false,
|
||||
}
|
||||
}
|
||||
}
|
16
voxygen/src/settings/language.rs
Normal file
16
voxygen/src/settings/language.rs
Normal file
@ -0,0 +1,16 @@
|
||||
use crate::i18n;
|
||||
use serde::{Deserialize, Serialize};
|
||||
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct LanguageSettings {
|
||||
pub selected_language: String,
|
||||
}
|
||||
|
||||
impl Default for LanguageSettings {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
selected_language: i18n::REFERENCE_LANG.to_string(),
|
||||
}
|
||||
}
|
||||
}
|
@ -1,554 +1,25 @@
|
||||
use crate::{
|
||||
hud::{BarNumbers, BuffPosition, CrosshairType, Intro, PressBehavior, ShortcutNumbers, XpBar},
|
||||
i18n,
|
||||
render::RenderMode,
|
||||
ui::ScaleMode,
|
||||
window::{FullScreenSettings, GameInput, KeyMouse},
|
||||
};
|
||||
use directories_next::UserDirs;
|
||||
use hashbrown::{HashMap, HashSet};
|
||||
use serde::{Deserialize, Serialize};
|
||||
use std::{fmt, fs, path::PathBuf};
|
||||
use std::{fs, path::PathBuf};
|
||||
use tracing::warn;
|
||||
use vek::*;
|
||||
use winit::event::{MouseButton, VirtualKeyCode};
|
||||
// ControlSetting-like struct used by Serde, to handle not serializing/building
|
||||
// post-deserializing the inverse_keybindings hashmap
|
||||
#[derive(Serialize, Deserialize)]
|
||||
struct ControlSettingsSerde {
|
||||
keybindings: HashMap<GameInput, KeyMouse>,
|
||||
}
|
||||
|
||||
impl From<ControlSettings> for ControlSettingsSerde {
|
||||
fn from(control_settings: ControlSettings) -> Self {
|
||||
let mut user_bindings: HashMap<GameInput, KeyMouse> = HashMap::new();
|
||||
// Do a delta between default() ControlSettings and the argument, and let
|
||||
// keybindings be only the custom keybindings chosen by the user.
|
||||
for (k, v) in control_settings.keybindings {
|
||||
if ControlSettings::default_binding(k) != v {
|
||||
// Keybinding chosen by the user
|
||||
user_bindings.insert(k, v);
|
||||
}
|
||||
}
|
||||
ControlSettingsSerde {
|
||||
keybindings: user_bindings,
|
||||
}
|
||||
}
|
||||
}
|
||||
mod audio;
|
||||
mod control;
|
||||
mod gamepad;
|
||||
mod gameplay;
|
||||
mod graphics;
|
||||
mod interface;
|
||||
mod language;
|
||||
mod networking;
|
||||
|
||||
/// `ControlSettings` contains keybindings.
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(from = "ControlSettingsSerde", into = "ControlSettingsSerde")]
|
||||
pub struct ControlSettings {
|
||||
pub keybindings: HashMap<GameInput, KeyMouse>,
|
||||
pub inverse_keybindings: HashMap<KeyMouse, HashSet<GameInput>>, // used in event loop
|
||||
}
|
||||
|
||||
impl From<ControlSettingsSerde> for ControlSettings {
|
||||
fn from(control_serde: ControlSettingsSerde) -> Self {
|
||||
let user_keybindings = control_serde.keybindings;
|
||||
let mut control_settings = ControlSettings::default();
|
||||
for (k, v) in user_keybindings {
|
||||
control_settings.modify_binding(k, v);
|
||||
}
|
||||
control_settings
|
||||
}
|
||||
}
|
||||
|
||||
/// Since Macbook trackpads lack middle click, on OS X we default to LShift
|
||||
/// instead It is an imperfect heuristic, but hopefully it will be a slightly
|
||||
/// better default, and the two places we default to middle click currently
|
||||
/// (roll and wall jump) are both situations where you cannot glide (the other
|
||||
/// default mapping for LShift).
|
||||
#[cfg(target_os = "macos")]
|
||||
const MIDDLE_CLICK_KEY: KeyMouse = KeyMouse::Key(VirtualKeyCode::LShift);
|
||||
#[cfg(not(target_os = "macos"))]
|
||||
const MIDDLE_CLICK_KEY: KeyMouse = KeyMouse::Mouse(MouseButton::Middle);
|
||||
|
||||
impl ControlSettings {
|
||||
pub fn get_binding(&self, game_input: GameInput) -> Option<KeyMouse> {
|
||||
self.keybindings.get(&game_input).copied()
|
||||
}
|
||||
|
||||
pub fn get_associated_game_inputs(&self, key_mouse: &KeyMouse) -> Option<&HashSet<GameInput>> {
|
||||
self.inverse_keybindings.get(key_mouse)
|
||||
}
|
||||
|
||||
pub fn insert_binding(&mut self, game_input: GameInput, key_mouse: KeyMouse) {
|
||||
self.keybindings.insert(game_input, key_mouse);
|
||||
self.inverse_keybindings
|
||||
.entry(key_mouse)
|
||||
.or_default()
|
||||
.insert(game_input);
|
||||
}
|
||||
|
||||
pub fn modify_binding(&mut self, game_input: GameInput, key_mouse: KeyMouse) {
|
||||
// For the KeyMouse->GameInput hashmap, we first need to remove the GameInput
|
||||
// from the old binding
|
||||
if let Some(old_binding) = self.get_binding(game_input) {
|
||||
self.inverse_keybindings
|
||||
.entry(old_binding)
|
||||
.or_default()
|
||||
.remove(&game_input);
|
||||
}
|
||||
// then we add the GameInput to the proper key
|
||||
self.inverse_keybindings
|
||||
.entry(key_mouse)
|
||||
.or_default()
|
||||
.insert(game_input);
|
||||
// For the GameInput->KeyMouse hashmap, just overwrite the value
|
||||
self.keybindings.insert(game_input, key_mouse);
|
||||
}
|
||||
|
||||
/// Return true if this key is used for multiple GameInputs that aren't
|
||||
/// expected to be safe to have bound to the same key at the same time
|
||||
pub fn has_conflicting_bindings(&self, key_mouse: KeyMouse) -> bool {
|
||||
if let Some(game_inputs) = self.inverse_keybindings.get(&key_mouse) {
|
||||
for a in game_inputs.iter() {
|
||||
for b in game_inputs.iter() {
|
||||
if !GameInput::can_share_bindings(*a, *b) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
false
|
||||
}
|
||||
|
||||
pub fn default_binding(game_input: GameInput) -> KeyMouse {
|
||||
// If a new GameInput is added, be sure to update GameInput::iterator() too!
|
||||
match game_input {
|
||||
GameInput::Primary => KeyMouse::Mouse(MouseButton::Left),
|
||||
GameInput::Secondary => KeyMouse::Mouse(MouseButton::Right),
|
||||
GameInput::ToggleCursor => KeyMouse::Key(VirtualKeyCode::Comma),
|
||||
GameInput::Escape => KeyMouse::Key(VirtualKeyCode::Escape),
|
||||
GameInput::Chat => KeyMouse::Key(VirtualKeyCode::Return),
|
||||
GameInput::Command => KeyMouse::Key(VirtualKeyCode::Slash),
|
||||
GameInput::MoveForward => KeyMouse::Key(VirtualKeyCode::W),
|
||||
GameInput::MoveLeft => KeyMouse::Key(VirtualKeyCode::A),
|
||||
GameInput::MoveBack => KeyMouse::Key(VirtualKeyCode::S),
|
||||
GameInput::MoveRight => KeyMouse::Key(VirtualKeyCode::D),
|
||||
GameInput::Jump => KeyMouse::Key(VirtualKeyCode::Space),
|
||||
GameInput::Sit => KeyMouse::Key(VirtualKeyCode::K),
|
||||
GameInput::Dance => KeyMouse::Key(VirtualKeyCode::J),
|
||||
GameInput::Glide => KeyMouse::Key(VirtualKeyCode::LShift),
|
||||
GameInput::Climb => KeyMouse::Key(VirtualKeyCode::Space),
|
||||
GameInput::ClimbDown => KeyMouse::Key(VirtualKeyCode::LControl),
|
||||
GameInput::SwimUp => KeyMouse::Key(VirtualKeyCode::Space),
|
||||
GameInput::SwimDown => KeyMouse::Key(VirtualKeyCode::LShift),
|
||||
GameInput::Fly => KeyMouse::Key(VirtualKeyCode::H),
|
||||
GameInput::Sneak => KeyMouse::Key(VirtualKeyCode::LControl),
|
||||
GameInput::ToggleLantern => KeyMouse::Key(VirtualKeyCode::G),
|
||||
GameInput::Mount => KeyMouse::Key(VirtualKeyCode::F),
|
||||
GameInput::Map => KeyMouse::Key(VirtualKeyCode::M),
|
||||
GameInput::Bag => KeyMouse::Key(VirtualKeyCode::B),
|
||||
GameInput::Trade => KeyMouse::Key(VirtualKeyCode::R),
|
||||
GameInput::Social => KeyMouse::Key(VirtualKeyCode::O),
|
||||
GameInput::Crafting => KeyMouse::Key(VirtualKeyCode::C),
|
||||
GameInput::Spellbook => KeyMouse::Key(VirtualKeyCode::P),
|
||||
GameInput::Settings => KeyMouse::Key(VirtualKeyCode::N),
|
||||
GameInput::Help => KeyMouse::Key(VirtualKeyCode::F1),
|
||||
GameInput::ToggleInterface => KeyMouse::Key(VirtualKeyCode::F2),
|
||||
GameInput::ToggleDebug => KeyMouse::Key(VirtualKeyCode::F3),
|
||||
GameInput::Fullscreen => KeyMouse::Key(VirtualKeyCode::F11),
|
||||
GameInput::Screenshot => KeyMouse::Key(VirtualKeyCode::F4),
|
||||
GameInput::ToggleIngameUi => KeyMouse::Key(VirtualKeyCode::F6),
|
||||
GameInput::Roll => MIDDLE_CLICK_KEY,
|
||||
GameInput::Respawn => KeyMouse::Key(VirtualKeyCode::Space),
|
||||
GameInput::Interact => KeyMouse::Key(VirtualKeyCode::E),
|
||||
GameInput::ToggleWield => KeyMouse::Key(VirtualKeyCode::T),
|
||||
GameInput::FreeLook => KeyMouse::Key(VirtualKeyCode::L),
|
||||
GameInput::AutoWalk => KeyMouse::Key(VirtualKeyCode::Period),
|
||||
GameInput::CameraClamp => KeyMouse::Key(VirtualKeyCode::Apostrophe),
|
||||
GameInput::CycleCamera => KeyMouse::Key(VirtualKeyCode::Key0),
|
||||
GameInput::Slot1 => KeyMouse::Key(VirtualKeyCode::Key1),
|
||||
GameInput::Slot2 => KeyMouse::Key(VirtualKeyCode::Key2),
|
||||
GameInput::Slot3 => KeyMouse::Key(VirtualKeyCode::Key3),
|
||||
GameInput::Slot4 => KeyMouse::Key(VirtualKeyCode::Key4),
|
||||
GameInput::Slot5 => KeyMouse::Key(VirtualKeyCode::Key5),
|
||||
GameInput::Slot6 => KeyMouse::Key(VirtualKeyCode::Key6),
|
||||
GameInput::Slot7 => KeyMouse::Key(VirtualKeyCode::Key7),
|
||||
GameInput::Slot8 => KeyMouse::Key(VirtualKeyCode::Key8),
|
||||
GameInput::Slot9 => KeyMouse::Key(VirtualKeyCode::Key9),
|
||||
GameInput::Slot10 => KeyMouse::Key(VirtualKeyCode::Q),
|
||||
GameInput::SwapLoadout => KeyMouse::Key(VirtualKeyCode::Tab),
|
||||
GameInput::Select => KeyMouse::Key(VirtualKeyCode::Y),
|
||||
GameInput::AcceptGroupInvite => KeyMouse::Key(VirtualKeyCode::U),
|
||||
GameInput::DeclineGroupInvite => KeyMouse::Key(VirtualKeyCode::I),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Default for ControlSettings {
|
||||
fn default() -> Self {
|
||||
let mut new_settings = Self {
|
||||
keybindings: HashMap::new(),
|
||||
inverse_keybindings: HashMap::new(),
|
||||
};
|
||||
// Sets the initial keybindings for those GameInputs.
|
||||
for game_input in GameInput::iterator() {
|
||||
new_settings.insert_binding(game_input, ControlSettings::default_binding(game_input));
|
||||
}
|
||||
new_settings
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct GamepadSettings {
|
||||
pub game_buttons: con_settings::GameButtons,
|
||||
pub menu_buttons: con_settings::MenuButtons,
|
||||
pub game_axis: con_settings::GameAxis,
|
||||
pub menu_axis: con_settings::MenuAxis,
|
||||
pub game_analog_buttons: con_settings::GameAnalogButton,
|
||||
pub menu_analog_buttons: con_settings::MenuAnalogButton,
|
||||
pub pan_sensitivity: u32,
|
||||
pub pan_invert_y: bool,
|
||||
pub axis_deadzones: HashMap<crate::controller::Axis, f32>,
|
||||
pub button_deadzones: HashMap<crate::controller::AnalogButton, f32>,
|
||||
pub mouse_emulation_sensitivity: u32,
|
||||
pub inverted_axes: Vec<crate::controller::Axis>,
|
||||
}
|
||||
|
||||
impl Default for GamepadSettings {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
game_buttons: con_settings::GameButtons::default(),
|
||||
menu_buttons: con_settings::MenuButtons::default(),
|
||||
game_axis: con_settings::GameAxis::default(),
|
||||
menu_axis: con_settings::MenuAxis::default(),
|
||||
game_analog_buttons: con_settings::GameAnalogButton::default(),
|
||||
menu_analog_buttons: con_settings::MenuAnalogButton::default(),
|
||||
pan_sensitivity: 10,
|
||||
pan_invert_y: false,
|
||||
axis_deadzones: HashMap::new(),
|
||||
button_deadzones: HashMap::new(),
|
||||
mouse_emulation_sensitivity: 12,
|
||||
inverted_axes: Vec::new(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub mod con_settings {
|
||||
use crate::controller::*;
|
||||
use gilrs::{Axis as GilAxis, Button as GilButton};
|
||||
use serde::{Deserialize, Serialize};
|
||||
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct GameButtons {
|
||||
pub primary: Button,
|
||||
pub secondary: Button,
|
||||
pub toggle_cursor: Button,
|
||||
pub escape: Button,
|
||||
pub enter: Button,
|
||||
pub command: Button,
|
||||
pub move_forward: Button,
|
||||
pub move_left: Button,
|
||||
pub move_back: Button,
|
||||
pub move_right: Button,
|
||||
pub jump: Button,
|
||||
pub sit: Button,
|
||||
pub dance: Button,
|
||||
pub glide: Button,
|
||||
pub climb: Button,
|
||||
pub climb_down: Button,
|
||||
pub swimup: Button,
|
||||
pub swimdown: Button,
|
||||
pub sneak: Button,
|
||||
pub toggle_lantern: Button,
|
||||
pub mount: Button,
|
||||
pub map: Button,
|
||||
pub bag: Button,
|
||||
pub quest_log: Button,
|
||||
pub character_window: Button,
|
||||
pub social: Button,
|
||||
pub crafting: Button,
|
||||
pub spellbook: Button,
|
||||
pub settings: Button,
|
||||
pub help: Button,
|
||||
pub toggle_interface: Button,
|
||||
pub toggle_debug: Button,
|
||||
pub fullscreen: Button,
|
||||
pub screenshot: Button,
|
||||
pub toggle_ingame_ui: Button,
|
||||
pub roll: Button,
|
||||
pub respawn: Button,
|
||||
pub interact: Button,
|
||||
pub toggle_wield: Button,
|
||||
pub swap_loadout: Button,
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct MenuButtons {
|
||||
pub up: Button,
|
||||
pub down: Button,
|
||||
pub left: Button,
|
||||
pub right: Button,
|
||||
pub scroll_up: Button,
|
||||
pub scroll_down: Button,
|
||||
pub scroll_left: Button,
|
||||
pub scroll_right: Button,
|
||||
pub home: Button,
|
||||
pub end: Button,
|
||||
pub apply: Button,
|
||||
pub back: Button,
|
||||
pub exit: Button,
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct GameAxis {
|
||||
pub movement_x: Axis,
|
||||
pub movement_y: Axis,
|
||||
pub camera_x: Axis,
|
||||
pub camera_y: Axis,
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct MenuAxis {
|
||||
pub move_x: Axis,
|
||||
pub move_y: Axis,
|
||||
pub scroll_x: Axis,
|
||||
pub scroll_y: Axis,
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct GameAnalogButton {}
|
||||
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct MenuAnalogButton {}
|
||||
|
||||
impl Default for GameButtons {
|
||||
fn default() -> Self {
|
||||
// binding to unknown = getting skipped from processing
|
||||
Self {
|
||||
primary: Button::Simple(GilButton::RightTrigger2),
|
||||
secondary: Button::Simple(GilButton::LeftTrigger2),
|
||||
toggle_cursor: Button::Simple(GilButton::Unknown),
|
||||
escape: Button::Simple(GilButton::Start),
|
||||
enter: Button::Simple(GilButton::Unknown),
|
||||
command: Button::Simple(GilButton::Unknown),
|
||||
move_forward: Button::Simple(GilButton::Unknown),
|
||||
move_left: Button::Simple(GilButton::Unknown),
|
||||
move_back: Button::Simple(GilButton::Unknown),
|
||||
move_right: Button::Simple(GilButton::Unknown),
|
||||
jump: Button::Simple(GilButton::South),
|
||||
sit: Button::Simple(GilButton::Unknown),
|
||||
dance: Button::Simple(GilButton::Unknown),
|
||||
glide: Button::Simple(GilButton::LeftTrigger),
|
||||
climb: Button::Simple(GilButton::South),
|
||||
climb_down: Button::Simple(GilButton::East),
|
||||
swimup: Button::Simple(GilButton::South),
|
||||
swimdown: Button::Simple(GilButton::East),
|
||||
sneak: Button::Simple(GilButton::East),
|
||||
toggle_lantern: Button::Simple(GilButton::DPadLeft),
|
||||
mount: Button::Simple(GilButton::North),
|
||||
map: Button::Simple(GilButton::Select),
|
||||
bag: Button::Simple(GilButton::DPadRight),
|
||||
quest_log: Button::Simple(GilButton::Unknown),
|
||||
character_window: Button::Simple(GilButton::Unknown),
|
||||
social: Button::Simple(GilButton::Unknown),
|
||||
crafting: Button::Simple(GilButton::DPadDown),
|
||||
spellbook: Button::Simple(GilButton::Unknown),
|
||||
settings: Button::Simple(GilButton::Unknown),
|
||||
help: Button::Simple(GilButton::Unknown),
|
||||
toggle_interface: Button::Simple(GilButton::Unknown),
|
||||
toggle_debug: Button::Simple(GilButton::Unknown),
|
||||
fullscreen: Button::Simple(GilButton::Unknown),
|
||||
screenshot: Button::Simple(GilButton::Unknown),
|
||||
toggle_ingame_ui: Button::Simple(GilButton::Unknown),
|
||||
roll: Button::Simple(GilButton::RightTrigger),
|
||||
respawn: Button::Simple(GilButton::South),
|
||||
interact: Button::Simple(GilButton::North),
|
||||
toggle_wield: Button::Simple(GilButton::West),
|
||||
swap_loadout: Button::Simple(GilButton::LeftThumb),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Default for MenuButtons {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
up: Button::Simple(GilButton::Unknown),
|
||||
down: Button::Simple(GilButton::Unknown),
|
||||
left: Button::Simple(GilButton::Unknown),
|
||||
right: Button::Simple(GilButton::Unknown),
|
||||
scroll_up: Button::Simple(GilButton::Unknown),
|
||||
scroll_down: Button::Simple(GilButton::Unknown),
|
||||
scroll_left: Button::Simple(GilButton::Unknown),
|
||||
scroll_right: Button::Simple(GilButton::Unknown),
|
||||
home: Button::Simple(GilButton::DPadUp),
|
||||
end: Button::Simple(GilButton::DPadDown),
|
||||
apply: Button::Simple(GilButton::South),
|
||||
back: Button::Simple(GilButton::East),
|
||||
exit: Button::Simple(GilButton::Mode),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Default for GameAxis {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
movement_x: Axis::Simple(GilAxis::LeftStickX),
|
||||
movement_y: Axis::Simple(GilAxis::LeftStickY),
|
||||
camera_x: Axis::Simple(GilAxis::RightStickX),
|
||||
camera_y: Axis::Simple(GilAxis::RightStickY),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Default for MenuAxis {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
move_x: Axis::Simple(GilAxis::RightStickX),
|
||||
move_y: Axis::Simple(GilAxis::RightStickY),
|
||||
scroll_x: Axis::Simple(GilAxis::LeftStickX),
|
||||
scroll_y: Axis::Simple(GilAxis::LeftStickY),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Default for GameAnalogButton {
|
||||
fn default() -> Self { Self {} }
|
||||
}
|
||||
|
||||
impl Default for MenuAnalogButton {
|
||||
fn default() -> Self { Self {} }
|
||||
}
|
||||
}
|
||||
|
||||
/// `InterfaceSettings` contains UI, HUD and Map options.
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct InterfaceSettings {
|
||||
pub toggle_debug: bool,
|
||||
pub sct: bool,
|
||||
pub sct_player_batch: bool,
|
||||
pub sct_damage_batch: bool,
|
||||
pub speech_bubble_dark_mode: bool,
|
||||
pub speech_bubble_icon: bool,
|
||||
pub crosshair_transp: f32,
|
||||
pub chat_transp: f32,
|
||||
pub chat_character_name: bool,
|
||||
pub crosshair_type: CrosshairType,
|
||||
pub intro_show: Intro,
|
||||
pub xp_bar: XpBar,
|
||||
pub shortcut_numbers: ShortcutNumbers,
|
||||
pub buff_position: BuffPosition,
|
||||
pub bar_numbers: BarNumbers,
|
||||
pub ui_scale: ScaleMode,
|
||||
pub map_zoom: f64,
|
||||
pub map_drag: Vec2<f64>,
|
||||
pub map_show_topo_map: bool,
|
||||
pub map_show_difficulty: bool,
|
||||
pub map_show_towns: bool,
|
||||
pub map_show_dungeons: bool,
|
||||
pub map_show_castles: bool,
|
||||
pub loading_tips: bool,
|
||||
pub map_show_caves: bool,
|
||||
pub map_show_trees: bool,
|
||||
pub minimap_show: bool,
|
||||
pub minimap_face_north: bool,
|
||||
}
|
||||
|
||||
impl Default for InterfaceSettings {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
toggle_debug: false,
|
||||
sct: true,
|
||||
sct_player_batch: false,
|
||||
sct_damage_batch: false,
|
||||
speech_bubble_dark_mode: false,
|
||||
speech_bubble_icon: true,
|
||||
crosshair_transp: 0.6,
|
||||
chat_transp: 0.4,
|
||||
chat_character_name: true,
|
||||
crosshair_type: CrosshairType::Round,
|
||||
intro_show: Intro::Show,
|
||||
xp_bar: XpBar::Always,
|
||||
shortcut_numbers: ShortcutNumbers::On,
|
||||
buff_position: BuffPosition::Bar,
|
||||
bar_numbers: BarNumbers::Values,
|
||||
ui_scale: ScaleMode::RelativeToWindow([1920.0, 1080.0].into()),
|
||||
map_zoom: 10.0,
|
||||
map_drag: Vec2 { x: 0.0, y: 0.0 },
|
||||
map_show_topo_map: false,
|
||||
map_show_difficulty: true,
|
||||
map_show_towns: true,
|
||||
map_show_dungeons: true,
|
||||
map_show_castles: true,
|
||||
loading_tips: true,
|
||||
map_show_caves: true,
|
||||
map_show_trees: true,
|
||||
minimap_show: true,
|
||||
minimap_face_north: false,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// `GameplaySettings` contains sensitivity and gameplay options.
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct GameplaySettings {
|
||||
pub pan_sensitivity: u32,
|
||||
pub zoom_sensitivity: u32,
|
||||
pub camera_clamp_angle: u32,
|
||||
pub zoom_inversion: bool,
|
||||
pub mouse_y_inversion: bool,
|
||||
pub smooth_pan_enable: bool,
|
||||
pub free_look_behavior: PressBehavior,
|
||||
pub auto_walk_behavior: PressBehavior,
|
||||
pub camera_clamp_behavior: PressBehavior,
|
||||
pub stop_auto_walk_on_input: bool,
|
||||
pub auto_camera: bool,
|
||||
}
|
||||
|
||||
impl Default for GameplaySettings {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
pan_sensitivity: 100,
|
||||
zoom_sensitivity: 100,
|
||||
camera_clamp_angle: 45,
|
||||
zoom_inversion: false,
|
||||
mouse_y_inversion: false,
|
||||
smooth_pan_enable: false,
|
||||
free_look_behavior: PressBehavior::Toggle,
|
||||
auto_walk_behavior: PressBehavior::Toggle,
|
||||
camera_clamp_behavior: PressBehavior::Toggle,
|
||||
stop_auto_walk_on_input: true,
|
||||
auto_camera: false,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// `NetworkingSettings` stores server and networking settings.
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct NetworkingSettings {
|
||||
pub username: String,
|
||||
pub servers: Vec<String>,
|
||||
pub default_server: String,
|
||||
pub trusted_auth_servers: HashSet<String>,
|
||||
}
|
||||
|
||||
impl Default for NetworkingSettings {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
username: "".to_string(),
|
||||
servers: vec!["server.veloren.net".to_string()],
|
||||
default_server: "server.veloren.net".to_string(),
|
||||
trusted_auth_servers: ["https://auth.veloren.net"]
|
||||
.iter()
|
||||
.map(|s| s.to_string())
|
||||
.collect(),
|
||||
}
|
||||
}
|
||||
}
|
||||
pub use audio::{AudioOutput, AudioSettings};
|
||||
pub use control::ControlSettings;
|
||||
pub use gamepad::GamepadSettings;
|
||||
pub use gameplay::GameplaySettings;
|
||||
pub use graphics::{get_fps, Fps, GraphicsSettings};
|
||||
pub use interface::InterfaceSettings;
|
||||
pub use language::LanguageSettings;
|
||||
pub use networking::NetworkingSettings;
|
||||
|
||||
/// `Log` stores whether we should create a log file
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
@ -584,123 +55,6 @@ impl Default for Log {
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Copy, Clone, Serialize, Deserialize, Debug, PartialEq)]
|
||||
pub enum Fps {
|
||||
Max(u32),
|
||||
Unlimited,
|
||||
}
|
||||
|
||||
pub fn get_fps(max_fps: Fps) -> u32 {
|
||||
match max_fps {
|
||||
Fps::Max(x) => x,
|
||||
Fps::Unlimited => u32::MAX,
|
||||
}
|
||||
}
|
||||
|
||||
impl fmt::Display for Fps {
|
||||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
||||
match *self {
|
||||
Fps::Max(x) => write!(f, "{}", x),
|
||||
Fps::Unlimited => write!(f, "Unlimited"),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// `GraphicsSettings` contains settings related to framerate and in-game
|
||||
/// visuals.
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct GraphicsSettings {
|
||||
pub view_distance: u32,
|
||||
pub sprite_render_distance: u32,
|
||||
pub particles_enabled: bool,
|
||||
pub figure_lod_render_distance: u32,
|
||||
pub max_fps: Fps,
|
||||
pub fov: u16,
|
||||
pub gamma: f32,
|
||||
pub exposure: f32,
|
||||
pub ambiance: f32,
|
||||
pub render_mode: RenderMode,
|
||||
pub window_size: [u16; 2],
|
||||
pub fullscreen: FullScreenSettings,
|
||||
pub lod_detail: u32,
|
||||
}
|
||||
|
||||
impl Default for GraphicsSettings {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
view_distance: 10,
|
||||
sprite_render_distance: 100,
|
||||
particles_enabled: true,
|
||||
figure_lod_render_distance: 300,
|
||||
max_fps: Fps::Max(60),
|
||||
fov: 70,
|
||||
gamma: 1.0,
|
||||
exposure: 1.0,
|
||||
ambiance: 10.0,
|
||||
render_mode: RenderMode::default(),
|
||||
window_size: [1280, 720],
|
||||
fullscreen: FullScreenSettings::default(),
|
||||
lod_detail: 250,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
pub enum AudioOutput {
|
||||
/// Veloren's audio system wont work on some systems,
|
||||
/// so you can use this to disable it, and allow the
|
||||
/// game to function
|
||||
// If this option is disabled, functions in the rodio
|
||||
// library MUST NOT be called.
|
||||
Off,
|
||||
#[serde(other)]
|
||||
Automatic,
|
||||
}
|
||||
|
||||
impl AudioOutput {
|
||||
pub fn is_enabled(&self) -> bool { !matches!(self, Self::Off) }
|
||||
}
|
||||
/// `AudioSettings` controls the volume of different audio subsystems and which
|
||||
/// device is used.
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct AudioSettings {
|
||||
pub master_volume: f32,
|
||||
pub music_volume: f32,
|
||||
pub sfx_volume: f32,
|
||||
pub max_sfx_channels: usize,
|
||||
|
||||
/// Audio Device that Voxygen will use to play audio.
|
||||
pub output: AudioOutput,
|
||||
}
|
||||
|
||||
impl Default for AudioSettings {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
master_volume: 1.0,
|
||||
music_volume: 0.4,
|
||||
sfx_volume: 0.6,
|
||||
max_sfx_channels: 30,
|
||||
output: AudioOutput::Automatic,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct LanguageSettings {
|
||||
pub selected_language: String,
|
||||
}
|
||||
|
||||
impl Default for LanguageSettings {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
selected_language: i18n::REFERENCE_LANG.to_string(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// `Settings` contains everything that can be configured in the settings.ron
|
||||
/// file.
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
|
26
voxygen/src/settings/networking.rs
Normal file
26
voxygen/src/settings/networking.rs
Normal file
@ -0,0 +1,26 @@
|
||||
use hashbrown::HashSet;
|
||||
use serde::{Deserialize, Serialize};
|
||||
|
||||
/// `NetworkingSettings` stores server and networking settings.
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
#[serde(default)]
|
||||
pub struct NetworkingSettings {
|
||||
pub username: String,
|
||||
pub servers: Vec<String>,
|
||||
pub default_server: String,
|
||||
pub trusted_auth_servers: HashSet<String>,
|
||||
}
|
||||
|
||||
impl Default for NetworkingSettings {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
username: "".to_string(),
|
||||
servers: vec!["server.veloren.net".to_string()],
|
||||
default_server: "server.veloren.net".to_string(),
|
||||
trusted_auth_servers: ["https://auth.veloren.net"]
|
||||
.iter()
|
||||
.map(|s| s.to_string())
|
||||
.collect(),
|
||||
}
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue
Block a user