tBorder resizing by dragging. Thanks to Axel Belinfante. - plan9port - [fork] Plan 9 from user space
git clone git://src.adamsgaard.dk/plan9port
Log
Files
Refs
README
LICENSE
---
commit 1cb3fa80938299775382766b4b754e6220bf9831
parent d99b2f34e69bc363c2973a2473e75654196ab40e
Author: rsc 
Date:   Mon, 29 Mar 2004 12:00:15 +0000

Border resizing by dragging.
Thanks to Axel Belinfante.

Diffstat:
  M src/cmd/rio/client.c                |       1 +
  M src/cmd/rio/color.c                 |       6 ++----
  M src/cmd/rio/cursor.c                |       9 +++++++++
  M src/cmd/rio/dat.h                   |      17 +++++++++++++++++
  M src/cmd/rio/event.c                 |      94 +++++++++++++++++++++++++++++++
  M src/cmd/rio/fns.h                   |       6 +++++-
  M src/cmd/rio/grab.c                  |      88 ++++++++++++++++++++++++++-----
  M src/cmd/rio/main.c                  |      41 ++++++++++++++++++++-----------
  M src/cmd/rio/manage.c                |      18 +++++++++++-------
  M src/cmd/rio/menu.c                  |      33 ++++++++++++++++++++++++-------

10 files changed, 268 insertions(+), 45 deletions(-)
---
diff --git a/src/cmd/rio/client.c b/src/cmd/rio/client.c
t@@ -49,6 +49,7 @@ draw_border(Client *c, int active)
                         pixel = c->screen->inactiveborder;
         }
 
+        if (debug) fprintf(stderr, "draw_border 0x%p pixel %ld active %d hold %d\n", c, pixel, active, c->hold);
         XSetWindowBackground(dpy, c->parent, pixel);
         XClearWindow(dpy, c->parent);
 }
diff --git a/src/cmd/rio/color.c b/src/cmd/rio/color.c
t@@ -8,7 +8,7 @@
 #include "fns.h"
 
 unsigned long
-colorpixel(Display *dpy, int depth, unsigned long rgb)
+colorpixel(Display *dpy, int depth, unsigned long rgb, unsigned long def)
 {
         int r, g, b;
 
t@@ -23,9 +23,7 @@ colorpixel(Display *dpy, int depth, unsigned long rgb)
         case 8:
         default:
                 /* not going to waste color map entries */
-                if(rgb == 0xFFFFFF)
-                        return WhitePixel(dpy, DefaultScreen(dpy));
-                return BlackPixel(dpy, DefaultScreen(dpy));
+                return def;
         case 15:
                 r >>= 3;
                 g >>= 3;
diff --git a/src/cmd/rio/cursor.c b/src/cmd/rio/cursor.c
t@@ -198,6 +198,15 @@ ScreenInfo *s;
         s->root_pixmap = XCreatePixmapFromBitmapData(dpy,
                 s->root, grey_bits, grey_width, grey_height,
                 s->black, s->white, DefaultDepth(dpy, s->num));
+        
+        s->bordcurs[BorderN] = XCreateFontCursor(dpy, 138);
+        s->bordcurs[BorderS] = XCreateFontCursor(dpy, 16);
+        s->bordcurs[BorderW] = XCreateFontCursor(dpy, 70);
+        s->bordcurs[BorderE] = XCreateFontCursor(dpy, 96);
+        s->bordcurs[BorderNW] = XCreateFontCursor(dpy, 134);
+        s->bordcurs[BorderSW] = XCreateFontCursor(dpy, 12);
+        s->bordcurs[BorderNE] = XCreateFontCursor(dpy, 136);
+        s->bordcurs[BorderSE] = XCreateFontCursor(dpy, 14);
 }
 
 
diff --git a/src/cmd/rio/dat.h b/src/cmd/rio/dat.h
t@@ -1,6 +1,7 @@
 /* Copyright (c) 1994-1996 David Hogan, see README for licence details */
 
 #define BORDER                _border
+#define CORNER                _corner
 #define        INSET                _inset
 #define MAXHIDDEN        32
 #define B3FIXED         5
t@@ -20,6 +21,7 @@
 typedef struct Client Client;
 typedef struct Menu Menu;
 typedef struct ScreenInfo ScreenInfo;
