commit a3db7c5
soggy
·
2026-11-05 18:32:11 +0000 UTC
parent a4adaa6
slgro - config can now autostart stuff + tweaked the window movement and snapping
6 files changed,
+286,
-96
+18,
-9
1@@ -1,17 +1,24 @@
2-border_active = 0xff000000
3-border_normal = 0xff000000
4-border_width = 2
5+border_active = 0xff000000
6+border_normal = 0xff000000
7+border_width = 2
8
9 -- for those who may want double borders, uncomment these !!
10---border_active_outer = 0xffffffff
11---border_normal_outer = 0xffffffff
12---border_width_outher = 2
13+--border_active_outer = 0xffffffff
14+--border_normal_outer = 0xffffffff
15+--border_width_outher = 2
16
17-motion_throttle_hz = 85
18+motion_throttle_hz = 85
19
20 terminal = "foot"
21 menu = "neumenu_run"
22
23+autostart = {
24+ -- i forgor who suggested me to add autostart, but, thank you for the suggestion, and, here it is ^^
25+
26+ -- to add smth to autostart the syntax is just
27+ -- "/home/dani/Prog/Scripts/verycoolscript.sh",
28+}
29+
30 binds = {
31 { mods="MOD4", key="q", action="spawn", arg=terminal },
32 { mods="MOD4", key="d", action="spawn", arg=menu },
33@@ -31,7 +38,9 @@ binds = {
34 { mods="MOD4|SHFT", key="Left", action="resize_width", arg=-25 },
35 { mods="MOD4|SHFT", key="Down", action="resize_height", arg=25 },
36 { mods="MOD4|SHFT", key="Up", action="resize_height", arg=-25 },
37- { mods="MOD4", key="h", action="snap_left" },
38+ { mods="MOD4", key="k", action="snap_top" },
39+ { mods="MOD4", key="j", action="snap_bottom" },
40+ { mods="MOD4", key="h", action="snap_left" },
41 { mods="MOD4", key="l", action="snap_right" },
42 { mods="MOD4|SHFT", key="Return", action="quit" },
43 { mods="MOD4", key="1", action="workspace_goto", arg=1 },
44@@ -52,4 +61,4 @@ binds = {
45 { mods="MOD4|SHFT", key="7", action="workspace_moveto", arg=7 },
46 { mods="MOD4|SHFT", key="8", action="workspace_moveto", arg=8 },
47 { mods="MOD4|SHFT", key="9", action="workspace_moveto", arg=9 },
48-}
49+}
+2,
-0
1@@ -12,6 +12,8 @@ extern void kb_move_x(void* data, uint32_t time, uint32_t value, uint32_t state)
2 extern void kb_move_y(void* data, uint32_t time, uint32_t value, uint32_t state);
3 extern void kb_resize_width(void* data, uint32_t time, uint32_t value, uint32_t state);
4 extern void kb_resize_height(void* data, uint32_t time, uint32_t value, uint32_t state);
5+void snap_top_half(void*, uint32_t, uint32_t, uint32_t);
6+void snap_bottom_half(void*, uint32_t, uint32_t, uint32_t);
7 extern void snap_left_half(void* data, uint32_t time, uint32_t value, uint32_t state);
8 extern void snap_right_half(void* data, uint32_t time, uint32_t value, uint32_t state);
9 extern void center_window(void* data, uint32_t time, uint32_t value, uint32_t state);
+1,
-1
1@@ -76,4 +76,4 @@ struct wm {
2 uint8_t ws;
3 };
4
5-#endif /* TYPES_H */
6+#endif /* TYPES_H */
+105,
-18
1@@ -2,9 +2,11 @@
2 #include <luajit-2.1/lauxlib.h>
3 #include <luajit-2.1/lualib.h>
4 #include <xkbcommon/xkbcommon-keysyms.h>
5+#include <sys/wait.h>
6 #include <string.h>
7 #include <stdlib.h>
8 #include <stdio.h>
9+#include <unistd.h>
10
11 #include "include/types.h"
12 #include "include/slgro.h"
13@@ -14,31 +16,44 @@ struct bind *binds = NULL;
14 size_t nbinds = 0;
15
16 static char *spawn_args[128][2];
17+static char *autostart[128];
18+static size_t nautostart = 0;
19 static size_t nspawn = 0;
20
21-static uint32_t parse_mods(const char *s)
22+static uint32_t parse_mods
23+(const char *s)
24 {
25- uint32_t mods = 0;
26+ uint32_t mods = 0;
27 char buf[64];
28- strncpy(buf, s, sizeof(buf) - 1);
29- char *tok = strtok(buf, "|");
30- while (tok) {
31+
32+ if (!s) return 0;
33+
34+ strncpy(buf, s, sizeof(buf) - 1);
35+ buf[sizeof(buf) - 1] = '\0';
36+
37+ char *tok = strtok(buf, "|");
38+ while (tok) {
39+
40 if (!strcmp(tok, "MOD4")) mods |= SWC_MOD_LOGO;
41 else if (!strcmp(tok, "MOD1")) mods |= SWC_MOD_ALT;
42 else if (!strcmp(tok, "SHFT")) mods |= SWC_MOD_SHIFT;
43 else if (!strcmp(tok, "CTRL")) mods |= SWC_MOD_CTRL;
44 tok = strtok(NULL, "|");
45 }
46+
47 return mods;
48 }
49
50-static uint32_t parse_key(const char *s)
51+static uint32_t parse_key
52+(const char *s)
53 {
54 if (s[1] == '\0') {
55+
56 if (s[0] >= 'a' && s[0] <= 'z') return XKB_KEY_a + (s[0] - 'a');
57 if (s[0] >= '1' && s[0] <= '9') return XKB_KEY_1 + (s[0] - '1');
58 if (s[0] == '0') return XKB_KEY_0;
59 }
60+
61 if (!strcmp(s, "Return")) return XKB_KEY_Return;
62 if (!strcmp(s, "Tab")) return XKB_KEY_Tab;
63 if (!strcmp(s, "space")) return XKB_KEY_space;
64@@ -47,24 +62,31 @@ static uint32_t parse_key(const char *s)
65 if (!strcmp(s, "Up")) return XKB_KEY_Up;
66 if (!strcmp(s, "Down")) return XKB_KEY_Down;
67 fprintf(stderr, "slgro: sorry, unknown key >.< '%s'\n", s);
68- return XKB_KEY_VoidSymbol;
69+
70+ return XKB_KEY_VoidSymbol;
71 }
72
73-static void resolve_action(const char *action, const char *arg_str, int arg_int, struct bind *b)
74+static void resolve_action
75+(const char *action, const char *arg_str, int arg_int, struct bind *b)
76 {
77 b->type = SWC_BINDING_KEY;
78- if (!strcmp(action, "spawn")) {
79+
80+ if (!strcmp(action, "spawn")) {
81+
82 spawn_args[nspawn][0] = strdup(arg_str);
83 spawn_args[nspawn][1] = NULL;
84 b->arg.v = spawn_args[nspawn++];
85 b->fn = spawn;
86 }
87+
88 else if (!strcmp(action, "kill")) b->fn = kill_sel;
89 else if (!strcmp(action, "focus_next")) b->fn = focus_next;
90 else if (!strcmp(action, "fullscreen")) b->fn = fullscreen;
91- else if (!strcmp(action, "center")) b->fn = center_window;
92- else if (!strcmp(action, "snap_left")) b->fn = snap_left_half;
93- else if (!strcmp(action, "snap_right")) b->fn = snap_right_half;
94+ else if (!strcmp(action, "center")) b->fn = center_window;
95+ else if (!strcmp(action, "snap_top")) b->fn = snap_top_half;
96+ else if (!strcmp(action, "snap_bottom")) b->fn = snap_bottom_half;
97+ else if (!strcmp(action, "snap_left")) b->fn = snap_left_half;
98+ else if (!strcmp(action, "snap_right")) b->fn = snap_right_half;
99 else if (!strcmp(action, "quit")) b->fn = quit;
100 else if (!strcmp(action, "move_x")) { b->fn = kb_move_x; b->arg.i = arg_int; }
101 else if (!strcmp(action, "move_y")) { b->fn = kb_move_y; b->arg.i = arg_int; }
102@@ -75,7 +97,8 @@ static void resolve_action(const char *action, const char *arg_str, int arg_int,
103 else fprintf(stderr, "slgro: sorry, unknown action >.< '%s'\n", action);
104 }
105
106-void load_config(void)
107+void load_config
108+(void)
109 {
110 const char *home = getenv("HOME");
111 char path[256];
112@@ -95,7 +118,9 @@ void load_config(void)
113 luaL_openlibs(L);
114
115 if (luaL_dofile(L, path) != LUA_OK) {
116+
117 if (luaL_dofile(L, "/usr/share/slgro/config.lua") != LUA_OK) {
118+
119 fprintf(stderr, "slgro: %s\n", lua_tostring(L, -1));
120 fprintf(stderr, "slgro: using defaults :P\n");
121 lua_close(L);
122@@ -103,6 +128,31 @@ void load_config(void)
123 }
124 }
125
126+ lua_getglobal(L, "autostart");
127+
128+ if (lua_istable(L, -1)) {
129+
130+ size_t n = lua_objlen(L, -1);
131+
132+ for (size_t i = 1; i <= n && nautostart < 128; i++) {
133+
134+ lua_rawgeti(L, -1, i);
135+
136+ if (lua_isstring(L, -1)) {
137+
138+ autostart[nautostart] = strdup(lua_tostring(L, -1));
139+
140+ if (autostart[nautostart])
141+
142+ nautostart++;
143+ }
144+
145+ lua_pop(L, 1);
146+ }
147+ }
148+
149+ lua_pop(L, 1);
150+
151 lua_getglobal(L, "border_active");
152 if (lua_isnumber(L, -1)) cfg.border_col_active = (uint32_t)lua_tonumber(L, -1);
153 lua_pop(L, 1);
154@@ -128,21 +178,31 @@ void load_config(void)
155 lua_pop(L, 1);
156
157 lua_getglobal(L, "motion_throttle_hz");
158- if (lua_isnumber(L, -1)) cfg.motion_throttle_hz = (uint32_t)lua_tonumber(L, -1);
159+ if (lua_isnumber(L, -1)) cfg.motion_throttle_hz = (uint32_t)lua_tonumber(L, -1);
160 lua_pop(L, 1);
161
162 lua_getglobal(L, "binds");
163+
164 if (!lua_istable(L, -1)) {
165+
166 fprintf(stderr, "slgro: couldn't find the binds table :<\n");
167 lua_close(L);
168 return;
169 }
170
171 int binds_index = lua_gettop(L);
172- size_t n = lua_objlen(L, binds_index);
173- binds = calloc(n, sizeof(struct bind));
174+ size_t n = lua_objlen(L, binds_index);
175+ binds = calloc(n, sizeof(struct bind));
176+
177+ if (n && !binds) {
178+
179+ fprintf(stderr, "slgro: couldn't allocate bindings :<\n");
180+ lua_close(L);
181+ return;
182+ }
183
184 for (size_t i = 1; i <= n; i++) {
185+
186 lua_rawgeti(L, binds_index, i);
187 struct bind b = {0};
188
189@@ -164,9 +224,36 @@ void load_config(void)
190 lua_pop(L, 1);
191
192 if (action) resolve_action(action, arg_str, arg_int, &b);
193- binds[nbinds++] = b;
194+ if (b.fn) binds[nbinds++] = b;
195 lua_pop(L, 1);
196 }
197
198- lua_close(L); /* man i love lua :3 */
199+ lua_close(L);
200+}
201+
202+void run_autostart
203+(void)
204+{
205+ for (size_t i = 0; i < nautostart; i++) {
206+
207+ pid_t pid = fork();
208+
209+ if (pid == 0) {
210+
211+ setsid();
212+
213+ if (fork() == 0) {
214+
215+ execl("/bin/sh", "sh", "-c", autostart[i], (char *)NULL);
216+ _exit(127);
217+ }
218+
219+ _exit(0);
220+ }
221+
222+ else if (pid > 0) {
223+
224+ waitpid(pid, NULL, 0);
225+ }
226+ }
227 }
+154,
-65
1@@ -15,6 +15,7 @@ extern struct config cfg;
2 extern struct bind *binds;
3 extern size_t nbinds;
4 extern void load_config(void);
5+extern void run_autostart(void);
6
7 #include "include/types.h"
8 #include "include/util.h"
9@@ -43,20 +44,23 @@ static void sync_window_visibility(void);
10 union arg* a = (data)
11
12 /* read geometry from client window; returns true if successful */
13-static bool get_geometry(struct client *c, struct swc_rectangle *geom)
14+static bool get_geometry
15+(struct client *c, struct swc_rectangle *geom)
16 {
17 if (!c || !c->win)
18- return false;
19+ return false;
20
21 return swc_window_get_geometry(c->win, geom);
22 }
23
24 /* adjust geometry fields and write back */
25-static void adjust_geom(struct client *c, int dx, int dy, int dw, int dh)
26+static void adjust_geom
27+(struct client *c, int dx, int dy, int dw, int dh)
28 {
29 struct swc_rectangle geom;
30- if (!get_geometry(c, &geom)) return;
31-
32+ if (!get_geometry(c, &geom))
33+ return;
34+
35 geom.x += dx;
36 geom.y += dy;
37
38@@ -79,54 +83,65 @@ struct swc_screen_handler screen_handler = {
39 .destroy = on_screen_destroy,
40 };
41
42-static struct client* get_focus_candidate(struct screen* s)
43+static struct client* get_focus_candidate
44+(struct screen* s)
45 {
46 struct client* c = first_client(s);
47 if (!c && s) c = first_client(NULL);
48- return c;
49+
50+ return c;
51 }
52
53-static void focus(struct client* c)
54+static void focus
55+(struct client* c)
56 {
57 if (wm.sel_client && wm.sel_client != c) {
58- swc_window_set_border(wm.sel_client->win, cfg.border_col_normal, cfg.border_width, cfg.border_col_normal_outer, cfg.border_width_outer);
59+
60+ swc_window_set_border(wm.sel_client->win, cfg.border_col_normal, cfg.border_width, cfg.border_col_normal_outer, cfg.border_width_outer);
61 }
62+
63 if (c) {
64- swc_window_set_border(c->win, cfg.border_col_active, cfg.border_width, cfg.border_col_active_outer, cfg.border_width_outer);
65+
66+ swc_window_set_border(c->win, cfg.border_col_active, cfg.border_width, cfg.border_col_active_outer, cfg.border_width_outer);
67 }
68
69 swc_window_focus(c ? c->win : NULL);
70 wm.sel_client = c;
71 }
72
73-static struct client* first_client(struct screen* s)
74+static struct client* first_client
75+(struct screen* s)
76 {
77 struct client* c;
78
79 wl_list_for_each(c, &wm.clients, link) {
80+
81 if (is_ws_client(c, s))
82- return c;
83+ return c;
84 }
85
86 return NULL;
87 }
88
89-static bool is_ws_client(const struct client* c, const struct screen* s)
90+static bool is_ws_client
91+(const struct client* c, const struct screen* s)
92 {
93 return c && c->ws == wm.ws && (!s || c->scr == s);
94 }
95
96-static void on_screen_destroy(void* data)
97+static void on_screen_destroy
98+(void* data)
99 {
100 struct screen* s = data;
101
102 if (!s)
103- return;
104+ return;
105
106 wl_list_remove(&s->link);
107
108 if (wm.sel_screen == s) {
109- wm.sel_screen = wl_list_empty(&wm.screens)
110+
111+ wm.sel_screen = wl_list_empty(&wm.screens)
112 ? NULL
113 : wl_container_of(wm.screens.next, wm.sel_screen, link);
114 }
115@@ -134,10 +149,12 @@ static void on_screen_destroy(void* data)
116 free(s);
117 }
118
119-static void on_win_destroy(void* data)
120+static void on_win_destroy
121+(void* data)
122 {
123 struct client* c = data;
124- if (!c) return;
125+ if (!c)
126+ return;
127
128 if (wm.sel_client == c)
129 wm.sel_client = NULL;
130@@ -148,7 +165,8 @@ static void on_win_destroy(void* data)
131 focus(get_focus_candidate(wm.sel_screen));
132 }
133
134-static void on_win_entered(void* data)
135+static void on_win_entered
136+(void* data)
137 {
138 struct client* c = data;
139 if (!is_ws_client(c, NULL))
140@@ -157,13 +175,14 @@ static void on_win_entered(void* data)
141 focus(c);
142 }
143
144-static void setup(void)
145+static void setup
146+(void)
147 {
148 /* display */
149 load_config();
150 wm.dpy = wl_display_create();
151 if (!wm.dpy)
152- die(EXIT_FAILURE, "wl_display_create failed");
153+ die(EXIT_FAILURE, "wl_display_create failed");
154
155 /* variables */
156 wl_list_init(&wm.screens);
157@@ -176,7 +195,7 @@ static void setup(void)
158 /* event loop */
159 wm.ev_loop = wl_display_get_event_loop(wm.dpy);
160 if (!swc_initialize(wm.dpy, wm.ev_loop, &manager))
161- die(EXIT_FAILURE, "swc_initialize failed\n");
162+ die(EXIT_FAILURE, "swc_initialize failed\n");
163
164 setup_binds();
165
166@@ -184,43 +203,51 @@ static void setup(void)
167 const char* sock;
168 sock = wl_display_add_socket_auto(wm.dpy);
169 if (!sock)
170- die(EXIT_FAILURE, "wl_display_add_socket_auto failed\n");
171+ die(EXIT_FAILURE, "wl_display_add_socket_auto failed\n");
172
173 setenv("WAYLAND_DISPLAY", sock, 1);
174 _log(stderr, "WAYLAND_DISPLAY=%s\n", sock);
175
176+ run_autostart();
177+
178 /* signals */
179 signal(SIGINT, sig_handler);
180 signal(SIGTERM, sig_handler);
181 signal(SIGQUIT, sig_handler);
182 }
183
184-static void setup_binds(void)
185+static void setup_binds
186+(void)
187 {
188 for (size_t i = 0; i < nbinds; i++) {
189- const struct bind* b = &binds[i];
190+
191+ const struct bind* b = &binds[i];
192 swc_add_binding(b->type, b->mods, b->ksym, b->fn, (void*)&b->arg);
193 }
194 }
195
196-static void sync_window_visibility(void)
197+static void sync_window_visibility
198+(void)
199 {
200 struct client* c;
201
202 wl_list_for_each(c, &wm.clients, link) {
203 if (c->ws == wm.ws)
204- swc_window_show(c->win);
205- else
206+ swc_window_show(c->win);
207+
208+ else
209 swc_window_hide(c->win);
210 }
211 }
212
213 /* focus next/prev helpers */
214-static void focus_walk_direction(bool forward)
215+static void focus_walk_direction
216+(bool forward)
217 {
218 if (wl_list_empty(&wm.clients)) return;
219
220 if (!is_ws_client(wm.sel_client, wm.sel_screen)) {
221+
222 focus(get_focus_candidate(wm.sel_screen));
223 return;
224 }
225@@ -239,24 +266,30 @@ static void focus_walk_direction(bool forward)
226 if (it == &wm.clients) break;
227
228 c = wl_container_of(it, c, link);
229- if (is_ws_client(c, wm.sel_screen)) {
230+
231+ if (is_ws_client(c, wm.sel_screen)) {
232+
233 focus(c);
234 return;
235 }
236
237 it = forward ? it->next : it->prev;
238- } while (it != start);
239+ }
240+
241+ while (it != start);
242
243 focus(get_focus_candidate(wm.sel_screen));
244 }
245
246-void focus_next(void* data, uint32_t time, uint32_t value, uint32_t state)
247+void focus_next
248+(void* data, uint32_t time, uint32_t value, uint32_t state)
249 {
250 (void)data; BIND_EVENT(time, value, state);
251 focus_walk_direction(true);
252 }
253
254-void kill_sel(void* data, uint32_t time, uint32_t value, uint32_t state)
255+void kill_sel
256+(void* data, uint32_t time, uint32_t value, uint32_t state)
257 {
258 (void)data; BIND_EVENT(time, value, state);
259
260@@ -264,28 +297,35 @@ void kill_sel(void* data, uint32_t time, uint32_t value, uint32_t state)
261 swc_window_close(wm.sel_client->win);
262 }
263
264-void fullscreen(void* data, uint32_t time, uint32_t value, uint32_t state)
265+void fullscreen
266+(void* data, uint32_t time, uint32_t value, uint32_t state)
267 {
268 (void)data; BIND_EVENT(time, value, state);
269- if (!wm.sel_client) return;
270+
271+ if (!wm.sel_client)
272+ return;
273
274 struct client *c = wm.sel_client;
275 struct swc_rectangle geom;
276
277 if (c->fullscreen) {
278+
279 c->fullscreen = false;
280 swc_window_set_stacked(c->win);
281
282 if (c->w > 0 && c->h > 0) {
283+
284 geom = (struct swc_rectangle){ c->x, c->y, c->w, c->h };
285 swc_window_set_geometry(c->win, &geom);
286 }
287+
288 return;
289 }
290
291 if (!c->scr || !c->scr->scr) return;
292
293 if (get_geometry(c, &geom)) {
294+
295 c->x = geom.x;
296 c->y = geom.y;
297 c->w = geom.width;
298@@ -296,52 +336,63 @@ void fullscreen(void* data, uint32_t time, uint32_t value, uint32_t state)
299 swc_window_set_fullscreen(c->win, c->scr->scr);
300 }
301
302-void kb_move_x(void* data, uint32_t time, uint32_t value, uint32_t state)
303+void kb_move_x
304+(void* data, uint32_t time, uint32_t value, uint32_t state)
305 {
306 BIND_ACTION(data, time, value, state);
307 adjust_geom(wm.sel_client, a->i, 0, 0, 0);
308 }
309
310-void kb_move_y(void* data, uint32_t time, uint32_t value, uint32_t state)
311+void kb_move_y
312+(void* data, uint32_t time, uint32_t value, uint32_t state)
313 {
314 BIND_ACTION(data, time, value, state);
315 adjust_geom(wm.sel_client, 0, a->i, 0, 0);
316 }
317
318-void kb_resize_width(void* data, uint32_t time, uint32_t value, uint32_t state)
319+void kb_resize_width
320+(void* data, uint32_t time, uint32_t value, uint32_t state)
321 {
322 BIND_ACTION(data, time, value, state);
323 adjust_geom(wm.sel_client, 0, 0, a->i, 0);
324 }
325
326-void kb_resize_height(void* data, uint32_t time, uint32_t value, uint32_t state)
327+void kb_resize_height
328+(void* data, uint32_t time, uint32_t value, uint32_t state)
329 {
330 BIND_ACTION(data, time, value, state);
331 adjust_geom(wm.sel_client, 0, 0, 0, a->i);
332 }
333
334-static void apply_grid_geometry(struct client *c, float x_frac, float w_frac)
335+static void apply_grid_geometry
336+(struct client *c, float x_frac, float y_frac, float w_frac, float h_frac)
337 {
338- if (!c || !c->scr || !c->scr->scr) return;
339+ if (!c || !c->scr || !c->scr->scr)
340+ return;
341
342 struct swc_rectangle geom;
343 struct swc_rectangle *ug = &c->scr->scr->usable_geometry;
344
345 geom.x = ug->x + (ug->width * x_frac);
346- geom.y = ug->y;
347+ geom.y = ug->y + (ug->height * y_frac);
348 geom.width = ug->width * w_frac;
349- geom.height = ug->height;
350+ geom.height = ug->height * h_frac;
351
352 swc_window_set_geometry(c->win, &geom);
353 }
354
355-void center_window(void* data, uint32_t time, uint32_t value, uint32_t state)
356+void center_window
357+(void* data, uint32_t time, uint32_t value, uint32_t state)
358 {
359 (void)data; BIND_EVENT(time, value, state);
360- if (!wm.sel_client->scr || !wm.sel_client->scr->scr) return;
361+
362+ if (!wm.sel_client || !wm.sel_client->scr || !wm.sel_client->scr->scr)
363+ return;
364
365 struct swc_rectangle geom;
366- if (!get_geometry(wm.sel_client, &geom)) return;
367+
368+ if (!get_geometry(wm.sel_client, &geom))
369+ return;
370
371 struct swc_rectangle *ug = &wm.sel_client->scr->scr->usable_geometry;
372 geom.x = ug->x + (ug->width - geom.width) / 2;
373@@ -350,22 +401,41 @@ void center_window(void* data, uint32_t time, uint32_t value, uint32_t state)
374 swc_window_set_geometry(wm.sel_client->win, &geom);
375 }
376
377-void snap_left_half(void* data, uint32_t time, uint32_t value, uint32_t state)
378+void snap_top_half
379+(void* data, uint32_t time, uint32_t value, uint32_t state)
380+{
381+ (void)data; BIND_EVENT(time, value, state);
382+ apply_grid_geometry(wm.sel_client, 0.0f, 0.0f, 1.0f, 0.5f);
383+}
384+
385+void snap_bottom_half
386+(void* data, uint32_t time, uint32_t value, uint32_t state)
387+{
388+ (void)data; BIND_EVENT(time, value, state);
389+ apply_grid_geometry(wm.sel_client, 0.0f, 0.5f, 1.0f, 0.5f);
390+}
391+
392+void snap_left_half
393+(void* data, uint32_t time, uint32_t value, uint32_t state)
394 {
395 (void)data; BIND_EVENT(time, value, state);
396- apply_grid_geometry(wm.sel_client, 0.0f, 0.5f);
397+ apply_grid_geometry(wm.sel_client, 0.0f, 0.0f, 0.5f, 1.0f);
398 }
399
400-void snap_right_half(void* data, uint32_t time, uint32_t value, uint32_t state)
401+void snap_right_half
402+(void* data, uint32_t time, uint32_t value, uint32_t state)
403 {
404 (void)data; BIND_EVENT(time, value, state);
405- apply_grid_geometry(wm.sel_client, 0.5f, 0.5f);
406+ apply_grid_geometry(wm.sel_client, 0.5f, 0.0f, 0.5f, 1.0f);
407 }
408
409-void new_screen(struct swc_screen* scr)
410+void new_screen
411+(struct swc_screen* scr)
412 {
413 struct screen* s = calloc(1, sizeof(*s));
414- if (!s) die(EXIT_FAILURE, "new screen calloc failed");
415+
416+ if (!s)
417+ die(EXIT_FAILURE, "new screen calloc failed");
418
419 s->scr = scr;
420 wl_list_insert(&wm.screens, &s->link);
421@@ -376,10 +446,13 @@ void new_screen(struct swc_screen* scr)
422 _log(stderr, "new_screen=%p\n", (void*)scr);
423 }
424
425-void new_window(struct swc_window* win)
426+void new_window
427+(struct swc_window* win)
428 {
429 struct client* c = calloc(1, sizeof(*c));
430- if (!c) die(EXIT_FAILURE, "calloc client failed");
431+
432+ if (!c)
433+ die(EXIT_FAILURE, "calloc client failed");
434
435 win->motion_throttle_ms = 1000 / cfg.motion_throttle_hz;
436 win->min_width = 1;
437@@ -394,7 +467,8 @@ void new_window(struct swc_window* win)
438 swc_window_set_stacked(win);
439
440 int32_t cx = 0, cy = 0;
441- if (swc_cursor_position(&cx, &cy))
442+
443+ if (swc_cursor_position(&cx, &cy))
444 swc_window_set_position(win, cx / 256, cy / 256);
445
446 swc_window_show(win);
447@@ -403,43 +477,56 @@ void new_window(struct swc_window* win)
448 _log(stderr, "new_window=%p\n", (void*)win);
449 }
450
451-void new_device(struct libinput_device* dev)
452+void new_device
453+(struct libinput_device* dev)
454 {
455 (void)dev;
456 }
457
458-void quit(void* data, uint32_t time, uint32_t value, uint32_t state)
459+void quit
460+(void* data, uint32_t time, uint32_t value, uint32_t state)
461 {
462 (void)data; BIND_EVENT(time, value, state);
463 wl_display_terminate(wm.dpy);
464 }
465
466-void spawn(void* data, uint32_t time, uint32_t value, uint32_t state)
467+void spawn
468+(void* data, uint32_t time, uint32_t value, uint32_t state)
469 {
470 BIND_EVENT(time, value, state);
471
472 pid_t pid = fork();
473- if (pid == 0) {
474+
475+ if (pid == 0) {
476+
477 setsid();
478- if (fork() == 0) {
479+
480+ if (fork() == 0) {
481+
482 union arg* a = data;
483 char* const* cmd = (char* const*)a->v;
484
485 execvp(cmd[0], cmd);
486 _exit(127);
487 }
488+
489 _exit(0);
490- } else if (pid > 0) {
491+ }
492+
493+ else if (pid > 0) {
494+
495 waitpid(pid, NULL, 0);
496 }
497 }
498
499-void workspace_goto(void* data, uint32_t time, uint32_t value, uint32_t state)
500+void workspace_goto
501+(void* data, uint32_t time, uint32_t value, uint32_t state)
502 {
503 union arg* a = data;
504 BIND_EVENT(time, value, state);
505
506- if (a->ui < 1 || a->ui > 9 || a->ui == wm.ws) return;
507+ if (a->ui < 1 || a->ui > 9 || a->ui == wm.ws)
508+ return;
509
510 wm.ws = a->ui;
511 sync_window_visibility();
512@@ -447,7 +534,8 @@ void workspace_goto(void* data, uint32_t time, uint32_t value, uint32_t state)
513 focus(get_focus_candidate(wm.sel_screen));
514 }
515
516-void workspace_moveto(void* data, uint32_t time, uint32_t value, uint32_t state)
517+void workspace_moveto
518+(void* data, uint32_t time, uint32_t value, uint32_t state)
519 {
520 BIND_ACTION(data, time, value, state);
521 if (a->ui < 1 || a->ui > 9 || wm.sel_client->ws == a->ui) return;
522@@ -457,7 +545,8 @@ void workspace_moveto(void* data, uint32_t time, uint32_t value, uint32_t state)
523
524 if (c->ws == wm.ws)
525 swc_window_show(c->win);
526- else
527+
528+ else
529 swc_window_hide(c->win);
530
531 focus(get_focus_candidate(wm.sel_screen));
+6,
-3
1@@ -5,7 +5,8 @@
2 #include "include/util.h"
3 #include "include/slgro.h"
4
5-void die(int ret, const char* fmt, ...)
6+void die
7+(int ret, const char* fmt, ...)
8 {
9 va_list ap;
10
11@@ -21,7 +22,8 @@ void die(int ret, const char* fmt, ...)
12 exit(ret);
13 }
14
15-void _log(FILE* fd, const char* fmt, ...)
16+void _log
17+(FILE* fd, const char* fmt, ...)
18 {
19 va_list ap;
20
21@@ -35,7 +37,8 @@ void _log(FILE* fd, const char* fmt, ...)
22 fflush(fd);
23 }
24
25-void sig_handler(int s)
26+void sig_handler
27+(int s)
28 {
29 (void)s;
30