Commit Graph
248 Commits
Author SHA1 Message Date
LGUG2Z 434e2bc1d8 test(nix): the ring of wallpaper is read outside the frame
A port whose test window has a color of its own put it in the ring, and
a warm ring beside a cool window read as mixed. Both ports draw the
border outside the frame, so what is inside it is not read. The fake
leaves room for the ring and follows focus-workspace. BEHAVIOUR.md says
what kfw's next has fixed or found since: the maximize, the killed
daemon, and the top edge.
2026-10-30 16:50:07 -07:00
LGUG2Z 7263151275 test(nix): a failed ring check of wallpaper prints what it saw
The frame of the window, the hue that was found and the colors of the
pixels near its left edge, so that a port whose border is not repainted
(or is drawn elsewhere) can be told from one that has no border.
2026-10-30 16:39:15 -07:00
LGUG2Z 1f0ec180ca test(nix): resize presses wait for the frames to match the layout
A frame that is still on its way to its tile is not where its border is:
a press on it lands on the window, and a drop on another tile swaps
windows. kfw saw it once in three runs of edge_cases. The press now
waits until every window is where the daemon's layout says.
2026-10-30 16:39:15 -07:00
LGUG2Z dedcab71bc test(nix): share the wallpaper scenario, and the files kfw must sync
Wallpapers and the colors of the borders that come from them are in the
config of both ports. wallpaper.run is the neutral part: a monitor's
wallpaper at start, a workspace's own while it is shown, the ring in the
hue of the wallpaper, and a changed wallpaper put back. Platform gets
put_file, wallpaper and set_wallpaper; in a Plasma session restart_with
restarts the module's unit with the user's komorebi.json. The KDE extra
keeps what only the shell tells. sync-e2e-core carries the two fakes the
shared tests import.
2026-10-30 16:18:32 -07:00
LGUG2Z a8e79ca5d2 test(nix): share the columns of the scrolling layout, and two monitors
The checks of the scrolling suite were KDE's, but kfde and komorebi for
Windows lay the strip out with the same model. scrolling.columns is the
scenario of the five windows in two columns, now run by the scrolling
suite and by core-e2e; scrolling.two_monitors checks that a strip with a
display next to it leaves no window shown on that display.
2026-10-30 16:18:32 -07:00
LGUG2Z b4edd1c023 feat(nix): the platform says where a resize border is pressed
The press point of the resize scenarios was a gap outside the frame, which
is KDE's resize zone. On Windows there is no invisible border on the top
of a window, so a press there reached the desktop. Platform.resize_grab
gives each port its own point; KDE keeps the gap outside the frame.
2026-10-30 15:50:24 -07:00
LGUG2Z b80c18a9be docs(scrolling): the scrolling suite has run, and what no VM check covers 2026-10-30 15:37:53 -07:00
LGUG2Z e8963aee21 docs(behaviour): the differences kfw has with kfde, as known 2026-10-30 15:37:53 -07:00
LGUG2Z 79b0f4dc91 test(nix): rest by cells at the left edge in the scrolling suite
foot rounds its frame to whole cells, so a window the daemon rests with
five pixels showing can end a pixel short of the screen edge. Accept a
frame whose right edge is within the platform's tolerance of it.
2026-10-30 15:34:57 -07:00
LGUG2Z 76c97fb4e1 docs(scrolling): the scrolling layout, and what changed in the design docs
docs/usage/scrolling-layout.md says how the columns work. The design docs
say what the strip is, where a window out of view rests, and that the
generated tables of COMPARE.md are to be made again.
2026-10-30 14:44:54 -07:00
LGUG2Z e42a86454c test(nix): the commands of the columns of the scrolling layout
The scrolling suite checks where a window out of view rests, which is at the
edge it left by with a few pixels on the screen, and runs pan, consume,
toggle-column-stack, expel and scrolling-layout-full-width. They are not in
the shared scenario, which komorebi for Windows runs too, and has them only
on its next branch. Not run: the VM suites are for a later run.
2026-10-30 14:44:54 -07:00
LGUG2Z 555e2e97da docs(schema): the schemas and the command help for the scrolling layout
schema.json gets center_focused_column as a boolean or one of Never, Always
and OnOverflow, the options of the module follow it, and docs/cli has the
new commands.
2026-10-30 14:44:54 -07:00
LGUG2Z db976212b1 feat(scrolling): lay out the Scrolling layout with the scrolling model
The workspace keeps a ScrollingSpace of komorebi-scrolling, keyed by the id
of each container, in place of recomputing equal columns from the last
layout. A column can hold several windows. New commands and messages:
consume, expel, toggle-column-stack, scrolling-layout-full-width,
center-focus, expand and pan. Focus, move, resize, retile and closing a
window go through the strip, and a drag of an edge keeps it with the rest
of what the drag started from.