+typedef enum BorderLocation BorderLocation;
 
 struct Client {
         Window                window;
t@@ -72,6 +74,19 @@ struct Menu {
         int        lasthit;
 };
 
+enum BorderLocation {
+        BorderN,
+        BorderNE,
+        BorderE,
+        BorderSE,
+        BorderS,
+        BorderSW,
+        BorderW,
+        BorderNW,
+        BorderUnknown,
+        NBorder,
+};
+
 struct ScreenInfo {
         int                        num;
         int                        depth;
t@@ -102,6 +117,7 @@ struct ScreenInfo {
         Cursor                sweep0;
         Cursor                boxcurs;
         Cursor                arrow;
+        Cursor                bordcurs[NBorder];
         Pixmap                root_pixmap;
         char                        display[256];        /* arbitrary limit */
 };
t@@ -119,6 +135,7 @@ extern char                 *termprog;
 extern char                 *shell;
 extern char                 *version[];
 extern int                        _border;
+extern int                        _corner;
 extern int                        _inset;
 extern int                        curtime;
 extern int                        debug;
diff --git a/src/cmd/rio/event.c b/src/cmd/rio/event.c
t@@ -78,6 +78,9 @@ mainloop(int shape_event)
                 case EnterNotify:
                         enter(&ev.xcrossing);
                         break;
+                case LeaveNotify:
+                        leave(&ev.xcrossing);
+                        break;
                 case ReparentNotify:
                         reparent(&ev.xreparent);
                         break;
t@@ -85,6 +88,8 @@ mainloop(int shape_event)
                         focusin(&ev.xfocus);
                         break;
                 case MotionNotify:
+                        motionnotify(&ev.xmotion);
+                        break;
                 case Expose:
                 case NoExpose:
                 case FocusOut:
t@@ -450,6 +455,16 @@ enter(XCrossingEvent *e)
 }
 
 void
+leave(XCrossingEvent *e)
+{
+        Client *c;
+
+        c = getclient(e->window, 0);
+        XUndefineCursor(dpy, c->parent);
+/*         XDefineCursor(dpy, c->parent, c->screen->arrow); */
+}
+
+void
 focusin(XFocusChangeEvent *e)
 {
         Client *c;
t@@ -465,3 +480,82 @@ focusin(XFocusChangeEvent *e)
                 active(c);
         }
 }
+
+BorderLocation
+borderlocation(Client *c, int x, int y)
+{
+        if (x <= BORDER) {
+                if (y <= CORNER) {
+                        if (debug) fprintf(stderr, "topleft\n");
+                        return BorderNW;
+                }
+                if (y >= (c->dy + 2*BORDER) - CORNER) {
+                        if (debug) fprintf(stderr, "botleft\n");
+                        return BorderSW;
+                }
+                if (y > CORNER &&
+                y < (c->dy + 2*BORDER) - CORNER) {
+                        if (debug) fprintf(stderr, "left\n");
+                        return BorderW;
+                }
+        } else if (x <= CORNER) {
+                if (y <= BORDER) {
+                        if (debug) fprintf(stderr, "topleft\n");
+                        return BorderNW;
+                }
+                if  (y >= (c->dy + BORDER)) {
+                        if (debug) fprintf(stderr, "botleft\n");
+                        return BorderSW;
+                }
+        } else if (x >= (c->dx + BORDER)) {
+                if (y <= CORNER) {
+                        if (debug) fprintf(stderr, "topright\n");
+                        return BorderNE;
+                }
+                if (y >= (c->dy + 2*BORDER) - CORNER) {
+                        if (debug) fprintf(stderr, "botright\n");
+                        return BorderSE;
+                }
+                if (y > CORNER &&
+                        y < (c->dy + 2*BORDER) - CORNER) {
+                        if (debug) fprintf(stderr, "right\n");
+                        return BorderE;
+                }
+        } else if (x >= (c->dx + 2*BORDER) - CORNER) {
+                if (y <= BORDER) {
+                        if (debug) fprintf(stderr, "topright\n");
+                        return BorderNE;
+                }
+                if  (y >= (c->dy + BORDER)) {
+                        if (debug) fprintf(stderr, "botright\n");
+                        return BorderSE;
+                }
+        } else if (x > CORNER &&
+                       x < (c->dx + 2*BORDER) - CORNER) {
+                if (y <= BORDER) {
+                        if (debug) fprintf(stderr, "top\n");
+                        return BorderN;
+                }
+                if (y >= (c->dy + BORDER)) {
+                        if (debug) fprintf(stderr, "bot\n");
+                        return BorderS;
+                }
+        }
+        return BorderUnknown;
+}
+
+void
+motionnotify(XMotionEvent *e)
+{
+        Client *c;
+        BorderLocation bl;
+
+        c = getclient(e->window, 0);
+        if (c) {
+                bl = borderlocation(c, e->x, e->y);
+                if (bl == BorderUnknown)
+                        XUndefineCursor(dpy, c->parent);
+                else
+                        XDefineCursor(dpy, c->parent, c->screen->bordcurs[bl]);
+        }
+}
diff --git a/src/cmd/rio/fns.h b/src/cmd/rio/fns.h
t@@ -10,7 +10,7 @@
 
 
 /* color.c */
