Watch
1
0
Fork
You've already forked souveraine
0
Commit graph souveraine/surfaces/quickshell/modules/ii
Author SHA1 Message Date
Fimeg
a5f0fadba8 unlocking closes a keyboard nobody asked for 2026-08-05 21:55:11 -04:00
Fimeg
bb81781007 the backdrop is the input region, so it owes the way out 2026-08-05 20:10:40 -04:00
Fimeg
1ac33afb25 dock is home's alone; the pill stops riding above it 2026-08-05 20:04:45 -04:00
Fimeg
d7965a57fd two swipes, one progress; home is zone 0; pocket is a belief 2026-08-05 19:16:41 -04:00
Fimeg
277a0d2b32 dock lives on zone one; short swipe multitasks, big swipe goes home 2026-08-05 16:17:47 -04:00
Fimeg
bf8bc013ef three-finger tap opens a window sheet, not the overview 2026-08-05 14:12:22 -04:00
Fimeg
3aea8398a9 shell: intent wins the settle window, and a swap is a request for a keyboard
Two gaps in the owner-change handling, both found on device.

The push at adopt time can lose a race. osk-switch sleeps 0.3s before
its deliberate SetVisible(true), and stevia self-shows once it has
finished coming up - both land after the shell has spoken. Measured:
adopt+hide 07:37:51, Visible=true 07:37:52, leaving oskOpen=false with a
keyboard on the screen. Re-assert when the settle window closes so the
last speaker is not the winner.

And the oskSwap gesture never recorded that a swap means the user wants
a keyboard, so osk-switch's re-show and the shell's stale false were
racing with nothing to arbitrate them. Declare the intent first.
2026-08-05 07:41:02 -04:00
Fimeg
d7a04f27d5 shell: an owner change is not a visibility event
sm.puri.OSK0 is a name, not a process. Boot, a crash-restart and an
osk-switch swap each put a fresh keyboard behind it, and the visibility
monitor mirrored the newcomer's opening claim into oskOpen as though the
user had asked for a keyboard. Measured: shell up 03:03:38, self-showed
at 03:03:43, nobody near the phone.

Track the bus owner - gdbus already prints it and the 'Visible' filter
was throwing it away - and on a change push oskOpen at the new owner
instead of pulling state out of it. A process that just started has no
history; the shell is the continuity of intent across the keyboard's
lifetime.
2026-08-05 07:34:53 -04:00
Fimeg
f320a0221d shell: answer to the ipc target sessiond actually calls
Action::Overview shells out to `ipc call overview toggle`. The only handler
here was `search`, so that call reached nothing and the three-finger tap
did nothing, without an error anyone would see.

It has been invisible from the device because the shipped sessiond has no
`gesture` verb yet and refuses the op long before the executor runs, so
only the first half of the break was observable.

This makes the existing binding reach the surface it already names. What
the tap should raise is TASK-55 Q1 and is not decided here.
2026-08-04 15:02:34 -04:00
Fimeg
44a54330c2 shell: mission control draws the cards it was already building
The panel, its mask and the loader all moved to overviewOpen ||
missionControlOpen when mission control landed; the Column holding them
did not. So the second-stage pill swipe raised a panel whose entire
contents were invisible — WindowOverview instantiated, laid out, and never
shown.

Search stays overview-only: mission control takes no keyboard focus on
purpose, so a field there is one you can see and cannot use. Outside-tap
now clears both states, because with no focus grab that tap is mission
control's only way back.
2026-08-04 14:43:35 -04:00
Fimeg
cc4bb83573 shell: the overview arrives as one surface, and mission control finally lands
Everything drove off a visible/not-visible flag, so the cards appeared
rather than the overview opening. One shared `progress` now: the strip
slides 24px, each card takes its own share of it staggered by index and
capped at the fifth, and scale runs 0.86 to 1.0 — the reference shell's
numbers, driven from the same clock instead of a timer per card. The cap
is what stops the tenth card starting half a second after the first,
which reads as loading rather than opening.

