fn read_display_geometry<R: Runtime>(
app: &AppHandle<R>,
) -> Option<(Vec<Monitor>, Option<usize>)>Expand description
Read the display layout on the main thread and hand back plain data.
Every caller of fire_break runs on a tokio worker (the scheduler run
loop, the IPC handler, and the tray menu all go through
async_runtime::spawn), which is exactly the thread the monitor getters
must not be called from — see crate::display::on_main_thread for the
mechanism, the create_webview exclusion that keeps ensure_overlay off
the main thread, and the degrade-to-None behaviour (here: no overlay this
time, rather than risking a hang).
Both reads share a single hop so the returned monitor list and primary come from one consistent snapshot. Resolving the primary’s index happens inside the hop too, so the caller receives only plain data and never re-touches a live handle.