comparison client.c @ 76:4bd49f404f10

proceeded with cleaning up, sorting functions, etc
author Anselm R. Garbe <garbeam@wmii.de>
date Sat, 15 Jul 2006 17:00:56 +0200
parents f08271b7cb20
children 38c8f7f7d401
comparison
equal deleted inserted replaced
75:f08271b7cb20 76:4bd49f404f10
1 /* 1 /*
2 * (C)opyright MMVI Anselm R. Garbe <garbeam at gmail dot com> 2 * (C)opyright MMVI Anselm R. Garbe <garbeam at gmail dot com>
3 * See LICENSE file for license details. 3 * See LICENSE file for license details.
4 */ 4 */
5 #include "dwm.h"
5 6
6 #include <stdlib.h> 7 #include <stdlib.h>
7 #include <stdio.h>
8 #include <string.h> 8 #include <string.h>
9 #include <X11/Xatom.h> 9 #include <X11/Xatom.h>
10 #include <X11/Xutil.h> 10 #include <X11/Xutil.h>
11 11
12 #include "dwm.h" 12 /* static functions */
13
14 void
15 ban(Client *c)
16 {
17 XMoveWindow(dpy, c->win, c->x + 2 * sw, c->y);
18 XMoveWindow(dpy, c->title, c->tx + 2 * sw, c->ty);
19 }
20 13
21 static void 14 static void
22 resizetitle(Client *c) 15 resizetitle(Client *c)
23 { 16 {
24 int i; 17 int i;
33 c->tx = c->x + c->w - c->tw + 2; 26 c->tx = c->x + c->w - c->tw + 2;
34 c->ty = c->y; 27 c->ty = c->y;
35 XMoveResizeWindow(dpy, c->title, c->tx, c->ty, c->tw, c->th); 28 XMoveResizeWindow(dpy, c->title, c->tx, c->ty, c->tw, c->th);
36 } 29 }
37 30
38 void 31 static int
39 settitle(Client *c) 32 xerrordummy(Display *dsply, XErrorEvent *ee)
40 { 33 {
41 XTextProperty name; 34 return 0;
42 int n; 35 }
43 char **list = NULL; 36
44 37 /* extern functions */
45 name.nitems = 0; 38
46 c->name[0] = 0; 39 void
47 XGetTextProperty(dpy, c->win, &name, net_atom[NetWMName]); 40 ban(Client *c)
48 if(!name.nitems) 41 {
49 XGetWMName(dpy, c->win, &name); 42 XMoveWindow(dpy, c->win, c->x + 2 * sw, c->y);
50 if(!name.nitems) 43 XMoveWindow(dpy, c->title, c->tx + 2 * sw, c->ty);
51 return;
52 if(name.encoding == XA_STRING)
53 strncpy(c->name, (char *)name.value, sizeof(c->name));
54 else {
55 if(XmbTextPropertyToTextList(dpy, &name, &list, &n) >= Success
56 && n > 0 && *list)
57 {
58 strncpy(c->name, *list, sizeof(c->name));
59 XFreeStringList(list);
60 }
61 }
62 XFree(name.value);
63 resizetitle(c);
64 }
65
66 void
67 setsize(Client *c)
68 {
69 XSizeHints size;
70 long msize;
71 if(!XGetWMNormalHints(dpy, c->win, &size, &msize) || !size.flags)
72 size.flags = PSize;
73 c->flags = size.flags;
74 if(c->flags & PBaseSize) {
75 c->basew = size.base_width;
76 c->baseh = size.base_height;
77 }
78 else
79 c->basew = c->baseh = 0;
80 if(c->flags & PResizeInc) {
81 c->incw = size.width_inc;
82 c->inch = size.height_inc;
83 }
84 else
85 c->incw = c->inch = 0;
86 if(c->flags & PMaxSize) {
87 c->maxw = size.max_width;
88 c->maxh = size.max_height;
89 }
90 else
91 c->maxw = c->maxh = 0;
92 if(c->flags & PMinSize) {
93 c->minw = size.min_width;
94 c->minh = size.min_height;
95 }
96 else
97 c->minw = c->minh = 0;
98 if(c->flags & PWinGravity)
99 c->grav = size.win_gravity;
100 else
101 c->grav = NorthWestGravity;
102 }
103
104 void
105 higher(Client *c)
106 {
107 XRaiseWindow(dpy, c->win);
108 XRaiseWindow(dpy, c->title);
109 }
110
111 void
112 lower(Client *c)
113 {
114 XLowerWindow(dpy, c->title);
115 XLowerWindow(dpy, c->win);
116 } 44 }
117 45
118 void 46 void
119 focus(Client *c) 47 focus(Client *c)
120 { 48 {
127 drawtitle(old); 55 drawtitle(old);
128 drawtitle(c); 56 drawtitle(c);
129 XSetInputFocus(dpy, c->win, RevertToPointerRoot, CurrentTime); 57 XSetInputFocus(dpy, c->win, RevertToPointerRoot, CurrentTime);
130 XFlush(dpy); 58 XFlush(dpy);
131 while(XCheckMaskEvent(dpy, EnterWindowMask, &ev)); 59 while(XCheckMaskEvent(dpy, EnterWindowMask, &ev));
60 }
61
62 void
63 focusnext(Arg *arg)
64 {
65 Client *c;
66
67 if(!sel)
68 return;
69
70 if(!(c = getnext(sel->next)))
71 c = getnext(clients);
72 if(c) {
73 higher(c);
74 c->revert = sel;
75 focus(c);
76 }
77 }
78
79 void
80 focusprev(Arg *arg)
81 {
82 Client *c;
83
84 if(!sel)
85 return;
86
87 if((c = sel->revert && sel->revert->tags[tsel] ? sel->revert : NULL)) {
88 higher(c);
89 focus(c);
90 }
91 }
92
93 Client *
94 getclient(Window w)
95 {
96 Client *c;
97 for(c = clients; c; c = c->next)
98 if(c->win == w)
99 return c;
100 return NULL;
101 }
102
103 Client *
104 getctitle(Window w)
105 {
106 Client *c;
107 for(c = clients; c; c = c->next)
108 if(c->title == w)
109 return c;
110 return NULL;
111 }
112
113 void
114 gravitate(Client *c, Bool invert)
115 {
116 int dx = 0, dy = 0;
117
118 switch(c->grav) {
119 case StaticGravity:
120 case NorthWestGravity:
121 case NorthGravity:
122 case NorthEastGravity:
123 dy = c->border;
124 break;
125 case EastGravity:
126 case CenterGravity:
127 case WestGravity:
128 dy = -(c->h / 2) + c->border;
129 break;
130 case SouthEastGravity:
131 case SouthGravity:
132 case SouthWestGravity:
133 dy = -c->h;
134 break;
135 default:
136 break;
137 }
138
139 switch (c->grav) {
140 case StaticGravity:
141 case NorthWestGravity:
142 case WestGravity:
143 case SouthWestGravity:
144 dx = c->border;
145 break;
146 case NorthGravity:
147 case CenterGravity:
148 case SouthGravity:
149 dx = -(c->w / 2) + c->border;
150 break;
151 case NorthEastGravity:
152 case EastGravity:
153 case SouthEastGravity:
154 dx = -(c->w + c->border);
155 break;
156 default:
157 break;
158 }
159
160 if(invert) {
161 dx = -dx;
162 dy = -dy;
163 }
164 c->x += dx;
165 c->y += dy;
166 }
167
168 void
169 higher(Client *c)
170 {
171 XRaiseWindow(dpy, c->win);
172 XRaiseWindow(dpy, c->title);
173 }
174
175 void
176 killclient(Arg *arg)
177 {
178 if(!sel)
179 return;
180 if(sel->proto & WM_PROTOCOL_DELWIN)
181 sendevent(sel->win, wm_atom[WMProtocols], wm_atom[WMDelete]);
182 else
183 XKillClient(dpy, sel->win);
184 }
185
186 void
187 lower(Client *c)
188 {
189 XLowerWindow(dpy, c->title);
190 XLowerWindow(dpy, c->win);
132 } 191 }
133 192
134 void 193 void
135 manage(Window w, XWindowAttributes *wa) 194 manage(Window w, XWindowAttributes *wa)
136 { 195 {
193 XMapRaised(dpy, c->title); 252 XMapRaised(dpy, c->title);
194 } 253 }
195 } 254 }
196 255
197 void 256 void
198 gravitate(Client *c, Bool invert) 257 maximize(Arg *arg)
199 { 258 {
200 int dx = 0, dy = 0; 259 if(!sel)
201 260 return;
202 switch(c->grav) { 261 sel->x = sx;
203 case StaticGravity: 262 sel->y = sy + bh;
204 case NorthWestGravity: 263 sel->w = sw - 2 * sel->border;
205 case NorthGravity: 264 sel->h = sh - 2 * sel->border - bh;
206 case NorthEastGravity: 265 higher(sel);
207 dy = c->border; 266 resize(sel, False);
208 break; 267 }
209 case EastGravity:
210 case CenterGravity:
211 case WestGravity:
212 dy = -(c->h / 2) + c->border;
213 break;
214 case SouthEastGravity:
215 case SouthGravity:
216 case SouthWestGravity:
217 dy = -c->h;
218 break;
219 default:
220 break;
221 }
222
223 switch (c->grav) {
224 case StaticGravity:
225 case NorthWestGravity:
226 case WestGravity:
227 case SouthWestGravity:
228 dx = c->border;
229 break;
230 case NorthGravity:
231 case CenterGravity:
232 case SouthGravity:
233 dx = -(c->w / 2) + c->border;
234 break;
235 case NorthEastGravity:
236 case EastGravity:
237 case SouthEastGravity:
238 dx = -(c->w + c->border);
239 break;
240 default:
241 break;
242 }
243
244 if(invert) {
245 dx = -dx;
246 dy = -dy;
247 }
248 c->x += dx;
249 c->y += dy;
250 }
251
252 268
253 void 269 void
254 resize(Client *c, Bool inc) 270 resize(Client *c, Bool inc)
255 { 271 {
256 XConfigureEvent e; 272 XConfigureEvent e;
288 e.override_redirect = False; 304 e.override_redirect = False;
289 XSendEvent(dpy, c->win, False, StructureNotifyMask, (XEvent *)&e); 305 XSendEvent(dpy, c->win, False, StructureNotifyMask, (XEvent *)&e);
290 XFlush(dpy); 306 XFlush(dpy);
291 } 307 }
292 308
293 static int 309 void
294 xerrordummy(Display *dsply, XErrorEvent *ee) 310 setsize(Client *c)
295 { 311 {
296 return 0; 312 XSizeHints size;
313 long msize;
314 if(!XGetWMNormalHints(dpy, c->win, &size, &msize) || !size.flags)
315 size.flags = PSize;
316 c->flags = size.flags;
317 if(c->flags & PBaseSize) {
318 c->basew = size.base_width;
319 c->baseh = size.base_height;
320 }
321 else
322 c->basew = c->baseh = 0;
323 if(c->flags & PResizeInc) {
324 c->incw = size.width_inc;
325 c->inch = size.height_inc;
326 }
327 else
328 c->incw = c->inch = 0;
329 if(c->flags & PMaxSize) {
330 c->maxw = size.max_width;
331 c->maxh = size.max_height;
332 }
333 else
334 c->maxw = c->maxh = 0;
335 if(c->flags & PMinSize) {
336 c->minw = size.min_width;
337 c->minh = size.min_height;
338 }
339 else
340 c->minw = c->minh = 0;
341 if(c->flags & PWinGravity)
342 c->grav = size.win_gravity;
343 else
344 c->grav = NorthWestGravity;
345 }
346
347 void
348 settitle(Client *c)
349 {
350 XTextProperty name;
351 int n;
352 char **list = NULL;
353
354 name.nitems = 0;
355 c->name[0] = 0;
356 XGetTextProperty(dpy, c->win, &name, net_atom[NetWMName]);
357 if(!name.nitems)
358 XGetWMName(dpy, c->win, &name);
359 if(!name.nitems)
360 return;
361 if(name.encoding == XA_STRING)
362 strncpy(c->name, (char *)name.value, sizeof(c->name));
363 else {
364 if(XmbTextPropertyToTextList(dpy, &name, &list, &n) >= Success
365 && n > 0 && *list)
366 {
367 strncpy(c->name, *list, sizeof(c->name));
368 XFreeStringList(list);
369 }
370 }
371 XFree(name.value);
372 resizetitle(c);
297 } 373 }
298 374
299 void 375 void
300 unmanage(Client *c) 376 unmanage(Client *c)
301 { 377 {
323 arrange(NULL); 399 arrange(NULL);
324 if(sel) 400 if(sel)
325 focus(sel); 401 focus(sel);
326 } 402 }
327 403
328 Client *
329 getctitle(Window w)
330 {
331 Client *c;
332 for(c = clients; c; c = c->next)
333 if(c->title == w)
334 return c;
335 return NULL;
336 }
337
338 Client *
339 getclient(Window w)
340 {
341 Client *c;
342 for(c = clients; c; c = c->next)
343 if(c->win == w)
344 return c;
345 return NULL;
346 }
347
348 void 404 void
349 zoom(Arg *arg) 405 zoom(Arg *arg)
350 { 406 {
351 Client **l, *c; 407 Client **l, *c;
352 408
364 sel->next = clients; /* pop */ 420 sel->next = clients; /* pop */
365 clients = sel; 421 clients = sel;
366 arrange(NULL); 422 arrange(NULL);
367 focus(sel); 423 focus(sel);
368 } 424 }
369
370 void
371 maximize(Arg *arg)
372 {
373 if(!sel)
374 return;
375 sel->x = sx;
376 sel->y = sy + bh;
377 sel->w = sw - 2 * sel->border;
378 sel->h = sh - 2 * sel->border - bh;
379 higher(sel);
380 resize(sel, False);
381 }
382
383 void
384 focusprev(Arg *arg)
385 {
386 Client *c;
387
388 if(!sel)
389 return;
390
391 if((c = sel->revert && sel->revert->tags[tsel] ? sel->revert : NULL)) {
392 higher(c);
393 focus(c);
394 }
395 }
396
397 void
398 focusnext(Arg *arg)
399 {
400 Client *c;
401
402 if(!sel)
403 return;
404
405 if(!(c = getnext(sel->next)))
406 c = getnext(clients);
407 if(c) {
408 higher(c);
409 c->revert = sel;
410 focus(c);
411 }
412 }
413
414 void
415 killclient(Arg *arg)
416 {
417 if(!sel)
418 return;
419 if(sel->proto & WM_PROTOCOL_DELWIN)
420 sendevent(sel->win, wm_atom[WMProtocols], wm_atom[WMDelete]);
421 else
422 XKillClient(dpy, sel->win);
423 }