home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1994 January / usenetsourcesnewsgroupsinfomagicjanuary1994.iso / sources / x / volume5 / xldimage / part02 / window.c < prev    next >
Encoding:
C/C++ Source or Header  |  1989-11-13  |  6.5 KB  |  248 lines

  1. /* window.c:
  2.  *
  3.  * display an image in a window
  4.  *
  5.  * jim frost 10.03.89
  6.  *
  7.  * Copyright 1989 Jim Frost.  See included file "copyright.h" for complete
  8.  * copyright information.
  9.  */
  10.  
  11. #include "copyright.h"
  12. #include "xloadimage.h"
  13. #include <X11/cursorfont.h>
  14.  
  15. static void setCursor(disp, window, iw, ih, ww, wh, cursor)
  16.      Display      *disp;
  17.      Window        window;
  18.      unsigned int  iw, ih;
  19.      unsigned int  ww, wh;
  20.      Cursor       *cursor;
  21. { XSetWindowAttributes swa;
  22.  
  23.   if ((ww == iw) && (wh == ih))
  24.     swa.cursor= XCreateFontCursor(disp, XC_icon);
  25.   else if ((ww < iw) && (wh == ih))
  26.     swa.cursor= XCreateFontCursor(disp, XC_sb_h_double_arrow);
  27.   else if ((ww == iw) && (wh < ih))
  28.     swa.cursor= XCreateFontCursor(disp, XC_sb_v_double_arrow);
  29.   else
  30.     swa.cursor= XCreateFontCursor(disp, XC_fleur);
  31.   XChangeWindowAttributes(disp, window, CWCursor, &swa);
  32.   XFreeCursor(disp, *cursor);
  33.   *cursor= swa.cursor;
  34. }
  35.  
  36. void imageInWindow(disp, scrn, image, winx, winy, winwidth, winheight, install,
  37.            verbose)
  38.      Display      *disp;
  39.      int           scrn;
  40.      Image        *image;
  41.      unsigned int  winx, winy, winwidth, winheight;
  42.      unsigned int  install;
  43.      unsigned int  verbose;
  44. { Pixmap               pixmap;
  45.   Colormap             xcmap;
  46.   XSetWindowAttributes swa;
  47.   XSizeHints           sh;
  48.   XGCValues            gcv;
  49.   GC                   gc;
  50.   Window               window;
  51.   int                  pixx, pixy;
  52.   int                  lastx, lasty, mousex, mousey;
  53.   union {
  54.     XEvent              event;
  55.     XAnyEvent           any;
  56.     XButtonEvent        button;
  57.     XKeyEvent           key;
  58.     XConfigureEvent     configure;
  59.     XExposeEvent        expose;
  60.     XMotionEvent        motion;
  61.     XResizeRequestEvent resize;
  62.   } event;
  63.  
  64.   /* figure out the window size.  unless specifically requested to do so,
  65.    * we will not exceed 90% of display real estate.
  66.    */
  67.  
  68.   lastx= (winwidth || winheight);
  69.   if (!winwidth) {
  70.     winwidth= image->width;
  71.     if (winwidth > DisplayWidth(disp, scrn) * 0.9)
  72.       winwidth= DisplayWidth(disp, scrn) * 0.9;
  73.   }
  74.   if (!winheight) {
  75.     winheight= image->height;
  76.     if (winheight > DisplayHeight(disp, scrn) * 0.9)
  77.       winheight= DisplayHeight(disp, scrn) * 0.9;
  78.   }
  79.  
  80.   if (! sendImageToX(disp, scrn, DefaultVisual(disp, scrn),
  81.              image, &pixmap, &xcmap, verbose))
  82.     exit(1);
  83.   swa.backing_store= NotUseful;
  84.   swa.bit_gravity= NorthWestGravity;
  85.   swa.cursor= XCreateFontCursor(disp, XC_watch);
  86.   swa.colormap= xcmap;
  87.   swa.event_mask= ButtonPressMask | Button1MotionMask | KeyPressMask |
  88.     ExposureMask | StructureNotifyMask | EnterWindowMask | LeaveWindowMask;
  89.   swa.save_under= False;
  90.   window= XCreateWindow(disp, RootWindow(disp, scrn), 0, 0,
  91.             image->width, image->height, 0,
  92.             DefaultDepth(disp, scrn),
  93.             InputOutput, CopyFromParent,
  94.             CWBackingStore | CWBitGravity | CWCursor |
  95.             CWColormap | CWEventMask | CWSaveUnder, &swa);
  96.   XStoreName(disp, window, image->title);
  97.   XSetIconName(disp, window, image->title);
  98.  
  99.   sh.width= winwidth;
  100.   sh.height= winheight;
  101.   sh.min_width= 1;
  102.   sh.min_height= 1;
  103.   sh.max_width= image->width;
  104.   sh.max_height= image->height;
  105.   sh.width_inc= 1;
  106.   sh.height_inc= 1;
  107.   sh.flags= PMinSize | PMaxSize | PResizeInc;
  108.   if (lastx)
  109.     sh.flags |= USSize;
  110.   else
  111.     sh.flags |= PSize;
  112.   if (winx || winy) {
  113.     sh.x= winx;
  114.     sh.y= winy;
  115.     sh.flags |= USPosition;
  116.   }
  117.   XSetNormalHints(disp, window, &sh);
  118.  
  119.   gcv.function= GXcopy;
  120.   gc= XCreateGC(disp, window, GCFunction, &gcv);
  121.   XMapWindow(disp, window);
  122.   pixx= pixy= 0;
  123.   lastx= lasty= -1;
  124.   setCursor(disp, window, image->width, image->height,
  125.         winwidth, winheight, &(swa.cursor));
  126.  
  127.   for (;;) {
  128.     XNextEvent(disp, &event);
  129.     switch (event.any.type) {
  130.     case ButtonPress:
  131.       if (event.button.button == 1) {
  132.     lastx= event.button.x;
  133.     lasty= event.button.y;
  134.     break;
  135.       }
  136. #ifdef NUKE_ME
  137.       XDestroyWindow(disp, window);
  138.       XFreeCursor(disp, swa.cursor);
  139.       XFreePixmap(disp, pixmap);
  140.       XFreeColormap(disp, xcmap);
  141.       return;
  142. #else
  143.       break;
  144. #endif
  145.  
  146.     case KeyPress: {
  147.       char buf[128];
  148.       KeySym ks;
  149.       XComposeStatus status;
  150.  
  151.       XLookupString(&event.key,buf,128,&ks,&status);
  152.       if (buf[0]=='q' || buf[0]=='Q') {
  153.         XDestroyWindow(disp, window);
  154.         XFreeCursor(disp, swa.cursor);
  155.         XFreePixmap(disp, pixmap);
  156.         XFreeColormap(disp, xcmap);
  157.         return;
  158.       }
  159.     }
  160.       break;
  161.  
  162.     case MotionNotify:
  163.       mousex= event.button.x;
  164.       mousey= event.button.y;
  165.       while (XCheckTypedEvent(disp, MotionNotify, &event) == True) {
  166.     mousex= event.button.x;
  167.     mousey= event.button.y;
  168.       }
  169.       pixx += lastx - mousex;
  170.       pixy += lasty - mousey;
  171.       lastx= mousex;
  172.       lasty= mousey;
  173.       if (pixx < 0)
  174.     pixx= 0;
  175.       if (pixy < 0)
  176.     pixy= 0;
  177.       if (pixx + winwidth > image->width)
  178.     pixx= image->width - winwidth;
  179.       if (pixy + winheight > image->height)
  180.     pixy= image->height - winheight;
  181.       XCopyArea(disp, pixmap, window, gc,
  182.         pixx, pixy, winwidth, winheight, 0, 0);
  183.       break;
  184.  
  185.     case ConfigureNotify:
  186.  
  187.       /* if we got resized too big, fix it.  it's a stupid window manager.
  188.        */
  189.  
  190.       if ((event.configure.width > image->width) ||
  191.       (event.configure.height > image->height)) {
  192.     if (event.configure.width > image->width)
  193.       winwidth= image->width;
  194.     else
  195.       winwidth= event.configure.width;
  196.     if (event.configure.height > image->height)
  197.       winheight= image->height;
  198.     else
  199.       winheight= event.configure.height;
  200.     XResizeWindow(disp, window, winwidth, winheight);
  201.       }
  202.       else {
  203.     winwidth= event.configure.width;
  204.     winheight= event.configure.height;
  205.       }
  206.  
  207.       /* configure the cursor to indicate which directions we can drag
  208.        */
  209.  
  210.       if (pixx + winwidth > image->width)
  211.     pixx= image->width - winwidth;
  212.       if (pixy + winheight > image->height)
  213.     pixy= image->height - winheight;
  214.       setCursor(disp, window, image->width, image->height,
  215.         winwidth, winheight, &(swa.cursor));
  216.  
  217.       /* repaint 
  218.        */
  219.  
  220.       XCopyArea(disp, pixmap, window, gc,
  221.         pixx, pixy, winwidth, winheight, 0, 0);
  222.       break;
  223.  
  224.     case DestroyNotify:
  225.       XFreeCursor(disp, swa.cursor);
  226.       XFreePixmap(disp, pixmap);
  227.       XFreeColormap(disp, xcmap);
  228.       return;
  229.  
  230.     case Expose:
  231.       XCopyArea(disp, pixmap, window, gc,
  232.         pixx + event.expose.x, pixy + event.expose.y,
  233.         event.expose.width, event.expose.height,
  234.         event.expose.x, event.expose.y);
  235.       break;
  236.  
  237.     case EnterNotify:
  238.       if (install)
  239.     XInstallColormap(disp, xcmap);
  240.       break;
  241.  
  242.     case LeaveNotify:
  243.       if (install)
  244.     XUninstallColormap(disp, xcmap);
  245.     }
  246.   }
  247. }
  248.