diff --git a/assets/voxygen/element/frames/esc menu.vox b/assets/voxygen/element/frames/esc menu.vox new file mode 100644 index 0000000000..f8c42e5ccc --- /dev/null +++ b/assets/voxygen/element/frames/esc menu.vox @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:184cc4eb64493aae944fa3265acd739f4c79cd2bf15d047da2698af4d1088cd0 +size 79928 diff --git a/assets/voxygen/element/frames/esc_menu.vox b/assets/voxygen/element/frames/esc_menu.vox new file mode 100644 index 0000000000..b4637818c8 --- /dev/null +++ b/assets/voxygen/element/frames/esc_menu.vox @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:f8e4a0d231a08ead9cb4677531d5aae0391ac69548e5cba8c7bfb98e3c22b85e +size 79856 diff --git a/client/src/lib.rs b/client/src/lib.rs index e8b4c791f0..51f871aac5 100644 --- a/client/src/lib.rs +++ b/client/src/lib.rs @@ -104,6 +104,20 @@ impl Client { self.client_state = ClientState::Pending; } + /// Request a state transition to `ClientState::Character`. + pub fn request_logout(&mut self) { + self.postbox + .send_message(ClientMsg::RequestState(ClientState::Connected)); + self.client_state = ClientState::Pending; + } + + /// Request a state transition to `ClientState::Character`. + pub fn request_remove_character(&mut self) { + self.postbox + .send_message(ClientMsg::RequestState(ClientState::Registered)); + self.client_state = ClientState::Pending; + } + pub fn set_view_distance(&mut self, view_distance: u32) { self.view_distance = Some(view_distance.max(1).min(25)); self.postbox diff --git a/voxygen/src/hud/esc_menu.rs b/voxygen/src/hud/esc_menu.rs index 1b7db480df..53017e57dc 100644 --- a/voxygen/src/hud/esc_menu.rs +++ b/voxygen/src/hud/esc_menu.rs @@ -3,7 +3,7 @@ use conrod_core::{ widget_ids, Labelable, Positionable, Sizeable, Widget, WidgetCommon, }; -use super::{img_ids::Imgs, Fonts, TEXT_COLOR}; +use super::{img_ids::Imgs, settings_window::SettingsTab, Fonts, TEXT_COLOR}; widget_ids! { struct Ids { @@ -14,6 +14,7 @@ widget_ids! { menu_button_3, menu_button_4, menu_button_5, + menu_button_6, } } @@ -41,7 +42,8 @@ pub struct State { } pub enum Event { - OpenSettings, + OpenSettings(SettingsTab), + CharacterSelection, Logout, Quit, Close, @@ -65,92 +67,107 @@ impl<'a> Widget for EscMenu<'a> { fn update(self, args: widget::UpdateArgs) -> Self::Event { let widget::UpdateArgs { state, ui, .. } = args; - Image::new(self.imgs.esc_bg) - .w_h(228.0, 450.0) + Image::new(self.imgs.esc_frame) + .w_h(240.0, 440.0) .middle_of(ui.window) .set(state.ids.esc_bg, ui); Image::new(self.imgs.fireplace) - .w_h(180.0, 60.0) - .mid_top_with_margin_on(state.ids.esc_bg, 50.0) + .w_h(210.0, 60.0) + .mid_top_with_margin_on(state.ids.esc_bg, 15.0) .set(state.ids.fireplace, ui); - // Settings + // Resume if Button::image(self.imgs.button) - .mid_top_with_margin_on(state.ids.esc_bg, 115.0) - .w_h(170.0, 50.0) + .mid_bottom_with_margin_on(state.ids.fireplace, -55.0) + .w_h(210.0, 50.0) .hover_image(self.imgs.button_hover) .press_image(self.imgs.button_press) - .label("Settings") - .label_y(conrod_core::position::Relative::Scalar(2.0)) + .label("Resume") + .label_y(conrod_core::position::Relative::Scalar(3.0)) .label_color(TEXT_COLOR) - .label_font_size(17) + .label_font_size(20) .set(state.ids.menu_button_1, ui) .was_clicked() { - return Some(Event::OpenSettings); + return Some(Event::Close); }; - // Controls + + // Settings if Button::image(self.imgs.button) - .mid_top_with_margin_on(state.ids.esc_bg, 175.0) - .w_h(170.0, 50.0) + .mid_bottom_with_margin_on(state.ids.menu_button_1, -65.0) + .w_h(210.0, 50.0) .hover_image(self.imgs.button_hover) .press_image(self.imgs.button_press) - .label("Controls") - .label_y(conrod_core::position::Relative::Scalar(2.0)) + .label("Settings") + .label_y(conrod_core::position::Relative::Scalar(3.0)) .label_color(TEXT_COLOR) - .label_font_size(17) + .label_font_size(20) .set(state.ids.menu_button_2, ui) .was_clicked() { - // TODO: Show controls window. + return Some(Event::OpenSettings(SettingsTab::Interface)); }; - // Servers + // Controls if Button::image(self.imgs.button) - .mid_top_with_margin_on(state.ids.esc_bg, 235.0) - .w_h(170.0, 50.0) + .mid_bottom_with_margin_on(state.ids.menu_button_2, -55.0) + .w_h(210.0, 50.0) .hover_image(self.imgs.button_hover) .press_image(self.imgs.button_press) - .label("Characters") - .label_y(conrod_core::position::Relative::Scalar(2.0)) + .label("Controls") + .label_y(conrod_core::position::Relative::Scalar(3.0)) .label_color(TEXT_COLOR) - .label_font_size(17) + .label_font_size(20) .set(state.ids.menu_button_3, ui) .was_clicked() { - return Some(Event::Logout); // TODO: Open Character Selection + return Some(Event::OpenSettings(SettingsTab::Controls)); + }; + // Characters + if Button::image(self.imgs.button) + .mid_bottom_with_margin_on(state.ids.menu_button_3, -55.0) + .w_h(210.0, 50.0) + .hover_image(self.imgs.button_hover) + .press_image(self.imgs.button_press) + .label("Characters") + .label_y(conrod_core::position::Relative::Scalar(3.0)) + .label_color(TEXT_COLOR) + .label_font_size(20) + .set(state.ids.menu_button_4, ui) + .was_clicked() + { + return Some(Event::CharacterSelection); }; // Logout if Button::image(self.imgs.button) - .mid_top_with_margin_on(state.ids.esc_bg, 295.0) - .w_h(170.0, 50.0) + .mid_bottom_with_margin_on(state.ids.menu_button_4, -65.0) + .w_h(210.0, 50.0) .hover_image(self.imgs.button_hover) .press_image(self.imgs.button_press) .label("Logout") - .label_y(conrod_core::position::Relative::Scalar(2.0)) + .label_y(conrod_core::position::Relative::Scalar(3.0)) .label_color(TEXT_COLOR) - .label_font_size(17) - .set(state.ids.menu_button_4, ui) + .label_font_size(20) + .set(state.ids.menu_button_5, ui) .was_clicked() { return Some(Event::Logout); }; // Quit if Button::image(self.imgs.button) - .mid_top_with_margin_on(state.ids.esc_bg, 355.0) - .w_h(170.0, 50.0) + .mid_bottom_with_margin_on(state.ids.menu_button_5, -55.0) + .w_h(210.0, 50.0) .hover_image(self.imgs.button_hover) .press_image(self.imgs.button_press) - .label("Quit") - .label_y(conrod_core::position::Relative::Scalar(2.0)) + .label("Quit Game") + .label_y(conrod_core::position::Relative::Scalar(3.0)) .label_color(TEXT_COLOR) - .label_font_size(17) - .set(state.ids.menu_button_5, ui) + .label_font_size(20) + .set(state.ids.menu_button_6, ui) .was_clicked() { return Some(Event::Quit); }; - None } } diff --git a/voxygen/src/hud/img_ids.rs b/voxygen/src/hud/img_ids.rs index 33a8462944..e67a8140c6 100644 --- a/voxygen/src/hud/img_ids.rs +++ b/voxygen/src/hud/img_ids.rs @@ -36,6 +36,7 @@ image_ids! { check_checked_mo: "voxygen/element/buttons/check/yes_mo.vox", slider: "voxygen/element/slider/track.vox", slider_indicator: "voxygen/element/slider/indicator.vox", + esc_frame: "voxygen/element/frames/esc_menu.vox", // Map Window map_frame_l: "voxygen/element/frames/map_l.vox", diff --git a/voxygen/src/hud/mod.rs b/voxygen/src/hud/mod.rs index 5bc2e971ac..e915b2de19 100644 --- a/voxygen/src/hud/mod.rs +++ b/voxygen/src/hud/mod.rs @@ -18,7 +18,7 @@ use esc_menu::EscMenu; use img_ids::Imgs; use map::Map; use minimap::MiniMap; -use settings_window::SettingsWindow; +use settings_window::{SettingsTab, SettingsWindow}; use skillbar::Skillbar; use small_window::{SmallWindow, SmallWindowType}; @@ -112,6 +112,7 @@ pub enum Event { AdjustViewDistance(u32), AdjustVolume(f32), ChangeAudioDevice(String), + CharacterSelection, Logout, Quit, } @@ -138,6 +139,7 @@ pub struct Show { inventory_test_button: bool, mini_map: bool, ingame: bool, + settings_tab: SettingsTab, want_grab: bool, } @@ -229,6 +231,14 @@ impl Show { self.want_grab = false; } } + + fn open_setting_tab(&mut self, tab: SettingsTab) { + self.open_windows = Windows::Settings; + self.esc_menu = false; + self.settings_tab = tab; + self.bag = false; + self.want_grab = false; + } } pub struct Hud { @@ -272,6 +282,7 @@ impl Hud { ui: true, inventory_test_button: false, mini_map: false, + settings_tab: SettingsTab::Interface, want_grab: true, ingame: true, }, @@ -546,7 +557,7 @@ impl Hud { // Settings if let Windows::Settings = self.show.open_windows { - for event in SettingsWindow::new(&self.show, &self.imgs, &self.fonts, &global_state) + for event in SettingsWindow::new(&global_state, &self.show, &self.imgs, &self.fonts) .set(self.ids.settings_window, ui_widgets) { match event { @@ -555,10 +566,8 @@ impl Hud { self.show.inventory_test_button = !self.show.inventory_test_button } settings_window::Event::ToggleDebug => self.show.debug = !self.show.debug, - settings_window::Event::Close => { - self.show.settings(false); - self.force_ungrab = true; - } + settings_window::Event::ChangeTab(tab) => self.show.open_setting_tab(tab), + settings_window::Event::Close => self.show.open_windows = Windows::None, settings_window::Event::AdjustViewDistance(view_distance) => { events.push(Event::AdjustViewDistance(view_distance)); } @@ -617,9 +626,8 @@ impl Hud { // Esc-menu if self.show.esc_menu { match EscMenu::new(&self.imgs, &self.fonts).set(self.ids.esc_menu, ui_widgets) { - Some(esc_menu::Event::OpenSettings) => { - self.show.esc_menu = false; - self.show.open_windows = Windows::Settings; + Some(esc_menu::Event::OpenSettings(tab)) => { + self.show.open_setting_tab(tab); } Some(esc_menu::Event::Close) => { self.show.esc_menu = false; @@ -628,6 +636,7 @@ impl Hud { } Some(esc_menu::Event::Logout) => events.push(Event::Logout), Some(esc_menu::Event::Quit) => events.push(Event::Quit), + Some(esc_menu::Event::CharacterSelection) => events.push(Event::CharacterSelection), None => {} } } diff --git a/voxygen/src/hud/settings_window.rs b/voxygen/src/hud/settings_window.rs index 8624a67b07..c3f8775fe6 100644 --- a/voxygen/src/hud/settings_window.rs +++ b/voxygen/src/hud/settings_window.rs @@ -16,7 +16,6 @@ use conrod_core::{ }; widget_ids! { struct Ids { - settings_content, settings_icon, settings_button_mo, @@ -51,7 +50,7 @@ widget_ids! { } } -enum SettingsTab { +pub enum SettingsTab { Interface, Video, Sound, @@ -61,37 +60,35 @@ enum SettingsTab { #[derive(WidgetCommon)] pub struct SettingsWindow<'a> { + global_state: &'a GlobalState, + show: &'a Show, imgs: &'a Imgs, fonts: &'a Fonts, - global_state: &'a GlobalState, - #[conrod(common_builder)] common: widget::CommonBuilder, } impl<'a> SettingsWindow<'a> { pub fn new( + global_state: &'a GlobalState, show: &'a Show, imgs: &'a Imgs, fonts: &'a Fonts, - global_state: &'a GlobalState, ) -> Self { Self { + global_state, show, imgs, fonts, - global_state, common: widget::CommonBuilder::default(), } } } pub struct State { - settings_tab: SettingsTab, - ids: Ids, } @@ -99,6 +96,7 @@ pub enum Event { ToggleHelp, ToggleInventoryTestButton, ToggleDebug, + ChangeTab(SettingsTab), Close, AdjustViewDistance(u32), AdjustVolume(f32), @@ -112,7 +110,6 @@ impl<'a> Widget for SettingsWindow<'a> { fn init_state(&self, id_gen: widget::id::Generator) -> Self::State { State { - settings_tab: SettingsTab::Interface, ids: Ids::new(id_gen), } } @@ -170,18 +167,18 @@ impl<'a> Widget for SettingsWindow<'a> { .set(state.ids.settings_title, ui); // Interface - if Button::image(if let SettingsTab::Interface = state.settings_tab { + if Button::image(if let SettingsTab::Interface = self.show.settings_tab { self.imgs.settings_button_pressed } else { self.imgs.settings_button }) .w_h(31.0 * 4.0, 12.0 * 4.0) - .hover_image(if let SettingsTab::Interface = state.settings_tab { + .hover_image(if let SettingsTab::Interface = self.show.settings_tab { self.imgs.settings_button_pressed } else { self.imgs.settings_button_hover }) - .press_image(if let SettingsTab::Interface = state.settings_tab { + .press_image(if let SettingsTab::Interface = self.show.settings_tab { self.imgs.settings_button_pressed } else { self.imgs.settings_button_press @@ -193,10 +190,10 @@ impl<'a> Widget for SettingsWindow<'a> { .set(state.ids.interface, ui) .was_clicked() { - state.update(|s| s.settings_tab = SettingsTab::Interface); + events.push(Event::ChangeTab(SettingsTab::Interface)); } - if let SettingsTab::Interface = state.settings_tab { + if let SettingsTab::Interface = self.show.settings_tab { // Help let show_help = ToggleButton::new(self.show.help, self.imgs.check, self.imgs.check_checked) @@ -265,18 +262,18 @@ impl<'a> Widget for SettingsWindow<'a> { } // 2 Gameplay - if Button::image(if let SettingsTab::Gameplay = state.settings_tab { + if Button::image(if let SettingsTab::Gameplay = self.show.settings_tab { self.imgs.settings_button_pressed } else { self.imgs.settings_button }) .w_h(31.0 * 4.0, 12.0 * 4.0) - .hover_image(if let SettingsTab::Gameplay = state.settings_tab { + .hover_image(if let SettingsTab::Gameplay = self.show.settings_tab { self.imgs.settings_button_pressed } else { self.imgs.settings_button_hover }) - .press_image(if let SettingsTab::Gameplay = state.settings_tab { + .press_image(if let SettingsTab::Gameplay = self.show.settings_tab { self.imgs.settings_button_pressed } else { self.imgs.settings_button_press @@ -288,22 +285,22 @@ impl<'a> Widget for SettingsWindow<'a> { .set(state.ids.gameplay, ui) .was_clicked() { - state.update(|s| s.settings_tab = SettingsTab::Gameplay); + events.push(Event::ChangeTab(SettingsTab::Gameplay)); } // 3 Controls - if Button::image(if let SettingsTab::Controls = state.settings_tab { + if Button::image(if let SettingsTab::Controls = self.show.settings_tab { self.imgs.settings_button_pressed } else { self.imgs.settings_button }) .w_h(31.0 * 4.0, 12.0 * 4.0) - .hover_image(if let SettingsTab::Controls = state.settings_tab { + .hover_image(if let SettingsTab::Controls = self.show.settings_tab { self.imgs.settings_button_pressed } else { self.imgs.settings_button_hover }) - .press_image(if let SettingsTab::Controls = state.settings_tab { + .press_image(if let SettingsTab::Controls = self.show.settings_tab { self.imgs.settings_button_pressed } else { self.imgs.settings_button_press @@ -315,9 +312,9 @@ impl<'a> Widget for SettingsWindow<'a> { .set(state.ids.controls, ui) .was_clicked() { - state.update(|s| s.settings_tab = SettingsTab::Controls); + events.push(Event::ChangeTab(SettingsTab::Controls)); } - if let SettingsTab::Controls = state.settings_tab { + if let SettingsTab::Controls = self.show.settings_tab { Text::new( "Free Cursor\n\ Toggle Help Window\n\ @@ -472,18 +469,18 @@ impl<'a> Widget for SettingsWindow<'a> { .set(state.ids.controls_controls, ui); } // 4 Video - if Button::image(if let SettingsTab::Video = state.settings_tab { + if Button::image(if let SettingsTab::Video = self.show.settings_tab { self.imgs.settings_button_pressed } else { self.imgs.settings_button }) .w_h(31.0 * 4.0, 12.0 * 4.0) - .hover_image(if let SettingsTab::Video = state.settings_tab { + .hover_image(if let SettingsTab::Video = self.show.settings_tab { self.imgs.settings_button_pressed } else { self.imgs.settings_button_hover }) - .press_image(if let SettingsTab::Video = state.settings_tab { + .press_image(if let SettingsTab::Video = self.show.settings_tab { self.imgs.settings_button_pressed } else { self.imgs.settings_button_press @@ -496,10 +493,10 @@ impl<'a> Widget for SettingsWindow<'a> { .set(state.ids.video, ui) .was_clicked() { - state.update(|s| s.settings_tab = SettingsTab::Video); + events.push(Event::ChangeTab(SettingsTab::Video)); } // Contents - if let SettingsTab::Video = state.settings_tab { + if let SettingsTab::Video = self.show.settings_tab { Text::new("View Distance") .top_left_with_margins_on(state.ids.settings_content, 10.0, 10.0) .font_size(14) @@ -525,18 +522,18 @@ impl<'a> Widget for SettingsWindow<'a> { } } // 5 Sound - if Button::image(if let SettingsTab::Sound = state.settings_tab { + if Button::image(if let SettingsTab::Sound = self.show.settings_tab { self.imgs.settings_button_pressed } else { self.imgs.settings_button }) .w_h(31.0 * 4.0, 12.0 * 4.0) - .hover_image(if let SettingsTab::Sound = state.settings_tab { + .hover_image(if let SettingsTab::Sound = self.show.settings_tab { self.imgs.settings_button_pressed } else { self.imgs.settings_button_hover }) - .press_image(if let SettingsTab::Sound = state.settings_tab { + .press_image(if let SettingsTab::Sound = self.show.settings_tab { self.imgs.settings_button_pressed } else { self.imgs.settings_button_press @@ -549,11 +546,10 @@ impl<'a> Widget for SettingsWindow<'a> { .set(state.ids.sound, ui) .was_clicked() { - state.update(|s| s.settings_tab = SettingsTab::Sound); + events.push(Event::ChangeTab(SettingsTab::Sound)); } // Contents - if let SettingsTab::Sound = state.settings_tab { - // Volume Slider ---------------------------------------------------- + if let SettingsTab::Sound = self.show.settings_tab { Text::new("Volume") .top_left_with_margins_on(state.ids.settings_content, 10.0, 10.0) .font_size(14) diff --git a/voxygen/src/session.rs b/voxygen/src/session.rs index 2de343e91d..4ca9513d6f 100644 --- a/voxygen/src/session.rs +++ b/voxygen/src/session.rs @@ -181,7 +181,10 @@ impl PlayState for SessionState { // TODO: Handle result self.client.borrow_mut().send_chat(msg); } - HudEvent::Logout => return PlayStateResult::Pop, + HudEvent::CharacterSelection => { + self.client.borrow_mut().request_remove_character() + } + HudEvent::Logout => self.client.borrow_mut().request_logout(), HudEvent::Quit => { return PlayStateResult::Shutdown; }