Keyboard shortcuts

Press ← or → to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

Roadmap

Ordering is intent, not a schedule. The docs hold what exists, DECISIONS.md why. Rust owns platform connections, validation, secrets, resource lifetimes, input and rendering; Lua owns composition, appearance and orchestration. A feature one config lacks is not an engine gap.

Next

Defects or missing pieces a config cannot work around.

ItemWhy / what’s leftADR
expected_revision is uncheckedThe socket drops a frame from another generation, but nothing reads the revision it claims, so it is no authorization guarantee. Settle stale-revision semantics before anything relies on it—
Keyboard focus and accessibilityOnly textfield holds focus; Tab reaches the config as on_navigate("tab"). Needs focusable controls, keyboard activation and an accessibility tree—
Blocking dofile / loadfileThe base library keeps both, and they read files on the Wayland thread outside the CPU budget, against ADR-0048’s intent. Remove them or route them through require’s resolver0048
HiDPIPaint scale is fixed at 1.0, so every surface on a scaled output is upscaled and soft. Needs set_buffer_scale (or fractional-scale plus viewporter) with a matching EGL resize and glyph raster scale—
Silent failuresAn invalid stop_signal is dropped with a log line; mantle set on a state a reload removed still passes. Each should reach the author—
Hyprland layout switchkeyboard/layout.rs sends switchxkblayout, which Hyprland 0.56’s Lua socket likely rejects; the other Hyprland writes already use hl.dsp.*—
Multi-prompt PAMThe worker relays every masked prompt, but LockState and secure_submit carry one password, answered to every prompt. Fingerprint, 2FA and expired passwords fail. Echo-on prompts stay refused0241

Later

Wanted, but each needs a consumer or a decision first.

ItemWhy / what’s leftADR
GreeterMantle as a greetd client under cage or sway. Needs multi-prompt PAM and a session-launch command—
DrawingGradients, mask, shadows and blurs exist; no config-facing paths, and no node masks another. Add the smallest set a real component needs; SVG covers static artwork, but its <text> draws nothing0254–0256
Large listsEvery item up to limit is laid out on every pass and built again whenever anything it read changes, visible or not. Virtualization would need key to be mandatory, which cannot be enforced0191, 0219
Output actionswindows has five actions; screens are read-only. Pick the actions, then settle niri/Hyprland differences and revert0119, 0247
Service depthMPRIS lacks stop, shuffle, repeat, rate and volume; audio has no per-channel levels or peak metering; UPower reads only DisplayDevice; network tracks only the first Wi-Fi device; Bluetooth pairing refuses PIN and passkey entry. Extend for concrete controls—
External IPCset/toggle answer only applied or refused; call returns only what the action returns. No generic state read or subscription0197
Process controlStart, stream and signal exist. No child stdin, cwd or env0175, 0188
Panel root sizingA panel spanning an axis sizes the surface but not its root node, while window and lock roots fill theirs (forced_root_size). Decide whether panel roots fill too—
Move transitionsA sibling closing a gap snaps. Needs the solver’s old and new rects per sibling—
Text field editingNo undo, paste or IME; the secure field edits only at its end. On RTL or mixed lines a click lands one cluster off and the caret does not move inside a ligature0236
Animated WebP and APNGOnly GIF animates; the others draw their first frame. AnimationDecoder covers both0233
LocalizationNo translation API; desktop entry Name, GenericName and Keywords are read unlocalized0112
Wayland and input extrasNo shortcut inhibition, per-surface idle inhibition, touch gestures, cross-app drag and drop, pointer buttons past left, right and middle, or a click position inside a button. logind and ScreenSaver inhibition work—
Window capturecapture takes an output. A window source would take windows ids0247, 0248
Native I/ONo HTTP, sockets, watched file contents or json.encode; JSON storage and folder watching exist. Native only for a measured latency or volume need—
KDE ConnectNo device or plugin model. A capability or a streaming helper, not unrestricted D-Bus—
Derived nested stub shapesGradient, GradientStop, Mask, Easing, Animation, Animations and Exit are still hand-written in nodes.lua’s header, since no struct holds their keys, so a parser change can leave them stale. Derive them with lua_shape! like Edges and Transition once their parsers fill one—
Dynamic topologyA reload rebuilds only what changed. Revisit only if dynamic windows need a different lifetime0216

Won’t do

ItemInsteadADR
Weather, currency or geolocation capabilitiesprocess.run with an HTTP CLI, then json.decode—
Native FFTStream Cava output into state and draw it—
Clipboard capabilityprocess.detach("wl-copy", { text }): a selection needs a process that stays alive to serve it0188
Video encodingA recorder under session_process, driven from config0175
Global input captureAn external input backend, streamed in—
Wallpaper capabilityA Background panel, an image with async/retain/transition, files for the folder, persistent_table for the choice0055
Rust widgets (sliders, calendars, launchers, settings)Lua components over existing nodes—
Framework settings schemapersistent_table with config-declared files—
Per-panel IPC commandsmantle set, toggle and call—
Deferred surface loaderWayland objects are created when shown; the 5 ms cap guards one signal resolve, not a whole evaluation0157
Shaders over a subtree or as a persistent filterimage.transition and the input-less shader node keep a stable contract. Fixed blur or shadow is content_blur and shadow_*0184, 0253, 0254
Display manager (PAM as root, sessions, seats)greetd; see Greeter—
X11 or i3The target is a Wayland session shell—