.TH RIVERGUILE 1 2024-01-13 "git.sr.ht/~leon_plickat/riverguile" "General Commands Manual" . .SH NAME .P riverguile \- scheme powered scripting layer for river . . .SH SYNOPSIS .SY riverguile path-to-script .YS . . .SH DESCRIPTION .P Scripting layer for the .BR river (1) Wayland server. Allows the user to send commands to the Wayland server (probably river) and install handlers for events from a scheme script. The scheme implementation is provided by .BR guile (1). .P The canonical way to use riverguile is as an interpreter for the river init script. To do so place the following expression at the very top of your init script: .P .RS .EX #!/bin/env riverguile !# .EE .RE .P Do not leave out the second line, as the octothorpe plus exclamation-mark combination indicates a multi-line comment in scheme. Do not forget to mark your init script as executable. Your custom scheme code to configure the river session may follow after these two lines. .P By default, riverguile will exit after the script has been loaded. However if certain handlers are installed it will run continuously to provide that functionality. . . .SH COMMANDS .P Riverguile exposes the special procedure \fB(riverctl \fR\fIfirst\fR . \fIrest\fR\fB)\fR, which can be used to send commands to the server in a similar fashion to .BR riverctl (1). All arguments must be strings. .P Here is an example of using this procedure to instruct river to spawn an instance of the .BR foot (1) terminal emulator: .P .RS .EX (\fBriverctl\fR "spawn" "foot") .EE .RE .P Riverguile also provides a scheme module which exports macros that wrap this procedure in a more ergonomic interface. This module is documented in the \fBRIVERGUILE MODULE\fR section of this document. . . .SH EVENT HANDLERS .P Riverguile exposes the special procedure \fB(install-handler \fR\fIkey\fR \fIproc\fR\fB)\fR, which can be used to install event handlers. The parameter \fIkey\fR is a symbol indicating for which event to install the procedure \fIproc\fR. The following keys are currently available: . .P \fBlayout-demand\fR .P .RS Installing a handler for this key allows the user to provide window layouts. All limitations of the river-layout-v3 protocol apply. The server will trigger this event when a new layout is required ("demanded"). .P Installing a layout-demand handler will cause riverguile to run continuously. .P The handler procedure must accept five required arguments, which are, in order: The amount of views in the layout (integer), the available width (integer), the available height (integer), the currently active tag set (integer representing a bitfield of size 32) and the global name of the output the layout is needed for (integer). The procedure must return a list containing exactly as many lists as there are views in the layout. Each of those sublists must contains exactly four numerical values, which are the x and y coordinates of the window as well as its width and height. Window positions and dimensions get applied to the window list top to bottom. .P Note that the numerical values do not need to be exact, riverguile takes care of rounding and casting for you. .P Here is an example of a simple layout-demand handler which simply makes all windows use all available space: .P .RS .EX (\fBinstall-handler\fR 'layout-demand (\fBlambda\fR (view-count width height tags output) (\fBletrec\fR ((iter (\fBlambda\fR (n) (if (eq? 0 n) '() (\fBappend\fR (\fBlist\fR (\fBlist\fR 0 0 width height)) (iter (1- n))))))) (iter view-count)))) .EE .RE .RE . .P \fBuser-command\fR .P .RS User commands are intended to allowing the user to update parameters of the layout live. The user sends a command - a string - to the server, which relays is to the layout generator. Of course, nothing is stopping you from (ab-)using this event to trigger arbitrary scheme code on key presses or on outside events, or from simply not using it at all. Please see .BR riverctl (1) regarding how to send user commands and how to configure the server to send them on key presses (note that usage of the riverctl executable maps one-to-one to the usage of the riverguile procedure of the same name). After a user-command has been received, the server will trigger a layout-demand if there are visible windows. .P Installing a user-command handler will \fInot\fR cause riverguile to run continuously. This event is an extension to the layout-demand event and as such it is invalid to install a user-command handler without also installing a layout-demand handler. .P The handler procedure must accept three arguments, which are, in order: The command (string), the currently active tags (integer representing a bitfield of size 32) and the global name of the output (integer). .P Here is an example of a simple user-command handler which simply evaluates the string as scheme code: .P .RS .EX (\fBinstall-handler\fR 'user-command (\fBlambda\fR (cmd tags output) (\fBeval-string\fR cmd))) .EE .RE .P Note that this is not necessarily good practice, but serves as a decent example. .RE . .P \fBidle:X\fR .P .RS A handler installed for this key will be triggered after the system has been idle for \fIX\fR seconds and once more once the system is no longer idle. .P Installing an idle handler will cause riverguile to run continuously. Multiple idle handlers can be installed. .P Idle state is server policy and may depend on a multitude of factors, but usually maps directly to the usage activity of input devices by the user. Certain programs may inhibit idle state, like for example video players. .P The handler procedure must accept one argument, a symbol indicating the type of idle event. This symbol is either \fBidle\fR, indicating the system has been idle for the configured amount of time, or \fBresume\fR, indicating that the system is no longer idle. .P Here is an example which will dim the screen after two minutes of inactivity and lock it after five: .P .RS .EX (\fBinstall-handler\fR 'idle:120 (\fBlambda\fR (event) (\fBcond\fR ((\fBeq?\fR event 'idle) (riverctl "spawn" "light -S 20")) ((\fBeq?\fR event 'resume) (riverctl "spawn" "light -S 100"))))) (\fBinstall-handler\fR 'idle:300 (\fBlambda\fR (event) (if (\fBeq?\fR event 'idle) (riverctl "spawn" "swaylock")))) .EE .RE .P Note: All idle events relate to the first advertised seat. As of now, river only supports a single seat anyway. .RE . .P \fBnew-output\fR .RE .RS A handler installed under this key will be called everytime a new output appears. On binding, it is also called for all outputs that already exist at that time. .P Installing a new-output handler will cause riverguile to run continously. .P The handler procderure must accept a single argument, the global name of the output (integer). .P Here is an example of a simple new-output handler which merely logs new outputs: .P .RS .EX (\fBinstall-handler\fR 'new-output (\fBlambda\fR (output) (\fBdisplay\fR "New output: ") (\fBdisplay\fR output) (\fBnewline\fR))) .EE .RE .RE . .P \fBexit\fR .RE .RS This key allows you to install a handler which is called when riverguile exits. .P The procedure takes no arguments. .P Here is an example which adds a message to the system log on exit: .P .RS .EX (\fBinstall-handler\fR 'exit (\fBlambda\fR () (riverctl "spawn" "logger 'goodbye from riverguile'"))) .EE .RE .RE . . .SH RIVERGUILE MODULE .P A complete installation of riverguile also provides a scheme module which exposes macros and procedures with the intention of exposing more ergonomic interfaces. .P .RS .EX (\fBuse-modules\fR (riverguile)) .EE .RE .P This module is not necessary to use riverguile and also will not provide any of riverguiles functionality to any scheme script not executed by riverguile. .P The following documents all exported procedures and macros. . .P (\fBR\fR \fIarg\fR ...) .P .RS A direct wrapper for the \fBriverctl\fR procedure, however it also accepts symbols and numbers in addition to strings. Any expressions you need evaluated must be unquoted. .P .RS .EX (R spawn foot) (R spawn "notify-send hello") (\fBfor-each\fR (\fBlambda\fR (cmd) (R spawn ,cmd)) '("foot" "firefox" "nautilus")) .EE .RE .RE . .P (\fBR:map\fR \fImode\fR (\fImod\fR \fIkey\fR \fIcmd\fR ...) ...) .P .RS This macro is intended to simplify defining keymaps. Please refer to the .BR riverctl (1) manual page for more details and specifics regarding rivers map mechanism. Any expressions you need evaluated must be unquoted. .P .RS .EX (R:map normal (Super H focus-view left) (Super Space spawn foot) (-repeat None XF86AudioRaiseVolume spawn "volume.sh raise 5%")) (\fBfor-each\fR (\fBlambda\fR (mode) (R:map ,mode (None XF86MonBrightnessUp spawn "light -A 5") (None XF86MonBrightnessDown spawn "light -U 5"))) '("normal" "locked")) .EE .RE .RE . .P (\fBR:input\fR \fIname\fR (\fIval\fR \fIvar\fR ...) ...) .P .RS This macro is intended to simplify input device configuration. Please refer to the .BR riverctl (1) manual page for details and specifics regarding the input device configuration. Any expressions you need evaluated must be unquoted. .P .RS .EX (R:input pointer-1149-4128-Kensington_Expert_mouse (accel-profile none) (pointer-accel 0.6) (scroll-method button) (scroll-button BTN_SIDE)) .EE .RE .RE . .P (\fBR:keyboard-group\fR \fIname\fR . \fIdevices\fR) .P .RS This macro is intended to simplify creation of keyboard groups. Please refer to the .BR riverctl (1) manual page for details and specifics regarding keyboard groups. Any expressions you need evaluated must be unquoted. .P .RS .EX (R:keyboard-group split keyboard-XXXX-XXXX-Device-1 keyboard-XXXX-XXXX-Device-2 keyboard-XXXX-XXXX-Device-3) .EE .RE .RE . . .SH SEE ALSO .BR river (1), .BR riverctl (1), .BR rivertile (1), .BR guile (1) . . .SH AUTHOR .P .MT leonhenrik.plickat@stud.uni-goettingen.de Leon Henrik Plickat .ME