Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Added force resizing for some bad resizehint windows #283

Merged
merged 1 commit into from
Jul 6, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions keybinds.h
Original file line number Diff line number Diff line change
Expand Up @@ -142,6 +142,11 @@ static const Button buttons[] =
/* Type Button Mask function arg */
{ XCBButtonPress, RMB, SUPER, ResizeWindow, {0} },
{ XCBButtonRelease, RMB, SUPER, 0, {0} },

/* debug */
{ XCBButtonPress, RMB, SUPER|ALT, ResizeWindowAlt, {0} },
{ XCBButtonRelease, RMB, SUPER|ALT, 0, {0} },

{ XCBButtonPress, LMB, SUPER, DragWindow, {0} },
{ XCBButtonRelease, LMB, SUPER, 0, {0} },
};
Expand Down
199 changes: 199 additions & 0 deletions toggle.c
Original file line number Diff line number Diff line change
Expand Up @@ -584,6 +584,205 @@ ResizeWindow(const Arg *arg)
XCBFlush(_wm.dpy);
}

void
ResizeWindowAlt(const Arg *arg)
{
DEBUG0("Called.");
static u8 running = 0;
if(!arg->v || ((XCBButtonPressEvent *)arg->v)->event == _wm.root || running)
{ return;
}
/* get any requests that may have moved the window back */
XCBSync(_wm.dpy);
XCBGenericEvent *ev = arg->v;
const i64 detail = ((XCBButtonPressEvent *)arg->v)->detail;
XCBWindow win = ((XCBButtonPressEvent *)ev)->event;
Client *c = wintoclient(win);
XCBDisplay *display = _wm.dpy;

i16 curx, cury;
i32 oldw, oldh;
i32 nx, ny;
i32 nw, nh;
i32 oldx, oldy;
i8 horz, vert;
XCBCursor cur;

/* init data */
curx = cury = oldw = oldh = nx = ny = nw = nh = oldx = oldy = horz = vert = 0;

XCBCookie QueryPointerCookie = XCBQueryPointerCookie(display, win);
XCBQueryPointer *pointer = XCBQueryPointerReply(display, QueryPointerCookie);

if(pointer)
{
curx = pointer->root_x;
cury = pointer->root_y;
nx = pointer->win_x;
ny = pointer->win_y;
free(pointer);
}
else
{ return;
}

if(!c)
{
XCBCookie GetGeometryCookie = XCBGetGeometryCookie(display, win);
XCBGeometry *wa = XCBGetGeometryReply(display, GetGeometryCookie);

if(wa)
{
oldw = wa->width;
oldh = wa->height;
oldx = wa->x;
oldy = wa->y;
free(wa);
}
else
{ return;
}
}
else
{
oldw = c->w;
oldh = c->h;
oldx = c->x;
oldy = c->y;
}

if(!c)
{
XCBSizeHints hints;
XCBCookie GetWMNormalHintsCookie = XCBGetWMNormalHintsCookie(_wm.dpy, win);
u8 hintsstatus = XCBGetWMNormalHintsReply(_wm.dpy, GetWMNormalHintsCookie, &hints);
if(hintsstatus)
{
Client c1;
updatesizehints(&c1, &hints);
}
else
{ return;
}
}
else
{
}

horz = nx < oldw / 2 ? -1 : 1;
vert = ny < oldh / 2 ? -1 : 1;

if(horz == -1)
{
/* top left */
if(vert == -1)
{ cur = cursors[CurResizeTopL];
}
/* Bottom Right */
else
{ cur = cursors[CurResizeTopR];
}
}
else
{
/* top right */
if(vert == -1)
{ cur = cursors[CurResizeTopR];
}
/* bottom right */
else
{ cur = cursors[CurResizeTopL];
}
}

XCBCookie GrabPointerCookie = XCBGrabPointerCookie(_wm.dpy, _wm.root, False, MOUSEMASK, XCB_GRAB_MODE_ASYNC, XCB_GRAB_MODE_ASYNC, None, cur, XCB_CURRENT_TIME);
XCBGrabPointer *GrabPointer = XCBGrabPointerReply(_wm.dpy, GrabPointerCookie);

if(!GrabPointer || GrabPointer->status != XCB_GRAB_STATUS_SUCCESS)
{ free(GrabPointer);
return;
}
/* Prevent it from being detected as non floating */
if(c)
{
setfloating(c, 1); c->x += 1;
arrange(c->desktop);
}
else
{ XCBRaiseWindow(display, win);
}
XCBFlush(_wm.dpy);
running = 1;
ev = NULL;
do
{
if(ev)
{
eventhandler(ev);
switch(XCB_EVENT_RESPONSE_TYPE(ev))
{
case XCB_MOTION_NOTIFY:
nw = oldw + horz * (((XCBMotionNotifyEvent *)ev)->root_x - curx);
nh = oldh + vert * (((XCBMotionNotifyEvent *)ev)->root_y - cury);

nx = oldx + !~horz * (oldw - nw);
ny = oldy + !~vert * (oldh - nh);
if(c)
{ resizeclient(c, nx, ny, nw, nh);
}
else
{ XCBMoveResizeWindow(_wm.dpy, win, nx, ny, nw, nh);
}
XCBFlush(_wm.dpy);
break;
/* TODO */
case XCB_BUTTON_PRESS:
break;
case XCB_BUTTON_RELEASE: /* failsafe (mainly chromium) */
if(((XCBButtonPressEvent *)ev)->detail == detail || ((XCBButtonPressEvent *)ev)->detail == RMB)
{ running = 0;
}
break;
case XCB_KEY_PRESS:
break;
case XCB_KEY_RELEASE:
break;
/* this accounts for users killing the window (cause they can) */
case XCB_UNMAP_NOTIFY:
if(((XCBUnmapNotifyEvent *)ev)->window == win)
{ running = 0;
}
break;
case XCB_DESTROY_NOTIFY:
if(((XCBDestroyNotifyEvent *)ev)->window == win)
{ running = 0;
}
break;
}
free(ev);
}
} while(_wm.running && running && !XCBNextEvent(_wm.dpy, &ev));
running = 0;
XCBUngrabPointer(_wm.dpy, XCB_CURRENT_TIME);
Monitor *m;
c = wintoclient(win);
if(c)
{
if ((m = recttomon(c->x, c->y, c->w, c->h)) != _wm.selmon)
{
setclientdesktop(c, m->desksel);
_wm.selmon = m;
focus(NULL);
}
if(DOCKED(c))
{ setfloating(c, 0);
}
}
arrange(_wm.selmon->desksel);
XCBFlush(_wm.dpy);
}


void
SetWindowLayout(const Arg *arg)
{
Expand Down
2 changes: 2 additions & 0 deletions toggle.h
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,8 @@ void Restart(const Arg *arg);
void Quit(const Arg *arg);
/* resizes the current window based on mouse position */
void ResizeWindow(const Arg *arg);
/* resizes the current window based on mouse position no restrictions */
void ResizeWindowAlt(const Arg *arg);
/* sets the window layout based on a enum in dwm.h -> Grid, Floating, Monocle, Tiled */
void SetWindowLayout(const Arg *arg);
/* Sets the size of the master window 0.0 -> 1.0 for the Tiled Layout
Expand Down