cow - Man Page
Compositor On Wayland
Synopsis
Description
cow is a window manager using River as the compositor.
A large virtual desktop can be created, effectively splitting the screen into an N x M matrix, called pages. These pages can then be viewed by using the mouse on the edge of the screen, or by using the scroll command.
Desktops provide a means of aggregating open applications into different areas.
cow provides commands which can be used to change settings, setup key/mouse bindings, etc.
Options
- -c config
Load the configuration from config instead of searching the default locations.
- -h
Print usage and exit.
- -v
Print version and exit.
Output Management
Neither cow nor River manages outputs (screens/monitors) directly. Instead, applications such as wlr-randr(1), and wdisplays (for something similar to xrandr) can be used instead.
Because cow needs to know information about outputs after it has started, it is recommended that the dedicated file ~/.config/cow/after-start.sh -- which is a shell-script, contains the relevant commands to set the output layout.
NOTE: in this example, it is assumed that $XDG_CONFIG_HOME is set to ~/.config.
cow will assign all outputs a number to a tree with a defined order. That order is top-down, left-to-right, so far example, the following diagram illustrates output configuration and their assigned number:
out1 (0) out2 (1) out3 (2) out4 (3)
Anatomy of a Window
cow puts a decorative border around windows. This border consists of a bar on each side, and a small L-shaped section on each corner. There is an additional top bar called the titlebar which is used to display the name of the window.
In addition, there are three titlebar buttons which can be defined and bound to actions, such as closing a window, maximizing, or iconifying a window.
The diagram below shows an outline of a typical window in cow:
NW N NE
+++──────────────────────────────────────────────────────────+++
+ [L] Titlebar [R][R2] +
+──────────────────────────────────────────────────────────────+
│ │
│ │
│ │
W │ │ E
│ │
│ │
│ │
│ │
+ +
+++──────────────────────────────────────────────────────────+++
SW S SEThe labels of the window indicate the different components that can be changed.
A window is made up of sides -- and are referenced like that of a compass.
All eight parts of the window border (which includes corners) can be styled via the set command,
The titlebar can also be styled or disabled completely, via the set command.
The Virtual Desktop
cow provides up to ten virtual desktops. The screen is a viewport onto a desktop which may be larger than the screen. Several distinct desktops can be accessed (for example, having different desktops for different projects).
Because the desktop can be larger than the physical screen, it can therefore be divided into N x M regions, called pages. This configuration is then applied to all desktops.
For example, the following would define nine pages, arranged in a square:
set desktop_size 3 3
Which would conceptually look like this:
+----+----+----+ | | | | | | | | +----+----+----* | | | | | | | | +----+----+----+ | | | | | | | | +----+----+----+
All pages are the same size.
Pages can be moved to/from by enabling edge_scroll by resting the mouse pointer at the screen edges. See the set command.
Windows on pages can be be viewed using the cowpager(1) command.
Windows can also be moved between pages by dragging them to the edge of the output, assuming edge_scroll has been enabled. See the set command.
cow keeps its windows in a Z-ordered stacking order. That is to say, windows can be raised or lowered over one another. This can be controlled via the winops command.
Layers
Every window belongs to a numbered layer. The layer range is [0, max_layer] (default 16) and newly mapped windows receive default_layer (default 4).
A window in layer 8 is always above every window in layer 4 regardless of focus, raise, or lower. winops -r and winops -l operate within the window's own layer: they reorder among windows in that layer but never push the window across a layer boundary.
For instance:
- stay-on-top -- winops -L top (toggles between max_layer and default_layer).
- stay-on-bottom -- winops -L bottom (toggles between 0 and default_layer).
- Always-on-top from launch -- bind a rule:
rule -g -n mpv-pip -T on-map -s %mpv winops -t %mpv -L =top
Use =top (rather than bare top) inside rules so a re-map event never accidentally toggles the layer back to default.
Iconified windows' icons are pinned to layer 0 regardless of the parent window's layer.
Focus-on-raise (the raise_on_focus setting) is layer-aware: focusing a layer-4 window with a layer-8 window present never visually pops the layer-4 window above the layer-8 one. The titlebar/border colours remain the only cross-layer signal of focus.
The two layer-aware settings are:
- set default_layer N -- layer assigned to newly mapped windows.
- set max_layer N -- cap for -L; raising the cap re-permits bigger numbers, lowering it clamps every existing window's layer.
The on-layer-change rule event fires whenever a window's layer changes -- this is the hook for visual cues that depend on layer. For example, to tint the titlebar of any window in the top layer:
rule -g -n top-layer-tint -T on-layer-change
set titlebar.active_colour 0xC04030The rule receives the same per-view scope as other view-bearing events, so -s / -t selectors and per-view set writes all work as expected.
When the rule body is an exec line, the per-firing JSON payload is available to the spawned shell as the COW_EVENT environment variable. For on-layer-change the payload is:
{"prev": P, "current": N}so a rule like:
rule -g -n log-layer -T on-layer-change
exec sh -c 'printf "%s\n" "$COW_EVENT" >> ~/cow-layer.log'writes one line per layer transition. jq makes parsing trivial (jq .current <<<"$COW_EVENT"). Other rule events without structured payload leave COW_EVENT unset; the variable is only visible inside the exec'd shell and never affects cow itself or other concurrent rule fires.
Desktop Behaviour
Desktops can be configured either independently of each output, or desktops are the same across all outputs. See the deskstop_configuration setting.
Configuration
Search Order
Unless overridden with -c or $COW_CONFIG, the configuration file is located by searching the following paths in order, stopping at the first that exists:
- $COW_CONFIG
- ~/cow.conf
- $XDG_CONFIG_HOME/cow/cow.conf
- ~/.config/cow/cow.conf
- /<PREFIX>/etc/cow/cow.conf
File Format
The configuration file is plain text. Each line is a cow command, using the Lines beginning with # are comments. A backslash (\) at the end of a line continues the command on the next line.
Example:
# This is a comment which cow ignores.
set border 10
set border_style fvwm
# This command is split over multiple lines for clarity.
bind \
L+Return \
exec footCommand Referencing
Commands in cow can operate on outputs, desktops, pages, and windows. The commands in cow are therefore pre-disposed to understand that they need one or more of those contexts to operate on.
In some cases that's automatic (such as operating on the focused window, or the current output, etc.) but commands can be told to override that.
Source and Target Definitions
Most commands have a target on which the command is going to operate on, and for consistency across those commands, that is the `-t` flag. The same concept exists for for a source window, via `-s`.
The format for both is the following:
output:desk.window
That is to say, there's three components -- the delimiters between the parts are literal and must be specified:
- output
Output name, @next, or @prev.
- desk
Desk number (0-9), @next, or @prev.
- window
One of:
- %app_id - match by app_id
- /substring/ - match by title substring
- #id - match by River identifier
- @focused - the currently focused window (default)
- @next - next window in stacking order
- @prev - previous window in stacking order
In the case of using a substring, this is run through `fnmatch(3)`
Command Chaining
With any given command, it's possible to chain them together. For example:
exec xterm ; exec notify-send "xterm executed"
The command divider is `\;` and must be escaped in this way so as not to incur any shell interpretation.
Also, line continuation between changed commands is also possible, and looks like this:
rule -g -T on-restart -n cleanup exec killall waybar ; exec killall conky ; exec killall pasystray
Command Output
Certain commands in cow are designed to return information. In such cases, the output is in JSON format.
This may be subject to change in the future.
Global Commands
The following details those commands which just operate on general settings. Note that the same command might also contain window/output settings, which will be also be added under the relevant section.
bind [-r] modifier+key action ...
Key bindings are specified as a modifier string immediately followed by + and a keysym name, or - and a numeric keycode:
bind MODIFIERS+keysym command bind MODIFIERS-keycode command
- -r
Mark the binding as repeatable. While the triggering key is held the action re-fires every repeat_interval_ms milliseconds after an initial repeat_delay_ms dwell (see set).
Modifier characters:
| Character | Modifier | |||
| L | Logo (Super / Windows key). | |||
| S | Shift. | |||
| C | Control. | |||
| A | Alt (Mod1). | |||
| 5 | AltGr (Mod5). |
Modifiers are combined by concatenation: LS means Logo+Shift, LCA means Logo+Control+Alt. Use 0 to specify no modifier.
Key symbols and codes can be determined with wev(1).
Examples:
bind L+Return exec xterm bind LS+a winops -c bind LCA+q quit bind 0+F1 action-help bind -r L+Right scroll -n # hold Super+Right to keep paging
mouse key action ...
Mouse bindings use the same modifier format as the bind command. The button name replaces the keysym:
mouse MODIFIERS+button command
Button names: left, right, middle, side, extra, forward, back, task.
Bind a pointer button combination to a command. The key format is the same as for bind, but the key name is a button name (see MOUSE BINDINGS).
Example:
mouse L+left window-move mouse L+right resize mouse L+middle window-move -C
bind-decoration [-2] region command ...
Bind a primary-button click on a window's decoration to a command. Each window's frame is divided into regions. See the ANATOMY_OF_A_WINDOW section.
When a bound region of the window is clicked on, the attached action runs against that window.
- -2
Double-click binding (default is single-click). A region can carry one single-click binding and one double-click binding simultaneously.
The region argument is case-insensitive and accepts both the compass shorthands and the long form:
| Region | Aliases | |||
| N | north | |||
| S | south | |||
| E | east | |||
| W | west | |||
| NE | north-east | |||
| NW | north-west | |||
| SE | south-east | |||
| SW | south-west | |||
| titlebar | title |
The defaults bindings are:
| Region | Clicks | Default action | |||
| N / S / E / W | single | window-resize -e dir (interactive one-axis resize) | |||
| NE / NW / SE / SW | single | window-resize -e dir (interactive diagonal resize) | |||
| titlebar | single | window-move (interactive title-drag move) | |||
| titlebar | double | window-shade -d north (shade / unshade) |
Double-clicks on edges and corners have no defaults.
Limitation: River does not expose which button was used when clicking on the window decoration, so currently, only mouse button 1 is usable.
Examples:
# Maximise a window by clicking anywhere on its titlebar # (replaces the default window-move). bind-decoration titlebar window-maximize -m # Re-express the default double-click-shade explicitly. bind-decoration -2 titlebar window-shade -d north # Maximise on a click on the north edge. bind-decoration N window-maximize -m # Double-click NE corner closes the window (the single-click default # of starting a corner resize still fires on the first click; bind # the single-click pair too if you want to suppress it). bind-decoration -2 NE winops -c # Chain: start a resize then focus the next window. bind-decoration SE window-resize -e se ; focus -n
rule -d -n <name> | -g | -t output[:desk] -n <name> -T <event> [-s sel] cmd...
Apply rules (groups of commands) to certain conditions (events).
A rule has a name (via `-n`) which must be specified. Note that rules are globally stored, so any conflicting names will mean that rule is replaced. It also has a type (via `-T`) which specifies when to run the rule. Multiple rules can be defined against the same type as long as their names are distinct.
The following table shows which events are available:
| Event | Description | |||
| on-map | Fired when a window appears on the screen. | |||
| on-move | Fired when a window is moved. | |||
| on-resize | Fired when a window is resized. | |||
| on-shade | Fired when a window is shaded. | |||
| on-unshade | Fired when a window is unshaded. | |||
| on-iconify | Fired when a window is iconified. | |||
| on-deiconify | Fired when a window is deiconified. | |||
| on-layer-change | Fired when a window's layer changes (see Layers). Fires per-window for container members. No-op assignments do not fire. | |||
| on-new-desk | Fired a new desk is switched to. | |||
| on-new-page | Fired when a new page is switched to. | |||
| on-restart | Fired when cow is restarted (can also happen via `-USR1` signal. | |||
| on-desk | Used to change window styles on a particular desk. |
Specificity of rules are such that global rules (via `-g`) run before any specific defined rules. For example:
# Define a global rule -- this will always run.
rule -g -Ton-map -ng-on-map exec notify-send "A window has appeared."
# Define a rule to change a window property when windows appears on desk 2
rule -t :2 -Ton-map -ndesk2
set titlebar.active_colour 0xFF8C00 ;
set titlebar.inactive_colour 0xB28E4C ;
set colour.inactive 0xB28E4CRules can be deleted with the `-d` option. Additionally, `-n` is needed to specify the name, example:
rule -d -ndesk2
Defined rules can be seen with the show command.
exec command ...
Execute a shell command. During configuration loading, exec commands are deferred until cow has fully connected to River.
show [topic] [config key]
Query window manager state. The response is a JSON object. When used via moocow(1) the JSON is printed to standard output.
Topics:
- show windows
Return an array of all managed windows. Each element contains: id, app_id, title, desk, x, y, width, height, focused, maximized, shaded, iconified.
- show desk
Return {"current": N} for the current output's active desk.
- show rules
Return an array of all defined rules.
- show output
Return an array of output objects, each with name, x, y, width, height, and a usable sub-object reflecting reserved areas.
- show config key
Return the current value of a configuration key. Supported keys: border, step, corner_length, border_style, focus. Also accepted as show config.key.
quit [-r]
Without any options, cow quits. With -r, reload the configuration from the file cow was started with, instead of quitting.
Keybindings and window decorations are updated immediately on reload.
list-commands
Return a JSON array of all registered commands, each with name and usage fields.
set [-v] key value
Set a configuration option at runtime. -v prints the resulting value.
The specific keys/values for this command are detailed under relevant section in this man page.
Window Commands
The following detail commands which operate on windows directly.
winops [-Icilrs] [-L layer] [-t target]
Operate on a window.
- -t target
Target window (see Command Referencing). Defaults to the focused window.
- -I
Identify the window; returns a JSON object with geometry and state.
- -c
Close the window.
- -r
Raise the window to the top of the stacking order within its layer. See Layers below for the cross-layer invariant.
- -l
Lower the window to the bottom of the stacking order within its layer.
- -s
Toggle desk-sticky: window appears on all desks.
- -S
Toggle page-sticky: window appears on all pages of the current desk. Combine -s and -S for fully sticky (all desks and pages).
- -i
Toggle the window's iconified (minimised) state.
- -L layer
Set the window's layer (see Layers). Accepted forms:
- N -- absolute layer (clamped to [0, max_layer]).
- =N -- absolute layer, explicit (never toggles).
- +N / -N -- relative bump, clamped at edges.
- top -- shorthand for max_layer; toggles back to default_layer when the window is already at max_layer.
- bottom -- shorthand for 0; toggles back to default_layer when the window is already at 0.
- =top / =bottom -- non-toggling variants; useful inside rules so a re-map event doesn't accidentally revert the layer.
Container members share a single layer: setting -L on any member updates every member of the container.
window-move [-C] [-t target] [-d dir [-n]] [-o output] [-c] [-k 0-9] [-x X] [-y Y]
Move a window. With no flags, begin an interactive move using the mouse.
- -t target
Target window.
- -d dir
Move one step in direction dir (up, down, left, right).
- -n
With -d, snap to the nearest edge instead of stepping.
- -o output
Move the window to the named output.
- -C
Enable container-formation on drop. When the interactive move ends with the pointer over another window's titlebar, the two windows are grouped into a container instead of completing a normal move. Releasing over empty space performs a normal move. The target window's titlebar highlights in orange while the pointer is over it.
- -P col [row]
Move the window to the page at column col, row row (0-indexed), preserving its within-page position. row defaults to 0. Only meaningful when desktop_size is larger than 1×1.
- -c
Centre the window on its current output.
- -k 0-9
Move the window to desk number 0-9.
- -x X
Set the window's X position. A leading + or - makes the value relative to the current position.
- -y Y
Set the window's Y position. A leading + or - makes the value relative to the current position.
window-resize [-t target] [-gs] [-d dir] [-e edges] [-w width] [-h height]
Resize a window. With no flags, begin an interactive resize operation with the mouse, from the bottom-right corner.
- -t target
Target window.
- -g -d dir
Grow the window in direction dir (up, down, left, right) by one step.
- -s -d dir
Shrink the window in direction dir by one step.
- -e edges
Begin an interactive resize anchored on the named edges -- a compass spec built from the letters n, s, e, w. Single letters select an edge (n, s, e, w); two-letter combos select a corner (ne, nw, se, sw). Used by bind-decoration to express per-edge / per-corner resize defaults as ordinary commands; default if -e is omitted is the historic se (bottom-right) corner.
- -w width
Set the window width in pixels.
- -h height
Set the window height in pixels.
focus [-npwL] [-l N] [-t target] [-d dir] [-o output] [-A app_id] [-T title] [-i id]
Move keyboard focus.
- -n
Focus the next window in stacking order.
- -p
Focus the previous window in stacking order.
- -w
Warp the pointer to the centre of the focused window after focus is applied. May be combined with any other focus flag. When used alone, warps to the currently focused window without changing focus.
- -d dir
Focus the nearest window in direction dir (up, down, left, right).
- -o output
Warp the pointer to the named output. The -w flag is ignored when -o is given, as -o performs its own pointer movement.
- -A app_id
Focus the window with the exact app_id app_id.
- -T pattern
Focus the window whose title contains pattern.
- -i id
Focus the window with River identifier id.
- -L
Restrict traversal to the focused window's layer (see Layers). Combine with -n, -p, or -d; standalone -L is an error. When no window is focused, the current layer is taken as default_layer.
- -l N
Restrict to layer N. Without -n or -p, focuses the topmost focusable window in layer N; if the focused window is already in layer N, cycles to the next focusable window in that layer. Combine with -n/-p to walk only within N. Mutually exclusive with -L.
window-expand [-t target] [-d dir] [-T]
Expand a window to fill available space between windows, or the whole monitor if the window is the only window on that monitor.
- -t target
Target window.
- -d dir
Expand in direction dir (up, down, left, right). Omit to expand in all directions.
- -T
Toggle: restore original geometry if the window is already expanded.
window-maximize [-t target] [-T] [-m] [-u] [-h] [-v]
Maximize or restore a window.
- -t target
Target window.
- -T
Toggle between maximized and restored. Combined with -h / -v, toggles only that axis; toggling an unmaxed axis maximises it.
- -m
Maximize the window (default if no flag is given).
- -u
Restore (unmaximize) the window. Combined with -h / -v, restores only that axis; a window can stay maximised on the other axis.
- -h
Maximize horizontally only -- the window's width grows to the output's usable area.
- -v
Maximize vertically only -- the window's height grows to the output's usable area.
Per-axis maximised state is independent: window-maximize -h followed by window-maximize -v leaves the window maximised on both axes, and each axis can be restored separately with -T -h and -T -v.
Examples:
window-maximize # full maximise window-maximize -T # toggle full maximise window-maximize -h # horizontal only window-maximize -v # vertical only window-maximize -T -h # toggle horizontal maximised state only window-maximize -u -v # un-maximise vertical only, keep horizontal
window-shade [-t target] -d dir
Shade (roll up) a window in a given direction, hiding its content but leaving its border visible.
- -t target
Target window.
- -d dir
Shade direction: north, south, east, west, nw, ne, sw, se. Required.
Window Decoration Settings
The following tables show which settings are available to control the look and feel of a window. All of these can be used with the set command.
General / Misc:
| Key | Description | |||
| border | Border thickness in pixels (default: 1). | |||
| step | Move/resize step in pixels (default: 100). | |||
| corner_length | Length of border corner handles in pixels (default: 20). | |||
| icon.size | Iconified window icon size in pixels (default: 64). | |||
| snap_distance | Snap attraction distance in pixels; 0 disables (default: 10). |
Border Colour Settings (values are hexadecimal RGB, e.g. 0xFF0000):
| Key | Description | |||
| colour.active | Active (focused) window border colour. | |||
| colour.active.n | Active border: north edge. | |||
| colour.active.s | Active border: south edge. | |||
| colour.active.e | Active border: east edge. | |||
| colour.active.w | Active border: west edge. | |||
| colour.active.nw | Active border: north-west corner. | |||
| colour.active.ne | Active border: north-east corner. | |||
| colour.active.sw | Active border: south-west corner. | |||
| colour.active.se | Active border: south-east corner. | |||
| colour.inactive | Inactive (unfocused) border colour. | |||
| colour.inactive.n | Inactive border: north edge. | |||
| colour.inactive.s | Inactive border: south edge. | |||
| colour.inactive.e | Inactive border: east edge. | |||
| colour.inactive.w | Inactive border: west edge. |
Titlebar Colour Settings (values are hexadecimal RGB, e.g. 0xFF0000):
| Key | Description | |||
| titlebar.active_colour | Titlebar background when focused. | |||
| titlebar.inactive_colour | Titlebar background when unfocused. | |||
| titlebar.fg_active | Titlebar foreground (text) when focused. | |||
| titlebar.fg_inactive | Titlebar foreground (text) when unfocused. |
Window Decoration Settings:
| Key | Values | Description | |||
| border_style | fvwm | mwm | none | Border rendering style. Default: none. | |||
| focus | sloppy | click | Focus model. Default: click. | |||
| placement | cascade | undermouse | centre | center | New window placement. Default: cascade. | |||
| font name | Pango font string | Font for titlebars. Default: monospace 10. | |||
| handles | true | 1 | Draw handle marks on border corners. | |||
| titlebar.enabled | true | 1 | Show titlebars. | |||
| titlebar.height | integer (pixels) | Fix the titlebar height in pixels. When set to 0 (the default) the height is derived from the font size. | |||
| titlebar.button_left.vector | vector string | Geometry of the left titlebar button. | |||
| titlebar.button_left.action | command string | Action for the left titlebar button. | |||
| titlebar.button_right.vector | vector string | Geometry of the right titlebar button. | |||
| titlebar.button_right.action | command string | Action for the right titlebar button. | |||
| titlebar.button_right2.vector | vector string | Geometry of the second right titlebar button. | |||
| titlebar.button_right2.action | command string | Action for the second right titlebar button. | |||
| titlebar.squeeze | none | natural | fixed | Shrink the titlebar down to a minimum size. Remaining pixels of the titlebar strip are transparent and pass clicks through. none is the default (full-width titlebar); natural sizes the titlebar to the title text + buttons; fixed uses titlebar.squeeze.width. | |||
| titlebar.squeeze.justify | left | centre | right | Horizontal alignment of the squeezed titlebar within the full-width strip. Default: left. center is accepted as a synonym for centre. | |||
| titlebar.squeeze.width | integer (pixels) | Width of the squeezed titlebar when titlebar.squeeze is fixed. Default: 300. | |||
| titlebar.squeeze.offset | integer (pixels; may be negative) | Horizontal nudge applied after justify. Useful for e.g. positioning the titlebar 40px in from the left edge. Default: 0. | |||
| titlebar.squeeze.min_width | integer (pixels) | Minimum width for natural mode (floor applied after measurement). Default: 80. |
Button vector format: N x1X_y1_@c1 x2X_y2_@c2 ... where N is the number of points, coordinates are 0-100 (percentages of the button area), and @c is a colour index (0 or 1).
Window Containers
Group windows into a tabbed container. A container is a meta-window that holds multiple application windows as tabs. Only the active tab's content is visible; all tabs share the container's position, size, and frame. The titlebar shows a clickable label for each member. Clicking a label activates that tab.
window-container [-t target] [-s source] [-arnpNP]
- window-container -a
Add source to target's container. If neither window is already in a container, a new container is created.
source defaults to the focused window. target defaults to the focused window when -t is given explicitly.
When neither -t nor -s is given, source is the focused window and target is the next focusable window in stacking order. This means container add with no arguments is a self-contained keyboard-only action: it groups the focused window with the one below it in the stack. This is useful in environments where mouse modifier combinations are unavailable (e.g. VNC).
- window-container -r [-t target]
Remove target from its container. The detached window reappears offset from the container position. If the container drops to one member, the container is dissolved.
- window-container -n [-t target]
Activate the next tab in the container that holds target.
- window-container -p [-t target]
Activate the previous tab in the container that holds target.
- window-container -N [-t target]
Move the tab containing target one position to the right in the tab strip. The tab remains active. No-op if it is already the last tab.
- window-container -P [-t target]
Move the tab containing target one position to the left in the tab strip. The tab remains active. No-op if it is already the first tab.
See also window-move -C, which allows containers to be formed interactively by dragging a window's titlebar onto another. In environments where mouse modifier combinations are unreliable (e.g. VNC), bind container add to a key instead:
bind L+g window-container -a bind LS+g window-container -r bind L+Tab window-container -n
Container Settings
The following options can be used with the set command to change the behaviour of containers:
| Key | Values | Description | |||
| container.tab.active_colour | hex colour (0xRRGGBB) | Background colour of the active tab label. Default: 0xC0C0C0. | |||
| container.tab.inactive_colour | hex colour (0xRRGGBB) | Background colour of inactive tab labels. Default: 0x808080. | |||
| container.tab.fg_active | hex colour (0xRRGGBB) | Foreground (text) colour of the active tab label. Default: 0x000000. | |||
| container.tab.fg_inactive | hex colour (0xRRGGBB) | Foreground (text) colour of inactive tab labels. Default: 0x202020. | |||
| container.tab.sunken | true | 1 | false | 0 | Draw inactive tabs with a sunken (depressed) bevel. Default: false (flat). |
Desktop / Output Commands
This section details commands which affect desktops/pages often per-output.
scroll [-t output] [-w] [-p] _H_ _V_
scroll [-t output] -a _col_,_row_
scroll [-t output] -d _left_|_right_|_up_|_down_
scroll [-t output] -n
scroll [-t output] -P
scroll [-t output] [-R] -r
Pan the virtual page viewport for the current desk.
Pages can be scrolled in either full pages, or part increments. Additionally, it's possible to in-effect, "drag" the viewport with the mouse to any position.
In the deltas form (H V), H is the horizontal scroll and V the vertical. By default each value is a percentage of one page in that axis: 100 is one full page right (or down), -100 one page left (or up), 50 is half a page, and so on. With -p the values are raw pixels instead.
Options are:
- -t output
Target the named output instead of the current one.
- -w
Wrap at the desk edges. Without -w, the viewport is clamped to the desk extent. The legacy fvwm idiom of multiplying the percentage by 1000 (e.g. scroll 100000 0) is also recognised as an implicit -w.
- -p
Treat H and V as pixels rather than percent of a page.
- -a col,row
Absolute jump: land the viewport at the page col,row (0-indexed). The pair are a single comma-separated token.
- -d dir
Jump one page in direction dir: left, right, up, or down, wrapping at desk edges.
- -n
Next page (right, wrapping at the end of a row to the start of the next row). Shorthand for scroll -w 100 0.
- -P
Previous page (left, wrapping).
- -r
Start an interactive drag-the-viewport pan. The viewport follows the pointer until the triggering mouse button is released. Only valid when invoked from a mouse or key binding. Bind it to a mouse button to "grab and drag" the desk. The -w and -p flags are ignored with -r since interactive drag works in raw pixels and never wraps.
- -R
Paired with -r, makes the viewport follow the pointer in the same direction instead of opposite.
Pages exist only when desktop_size N M is configured with N > 1 or M > 1.
Examples:
# One full page right (clamps at the last column). scroll 100 0 # Half a page right, a quarter page down. scroll 50 25 # 200 pixels right. scroll -p 200 0 # One page right, wrapping at the desk edge. scroll -w 100 0 # Jump straight to page (col=2, row=0). scroll -a 2,0 # One page right, wrapping; convenient for keybindings. scroll -d right # Next / previous page with wrap. scroll -n scroll -P # Bind Ctrl+Meta+Button1 to grab and drag the viewport. mouse CM+left scroll -r
desk [-t output] [-d N] [-c N] [-np]
Switch or manipulate virtual desks.
- -t output
Target the named output instead of the current one.
- -d N
Switch to desk number N.
- -n
Switch to the next desk, wrapping around.
- -p
Switch to the previous desk, wrapping around.
- -c N
Toggle collection of desk N: overlay its windows on top of the current desk without switching.
desk-name [-t output] N NAME | -d N | -l | -r
Manage the naming of virtual desktops. By default, cow sets ten desktops, whose names default to '0'..'9'. With this command it is possible to change that, either by increasing or decreasing the number of desktops, and/or renaming existing desks.
- -t output
Target the named output instead of the current one. In global desktop mode the operation is mirrored across every output.
- N NAME
Ensure desk N exists and set its name to NAME. Gaps below N are auto-filled with default-named desks. Names must be non-empty, printable, and contain no whitespace or :; duplicates within one set are rejected.
- -d N
Delete desk N. Refused if any window is on it.
- -l
List the current desks as JSON, per output.
- -r
Reset every desk set to the default set, as if no manipulation had ever occurred.
The following examples show how this command can be used:
# Three named desks instead of the default ten. desk-name 0 main desk-name 1 web desk-name 2 dev # Now both forms select the same desk. focus -t :main focus -t :0
The minimum number of desks can be set with desks.count. Note that it is possible with the desk-name command to name desks greater than desks.count number, and that this will effectively create this desk.
Desktop / Page Settings
The following options can be used with the set command to change the behaviour of desktops and pages:
| Key | Values | Description | |||
| desktop-configuration | global | per-output | shared | Desk layout mode. | |||
| desktop_size N M | N × M integer | Virtual page grid: N columns × M rows per desk. Default: 1 1 (no pages). Set e.g. 3 2 for three columns and two rows. | |||
| desks.count | 0-32 | Sets the number of available virtual desktops. Defaults: 10. | |||
| page_scroll_animate | true | false | Animate page transitions. Default: false (instant cut). | |||
| page_scroll_ms | integer (ms) | Page scroll animation duration. Default: 200. | |||
| edge_scroll | true | false | Enable edge scroll: dwell at a screen edge to switch page. Default: false. | |||
| edge_scroll_delay_ms | integer (ms) | Time the pointer must dwell at an edge before a page switch fires. Default: 300. | |||
| output.colour.background | hex colour (0xRRGGBB) | Background colour for all outputs. | |||
| output.colour.background.name | hex colour (0xRRGGBB) | Background colour for the named output. | |||
| reserved.top | integer (default: 0) | Pixels reserved at the top of each output. | |||
| reserved.bottom | integer (default: 0) | Pixels reserved at the bottom of each output. | |||
| reserved.left | integer (default: 0) | Pixels reserved at the left of each output. | |||
| reserved.right | integer (default: 0) | Pixels reserved at the right of each output. |
NOT£: The reserved. settings are akin to X11's concept of a working-area. That is to say, these settings will reserve parts of the screen to be able to put taskbars, etc.
Keyboard Settings
The following options can be used with the set command to tune keybinding behaviour:
| Key | Values | Description | |||
| repeat_delay_ms | integer (ms) | Time the user must hold a bind -r repeatable key before the action starts repeating after its first fire. Default: 400. | |||
| repeat_interval_ms | integer (ms, >= 1) | Gap between consecutive repeats of a held bind -r binding once the initial dwell has elapsed. Default: 40 (= 25 fires / s). |
A binding registered without -r fires exactly once per press, regardless of either setting.
Signals
- SIGTERM, SIGINT
Save state and exit cleanly.
- SIGUSR1
Restart: execute the rule restart hook command (if configured), then re-execute cow itself via execvp(3) without tearing down the River session.
- SIGPIPE
Ignored.
Environment
- COW_CONFIG
If set, use this path as the configuration file, bypassing the default search order.
- XDG_CONFIG_HOME
Base directory for the user configuration search ($XDG_CONFIG_HOME/cow/cow.conf). Defaults to ~/.config.
- XDG_RUNTIME_DIR
Directory in which the IPC command and status sockets are created.
Files
- ~/cow.conf
User configuration (second search location).
- $XDG_CONFIG_HOME/cow/cow.conf
User configuration in XDG base directory (third search location).
- ~/.config/cow/cow.conf
Fallback user configuration (fourth search location).
- /etc/cow/cow.conf
System-wide configuration (fifth search location).
- $XDG_RUNTIME_DIR/cow-cmd.sock
IPC command socket. Accepts one command per connection; returns JSON.
- $XDG_RUNTIME_DIR/cow-status.sock
Status broadcast socket. Emits a JSON state snapshot on each change.
See Also
moocow(1), cowbar(1), river(1), wev(1), xdg-desktop-portal(1), xdg-desktop-portal-wlr(1), pipewire(1), wl-clip-persist(1)
Authors
Thomas Adam <thomas@xteddy.org>
Parts of cow were derived from code under copyright by:
Nicholas Marriott
Referenced By
cowbar(1), cowident(1), cowpager(1), cowrearrange(1), moocow(1).