-unsigned long colorpixel(Display*, int, unsigned long);
+unsigned long colorpixel(Display*, int, unsigned long, unsigned long);
 
 /* main.c */
 void        usage();
t@@ -36,8 +36,11 @@ void        cmap();
 void        property();
 void        shapenotify();
 void        enter();
+void        leave();
 void        focusin();
 void        reparent();
+void         motionnotify();
+BorderLocation borderlocation();
 
 /* manage.c */
 int         manage();
t@@ -85,6 +88,7 @@ int         menuhit();
 Client        *selectwin();
 int         sweep();
 int         drag();
+int         pull();
 void        getmouse();
 void        setmouse();
 
diff --git a/src/cmd/rio/grab.c b/src/cmd/rio/grab.c
t@@ -223,7 +223,7 @@ selectwin(int release, int *shift, ScreenInfo *s)
 }
 
 void
-sweepcalc(Client *c, int x, int y)
+sweepcalc(Client *c, int x, int y, BorderLocation bl)
 {
         int dx, dy, sx, sy;
 
t@@ -267,12 +267,55 @@ sweepcalc(Client *c, int x, int y)
 }
 
 void
-dragcalc(Client *c, int x, int y)
+dragcalc(Client *c, int x, int y, BorderLocation bl)
 {
         c->x += x;
         c->y += y;
 }
 
+void
+pullcalc(Client *c, int x, int y, BorderLocation bl)
+{
+        switch(bl) {
+        case BorderN:
+                c->y += y;
+                c->dy -= y;
+                break;
+        case BorderS:
+                c->dy += y;
+                break;
+        case BorderE:
+                c->dx += x;
+                break;
+        case BorderW:
+                c->x += x;
+                c->dx -= x;
+                break;
+        case BorderNW:
+                c->x += x;
+                c->dx -= x;
+                c->y += y;
+                c->dy -= y;
+                break;
+        case BorderNE:
+                c->dx += x;
+                c->y += y;
+                c->dy -= y;
+                break;
+        case BorderSE:
+                c->dx += x;
+                c->dy += y;
+                break;
+        case BorderSW:
+                c->x += x;
+                c->dx -= x;
+                c->dy += y;
+                break;
+        default:
+                break;
+        }
+}
+
 static void
 xcopy(int fwd, Display *dpy, Drawable src, Drawable dst, GC gc, int x, int y, int dx, int dy, int x1, int y1)
 {
t@@ -350,7 +393,7 @@ misleep(int msec)
 }
 
 int
-sweepdrag(Client *c, XButtonEvent *e0, void (*recalc)(Client*, int, int))
+sweepdrag(Client *c, int but, XButtonEvent *e0, BorderLocation bl, void (*recalc)(Client*, int, int, BorderLocation))
 {
         XEvent ev;
         int idle;
t@@ -366,7 +409,9 @@ sweepdrag(Client *c, XButtonEvent *e0, void (*recalc)(Client*, int, int))
         c->y -= BORDER;
         c->dx += 2*BORDER;
         c->dy += 2*BORDER;
-        if (e0)
+        if (bl)
+                getmouse(&cx, &cy, c->screen);
+        else if (e0)
                 getmouse(&c->x, &c->y, c->screen);
         else
                 getmouse(&cx, &cy, c->screen);
t@@ -386,9 +431,9 @@ sweepdrag(Client *c, XButtonEvent *e0, void (*recalc)(Client*, int, int))
                                         idle = 0;
                                 }
                                 if(e0)
-                                        recalc(c, rx, ry);
+                                        recalc(c, rx, ry, bl);
                                 else
-                                        recalc(c, rx-cx, ry-cy);
+                                        recalc(c, rx-cx, ry-cy, bl);
                                 cx = rx;
                                 cy = ry;
                                 drawbound(c, 1);
t@@ -404,7 +449,7 @@ sweepdrag(Client *c, XButtonEvent *e0, void (*recalc)(Client*, int, int))
                         drawbound(c, 0);
                         ungrab(e);
                         XUngrabServer(dpy);
