Phosphor
Qt6 / Wayland library suite for window-management tools
 
Loading...
Searching...
No Matches
phosphor-snap-engine

‍Manual zone-based placement engine. Implements IPlacementEngine for screens running a user-drawn layout; handles auto-snap on window open, directional zone navigation, floating, rotation, resnap-on-layout- change, and serialisation through SnapState.

Responsibility

The PlasmaZones daemon dispatches every window-lifecycle and shortcut event through PhosphorEngine::IPlacementEngine so it doesn't have to branch on the current placement mode. phosphor-snap-engine is the manual-mode implementation: when a screen has a zone layout active, this engine owns the decisions about which zone a new window joins, how Super+arrow navigates between zones, how rotation cycles windows, and what happens on float / unfloat.

The engine reads from shared services (none of which it owns):

The engine owns SnapState (per-screen mutable state implementing IPlacementState) and SnapNavigationTargetResolver (pure compute for keyboard-navigation target geometries).

Key types

Type Purpose
PhosphorSnapEngine::SnapEngine Concrete IPlacementEngine for manual zone layouts
PhosphorSnapEngine::SnapState Per-screen IPlacementState: zone assignments, pre-tile geometry, floating set
PhosphorEngine::ISnapSettings Settings the engine reads (exclusions, sticky-window handling, master toggle)
PhosphorSnapEngine::INavigationStateProvider Narrow read-only state contract the daemon implements
PhosphorSnapEngine::IZoneAdjacencyResolver Directional zone lookup contract the daemon implements
PhosphorSnapEngine::SnapNavigationTargetResolver Pure compute for move / focus / swap / push / cycle / restore target geometries

Typical use

Wire up the engine inside the daemon's composition root:

#include <PhosphorSnapEngine/SnapEngine.h>

using namespace PhosphorSnapEngine;

auto* snap = new SnapEngine(layoutRegistry,
                            windowTrackingService,
                            zoneDetector,
                            virtualDesktopManager,
                            /*parent*/ daemon);
snap->setSettings(snapSettingsAdaptor);
snap->setNavigationStateProvider(windowTrackingAdaptor);
snap->setZoneAdjacencyResolver(zoneDetectionAdaptor);

// Dispatch from the daemon:
placementEngineRouter.bind("snap", snap);

Design notes

  • Inherits PlacementEngineBase. The Unmanaged / EngineOwned / Floated FSM lives once in the base class; this engine only adds the manual-zone-specific decisions (which zone, when to auto-snap, how to navigate).
  • Typed interfaces, not QObject* + invokeMethod. Daemon dispatch uses the narrow INavigationStateProvider and IZoneAdjacencyResolver contracts — strictly typed, no string method names, no opaque pointers.
  • State is shared, not owned. Window-tracking, virtual-desktop, layout-registry, and zone-detector all live outside the engine. SnapState is the one thing this lib owns mutably; everything else is read or commanded.
  • Cross-engine handoff. engineId(), handoffReceive, and handoffRelease implement the placement-engine handoff protocol so a window that moves from a snap screen to an autotile screen cleanly transitions ownership without the daemon doing the bookkeeping.
  • Auto-assign master toggle. autoAssignAllLayouts() is the process-wide override; effective behaviour is globalAutoAssign OR layout->autoAssign(). Autotile screens are short-circuited upstream in windowOpened and never reach this path.

Dependencies

See also