A window that is out of view rests at the edge it left by, with 5 pixels of
it on the screen and its size unchanged, and is hidden where another
monitor is next to that edge. A window that will not get as narrow as its
column widens the column, at the first layout after the windows have had
400 ms to draw. center_focused_column is Never, Always or OnOverflow, and
still reads a boolean.
2026-10-30 14:44:54 -07:00
LGUG2Z 3f51b3a0ca build(repo): take the scrolling model from upstream's next branch
komorebi-layouts and komorebi-themes move to the revision of next that has
the platform-free half of the rework of the Scrolling layout, and
komorebi-scrolling, the model of a strip of columns, is a dependency of
komorebi at the same revision.
2026-10-30 14:44:54 -07:00
LGUG2Z b86aa6fb78 docs(scrolling): review of upstream's rework of the Scrolling layout
For each commit of master...next that touches the layout: what it changes,
whether kfde takes it, and why not where it does not.
2026-10-30 14:44:54 -07:00
LGUG2Z d205320d64 docs(repo): KDE pads every monitor to the same number of workspaces 2026-10-30 14:44:33 -07:00
LGUG2Z 6190a4ad84 fix(nix): monitors reads the workspace counts when it needs them 2026-10-30 14:44:33 -07:00
LGUG2Z a2897edd12 docs(repo): a title change does not re-evaluate a window, as in kfw 2026-10-30 14:12:26 -07:00
LGUG2Z 3830bb27e9 feat(nix): title_rule asserts what kfw does: a rule decides when a window opens 2026-10-30 14:12:15 -07:00
LGUG2Z 84080f879e fix(wm): a title change does not make the daemon look at a window again 2026-10-30 14:12:15 -07:00
LGUG2Z 4920650155 fix(nix): the shared core: neutral names, E2E_ONLY, waits and diagnostics 2026-10-30 14:07:21 -07:00
LGUG2Z 225bf22a07 fix(nix): KWin is asked for the outputs once a second, and longer timeouts 2026-10-30 14:07:21 -07:00
LGUG2Z 3ef5f8279f docs(repo): the Windows displays and the Rect naming, from kfw 2026-10-30 13:20:41 -07:00
LGUG2Z c71c8fd013 fix(nix): the monocle check and the fakes, after merging the agents 2026-10-30 12:56:48 -07:00
LGUG2Z 86cf814f92 feat(nix): a crashed daemon leaves nothing hidden, as a shared scenario
Platform.crash kills the daemon abruptly. lifecycle_hidden.crash turns a
monocle on, crashes, starts the daemon again, and checks that it manages
every window, that none is left out of sight, and that a monocle works
again. The KDE extra parking keeps the stale parking desktop checks.
2026-10-30 12:53:28 -07:00
LGUG2Z cb134e7908 feat(nix): fullscreen and the user's maximize are shared scenarios
Platform.fullscreen and Platform.user_maximize take a window fullscreen or
maximize it as the user would, without asking the daemon. The scenarios
maximizing.user and fullscreen check that the daemon takes the window out
of the layout, leaves it alone, and puts it back. The KDE extras keep the
on-top screenshot, the daemon's log and the setup.
2026-10-30 12:53:27 -07:00
LGUG2Z 595706d66f feat(nix): the drag-resize edge cases are a shared scenario
resize.edge_cases makes its drags from the daemon's layout and reads the
frames from the operating system: both sides of a shared edge, a horizontal
edge, a corner and an edge of the screen, with a neighbour or without. The
KDE extra keeps pointer_is_exact.
2026-10-30 12:53:13 -07:00
LGUG2Z 4db3f97e2e feat(nix): the display_change scenario, and resizable_display
A display whose mode changes: the daemon's monitor follows, the windows
stay on a display and apart, and changed back they are where they were.
Platform.resizable_display says which display can change its mode, or None
and the scenario is skipped; KDE says None, as the virtual outputs of the
headless KWin have one mode. Platform.resize_display changes the mode.
2026-10-30 12:53:13 -07:00
LGUG2Z 3beb1b82d9 feat(nix): a window the user moves to another display is a shared scenario
hotplug.user_move moves a window with Platform.move_window to the second
display and checks that the daemon has it on that monitor and every window
is tiled on its display. The KDE suite runs it before the unplug and after
the replug, and the extra sent_by_the_user is gone.
2026-10-30 12:52:51 -07:00
LGUG2Z d14ce4d2e7 feat(nix): monocle focus behaviour is a shared scenario
monocle.focus_behaviour checks that with no-op the window keeps the work
area when the focus is moved in a direction, and with cycle another window
gets it. The KDE extra monocle_focus_behaviour is gone.
2026-10-30 12:52:22 -07:00
LGUG2Z 19c71eef9e feat(nix): named workspace rules and cleared rules are in the shared scenario
The shared rules scenario sends a window by the name of a workspace, checks
that a rule that is not initial is applied again when a window opens, and
that the daemon's global state has no rule after clear-all-workspace-rules.
The KDE extras keep the desktop numbers.
2026-10-30 12:52:21 -07:00
LGUG2Z f2a5c234e1 feat(nix): placement by the class of a window is a shared case
The shared placement scenario opens a window with a class and a rule that
puts the windows of that class first. The KDE extra by_app_id is gone;
by_program (foot.exe) stays.
2026-10-30 12:52:21 -07:00
LGUG2Z fec9b1e3da feat(nix): the query scenario is shared and asserts values
Each komorebic query is compared with the daemon's state, before and after
a change of focus and layout, and a resize that was saved is undone by
loading it, with quick-save-resize and with save-resize. Platform gets
temp_path for the file of save-resize.
2026-10-30 12:52:20 -07:00
LGUG2Z dc710ce419 feat(nix): every layout is tried with three, two and one windows
commands.layouts and layouts.run close windows from the end and open them
again with their own titles. The KDE extra layouts_by_count keeps only what
reads the daemon's log: KWin has each window where the daemon last asked.
2026-10-30 12:52:20 -07:00
LGUG2Z 7d32b02ec8 feat(nix): the handover scenario is shared
minimize, unmanage and manage on the focused window now run through the
neutral platform. The check that the unmanaged window is centered is
neutral: inside the work area and not on a tile of the layout.
2026-10-30 12:52:20 -07:00
LGUG2Z 8b64b3373a feat(nix): the title rule scenario is shared, and a window can rename itself
Platform.spawn takes rename_to and after: the window gives itself another
title after some seconds (a terminal escape on KDE). The scenario ignores a
title, and checks that the window is left alone while it has it, and tiled
once it has another.
2026-10-30 12:51:41 -07:00
LGUG2Z 26b4ff931b docs(repo): the ledger and the scenario table for monitors and layout_flip
Both are new shared scenarios and have not been run on a real KWin or Windows
guest yet, so their columns say so.
2026-10-30 12:51:06 -07:00
LGUG2Z b8be236f98 feat(nix): the layout_flip scenario, shared by both ports
Starts the daemon with the layout_flip option of a workspace set to each value
it takes, over columns, rows and BSP with two and three windows. Checks the
mirror from the OS, that flip-layout turns the option off and on, that a command
adds the other axis, and that the option is the named workspace's own.