This is also SHELL-ECOSYSTEM's stated model, taken from Phosh: state
gates visibility, never the reverse.

`missionControlOpen` has been set by the pill's second-stage swipe since
July and consumed by NOTHING — TASK-14 records the Auxo-like card
surface it was meant to raise as never built. WindowOverview is that
surface. The state reaches something now instead of being set and
dropped.

Mission control is the cards alone: no search, and no keyboard focus,
because it is "switch to what is running" and not "find something" — and
taking the keyboard would summon the OSK over a surface with no field.
2026-08-03 22:18:43 -04:00
Fimeg
fdb0acfdce shell: the overview shows windows, because there are no workspaces here
OverviewWidget draws a grid of workspaces and places windows in them by
Hyprland coordinates — HyprlandData.windowList, monitorData,
Hyprland.monitorFor. Under viewtop none of it resolves, and more to the
point viewtop has no workspaces at all: one space, a tiling layout. The
old overview could not be repaired by repointing it at another data
source, because the thing it draws does not exist. It rendered an empty
frame, which reads as the overview being broken.

WindowOverview lists what does exist. Cards from
ToplevelManager.toplevels — the same list the dock and TaskbarApps
already read, so there is one idea of what is open — each holding a
live ScreencopyView of one window, which only became possible when the
compositor started serving a per-window capture source; until then a
card could have shown nothing but the screen it was covering.

The motion is the reference shell's, read out of
overview_window_card.dart rather than invented: stagger at index * 45 ms
capped at the fifth card, intro scale 0.86 to 1.0, dismiss past 32% of
the card height, 56 px of downward rubber-banding, settle under 200 ms.
The cap is the part worth keeping — without it the tenth card starts
half a second after the first and the overview feels like it is loading
rather than opening.

Captures run only while the overview is up. A live capture per window is
a render of that window every frame, and leaving them going behind a
closed overview is battery spent drawing what nobody can see.
2026-08-03 18:37:56 -04:00
Fimeg
c21bd1d7d9 shell: stop gating the dock on a flag the keyboard flaps
Suppressing the dock whenever oskOpen was true, above effectivePinned so
it applied in every state, hid the dock permanently on the device.

oskOpen is not "the keyboard is on screen". GlobalStates' own comment
says squeekboard hides itself whenever input-method focus drops and that
a hold re-asserts it, and the journal shows exactly that: self-showed /
self-hid every couple of seconds, settling at Visible=true with no
keyboard in front of the user. Gating a persistent surface on a flag
that flaps turns a cosmetic overlap into a dock nobody can reach.

The empty-desktop check keeps its oskOpen term, where it always was: a
spuriously-true flag there costs a reveal that was cosmetic anyway,
which is a different price from hiding a pinned dock.

The real signal is the keyboard's exclusive zone, which the compositor
already applies — an unpinned dock declares zone 0 and is placed above
the keyboard for free, the same mechanism that fixed the pill. The
pinned case, where both reserve space and the reservations stack, wants
fixing where the zones are arbitrated.
2026-08-03 17:17:01 -04:00
Fimeg
ca44b0be2a shell: the keyboard owns the bottom edge, and nothing measures it
Two bugs with one cause — the bottom edge was being reasoned about
twice, by hand, against a compositor that is gone.

The rail set ExclusionMode.Ignore (exclusive zone -1: ignore what
everyone else reserved, anchor to the whole screen) and then computed
its own lift from the keyboard's height, probed by shelling out to
`hyprctl -j layers`. Under viewtop there is no hyprctl, so every probe
threw a JSON.parse on empty output and logged it in a loop every second
or two, forever, while the margin stayed at a hardcoded fallback
measured against a keyboard that is not the one running. A 200px
fallback against some other height is exactly "the pill spawns in the
middle of the keyboard". Zone 0 with Normal — the idiom SidebarRight and
ReloadPopup already use — reserves nothing and respects what others
reserved, so the compositor anchors the rail to the top of the
keyboard's exclusive zone. Correct at any height, any rotation, across a
swap, with nothing to go stale. The probe, its retry timer and
probeOskHeight() are deleted rather than ported: a second measurement of
a number the protocol already carries is what this class of bug is made
of.

