JasonWoof Got questions, comments, patches, etc.? Contact Jason Woofenden
several additions in mouse handling ;)
[dwm.git] / tag.c
1 /*
2  * (C)opyright MMVI Anselm R. Garbe <garbeam at gmail dot com>
3  * See LICENSE file for license details.
4  */
5 #include "dwm.h"
6
7 #include <string.h>
8 #include <X11/Xutil.h>
9
10 /********** CUSTOMIZE **********/
11
12 char *tags[TLast] = {
13         [Tscratch] = "scratch",
14         [Tdev] = "dev",
15         [Twww] = "www",
16         [Twork] = "work",
17 };
18
19 static Rule rule[] = {
20         /* class                        instance        tags                                            isfloat */
21         { "Firefox-bin",        "Gecko",        { [Twww] = "www" },                     False },
22 };
23
24 /********** CUSTOMIZE **********/
25
26 /* extern functions */
27
28 void (*arrange)(Arg *) = dotile;
29
30 void
31 appendtag(Arg *arg)
32 {
33         if(!sel)
34                 return;
35
36         sel->tags[arg->i] = tags[arg->i];
37         arrange(NULL);
38 }
39
40 void
41 dofloat(Arg *arg)
42 {
43         Client *c;
44
45         arrange = dofloat;
46         for(c = clients; c; c = c->next) {
47                 if(c->tags[tsel])
48                         resize(c, True);
49                 else
50                         ban(c);
51         }
52         if(sel && !sel->tags[tsel]) {
53                 if((sel = getnext(clients))) {
54                         higher(sel);
55                         focus(sel);
56                 }
57         }
58         drawall();
59 }
60
61 void
62 dotile(Arg *arg)
63 {
64         Client *c;
65         int n, i, w, h;
66
67         w = sw - mw;
68         arrange = dotile;
69         for(n = 0, c = clients; c; c = c->next)
70                 if(c->tags[tsel] && !c->isfloat)
71                         n++;
72
73         if(n > 1)
74                 h = (sh - bh) / (n - 1);
75         else
76                 h = sh - bh;
77
78         for(i = 0, c = clients; c; c = c->next) {
79                 if(c->tags[tsel]) {
80                         if(c->isfloat) {
81                                 higher(c);
82                                 resize(c, True);
83                                 continue;
84                         }
85                         if(n == 1) {
86                                 c->x = sx;
87                                 c->y = sy + bh;
88                                 c->w = sw - 2 * c->border;
89                                 c->h = sh - 2 * c->border - bh;
90                         }
91                         else if(i == 0) {
92                                 c->x = sx;
93                                 c->y = sy + bh;
94                                 c->w = mw - 2 * c->border;
95                                 c->h = sh - 2 * c->border - bh;
96                         }
97                         else {
98                                 c->x = sx + mw;
99                                 c->y = sy + (i - 1) * h + bh;
100                                 c->w = w - 2 * c->border;
101                                 c->h = h - 2 * c->border;
102                         }
103                         resize(c, False);
104                         i++;
105                 }
106                 else
107                         ban(c);
108         }
109         if(!sel || (sel && !sel->tags[tsel])) {
110                 if((sel = getnext(clients))) {
111                         higher(sel);
112                         focus(sel);
113                 }
114         }
115         drawall();
116 }
117
118 Client *
119 getnext(Client *c)
120 {
121         for(; c && !c->tags[tsel]; c = c->next);
122         return c;
123 }
124
125 void
126 replacetag(Arg *arg)
127 {
128         int i;
129         if(!sel)
130                 return;
131
132         for(i = 0; i < TLast; i++)
133                 sel->tags[i] = NULL;
134         appendtag(arg);
135 }
136
137 void
138 settags(Client *c)
139 {
140         XClassHint ch;
141         static unsigned int len = rule ? sizeof(rule) / sizeof(rule[0]) : 0;
142         unsigned int i, j;
143         Bool matched = False;
144
145         if(!len) {
146                 c->tags[tsel] = tags[tsel];
147                 return;
148         }
149
150         if(XGetClassHint(dpy, c->win, &ch)) {
151                 if(ch.res_class && ch.res_name) {
152                         for(i = 0; i < len; i++)
153                                 if(!strncmp(rule[i].class, ch.res_class, sizeof(rule[i].class))
154                                         && !strncmp(rule[i].instance, ch.res_name, sizeof(rule[i].instance)))
155                                 {
156                                         for(j = 0; j < TLast; j++)
157                                                 c->tags[j] = rule[i].tags[j];
158                                         c->isfloat = rule[i].isfloat;
159                                         matched = True;
160                                         break;
161                                 }
162                 }
163                 if(ch.res_class)
164                         XFree(ch.res_class);
165                 if(ch.res_name)
166                         XFree(ch.res_name);
167         }
168
169         if(!matched)
170                 c->tags[tsel] = tags[tsel];
171 }
172
173 void
174 view(Arg *arg)
175 {
176         tsel = arg->i;
177         arrange(NULL);
178         drawall();
179 }