fix(startup): block Windows activation during WebView2 init (#37)

- Issue #37: keep the Windows host hidden, unfocused, and non-activatable while WebView2 is constructed.\n- Restore focusability and reveal the main window only after Tauri reports Ready.\n- Preserve queued startup restores on non-Windows instead of clearing them before servicing.\n\nFixes #37.
This commit is contained in:
NimBold
2026-08-27 17:34:04 +03:30
parent 9c0ba106d6
commit a5cecb3777
+23 -8
View File
@@ -3993,6 +3993,18 @@ fn mark_main_window_startup_complete(app_handle: &tauri::AppHandle) {
} }
} }
#[cfg(target_os = "windows")]
fn reveal_main_window(app_handle: &tauri::AppHandle) {
if let Some(window) = app_handle.get_webview_window("main") {
if let Err(error) = window.set_focusable(true) {
log::warn!("Could not make the main window focusable: {error}");
}
if let Err(error) = window.show() {
eprintln!("Failed to reveal the main window: {error}");
}
}
}
fn restore_pending_main_window(app_handle: &tauri::AppHandle) { fn restore_pending_main_window(app_handle: &tauri::AppHandle) {
if app_handle if app_handle
.try_state::<MainWindowRestoreState>() .try_state::<MainWindowRestoreState>()
@@ -18541,10 +18553,13 @@ pub fn run() {
#[cfg(target_os = "windows")] #[cfg(target_os = "windows")]
{ {
// Wry installs its parent WM_SETFOCUS handler while WebView2 // Wry installs its parent WM_SETFOCUS handler while WebView2
// is still being initialized. Keep the host unfocused and // is still being initialized. Keep the host hidden and
// hidden until RunEvent::Ready so Windows cannot re-enter that // non-activatable until RunEvent::Ready so Windows cannot
// handler during native construction. // re-enter that handler during native construction.
main_window_builder = main_window_builder.visible(false).focused(false); main_window_builder = main_window_builder
.visible(false)
.focused(false)
.focusable(false);
} }
main_window_builder main_window_builder
.build() .build()
@@ -19883,10 +19898,10 @@ pub fn run() {
.run(|app_handle, event| match event { .run(|app_handle, event| match event {
tauri::RunEvent::Ready => { tauri::RunEvent::Ready => {
mark_main_window_startup_complete(app_handle); mark_main_window_startup_complete(app_handle);
if let Some(state) = app_handle.try_state::<MainWindowRestoreState>() { #[cfg(target_os = "windows")]
state.requested.swap(false, Ordering::AcqRel); reveal_main_window(app_handle);
} #[cfg(not(target_os = "windows"))]
restore_main_window(app_handle); restore_pending_main_window(app_handle);
} }
#[cfg(target_os = "macos")] #[cfg(target_os = "macos")]
tauri::RunEvent::Opened { urls } => { tauri::RunEvent::Opened { urls } => {