The dock consulted oskOpen only in its empty-desktop branch, below
effectivePinned, so a PINNED dock ignored the keyboard and sat under it.
DockManifest.dockState() has always reported "suppressed-by-osk" and
_blockReason() has always refused mutations with "osk-open" — the
manifest promised a suppression the dock never performed, so the agent's
view of the screen and the screen disagreed. The check moves above
pinning and applies in every state, staying below dockRevealPulse
because an explicit reveal is the one thing that should outrank the
keyboard.

Verified on the phone: the probe loop is gone from the journal. The
resulting pill and dock positions want eyes on the glass.
2026-08-03 16:53:06 -04:00
Fimeg
5c618f1514 lock: hoist the lock out of the Config.ready loaders so a reload can adopt
PanelLoader is a LazyLoader gated on Config.ready, behind a second one.
On reload both are shut when quickshell propagates, so LazyLoader has no
item to hand its successor and the new WlSessionLock never adopts the live
compositor lock. Lock is a direct child of ShellRoot now, as the boot-order
doc already asked.

Ungated means Config may not have loaded, and touchKeypad reads false from
the adapter defaults — which would bind the desktop surface on the phone and
cannot be changed once the lock is active. The choice rides the reload too.
2026-07-31 21:25:05 -04:00
Fimeg
49635fb005 shell: give the subconscious event log a host
Tier 2 was written, deployed and mounted by nothing — its own header named the
gap. The chat sidebar hosts it now: ticker long-press, or the psychology
indicator by the input box, which works when no pass is running.
2026-07-31 12:51:17 -04:00
Fimeg
483902a40e shell: restore the subconscious ticker to the chat column
Re-mount SubconsciousTicker in AiChat (lost in the 07-30 relocation out
of the ii tree). The view is decoupled; it just needed its host back.
2026-07-30 15:17:55 -04:00
Fimeg
25898a9d14 shell: re-home the subconscious surface from the ii tree to souveraine
The subconscious three-tier surface (SubconsciousTicker + SubconsciousEventPanel)
is Souveraine-original, not upstream ii. It lived under ii-base/modules/ii only
because it had never been re-homed, so the ii -> souveraine shell migration
silently stranded it: the files survived, but the running shell (qs -c souveraine)
never loaded them, and the feature dropped off the device.

Relocated into modules/souveraine/subconscious/, decoupled from the ii overlay
system it was riveted to:

- SubconsciousTicker: was clean of ii imports but opened the panel through the
  ii OverlayContext singleton. Now emits requestOpenPanel(); a host connects it.
- SubconsciousEventPanel: was a StyledOverlayWidget (qs.modules.ii.overlay). Now
  plain content a host instantiates; the pin/close/drag affordances were the
  overlay host's job, not the content's.

The model (services/Ai.qml) was already substrate-neutral and never moved; only
the views were stranded. GAP NAMED: no souveraine overlay host mounts these yet,
so they do not reach the glass until one exists — the ii overlay host was
intentionally not ported. The dangling ii references (AiChat, OverlayContext,
OverlayWidgetDelegateChooser) are removed.
2026-07-30 12:57:19 -04:00
Fimeg
0ef239515f surface: per-agent TTS voice + turn clock + reply-handler fix
Speech resolves voice per active agent (agents[].voice_id from the list),
with the system voice as fallback — two agents on a host need not match.
Souveraine.qml carries voice_id into the agents map and adds a turn clock
(turnStartedAt/turnElapsedMs) + a 60s agent-inventory refresh. Ai.qml
declares pendingFilePath and imports qs.modules.common.functions so
StringUtils.ttsClean no longer aborts the stream-finished handler.
2026-07-30 09:18:56 -04:00
Fimeg
5965c64781 shell: recover the phone-only edits into the repo
~/souveraine-surfaces/quickshell on the phone is not a git repo and was the
only copy of five files. Brought back verbatim:

