Annotation of researchv9/X11/src/X.V11R1/demos/wm/test.c, revision 1.1

1.1     ! root        1: /* 
        !             2:  * $Locker:  $ 
        !             3:  */ 
        !             4: static char     *rcsid = "$Header: test.c,v 1.2 87/06/17 16:08:52 swick Locked ";
        !             5: #include <stdio.h>
        !             6: #include <X11/Xlib.h>
        !             7: #include <X11/Xutil.h>
        !             8: #include <X11/Xatom.h>
        !             9: #include <X11/X10.h>
        !            10: #include "test.h"
        !            11: #include "externs.h"
        !            12: #include "dblArrow.h"
        !            13: #include "growBox.h"
        !            14: #include "cross.h"
        !            15: 
        !            16: XAssocTable *frameInfo;
        !            17: XFontStruct *font;
        !            18: Display *dpy;
        !            19: int ErrorFunc();
        !            20: 
        !            21: extern char *malloc();
        !            22: 
        !            23: void MoveOutline();
        !            24: 
        !            25: RootInfoRec *
        !            26: findRootInfo(win)
        !            27:     Window win;
        !            28: {
        !            29:     int        i;
        !            30: 
        !            31:     for (i = 0; i < ScreenCount(dpy); i++) {
        !            32:        if (RootInfo[i].root == win)
        !            33:            return (&(RootInfo[i]));
        !            34:     }
        !            35:     return (NULL);
        !            36: }
        !            37: 
        !            38: #ifdef debug
        !            39: static char *eventtype[] = {
        !            40:        "zero",
        !            41:        "one",
        !            42:        "KeyPress",
        !            43:        "KeyRelease",
        !            44:        "ButtonPress",
        !            45:        "ButtonRelease",
        !            46:        "MotionNotify",
        !            47:        "EnterNotify",
        !            48:        "LeaveNotify",
        !            49:        "FocusIn",
        !            50:        "FocusOut",
        !            51:        "KeymapNotify",
        !            52:        "Expose",
        !            53:        "GraphicsExpose",
        !            54:        "NoExpose",
        !            55:        "VisibilityNotify",
        !            56:        "CreateNotify",
        !            57:        "DestroyNotify",
        !            58:        "UnmapNotify",
        !            59:        "MapNotify",
        !            60:        "MapRequest",
        !            61:        "ReparentNotify",
        !            62:        "ConfigureNotify",
        !            63:        "ConfigureRequest",
        !            64:        "GravityNotify",
        !            65:        "ResizeRequest",
        !            66:        "CirculateNotify",
        !            67:        "CirculateRequest",
        !            68:        "PropertyNotify",
        !            69:        "SelectionClear",
        !            70:        "SelectionRequest",
        !            71:        "SelectionNotify",
        !            72:        "ColormapNotify",
        !            73:        "ClientMessage",
        !            74:        "MappingNotify",
        !            75: };
        !            76: #endif debug
        !            77: 
        !            78: main(argc, argv) int argc; char *argv[];
        !            79: {
        !            80:     Window      parent;
        !            81:     Window     *children;
        !            82:     int         nchildren;
        !            83:     int         i;
        !            84:     Window      dragWindow = None;
        !            85:     Window      resizeWindow = None;
        !            86:     Window      iconifyWindow = None;
        !            87:     int         dragx, dragy;
        !            88:     int         iconPressx, iconPressy;
        !            89:     int         dragHeight, dragWidth;
        !            90:     int         origx, origy, origWidth, origHeight;
        !            91:     int         clampTop, clampBottom, clampLeft, clampRight;
        !            92:     int         buttonsPressed = 0;
        !            93:     int         buttonsDown[128]; /* XXX */
        !            94:     int         hdrWidth;
        !            95: 
        !            96:     XSetWindowAttributes attributes;
        !            97:     XGCValues   gcv;
        !            98: 
        !            99:     for (i = 0; i < 128; i++) buttonsDown[i] = 0; /* XXX */
        !           100:     StartConnectionToServer(argc, argv);
        !           101:     XSetErrorHandler(ErrorHandler);
        !           102: #ifdef debug
        !           103:     XSynchronize(dpy, 1);
        !           104: #endif
        !           105:     frameInfo = XCreateAssocTable(ASSOCTABLESZ);
        !           106:     if (!frameInfo) {
        !           107:        Error(1, "XCreateAssocTable failed\n");
        !           108:     }
        !           109: 
        !           110:     font = XLoadQueryFont(dpy, "fixed");
        !           111:     if (!font)
        !           112:        Error(1, "XFont failed\n");
        !           113: #ifdef debug
        !           114:     printf("descent=%d, ascent=%d, width=%d\n",
        !           115:           font->max_bounds.descent, font->max_bounds.ascent,
        !           116:           font->max_bounds.width);
        !           117: #endif
        !           118: 
        !           119:     RootInfo = (RootInfoRec *) malloc(ScreenCount(dpy) * sizeof(RootInfoRec));
        !           120:     for (i = 0; i < ScreenCount(dpy); i++) {
        !           121:        RootInfo[i].root = RootWindow(dpy, i);
        !           122:        RootInfo[i].doubleArrow = MakePixmap(RootInfo[i].root,
        !           123:                                             dblArrow_bits,
        !           124:                                             dblArrow_width,
        !           125:                                             dblArrow_height);
        !           126:        RootInfo[i].growBox = MakePixmap(RootInfo[i].root,
        !           127:                                         growBox_bits,
        !           128:                                         growBox_width,
        !           129:                                         growBox_height);
        !           130:        RootInfo[i].cross = MakePixmap(RootInfo[i].root,
        !           131:                                       cross_bits,
        !           132:                                       cross_width,
        !           133:                                       cross_height);
        !           134:        gcv.font = font->fid;
        !           135:        gcv.foreground = WhitePixel(dpy, i);
        !           136:        gcv.background = BlackPixel(dpy, i);
        !           137:        RootInfo[i].headerGC = XCreateGC(dpy, RootInfo[i].root,
        !           138:                                         GCForeground | GCBackground | GCFont, &gcv);
        !           139:        gcv.function = GXinvert;
        !           140:        gcv.subwindow_mode = IncludeInferiors;
        !           141:        RootInfo[i].xorGC = XCreateGC(dpy, RootInfo[i].root,
        !           142:                                      GCFunction | GCSubwindowMode, &gcv);
        !           143:        {
        !           144:            Window      retroot;
        !           145:            int         bw, depth;
        !           146:            XGetGeometry(dpy, (Drawable) RootInfo[i].root, &retroot,
        !           147:                         &RootInfo[i].rootx, &RootInfo[i].rooty,
        !           148:            &RootInfo[i].rootwidth, &RootInfo[i].rootheight, &bw, &depth);
        !           149:        }
        !           150:        /*
        !           151:         * select Substructure Redirect on the root to have MapRequest
        !           152:         * events generated instead of windows getting mapped 
        !           153:         */
        !           154:        errorStatus = False;
        !           155:        attributes.event_mask = (SubstructureRedirectMask|
        !           156:                        ButtonPressMask|ButtonReleaseMask|FocusChangeMask);
        !           157:        XChangeWindowAttributes(dpy, RootInfo[i].root, CWEventMask, &attributes);
        !           158:        /* XSelectInput(dpy, root, SubstructureRedirectMask); */
        !           159:        XSync(dpy, False);
        !           160:        if (errorStatus == True) {
        !           161:            fprintf(stderr, "Are you running another window manager?\n");
        !           162:            exit(1);
        !           163:        }
        !           164:        if (XQueryTree(dpy, RootInfo[i].root, &RootInfo[i].root, &parent,
        !           165:                       &children, &nchildren)) {
        !           166:            int         i;
        !           167: 
        !           168:            for (i = 0; i < nchildren; i++) {
        !           169:                if (MappedNotOverride(children[i]))
        !           170:                    AddGizmos(children[i]);
        !           171:            }
        !           172:            if (children)
        !           173:                free((char *)children);
        !           174:        }
        !           175:        XFlush(dpy);
        !           176:     }
        !           177:     XSetErrorHandler(ErrorFunc);
        !           178:     while (1) {
        !           179:        XEvent      ev;
        !           180:        XNextEvent(dpy, &ev);
        !           181: #ifdef debug
        !           182:        printf("event %s ", eventtype[ev.type]);
        !           183: #endif
        !           184:        switch (ev.type) {
        !           185:        case MapRequest:{
        !           186:                Window      w;
        !           187:                GenericAssoc *ga;
        !           188:                w = ev.xmaprequest.window;
        !           189:                ga = (GenericAssoc *) XLookUpAssoc(dpy, frameInfo, (XID) w);
        !           190:                if (ga) {
        !           191:                    XMapWindow(dpy, ga->frame);
        !           192:                }
        !           193:                else {
        !           194:                    AddGizmos(w);
        !           195: #ifdef debug
        !           196:                    printf("delivered to %s of frame %d\n",
        !           197:                           WindowType(w), Frame(w));
        !           198: #endif
        !           199:                }
        !           200:                break;
        !           201:            }
        !           202:        case UnmapNotify:{
        !           203:                GenericAssoc *ga;
        !           204:                Window      w;
        !           205:                w = ev.xunmap.window;
        !           206: #ifdef debug
        !           207:                printf("delivered to %s of frame %d\n",
        !           208:                       WindowType(w), Frame(w));
        !           209: #endif
        !           210:                ga = (GenericAssoc *) XLookUpAssoc(dpy, frameInfo, (XID) w);
        !           211:                if (ga && (ga->client == w))
        !           212:                    XUnmapWindow(dpy, ga->frame);
        !           213:                break;
        !           214:            }
        !           215:        case DestroyNotify:{
        !           216:                GenericAssoc *ga;
        !           217:                Window      w;
        !           218:                w = ev.xdestroywindow.window;
        !           219: #ifdef debug
        !           220:                printf("delivered to %s of frame %d\n",
        !           221:                       WindowType(w), Frame(w));
        !           222: #endif
        !           223:                ga = (GenericAssoc *) XLookUpAssoc(dpy, frameInfo, (XID) w);
        !           224:                if (ga && (ga->client == w))
        !           225:                    RemoveGizmos(ga);
        !           226:                break;
        !           227:            }
        !           228:        case PropertyNotify:{
        !           229:                GenericAssoc *ga;
        !           230:                Window      w;
        !           231:                Window      root;
        !           232:                int         x, y, wd, ht, bw, d;
        !           233: 
        !           234:                w = ev.xproperty.window;
        !           235:                XGetGeometry(dpy, (Drawable) w, &root, &x, &y, &wd, &ht, &bw, &d);
        !           236:                ga = (GenericAssoc *) XLookUpAssoc(dpy, frameInfo, (XID) w);
        !           237:                if (!ga || w != ga->client)
        !           238:                    break;
        !           239:                switch (ev.xproperty.atom) {
        !           240:                case XA_WM_NAME:
        !           241:                    ProcessNewName(root, ga);
        !           242:                    break;
        !           243:                case XA_WM_ICON_NAME:
        !           244:                    ProcessNewIconName(root, ga);
        !           245:                    break;
        !           246:                default:
        !           247:                    break;
        !           248:                }
        !           249:                break;
        !           250:            }
        !           251:        case ButtonPress:{
        !           252:                GenericAssoc *ga;
        !           253:                Window      w;
        !           254:                w = ev.xbutton.window;
        !           255: #ifdef debug
        !           256:                printf("delivered to %s of frame %d\n",
        !           257:                       WindowType(w), Frame(w));
        !           258: #endif
        !           259:                if (buttonsDown[ev.xbutton.button])
        !           260:                   break;
        !           261:                buttonsDown[ev.xbutton.button] = 1;
        !           262:                if (buttonsPressed++) {
        !           263:                    iconifyWindow = None;
        !           264:                    dragWindow = None;
        !           265:                    resizeWindow = None;
        !           266:                    MoveOutline(ev.xbutton.root,
        !           267:                                ev.xbutton.x_root - dragx - BORDERWIDTH,
        !           268:                                ev.xbutton.y_root - dragy - BORDERWIDTH,
        !           269:                                0, 0);
        !           270:                    XUngrabServer(dpy);
        !           271:                    break;
        !           272:                }
        !           273:                ga = (GenericAssoc *) XLookUpAssoc(dpy, frameInfo, (XID) w);
        !           274:                if (ga && (ga->rbox == w) && resizeWindow == None) {
        !           275:                    Window      junkRoot;
        !           276:                    int         junkbw, junkDepth;
        !           277:                    resizeWindow = ga->frame;
        !           278:                    XGrabServer(dpy);
        !           279:                    XGetGeometry(dpy, (Drawable) resizeWindow, &junkRoot,
        !           280:                        &dragx, &dragy, &dragWidth, &dragHeight, &junkbw,
        !           281:                                 &junkDepth);
        !           282:                    dragx += BW;
        !           283:                    dragy += BW;
        !           284:                    origx = dragx;
        !           285:                    origy = dragy;
        !           286:                    origWidth = dragWidth;
        !           287:                    origHeight = dragHeight;
        !           288:                    clampTop = clampBottom = clampLeft = clampRight = 0;
        !           289:                }
        !           290:                else if (ga && (ga->iconWindow == w)) {
        !           291:                    iconifyWindow = w;
        !           292:                    if (ev.xbutton.state & ShiftMask) {
        !           293:                        Window      junkRoot;
        !           294:                        int         junkX, junkY, junkbw, junkDepth;
        !           295:                        dragWindow = w;
        !           296:                        dragx = ev.xbutton.x;
        !           297:                        dragy = ev.xbutton.y;
        !           298:                        XGrabServer(dpy);
        !           299:                        XGetGeometry(dpy, (Drawable) dragWindow,
        !           300:                                     &junkRoot, &junkX,
        !           301:                                &junkY, &dragWidth, &dragHeight, &junkbw,
        !           302:                                     &junkDepth);
        !           303: #ifdef debug
        !           304:                        printf("From: x=%d, y=%d, w=%d, h=%d\n",
        !           305:                               junkX, junkY, dragWidth, dragHeight);
        !           306: #endif
        !           307:                        MoveOutline(ev.xbutton.root,
        !           308:                                 ev.xbutton.x_root - dragx - BORDERWIDTH,
        !           309:                                 ev.xbutton.y_root - dragy - BORDERWIDTH,
        !           310:                                    dragWidth + 2 * BORDERWIDTH,
        !           311:                                    dragHeight + 2 * BORDERWIDTH);
        !           312:                    }
        !           313:                }
        !           314:                else if (ga && (ga->upbox == w)) {
        !           315:                    XWindowChanges wc;
        !           316:                    wc.stack_mode = Opposite;
        !           317:                    XConfigureWindow(dpy, ga->frame, CWStackMode, &wc);
        !           318:                }
        !           319:                else if (ga && (ga->iconify == w) && (iconifyWindow == None)) {
        !           320:                    Window      junkRoot;
        !           321:                    int         junkX, junkY, junkbw, junkDepth;
        !           322:                    iconifyWindow = w;
        !           323:                    iconPressx = ev.xbutton.x_root;
        !           324:                    iconPressy = ev.xbutton.y_root;
        !           325:                    dragx = 0;
        !           326:                    dragy = 0;
        !           327:                    dragWindow = ga->iconWindow;
        !           328:                    XGrabServer(dpy);
        !           329:                    XGetGeometry(dpy, (Drawable) dragWindow,
        !           330:                                 &junkRoot, &junkX,
        !           331:                                 &junkY, &dragWidth, &dragHeight, &junkbw,
        !           332:                                 &junkDepth);
        !           333: #ifdef debug
        !           334:                    printf("From: x=%d, y=%d, w=%d, h=%d\n",
        !           335:                           junkX, junkY, dragWidth, dragHeight);
        !           336: #endif
        !           337:                    MoveOutline(ev.xbutton.root,
        !           338:                                ev.xbutton.x_root - dragx - BORDERWIDTH,
        !           339:                                ev.xbutton.y_root - dragy - BORDERWIDTH,
        !           340:                                dragWidth + 2 * BORDERWIDTH,
        !           341:                                dragHeight + 2 * BORDERWIDTH);
        !           342:                }
        !           343:                else if (ga && (ga->header == w) && dragWindow == None) {
        !           344:                    Window      junkRoot;
        !           345:                    int         junkX, junkY, junkbw, junkDepth;
        !           346:                    dragWindow = ga->frame;
        !           347:                    dragx = ev.xbutton.x + UPBOXWIDTH + ICONIFYWIDTH + BORDERWIDTH;
        !           348:                    dragy = ev.xbutton.y;
        !           349:                    hdrWidth = ga->headerWidth;
        !           350:                    XGrabServer(dpy);
        !           351:                    XGetGeometry(dpy, (Drawable) dragWindow, &junkRoot, &junkX,
        !           352:                                 &junkY, &dragWidth, &dragHeight, &junkbw,
        !           353:                                 &junkDepth);
        !           354: #ifdef debug
        !           355:                    printf("From: x=%d, y=%d, w=%d, h=%d\n",
        !           356:                           junkX, junkY, dragWidth, dragHeight);
        !           357: #endif
        !           358:                    MoveOutline(ev.xbutton.root,
        !           359:                                ev.xbutton.x_root - dragx - BORDERWIDTH,
        !           360:                                ev.xbutton.y_root - dragy - BORDERWIDTH,
        !           361:                                dragWidth + 2 * BORDERWIDTH,
        !           362:                                dragHeight + 2 * BORDERWIDTH);
        !           363:                }
        !           364:                else {
        !           365:                    int newx, newy;
        !           366:                    Window newRoot;
        !           367:                    RootInfoRec *ro = findRootInfo(ev.xbutton.root);
        !           368:                    RootInfoRec *rn = ro;
        !           369: 
        !           370:                    if (++rn >= (RootInfo + ScreenCount(dpy)))
        !           371:                        rn = RootInfo;
        !           372: #ifdef debug
        !           373:                    printf("Roots 0x%x: old 0x%x, new 0x%x\n", ev.xbutton.root, ro, rn);
        !           374: #endif
        !           375:                    if (rn != ro) {
        !           376: #ifdef debug
        !           377:                        printf("Warp from %d to %d new root is 0x%x\n",
        !           378:                               (ro - RootInfo), (rn - RootInfo), rn->root);
        !           379: #endif
        !           380:                        newx = (((ev.xbutton.x_root - ro->rootx)*100/(ro->rootwidth))
        !           381:                            *(rn->rootwidth))/100 + rn->rootx;
        !           382:                        newy = (((ev.xbutton.y_root - ro->rooty)*100/(ro->rootheight))
        !           383:                            *(rn->rootheight))/100 + rn->rooty;
        !           384:                        XWarpPointer(dpy, None, rn->root, 0, 0, 0, 0, newx, newy);
        !           385:                    }
        !           386:                }
        !           387:                break;
        !           388:            }
        !           389:        case MotionNotify:{
        !           390:                Window      junkRoot, junkChild;
        !           391:                int         junkx, junky, junkrx, junkry;
        !           392:                unsigned int junkMask;
        !           393:                Window      root;
        !           394: #ifdef debug
        !           395:                printf("\n");
        !           396: #endif
        !           397:                if (QLength(dpy)) {
        !           398:                    XEvent      rete;
        !           399:                    XPeekEvent(dpy, &rete);
        !           400:                    if (rete.type == MotionNotify &&
        !           401:                        rete.xmotion.window == ev.xmotion.window) {
        !           402:                        break;
        !           403:                    }
        !           404:                }
        !           405:                root = ev.xmotion.root;
        !           406:                if (dragWindow != None) {
        !           407:                    int         x, y;
        !           408:                    x = ev.xmotion.x_root - dragx;
        !           409:                    y = ev.xmotion.y_root - dragy;
        !           410:                    if (iconifyWindow != None)
        !           411:                        MakeReachable(root, &x, &y, dragWidth,
        !           412:                                      dragHeight);
        !           413:                    else {
        !           414:                        x += UPBOXWIDTH + ICONIFYWIDTH + BW;
        !           415:                        MakeReachable(root, &x, &y, hdrWidth,
        !           416:                                      TITLEHEIGHT);
        !           417:                        x -= UPBOXWIDTH + ICONIFYWIDTH + BW;
        !           418:                    }
        !           419:                    MoveOutline(root,
        !           420:                                x - BORDERWIDTH, y - BORDERWIDTH,
        !           421:                                dragWidth + 2 * BORDERWIDTH,
        !           422:                                dragHeight + 2 * BORDERWIDTH);
        !           423:                    XQueryPointer(dpy, root, &junkRoot, &junkChild,
        !           424:                                  &junkrx, &junkry,
        !           425:                                  &junkx, &junky, &junkMask);
        !           426:                }
        !           427:                else if (resizeWindow != None) {
        !           428:                    int         action = 0;
        !           429:                    if (clampTop) {
        !           430:                        int         delta = ev.xmotion.y_root - dragy;
        !           431:                        if (dragHeight - delta < MINHEIGHT) {
        !           432:                            delta = dragHeight - MINHEIGHT;
        !           433:                            clampTop = 0;
        !           434:                        }
        !           435:                        dragy += delta;
        !           436:                        dragHeight -= delta;
        !           437:                        action = 1;
        !           438:                    }
        !           439:                    else if (ev.xmotion.y_root <= dragy ||
        !           440:                             ev.xmotion.y_root == findRootInfo(root)->rooty) {
        !           441:                        dragy = ev.xmotion.y_root;
        !           442:                        dragHeight = origy + origHeight -
        !           443:                            ev.xmotion.y_root;
        !           444:                        clampBottom = 0;
        !           445:                        clampTop = 1;
        !           446:                        action = 1;
        !           447:                    }
        !           448:                    if (clampLeft) {
        !           449:                        int         delta = ev.xmotion.x_root - dragx;
        !           450:                        if (dragWidth - delta < MINWIDTH) {
        !           451:                            delta = dragWidth - MINWIDTH;
        !           452:                            clampLeft = 0;
        !           453:                        }
        !           454:                        dragx += delta;
        !           455:                        dragWidth -= delta;
        !           456:                        action = 1;
        !           457:                    }
        !           458:                    else if (ev.xmotion.x_root <= dragx ||
        !           459:                             ev.xmotion.x_root == findRootInfo(root)->rootx) {
        !           460:                        dragx = ev.xmotion.x_root;
        !           461:                        dragWidth = origx + origWidth -
        !           462:                            ev.xmotion.x_root;
        !           463:                        clampRight = 0;
        !           464:                        clampLeft = 1;
        !           465:                        action = 1;
        !           466:                    }
        !           467:                    if (clampBottom) {
        !           468:                        int         delta = ev.xmotion.y_root - dragy - dragHeight;
        !           469:                        if (dragHeight + delta < MINHEIGHT) {
        !           470:                            delta = MINHEIGHT - dragHeight;
        !           471:                            clampBottom = 0;
        !           472:                        }
        !           473:                        dragHeight += delta;
        !           474:                        action = 1;
        !           475:                    }
        !           476:                    else if (ev.xmotion.y_root >= dragy + dragHeight - 1 ||
        !           477:                           ev.xmotion.y_root == findRootInfo(root)->rooty
        !           478:                           + findRootInfo(root)->rootheight - 1) {
        !           479:                        dragy = origy;
        !           480:                        dragHeight = 1 + ev.xmotion.y_root - dragy;
        !           481:                        clampTop = 0;
        !           482:                        clampBottom = 1;
        !           483:                        action = 1;
        !           484:                    }
        !           485:                    if (clampRight) {
        !           486:                        int         delta = ev.xmotion.x_root - dragx - dragWidth;
        !           487:                        if (dragWidth + delta < MINWIDTH) {
        !           488:                            delta = MINWIDTH - dragWidth;
        !           489:                            clampRight = 0;
        !           490:                        }
        !           491:                        dragWidth += delta;
        !           492:                        action = 1;
        !           493:                    }
        !           494:                    else if (ev.xmotion.x_root >= dragx + dragWidth - 1 ||
        !           495:                             ev.xmotion.x_root == findRootInfo(root)->rootx +
        !           496:                             findRootInfo(root)->rootwidth - 1) {
        !           497:                        dragx = origx;
        !           498:                        dragWidth = 1 + ev.xmotion.x_root - origx;
        !           499:                        clampLeft = 0;
        !           500:                        clampRight = 1;
        !           501:                        action = 1;
        !           502:                    }
        !           503:                    if (action) {
        !           504:                        MoveOutline(root,
        !           505:                                    dragx - BORDERWIDTH,
        !           506:                                    dragy - BORDERWIDTH,
        !           507:                                    dragWidth + 2 * BORDERWIDTH,
        !           508:                                    dragHeight + 2 * BORDERWIDTH);
        !           509:                        XQueryPointer(dpy, root, &junkRoot, &junkChild,
        !           510:                                      &junkrx, &junkry,
        !           511:                                      &junkx, &junky, &junkMask);
        !           512:                    }
        !           513:                }
        !           514:                break;
        !           515:            }
        !           516:        case ButtonRelease:{
        !           517:                Window      w;
        !           518:                GenericAssoc *ga;
        !           519:                if (!buttonsDown[ev.xbutton.button])
        !           520:                   break;
        !           521:                buttonsDown[ev.xbutton.button] = 0;
        !           522:                buttonsPressed--;
        !           523:                w = ev.xbutton.window;
        !           524:                ga = (GenericAssoc *) XLookUpAssoc(dpy, frameInfo,
        !           525:                                                   (XID) w);
        !           526: 
        !           527:                if (ga && (ga->header == w)
        !           528:                    && (ga->frame == dragWindow)) {
        !           529:                    XWindowChanges wc;
        !           530:                    wc.x = ev.xbutton.x_root - dragx;
        !           531:                    wc.y = ev.xbutton.y_root - dragy;
        !           532:                    wc.x += UPBOXWIDTH + ICONIFYWIDTH + BW;
        !           533:                    MakeReachable(ev.xbutton.root, &wc.x, &wc.y, ga->headerWidth,
        !           534:                                  TITLEHEIGHT);
        !           535:                    wc.x -= UPBOXWIDTH + ICONIFYWIDTH + 2 * BW;
        !           536:                    /*
        !           537:                     * the extra BW is because XReconfigureWindow includes
        !           538:                     * the border width in x and y, but not in width and
        !           539:                     * height 
        !           540:                     */
        !           541:                    wc.y -= BW;
        !           542: #ifdef debug
        !           543:                    printf("delivered to %s of frame %d\n",
        !           544:                           WindowType(w), Frame(w));
        !           545: #endif
        !           546:                    MoveOutline(ev.xbutton.root, 0, 0, 0, 0);
        !           547:                    XUngrabServer(dpy);
        !           548: #ifdef debug
        !           549:                    printf("To x=%d, y=%d\n",
        !           550:                           ev.xbutton.x_root - dragx,
        !           551:                           ev.xbutton.y_root - dragy);
        !           552: #endif
        !           553:                    XConfigureWindow(dpy, dragWindow,
        !           554:                                       CWX | CWY, &wc);
        !           555:                    dragWindow = None;
        !           556:                }
        !           557:                else if (ga && (ga->rbox == w)
        !           558:                         && (ga->frame == resizeWindow)) {
        !           559: #ifdef debug
        !           560:                    printf("delivered to %s of frame %d\n",
        !           561:                           WindowType(w), Frame(w));
        !           562: #endif
        !           563:                    MoveOutline(ev.xbutton.root, 0, 0, 0, 0);
        !           564:                    XUngrabServer(dpy);
        !           565:                    ReconfigureFrameAndClient(ev.xbutton.root, ga, dragx,
        !           566:                        dragy + TITLEHEIGHT + BORDERWIDTH, dragWidth,
        !           567:                                 dragHeight - TITLEHEIGHT - BORDERWIDTH);
        !           568:                    resizeWindow = None;
        !           569:                }
        !           570:                else if (ga && (ga->iconify == w) && (iconifyWindow == w)) {
        !           571:                    XWindowChanges wc;
        !           572: #ifdef debug
        !           573:                    printf("delivered to %s of frame %d\n",
        !           574:                           WindowType(w), Frame(w));
        !           575: #endif
        !           576:                    if (ga->iconknown && iconPressx == ev.xbutton.x_root
        !           577:                        && iconPressy == ev.xbutton.y_root) {
        !           578:                        wc.x = ga->iconx;
        !           579:                        wc.y = ga->icony;
        !           580:                    }
        !           581:                    else {
        !           582:                        ga->iconknown = True;
        !           583:                        wc.x = ga->iconx = ev.xbutton.x_root;
        !           584:                        wc.y = ga->icony = ev.xbutton.y_root;
        !           585:                    }
        !           586:                    MakeReachable(ev.xbutton.root, &wc.x, &wc.y,
        !           587:                                  dragWidth, dragHeight);
        !           588:                    wc.x -= BW;
        !           589:                    wc.y -= BW;
        !           590:                    MoveOutline(ev.xbutton.root, 0, 0, 0, 0);
        !           591:                    XUngrabServer(dpy);
        !           592:                    dragWindow = None;
        !           593:                    iconifyWindow = None;
        !           594:                    XConfigureWindow(dpy, ga->iconWindow, CWX | CWY, &wc);
        !           595:                    XUnmapWindow(dpy, ga->frame);
        !           596:                    XMapWindow(dpy, ga->iconWindow);
        !           597:                }
        !           598:                else if (ga && (ga->iconWindow == w) && (iconifyWindow == w)) {
        !           599:                    if (dragWindow == w) {
        !           600:                        XWindowChanges wc;
        !           601:                        wc.x = ev.xbutton.x_root - dragx;
        !           602:                        wc.y = ev.xbutton.y_root - dragy;
        !           603: #ifdef debug
        !           604:                        printf("delivered to %s of frame %d\n",
        !           605:                               WindowType(w), Frame(w));
        !           606: #endif
        !           607:                        MoveOutline(ev.xbutton.root, 0, 0, 0, 0);
        !           608:                        XUngrabServer(dpy);
        !           609:                        ga->iconx = wc.x;
        !           610:                        ga->icony = wc.y;
        !           611: #ifdef debug
        !           612:                        printf("To x=%d, y=%d\n",
        !           613:                               ev.xbutton.x_root - dragx,
        !           614:                               ev.xbutton.y_root - dragy);
        !           615: #endif
        !           616:                        MakeReachable(ev.xbutton.root, &wc.x, &wc.y, dragWidth,
        !           617:                                      dragHeight);
        !           618:                        wc.x -= BW;
        !           619:                        wc.y -= BW;
        !           620:                        XConfigureWindow(
        !           621:                                        dpy, dragWindow, CWX | CWY, &wc);
        !           622:                        dragWindow = None;
        !           623:                    }
        !           624:                    else {
        !           625:                        XUnmapWindow(dpy, ga->iconWindow);
        !           626:                        XMapWindow(dpy, ga->frame);
        !           627:                    }
        !           628:                    iconifyWindow = None;
        !           629:                }
        !           630:                else {
        !           631: #ifdef debug
        !           632:                    printf("delivered to ???\n");
        !           633: #endif
        !           634:                }
        !           635:                break;
        !           636:            }
        !           637:        case ConfigureRequest:{
        !           638:                Window      w;
        !           639:                GenericAssoc *ga;
        !           640:                XWindowChanges wc;
        !           641:                XConfigureRequestEvent evc;
        !           642:                evc = ev.xconfigurerequest;
        !           643:                w = evc.window;
        !           644:                ga = (GenericAssoc *) XLookUpAssoc(dpy, frameInfo, (XID) w);
        !           645:                if (!ga) {
        !           646: #ifdef debug
        !           647:                    printf("delivered to unknown client\n");
        !           648: #endif
        !           649:                    wc.x = evc.x;
        !           650:                    wc.y = evc.y;
        !           651:                    wc.width = evc.width;
        !           652:                    wc.height = evc.height;
        !           653:                    wc.border_width = evc.border_width;
        !           654:                    wc.sibling = evc.above;
        !           655:                    wc.stack_mode = Above;
        !           656:                    XConfigureWindow(dpy, w, CWX | CWY | CWWidth |
        !           657:                                       CWBorderWidth | CWSibling | CWStackMode,
        !           658:                                       &wc);
        !           659:                }
        !           660:                else if (ga->client == w) {
        !           661:                    int         x, y;
        !           662:                    Window      root, jc;
        !           663:                    int         ht, wd, bw, d, x1, y1;
        !           664: #ifdef debug
        !           665:                    printf("delivered to %s of frame %d\n",
        !           666:                           WindowType(w), Frame(w));
        !           667: #endif
        !           668:                    XGetGeometry(dpy,
        !           669:                                 (Drawable) w, &root, &x1, &y1, &wd, &ht, &bw, &d);
        !           670:                    XTranslateCoordinates(dpy, w, root, 0, 0, &x, &y, &jc);
        !           671:                    ReconfigureFrameAndClient
        !           672:                        (root, ga, x, y, evc.width, evc.height);
        !           673:                }
        !           674:                else {
        !           675: #ifdef debug
        !           676:                    printf("delivered to %s of frame %d\n",
        !           677:                           WindowType(w), Frame(w));
        !           678: #endif
        !           679:                }
        !           680:                break;
        !           681:            }
        !           682:        case Expose:{
        !           683:                Window      w = ev.xexpose.window;
        !           684:                GenericAssoc *ga;
        !           685:                Window      root;
        !           686:                int         x, y, wd, ht, bw, d;
        !           687: 
        !           688: #ifdef debug
        !           689:                printf("delivered to %s of frame %d\n",
        !           690:                       WindowType(w), Frame(w));
        !           691: #endif
        !           692:                ga = (GenericAssoc *) XLookUpAssoc(dpy, frameInfo, (XID) w);
        !           693:                XGetGeometry(dpy, (Drawable) w, &root, &x, &y, &wd, &ht, &bw, &d);
        !           694:                if (ga && ga->header == w) {
        !           695:                    int         x;
        !           696:                    x = (ga->headerWidth -
        !           697:                         XTextWidth(font, ga->name, ga->namelen)) / 2;
        !           698:                    XDrawString(dpy, w, findRootInfo(root)->headerGC, x,
        !           699:                          font->max_bounds.ascent + 5,
        !           700:                          ga->name, ga->namelen);
        !           701:                }
        !           702:                else if (ga && ga->iconWindow == w) {
        !           703:                    if (ga->iconnamelen == 0)
        !           704:                        XDrawString(dpy, w, findRootInfo(root)->headerGC, 2,
        !           705:                              font->max_bounds.ascent + 5,
        !           706:                              ga->name, ga->namelen);
        !           707:                    else
        !           708:                        XDrawString(dpy, w, findRootInfo(root)->headerGC, 2,
        !           709:                              font->max_bounds.ascent + 5,
        !           710:                              ga->iconname, ga->iconnamelen);
        !           711:                }               /* else if (ga && (ga->upbox == w)) {
        !           712:                                 * XCopyArea(dpy, doubleArrow, w,
        !           713:                                 * headerGC, 0, 0, UPBOXWIDTH,
        !           714:                                 * TITLEHEIGHT, 0, 0); } else if (ga &&
        !           715:                                 * (ga->rbox == w)) { XCopyArea(dpy,
        !           716:                                 * growBox, w, headerGC, 0, 0, UPBOXWIDTH,
        !           717:                                 * TITLEHEIGHT, 0, 0); } else if (ga &&
        !           718:                                 * (ga->iconify == w)) { XCopyArea(dpy,
        !           719:                                 * cross, w, headerGC, 0, 0, UPBOXWIDTH,
        !           720:                                 * TITLEHEIGHT, 0, 0); } */
        !           721:                break;
        !           722:            }
        !           723:        case FocusIn: break;    /* just ignore */
        !           724:        case FocusOut: {
        !           725:                if (ev.xfocus.detail == NotifyPointerRoot)
        !           726:                    XSetInputFocus(dpy, PointerRoot, None, CurrentTime);
        !           727:                break;
        !           728:            }
        !           729:        default:
        !           730: #ifdef debug
        !           731:            printf("\n");
        !           732: #endif
        !           733:            ;
        !           734:        }
        !           735:     }
        !           736: }
        !           737: 
        !           738: int
        !           739: ErrorFunc(dpy, event)
        !           740:        Display *dpy;
        !           741:        XErrorEvent *event;
        !           742: {
        !           743:     switch (event->error_code) {
        !           744:        case BadWindow:
        !           745:        case BadDrawable:
        !           746:                (void) fprintf(stderr, "wm: Window #0x%x disappeared!\n",
        !           747:                        event->resourceid);
        !           748:                break;
        !           749:        default:
        !           750:                _XDefaultError(dpy, event);
        !           751:     }
        !           752:     return (0);
        !           753: }
        !           754: 
        !           755: Bool
        !           756: MappedNotOverride(w) Window w;
        !           757: {
        !           758: XWindowAttributes wa;
        !           759:        XGetWindowAttributes(dpy, w, &wa);
        !           760:        return ((wa.map_state != IsUnmapped) && (wa.override_redirect != True));
        !           761: }
        !           762: 
        !           763: static void
        !           764: MoveOutline(root, x, y, width, height)
        !           765:     Window root;
        !           766:     int x, y, width, height;
        !           767: {
        !           768:     static int  lastx = 0;
        !           769:     static int  lasty = 0;
        !           770:     static int  lastWidth = 0;
        !           771:     static int  lastHeight = 0;
        !           772:     XRectangle  outline[8];
        !           773:     XRectangle *r = outline;
        !           774: 
        !           775:     if (x == lastx && y == lasty && width == lastWidth && height == lastHeight)
        !           776:        return;
        !           777:     if (lastWidth || lastHeight) {
        !           778:        r->x = lastx;
        !           779:        r->y = lasty;
        !           780:        r->width = lastWidth;
        !           781:        r++->height = BORDERWIDTH;
        !           782:        r->x = lastx;
        !           783:        r->y = lasty + lastHeight - BORDERWIDTH;
        !           784:        r->width = lastWidth;
        !           785:        r++->height = BORDERWIDTH;
        !           786:        r->x = lastx;
        !           787:        r->y = lasty + BORDERWIDTH;
        !           788:        r->width = BORDERWIDTH;
        !           789:        r++->height = lastHeight - 2 * BORDERWIDTH;
        !           790:        r->x = lastx + lastWidth - BORDERWIDTH;
        !           791:        r->y = lasty + BORDERWIDTH;
        !           792:        r->width = BORDERWIDTH;
        !           793:        r++->height = lastHeight - 2 * BORDERWIDTH;
        !           794:     }
        !           795:     lastx = x;
        !           796:     lasty = y;
        !           797:     lastWidth = width;
        !           798:     lastHeight = height;
        !           799:     if (lastWidth || lastHeight) {
        !           800:        r->x = lastx;
        !           801:        r->y = lasty;
        !           802:        r->width = lastWidth;
        !           803:        r++->height = BORDERWIDTH;
        !           804:        r->x = lastx;
        !           805:        r->y = lasty + lastHeight - BORDERWIDTH;
        !           806:        r->width = lastWidth;
        !           807:        r++->height = BORDERWIDTH;
        !           808:        r->x = lastx;
        !           809:        r->y = lasty + BORDERWIDTH;
        !           810:        r->width = BORDERWIDTH;
        !           811:        r++->height = lastHeight - 2 * BORDERWIDTH;
        !           812:        r->x = lastx + lastWidth - BORDERWIDTH;
        !           813:        r->y = lasty + BORDERWIDTH;
        !           814:        r->width = BORDERWIDTH;
        !           815:        r++->height = lastHeight - 2 * BORDERWIDTH;
        !           816:     }
        !           817:     if (r != outline) {
        !           818:        XFillRectangles(dpy, root, findRootInfo(root)->xorGC, outline, r - outline);
        !           819:     }
        !           820: }
        !           821:                
        !           822: void
        !           823: AddGizmos(w)
        !           824:     Window w;
        !           825: {
        !           826:     XWindowAttributes wa;
        !           827:     Window      root, fw, gw, lw, uw, iw, iconw, hpw;
        !           828:     int         hw;
        !           829:     Bool        resize = False;
        !           830:     int                x, y, wd, h, bw, d;
        !           831: 
        !           832:     /*
        !           833:      * When we reparent w to fw, below, make sure w gets reparented back when
        !           834:      * fw goes away.  We do this early, in case we die, otherwise the map
        !           835:      * request in the client will hang forever. 
        !           836:      */
        !           837:     XChangeSaveSet(dpy, w, SetModeInsert);
        !           838: 
        !           839:     /*
        !           840:      * Don't try to fiddle with InputOnly windows.
        !           841:      */
        !           842:     XGetWindowAttributes(dpy, w, &wa);
        !           843:     if (wa.class == InputOnly) {
        !           844:         XClientMessageEvent ev;
        !           845: 
        !           846:        ev.type = ClientMessage;
        !           847:        ev.display = (Display *)NULL;
        !           848:        ev.window = w;
        !           849:        ev.message_type = XA_WM_HINTS;
        !           850:        ev.format = 8;
        !           851:        strcpy( ev.data.b, "bad window class" ); /* fix */
        !           852:         XSendEvent( dpy, w, False, -1, &ev );
        !           853:        return;
        !           854:     }
        !           855: 
        !           856:     XGetGeometry(dpy, (Drawable) w, &root, &x, &y, &wd, &h, &bw, &d);
        !           857:     /* set the border of the original window to 0 */
        !           858:     ChangeBorderWidth(w, 0);
        !           859:     /* make sure this window is big enough */
        !           860:     if (wa.width < MINWIDTH) {
        !           861:        resize = True;
        !           862:        wa.width = MINWIDTH;
        !           863:     }
        !           864:     if (wa.height + TITLEHEIGHT + 2 * BW < MINHEIGHT) {
        !           865:        resize = True;
        !           866:        wa.height = MINHEIGHT;
        !           867:     }
        !           868:     if (resize == True) {
        !           869:        XResizeWindow(dpy, w, wa.width, wa.height);
        !           870:     }
        !           871:     /* MakeFrame makes sure part of the header is on-screen */
        !           872:     fw = MakeFrame(root, wa.x, wa.y - TITLEHEIGHT - BW, wa.width,
        !           873:                   wa.height + TITLEHEIGHT + BW);
        !           874:     if (!fw)
        !           875:        return;
        !           876:     hw = wa.width - GROWBOXWIDTH - UPBOXWIDTH - ICONIFYWIDTH - 2 * BW;
        !           877:     hpw = MakeHeaderParent(root, fw, hw);
        !           878:     gw = MakeHeader(root, hpw, hw);
        !           879:     lw = MakeGrowBox(root, fw, wa.width - GROWBOXWIDTH);
        !           880:     iw = MakeIconBox(root, fw, UPBOXWIDTH);
        !           881:     uw = MakeUpBox(root, fw);
        !           882:     iconw = MakeIcon(root, fw);
        !           883:     XSync(dpy, False);
        !           884:     errorStatus = False;
        !           885:     {
        !           886:        XWindowChanges wc;
        !           887: 
        !           888:        wc.sibling = w;
        !           889:        wc.stack_mode = Above;
        !           890:        XConfigureWindow(dpy, fw, CWSibling|CWStackMode, &wc);
        !           891:     }
        !           892:     XReparentWindow(dpy, w, fw, 0, TITLEHEIGHT + BW);
        !           893:     XSync(dpy, False);
        !           894:     if (errorStatus == True) {
        !           895:        XDestroyWindow(dpy, fw);
        !           896:        return;
        !           897:     }
        !           898:     /* register fw, w, gw, and lw in the association table */
        !           899:     RegisterCompleteWindow(fw, w, gw, hpw, lw, iw, uw, iconw, hw);
        !           900:     MapCompleteWindow(fw);
        !           901: }
        !           902: 
        !           903: void
        !           904: ReconfigureFrameAndClient(root, ga, x, y, width, height)
        !           905:     Window root;
        !           906:        GenericAssoc *ga;
        !           907:        int x, y, width, height;
        !           908: {
        !           909:     XWindowAttributes wa;
        !           910:     XWindowChanges wc;
        !           911:     unsigned long mask;
        !           912: 
        !           913:     if (width < MINWIDTH)
        !           914:        width = MINWIDTH;
        !           915:     if (height < TITLEHEIGHT)
        !           916:        height = TITLEHEIGHT;
        !           917: 
        !           918:     /* let's unmap all the inferiors, so we dont' see all the interim
        !           919:      * exposure events of the inferior windows in the old sizes.
        !           920:      * XXX I suspect this might actually be hiding a real bug in the
        !           921:      * server, and should be reexamined someday.
        !           922:      */
        !           923:     XUnmapSubwindows(dpy,ga->frame);
        !           924: 
        !           925:     /* Reconfigure frame */
        !           926:     wc.x = x + UPBOXWIDTH + ICONIFYWIDTH + BW;
        !           927:     wc.y = y - TITLEHEIGHT - BW;
        !           928:     MakeReachable(root, &wc.x, &wc.y, width - UPBOXWIDTH - GROWBOXWIDTH -
        !           929:                  ICONIFYWIDTH - 2 * BW, TITLEHEIGHT);
        !           930:     wc.x -= UPBOXWIDTH + ICONIFYWIDTH + 2 * BW;
        !           931:     /* the extra BW is because XReconfigureWindow includes the border */
        !           932:     /* width in x and y, but not in width and height */
        !           933:     wc.y -= BW;
        !           934:     wc.width = width;
        !           935:     wc.height = height + TITLEHEIGHT + BW;
        !           936:     mask = CWX | CWY | CWWidth | CWHeight;
        !           937:     XConfigureWindow(dpy, ga->frame, mask, &wc);
        !           938:     /* Reconfigure client */
        !           939:     wc.x = 0;
        !           940:     wc.y = TITLEHEIGHT + BW;
        !           941:     wc.width = width;
        !           942:     wc.height = height;
        !           943:     wc.border_width = 0;
        !           944:     mask = CWX | CWY | CWWidth | CWHeight | CWBorderWidth;
        !           945:     XConfigureWindow(dpy, ga->client, mask, &wc);
        !           946:     /* Reconfigure raise button */
        !           947:     wc.x = 0;
        !           948:     wc.y = 0;
        !           949:     wc.width = UPBOXWIDTH;
        !           950:     wc.height = TITLEHEIGHT;
        !           951:     mask = CWX | CWY | CWWidth | CWHeight;
        !           952:     XConfigureWindow(dpy, ga->upbox, mask, &wc);
        !           953:     /* Reconfigure header parent */
        !           954:     wc.x = UPBOXWIDTH + BW + ICONIFYWIDTH;
        !           955:     wc.y = 0;
        !           956:     wc.width = width - UPBOXWIDTH - GROWBOXWIDTH - 2 * BW - ICONIFYWIDTH;
        !           957:     ga->headerWidth = wc.width;
        !           958:     wc.height = TITLEHEIGHT;
        !           959:     mask = CWX | CWY | CWWidth | CWHeight;
        !           960:     XConfigureWindow(dpy, ga->headerParent, mask, &wc);
        !           961:     /* Reconfigure header */
        !           962:     wc.x = 0;
        !           963:     wc.y = 0;
        !           964:     wc.width = width - UPBOXWIDTH - GROWBOXWIDTH - 2 * BW - ICONIFYWIDTH;
        !           965:     wc.height = TITLEHEIGHT;
        !           966:     mask = CWX | CWY | CWWidth | CWHeight;
        !           967:     XConfigureWindow(dpy, ga->header, mask, &wc);
        !           968:     /* Reconfigure resize button */
        !           969:     wc.x = width - GROWBOXWIDTH;
        !           970:     wc.y = 0;
        !           971:     wc.width = GROWBOXWIDTH;
        !           972:     wc.height = TITLEHEIGHT;
        !           973:     mask = CWX | CWY | CWWidth | CWHeight;
        !           974:     XConfigureWindow(dpy, ga->rbox, mask, &wc);
        !           975:     /* Reconfigure iconify button */
        !           976:     wc.x = UPBOXWIDTH;
        !           977:     wc.y = 0;
        !           978:     wc.width = ICONIFYWIDTH;
        !           979:     wc.height = TITLEHEIGHT;
        !           980:     mask = CWX | CWY | CWWidth | CWHeight;
        !           981:     XConfigureWindow(dpy, ga->iconify, mask, &wc);
        !           982:     XGetWindowAttributes(dpy, ga->frame, &wa);
        !           983: 
        !           984:     XMapSubwindows(dpy,ga->frame);
        !           985: }
        !           986: 
        !           987: Window
        !           988: MakeGrowBox(root, fw, lx)
        !           989:     Window root;
        !           990:     Window fw;
        !           991:     int lx;
        !           992: {
        !           993:     unsigned long valuemask;
        !           994:     XSetWindowAttributes attributes;
        !           995:     RootInfoRec *ri = findRootInfo(root);
        !           996:     int scr = ri - RootInfo;
        !           997: 
        !           998:     valuemask = CWEventMask | CWBackPixmap;
        !           999:     attributes.background_pixmap = ri->growBox;
        !          1000:     attributes.event_mask =
        !          1001:        ButtonPressMask | ButtonReleaseMask | ButtonMotionMask |
        !          1002:        PointerMotionHintMask | ExposureMask;
        !          1003:     return XCreateWindow(dpy, fw, lx, 0, GROWBOXWIDTH, TITLEHEIGHT, 0,
        !          1004:                   DefaultDepth(dpy, scr), CopyFromParent,
        !          1005:                   DefaultVisual(dpy, scr), valuemask, &attributes);
        !          1006: }
        !          1007: 
        !          1008: Window
        !          1009: MakeUpBox(root, fw)
        !          1010:     Window root;
        !          1011:     Window fw;
        !          1012: {
        !          1013:     unsigned long valuemask;
        !          1014:     XSetWindowAttributes attributes;
        !          1015:     RootInfoRec *ri = findRootInfo(root);
        !          1016:     int scr = ri - RootInfo;
        !          1017: 
        !          1018:     valuemask = CWEventMask | CWBackPixmap;
        !          1019:     attributes.background_pixmap = ri->doubleArrow;
        !          1020:     attributes.event_mask =
        !          1021:        ButtonPressMask | ButtonReleaseMask | ExposureMask;
        !          1022:     return XCreateWindow(dpy, fw, 0, 0, UPBOXWIDTH, TITLEHEIGHT, 0,
        !          1023:             DefaultDepth(dpy, scr), CopyFromParent, DefaultVisual(dpy, scr),
        !          1024:                   valuemask, &attributes);
        !          1025: }
        !          1026: 
        !          1027: Window
        !          1028: MakeIconBox(root, fw, ix)
        !          1029:     Window root;
        !          1030:     Window fw;
        !          1031:     int ix;
        !          1032: {
        !          1033:     unsigned long valuemask;
        !          1034:     XSetWindowAttributes attributes;
        !          1035:     RootInfoRec *ri = findRootInfo(root);
        !          1036:     int         scr = ri - RootInfo;
        !          1037: 
        !          1038:     valuemask = CWEventMask | CWBackPixmap;
        !          1039:     attributes.background_pixmap = ri->cross;
        !          1040:     attributes.event_mask =
        !          1041:        ButtonPressMask | ButtonReleaseMask | ButtonMotionMask |
        !          1042:        PointerMotionHintMask | ExposureMask;
        !          1043:     return XCreateWindow(dpy, fw, ix, 0, UPBOXWIDTH, TITLEHEIGHT, 0,
        !          1044:             DefaultDepth(dpy, scr), CopyFromParent, DefaultVisual(dpy, scr),
        !          1045:                   valuemask, &attributes);
        !          1046: }
        !          1047:        
        !          1048: void
        !          1049: ChangeBorderWidth(w, newWidth) Window w; int newWidth;
        !          1050: {
        !          1051: XWindowChanges wch;
        !          1052:        wch.border_width = newWidth;
        !          1053:        XConfigureWindow(dpy, w, CWBorderWidth, &wch);
        !          1054: }
        !          1055: 
        !          1056: void
        !          1057: MapCompleteWindow(frame) Window frame;
        !          1058: {
        !          1059:        XMapSubwindows(dpy, frame);
        !          1060:        XMapWindow(dpy, frame);
        !          1061: }
        !          1062: 
        !          1063: void
        !          1064: RegisterCompleteWindow(frame, client, header, hp, rbox, iconify, upbox, iconw, headerWidth)
        !          1065:        Window frame, client, header, hp, rbox, upbox, iconify, iconw;
        !          1066:        int headerWidth;
        !          1067: {
        !          1068:     GenericAssoc *fa;
        !          1069:     XWMHints   *wmhints;
        !          1070:     Window      root;
        !          1071:     int         x, y, wd, ht, bw, d;
        !          1072: 
        !          1073:     XGetGeometry(dpy, (Drawable) client, &root, &x, &y, &wd, &ht, &bw, &d);
        !          1074: 
        !          1075:     XSelectInput(dpy, client, PropertyChangeMask);
        !          1076:     fa = GimmeAssocStruct();
        !          1077:     fa->frame = frame;
        !          1078:     fa->header = header;
        !          1079:     fa->headerParent = hp;
        !          1080:     fa->client = client;
        !          1081:     fa->rbox = rbox;
        !          1082:     fa->iconify = iconify;
        !          1083:     fa->upbox = upbox;
        !          1084:     fa->headerWidth = headerWidth;
        !          1085:     fa->iconWindow = iconw;
        !          1086:     fa->iconnamelen = fa->namelen = 0;
        !          1087:     ProcessNewIconName(root, fa);
        !          1088:     ProcessNewName(root, fa);
        !          1089:     if ((wmhints = XGetWMHints(dpy, client)) &&
        !          1090:        (wmhints->flags & IconPositionHint)) {
        !          1091:        fa->iconx = wmhints->icon_x;
        !          1092:        fa->icony = wmhints->icon_y;
        !          1093:        fa->iconknown = True;
        !          1094:     }
        !          1095:     else
        !          1096:        fa->iconknown = False;
        !          1097:     if (wmhints)
        !          1098:        free((char *) wmhints);
        !          1099:     XMakeAssoc(dpy, frameInfo, (XID) frame, (char *) fa);
        !          1100:     XMakeAssoc(dpy, frameInfo, (XID) header, (char *) fa);
        !          1101:     XMakeAssoc(dpy, frameInfo, (XID) hp, (char *) fa);
        !          1102:     XMakeAssoc(dpy, frameInfo, (XID) client, (char *) fa);
        !          1103:     XMakeAssoc(dpy, frameInfo, (XID) rbox, (char *) fa);
        !          1104:     XMakeAssoc(dpy, frameInfo, (XID) iconify, (char *) fa);
        !          1105:     XMakeAssoc(dpy, frameInfo, (XID) upbox, (char *) fa);
        !          1106:     XMakeAssoc(dpy, frameInfo, (XID) iconw, (char *) fa);
        !          1107:     /* Xfree(pd); */
        !          1108: }
        !          1109: 
        !          1110: Window
        !          1111: MakeHeaderParent(root, fw, width)
        !          1112:     Window root;
        !          1113:     Window fw;
        !          1114:     int width;
        !          1115: {
        !          1116:     unsigned long valuemask;
        !          1117:     XSetWindowAttributes attributes;
        !          1118:     Window      result;
        !          1119:     int scr = findRootInfo(root) - RootInfo;
        !          1120: 
        !          1121:     valuemask = CWBackPixel;
        !          1122:     attributes.background_pixel = BlackPixel(dpy, scr);
        !          1123:     result = XCreateWindow(dpy, fw, UPBOXWIDTH + ICONIFYWIDTH + BW, 0,
        !          1124:                     width, TITLEHEIGHT, 0,
        !          1125:                     DefaultDepth(dpy, scr), CopyFromParent,
        !          1126:                     DefaultVisual(dpy, scr), valuemask,
        !          1127:                     &attributes);
        !          1128:     return result;
        !          1129: }
        !          1130: 
        !          1131: Window
        !          1132: MakeHeader(root, hw, width)
        !          1133:     Window root;
        !          1134:     Window hw;
        !          1135:     int width;
        !          1136: {
        !          1137:     unsigned long    valuemask;
        !          1138:     XSetWindowAttributes attributes;
        !          1139:     Window      result;
        !          1140:     int         scr = findRootInfo(root) - RootInfo;
        !          1141: 
        !          1142:     valuemask = CWEventMask | CWBackPixel;
        !          1143:     attributes.event_mask =
        !          1144:        ButtonPressMask | ButtonReleaseMask | ButtonMotionMask |
        !          1145:        ExposureMask | PointerMotionHintMask;
        !          1146:     attributes.background_pixel = BlackPixel(dpy, scr);
        !          1147:     result = XCreateWindow(dpy, hw, 0, 0, width, TITLEHEIGHT, 0,
        !          1148:                     DefaultDepth(dpy, scr), CopyFromParent,
        !          1149:                     DefaultVisual(dpy, scr), valuemask,
        !          1150:                     &attributes);
        !          1151:     return result;
        !          1152: }
        !          1153: 
        !          1154: /* XXX fw unused? */
        !          1155: MakeIcon(root, fw)
        !          1156:     Window root;
        !          1157:     Window fw;
        !          1158: {
        !          1159:     unsigned long  valuemask;
        !          1160:     XSetWindowAttributes attributes;
        !          1161:     Window      result;
        !          1162:     int         scr = findRootInfo(root) - RootInfo;
        !          1163: 
        !          1164:     valuemask = CWEventMask | CWBackPixel | CWBorderPixel;
        !          1165:     attributes.event_mask =
        !          1166:        ButtonPressMask | ButtonReleaseMask | ButtonMotionMask |
        !          1167:        ExposureMask | PointerMotionHintMask;
        !          1168:     attributes.background_pixel = BlackPixel(dpy, scr);
        !          1169:     attributes.border_pixel = WhitePixel(dpy, scr);
        !          1170:     result = XCreateWindow(dpy, root, 0, 0, ICONWIDTH, TITLEHEIGHT, BW,
        !          1171:             DefaultDepth(dpy, scr), CopyFromParent, DefaultVisual(dpy, scr),
        !          1172:                     valuemask, &attributes);
        !          1173:     return result;
        !          1174: }
        !          1175: 
        !          1176: 
        !          1177: Window
        !          1178: MakeFrame(root, x, y, width, height)
        !          1179:     Window root;
        !          1180:        int x, y, width, height;
        !          1181: {
        !          1182:     unsigned long valuemask;
        !          1183:     XSetWindowAttributes attributes;
        !          1184:     int         hx, hy;
        !          1185:     int         scr;
        !          1186:     RootInfoRec *ri = findRootInfo(root);
        !          1187: 
        !          1188:     if (!ri)
        !          1189:        return (NULL);
        !          1190:     scr = ri - RootInfo;
        !          1191:     hx = x + ICONIFYWIDTH + UPBOXWIDTH + BW;
        !          1192:     hy = y;
        !          1193:     MakeReachable(root, &hx, &hy, width - UPBOXWIDTH - GROWBOXWIDTH - ICONIFYWIDTH
        !          1194:                  - 2 * BW, TITLEHEIGHT);
        !          1195:     x = hx - (ICONIFYWIDTH + UPBOXWIDTH + BW) - BW;
        !          1196:     y = hy - BW;
        !          1197:     valuemask = CWEventMask | CWBorderPixel | CWBackPixel;
        !          1198:     attributes.event_mask = SubstructureRedirectMask
        !          1199:        | SubstructureNotifyMask;
        !          1200:     attributes.background_pixel = WhitePixel(dpy, scr);
        !          1201:     attributes.border_pixel = WhitePixel(dpy, scr);
        !          1202:     attributes.bit_gravity = NorthWestGravity;
        !          1203:     return XCreateWindow(dpy, root, x, y, width, height, BORDERWIDTH,
        !          1204:             DefaultDepth(dpy, scr), CopyFromParent, DefaultVisual(dpy, scr),
        !          1205:                   valuemask, &attributes);
        !          1206: }
        !          1207: 
        !          1208: void
        !          1209: RemoveGizmos(ga) GenericAssoc *ga;
        !          1210: {
        !          1211:        XDeleteAssoc(dpy, frameInfo, ga->frame);
        !          1212:        XDeleteAssoc(dpy, frameInfo, ga->header);
        !          1213:        XDeleteAssoc(dpy, frameInfo, ga->rbox);
        !          1214:        XDeleteAssoc(dpy, frameInfo, ga->iconify);
        !          1215:        XDeleteAssoc(dpy, frameInfo, ga->upbox);
        !          1216:        XDeleteAssoc(dpy, frameInfo, ga->iconWindow);
        !          1217:        XDeleteAssoc(dpy, frameInfo, ga->client);
        !          1218:        XDestroyWindow(dpy, ga->frame);
        !          1219:        XDestroyWindow(dpy, ga->iconWindow);
        !          1220:        free((char *) ga);
        !          1221: }
        !          1222: 
        !          1223: 
        !          1224: StartConnectionToServer(argc, argv)
        !          1225:        int     argc;
        !          1226:        char    *argv[];
        !          1227: {
        !          1228:     char       *display;
        !          1229:     int         i;
        !          1230:     extern char *index();
        !          1231: 
        !          1232:     display = NULL;
        !          1233:     for (i = 1; i < argc; i++) {
        !          1234:        if (index(argv[i], ':') != NULL)
        !          1235:            display = argv[i];
        !          1236:     }
        !          1237:     if (!(dpy = XOpenDisplay(display))) {
        !          1238:        Error(1, "Cannot open display\n");
        !          1239:     }
        !          1240: }
        !          1241: 
        !          1242: Error(status, message) int status; char *message;
        !          1243: {
        !          1244:        printf("%s", message);
        !          1245:        if (!status) return;
        !          1246:        else exit(1);
        !          1247: }
        !          1248: 
        !          1249: GenericAssoc *
        !          1250: GimmeAssocStruct(){
        !          1251:        return (GenericAssoc *) malloc(sizeof(GenericAssoc));
        !          1252: }
        !          1253: 
        !          1254: 
        !          1255: char *
        !          1256: WindowType(w) Window w;
        !          1257: {
        !          1258: GenericAssoc *ga;
        !          1259:        ga = (GenericAssoc *) XLookUpAssoc(dpy, frameInfo, w);
        !          1260:        if (ga && w == ga->frame) return "frame";
        !          1261:        if (ga && w == ga->header) return "header";
        !          1262:        if (ga && w == ga->client) return "client";
        !          1263:        if (ga && w == ga->rbox) return "resize box";
        !          1264:        if (ga && w == ga->iconify) return "iconify box";
        !          1265:        if (ga && w == ga->upbox) return "raise box";
        !          1266:        if (ga && w == ga->iconWindow) return "icon";
        !          1267:        if (ga) {
        !          1268:                Error(0, "WindowType: error in association table routines\n");
        !          1269:                return "error";
        !          1270:        }
        !          1271:        Error(0, "WindowType: window %d not found in assoc table\n", w);
        !          1272:        return "error";
        !          1273: }
        !          1274: 
        !          1275: Window
        !          1276: Frame(w) Window w;
        !          1277: {
        !          1278: GenericAssoc *ga;
        !          1279:        ga = (GenericAssoc *) XLookUpAssoc(dpy, frameInfo, w);
        !          1280:        if (ga) return ga->frame;
        !          1281:        Error(0, "Frame: window %d not found in assoc table\n");
        !          1282:        return None;
        !          1283: }
        !          1284: 
        !          1285: void
        !          1286: MakeReachable(root, x, y, width, height)
        !          1287:     Window root;
        !          1288:        int *x, *y;
        !          1289:        int width, height;
        !          1290: {
        !          1291:     RootInfoRec *ri = findRootInfo(root);
        !          1292: 
        !          1293:     if (!ri)
        !          1294:        return;
        !          1295:     if (*x <= MARGIN + ri->rootx - width)
        !          1296:        *x = MARGIN + ri->rootx - width + 1;
        !          1297:     if (*y <= MARGIN + ri->rooty - height)
        !          1298:        *y = MARGIN + ri->rooty - height + 1;
        !          1299:     if (*x >= ri->rootx + ri->rootwidth - MARGIN)
        !          1300:        *x = ri->rootx + ri->rootwidth - MARGIN - 1;
        !          1301:     if (*y >= ri->rooty + ri->rootheight - MARGIN)
        !          1302:        *y = ri->rooty + ri->rootheight - MARGIN - 1;
        !          1303: }
        !          1304: 
        !          1305: Bool
        !          1306: FillName(ga) GenericAssoc *ga;
        !          1307: {
        !          1308:     Status      status;
        !          1309:     char       *name;
        !          1310:     Bool        noname = False;
        !          1311:     int         len;
        !          1312:     Bool        res;
        !          1313:     extern char *strncpy();
        !          1314: 
        !          1315:     status = XFetchName(dpy, ga->client, &name);
        !          1316:     if (!status || !name || !(*name)) {
        !          1317:        name = "No name";
        !          1318:        noname = True;
        !          1319:     }
        !          1320: 
        !          1321:     len = strlen(name);
        !          1322:     if (len >= MAXNAME)
        !          1323:        len = MAXNAME;
        !          1324:     if (len != ga->namelen || strncmp(name, ga->name, len)) {
        !          1325:        ga->namelen = len;
        !          1326:        (void) strncpy(ga->name, name, ga->namelen);
        !          1327:        res = True;
        !          1328:     }
        !          1329:     else
        !          1330:        res = False;
        !          1331:     if (!noname)
        !          1332:        free(name);
        !          1333:     return res;
        !          1334: }
        !          1335: 
        !          1336: void
        !          1337: FillIconName(ga) GenericAssoc *ga;
        !          1338: {
        !          1339: Status status;
        !          1340: long len2;
        !          1341: char *pd;
        !          1342: Atom at;
        !          1343: int af;
        !          1344: long ba;
        !          1345:        status = XGetWindowProperty(dpy, ga->client, XA_WM_ICON_NAME,
        !          1346:                0,  MAXNAME, False,
        !          1347:                XA_STRING, &at, &af, &len2, &ba, &pd);
        !          1348:        if (status != Success) {
        !          1349:                ga->iconnamelen = 0;
        !          1350:        } else {
        !          1351:                switch (af) {
        !          1352:                case 8:
        !          1353:                        ga->iconnamelen = len2;
        !          1354:                        if (ga->iconnamelen >= MAXNAME) ga->iconnamelen = MAXNAME;
        !          1355:                        strncpy(ga->iconname, pd, ga->iconnamelen);
        !          1356:                        free (pd);
        !          1357:                        break;
        !          1358:                default:
        !          1359:                        ga->iconnamelen = 0;
        !          1360:                        if (pd) free(pd);
        !          1361:                }
        !          1362:        } 
        !          1363: }
        !          1364: 
        !          1365: void
        !          1366: ProcessNewName(root, ga)
        !          1367:     Window root;
        !          1368:     GenericAssoc *ga;
        !          1369: {
        !          1370:        if (!FillName(ga)) return;
        !          1371:        if (ga->iconnamelen == 0) {
        !          1372:                Bool wasMapped;
        !          1373:                int width;
        !          1374:                wasMapped = MappedNotOverride(ga->iconWindow);
        !          1375:                width = XTextWidth(font, ga->name, ga->namelen) + 2*BW;
        !          1376:                MakeReachable(root, &ga->iconx, &ga->icony, width, TITLEHEIGHT);
        !          1377:                if (wasMapped) XUnmapWindow(dpy, ga->iconWindow); 
        !          1378:                XMoveResizeWindow(dpy, ga->iconWindow, ga->iconx - BW,
        !          1379:                        ga->icony - BW, width, TITLEHEIGHT);
        !          1380:                if (wasMapped) XMapWindow(dpy, ga->iconWindow);
        !          1381:        }
        !          1382:        XUnmapWindow(dpy, ga->header);
        !          1383:        XMapWindow(dpy, ga->header);
        !          1384: }
        !          1385: 
        !          1386: void
        !          1387: ProcessNewIconName(root, ga)
        !          1388:     Window root;
        !          1389:     GenericAssoc *ga;
        !          1390: {
        !          1391:     int         oldIconLen;
        !          1392:     Bool        wasMapped;
        !          1393:     int         width;
        !          1394: 
        !          1395:     wasMapped = MappedNotOverride(ga->iconWindow);
        !          1396:     oldIconLen = ga->iconnamelen;
        !          1397:     FillIconName(ga);
        !          1398:     if (ga->iconnamelen == 0) {
        !          1399:        if (oldIconLen == 0)
        !          1400:            return;
        !          1401:        width = XTextWidth(font, ga->name, ga->namelen) + 2 * BW;
        !          1402:        MakeReachable(root, &ga->iconx, &ga->icony, width, TITLEHEIGHT);
        !          1403:        if (wasMapped)
        !          1404:            XUnmapWindow(dpy, ga->iconWindow);
        !          1405:        XMoveResizeWindow(dpy, ga->iconWindow, ga->iconx - BW,
        !          1406:                         ga->icony - BW, width, TITLEHEIGHT);
        !          1407:        if (wasMapped)
        !          1408:            XMapWindow(dpy, ga->iconWindow);
        !          1409:        return;
        !          1410:     }
        !          1411:     width = XTextWidth(font, ga->iconname, ga->iconnamelen) + 2 * BW;
        !          1412:     MakeReachable(root, &ga->iconx, &ga->icony, width, TITLEHEIGHT);
        !          1413:     if (wasMapped)
        !          1414:        XUnmapWindow(dpy, ga->iconWindow);
        !          1415:     XMoveResizeWindow(dpy, ga->iconWindow, ga->iconx - BW,
        !          1416:                     ga->icony - BW, width, TITLEHEIGHT);
        !          1417:     if (wasMapped)
        !          1418:        XMapWindow(dpy, ga->iconWindow);
        !          1419: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.