mirror of
https://github.com/0intro/wmii
synced 2025-02-08 18:34:43 +03:00
Better modkey resizing behavior in managed mode.
This commit is contained in:
parent
0f8df1e36c
commit
6cc9c57dfd
@ -47,7 +47,7 @@ enum {
|
||||
enum {
|
||||
CurNormal,
|
||||
CurNECorner, CurNWCorner, CurSECorner, CurSWCorner,
|
||||
CurDHArrow, CurMove, CurInput,
|
||||
CurDHArrow, CurMove, CurInput, CurSizing,
|
||||
CurInvisible,
|
||||
CurLast
|
||||
};
|
||||
|
@ -129,14 +129,15 @@ bdown_event(Window *w, XButtonEvent *e) {
|
||||
frame_to_top(f);
|
||||
focus(c, True);
|
||||
break;
|
||||
default: break;
|
||||
default:
|
||||
XAllowEvents(display, ReplayPointer, e->time);
|
||||
break;
|
||||
}
|
||||
XAllowEvents(display, AsyncPointer, e->time);
|
||||
}else{
|
||||
if(e->button == Button1) {
|
||||
if(frame_to_top(f))
|
||||
restack_view(f->view);
|
||||
|
||||
else if(ptinrect(Pt(e->x, e->y), f->grabbox))
|
||||
do_mouse_resize(c, True, CENTER);
|
||||
else if(f->area->floating)
|
||||
|
@ -174,6 +174,7 @@ init_cursors() {
|
||||
create_cursor(CurMove, XC_fleur);
|
||||
create_cursor(CurDHArrow, XC_sb_h_double_arrow);
|
||||
create_cursor(CurInput, XC_xterm);
|
||||
create_cursor(CurSizing, XC_sizing);
|
||||
|
||||
XAllocNamedColor(display, scr.colormap,
|
||||
"black", &black,
|
||||
@ -222,6 +223,21 @@ init_screen(WMScreen *screen) {
|
||||
&mask);
|
||||
}
|
||||
|
||||
static void
|
||||
cleanup() {
|
||||
Client *c;
|
||||
|
||||
for(c=client; c; c=c->next) {
|
||||
reparent_client(c, &scr.root, c->sel->rect.min);
|
||||
if(c->sel->view != screen->sel)
|
||||
unmap_client(c, IconicState);
|
||||
}
|
||||
XSync(display, False);
|
||||
XCloseDisplay(display);
|
||||
ixp_server_close(&srv);
|
||||
close(sleeperfd);
|
||||
}
|
||||
|
||||
struct {
|
||||
uchar rcode, ecode;
|
||||
} itab[] = {
|
||||
@ -242,6 +258,7 @@ struct {
|
||||
*/
|
||||
int
|
||||
wmii_error_handler(Display *dpy, XErrorEvent *error) {
|
||||
static Bool dead;
|
||||
int i;
|
||||
|
||||
if(check_other_wm)
|
||||
@ -254,21 +271,11 @@ wmii_error_handler(Display *dpy, XErrorEvent *error) {
|
||||
|
||||
fprintf(stderr, "%s: fatal error: Xrequest code=%d, Xerror code=%d\n",
|
||||
argv0, error->request_code, error->error_code);
|
||||
if(!dead++)
|
||||
cleanup();
|
||||
return x_error_handler(display, error); /* calls exit() */
|
||||
}
|
||||
|
||||
static void
|
||||
cleanup() {
|
||||
Client *c;
|
||||
|
||||
for(c=client; c; c=c->next) {
|
||||
reparent_client(c, &scr.root, c->sel->rect.min);
|
||||
if(c->sel->view != screen->sel)
|
||||
unmap_client(c, IconicState);
|
||||
}
|
||||
XSync(display, False);
|
||||
}
|
||||
|
||||
static void
|
||||
cleanup_handler(int signal) {
|
||||
sa.sa_handler = SIG_DFL;
|
||||
@ -491,9 +498,6 @@ main(int argc, char *argv[]) {
|
||||
fprintf(stderr, "%s: error: %s\n", argv0, errstr);
|
||||
|
||||
cleanup();
|
||||
XCloseDisplay(display);
|
||||
ixp_server_close(&srv);
|
||||
close(sleeperfd);
|
||||
|
||||
if(exitsignal)
|
||||
raise(exitsignal);
|
||||
|
154
cmd/wmii/mouse.c
154
cmd/wmii/mouse.c
@ -1,6 +1,7 @@
|
||||
/* Copyright ©2006-2007 Kris Maglione <fbsdaemon@gmail.com>
|
||||
* See LICENSE file for license details.
|
||||
*/
|
||||
#include <assert.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
@ -15,6 +16,18 @@ enum {
|
||||
ButtonMask | PointerMotionMask
|
||||
};
|
||||
|
||||
static Window *
|
||||
gethsep(Rectangle r) {
|
||||
Window *w;
|
||||
WinAttr wa;
|
||||
|
||||
wa.background_pixel = def.normcolor.border;
|
||||
w = createwindow(&scr.root, r, scr.depth, InputOutput, &wa, CWBackPixel);
|
||||
mapwin(w);
|
||||
XRaiseWindow(display, w->w);
|
||||
return w;
|
||||
}
|
||||
|
||||
static void
|
||||
rect_morph_xy(Rectangle *r, Point d, Align *mask) {
|
||||
int n;
|
||||
@ -258,11 +271,9 @@ querypointer(Window *w, int *x, int *y) {
|
||||
void
|
||||
warppointer(int x, int y) {
|
||||
XWarpPointer(display,
|
||||
/* src_w */ None,
|
||||
/* dest_w */ scr.root.w,
|
||||
/* src, dest w */ None, scr.root.w,
|
||||
/* src_rect */ 0, 0, 0, 0,
|
||||
/* target */ x, y
|
||||
);
|
||||
/* target */ x, y);
|
||||
}
|
||||
|
||||
static void
|
||||
@ -319,6 +330,139 @@ do_managed_move(Client *c) {
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
mouse_resizecolframe(Frame *f, Align align) {
|
||||
WinAttr wa;
|
||||
XEvent ev;
|
||||
Window *cwin, *hwin;
|
||||
Divide *d;
|
||||
Frame *fp;
|
||||
View *v;
|
||||
Area *a, *ap;
|
||||
Rectangle r;
|
||||
uint minw, minh;
|
||||
int x, y;
|
||||
|
||||
assert((align&(EAST|WEST)) != (EAST|WEST));
|
||||
assert((align&(NORTH|SOUTH)) != (NORTH|SOUTH));
|
||||
|
||||
v = screen->sel;
|
||||
for(a = v->area->next, d = divs; a; a = a->next, d = d->next) {
|
||||
if(a->next == f->area)
|
||||
ap = a;
|
||||
if(a == f->area)
|
||||
break;
|
||||
}
|
||||
for(fp = a->frame; fp; fp = fp->anext)
|
||||
if(fp->anext == f) break;
|
||||
|
||||
if(align&EAST)
|
||||
d = d->next;
|
||||
|
||||
minw = Dx(screen->rect)/NCOL;
|
||||
minh = frame_delta_h() + labelh(def.font);
|
||||
|
||||
if(align&NORTH) {
|
||||
r.min.y = (fp ? fp->rect.min.y : screen->rect.min.y);
|
||||
r.max.y = f->rect.max.y;
|
||||
}else {
|
||||
r.min.y = f->rect.min.y;
|
||||
r.max.y = (f->anext ? f->anext->rect.max.y : a->rect.max.y);
|
||||
}
|
||||
r.min.y += minh;
|
||||
r.max.y -= minh;
|
||||
|
||||
if(align&WEST) {
|
||||
r.min.x = (ap ? ap->rect.min.x : screen->rect.min.x);
|
||||
r.max.x = a->rect.max.x;
|
||||
}else {
|
||||
r.min.x = a->rect.min.x;
|
||||
r.max.x = (a->next ? a->next->rect.max.x : screen->rect.max.x);
|
||||
}
|
||||
r.min.x += minw;
|
||||
r.max.x -= minw;
|
||||
|
||||
cwin = createwindow(&scr.root, r, 0, InputOnly, &wa, 0);
|
||||
mapwin(cwin);
|
||||
|
||||
r = f->rect;
|
||||
if(align&NORTH)
|
||||
r.min.y--;
|
||||
else
|
||||
r.min.y = r.max.y - 1;
|
||||
r.max.y = r.min.y + 2;
|
||||
hwin = gethsep(r);
|
||||
|
||||
if(XGrabPointer(
|
||||
display, scr.root.w,
|
||||
/* owner_events*/ False,
|
||||
/* event_mask */ MouseMask,
|
||||
/* kbd, mouse */ GrabModeAsync, GrabModeAsync,
|
||||
/* confine_to */ cwin->w,
|
||||
/* cursor */ cursor[CurSizing],
|
||||
/* time */ CurrentTime
|
||||
) != GrabSuccess)
|
||||
goto done;
|
||||
|
||||
x = ((align&WEST) ? f->rect.min.x : f->rect.max.x);
|
||||
y = ((align&NORTH) ? f->rect.min.y : f->rect.max.y);
|
||||
warppointer(x, y);
|
||||
|
||||
for(;;) {
|
||||
XMaskEvent(display, MouseMask | ExposureMask, &ev);
|
||||
switch (ev.type) {
|
||||
case ButtonRelease:
|
||||
if(align&WEST)
|
||||
r.min.x = x;
|
||||
else
|
||||
r.max.x = x;
|
||||
if(align&NORTH) {
|
||||
r.min.y = y;
|
||||
r.max.y = f->rect.max.y;
|
||||
}else {
|
||||
r.min.y = f->rect.min.y;
|
||||
r.max.y = y;
|
||||
}
|
||||
resize_colframe(f, &r);
|
||||
|
||||
if(align&WEST)
|
||||
x = f->rect.min.x + 1;
|
||||
else
|
||||
x = f->rect.max.x - 2;
|
||||
if(align&NORTH)
|
||||
y = f->rect.min.y + 1;
|
||||
else
|
||||
y = f->rect.max.y - 2;
|
||||
warppointer(x, y);
|
||||
|
||||
XUngrabPointer(display, CurrentTime);
|
||||
XSync(display, False);
|
||||
goto done;
|
||||
case MotionNotify:
|
||||
x = ev.xmotion.x_root;
|
||||
y = ev.xmotion.y_root;
|
||||
|
||||
if(align&WEST)
|
||||
r.min.x = x;
|
||||
else
|
||||
r.max.x = x;
|
||||
r.min.y = ((align&SOUTH) ? y : y-1);
|
||||
r.max.y = r.min.y+2;
|
||||
|
||||
setdiv(d, x);
|
||||
reshapewin(hwin, r);
|
||||
break;
|
||||
case Expose:
|
||||
dispatch_event(&ev);
|
||||
break;
|
||||
default: break;
|
||||
}
|
||||
}
|
||||
done:
|
||||
destroywindow(cwin);
|
||||
destroywindow(hwin);
|
||||
}
|
||||
|
||||
void
|
||||
mouse_resizecol(Divide *d) {
|
||||
WinAttr wa;
|
||||
@ -404,6 +548,8 @@ do_mouse_resize(Client *c, Bool opaque, Align align) {
|
||||
rects = rects_of_view(f->area->view, &num, (opaque ? c->frame : nil));
|
||||
snap = def.snap;
|
||||
}else{
|
||||
mouse_resizecolframe(f, align);
|
||||
return;
|
||||
rects = nil;
|
||||
snap = 0;
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user