Scheduler
The scheduler is a 1 Hz Tokio loop in scheduler/run_loop.rs, part of the scheduler module. Every second it walks a priority cascade. First match wins; all other timers reset.
The cascade
- Pause state —
RunningorPausedUntil(Option<Instant>).Nonemeans indefinite. Auto-resumes when the deadline expires and emitspause:changed. - Bedtime window — if active and local time is inside the window, fire a
Sleepbreak everybedtime_interval_secs. Always enforceable. - Active hours — if
work_window_enabledand local time is outside the window, skip. - Do Not Disturb —
dnd::is_active()(macOS + Windows). - Camera in use —
camera_activeatomic, updated by a background monitor thread. - Idle reset — if idle longer than
idle_reset_secs, skip and reset. - Micro / Long breaks — fire when the interval elapses, if the per-type
*_enabledflag is on.
A pre-break notification fires prebreak_notification_seconds before each break (once per cycle, gated by prebreak_notification_enabled).
Break kinds
| Kind | Duration | Dismissable | Used for |
|---|---|---|---|
Micro | ~20s | Yes | Eye, posture, small reset |
Long | minutes | No (by default) | Real rest |
Sleep | persistent | Snooze, not skip | Bedtime nudge |
Multi-monitor overlay
fire_break picks the target monitors via the monitor_placement setting (primary, active, or all) and ensures one borderless overlay-N window per monitor, sized to that monitor's bounds. active resolves to whichever monitor currently contains the OS cursor (using cursor_position() + a containing-rect lookup); if the cursor lookup fails it falls back to the primary monitor. Existing overlay windows are reused across breaks; the first creation in a cycle gets a 200ms grace before emitting break:start so the React listener has time to register.
When a break's per-kind mode is windowed (see delivery_for and is_windowed_mode), each overlay is sized to 80% of its monitor's physical resolution and centered, and always_on_top is dropped so the surrounding desktop stays reachable. Bedtime (Sleep) is hard-coded to full-screen overlay and ignores this — sleep prompts should be hard to miss.
Never use native fullscreen on macOS
macOS opens a new Space per fullscreen window. That breaks multi-display coverage and feels awful. Size and position manually.
Tray pause
Pause for… is a submenu with seven options (15m / 30m / 1h / 2h / 4h / Until tomorrow 6am / Indefinitely). On pause, Resume enables and the submenu disables; reverse on resume. The pause:changed event keeps the Preferences window in sync.