Files
komorebi/docs/usage/changing-monitors.md
T
LGUG2Z 40eec2f6be feat(wm): follow a window moved to another output
A window can be moved to another output by something other than komorebi: a KWin
shortcut that sends it to the next screen, the window menu, an application.
komorebi had it in a container of the old monitor, whose tile is on a screen the
window is not on, so it sat untiled where it landed.

The bridge now reports a window's output changing, with the frame the window has
by then, since the signal and the frame arrive in no fixed order, and the table
makes it an OutputChange event. The window manager handles it with
WindowManager::follow_windows_to_their_monitors: every container whose focused
window, and every floating window, is on another monitor than the one it has it
on moves whole to the workspace of the same number on the monitor that holds the
middle of its frame, and the monitors that changed are tiled. Every window is
looked at, not only the one in the event, and a move komorebi made itself is in
its state already and finds nothing to do.

Nothing is followed while the user drags a window: the end of the drag decides
where that window goes, so the method returns at once while a move or a resize
by the user is going on.

KWin also moves windows for a moment after outputs come and go, so the monitor
reconciliator looks again 1.5 seconds after each notification, where it used to
trust what it found at once. vm-hotplug sends windows over with kdotool as well
as with komorebic.
2026-10-28 07:20:57 -07:00

4.6 KiB

Monitors that change

komorebi follows the outputs KWin has. There is nothing to configure and no command to run: this page says what komorebi does when a monitor changes.

A monitor changes size

A monitor changes size when its resolution or its scale changes (in System Settings, under Display & Monitor, or with kscreen-doctor output.<name>.scale.1.5), and when a panel changes the room the windows have on it: a panel that starts, grows, moves or is hidden. komorebi reads the size and the work area of every monitor again, and tiles the workspace in front on the focused monitor in the area it now has.

The windows of the other monitors keep their tiles until something tiles them again. komorebic retile does it for every monitor.

KWin has no signal for the room a panel leaves, so komorebi looks at it when a panel opens, closes or moves, and once a second. A panel that is laid out a moment after komorebi starts is found within a second.

A window is moved to another monitor

A window moves to another monitor when something other than komorebi moves it: a KWin shortcut that sends the window to the next screen, the window menu, a drag with the pointer, or an application. KWin tells komorebi, which finds every container and floating window that is on another monitor than the one it has it on, and moves it to the workspace with the same number on the monitor it is on. The monitors that windows moved between are tiled again.

A window is on the monitor whose area has the middle of its frame. A container is on the monitor of the window that has the focus in it. A move komorebi made itself, with komorebic move-to-monitor for one, is in komorebi's state already, and finds nothing to do.

While the user drags a window with the pointer, komorebi moves nothing: where the window goes is decided when they let go of it (moving windows by dragging).

A monitor is unplugged

KWin takes the windows of an output that goes (it is unplugged, or disabled with kscreen-doctor output.<name>.disable) to the outputs that are left, and puts them where it likes. komorebi takes the monitor's workspaces over there: every container, and every floating window, goes to the workspace with the same number on the monitor KWin put its window on, and the workspaces that changed are tiled again. A stack goes as a stack. A monocle window and a maximized window come as tiles of their own, and the windows the monocle hid are shown again.

A moment after an output goes or comes back (1.5 seconds), komorebi looks at where every window is once more, because KWin moves windows about for a while after the outputs change: the windows it took to the monitor that is left may go back to the output that is plugged in again, and a change of resolution or scale changes where the middle of a window is.

komorebi keeps the monitor that went, with its workspaces, layouts, paddings and offsets, for when it comes back, and forgets the workspace rules of its workspaces until then. When no output is left at all, komorebi does nothing.

A monitor is plugged in

komorebi knows a monitor by the manufacturer, the model and the serial number KWin reports for the output, or by the output's name when it has no serial number. A monitor komorebi has kept comes back with what was kept: its workspaces and their settings, and the wallpaper of the monitor, less the windows that have closed or that are somewhere else now. Its windows were tiled on other monitors when it went, so it comes back with none of them. The monitor that had the focus keeps it, and every monitor shows its workspace in front.

A monitor that komorebi has not seen gets workspaces of its own, and the windows that open on it are tiled there. When komorebi.json has an entry for the monitor in display_index_preferences and the monitor was not connected when the file was read, it takes the entry when it is plugged in. The monitors are put at the index the user gave them with komorebic display-index-preference, and after the other monitors otherwise.

Following it from a program

A subscriber is sent a notification each time komorebi has dealt with a change of the monitors, whether or not anything changed in the state. Its event is {"Resize":0} for a change of size, where the number is the id of the monitor that changed, or 0 when KWin does not say which, and {"DisplayConnectionChange":0} for a monitor that was unplugged or plugged in.