mirror of
https://github.com/eRgo35/dwm.git
synced 2025-12-16 21:56:10 +01:00
initial commit
This commit is contained in:
195
patch/floatpos.c
Normal file
195
patch/floatpos.c
Normal file
@@ -0,0 +1,195 @@
|
||||
void
|
||||
floatpos(const Arg *arg)
|
||||
{
|
||||
Client *c = selmon->sel;
|
||||
|
||||
if (!c || (selmon->lt[selmon->sellt]->arrange && !c->isfloating))
|
||||
return;
|
||||
|
||||
setfloatpos(c, (char *)arg->v);
|
||||
resizeclient(c, c->x, c->y, c->w, c->h);
|
||||
|
||||
#if !FOCUSONCLICK_PATCH
|
||||
XRaiseWindow(dpy, c->win);
|
||||
XWarpPointer(dpy, None, c->win, 0, 0, 0, 0, c->w/2, c->h/2);
|
||||
#endif // FOCUSONCLICK_PATCH
|
||||
}
|
||||
|
||||
void
|
||||
setfloatpos(Client *c, const char *floatpos)
|
||||
{
|
||||
char xCh, yCh, wCh, hCh;
|
||||
int x, y, w, h, wx, ww, wy, wh;
|
||||
#if FLOATPOS_RESPECT_GAPS_PATCH && VANITYGAPS_PATCH
|
||||
int oh, ov, ih, iv;
|
||||
unsigned int n;
|
||||
#endif // FLOATPOS_RESPECT_GAPS_PATCH | VANITYGAPS_PATCH
|
||||
|
||||
if (!c || !floatpos)
|
||||
return;
|
||||
if (selmon->lt[selmon->sellt]->arrange && !c->isfloating)
|
||||
return;
|
||||
|
||||
switch(sscanf(floatpos, "%d%c %d%c %d%c %d%c", &x, &xCh, &y, &yCh, &w, &wCh, &h, &hCh)) {
|
||||
case 4:
|
||||
if (xCh == 'w' || xCh == 'W') {
|
||||
w = x; wCh = xCh;
|
||||
h = y; hCh = yCh;
|
||||
x = -1; xCh = 'C';
|
||||
y = -1; yCh = 'C';
|
||||
} else if (xCh == 'p' || xCh == 'P') {
|
||||
w = x; wCh = xCh;
|
||||
h = y; hCh = yCh;
|
||||
x = 0; xCh = 'G';
|
||||
y = 0; yCh = 'G';
|
||||
} else if (xCh == 'm' || xCh == 'M') {
|
||||
getrootptr(&x, &y);
|
||||
} else {
|
||||
w = 0; wCh = 0;
|
||||
h = 0; hCh = 0;
|
||||
}
|
||||
break;
|
||||
case 8:
|
||||
if (xCh == 'm' || xCh == 'M')
|
||||
getrootptr(&x, &y);
|
||||
break;
|
||||
default:
|
||||
return;
|
||||
}
|
||||
|
||||
#if FLOATPOS_RESPECT_GAPS_PATCH && VANITYGAPS_PATCH
|
||||
getgaps(c->mon, &oh, &ov, &ih, &iv, &n);
|
||||
wx = c->mon->wx + ov;
|
||||
wy = c->mon->wy + oh;
|
||||
ww = c->mon->ww - 2*ov;
|
||||
wh = c->mon->wh - 2*oh;
|
||||
#else
|
||||
wx = c->mon->wx;
|
||||
wy = c->mon->wy;
|
||||
ww = c->mon->ww;
|
||||
wh = c->mon->wh;
|
||||
#endif // FLOATPOS_RESPECT_GAPS_PATCH | VANITYGAPS_PATCH
|
||||
|
||||
getfloatpos(x, xCh, w, wCh, wx, ww, c->x, c->w, c->bw, floatposgrid_x, &c->x, &c->w);
|
||||
getfloatpos(y, yCh, h, hCh, wy, wh, c->y, c->h, c->bw, floatposgrid_y, &c->y, &c->h);
|
||||
}
|
||||
|
||||
/* p - position, s - size, cp and cs represents current position and size */
|
||||
void
|
||||
getfloatpos(int pos, char pCh, int size, char sCh, int min_p, int max_s, int cp, int cs, int cbw, int defgrid, int *out_p, int *out_s)
|
||||
{
|
||||
int abs_p, abs_s, i, delta, rest;
|
||||
|
||||
abs_p = pCh == 'A' || pCh == 'a';
|
||||
abs_s = sCh == 'A' || sCh == 'a';
|
||||
|
||||
cs += 2*cbw;
|
||||
|
||||
switch(pCh) {
|
||||
case 'A': // absolute position
|
||||
cp = pos;
|
||||
break;
|
||||
case 'a': // absolute relative position
|
||||
cp += pos;
|
||||
break;
|
||||
case 'y':
|
||||
case 'x': // client relative position
|
||||
cp = MIN(cp + pos, min_p + max_s);
|
||||
break;
|
||||
case 'Y':
|
||||
case 'X': // client position relative to monitor
|
||||
cp = min_p + MIN(pos, max_s);
|
||||
break;
|
||||
case 'S': // fixed client position (sticky)
|
||||
case 'C': // fixed client position (center)
|
||||
case 'Z': // fixed client right-hand position (position + size)
|
||||
if (pos == -1)
|
||||
break;
|
||||
pos = MAX(MIN(pos, max_s), 0);
|
||||
if (pCh == 'Z')
|
||||
cs = abs((cp + cs) - (min_p + pos));
|
||||
else if (pCh == 'C')
|
||||
cs = abs((cp + cs / 2) - (min_p + pos));
|
||||
else
|
||||
cs = abs(cp - (min_p + pos));
|
||||
cp = min_p + pos;
|
||||
sCh = 0; // size determined by position, override defined size
|
||||
break;
|
||||
case 'G': // grid
|
||||
if (pos <= 0)
|
||||
pos = defgrid; // default configurable
|
||||
if (size == 0 || pos < 2 || (sCh != 'p' && sCh != 'P'))
|
||||
break;
|
||||
delta = (max_s - cs) / (pos - 1);
|
||||
rest = max_s - cs - delta * (pos - 1);
|
||||
if (sCh == 'P') {
|
||||
if (size < 1 || size > pos)
|
||||
break;
|
||||
cp = min_p + delta * (size - 1);
|
||||
} else {
|
||||
for (i = 0; i < pos && cp >= min_p + delta * i + (i > pos - rest ? i + rest - pos + 1 : 0); i++);
|
||||
cp = min_p + delta * (MAX(MIN(i + size, pos), 1) - 1) + (i > pos - rest ? i + rest - pos + 1 : 0);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
switch(sCh) {
|
||||
case 'A': // absolute size
|
||||
cs = size;
|
||||
break;
|
||||
case 'a': // absolute relative size
|
||||
cs = MAX(1, cs + size);
|
||||
break;
|
||||
case '%': // client size percentage in relation to monitor window area size
|
||||
if (size <= 0)
|
||||
break;
|
||||
size = max_s * MIN(size, 100) / 100;
|
||||
/* falls through */
|
||||
case 'h':
|
||||
case 'w': // size relative to client
|
||||
if (sCh == 'w' || sCh == 'h') {
|
||||
if (size == 0)
|
||||
break;
|
||||
size += cs;
|
||||
}
|
||||
/* falls through */
|
||||
case 'H':
|
||||
case 'W': // normal size, position takes precedence
|
||||
if (pCh == 'S' && cp + size > min_p + max_s)
|
||||
size = min_p + max_s - cp;
|
||||
else if (size > max_s)
|
||||
size = max_s;
|
||||
|
||||
if (pCh == 'C') { // fixed client center, expand or contract client
|
||||
delta = size - cs;
|
||||
if (delta < 0 || (cp - delta / 2 + size <= min_p + max_s))
|
||||
cp -= delta / 2;
|
||||
else if (cp - delta / 2 < min_p)
|
||||
cp = min_p;
|
||||
else if (delta)
|
||||
cp = min_p + max_s;
|
||||
} else if (pCh == 'Z')
|
||||
cp -= size - cs;
|
||||
|
||||
cs = size;
|
||||
break;
|
||||
}
|
||||
|
||||
if (pCh == '%') // client mid-point position in relation to monitor window area size
|
||||
cp = min_p + max_s * MAX(MIN(pos, 100), 0) / 100 - (cs) / 2;
|
||||
if (pCh == 'm' || pCh == 'M')
|
||||
cp = pos - cs / 2;
|
||||
|
||||
if (!abs_p && cp < min_p)
|
||||
cp = min_p;
|
||||
if (cp + cs > min_p + max_s && !(abs_p && abs_s)) {
|
||||
if (abs_p || cp == min_p)
|
||||
cs = min_p + max_s - cp;
|
||||
else
|
||||
cp = min_p + max_s - cs;
|
||||
}
|
||||
|
||||
*out_p = cp;
|
||||
*out_s = MAX(cs - 2*cbw, 1);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user