-                        if (e->button != Button3 && c->init)
+                        if (e->button != but && c->init)
                                 goto bad;
                         if (c->dx < 0) {
                                 c->x += c->dx;
t@@ -424,6 +469,7 @@ sweepdrag(Client *c, XButtonEvent *e0, void (*recalc)(Client*, int, int))
                 }
         }
 bad:
+        if (debug) fprintf(stderr, "sweepdrag bad\n");
         c->x = ox;
         c->y = oy;
         c->dx = odx;
t@@ -433,7 +479,7 @@ bad:
 }
 
 int
-sweep(Client *c)
+sweep(Client *c, int but, XButtonEvent *ignored)
 {
         XEvent ev;
         int status;
t@@ -449,16 +495,34 @@ sweep(Client *c)
 
         XMaskEvent(dpy, ButtonMask, &ev);
         e = &ev.xbutton;
-        if (e->button != Button3) {
+        if (e->button != but) {
                 ungrab(e);
                 return 0;
         }
         XChangeActivePointerGrab(dpy, ButtonMask, s->boxcurs, e->time);
-        return sweepdrag(c, e, sweepcalc);
+        return sweepdrag(c, but, e, 0, sweepcalc);
+}
+
+int
+pull(Client *c, int but, XButtonEvent *e)
+{
+        int status;
+        ScreenInfo *s;
+        BorderLocation bl;
+
+        bl = borderlocation(c, e->x, e->y);
+        s = c->screen;
+        status = grab(s->root, s->root, ButtonMask, s->bordcurs[bl], 0);
+        if (status != GrabSuccess) {
+                graberror("pull", status); /* */
+                return 0;
+        }
+
+        return sweepdrag(c, but, 0, bl, pullcalc);
 }
 
 int
-drag(Client *c)
+drag(Client *c, int but)
 {
         int status;
         ScreenInfo *s;
t@@ -469,7 +533,7 @@ drag(Client *c)
                 graberror("drag", status); /* */
                 return 0;
         }
-        return sweepdrag(c, 0, dragcalc);
+        return sweepdrag(c, but, 0, 0, dragcalc);
 }
 
 void
diff --git a/src/cmd/rio/main.c b/src/cmd/rio/main.c
t@@ -31,6 +31,7 @@ char                        *termprog;
 char                        *shell;
 Bool                        shape;
 int                         _border = 4;
+int                         _corner = 25;
 int                         _inset = 1;
 int                         curtime;
 int                         debug;
t@@ -236,13 +237,13 @@ initscreen(ScreenInfo *s, int i, int background)
         else
                 s->display[0] = '\0';
 
-        s->activeholdborder = colorpixel(dpy, s->depth, 0x000099);
-        s->inactiveholdborder = colorpixel(dpy, s->depth, 0x005DBB);
-        s->activeborder = colorpixel(dpy, s->depth ,0x55AAAA);
-        s->inactiveborder = colorpixel(dpy, s->depth, 0x9EEEEE);
-        s->red = colorpixel(dpy, s->depth, 0xDD0000);
         s->black = BlackPixel(dpy, i);
         s->white = WhitePixel(dpy, i);
+        s->activeholdborder = colorpixel(dpy, s->depth, 0x000099, s->white);
+        s->inactiveholdborder = colorpixel(dpy, s->depth, 0x005DBB, s->black);
+        s->activeborder = colorpixel(dpy, s->depth ,0x55AAAA, s->black);
+        s->inactiveborder = colorpixel(dpy, s->depth, 0x9EEEEE, s->white);
+        s->red = colorpixel(dpy, s->depth, 0xDD0000, s->white);
         s->width = WidthOfScreen(ScreenOfDisplay(dpy, i));
         s->height = HeightOfScreen(ScreenOfDisplay(dpy, i));
         s->bkup[0] = XCreatePixmap(dpy, s->root, 2*s->width, BORDER, DefaultDepth(dpy, i));
t@@ -267,21 +268,21 @@ initscreen(ScreenInfo *s, int i, int background)
         gv.foreground = s->red;
         s->gcred = XCreateGC(dpy, s->root, mask, &gv);
 
-        gv.foreground = colorpixel(dpy, s->depth, 0xEEEEEE);
+        gv.foreground = colorpixel(dpy, s->depth, 0xEEEEEE, s->black);
         s->gcsweep = XCreateGC(dpy, s->root, mask, &gv);
 