- Gestures.qml, SystemGestureRail.qml: TASK-38 osk-swap detent (DUMP §5, §6)
- OnScreenKeyboard.qml: showOsk asks the bus instead of pgrep+sleep 1
- DockAppButton.qml, DockStack.qml: suffix-tolerant AppSearch.resolveEntry

resolveEntry itself had been added to the phone's live ~/.config/quickshell/ii
tree, which deploy.sh rsyncs from ii-base — the next deploy would have deleted
it and left the two dock callers referring to nothing. It lands in ii-base here.
2026-07-29 08:27:27 -04:00
Fimeg
7475fae505 osk: polkit holds the keyboard open instead of poking it once
squeekboard hides itself when input-method focus drops, so the password
field was left with no keyboard. A hold re-asserts through that and
releases on dismiss; a manual close drops the hold.
2026-07-26 16:56:34 -04:00
Fimeg
19fe6b1d0e shell: dock reorder, fullscreen detection fix, idle-power, sessiond, misc shell work
- Dock drag-to-reorder for pinned apps (insertion gap, quick-slide vs dwell)
- Fullscreen detection: scan all windows via HyprlandData.windowList
- IdleCoordinator, GlobalStates, Session.qml updates
- Deploy script, qmldir, settings, wallpaper, visualizer fixes
- sessiond server, memory module updates

Co-Authored-By: Claude <noreply@anthropic.com>
2026-07-22 22:18:20 -04:00
Fimeg
9ccefd6c73 dock: fix fullscreen detection — scan all windows, not just active/focused
Previous fullscreen detection had two blind spots:
1. Workspace scan used wayland?.fullscreen (unreliable) and missed qs -p windows
2. HyprlandData.activeWindow fallback only saw the focused window — missed
   fullscreen apps that lost focus to layer-shell surfaces (dock, notifications)

Now scans HyprlandData.windowList (hyprctl clients -j) for any window with
fullscreen === 2 on the focused monitor. Source of truth for all windows,
not just the active one. Reactive via HyprlandData's event-driven updates.

Co-Authored-By: Claude <noreply@anthropic.com>
2026-07-22 21:25:08 -04:00
Fimeg
132d8134f2 dock: add drag-to-reorder for pinned apps alongside existing combine-into-stack
Dragging a pinned app now shows an insertion gap indicator when hovering
over other pinned apps. Quick horizontal slide + release = reorder the
pinned apps array. Dwell (500ms) on a target still = combine into stack
(existing behavior). Both gestures share the same drag start and ghost.

TaskbarApps: reorderPinned() splice-moves within Config.options.dock.pinnedApps.
DockApps: shared dragSourceIndex/dragInsertIndex state, delegate passes
  parent.index as modelIndex to DockAppButton.
DockAppButton: insertion indicator (2px primary-color line), DropArea
  onEntered computes gap position based on drag direction, release handler
  commits reorder when no dwell fired.

