fix(linux): prefer native Wayland for AppImage webviews
This commit is contained in:
1 parent
638f4ccdfd
commit
66b6ed8efc
3 files changed
+76
No files matched your search
@@ -37,6 +37,7 @@ use crate::core::{
|
||||
|
||||
#[cfg_attr(mobile, tauri::mobile_entry_point)]
|
||||
pub fn run() {
|
||||
platform::prepare_appimage_wayland_backend();
|
||||
portable_updater::schedule_cleanup_from_environment();
|
||||
let runtime = runtime::resolve().expect("failed to resolve runtime paths");
|
||||
runtime::prepare_webview_environment(&runtime);
|
||||
|
||||
@@ -0,0 +1,66 @@
|
||||
const PREFERRED_APPIMAGE_WAYLAND_BACKENDS: &str = "wayland,x11";
|
||||
|
||||
pub fn prepare_appimage_wayland_backend() {
|
||||
let is_appimage = env_var_is_non_empty("APPIMAGE") || env_var_is_non_empty("APPDIR");
|
||||
let has_wayland_display = env_var_is_non_empty("WAYLAND_DISPLAY");
|
||||
let current_backend = std::env::var("GDK_BACKEND").ok();
|
||||
|
||||
let Some(backend) =
|
||||
preferred_gdk_backend(is_appimage, has_wayland_display, current_backend.as_deref())
|
||||
else {
|
||||
return;
|
||||
};
|
||||
|
||||
// SAFETY: `run()` calls this synchronously before Tauri/GTK initialization and before
|
||||
// NyaTerm starts worker threads. Changing the process environment is therefore not racing
|
||||
// with environment reads in other threads.
|
||||
unsafe {
|
||||
std::env::set_var("GDK_BACKEND", backend);
|
||||
}
|
||||
}
|
||||
|
||||
fn env_var_is_non_empty(name: &str) -> bool {
|
||||
std::env::var_os(name).is_some_and(|value| !value.is_empty())
|
||||
}
|
||||
|
||||
fn preferred_gdk_backend(
|
||||
is_appimage: bool,
|
||||
has_wayland_display: bool,
|
||||
current_backend: Option<&str>,
|
||||
) -> Option<&'static str> {
|
||||
// Tauri's AppImage GTK hook currently forces GDK_BACKEND=x11. On modern Wayland
|
||||
// sessions that sends WebKitGTK through XWayland and can leave the webview unable to
|
||||
// receive pointer/keyboard input. Prefer native Wayland while retaining X11 as a fallback.
|
||||
(is_appimage && has_wayland_display && current_backend == Some("x11"))
|
||||
.then_some(PREFERRED_APPIMAGE_WAYLAND_BACKENDS)
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::{PREFERRED_APPIMAGE_WAYLAND_BACKENDS, preferred_gdk_backend};
|
||||
|
||||
#[test]
|
||||
fn prefers_wayland_for_appimage_when_tauri_forced_x11() {
|
||||
assert_eq!(
|
||||
preferred_gdk_backend(true, true, Some("x11")),
|
||||
Some(PREFERRED_APPIMAGE_WAYLAND_BACKENDS)
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn leaves_non_appimage_linux_packages_unchanged() {
|
||||
assert_eq!(preferred_gdk_backend(false, true, Some("x11")), None);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn leaves_x11_sessions_unchanged() {
|
||||
assert_eq!(preferred_gdk_backend(true, false, Some("x11")), None);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn preserves_existing_non_x11_backend_selection() {
|
||||
assert_eq!(preferred_gdk_backend(true, true, Some("wayland")), None);
|
||||
assert_eq!(preferred_gdk_backend(true, true, Some("wayland,x11")), None);
|
||||
assert_eq!(preferred_gdk_backend(true, true, None), None);
|
||||
}
|
||||
}
|
||||
@@ -1,6 +1,15 @@
|
||||
#[cfg(windows)]
|
||||
mod windows_external_drop;
|
||||
|
||||
#[cfg(target_os = "linux")]
|
||||
mod linux_appimage_wayland;
|
||||
|
||||
#[cfg(target_os = "linux")]
|
||||
pub use linux_appimage_wayland::prepare_appimage_wayland_backend;
|
||||
|
||||
#[cfg(not(target_os = "linux"))]
|
||||
pub fn prepare_appimage_wayland_backend() {}
|
||||
|
||||
#[cfg(windows)]
|
||||
pub use windows_external_drop::install_external_file_drop_bridge;
|
||||
|
||||
|
||||
Reference in new issue
Block a user