-        gv.foreground = colorpixel(dpy, s->depth, 0xE9FFE9);
+        gv.foreground = colorpixel(dpy, s->depth, 0xE9FFE9, s->white);
         s->gcmenubg = XCreateGC(dpy, s->root, mask, &gv);
 
-        gv.foreground = colorpixel(dpy, s->depth, 0x448844);
+        gv.foreground = colorpixel(dpy, s->depth, 0x448844, s->black);
         s->gcmenubgs = XCreateGC(dpy, s->root, mask, &gv);
 
         gv.foreground = s->black;
-        gv.background = colorpixel(dpy, s->depth, 0xE9FFE9);
+        gv.background = colorpixel(dpy, s->depth, 0xE9FFE9, s->white);
         s->gcmenufg = XCreateGC(dpy, s->root, mask, &gv);
 
-        gv.foreground = colorpixel(dpy, s->depth, 0xE9FFE9);
-        gv.background = colorpixel(dpy, s->depth, 0x448844);
+        gv.foreground = colorpixel(dpy, s->depth, 0xE9FFE9, s->white);
+        gv.background = colorpixel(dpy, s->depth, 0x448844, s->black);
         s->gcmenufgs = XCreateGC(dpy, s->root, mask, &gv);
 
         initcurs(s);
t@@ -299,9 +300,21 @@ initscreen(ScreenInfo *s, int i, int background)
                 XClearWindow(dpy, s->root);
         } else
                 system("xsetroot -solid grey30");
-
-        s->menuwin = XCreateSimpleWindow(dpy, s->root, 0, 0, 1, 1, 2, colorpixel(dpy, s->depth, 0x88CC88), colorpixel(dpy, s->depth, 0xE9FFE9));
-        s->sweepwin = XCreateSimpleWindow(dpy, s->root, 0, 0, 1, 1, 4, s->red, colorpixel(dpy, s->depth, 0xEEEEEE));
+        s->menuwin = XCreateSimpleWindow(dpy, s->root, 0, 0, 1, 1, 2, colorpixel(dpy, s->depth, 0x88CC88, s->black), colorpixel(dpy, s->depth, 0xE9FFE9, s->white));
+        // s->sweepwin = XCreateWindow(dpy, s->root, 0, 0, 1, 1, 4, s->red, colorpixel(dpy, s->depth, 0xEEEEEE, s->black));
+        {
+                XSetWindowAttributes attrs;
+                attrs.background_pixel =  colorpixel(dpy, s->depth, 0xEEEEEE, s->black);
+                attrs.border_pixel =  s->red;
+                attrs.save_under = True;
+        s->sweepwin = XCreateWindow(dpy, s->root, 0, 0, 1, 1, 4,
+                                                CopyFromParent,
+                                                CopyFromParent,
+                                                CopyFromParent,
+                                                CWBackPixel | CWBorderPixel | CWSaveUnder,
+                                                &attrs
+                                                );
+        }
 }
 
 ScreenInfo*
diff --git a/src/cmd/rio/manage.c b/src/cmd/rio/manage.c
t@@ -107,7 +107,7 @@ manage(Client *c, int mapped)
                         nwin %= 10;
                 }
 