Co-Authored-By: Claude <noreply@anthropic.com>
2026-07-22 21:11:19 -04:00
Fimeg
b0a1304ba1 quickshell: pin shared ii base and phone overlay 2026-07-21 18:55:02 -04:00
Fimeg
0d06cbb983 quickshell: dock fullscreen fallback via HyprlandData IPC, wallpaper folder browsing 2026-07-21 15:52:32 -04:00
Fimeg
db6d732e32 shell: regenerate qmldir manifests from the composed tree
The repo qmldirs listed only repo-owned types; composed dirs also carry
ii-borrowed types (ReloadPopup, PanelLoader, Bar, ...) which a qmldir
present in the dir must list or they stop resolving — broke the phone
shell on deploy. Regenerated every deployed qmldir from the composed
config on-device (capitalized .qml -> type line, pragma Singleton ->
singleton line) and pulled back. Shell verified active, zero load
errors.
2026-07-21 13:36:39 -04:00
Fimeg
acc1161e71 shell: Speech service + sidebar Speak button (Read Aloud seam)
Speech.qml singleton: speak(text) reads the who->voice mapping live
from souveraine /v1/config (VoiceConfig tts_url + voice_id), POSTs
VibeVoice /audio/speech ({input, voice, model} -> mp3, same contract
as core/voice/client.rs) and plays via mpv/ffplay. The shell picks no
voice of its own. speech.tts.enable is the kill switch (button hidden
when off); speech.tts.endpoint overrides the mapped URL. Sidebar gains
a volume_up/stop toggle beside send that reads the last visible
assistant reply, skipping lock-redacted content.
2026-07-21 13:28:47 -04:00
Fimeg
271e4f2cc2 shell: add missing qmldir manifests + rail OSK layer fix
19 dirs had .qml but no qmldir -> quickshell config load failed
(File not found @ shell.qml[-1:-1]). Corrected singleton decls in
3 existing qmldir. SystemGestureRail: pill->WlrLayer.Top, oskLift
200, drop oskOpen hide.
2026-07-21 13:01:58 -04:00
Fimeg
5083954c38 lock: own backdrop with wallpaper option, am/pm clock
The session-lock surface was transparent with nothing painting behind it.
TouchLockSurface now owns its backdrop: lock.wallpaperPath when pinned,
else the system wallpaper, else a dark field — plus a scrim for glance
legibility. Glance clock gains lock.twelveHourClock (default on, h:mm ap).
LockConfig grows the wallpaper picker (same FolderListModel grid as the
wallpaper page, no matugen side effects) and the 12-hour switch.
2026-07-20 22:47:11 -04:00
Fimeg
3837698c8b osk: mirror squeekboard's real Visible back into oskOpen
squeekboard auto-shows/hides itself on input-method focus without
telling the shell; the stale flag left the dock suppressed and the rail
floating at keyboard height. gdbus monitor on its Visible property is
the single truth now.
2026-07-19 22:46:09 -04:00
Fimeg
47858d5b06 phone: wallpaper picker settings page, drag-follow PIN reveal
Wallpaper grid in the settings app applying through the shell's
wallpapers IPC. Lock pad now tracks the finger during the swipe and
settles on release instead of snapping at a threshold.
2026-07-19 22:46:01 -04:00
Fimeg
5cb1be06cd lock primitives: power-from-lock, login1 polkit rule, gesture rail progress
seat0-active polkit rule so power off/reboot/suspend stop returning
challenge into a session with no polkit agent on the lock surface.
Lock-surface buttons stay gated behind allowPowerFromLock (opt-in) and
requirePasswordToPower. SystemGestureRail progressive gesture + mission
control nav flag.
2026-07-19 22:13:08 -04:00
Fimeg
dfd494c5f1 quickshell: complete native PulseAudio source support 2026-07-18 15:05:17 -04:00
Fimeg
401a6609ea lock: glance-first touch surface, keypad behind swipe-to-unlock
PIN pad hidden until swipe up / tap hint / hardware key; retreats after
25s idle with nothing typed. shouldReFocus no longer implies reveal --
hypridle fires it on every wake and wake must land on glance.
2026-07-17 06:46:49 -04:00
Fimeg
c96f95b9da quickshell: fix drag-to-combine, rail rides the keyboard, overview gap-tap dismiss
The drag ghost was anchored (centerIn) — Qt won't move an anchored
drag.target, so no DropArea ever fired and stack creation died silently;
position it on press instead. Drag lifecycle now sets dockDragInProgress
(the DockManifest guard finally has a writer). Restored pulseDockReveal,
lost in a refactor while its osk.pulseDock caller survived.

