dwm-stacker-6.0.diff - sites - public wiki contents of suckless.org | |
git clone git://git.suckless.org/sites | |
Log | |
Files | |
Refs | |
--- | |
dwm-stacker-6.0.diff (6401B) | |
--- | |
1 diff --git a/config.def.h b/config.def.h | |
2 index 77ff358..566e0c7 100644 | |
3 --- a/config.def.h | |
4 +++ b/config.def.h | |
5 @@ -41,6 +41,14 @@ static const Layout layouts[] = { | |
6 { MODKEY|ControlMask, KEY, toggleview, {.ui … | |
7 { MODKEY|ShiftMask, KEY, tag, {.ui … | |
8 { MODKEY|ControlMask|ShiftMask, KEY, toggletag, {.ui … | |
9 +#define STACKKEYS(MOD,ACTION) \ | |
10 + { MOD, XK_j, ACTION##stack, {.i = INC(+1) } }, \ | |
11 + { MOD, XK_k, ACTION##stack, {.i = INC(-1) } }, \ | |
12 + { MOD, XK_grave, ACTION##stack, {.i = PREVSEL } }, \ | |
13 + { MOD, XK_q, ACTION##stack, {.i = 0 } }, \ | |
14 + { MOD, XK_a, ACTION##stack, {.i = 1 } }, \ | |
15 + { MOD, XK_z, ACTION##stack, {.i = 2 } }, \ | |
16 + { MOD, XK_x, ACTION##stack, {.i = -1 } }, | |
17 | |
18 /* helper for spawning shell commands in the pre dwm-5.0 fashion */ | |
19 #define SHCMD(cmd) { .v = (const char*[]){ "/bin/sh", "-c", cmd, NULL }… | |
20 @@ -54,8 +62,8 @@ static Key keys[] = { | |
21 { MODKEY, XK_p, spawn, {.v … | |
22 { MODKEY|ShiftMask, XK_Return, spawn, {.v … | |
23 { MODKEY, XK_b, togglebar, {0} … | |
24 - { MODKEY, XK_j, focusstack, {.i … | |
25 - { MODKEY, XK_k, focusstack, {.i … | |
26 + STACKKEYS(MODKEY, focus) | |
27 + STACKKEYS(MODKEY|ShiftMask, push) | |
28 { MODKEY, XK_i, incnmaster, {.i … | |
29 { MODKEY, XK_d, incnmaster, {.i … | |
30 { MODKEY, XK_h, setmfact, {.f … | |
31 @@ -83,7 +91,7 @@ static Key keys[] = { | |
32 TAGKEYS( XK_7, 6) | |
33 TAGKEYS( XK_8, 7) | |
34 TAGKEYS( XK_9, 8) | |
35 - { MODKEY|ShiftMask, XK_q, quit, {0} … | |
36 + { MODKEY|ShiftMask, XK_BackSpace, quit, {0} … | |
37 }; | |
38 | |
39 /* button definitions */ | |
40 diff --git a/dwm.c b/dwm.c | |
41 index 1d78655..6129f56 100644 | |
42 --- a/dwm.c | |
43 +++ b/dwm.c | |
44 @@ -43,17 +43,23 @@ | |
45 /* macros */ | |
46 #define BUTTONMASK (ButtonPressMask|ButtonReleaseMask) | |
47 #define CLEANMASK(mask) (mask & ~(numlockmask|LockMask) & (Shif… | |
48 +#define GETINC(X) ((X) - 2000) | |
49 +#define INC(X) ((X) + 2000) | |
50 #define INTERSECT(x,y,w,h,m) (MAX(0, MIN((x)+(w),(m)->wx+(m)->ww) - … | |
51 * MAX(0, MIN((y)+(h),(m)->wy+(m)->wh) - … | |
52 +#define ISINC(X) ((X) > 1000 && (X) < 3000) | |
53 #define ISVISIBLE(C) ((C->tags & C->mon->tagset[C->mon->selt… | |
54 +#define PREVSEL 3000 | |
55 #define LENGTH(X) (sizeof X / sizeof X[0]) | |
56 #define MAX(A, B) ((A) > (B) ? (A) : (B)) | |
57 #define MIN(A, B) ((A) < (B) ? (A) : (B)) | |
58 +#define MOD(N,M) ((N)%(M) < 0 ? (N)%(M) + (M) : (N)%(M)) | |
59 #define MOUSEMASK (BUTTONMASK|PointerMotionMask) | |
60 #define WIDTH(X) ((X)->w + 2 * (X)->bw) | |
61 #define HEIGHT(X) ((X)->h + 2 * (X)->bw) | |
62 #define TAGMASK ((1 << LENGTH(tags)) - 1) | |
63 #define TEXTW(X) (textnw(X, strlen(X)) + dc.font.height) | |
64 +#define TRUNC(X,A,B) (MAX((A), MIN((X), (B)))) | |
65 | |
66 /* enums */ | |
67 enum { CurNormal, CurResize, CurMove, CurLast }; /* cursor */ | |
68 @@ -205,6 +211,7 @@ static void movemouse(const Arg *arg); | |
69 static Client *nexttiled(Client *c); | |
70 static void pop(Client *); | |
71 static void propertynotify(XEvent *e); | |
72 +static void pushstack(const Arg *arg); | |
73 static void quit(const Arg *arg); | |
74 static Monitor *recttomon(int x, int y, int w, int h); | |
75 static void resize(Client *c, int x, int y, int w, int h, Bool interact… | |
76 @@ -224,6 +231,7 @@ static void setup(void); | |
77 static void showhide(Client *c); | |
78 static void sigchld(int unused); | |
79 static void spawn(const Arg *arg); | |
80 +static int stackpos(const Arg *arg); | |
81 static void tag(const Arg *arg); | |
82 static void tagmon(const Arg *arg); | |
83 static int textnw(const char *text, unsigned int len); | |
84 @@ -887,28 +895,16 @@ focusmon(const Arg *arg) { | |
85 | |
86 void | |
87 focusstack(const Arg *arg) { | |
88 - Client *c = NULL, *i; | |
89 + int i = stackpos(arg); | |
90 + Client *c, *p; | |
91 | |
92 - if(!selmon->sel) | |
93 + if(i < 0) | |
94 return; | |
95 - if(arg->i > 0) { | |
96 - for(c = selmon->sel->next; c && !ISVISIBLE(c); c = c->n… | |
97 - if(!c) | |
98 - for(c = selmon->clients; c && !ISVISIBLE(c); c … | |
99 - } | |
100 - else { | |
101 - for(i = selmon->clients; i != selmon->sel; i = i->next) | |
102 - if(ISVISIBLE(i)) | |
103 - c = i; | |
104 - if(!c) | |
105 - for(; i; i = i->next) | |
106 - if(ISVISIBLE(i)) | |
107 - c = i; | |
108 - } | |
109 - if(c) { | |
110 - focus(c); | |
111 - restack(selmon); | |
112 - } | |
113 + | |
114 + for(p = NULL, c = selmon->clients; c && (i || !ISVISIBLE(c)); | |
115 + i -= ISVISIBLE(c) ? 1 : 0, p = c, c = c->next); | |
116 + focus(c ? c : p); | |
117 + restack(selmon); | |
118 } | |
119 | |
120 Atom | |
121 @@ -1324,6 +1320,29 @@ propertynotify(XEvent *e) { | |
122 } | |
123 | |
124 void | |
125 +pushstack(const Arg *arg) { | |
126 + int i = stackpos(arg); | |
127 + Client *sel = selmon->sel, *c, *p; | |
128 + | |
129 + if(i < 0) | |
130 + return; | |
131 + else if(i == 0) { | |
132 + detach(sel); | |
133 + attach(sel); | |
134 + } | |
135 + else { | |
136 + for(p = NULL, c = selmon->clients; c; p = c, c = c->nex… | |
137 + if(!(i -= (ISVISIBLE(c) && c != sel))) | |
138 + break; | |
139 + c = c ? c : p; | |
140 + detach(sel); | |
141 + sel->next = c->next; | |
142 + c->next = sel; | |
143 + } | |
144 + arrange(selmon); | |
145 +} | |
146 + | |
147 +void | |
148 quit(const Arg *arg) { | |
149 running = False; | |
150 } | |
151 @@ -1674,6 +1693,36 @@ spawn(const Arg *arg) { | |
152 } | |
153 } | |
154 | |
155 +int | |
156 +stackpos(const Arg *arg) { | |
157 + int n, i; | |
158 + Client *c, *l; | |
159 + | |
160 + if(!selmon->clients) | |
161 + return -1; | |
162 + | |
163 + if(arg->i == PREVSEL) { | |
164 + for(l = selmon->stack; l && (!ISVISIBLE(l) || l == selm… | |
165 + if(!l) | |
166 + return -1; | |
167 + for(i = 0, c = selmon->clients; c != l; i += ISVISIBLE(… | |
168 + return i; | |
169 + } | |
170 + else if(ISINC(arg->i)) { | |
171 + if(!selmon->sel) | |
172 + return -1; | |
173 + for(i = 0, c = selmon->clients; c != selmon->sel; i += … | |
174 + for(n = i; c; n += ISVISIBLE(c) ? 1 : 0, c = c->next); | |
175 + return MOD(i + GETINC(arg->i), n); | |
176 + } | |
177 + else if(arg->i < 0) { | |
178 + for(i = 0, c = selmon->clients; c; i += ISVISIBLE(c) ? … | |
179 + return MAX(i + arg->i, 0); | |
180 + } | |
181 + else | |
182 + return arg->i; | |
183 +} | |
184 + | |
185 void | |
186 tag(const Arg *arg) { | |
187 if(selmon->sel && arg->ui & TAGMASK) { |