1package ports
2
3import (
4 "image"
5 "regexp"
6 "strings"
7 "time"
8)
9
10// DefaultSDRBrightness is the BT.2408 SDR reference white in HDR, in nits.
11const DefaultSDRBrightness = 203
12
13// OutputConfig configures one connector. Name is the connector (e.g. "DP-2").
14// Mode is "WxH" (highest refresh) or "WxH@Hz" (closest refresh); empty picks the
15// monitor's preferred mode. Off disables the connector.
16// Every connected output that is not off is used.
17// Placement, by precedence: Pos (set at runtime by wlr-output-management),
18// then Anchor against another connected output, then automatic: right of
19// everything placed so far (never left of 0), at y=0, in config order, then in
20// connection order.
21// Scale is the output scale (0 means 1); layout works in logical pixels,
22// physical = logical × Scale. Placement and offsets use the transformed
23// logical size.
24// Primary gets the focus and the pointer at startup, wherever it is placed.
25// ScaleOnly marks an entry set only by output.<name> subkeys: it
26// does not select the connector.
27type OutputConfig struct {
28 Name string
29 Mode string
30 Off bool
31 Scale float64
32 // Transform is output.<name>.transform; logical size swaps for 90/270.
33 Transform BufferTransform
34 // Pos is an explicit logical placement set at runtime; nil uses Anchor, else automatic layout.
35 Pos *image.Point
36 // Anchor places the output against another connected one.
37 Anchor OutputAnchor // RelationNone: automatic
38 Primary bool
39 HDR bool // opt-in to HDR10 on capable outputs
40 SDRBrightness int // nits; default DefaultSDRBrightness
41 ScaleOnly bool
42}
43
44// OutputRelation is the side of another output where an output is placed.
45type OutputRelation uint8
46
47const (
48 RelationNone OutputRelation = iota
49 RelationRightOf
50 RelationLeftOf
51 RelationAbove
52 RelationBelow
53)
54
55// OutputAnchor places an output against another connected one, named by To.
56// Offset is in logical pixels, along the shared edge: y for right-of and
57// left-of (positive is down), x for above and below (positive is right).
58type OutputAnchor struct {
59 Relation OutputRelation
60 To string
61 Offset int
62}
63
64// LayoutRules are the layout settings shared by the defaults, screens and
65// named workspaces. Zero MaxColumns and an empty Overflow inherit.
66type LayoutRules struct {
67 // MaxColumns is how many columns share the screen at once.
68 MaxColumns int
69 // Overflow is "scroll" (horizontal scrolling), "fixed" (spiral splits),
70 // or "cascade" (vertically scrolling bands of columns).
71 Overflow string
72}
73
74// Over fills the unset rules of r from base.
75func (r LayoutRules) Over(base LayoutRules) LayoutRules {
76 if r.MaxColumns == 0 {
77 r.MaxColumns = base.MaxColumns
78 }
79 if r.Overflow == "" {
80 r.Overflow = base.Overflow
81 }
82 return r
83}
84
85// OutputLayout is the layout of one screen, matched by connector (DP-2) or
86// monitor key.
87type OutputLayout struct {
88 Output string
89 LayoutRules
90}
91
92// Focus indicator: the animation (Config.Focus.Animation) shapes in time
93// the visual effect (Config.Focus.Effect) drawn on a newly focused window.
94const (
95 FocusAnimationOff = "off"
96 FocusAnimationPulse = "pulse"
97 FocusEffectScreen = "screen"
98)
99
100// Config is the parsed compositor configuration (see the config adapter for keys).
101type Config struct {
102 Keyboard struct {
103 Layout, Variant, Options string
104 RepeatRate int
105 RepeatDelay int
106 CmdKey string
107 }
108 Terminal struct {
109 Command []string
110 AutoOpen string
111 }
112 // Xwayland is the xwayland-satellite binary serving X11 clients; empty
113 // disables X11.
114 Xwayland string
115 // Startup are commands run once when the session starts, in order.
116 // One startup line may hold several, split by SplitCommands.
117 Startup [][]string
118 Background struct{ Color string }
119 Floating struct{ Dim float64 }
120 // Stash is the strip of windows set aside by toggle-window-stash:
121 // Width is the width of its selected window (10 to 90) and Gap the
122 // space between it and its neighbors (0 to 10), in percent of the
123 // usable width; Dim darkens the neighbors, 0 to 1. Capture puts new
124 // windows in the stash while it is shown.
125 Stash struct {
126 Width, Gap int
127 Dim float64
128 Capture bool
129 }
130 // Border is drawn inside the window edge; Width 0 disables it.
131 Border struct {
132 Width int
133 Active string
134 Inactive string
135 }
136 Layout struct {
137 Gaps int
138 // LayoutRules are the defaults; Outputs override them per screen and
139 // named workspaces override them again.
140 LayoutRules
141 Outputs []OutputLayout
142 }
143 // InputDevicesConfig holds Touchpad and Mouse, promoted.
144 InputDevicesConfig
145 // Cursor.HideAfter hides the pointer cursor after this long without
146 // motion; the next motion shows it. 0 never hides it.
147 Cursor struct{ HideAfter time.Duration }
148 // Animations: On enables motion (off lands everything instantly);
149 // Slowdown scales every spring's duration (not the focus pulse), 0.1 to
150 // 10 (the config's animations.speed maps to it).
151 Animations struct {
152 On bool
153 Slowdown float64
154 }
155 Focus struct {
156 // FollowMove shows the target workspace after a column or window
157 // moves to it.
158 FollowMove bool
159 // Animation and Effect mark a window that just got the focus:
160 // FocusAnimation* (off disables it) and FocusEffect*. Strength is
161 // the effect's peak, 0.01 to 0.2.
162 Animation, Effect string
163 Strength float64
164 }
165 // Workspaces are declared with workspace.<name>.* keys, in first-seen order.
166 Workspaces []WorkspaceConfig
167 // Rules are the window rules (rule.<name>.* keys), in first-seen order.
168 Rules []WindowRule
169 // Outputs selects and configures physical displays (drm backend).
170 Outputs []OutputConfig
171 Binds map[string]string
172 Render struct {
173 DirectScanout bool
174 // Tearing honours wp_tearing_control_v1 in direct scanout; VRR
175 // turns variable refresh on while a buffer is scanned out.
176 Tearing, VRR bool
177 // VRRFlipGap is the minimum time between a game frame's flip and
178 // the next frame commit under VRR (0: off). It works around
179 // flips that land at the panel's slowest refresh.
180 VRRFlipGap time.Duration
181 }
182 Performance struct{ Realtime bool }
183 Log struct {
184 Level string
185 Debug []string
186 }
187}
188
189// PointerConfig holds the settings mice and touchpads share. NaturalScroll
190// moves the content with the fingers or the wheel instead of against them.
191// AccelSpeed (-1 to 1) and AccelProfile (AccelAdaptive or AccelFlat) set the
192// pointer speed. LeftHanded swaps the left and right buttons.
193type PointerConfig struct {
194 NaturalScroll bool
195 AccelSpeed float64
196 AccelProfile string
197 LeftHanded bool
198}
199
200// TouchpadConfig configures touchpads: the shared pointer settings
201// (NaturalScroll also applies to two-finger scroll and swipes), plus Tap,
202// which clicks on a tap (one finger left, two right, three middle), and
203// ScrollFactor, which multiplies two-finger scroll.
204type TouchpadConfig struct {
205 PointerConfig
206 Tap bool
207 ScrollFactor float64
208}
209
210// InputDevicesConfig is the live configuration of the input devices, sent to
211// the input adapter as one value. It is comparable.
212type InputDevicesConfig struct {
213 Touchpad TouchpadConfig
214 Mouse PointerConfig
215}
216
217// Pointer acceleration profiles, for mice and touchpads.
218const (
219 AccelAdaptive = "adaptive"
220 AccelFlat = "flat"
221)
222
223// WorkspaceConfig declares a bind-only named workspace, outside the numbered list.
224// Zero MaxColumns and an empty Overflow use the layout.* defaults.
225type WorkspaceConfig struct {
226 Name string
227 // Monitor is the home monitor: a connector name (DP-2) or a monitor key
228 // ("make model serial"); empty follows the focused output when shown.
229 Monitor string
230 // Size overrides the workspace's logical width and height. Zero inherits
231 // the monitor; its scale is always inherited.
232 Size [2]int
233 // Slots are the declared columns (workspace.<name>.column.N), by N.
234 Slots []SlotConfig
235 LayoutRules
236}
237
238// CommandSeparator separates commands in config values that run programs
239// (startup, spawn binds): "waybar; mako" starts both, without waiting.
240const CommandSeparator = ";"
241
242// SplitCommands splits v on CommandSeparator, then each command on
243// whitespace. Empty commands are skipped; no shell is involved.
244func SplitCommands(v string) [][]string {
245 var commands [][]string
246 for part := range strings.SplitSeq(v, CommandSeparator) {
247 if argv := strings.Fields(part); len(argv) > 0 {
248 commands = append(commands, argv)
249 }
250 }
251 return commands
252}
253
254// SlotConfig reserves column N of a workspace for the window of one command.
255// neferwl spawns the command at startup; the window it opens goes to the
256// slot. Cells is its width in cells, a cell being one max-columns-th of
257// the usable width (1 to 16; 0 shares the width with the other columns).
258type SlotConfig struct {
259 Index int
260 Cells int
261 Argv []string
262}
263
264// WindowRule places the windows whose app ID it matches when they first map.
265// Matching rules merge in config order, a later rule winning per field.
266type WindowRule struct {
267 Name string
268 // AppID matches the whole app ID (the config anchors it).
269 AppID *regexp.Regexp
270 // Floating forces a window to float (true) or to tile (false); nil leaves it.
271 Floating *bool
272 // Workspace is a 1-based number of a numbered workspace or the name of a
273 // declared one; empty leaves it.
274 Workspace string
275 // Monitor is a connector (DP-2) or a monitor key ("make model serial").
276 Monitor string
277 // Cells is the width in cells of the new column of a tiled window
278 // (1 to 16; 0 leaves it automatic).
279 Cells int
280}