Rail lifts atop squeekboard by measured layer height (hyprctl -j layers,
namespace osk); swipe down dismisses the keyboard first, then a visible
dock in any state (new dockSuppressed, cleared by swipe up). Overview:
taps in the grid's dead space dismiss it instead of being eaten.
DockConfig grew the real pins/stacks editor (unpin, rename, unstack,
dissolve).
2026-07-16 12:04:08 -04:00
Fimeg
72b01457d2 quickshell: restore ii-stock config keys the fork dropped
Config.qml regained sidebar.width/widthExtended (their absence collapsed
the right sidebar PanelWindow to 1px — 'unclickable' on the laptop), plus
lock.dpmsTimeout, lock.unlockHook, and autoIdleInhibit with its Idle.qml
property. Audio.qml's absent capture source is now a zero-volume stub so
stock consumers stop dereferencing null, and the pactl status parse runs
under LC_ALL=C. volumeMixer dialog content comes along for the sidebar.
Findings logged in SouveraineOS/docs/DUMP-power-idle-lock-2026-07-15.md.
2026-07-16 08:06:11 -04:00
Fimeg
e31c3aaf62 quickshell: first-party lock/nav/session layer, retire the pill
Grows Souveraine's own surfaces on top of the borrowed ii shell and drops
the separate pill shell in favor of one integrated navigation rail.

Session arbiter (functions/Session.qml): probe logind's Can* methods over
busctl instead of guessing from installed binaries -- the answer carries the
polkit tier (yes/challenge/na), so a swapless phone reports hibernate as na
and refuses honestly rather than firing a verb that no-ops. Verbs run through
a Process that logs exit codes and tracks lastAction; refusals log too. The
busctl output is parsed with awk, not a sed regex buried under four escaping
layers -- the sed version returned nothing on the phone and left every
capability stuck at "unknown" (invisible on the laptop, where timing masked
it). Every structured result is JSON-over-string; quickshell maps a var
return to void.

Lock trust: screenLocked (the shell's lock request) is now distinct from
screenLockSecure (WlSessionLock.secure, the compositor's acknowledgement,
mirrored from LockScreen). Cards that disclose personal data gate on secure,
not on a button press. LockContentPolicy centralizes the ambient/personal/
step-up tiers so no card grows its own private rule.

New first-party namespace modules/souveraine/: LockMediaCard, LockSurfaceHost,
SystemGestureRail -- owned surfaces, not ii patches. IdleCoordinator gives one
staged idle vocabulary (dim/lock) gated behind nativeCoordinatorEnabled, off
until the native Wayland idle-notify is verified on the Pixel compositor;
hypridle stays the adapter. WallpaperAssets selects aspect-aware variants for
phone-vs-laptop display shapes.

Pill retired: pill/shell.qml and PillConfig gone, replaced by NavigationConfig
and the gesture rail. Hyprland starts qs -c souveraine directly; no secondary
shell, no qsConfig flip.

Verified on the phone: session.* reports challenge/na correctly, hibernate
and unlock refuse, inhibit round-trips with its reason.
2026-07-14 20:00:57 -04:00
Fimeg
cecde3bac2 quickshell: session arbiter + fix IPC returns silently dropping payloads
Fork ii's Session singleton and add a sessionctl.* surface.

The IPC bug is the important half. Quickshell marshals exactly five types
(string/int/bool/double/color) and maps a `var` return to VOID, discarding
the payload with no error -- src/io/ipc.cpp, "void and var get mixed by qml
engine". dock.*, shell.* and apps.* were all declared `: var`, so they
registered as `(): void` and returned nothing at all. The {ok, reason}
contract has never once reached a caller. All of them now return JSON as a
string, which is what actually crosses the socket.

Session: upstream fires `systemctl X || loginctl X` detached and throws the
exit code away. Fine on a desktop with someone at the keyboard, not fine on
a phone where the shell is the session manager and a verb that silently does
nothing leaves you believing the machine is suspending when it isn't. So:
probe loginctl/systemctl/hibernate once instead of assuming, run verbs
through a Process that logs the exit code, and refuse honestly when the
machine can't do the thing (the phone has no swap -- hibernate now says so
instead of no-opping). Every upstream verb keeps its name and call sites.

