dwm-cfacts-vanitygaps-6.2.diff - sites - public wiki contents of suckless.org
(HTM) git clone git://git.suckless.org/sites
(DIR) Log
(DIR) Files
(DIR) Refs
---
dwm-cfacts-vanitygaps-6.2.diff (26794B)
---
1 From 051e4de72079bb0b8e50d2faa61b9a0ef36434b5 Mon Sep 17 00:00:00 2001
2 From: bakkeby <bakkeby@gmail.com>
3 Date: Fri, 8 May 2020 16:51:00 +0200
4 Subject: [PATCH 2/2] vanitygaps - adds gaps to layouts
5
6 This patch differentiates between inner and outer gaps as well as
7 horizontal and vertical gaps.
8
9 The logic of these layouts also aims to be pixel perfect by ensuring
10 an even split of the available space and re-distributing the remainder
11 among the available clients.
12 ---
13 config.def.h | 38 ++-
14 dwm.c | 43 +--
15 vanitygaps.c | 822 +++++++++++++++++++++++++++++++++++++++++++++++++++
16 3 files changed, 867 insertions(+), 36 deletions(-)
17 create mode 100644 vanitygaps.c
18
19 diff --git a/config.def.h b/config.def.h
20 index 83910c1..91a9cfc 100644
21 --- a/config.def.h
22 +++ b/config.def.h
23 @@ -3,6 +3,11 @@
24 /* appearance */
25 static const unsigned int borderpx = 1; /* border pixel of windows */
26 static const unsigned int snap = 32; /* snap pixel */
27 +static const unsigned int gappih = 20; /* horiz inner gap between windows */
28 +static const unsigned int gappiv = 10; /* vert inner gap between windows */
29 +static const unsigned int gappoh = 10; /* horiz outer gap between windows and screen edge */
30 +static const unsigned int gappov = 30; /* vert outer gap between windows and screen edge */
31 +static int smartgaps = 0; /* 1 means no outer gap when there is only one window */
32 static const int showbar = 1; /* 0 means no bar */
33 static const int topbar = 1; /* 0 means bottom bar */
34 static const char *fonts[] = { "monospace:size=10" };
35 @@ -36,11 +41,26 @@ static const float mfact = 0.55; /* factor of master area size [0.05..0.95]
36 static const int nmaster = 1; /* number of clients in master area */
37 static const int resizehints = 1; /* 1 means respect size hints in tiled resizals */
38
39 +#define FORCE_VSPLIT 1 /* nrowgrid layout: force two clients to always split vertically */
40 +#include "vanitygaps.c"
41 +
42 static const Layout layouts[] = {
43 /* symbol arrange function */
44 { "[]=", tile }, /* first entry is default */
45 - { "><>", NULL }, /* no layout function means floating behavior */
46 { "[M]", monocle },
47 + { "[@]", spiral },
48 + { "[\\]", dwindle },
49 + { "H[]", deck },
50 + { "TTT", bstack },
51 + { "===", bstackhoriz },
52 + { "HHH", grid },
53 + { "###", nrowgrid },
54 + { "---", horizgrid },
55 + { ":::", gaplessgrid },
56 + { "|M|", centeredmaster },
57 + { ">M>", centeredfloatingmaster },
58 + { "><>", NULL }, /* no layout function means floating behavior */
59 + { NULL, NULL },
60 };
61
62 /* key definitions */
63 @@ -74,6 +94,22 @@ static Key keys[] = {
64 { MODKEY|ShiftMask, XK_l, setcfact, {.f = -0.25} },
65 { MODKEY|ShiftMask, XK_o, setcfact, {.f = 0.00} },
66 { MODKEY, XK_Return, zoom, {0} },
67 + { MODKEY|Mod4Mask, XK_u, incrgaps, {.i = +1 } },
68 + { MODKEY|Mod4Mask|ShiftMask, XK_u, incrgaps, {.i = -1 } },
69 + { MODKEY|Mod4Mask, XK_i, incrigaps, {.i = +1 } },
70 + { MODKEY|Mod4Mask|ShiftMask, XK_i, incrigaps, {.i = -1 } },
71 + { MODKEY|Mod4Mask, XK_o, incrogaps, {.i = +1 } },
72 + { MODKEY|Mod4Mask|ShiftMask, XK_o, incrogaps, {.i = -1 } },
73 + { MODKEY|Mod4Mask, XK_6, incrihgaps, {.i = +1 } },
74 + { MODKEY|Mod4Mask|ShiftMask, XK_6, incrihgaps, {.i = -1 } },
75 + { MODKEY|Mod4Mask, XK_7, incrivgaps, {.i = +1 } },
76 + { MODKEY|Mod4Mask|ShiftMask, XK_7, incrivgaps, {.i = -1 } },
77 + { MODKEY|Mod4Mask, XK_8, incrohgaps, {.i = +1 } },
78 + { MODKEY|Mod4Mask|ShiftMask, XK_8, incrohgaps, {.i = -1 } },
79 + { MODKEY|Mod4Mask, XK_9, incrovgaps, {.i = +1 } },
80 + { MODKEY|Mod4Mask|ShiftMask, XK_9, incrovgaps, {.i = -1 } },
81 + { MODKEY|Mod4Mask, XK_0, togglegaps, {0} },
82 + { MODKEY|Mod4Mask|ShiftMask, XK_0, defaultgaps, {0} },
83 { MODKEY, XK_Tab, view, {0} },
84 { MODKEY|ShiftMask, XK_c, killclient, {0} },
85 { MODKEY, XK_t, setlayout, {.v = &layouts[0]} },
86 diff --git a/dwm.c b/dwm.c
87 index 5592c57..7d503cb 100644
88 --- a/dwm.c
89 +++ b/dwm.c
90 @@ -120,6 +120,10 @@ struct Monitor {
91 int by; /* bar geometry */
92 int mx, my, mw, mh; /* screen size */
93 int wx, wy, ww, wh; /* window area */
94 + int gappih; /* horizontal gap between windows */
95 + int gappiv; /* vertical gap between windows */
96 + int gappoh; /* horizontal outer gaps */
97 + int gappov; /* vertical outer gaps */
98 unsigned int seltags;
99 unsigned int sellt;
100 unsigned int tagset[2];
101 @@ -210,7 +214,6 @@ static void sigchld(int unused);
102 static void spawn(const Arg *arg);
103 static void tag(const Arg *arg);
104 static void tagmon(const Arg *arg);
105 -static void tile(Monitor *);
106 static void togglebar(const Arg *arg);
107 static void togglefloating(const Arg *arg);
108 static void toggletag(const Arg *arg);
109 @@ -640,6 +643,10 @@ createmon(void)
110 m->nmaster = nmaster;
111 m->showbar = showbar;
112 m->topbar = topbar;
113 + m->gappih = gappih;
114 + m->gappiv = gappiv;
115 + m->gappoh = gappoh;
116 + m->gappov = gappov;
117 m->lt[0] = &layouts[0];
118 m->lt[1] = &layouts[1 % LENGTH(layouts)];
119 strncpy(m->ltsymbol, layouts[0].symbol, sizeof m->ltsymbol);
120 @@ -1691,40 +1698,6 @@ tagmon(const Arg *arg)
121 sendmon(selmon->sel, dirtomon(arg->i));
122 }
123
124 -void
125 -tile(Monitor *m)
126 -{
127 - unsigned int i, n, h, mw, my, ty;
128 - float mfacts = 0, sfacts = 0;
129 - Client *c;
130 -
131 - for (n = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), n++) {
132 - if (n < m->nmaster)
133 - mfacts += c->cfact;
134 - else
135 - sfacts += c->cfact;
136 - }
137 - if (n == 0)
138 - return;
139 -
140 - if (n > m->nmaster)
141 - mw = m->nmaster ? m->ww * m->mfact : 0;
142 - else
143 - mw = m->ww;
144 - for (i = my = ty = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), i++)
145 - if (i < m->nmaster) {
146 - h = (m->wh - my) * (c->cfact / mfacts);
147 - resize(c, m->wx, m->wy + my, mw - (2*c->bw), h - (2*c->bw), 0);
148 - my += HEIGHT(c);
149 - mfacts -= c->cfact;
150 - } else {
151 - h = (m->wh - ty) * (c->cfact / sfacts);
152 - resize(c, m->wx + mw, m->wy + ty, m->ww - mw - (2*c->bw), h - (2*c->bw), 0);
153 - ty += HEIGHT(c);
154 - sfacts -= c->cfact;
155 - }
156 -}
157 -
158 void
159 togglebar(const Arg *arg)
160 {
161 diff --git a/vanitygaps.c b/vanitygaps.c
162 new file mode 100644
163 index 0000000..1a816b6
164 --- /dev/null
165 +++ b/vanitygaps.c
166 @@ -0,0 +1,822 @@
167 +/* Key binding functions */
168 +static void defaultgaps(const Arg *arg);
169 +static void incrgaps(const Arg *arg);
170 +static void incrigaps(const Arg *arg);
171 +static void incrogaps(const Arg *arg);
172 +static void incrohgaps(const Arg *arg);
173 +static void incrovgaps(const Arg *arg);
174 +static void incrihgaps(const Arg *arg);
175 +static void incrivgaps(const Arg *arg);
176 +static void togglegaps(const Arg *arg);
177 +/* Layouts (delete the ones you do not need) */
178 +static void bstack(Monitor *m);
179 +static void bstackhoriz(Monitor *m);
180 +static void centeredmaster(Monitor *m);
181 +static void centeredfloatingmaster(Monitor *m);
182 +static void deck(Monitor *m);
183 +static void dwindle(Monitor *m);
184 +static void fibonacci(Monitor *m, int s);
185 +static void grid(Monitor *m);
186 +static void nrowgrid(Monitor *m);
187 +static void spiral(Monitor *m);
188 +static void tile(Monitor *m);
189 +/* Internals */
190 +static void getgaps(Monitor *m, int *oh, int *ov, int *ih, int *iv, unsigned int *nc);
191 +static void getfacts(Monitor *m, int msize, int ssize, float *mf, float *sf, int *mr, int *sr);
192 +static void setgaps(int oh, int ov, int ih, int iv);
193 +
194 +/* Settings */
195 +#if !PERTAG_PATCH
196 +static int enablegaps = 1;
197 +#endif // PERTAG_PATCH
198 +
199 +void
200 +setgaps(int oh, int ov, int ih, int iv)
201 +{
202 + if (oh < 0) oh = 0;
203 + if (ov < 0) ov = 0;
204 + if (ih < 0) ih = 0;
205 + if (iv < 0) iv = 0;
206 +
207 + selmon->gappoh = oh;
208 + selmon->gappov = ov;
209 + selmon->gappih = ih;
210 + selmon->gappiv = iv;
211 + arrange(selmon);
212 +}
213 +
214 +void
215 +togglegaps(const Arg *arg)
216 +{
217 + #if PERTAG_PATCH
218 + selmon->pertag->enablegaps[selmon->pertag->curtag] = !selmon->pertag->enablegaps[selmon->pertag->curtag];
219 + #else
220 + enablegaps = !enablegaps;
221 + #endif // PERTAG_PATCH
222 + arrange(NULL);
223 +}
224 +
225 +void
226 +defaultgaps(const Arg *arg)
227 +{
228 + setgaps(gappoh, gappov, gappih, gappiv);
229 +}
230 +
231 +void
232 +incrgaps(const Arg *arg)
233 +{
234 + setgaps(
235 + selmon->gappoh + arg->i,
236 + selmon->gappov + arg->i,
237 + selmon->gappih + arg->i,
238 + selmon->gappiv + arg->i
239 + );
240 +}
241 +
242 +void
243 +incrigaps(const Arg *arg)
244 +{
245 + setgaps(
246 + selmon->gappoh,
247 + selmon->gappov,
248 + selmon->gappih + arg->i,
249 + selmon->gappiv + arg->i
250 + );
251 +}
252 +
253 +void
254 +incrogaps(const Arg *arg)
255 +{
256 + setgaps(
257 + selmon->gappoh + arg->i,
258 + selmon->gappov + arg->i,
259 + selmon->gappih,
260 + selmon->gappiv
261 + );
262 +}
263 +
264 +void
265 +incrohgaps(const Arg *arg)
266 +{
267 + setgaps(
268 + selmon->gappoh + arg->i,
269 + selmon->gappov,
270 + selmon->gappih,
271 + selmon->gappiv
272 + );
273 +}
274 +
275 +void
276 +incrovgaps(const Arg *arg)
277 +{
278 + setgaps(
279 + selmon->gappoh,
280 + selmon->gappov + arg->i,
281 + selmon->gappih,
282 + selmon->gappiv
283 + );
284 +}
285 +
286 +void
287 +incrihgaps(const Arg *arg)
288 +{
289 + setgaps(
290 + selmon->gappoh,
291 + selmon->gappov,
292 + selmon->gappih + arg->i,
293 + selmon->gappiv
294 + );
295 +}
296 +
297 +void
298 +incrivgaps(const Arg *arg)
299 +{
300 + setgaps(
301 + selmon->gappoh,
302 + selmon->gappov,
303 + selmon->gappih,
304 + selmon->gappiv + arg->i
305 + );
306 +}
307 +
308 +void
309 +getgaps(Monitor *m, int *oh, int *ov, int *ih, int *iv, unsigned int *nc)
310 +{
311 + unsigned int n, oe, ie;
312 + #if PERTAG_PATCH
313 + oe = ie = selmon->pertag->enablegaps[selmon->pertag->curtag];
314 + #else
315 + oe = ie = enablegaps;
316 + #endif // PERTAG_PATCH
317 + Client *c;
318 +
319 + for (n = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), n++);
320 + if (smartgaps && n == 1) {
321 + oe = 0; // outer gaps disabled when only one client
322 + }
323 +
324 + *oh = m->gappoh*oe; // outer horizontal gap
325 + *ov = m->gappov*oe; // outer vertical gap
326 + *ih = m->gappih*ie; // inner horizontal gap
327 + *iv = m->gappiv*ie; // inner vertical gap
328 + *nc = n; // number of clients
329 +}
330 +
331 +void
332 +getfacts(Monitor *m, int msize, int ssize, float *mf, float *sf, int *mr, int *sr)
333 +{
334 + unsigned int n;
335 + float mfacts = 0, sfacts = 0;
336 + int mtotal = 0, stotal = 0;
337 + Client *c;
338 +
339 + for (n = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), n++)
340 + if (n < m->nmaster)
341 + mfacts += c->cfact;
342 + else
343 + sfacts += c->cfact;
344 +
345 + for (n = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), n++)
346 + if (n < m->nmaster)
347 + mtotal += msize * (c->cfact / mfacts);
348 + else
349 + stotal += ssize * (c->cfact / sfacts);
350 +
351 + *mf = mfacts; // total factor of master area
352 + *sf = sfacts; // total factor of stack area
353 + *mr = msize - mtotal; // the remainder (rest) of pixels after a cfacts master split
354 + *sr = ssize - stotal; // the remainder (rest) of pixels after a cfacts stack split
355 +}
356 +
357 +/***
358 + * Layouts
359 + */
360 +
361 +/*
362 + * Bottomstack layout + gaps
363 + * https://dwm.suckless.org/patches/bottomstack/
364 + */
365 +static void
366 +bstack(Monitor *m)
367 +{
368 + unsigned int i, n;
369 + int oh, ov, ih, iv;
370 + int mx = 0, my = 0, mh = 0, mw = 0;
371 + int sx = 0, sy = 0, sh = 0, sw = 0;
372 + float mfacts, sfacts;
373 + int mrest, srest;
374 + Client *c;
375 +
376 + getgaps(m, &oh, &ov, &ih, &iv, &n);
377 + if (n == 0)
378 + return;
379 +
380 + sx = mx = m->wx + ov;
381 + sy = my = m->wy + oh;
382 + sh = mh = m->wh - 2*oh;
383 + mw = m->ww - 2*ov - iv * (MIN(n, m->nmaster) - 1);
384 + sw = m->ww - 2*ov - iv * (n - m->nmaster - 1);
385 +
386 + if (m->nmaster && n > m->nmaster) {
387 + sh = (mh - ih) * (1 - m->mfact);
388 + mh = mh - ih - sh;
389 + sx = mx;
390 + sy = my + mh + ih;
391 + }
392 +
393 + getfacts(m, mw, sw, &mfacts, &sfacts, &mrest, &srest);
394 +
395 + for (i = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), i++) {
396 + if (i < m->nmaster) {
397 + resize(c, mx, my, mw * (c->cfact / mfacts) + (i < mrest ? 1 : 0) - (2*c->bw), mh - (2*c->bw), 0);
398 + mx += WIDTH(c) + iv;
399 + } else {
400 + resize(c, sx, sy, sw * (c->cfact / sfacts) + ((i - m->nmaster) < srest ? 1 : 0) - (2*c->bw), sh - (2*c->bw), 0);
401 + sx += WIDTH(c) + iv;
402 + }
403 + }
404 +}
405 +
406 +static void
407 +bstackhoriz(Monitor *m)
408 +{
409 + unsigned int i, n;
410 + int oh, ov, ih, iv;
411 + int mx = 0, my = 0, mh = 0, mw = 0;
412 + int sx = 0, sy = 0, sh = 0, sw = 0;
413 + float mfacts, sfacts;
414 + int mrest, srest;
415 + Client *c;
416 +
417 + getgaps(m, &oh, &ov, &ih, &iv, &n);
418 + if (n == 0)
419 + return;
420 +
421 + sx = mx = m->wx + ov;
422 + sy = my = m->wy + oh;
423 + mh = m->wh - 2*oh;
424 + sh = m->wh - 2*oh - ih * (n - m->nmaster - 1);
425 + mw = m->ww - 2*ov - iv * (MIN(n, m->nmaster) - 1);
426 + sw = m->ww - 2*ov;
427 +
428 + if (m->nmaster && n > m->nmaster) {
429 + sh = (mh - ih) * (1 - m->mfact);
430 + mh = mh - ih - sh;
431 + sy = my + mh + ih;
432 + sh = m->wh - mh - 2*oh - ih * (n - m->nmaster);
433 + }
434 +
435 + getfacts(m, mw, sh, &mfacts, &sfacts, &mrest, &srest);
436 +
437 + for (i = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), i++) {
438 + if (i < m->nmaster) {
439 + resize(c, mx, my, mw * (c->cfact / mfacts) + (i < mrest ? 1 : 0) - (2*c->bw), mh - (2*c->bw), 0);
440 + mx += WIDTH(c) + iv;
441 + } else {
442 + resize(c, sx, sy, sw - (2*c->bw), sh * (c->cfact / sfacts) + ((i - m->nmaster) < srest ? 1 : 0) - (2*c->bw), 0);
443 + sy += HEIGHT(c) + ih;
444 + }
445 + }
446 +}
447 +
448 +/*
449 + * Centred master layout + gaps
450 + * https://dwm.suckless.org/patches/centeredmaster/
451 + */
452 +void
453 +centeredmaster(Monitor *m)
454 +{
455 + unsigned int i, n;
456 + int oh, ov, ih, iv;
457 + int mx = 0, my = 0, mh = 0, mw = 0;
458 + int lx = 0, ly = 0, lw = 0, lh = 0;
459 + int rx = 0, ry = 0, rw = 0, rh = 0;
460 + float mfacts = 0, lfacts = 0, rfacts = 0;
461 + int mtotal = 0, ltotal = 0, rtotal = 0;
462 + int mrest = 0, lrest = 0, rrest = 0;
463 + Client *c;
464 +
465 + getgaps(m, &oh, &ov, &ih, &iv, &n);
466 + if (n == 0)
467 + return;
468 +
469 + /* initialize areas */
470 + mx = m->wx + ov;
471 + my = m->wy + oh;
472 + mh = m->wh - 2*oh - ih * ((!m->nmaster ? n : MIN(n, m->nmaster)) - 1);
473 + mw = m->ww - 2*ov;
474 + lh = m->wh - 2*oh - ih * (((n - m->nmaster) / 2) - 1);
475 + rh = m->wh - 2*oh - ih * (((n - m->nmaster) / 2) - ((n - m->nmaster) % 2 ? 0 : 1));
476 +
477 + if (m->nmaster && n > m->nmaster) {
478 + /* go mfact box in the center if more than nmaster clients */
479 + if (n - m->nmaster > 1) {
480 + /* ||<-S->|<---M--->|<-S->|| */
481 + mw = (m->ww - 2*ov - 2*iv) * m->mfact;
482 + lw = (m->ww - mw - 2*ov - 2*iv) / 2;
483 + rw = (m->ww - mw - 2*ov - 2*iv) - lw;
484 + mx += lw + iv;
485 + } else {
486 + /* ||<---M--->|<-S->|| */
487 + mw = (mw - iv) * m->mfact;
488 + lw = 0;
489 + rw = m->ww - mw - iv - 2*ov;
490 + }
491 + lx = m->wx + ov;
492 + ly = m->wy + oh;
493 + rx = mx + mw + iv;
494 + ry = m->wy + oh;
495 + }
496 +
497 + /* calculate facts */
498 + for (n = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), n++) {
499 + if (!m->nmaster || n < m->nmaster)
500 + mfacts += c->cfact;
501 + else if ((n - m->nmaster) % 2)
502 + lfacts += c->cfact; // total factor of left hand stack area
503 + else
504 + rfacts += c->cfact; // total factor of right hand stack area
505 + }
506 +
507 + for (n = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), n++)
508 + if (!m->nmaster || n < m->nmaster)
509 + mtotal += mh * (c->cfact / mfacts);
510 + else if ((n - m->nmaster) % 2)
511 + ltotal += lh * (c->cfact / lfacts);
512 + else
513 + rtotal += rh * (c->cfact / rfacts);
514 +
515 + mrest = mh - mtotal;
516 + lrest = lh - ltotal;
517 + rrest = rh - rtotal;
518 +
519 + for (i = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), i++) {
520 + if (!m->nmaster || i < m->nmaster) {
521 + /* nmaster clients are stacked vertically, in the center of the screen */
522 + resize(c, mx, my, mw - (2*c->bw), mh * (c->cfact / mfacts) + (i < mrest ? 1 : 0) - (2*c->bw), 0);
523 + my += HEIGHT(c) + ih;
524 + } else {
525 + /* stack clients are stacked vertically */
526 + if ((i - m->nmaster) % 2 ) {
527 + resize(c, lx, ly, lw - (2*c->bw), lh * (c->cfact / lfacts) + ((i - 2*m->nmaster) < 2*lrest ? 1 : 0) - (2*c->bw), 0);
528 + ly += HEIGHT(c) + ih;
529 + } else {
530 + resize(c, rx, ry, rw - (2*c->bw), rh * (c->cfact / rfacts) + ((i - 2*m->nmaster) < 2*rrest ? 1 : 0) - (2*c->bw), 0);
531 + ry += HEIGHT(c) + ih;
532 + }
533 + }
534 + }
535 +}
536 +
537 +void
538 +centeredfloatingmaster(Monitor *m)
539 +{
540 + unsigned int i, n;
541 + float mfacts, sfacts;
542 + float mivf = 1.0; // master inner vertical gap factor
543 + int oh, ov, ih, iv, mrest, srest;
544 + int mx = 0, my = 0, mh = 0, mw = 0;
545 + int sx = 0, sy = 0, sh = 0, sw = 0;
546 + Client *c;
547 +
548 + getgaps(m, &oh, &ov, &ih, &iv, &n);
549 + if (n == 0)
550 + return;
551 +
552 + sx = mx = m->wx + ov;
553 + sy = my = m->wy + oh;
554 + sh = mh = m->wh - 2*oh;
555 + mw = m->ww - 2*ov - iv*(n - 1);
556 + sw = m->ww - 2*ov - iv*(n - m->nmaster - 1);
557 +
558 + if (m->nmaster && n > m->nmaster) {
559 + mivf = 0.8;
560 + /* go mfact box in the center if more than nmaster clients */
561 + if (m->ww > m->wh) {
562 + mw = m->ww * m->mfact - iv*mivf*(MIN(n, m->nmaster) - 1);
563 + mh = m->wh * 0.9;
564 + } else {
565 + mw = m->ww * 0.9 - iv*mivf*(MIN(n, m->nmaster) - 1);
566 + mh = m->wh * m->mfact;
567 + }
568 + mx = m->wx + (m->ww - mw) / 2;
569 + my = m->wy + (m->wh - mh - 2*oh) / 2;
570 +
571 + sx = m->wx + ov;
572 + sy = m->wy + oh;
573 + sh = m->wh - 2*oh;
574 + }
575 +
576 + getfacts(m, mw, sw, &mfacts, &sfacts, &mrest, &srest);
577 +
578 + for (i = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), i++)
579 + if (i < m->nmaster) {
580 + /* nmaster clients are stacked horizontally, in the center of the screen */
581 + resize(c, mx, my, mw * (c->cfact / mfacts) + (i < mrest ? 1 : 0) - (2*c->bw), mh - (2*c->bw), 0);
582 + mx += WIDTH(c) + iv*mivf;
583 + } else {
584 + /* stack clients are stacked horizontally */
585 + resize(c, sx, sy, sw * (c->cfact / sfacts) + ((i - m->nmaster) < srest ? 1 : 0) - (2*c->bw), sh - (2*c->bw), 0);
586 + sx += WIDTH(c) + iv;
587 + }
588 +}
589 +
590 +/*
591 + * Deck layout + gaps
592 + * https://dwm.suckless.org/patches/deck/
593 + */
594 +void
595 +deck(Monitor *m)
596 +{
597 + unsigned int i, n;
598 + int oh, ov, ih, iv;
599 + int mx = 0, my = 0, mh = 0, mw = 0;
600 + int sx = 0, sy = 0, sh = 0, sw = 0;
601 + float mfacts, sfacts;
602 + int mrest, srest;
603 + Client *c;
604 +
605 + getgaps(m, &oh, &ov, &ih, &iv, &n);
606 + if (n == 0)
607 + return;
608 +
609 + sx = mx = m->wx + ov;
610 + sy = my = m->wy + oh;
611 + sh = mh = m->wh - 2*oh - ih * (MIN(n, m->nmaster) - 1);
612 + sw = mw = m->ww - 2*ov;
613 +
614 + if (m->nmaster && n > m->nmaster) {
615 + sw = (mw - iv) * (1 - m->mfact);
616 + mw = mw - iv - sw;
617 + sx = mx + mw + iv;
618 + sh = m->wh - 2*oh;
619 + }
620 +
621 + getfacts(m, mh, sh, &mfacts, &sfacts, &mrest, &srest);
622 +
623 + if (n - m->nmaster > 0) /* override layout symbol */
624 + snprintf(m->ltsymbol, sizeof m->ltsymbol, "D %d", n - m->nmaster);
625 +
626 + for (i = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), i++)
627 + if (i < m->nmaster) {
628 + resize(c, mx, my, mw - (2*c->bw), mh * (c->cfact / mfacts) + (i < mrest ? 1 : 0) - (2*c->bw), 0);
629 + my += HEIGHT(c) + ih;
630 + } else {
631 + resize(c, sx, sy, sw - (2*c->bw), sh - (2*c->bw), 0);
632 + }
633 +}
634 +
635 +/*
636 + * Fibonacci layout + gaps
637 + * https://dwm.suckless.org/patches/fibonacci/
638 + */
639 +void
640 +fibonacci(Monitor *m, int s)
641 +{
642 + unsigned int i, n;
643 + int nx, ny, nw, nh;
644 + int oh, ov, ih, iv;
645 + int nv, hrest = 0, wrest = 0, r = 1;
646 + Client *c;
647 +
648 + getgaps(m, &oh, &ov, &ih, &iv, &n);
649 + if (n == 0)
650 + return;
651 +
652 + nx = m->wx + ov;
653 + ny = m->wy + oh;
654 + nw = m->ww - 2*ov;
655 + nh = m->wh - 2*oh;
656 +
657 + for (i = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next)) {
658 + if (r) {
659 + if ((i % 2 && (nh - ih) / 2 <= (bh + 2*c->bw))
660 + || (!(i % 2) && (nw - iv) / 2 <= (bh + 2*c->bw))) {
661 + r = 0;
662 + }
663 + if (r && i < n - 1) {
664 + if (i % 2) {
665 + nv = (nh - ih) / 2;
666 + hrest = nh - 2*nv - ih;
667 + nh = nv;
668 + } else {
669 + nv = (nw - iv) / 2;
670 + wrest = nw - 2*nv - iv;
671 + nw = nv;
672 + }
673 +
674 + if ((i % 4) == 2 && !s)
675 + nx += nw + iv;
676 + else if ((i % 4) == 3 && !s)
677 + ny += nh + ih;
678 + }
679 +
680 + if ((i % 4) == 0) {
681 + if (s) {
682 + ny += nh + ih;
683 + nh += hrest;
684 + }
685 + else {
686 + nh -= hrest;
687 + ny -= nh + ih;
688 + }
689 + }
690 + else if ((i % 4) == 1) {
691 + nx += nw + iv;
692 + nw += wrest;
693 + }
694 + else if ((i % 4) == 2) {
695 + ny += nh + ih;
696 + nh += hrest;
697 + if (i < n - 1)
698 + nw += wrest;
699 + }
700 + else if ((i % 4) == 3) {
701 + if (s) {
702 + nx += nw + iv;
703 + nw -= wrest;
704 + } else {
705 + nw -= wrest;
706 + nx -= nw + iv;
707 + nh += hrest;
708 + }
709 + }
710 + if (i == 0) {
711 + if (n != 1) {
712 + nw = (m->ww - iv - 2*ov) - (m->ww - iv - 2*ov) * (1 - m->mfact);
713 + wrest = 0;
714 + }
715 + ny = m->wy + oh;
716 + }
717 + else if (i == 1)
718 + nw = m->ww - nw - iv - 2*ov;
719 + i++;
720 + }
721 +
722 + resize(c, nx, ny, nw - (2*c->bw), nh - (2*c->bw), False);
723 + }
724 +}
725 +
726 +void
727 +dwindle(Monitor *m)
728 +{
729 + fibonacci(m, 1);
730 +}
731 +
732 +void
733 +spiral(Monitor *m)
734 +{
735 + fibonacci(m, 0);
736 +}
737 +
738 +/*
739 + * Gappless grid layout + gaps (ironically)
740 + * https://dwm.suckless.org/patches/gaplessgrid/
741 + */
742 +void
743 +gaplessgrid(Monitor *m)
744 +{
745 + unsigned int i, n;
746 + int x, y, cols, rows, ch, cw, cn, rn, rrest, crest; // counters
747 + int oh, ov, ih, iv;
748 + Client *c;
749 +
750 + getgaps(m, &oh, &ov, &ih, &iv, &n);
751 + if (n == 0)
752 + return;
753 +
754 + /* grid dimensions */
755 + for (cols = 0; cols <= n/2; cols++)
756 + if (cols*cols >= n)
757 + break;
758 + if (n == 5) /* set layout against the general calculation: not 1:2:2, but 2:3 */
759 + cols = 2;
760 + rows = n/cols;
761 + cn = rn = 0; // reset column no, row no, client count
762 +
763 + ch = (m->wh - 2*oh - ih * (rows - 1)) / rows;
764 + cw = (m->ww - 2*ov - iv * (cols - 1)) / cols;
765 + rrest = (m->wh - 2*oh - ih * (rows - 1)) - ch * rows;
766 + crest = (m->ww - 2*ov - iv * (cols - 1)) - cw * cols;
767 + x = m->wx + ov;
768 + y = m->wy + oh;
769 +
770 + for (i = 0, c = nexttiled(m->clients); c; i++, c = nexttiled(c->next)) {
771 + if (i/rows + 1 > cols - n%cols) {
772 + rows = n/cols + 1;
773 + ch = (m->wh - 2*oh - ih * (rows - 1)) / rows;
774 + rrest = (m->wh - 2*oh - ih * (rows - 1)) - ch * rows;
775 + }
776 + resize(c,
777 + x,
778 + y + rn*(ch + ih) + MIN(rn, rrest),
779 + cw + (cn < crest ? 1 : 0) - 2*c->bw,
780 + ch + (rn < rrest ? 1 : 0) - 2*c->bw,
781 + 0);
782 + rn++;
783 + if (rn >= rows) {
784 + rn = 0;
785 + x += cw + ih + (cn < crest ? 1 : 0);
786 + cn++;
787 + }
788 + }
789 +}
790 +
791 +/*
792 + * Gridmode layout + gaps
793 + * https://dwm.suckless.org/patches/gridmode/
794 + */
795 +void
796 +grid(Monitor *m)
797 +{
798 + unsigned int i, n;
799 + int cx, cy, cw, ch, cc, cr, chrest, cwrest, cols, rows;
800 + int oh, ov, ih, iv;
801 + Client *c;
802 +
803 + getgaps(m, &oh, &ov, &ih, &iv, &n);
804 +
805 + /* grid dimensions */
806 + for (rows = 0; rows <= n/2; rows++)
807 + if (rows*rows >= n)
808 + break;
809 + cols = (rows && (rows - 1) * rows >= n) ? rows - 1 : rows;
810 +
811 + /* window geoms (cell height/width) */
812 + ch = (m->wh - 2*oh - ih * (rows - 1)) / (rows ? rows : 1);
813 + cw = (m->ww - 2*ov - iv * (cols - 1)) / (cols ? cols : 1);
814 + chrest = (m->wh - 2*oh - ih * (rows - 1)) - ch * rows;
815 + cwrest = (m->ww - 2*ov - iv * (cols - 1)) - cw * cols;
816 + for (i = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), i++) {
817 + cc = i / rows;
818 + cr = i % rows;
819 + cx = m->wx + ov + cc * (cw + iv) + MIN(cc, cwrest);
820 + cy = m->wy + oh + cr * (ch + ih) + MIN(cr, chrest);
821 + resize(c, cx, cy, cw + (cc < cwrest ? 1 : 0) - 2*c->bw, ch + (cr < chrest ? 1 : 0) - 2*c->bw, False);
822 + }
823 +}
824 +
825 +/*
826 + * Horizontal grid layout + gaps
827 + * https://dwm.suckless.org/patches/horizgrid/
828 + */
829 +void
830 +horizgrid(Monitor *m) {
831 + Client *c;
832 + unsigned int n, i;
833 + int oh, ov, ih, iv;
834 + int mx = 0, my = 0, mh = 0, mw = 0;
835 + int sx = 0, sy = 0, sh = 0, sw = 0;
836 + int ntop, nbottom = 1;
837 + float mfacts = 0, sfacts = 0;
838 + int mrest, srest, mtotal = 0, stotal = 0;
839 +
840 + /* Count windows */
841 + getgaps(m, &oh, &ov, &ih, &iv, &n);
842 + if (n == 0)
843 + return;
844 +
845 + if (n <= 2)
846 + ntop = n;
847 + else {
848 + ntop = n / 2;
849 + nbottom = n - ntop;
850 + }
851 + sx = mx = m->wx + ov;
852 + sy = my = m->wy + oh;
853 + sh = mh = m->wh - 2*oh;
854 + sw = mw = m->ww - 2*ov;
855 +
856 + if (n > ntop) {
857 + sh = (mh - ih) / 2;
858 + mh = mh - ih - sh;
859 + sy = my + mh + ih;
860 + mw = m->ww - 2*ov - iv * (ntop - 1);
861 + sw = m->ww - 2*ov - iv * (nbottom - 1);
862 + }
863 +
864 + /* calculate facts */
865 + for (i = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), i++)
866 + if (i < ntop)
867 + mfacts += c->cfact;
868 + else
869 + sfacts += c->cfact;
870 +
871 + for (i = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), i++)
872 + if (i < ntop)
873 + mtotal += mh * (c->cfact / mfacts);
874 + else
875 + stotal += sw * (c->cfact / sfacts);
876 +
877 + mrest = mh - mtotal;
878 + srest = sw - stotal;
879 +
880 + for (i = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), i++)
881 + if (i < ntop) {
882 + resize(c, mx, my, mw * (c->cfact / mfacts) + (i < mrest ? 1 : 0) - (2*c->bw), mh - (2*c->bw), 0);
883 + mx += WIDTH(c) + iv;
884 + } else {
885 + resize(c, sx, sy, sw * (c->cfact / sfacts) + ((i - ntop) < srest ? 1 : 0) - (2*c->bw), sh - (2*c->bw), 0);
886 + sx += WIDTH(c) + iv;
887 + }
888 +}
889 +
890 +/*
891 + * nrowgrid layout + gaps
892 + * https://dwm.suckless.org/patches/nrowgrid/
893 + */
894 +void
895 +nrowgrid(Monitor *m)
896 +{
897 + unsigned int n;
898 + int ri = 0, ci = 0; /* counters */
899 + int oh, ov, ih, iv; /* vanitygap settings */
900 + unsigned int cx, cy, cw, ch; /* client geometry */
901 + unsigned int uw = 0, uh = 0, uc = 0; /* utilization trackers */
902 + unsigned int cols, rows = m->nmaster + 1;
903 + Client *c;
904 +
905 + /* count clients */
906 + getgaps(m, &oh, &ov, &ih, &iv, &n);
907 +
908 + /* nothing to do here */
909 + if (n == 0)
910 + return;
911 +
912 + /* force 2 clients to always split vertically */
913 + if (FORCE_VSPLIT && n == 2)
914 + rows = 1;
915 +
916 + /* never allow empty rows */
917 + if (n < rows)
918 + rows = n;
919 +
920 + /* define first row */
921 + cols = n / rows;
922 + uc = cols;
923 + cy = m->wy + oh;
924 + ch = (m->wh - 2*oh - ih*(rows - 1)) / rows;
925 + uh = ch;
926 +
927 + for (c = nexttiled(m->clients); c; c = nexttiled(c->next), ci++) {
928 + if (ci == cols) {
929 + uw = 0;
930 + ci = 0;
931 + ri++;
932 +
933 + /* next row */
934 + cols = (n - uc) / (rows - ri);
935 + uc += cols;
936 + cy = m->wy + oh + uh + ih;
937 + uh += ch + ih;
938 + }
939 +
940 + cx = m->wx + ov + uw;
941 + cw = (m->ww - 2*ov - uw) / (cols - ci);
942 + uw += cw + iv;
943 +
944 + resize(c, cx, cy, cw - (2*c->bw), ch - (2*c->bw), 0);
945 + }
946 +}
947 +
948 +/*
949 + * Default tile layout + gaps
950 + */
951 +static void
952 +tile(Monitor *m)
953 +{
954 + unsigned int i, n;
955 + int oh, ov, ih, iv;
956 + int mx = 0, my = 0, mh = 0, mw = 0;
957 + int sx = 0, sy = 0, sh = 0, sw = 0;
958 + float mfacts, sfacts;
959 + int mrest, srest;
960 + Client *c;
961 +
962 + getgaps(m, &oh, &ov, &ih, &iv, &n);
963 + if (n == 0)
964 + return;
965 +
966 + sx = mx = m->wx + ov;
967 + sy = my = m->wy + oh;
968 + mh = m->wh - 2*oh - ih * (MIN(n, m->nmaster) - 1);
969 + sh = m->wh - 2*oh - ih * (n - m->nmaster - 1);
970 + sw = mw = m->ww - 2*ov;
971 +
972 + if (m->nmaster && n > m->nmaster) {
973 + sw = (mw - iv) * (1 - m->mfact);
974 + mw = mw - iv - sw;
975 + sx = mx + mw + iv;
976 + }
977 +
978 + getfacts(m, mh, sh, &mfacts, &sfacts, &mrest, &srest);
979 +
980 + for (i = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), i++)
981 + if (i < m->nmaster) {
982 + resize(c, mx, my, mw - (2*c->bw), mh * (c->cfact / mfacts) + (i < mrest ? 1 : 0) - (2*c->bw), 0);
983 + my += HEIGHT(c) + ih;
984 + } else {
985 + resize(c, sx, sy, sw - (2*c->bw), sh * (c->cfact / sfacts) + ((i - m->nmaster) < srest ? 1 : 0) - (2*c->bw), 0);
986 + sy += HEIGHT(c) + ih;
987 + }
988 +}
989 \ No newline at end of file
990 --
991 2.19.1
992