core-e2e runs it after startup_rules.
2026-10-30 12:51:06 -07:00
LGUG2Z 3711f235d7 feat(nix): the monitors scenario, shared by both ports
Checks from the OS and the daemon's state what send-to-monitor, move-to-monitor,
their cycle, workspace and named forms, focus-monitor, cycle-monitor,
focus-monitor-workspace and cycle-move-workspace-to-monitor do: the window on
the monitor and workspace asked for, tiled in that display, the others where
they were, and the focus where each command leaves it. focus-monitor-at-cursor
is its own function, for a platform with a pointer.

core-e2e starts KWin with two outputs and unplugs the second before the daemon,
so the other scenarios still see one display. The fake desk (two displays of
different sizes) and its tests are new files.
2026-10-30 12:51:06 -07:00
LGUG2Z 1b655251dd docs(repo): the contract of each Platform member, and the quirks
The audit behind the docstrings of Platform: what each member promises
to both ports, what each port answers for another reason, what each
finding of the review turned out to be, and what is left to run on a
KDE VM and on Windows.
2026-10-30 12:51:01 -07:00
LGUG2Z 40eba4aade fix(nix): KdePlatform meets the contract Windows already does
spawn raised nowhere on KDE when the window never came, so a check
that a window stays unmanaged passed for a window that was not there.
It does raise now, as do close, minimize, activate and move_window for
a window that does not exist, and a program name Windows rejects. A
title is looked for as it is and not as a pattern. displays() is what
KWin says of each output and not the size the session was given
(Kde.screens, the same script that gives the work area).