Inhibits carry a mandatory reason and get a cookie; state() lists who is
holding the machine awake and why. "Why didn't it sleep" is now answerable.
unlock() is refused by design -- the lock is the credential gate, so no IPC
caller routes around the PIN pad.

Named sessionctl, not session: ii's SessionScreen already owns "session",
and quickshell drops duplicate targets silently rather than erroring.

Idle: drop the 2>/dev/null and run hypridle through a Process, so a unit
that fails to come back is a log line instead of a flat battery.

Verified on the laptop: inhibit stops hypridle, uninhibit brings it back.
2026-07-14 18:31:59 -04:00
Fimeg
c78c5510af quickshell: run as qs -c souveraine + dock/shell/apps method surfaces
Own config name composed by deploy.sh from our files + pristine-ii dir
borrows; ii tree stays untouched. One SouveraineFamily, two modes gated
on souveraine.phone.

Three guarded IPC surfaces for the agent (via Souveraine's harness, not
a new integration): dock.manifest/pin/unpin/restack, shell.surfaces/state
(layer registry, live-derived), apps.list/get/find/categories (.desktop
scan). Refusals are result shapes, not errors.

Settings app split into per-domain pages (Device/Lock/Dock/Pill/Keyboard).
Config backports (background.widgets, claudeUsage, fileSearch) kill the
laptop TypeErrors.
2026-07-14 15:03:07 -04:00
Fimeg
72f5169458 quickshell: touch PIN lock screen for the phone
The OSK is layershell and can't rise above a session lock, so the lock
surface carries its own keypad. Lock state persists to states.json so a
qs crash while locked comes back locked; with lock.launchOnStartup the
lock screen is the greeter (greetd autologins straight into Hyprland).
Keypad gated behind lock.touchKeypad so desktop deploys keep the stock
surface.
2026-07-13 15:19:59 -04:00
Fimeg
6e21c50dcc quickshell: resume agent conversations from server 2026-07-12 16:31:55 -04:00
Fimeg
ec7c4e8e8c quickshell: dock geometry/icon-centering, GlobalStates, ConflictKiller service
Dock + pill z-order and icon centering pass; GlobalStates.qml and a
ConflictKiller service for the ii sidebar.
2026-07-12 14:56:56 -04:00
Fimeg
0a8e0f7294 dock/pill: fix icon centering, pill z-order, app-mode fullscreen
- dock icons center in the bar (DockApps top-margin was shoving the row
  down; DockAppButton block now reserves half the dot strip)
- pill double-tap fullscreens the real app: routes through dock IPC
  fullscreen() targeting Hyprland.activeToplevel.address, mode 0, so the
  pill tap focusing the shell no longer redirects it
- pill must be re-created after the dock or it sits under it and drops
  touch (both on Overlay; z-order = creation order)
- HOW-IT-WORKS.md: the concise contract for pill/dock/fullscreen
2026-07-12 13:07:02 -04:00
Fimeg
693df8b55b dock: revert thin-bar geometry; keep icons inset to land inside the bar 2026-07-12 11:30:51 -04:00
Fimeg
0beeb80357 dock: align icon row inside the visible rectangle (match its insets) 2026-07-12 11:13:24 -04:00
Fimeg
0e1f233857 dock: visible on empty desktop / hidden for focused apps; lift dock above pill strip 2026-07-12 11:09:28 -04:00
Fimeg
ccb51820e5 dock/pill: reserve pill strip (dock floats above), pill swipe-up = dock gesture not home/keyboard 2026-07-12 10:48:11 -04:00
Fimeg
57031bbf4f dock: drop the dead pin toggle button 2026-07-12 10:43:19 -04:00
Fimeg
b8b65273a1 dock: unmount layer when hidden so it stops painting over fullscreen apps 2026-07-12 10:41:50 -04:00