Xinqi Bao's Git

renamed seltag into seltags
[dwm.git] / layout.c
1 /* See LICENSE file for copyright and license details. */
2 #include "dwm.h"
3 #include <stdlib.h>
4
5 /* static */
6
7 typedef struct {
8 const char *symbol;
9 void (*arrange)(void);
10 } Layout;
11
12 unsigned int blw = 0;
13 static Layout *lt = NULL;
14
15 static void
16 floating(void) { /* default floating layout */
17 Client *c;
18
19 for(c = clients; c; c = c->next)
20 if(isvisible(c))
21 resize(c, c->x, c->y, c->w, c->h, True);
22 }
23
24 static unsigned int nlayouts = 0;
25
26 LAYOUTS
27
28 /* extern */
29
30 void
31 arrange(void) {
32 Client *c;
33
34 for(c = clients; c; c = c->next)
35 if(isvisible(c))
36 unban(c);
37 else
38 ban(c);
39 lt->arrange();
40 focus(NULL);
41 restack();
42 }
43
44 void
45 focusnext(const char *arg) {
46 Client *c;
47
48 if(!sel)
49 return;
50 for(c = sel->next; c && !isvisible(c); c = c->next);
51 if(!c)
52 for(c = clients; c && !isvisible(c); c = c->next);
53 if(c) {
54 focus(c);
55 restack();
56 }
57 }
58
59 void
60 focusprev(const char *arg) {
61 Client *c;
62
63 if(!sel)
64 return;
65 for(c = sel->prev; c && !isvisible(c); c = c->prev);
66 if(!c) {
67 for(c = clients; c && c->next; c = c->next);
68 for(; c && !isvisible(c); c = c->prev);
69 }
70 if(c) {
71 focus(c);
72 restack();
73 }
74 }
75
76 const char *
77 getsymbol(void)
78 {
79 return lt->symbol;
80 }
81
82 Bool
83 isfloating(void) {
84 return lt->arrange == floating;
85 }
86
87 Bool
88 isarrange(void (*func)())
89 {
90 return func == lt->arrange;
91 }
92
93 void
94 initlayouts(void) {
95 unsigned int i, w;
96
97 lt = &layouts[0];
98 nlayouts = sizeof layouts / sizeof layouts[0];
99 for(blw = i = 0; i < nlayouts; i++) {
100 w = textw(layouts[i].symbol);
101 if(w > blw)
102 blw = w;
103 }
104 }
105
106 Client *
107 nexttiled(Client *c) {
108 for(; c && (c->isfloating || !isvisible(c)); c = c->next);
109 return c;
110 }
111
112 void
113 restack(void) {
114 Client *c;
115 XEvent ev;
116 XWindowChanges wc;
117
118 drawstatus();
119 if(!sel)
120 return;
121 if(sel->isfloating || lt->arrange == floating)
122 XRaiseWindow(dpy, sel->win);
123 if(lt->arrange != floating) {
124 wc.stack_mode = Below;
125 wc.sibling = barwin;
126 if(!sel->isfloating) {
127 XConfigureWindow(dpy, sel->win, CWSibling | CWStackMode, &wc);
128 wc.sibling = sel->win;
129 }
130 for(c = nexttiled(clients); c; c = nexttiled(c->next)) {
131 if(c == sel)
132 continue;
133 XConfigureWindow(dpy, c->win, CWSibling | CWStackMode, &wc);
134 wc.sibling = c->win;
135 }
136 }
137 XSync(dpy, False);
138 while(XCheckMaskEvent(dpy, EnterWindowMask, &ev));
139 }
140
141 void
142 setlayout(const char *arg) {
143 int i;
144
145 if(!arg) {
146 lt++;
147 if(lt == layouts + nlayouts)
148 lt = layouts;
149 }
150 else {
151 i = atoi(arg);
152 if(i < 0 || i >= nlayouts)
153 return;
154 lt = &layouts[i];
155 }
156 if(sel)
157 arrange();
158 else
159 drawstatus();
160 }
161
162 void
163 togglebar(const char *arg) {
164 if(bpos == BarOff)
165 bpos = (BARPOS == BarOff) ? BarTop : BARPOS;
166 else
167 bpos = BarOff;
168 updatebarpos();
169 arrange();
170 }
171
172 void
173 togglemax(const char *arg) {
174 XEvent ev;
175
176 if(!sel || (lt->arrange != floating && !sel->isfloating) || sel->isfixed)
177 return;
178 if((sel->ismax = !sel->ismax)) {
179 sel->rx = sel->x;
180 sel->ry = sel->y;
181 sel->rw = sel->w;
182 sel->rh = sel->h;
183 resize(sel, wax, way, waw - 2 * sel->border, wah - 2 * sel->border, True);
184 }
185 else
186 resize(sel, sel->rx, sel->ry, sel->rw, sel->rh, True);
187 drawstatus();
188 while(XCheckMaskEvent(dpy, EnterWindowMask, &ev));
189 }