The docstrings of Platform say what each member promises and what a
scenario may not lean on.
2026-10-30 12:51:01 -07:00
LGUG2Z 5c4621ae44 fix(nix): shared scenarios take their pixels and waits from the platform
The quiet period of three seconds was written in nine places, each
a number. It is support.QUIET. The window the lock scenario moves is
a third into the work area, not at 400,300, and the scenario now
checks that it moved, or the check that it is back in its tile after
the unlock proves nothing. The room the padding must change by, the
pointer drag and the tile hotplug checks after an unplug come from
the work area.
2026-10-30 12:51:01 -07:00
LGUG2Z 1c701333ad fix(nix): focus_follows_mouse names no implementation and no compositor
The scenario toggled with --implementation windows on both ports, and
its settle time said it was KWin's 200 ms. The default of the command
is each port's own implementation, so the flag goes, and the settle is
a named wait that is longer than what either port needs.
2026-10-30 12:51:01 -07:00
LGUG2Z f012abf6ba fix(nix): a window that is gone is not in view, and what hidden means
Platform.hidden is false for a window the system does not have, so the
workspace scenarios that counted the windows that are not hidden took
a window that was lost for one that was shown. They count the windows
the system has (support.in_view). The docstring says what each port
answers true for beyond a window the daemon put away, and that a
scenario that asks for one to be put away asks the daemon too.
2026-10-30 12:51:01 -07:00
LGUG2Z 5f33e11fa5 fix(nix): resize_commands asks the layout for the change, not a frame
The decrease was checked against the frame within Platform.tolerance,
which is 24 px for a terminal: a daemon that gave back less than the
increase passed. The daemon's layout, which no client rounds, now has
to show the width asked for, and the frame has to follow within the
tolerance. Platform.tolerance says what it is and is not a bound on.
2026-10-30 12:51:01 -07:00
LGUG2Z 9c9639949c fix(nix): KdePlatform.work_area asks KWin for the area less the panels
The headless suites have no panel, so the whole output was right there,
but a session with one got a work area that scenarios could not hold a
window to. KWin's placement area of the first output is asked through a
script, with the whole output as the answer where KWin does not say.

The contract of Platform.work_area is spelled out: the display less what
the system keeps for itself, as the system says. Monocle and maximize
check that the window stays inside it. The fake platform takes a panel,
and a daemon that tiles under it.
2026-10-30 12:51:01 -07:00
LGUG2Z 720daea382 docs(repo): kfw confirms the four fixes on next 2026-10-30 12:48:13 -07:00
LGUG2Z 4c5606f235 docs(repo): the four upstream fixes, and what each means for kfde 2026-10-30 12:34:23 -07:00
LGUG2Z 50160477e6 feat(nix): core-e2e runs the new scenarios, and unknown_monitor without a marker 2026-10-30 12:29:02 -07:00
LGUG2Z 6748528b90 feat(nix): the manage_rules and state_fidelity scenarios 2026-10-30 12:29:02 -07:00