Watch: Add "Toggle Dashboard" button by default, Toast: Show user-specific error messages in various places, WayVR: Modify example env vars
This commit is contained in:
@@ -43,7 +43,7 @@ use crate::{
|
|||||||
};
|
};
|
||||||
|
|
||||||
#[cfg(feature = "wayvr")]
|
#[cfg(feature = "wayvr")]
|
||||||
use crate::overlays::wayvr::{wayvr_action, WayVRAction};
|
use crate::{gui::modular::button::WayVRAction, overlays::wayvr::wayvr_action};
|
||||||
|
|
||||||
pub mod helpers;
|
pub mod helpers;
|
||||||
pub mod input;
|
pub mod input;
|
||||||
|
|||||||
@@ -32,7 +32,7 @@ use crate::{
|
|||||||
};
|
};
|
||||||
|
|
||||||
#[cfg(feature = "wayvr")]
|
#[cfg(feature = "wayvr")]
|
||||||
use crate::overlays::wayvr::{wayvr_action, WayVRAction};
|
use crate::{gui::modular::button::WayVRAction, overlays::wayvr::wayvr_action};
|
||||||
|
|
||||||
mod helpers;
|
mod helpers;
|
||||||
mod input;
|
mod input;
|
||||||
|
|||||||
@@ -10,7 +10,7 @@ use serde::Deserialize;
|
|||||||
use crate::state::AppState;
|
use crate::state::AppState;
|
||||||
|
|
||||||
#[cfg(feature = "wayvr")]
|
#[cfg(feature = "wayvr")]
|
||||||
use crate::overlays::wayvr::WayVRAction;
|
use crate::gui::modular::button::WayVRAction;
|
||||||
|
|
||||||
use super::{
|
use super::{
|
||||||
common::OverlaySelector,
|
common::OverlaySelector,
|
||||||
|
|||||||
@@ -83,6 +83,8 @@ impl EGLData {
|
|||||||
|
|
||||||
let context = egl.create_context(display, config, None, &context_attrib_list)?;
|
let context = egl.create_context(display, config, None, &context_attrib_list)?;
|
||||||
|
|
||||||
|
log::debug!("eglMakeCurrent");
|
||||||
|
|
||||||
egl.make_current(display, None, None, Some(context))?;
|
egl.make_current(display, None, None, Some(context))?;
|
||||||
|
|
||||||
Ok(EGLData {
|
Ok(EGLData {
|
||||||
@@ -94,18 +96,6 @@ impl EGLData {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[allow(dead_code)]
|
|
||||||
pub fn make_current(&self, surface: &khronos_egl::Surface) -> anyhow::Result<()> {
|
|
||||||
self.egl.make_current(
|
|
||||||
self.display,
|
|
||||||
Some(*surface),
|
|
||||||
Some(*surface),
|
|
||||||
Some(self.context),
|
|
||||||
)?;
|
|
||||||
|
|
||||||
Ok(())
|
|
||||||
}
|
|
||||||
|
|
||||||
fn query_dmabuf_mod_info(&self) -> anyhow::Result<DMAbufModifierInfo> {
|
fn query_dmabuf_mod_info(&self) -> anyhow::Result<DMAbufModifierInfo> {
|
||||||
let target_fourcc = 0x34324258; //XB24
|
let target_fourcc = 0x34324258; //XB24
|
||||||
|
|
||||||
|
|||||||
@@ -17,7 +17,8 @@ use crate::{
|
|||||||
wayvr,
|
wayvr,
|
||||||
},
|
},
|
||||||
config::{load_known_yaml, ConfigType},
|
config::{load_known_yaml, ConfigType},
|
||||||
overlays::wayvr::{WayVRAction, WayVRData},
|
gui::modular::button::WayVRAction,
|
||||||
|
overlays::wayvr::WayVRData,
|
||||||
};
|
};
|
||||||
|
|
||||||
// Flat version of RelativeTo
|
// Flat version of RelativeTo
|
||||||
|
|||||||
@@ -19,14 +19,14 @@ use crate::{
|
|||||||
config::{save_layout, save_settings, AStrSetExt},
|
config::{save_layout, save_settings, AStrSetExt},
|
||||||
hid::VirtualKey,
|
hid::VirtualKey,
|
||||||
overlays::{
|
overlays::{
|
||||||
toast::{Toast, ToastTopic},
|
toast::{error_toast, Toast, ToastTopic},
|
||||||
watch::WATCH_NAME,
|
watch::WATCH_NAME,
|
||||||
},
|
},
|
||||||
state::AppState,
|
state::AppState,
|
||||||
};
|
};
|
||||||
|
|
||||||
#[cfg(feature = "wayvr")]
|
#[cfg(not(feature = "wayvr"))]
|
||||||
use crate::overlays::wayvr::WayVRAction;
|
use crate::overlays::toast::error_toast_str;
|
||||||
|
|
||||||
use super::{ExecArgs, ModularControl, ModularData};
|
use super::{ExecArgs, ModularControl, ModularData};
|
||||||
|
|
||||||
@@ -119,6 +119,26 @@ pub enum WindowAction {
|
|||||||
Destroy,
|
Destroy,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(Deserialize, Clone)]
|
||||||
|
pub enum WayVRDisplayClickAction {
|
||||||
|
ToggleVisibility,
|
||||||
|
Reset,
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Deserialize, Clone)]
|
||||||
|
#[allow(dead_code)] // in case if WayVR feature is disabled
|
||||||
|
pub enum WayVRAction {
|
||||||
|
AppClick {
|
||||||
|
catalog_name: Arc<str>,
|
||||||
|
app_name: Arc<str>,
|
||||||
|
},
|
||||||
|
DisplayClick {
|
||||||
|
display_name: Arc<str>,
|
||||||
|
action: WayVRDisplayClickAction,
|
||||||
|
},
|
||||||
|
ToggleDashboard,
|
||||||
|
}
|
||||||
|
|
||||||
#[derive(Deserialize, Clone)]
|
#[derive(Deserialize, Clone)]
|
||||||
#[serde(tag = "type")]
|
#[serde(tag = "type")]
|
||||||
pub enum ButtonAction {
|
pub enum ButtonAction {
|
||||||
@@ -137,8 +157,10 @@ pub enum ButtonAction {
|
|||||||
target: OverlaySelector,
|
target: OverlaySelector,
|
||||||
action: OverlayAction,
|
action: OverlayAction,
|
||||||
},
|
},
|
||||||
#[cfg(feature = "wayvr")]
|
// Ignored if "wayvr" feature is not enabled
|
||||||
WayVR(WayVRAction),
|
WayVR {
|
||||||
|
action: WayVRAction,
|
||||||
|
},
|
||||||
Window {
|
Window {
|
||||||
target: Arc<str>,
|
target: Arc<str>,
|
||||||
action: WindowAction,
|
action: WindowAction,
|
||||||
@@ -332,9 +354,16 @@ fn handle_action(action: &ButtonAction, press: &mut PressData, app: &mut AppStat
|
|||||||
ButtonAction::Watch { action } => run_watch(action, app),
|
ButtonAction::Watch { action } => run_watch(action, app),
|
||||||
ButtonAction::Overlay { target, action } => run_overlay(target, action, app),
|
ButtonAction::Overlay { target, action } => run_overlay(target, action, app),
|
||||||
ButtonAction::Window { target, action } => run_window(target, action, app),
|
ButtonAction::Window { target, action } => run_window(target, action, app),
|
||||||
#[cfg(feature = "wayvr")]
|
ButtonAction::WayVR { action } => {
|
||||||
ButtonAction::WayVR(action) => {
|
#[cfg(feature = "wayvr")]
|
||||||
app.tasks.enqueue(TaskType::WayVR(action.clone()));
|
{
|
||||||
|
app.tasks.enqueue(TaskType::WayVR(action.clone()));
|
||||||
|
}
|
||||||
|
#[cfg(not(feature = "wayvr"))]
|
||||||
|
{
|
||||||
|
let _ = &action;
|
||||||
|
error_toast_str(app, "WayVR feature is not enabled");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
ButtonAction::VirtualKey { keycode, action } => app
|
ButtonAction::VirtualKey { keycode, action } => app
|
||||||
.hid_provider
|
.hid_provider
|
||||||
@@ -461,12 +490,12 @@ fn run_system(action: &SystemAction, app: &mut AppState) {
|
|||||||
}
|
}
|
||||||
SystemAction::PersistConfig => {
|
SystemAction::PersistConfig => {
|
||||||
if let Err(e) = save_settings(&app.session.config) {
|
if let Err(e) = save_settings(&app.session.config) {
|
||||||
log::error!("Failed to save config: {:?}", e);
|
error_toast(app, "Failed to save config", e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
SystemAction::PersistLayout => {
|
SystemAction::PersistLayout => {
|
||||||
if let Err(e) = save_layout(&app.session.config) {
|
if let Err(e) = save_layout(&app.session.config) {
|
||||||
log::error!("Failed to save layout: {:?}", e);
|
error_toast(app, "Failed to save layout", e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -477,7 +506,7 @@ fn run_exec(args: &ExecArgs, toast: &Option<Arc<str>>, press: &mut PressData, ap
|
|||||||
match proc.try_wait() {
|
match proc.try_wait() {
|
||||||
Ok(Some(code)) => {
|
Ok(Some(code)) => {
|
||||||
if !code.success() {
|
if !code.success() {
|
||||||
log::error!("Child process exited with code: {}", code);
|
error_toast(app, "Child process exited with code", code);
|
||||||
}
|
}
|
||||||
press.child = None;
|
press.child = None;
|
||||||
}
|
}
|
||||||
@@ -487,7 +516,7 @@ fn run_exec(args: &ExecArgs, toast: &Option<Arc<str>>, press: &mut PressData, ap
|
|||||||
}
|
}
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
press.child = None;
|
press.child = None;
|
||||||
log::error!("Error checking child process: {:?}", e);
|
error_toast(app, "Error checking child process", e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -500,7 +529,7 @@ fn run_exec(args: &ExecArgs, toast: &Option<Arc<str>>, press: &mut PressData, ap
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
log::error!("Failed to spawn process {:?}: {:?}", args, e);
|
error_toast(app, &format!("Failed to spawn process {:?}", args), e);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
@@ -651,7 +680,9 @@ fn run_overlay(overlay: &OverlaySelector, action: &OverlayAction, app: &mut AppS
|
|||||||
if state_dirty {
|
if state_dirty {
|
||||||
match save_layout(&app.session.config) {
|
match save_layout(&app.session.config) {
|
||||||
Ok(_) => log::debug!("Saved state"),
|
Ok(_) => log::debug!("Saved state"),
|
||||||
Err(e) => log::error!("Failed to save state: {:?}", e),
|
Err(e) => {
|
||||||
|
error_toast(app, "Failed to save state", e);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}),
|
}),
|
||||||
|
|||||||
@@ -9,7 +9,11 @@ use std::{
|
|||||||
time::Instant,
|
time::Instant,
|
||||||
};
|
};
|
||||||
|
|
||||||
use crate::{gui::modular::FALLBACK_COLOR, state::AppState};
|
use crate::{
|
||||||
|
gui::modular::FALLBACK_COLOR,
|
||||||
|
overlays::toast::{error_toast, error_toast_str},
|
||||||
|
state::AppState,
|
||||||
|
};
|
||||||
|
|
||||||
use serde::Deserialize;
|
use serde::Deserialize;
|
||||||
|
|
||||||
@@ -233,14 +237,21 @@ pub(super) fn label_update(control: &mut ModularControl, _: &mut (), app: &mut A
|
|||||||
match proc.try_wait() {
|
match proc.try_wait() {
|
||||||
Ok(Some(code)) => {
|
Ok(Some(code)) => {
|
||||||
if !code.success() {
|
if !code.success() {
|
||||||
log::error!("Child process exited with code: {}", code);
|
error_toast(
|
||||||
|
app,
|
||||||
|
"LabelData::Exec: Child process exited with code",
|
||||||
|
code,
|
||||||
|
);
|
||||||
} else {
|
} else {
|
||||||
if let Some(mut stdout) = proc.stdout.take() {
|
if let Some(mut stdout) = proc.stdout.take() {
|
||||||
let mut buf = String::new();
|
let mut buf = String::new();
|
||||||
if stdout.read_to_string(&mut buf).is_ok() {
|
if stdout.read_to_string(&mut buf).is_ok() {
|
||||||
control.set_text(&buf);
|
control.set_text(&buf);
|
||||||
} else {
|
} else {
|
||||||
log::error!("Failed to read stdout for child process");
|
error_toast_str(
|
||||||
|
app,
|
||||||
|
"LabelData::Exec: Failed to read stdout for child process",
|
||||||
|
);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
return;
|
return;
|
||||||
@@ -256,7 +267,7 @@ pub(super) fn label_update(control: &mut ModularControl, _: &mut (), app: &mut A
|
|||||||
}
|
}
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
*child = None;
|
*child = None;
|
||||||
log::error!("Error checking child process: {:?}", e);
|
error_toast(app, "Error checking child process", e);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -282,7 +293,7 @@ pub(super) fn label_update(control: &mut ModularControl, _: &mut (), app: &mut A
|
|||||||
*child = Some(proc);
|
*child = Some(proc);
|
||||||
}
|
}
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
log::error!("Failed to spawn process {:?}: {:?}", args, e);
|
error_toast(app, &format!("Failed to spawn process {:?}", args), e);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -3,6 +3,9 @@ pub mod label;
|
|||||||
|
|
||||||
use std::{fs::File, sync::Arc};
|
use std::{fs::File, sync::Arc};
|
||||||
|
|
||||||
|
#[cfg(feature = "wayvr")]
|
||||||
|
use button::{WayVRAction, WayVRDisplayClickAction};
|
||||||
|
|
||||||
use glam::Vec4;
|
use glam::Vec4;
|
||||||
use serde::Deserialize;
|
use serde::Deserialize;
|
||||||
use vulkano::{command_buffer::CommandBufferUsage, image::view::ImageView};
|
use vulkano::{command_buffer::CommandBufferUsage, image::view::ImageView};
|
||||||
@@ -12,9 +15,6 @@ use crate::{
|
|||||||
graphics::dds::WlxCommandBufferDds, state::AppState,
|
graphics::dds::WlxCommandBufferDds, state::AppState,
|
||||||
};
|
};
|
||||||
|
|
||||||
#[cfg(feature = "wayvr")]
|
|
||||||
use crate::overlays::wayvr::{WayVRAction, WayVRDisplayClickAction};
|
|
||||||
|
|
||||||
use self::{
|
use self::{
|
||||||
button::{modular_button_init, ButtonAction, ButtonData, OverlayAction},
|
button::{modular_button_init, ButtonAction, ButtonData, OverlayAction},
|
||||||
label::{modular_label_init, LabelContent, LabelData},
|
label::{modular_label_init, LabelContent, LabelData},
|
||||||
@@ -452,10 +452,12 @@ pub fn modular_canvas(
|
|||||||
);
|
);
|
||||||
|
|
||||||
let data = ButtonData {
|
let data = ButtonData {
|
||||||
click_up: Some(vec![ButtonAction::WayVR(WayVRAction::AppClick {
|
click_up: Some(vec![ButtonAction::WayVR {
|
||||||
catalog_name: catalog_name.clone(),
|
action: WayVRAction::AppClick {
|
||||||
app_name: Arc::from(app.name.as_str()),
|
catalog_name: catalog_name.clone(),
|
||||||
})]),
|
app_name: Arc::from(app.name.as_str()),
|
||||||
|
},
|
||||||
|
}]),
|
||||||
..Default::default()
|
..Default::default()
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -502,16 +504,18 @@ pub fn modular_canvas(
|
|||||||
);
|
);
|
||||||
|
|
||||||
let data = ButtonData {
|
let data = ButtonData {
|
||||||
click_up: Some(vec![ButtonAction::WayVR(WayVRAction::DisplayClick {
|
click_up: Some(vec![ButtonAction::WayVR {
|
||||||
display_name: Arc::from(display_name.as_str()),
|
action: WayVRAction::DisplayClick {
|
||||||
action: WayVRDisplayClickAction::ToggleVisibility,
|
display_name: Arc::from(display_name.as_str()),
|
||||||
})]),
|
action: WayVRDisplayClickAction::ToggleVisibility,
|
||||||
long_click_up: Some(vec![ButtonAction::WayVR(
|
},
|
||||||
WayVRAction::DisplayClick {
|
}]),
|
||||||
|
long_click_up: Some(vec![ButtonAction::WayVR {
|
||||||
|
action: WayVRAction::DisplayClick {
|
||||||
display_name: Arc::from(display_name.as_str()),
|
display_name: Arc::from(display_name.as_str()),
|
||||||
action: WayVRDisplayClickAction::Reset,
|
action: WayVRDisplayClickAction::Reset,
|
||||||
},
|
},
|
||||||
)]),
|
}]),
|
||||||
..Default::default()
|
..Default::default()
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@@ -207,3 +207,26 @@ fn new_toast(toast: Toast, app: &mut AppState) -> Option<(OverlayState, Box<dyn
|
|||||||
|
|
||||||
Some((state, backend))
|
Some((state, backend))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn msg_err(app: &mut AppState, message: &str) {
|
||||||
|
Toast::new(ToastTopic::System, "Error".into(), message.into())
|
||||||
|
.with_timeout(3.)
|
||||||
|
.submit(app);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Display the same error in the terminal and as a toast in VR.
|
||||||
|
// Formatted as "Failed to XYZ: Object is not defined"
|
||||||
|
pub fn error_toast<ErrorType>(app: &mut AppState, title: &str, err: ErrorType)
|
||||||
|
where
|
||||||
|
ErrorType: std::fmt::Display + std::fmt::Debug,
|
||||||
|
{
|
||||||
|
log::error!("{}: {:?}", title, err); // More detailed version (use Debug)
|
||||||
|
|
||||||
|
// Brief version (use Display)
|
||||||
|
msg_err(app, &format!("{}: {}", title, err));
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn error_toast_str(app: &mut AppState, message: &str) {
|
||||||
|
log::error!("{}", message);
|
||||||
|
msg_err(app, message);
|
||||||
|
}
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
use glam::{vec3a, Affine2, Vec3, Vec3A};
|
use glam::{vec3a, Affine2, Vec3, Vec3A};
|
||||||
use serde::Deserialize;
|
|
||||||
use std::{cell::RefCell, collections::HashMap, rc::Rc, sync::Arc};
|
use std::{cell::RefCell, collections::HashMap, rc::Rc, sync::Arc};
|
||||||
use vulkano::image::SubresourceLayout;
|
use vulkano::image::SubresourceLayout;
|
||||||
use wlx_capture::frame::{DmabufFrame, FourCC, FrameFormat, FramePlane};
|
use wlx_capture::frame::{DmabufFrame, FourCC, FrameFormat, FramePlane};
|
||||||
@@ -21,9 +20,12 @@ use crate::{
|
|||||||
},
|
},
|
||||||
config_wayvr,
|
config_wayvr,
|
||||||
graphics::WlxGraphics,
|
graphics::WlxGraphics,
|
||||||
|
gui::modular::button::{WayVRAction, WayVRDisplayClickAction},
|
||||||
state::{self, AppState, KeyboardFocus},
|
state::{self, AppState, KeyboardFocus},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
use super::toast::error_toast;
|
||||||
|
|
||||||
// Hard-coded for now
|
// Hard-coded for now
|
||||||
const DASHBOARD_WIDTH: u16 = 960;
|
const DASHBOARD_WIDTH: u16 = 960;
|
||||||
const DASHBOARD_HEIGHT: u16 = 540;
|
const DASHBOARD_HEIGHT: u16 = 540;
|
||||||
@@ -54,6 +56,7 @@ struct OverlayToCreate {
|
|||||||
pub struct WayVRData {
|
pub struct WayVRData {
|
||||||
display_handle_map: HashMap<display::DisplayHandle, OverlayID>,
|
display_handle_map: HashMap<display::DisplayHandle, OverlayID>,
|
||||||
overlays_to_create: Vec<OverlayToCreate>,
|
overlays_to_create: Vec<OverlayToCreate>,
|
||||||
|
dashboard_executed: bool,
|
||||||
pub data: WayVR,
|
pub data: WayVR,
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -63,6 +66,7 @@ impl WayVRData {
|
|||||||
display_handle_map: Default::default(),
|
display_handle_map: Default::default(),
|
||||||
data: WayVR::new(config)?,
|
data: WayVR::new(config)?,
|
||||||
overlays_to_create: Vec::new(),
|
overlays_to_create: Vec::new(),
|
||||||
|
dashboard_executed: false,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -217,6 +221,19 @@ fn get_or_create_display_by_name(
|
|||||||
Ok(disp_handle)
|
Ok(disp_handle)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn executable_exists_in_path(command: &str) -> bool {
|
||||||
|
let Ok(path) = std::env::var("PATH") else {
|
||||||
|
return false; // very unlikely to happen
|
||||||
|
};
|
||||||
|
for dir in path.split(':') {
|
||||||
|
let exec_path = std::path::PathBuf::from(dir).join(command);
|
||||||
|
if exec_path.exists() && exec_path.is_file() {
|
||||||
|
return true; // executable found
|
||||||
|
}
|
||||||
|
}
|
||||||
|
false
|
||||||
|
}
|
||||||
|
|
||||||
fn toggle_dashboard<O>(
|
fn toggle_dashboard<O>(
|
||||||
app: &mut AppState,
|
app: &mut AppState,
|
||||||
overlays: &mut OverlayContainer<O>,
|
overlays: &mut OverlayContainer<O>,
|
||||||
@@ -225,6 +242,12 @@ fn toggle_dashboard<O>(
|
|||||||
where
|
where
|
||||||
O: Default,
|
O: Default,
|
||||||
{
|
{
|
||||||
|
let conf_dash = &app.session.wayvr_config.dashboard;
|
||||||
|
|
||||||
|
if !wayvr.dashboard_executed && !executable_exists_in_path(&conf_dash.exec) {
|
||||||
|
anyhow::bail!("Executable \"{}\" not found", &conf_dash.exec);
|
||||||
|
}
|
||||||
|
|
||||||
let (newly_created, disp_handle) = wayvr.data.state.get_or_create_dashboard_display(
|
let (newly_created, disp_handle) = wayvr.data.state.get_or_create_dashboard_display(
|
||||||
DASHBOARD_WIDTH,
|
DASHBOARD_WIDTH,
|
||||||
DASHBOARD_HEIGHT,
|
DASHBOARD_HEIGHT,
|
||||||
@@ -257,6 +280,8 @@ where
|
|||||||
overlay.state.z_order = Z_ORDER_DASHBOARD;
|
overlay.state.z_order = Z_ORDER_DASHBOARD;
|
||||||
overlay.state.reset(app, true);
|
overlay.state.reset(app, true);
|
||||||
|
|
||||||
|
let conf_dash = &app.session.wayvr_config.dashboard;
|
||||||
|
|
||||||
// FIXME: overlay curvature needs to be dispatched for some unknown reason, this value is not set otherwise
|
// FIXME: overlay curvature needs to be dispatched for some unknown reason, this value is not set otherwise
|
||||||
app.tasks.enqueue(TaskType::Overlay(
|
app.tasks.enqueue(TaskType::Overlay(
|
||||||
OverlaySelector::Id(overlay.state.id),
|
OverlaySelector::Id(overlay.state.id),
|
||||||
@@ -267,8 +292,6 @@ where
|
|||||||
|
|
||||||
overlays.add(overlay);
|
overlays.add(overlay);
|
||||||
|
|
||||||
let conf_dash = &app.session.wayvr_config.dashboard;
|
|
||||||
|
|
||||||
let args_vec = match &conf_dash.args {
|
let args_vec = match &conf_dash.args {
|
||||||
Some(args) => gen_args_vec(args),
|
Some(args) => gen_args_vec(args),
|
||||||
None => vec![],
|
None => vec![],
|
||||||
@@ -286,6 +309,8 @@ where
|
|||||||
.state
|
.state
|
||||||
.spawn_process(disp_handle, &conf_dash.exec, &args_vec, &env_vec)?;
|
.spawn_process(disp_handle, &conf_dash.exec, &args_vec, &env_vec)?;
|
||||||
|
|
||||||
|
wayvr.dashboard_executed = true;
|
||||||
|
|
||||||
return Ok(());
|
return Ok(());
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -626,25 +651,6 @@ where
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize, Clone)]
|
|
||||||
pub enum WayVRDisplayClickAction {
|
|
||||||
ToggleVisibility,
|
|
||||||
Reset,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Deserialize, Clone)]
|
|
||||||
pub enum WayVRAction {
|
|
||||||
AppClick {
|
|
||||||
catalog_name: Arc<str>,
|
|
||||||
app_name: Arc<str>,
|
|
||||||
},
|
|
||||||
DisplayClick {
|
|
||||||
display_name: Arc<str>,
|
|
||||||
action: WayVRDisplayClickAction,
|
|
||||||
},
|
|
||||||
ToggleDashboard,
|
|
||||||
}
|
|
||||||
|
|
||||||
fn show_display<O>(wayvr: &mut WayVRData, overlays: &mut OverlayContainer<O>, display_name: &str)
|
fn show_display<O>(wayvr: &mut WayVRData, overlays: &mut OverlayContainer<O>, display_name: &str)
|
||||||
where
|
where
|
||||||
O: Default,
|
O: Default,
|
||||||
@@ -775,7 +781,7 @@ where
|
|||||||
if let Err(e) = action_app_click(app, overlays, catalog_name, app_name) {
|
if let Err(e) = action_app_click(app, overlays, catalog_name, app_name) {
|
||||||
// Happens if something went wrong with initialization
|
// Happens if something went wrong with initialization
|
||||||
// or input exec path is invalid. Do nothing, just print an error
|
// or input exec path is invalid. Do nothing, just print an error
|
||||||
log::error!("action_app_click failed: {}", e);
|
error_toast(app, "action_app_click failed", e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
WayVRAction::DisplayClick {
|
WayVRAction::DisplayClick {
|
||||||
@@ -783,7 +789,7 @@ where
|
|||||||
action,
|
action,
|
||||||
} => {
|
} => {
|
||||||
if let Err(e) = action_display_click::<O>(app, overlays, display_name, action) {
|
if let Err(e) = action_display_click::<O>(app, overlays, display_name, action) {
|
||||||
log::error!("action_display_click failed: {}", e);
|
error_toast(app, "action_display_click failed", e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
WayVRAction::ToggleDashboard => {
|
WayVRAction::ToggleDashboard => {
|
||||||
@@ -791,7 +797,7 @@ where
|
|||||||
let mut wayvr = wayvr.borrow_mut();
|
let mut wayvr = wayvr.borrow_mut();
|
||||||
|
|
||||||
if let Err(e) = toggle_dashboard::<O>(app, overlays, &mut wayvr) {
|
if let Err(e) = toggle_dashboard::<O>(app, overlays, &mut wayvr) {
|
||||||
log::error!("toggle_dashboard failed: {}", e);
|
error_toast(app, "toggle_dashboard failed", e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -28,9 +28,21 @@ elements:
|
|||||||
target: settings
|
target: settings
|
||||||
action: Destroy # only triggers if exists since before current frame
|
action: Destroy # only triggers if exists since before current frame
|
||||||
|
|
||||||
|
# Dashboard toggle button
|
||||||
|
- type: Button
|
||||||
|
rect: [32, 162, 48, 36]
|
||||||
|
corner_radius: 4
|
||||||
|
font_size: 15
|
||||||
|
bg_color: "#2288FF"
|
||||||
|
fg_color: "#24273a"
|
||||||
|
text: "Dash"
|
||||||
|
click_up:
|
||||||
|
- type: WayVR
|
||||||
|
action: ToggleDashboard
|
||||||
|
|
||||||
# Keyboard button
|
# Keyboard button
|
||||||
- type: Button
|
- type: Button
|
||||||
rect: [32, 162, 60, 36]
|
rect: [84, 162, 48, 36]
|
||||||
corner_radius: 4
|
corner_radius: 4
|
||||||
font_size: 15
|
font_size: 15
|
||||||
fg_color: "#24273a"
|
fg_color: "#24273a"
|
||||||
@@ -65,7 +77,7 @@ elements:
|
|||||||
|
|
||||||
# bottom row, of keyboard + overlays
|
# bottom row, of keyboard + overlays
|
||||||
- type: OverlayList
|
- type: OverlayList
|
||||||
rect: [94, 160, 306, 40]
|
rect: [134, 160, 266, 40]
|
||||||
corner_radius: 4
|
corner_radius: 4
|
||||||
font_size: 15
|
font_size: 15
|
||||||
fg_color: "#cad3f5"
|
fg_color: "#cad3f5"
|
||||||
|
|||||||
@@ -28,11 +28,10 @@ keyboard_repeat_rate: 50
|
|||||||
# Build instructions: https://github.com/olekolek1000/wayvr-dashboard
|
# Build instructions: https://github.com/olekolek1000/wayvr-dashboard
|
||||||
# exec: Executable path, for example /home/USER/wayvr_dashboard/src-tauri/target/release/wayvr_dashboard
|
# exec: Executable path, for example /home/USER/wayvr_dashboard/src-tauri/target/release/wayvr_dashboard
|
||||||
# GDK_BACKEND=wayland: Force-use Wayland for GTK apps
|
# GDK_BACKEND=wayland: Force-use Wayland for GTK apps
|
||||||
# LIBGL_ALWAYS_SOFTWARE: Mesa crash mitigation for Tauri apps on AMD GPUs
|
|
||||||
dashboard:
|
dashboard:
|
||||||
exec: "wayvr_dashboard"
|
exec: "wayvr_dashboard"
|
||||||
args: ""
|
args: ""
|
||||||
env: ["GDK_BACKEND=wayland", "LIBGL_ALWAYS_SOFTWARE=1"]
|
env: ["GDK_BACKEND=wayland"]
|
||||||
|
|
||||||
displays:
|
displays:
|
||||||
Watch:
|
Watch:
|
||||||
|
|||||||
Reference in New Issue
Block a user