-                if (c->is9term && !(fixsize ? drag(c) : sweep(c))) {
+                if (c->is9term && !(fixsize ? drag(c, Button3) : sweep(c, Button3))) {
                         XKillClient(dpy, c->window);
                         rmclient(c);
                         if (current && current->screen == c->screen)
t@@ -121,13 +121,17 @@ manage(Client *c, int mapped)
         c->parent = XCreateSimpleWindow(dpy, c->screen->root,
                         c->x - BORDER, c->y - BORDER,
                         c->dx + 2*BORDER, c->dy + 2*BORDER,
-                        0, c->screen->black, c->screen->white);
-        XSelectInput(dpy, c->parent, SubstructureRedirectMask | SubstructureNotifyMask);
+                        0,
+                        c->screen->black, c->screen->white);
+        XSelectInput(dpy, c->parent, SubstructureRedirectMask | SubstructureNotifyMask|ButtonPressMask| PointerMotionMask|LeaveWindowMask);
         if (mapped)
                 c->reparenting = 1;
         if (doreshape && !fixsize)
                 XResizeWindow(dpy, c->window, c->dx, c->dy);
         XSetWindowBorderWidth(dpy, c->window, 0);
+        if (1 || c->screen->depth <= 8) {
+                XSetWindowBorderWidth(dpy, c->parent, 1);
+        }
         XReparentWindow(dpy, c->window, c->parent, BORDER, BORDER);
 #ifdef        SHAPE
         if (shape) {
t@@ -328,7 +332,7 @@ getcmaps(Client *c)
                 c->cmap = attr.colormap;
         }
 
-        n = _getprop(c->window, wm_colormaps, XA_WINDOW, 100L, (unsigned char **)&cw);
+        n = _getprop(c->window, wm_colormaps, XA_WINDOW, 100L, (void*)&cw);
         if (c->ncmapwins != 0) {
                 XFree((char *)c->cmapwins);
                 free((char *)c->wmcmaps);
t@@ -421,7 +425,7 @@ get1prop(Window w, Atom a, Atom type)
 {
         char **p, *x;
 
-        if (_getprop(w, a, type, 1L, (unsigned char**)&p) <= 0)
+        if (_getprop(w, a, type, 1L, (void*)&p) <= 0)
                 return 0;
         x = *p;
         XFree((void*) p);
t@@ -458,7 +462,7 @@ getstate(Window w, int *state)
 {
         long *p = 0;
 
-        if (_getprop(w, wm_state, wm_state, 2L, (unsigned char**)&p) <= 0)
+        if (_getprop(w, wm_state, wm_state, 2L, (void*)&p) <= 0)
                 return 0;
 
         *state = (int) *p;
t@@ -476,7 +480,7 @@ getproto(Client *c)
 
         w = c->window;
         c->proto = 0;
-        if ((n = _getprop(w, wm_protocols, XA_ATOM, 20L, (unsigned char**)&p)) <= 0)
+        if ((n = _getprop(w, wm_protocols, XA_ATOM, 20L, (void*)&p)) <= 0)
                 return;
 
         for (i = 0; i < n; i++)
diff --git a/src/cmd/rio/menu.c b/src/cmd/rio/menu.c
t@@ -48,12 +48,31 @@ button(XButtonEvent *e)
                 return;
         c = getclient(e->window, 0);
         if (c) {
+                if (debug) fprintf(stderr, "but: e x=%d y=%d c x=%d y=%d dx=%d dy=%d BORDR %d\n",
+                                e->x, e->y, c->x, c->y, c->dx, c->dy, BORDER);
+            if (e->x <= BORDER || e->x > (c->dx + BORDER) ||
+                e->y <= BORDER || e->y > (c->dy + BORDER)) {
+                        switch (e->button) {
+                        case Button1:
+                        case Button2:
+                                reshape(c, e->button, pull, e);
+                                return;
+                        case Button3:
+                                move(c, Button3);
+                                return;
+                        default:
+                                return;
+                        }
+            }
                 e->x += c->x - BORDER;
                 e->y += c->y - BORDER;
         }
-        else if (e->window != e->root)
+        else if (e->window != e->root) {
+                if (debug) fprintf(stderr, "but no client: e x=%d y=%d\n",
+                                e->x, e->y);
                 XTranslateCoordinates(dpy, e->window, s->root, e->x, e->y,
                                 &e->x, &e->y, &dw);
+        }                
         switch (e->button) {
         case Button1:
                 if (c) {
t@@ -79,10 +98,10 @@ button(XButtonEvent *e)
                 spawn(s);
                 break;
         case 1:         /* Reshape */
-                reshape(selectwin(1, 0, s));
+                reshape(selectwin(1, 0, s), Button3, sweep, 0);
                 break;
         case 2:         /* Move */
-                move(selectwin(0, 0, s));
+                move(selectwin(0, 0, s), Button3);
                 break;
         case 3:         /* Delete */
                 shift = 0;
t@@ -137,7 +156,7 @@ spawn(ScreenInfo *s)
 }
 
 void
-reshape(Client *c)
+reshape(Client *c, int but, int (*fn)(Client*, int, XButtonEvent *), XButtonEvent *e)
 {
         int odx, ody;
 
t@@ -145,7 +164,7 @@ reshape(Client *c)
                 return;
         odx = c->dx;
         ody = c->dy;
-        if (sweep(c) == 0)
+        if (fn(c, but, e) == 0)
                 return;
         active(c);
         top(c);
t@@ -159,11 +178,11 @@ reshape(Client *c)
 }
 
 void
-move(Client *c)
+move(Client *c, int but)
 {
         if (c == 0)
                 return;
-        if (drag(c) == 0)
+        if (drag(c, but) == 0)
                 return;
         active(c);
         top(c);