diff --git a/src/config.rs b/src/config.rs index bef1358..ce41047 100644 --- a/src/config.rs +++ b/src/config.rs @@ -10,6 +10,7 @@ use std::{fs::File, io::BufReader}; pub struct Config { pub selected_profile_name: String, pub debug_view_enabled: bool, + pub user_profiles: Vec, } impl Default for Config { @@ -18,6 +19,7 @@ impl Default for Config { // TODO: handle first start with no profile selected selected_profile_name: "".to_string(), debug_view_enabled: false, + user_profiles: vec![], } } } diff --git a/src/profile.rs b/src/profile.rs index 532bb33..486d3f1 100644 --- a/src/profile.rs +++ b/src/profile.rs @@ -1,6 +1,6 @@ use crate::{ - file_utils::get_writer, - paths::{BWRAP_SYSTEM_PREFIX, SYSTEM_PREFIX}, + file_utils::{get_data_dir, get_writer}, + paths::{data_monado_path, data_opencomposite_path, BWRAP_SYSTEM_PREFIX, SYSTEM_PREFIX}, }; use expect_dialog::ExpectDialog; use serde::{Deserialize, Serialize}; @@ -37,6 +37,30 @@ impl Display for Profile { } } +impl Default for Profile { + fn default() -> Self { + Self { + name: "Default profile name".into(), + xrservice_path: data_monado_path(), + xrservice_type: XRServiceType::Monado, + opencomposite_path: data_opencomposite_path(), + basalt_path: None, + mercury_path: None, + libsurvive_path: None, + basalt_enabled: false, + mercury_enabled: false, + libsurvive_enabled: false, + environment: HashMap::new(), + prefix: format!( + "{data}/prefixes/default_profile_prefix", + data = get_data_dir() + ), + can_be_built: true, + editable: true, + } + } +} + impl Profile { pub fn get_steam_launch_options(&self) -> String { let mut opts = vec![]; diff --git a/src/ui/app.rs b/src/ui/app.rs index 23b5deb..98e7483 100644 --- a/src/ui/app.rs +++ b/src/ui/app.rs @@ -350,11 +350,12 @@ impl SimpleComponent for App { sender: ComponentSender, ) -> ComponentParts { let config = Config::get_config(); - let profiles = vec![ + let mut profiles = vec![ valve_index_profile(), system_valve_index_profile(), wivrn_profile(), ]; + profiles.extend(config.user_profiles.clone()); let dependencies_dialog = adw::MessageDialog::builder() .modal(true) .transient_for(root) diff --git a/src/ui/main_view.rs b/src/ui/main_view.rs index 81acaca..457bd4d 100644 --- a/src/ui/main_view.rs +++ b/src/ui/main_view.rs @@ -49,6 +49,7 @@ pub enum MainViewMsg { ProfileSelected(u32), UpdateSelectedProfile(Profile), EditProfile, + CreateProfile, DuplicateProfile, } @@ -104,30 +105,6 @@ impl SimpleComponent for MainView { set_icon_name: icon_name::MENU, set_menu_model: Some(&app_menu), }, - pack_start = >k::Box { - set_orientation: gtk::Orientation::Horizontal, - add_css_class: "linked", - #[name(profiles_dropdown)] - gtk::DropDown { - set_tooltip_text: Some("Profiles"), - #[track = "model.changed(Self::profile_names())"] - set_model: Some(&{ - let names: Vec<_> = model.profile_names.iter().map(String::as_str).collect(); - gtk::StringList::new(&names) - }), - connect_selected_item_notify[sender] => move |this| { - sender.input(MainViewMsg::ProfileSelected(this.selected())); - }, - }, - gtk::Button { - set_icon_name: icon_name::EDIT, - add_css_class: "suggested-action", - set_tooltip_text: Some("Edit Profile"), - connect_clicked[sender] => move |_| { - sender.input(Self::Input::EditProfile); - } - } - }, #[track = "model.changed(Self::enable_debug_view())"] set_show_end_title_buttons: !model.enable_debug_view, }, @@ -162,6 +139,47 @@ impl SimpleComponent for MainView { model.steam_launch_options_box.widget(), model.install_wivrn_box.widget(), } + }, + gtk::Separator { + set_orientation: gtk::Orientation::Horizontal, + set_hexpand: true, + }, + gtk::Box { + set_orientation: gtk::Orientation::Horizontal, + set_spacing: 12, + add_css_class: "toolbar", + add_css_class: "view", + gtk::Box { + set_orientation: gtk::Orientation::Horizontal, + add_css_class: "linked", + #[name(profiles_dropdown)] + gtk::DropDown { + set_hexpand: true, + set_tooltip_text: Some("Profiles"), + #[track = "model.changed(Self::profile_names())"] + set_model: Some(&{ + let names: Vec<_> = model.profile_names.iter().map(String::as_str).collect(); + gtk::StringList::new(&names) + }), + connect_selected_item_notify[sender] => move |this| { + sender.input(MainViewMsg::ProfileSelected(this.selected())); + }, + }, + gtk::Button { + set_icon_name: icon_name::EDIT, + set_tooltip_text: Some("Edit Profile"), + connect_clicked[sender] => move |_| { + sender.input(Self::Input::EditProfile); + } + }, + gtk::Button { + set_icon_name: "list-add-symbolic", + set_tooltip_text: Some("Create Profile"), + connect_clicked[sender] => move |_| { + sender.input(Self::Input::CreateProfile); + } + } + }, } } } @@ -243,8 +261,11 @@ impl SimpleComponent for MainView { self.profile_not_editable_dialog.present(); } } + Self::Input::CreateProfile => { + println!("create"); + } Self::Input::DuplicateProfile => { - println!("dup") + println!("dup"); } } }