home *** CD-ROM | disk | FTP | other *** search
/ SGI Developer Toolbox 6.1 / SGI Developer Toolbox 6.1 - Disc 4.iso / src / exampleCode / GLX / rubberband / rubberMotif.c < prev   
Encoding:
C/C++ Source or Header  |  1994-08-02  |  8.5 KB  |  332 lines

  1. /*
  2.  * Copyright 1992, 1993, 1994, Silicon Graphics, Inc.
  3.  * All Rights Reserved.
  4.  *
  5.  * This is UNPUBLISHED PROPRIETARY SOURCE CODE of Silicon Graphics, Inc.;
  6.  * the contents of this file may not be disclosed to third parties, copied or
  7.  * duplicated in any form, in whole or in part, without the prior written
  8.  * permission of Silicon Graphics, Inc.
  9.  *
  10.  * RESTRICTED RIGHTS LEGEND:
  11.  * Use, duplication or disclosure by the Government is subject to restrictions
  12.  * as set forth in subdivision (c)(1)(ii) of the Rights in Technical Data
  13.  * and Computer Software clause at DFARS 252.227-7013, and/or in similar or
  14.  * successor clauses in the FAR, DOD or NASA FAR Supplement. Unpublished -
  15.  * rights reserved under the Copyright Laws of the United States.
  16.  */
  17.  
  18. #include <stdio.h>
  19. #include <X11/X.h>
  20. #include <X11/Xlib.h>
  21. #include <Xm/Xm.h>
  22. #include <X11/Intrinsic.h>
  23. #include <X11/Xirisw/GlxMDraw.h>
  24. #include <X11/keysym.h>
  25. #include </usr/include/X11/Xm/XmP.h>
  26. #include "copycmap.h"
  27.  
  28. #define DRAW 1
  29. #define ERASE 2
  30.  
  31. /* information for setting up colormap */
  32. static Colorindex red, green, yellow, blue, magenta, cyan;
  33. static Colorindex background;
  34. /* The following structure is declared in copycmap.h and is used by
  35.  * CopyGlColormap (in this demo directory) to set up a clormap
  36.  * with the specified colors.  Note that while we are using GLXC_NAMED
  37.  * to look up named colors, we could also use GLXC_ABSOLUTE and specify
  38.  * hardcoded pixel numbers 1-6 to copy from the X colormap.
  39.  */
  40. struct glxcColorInfo colorInfo[] =
  41. {
  42.     { GLXC_NAMED, (caddr_t)"red", &red},
  43.     { GLXC_NAMED, (caddr_t)"green", &green},
  44.     { GLXC_NAMED, (caddr_t)"yellow", &yellow},
  45.     { GLXC_NAMED, (caddr_t)"blue", &blue},
  46.     { GLXC_NAMED, (caddr_t)"magenta", &magenta},
  47.     { GLXC_NAMED, (caddr_t)"cyan", &cyan},
  48.     { GLXC_RESOURCE, (caddr_t)XmNbackground, &background},
  49. };
  50.  
  51.  
  52. static GLXconfig glxConfigZSize = { GLX_NORMAL, GLX_ZSIZE, GLX_NOCONFIG };
  53. static GLXconfig glxConfigRGB = {GLX_NORMAL, GLX_RGB, TRUE };
  54. static GLXconfig glxConfigDblBuf = {GLX_NORMAL, GLX_DOUBLE, TRUE };
  55. static GLXconfig glxConfigOverlay = {GLX_OVERLAY, GLX_BUFSIZE, 2 };
  56. static GLXconfig glxConfigPopup = {GLX_POPUP, GLX_BUFSIZE, 2 };
  57. static GLXconfig glxConfig [] = {
  58.     { 0, 0, 0 },
  59.     { 0, 0, 0 },
  60.     { 0, 0, 0 },
  61.     { 0, 0, 0 },
  62.     { 0, 0, 0 }
  63. };
  64. static int        usePups;
  65. static Widget    glw;
  66. static int        buttonDown;
  67. static void initCB();
  68.  
  69. /* 
  70.  * Return the overlay window of the widget 
  71.  * w - The GL widget
  72.  */
  73. Window 
  74. overlayWindow(w)
  75. Widget w;
  76. {
  77.     Arg args[1];
  78.     Window overlayWindow;
  79.  
  80.     XtSetArg(args[0], usePups?GlxNpopupWindow:GlxNoverlayWindow,
  81.              &overlayWindow);
  82.     XtGetValues(w, args, 1);
  83.     return (overlayWindow);
  84. }
  85.  
  86. /*
  87.  * drawOverlayLine - Draw or erase an overlay line from x1,y1 to x2,y2
  88.  */
  89.  
  90. drawOverlayLine(drawOrErase, x1, y1, x2, y2)
  91. int     drawOrErase;
  92. int x1, y1, x2, y2;
  93. {
  94.         long    vector1[2];
  95.         long    vector2[2];
  96.  
  97.         /*
  98.          * The y values need conversion from X land to GL land.
  99.          */
  100.         vector1[0] = x1;
  101.         vector1[1] = XtWidth(glw) - y1; 
  102.         vector2[0] = x2;
  103.         vector2[1] = XtWidth(glw) - y2;
  104.  
  105.         GLXwinset(XtDisplay(glw), overlayWindow(glw));
  106.         if (drawOrErase == DRAW) {
  107.                 /*
  108.                  * Draw a rubber band line in the overlay planes
  109.                  */
  110.                 color(1);
  111.         } else if (drawOrErase == ERASE) {
  112.                 /*
  113.                  * Erase a rubber band line in the overlay planes
  114.                  */
  115.                 color(0);
  116.         } else {
  117.             return;
  118.         }
  119.         bgnline();
  120.         v2i(vector1);
  121.         v2i(vector2);
  122.         endline();
  123. }
  124.  
  125.  
  126. /* Callbacks */
  127. static void
  128. exposeCB(w, client_data, call_data)
  129.     Widget w;
  130.     caddr_t client_data;
  131.     caddr_t call_data;
  132. {
  133.     GLXwinset(XtDisplay(w), XtWindow(w));
  134.     color(background);
  135.     clear();
  136. }
  137.  
  138. int        anchorX;
  139. int        anchorY;
  140. int        oldX;
  141. int        oldY;
  142. /*
  143.  * This is the input callback for the GL window.  Any button will
  144.  * Activate rubber-banding.  The rubber band line will follow the
  145.  * mouse until the button is let up.
  146.  */
  147. GLInputCB(w, client_data, call_data)
  148.         Widget  w;
  149.         caddr_t client_data;
  150.         GlxDrawCallbackStruct *call_data;
  151. {
  152.  
  153.     XEvent  *InputEvent;
  154.  
  155.     InputEvent = call_data->event;
  156.     switch (InputEvent->type) {
  157.         case ButtonPress:
  158.             anchorX = InputEvent->xbutton.x;
  159.             anchorY = InputEvent->xbutton.y;
  160.             oldX = anchorX;
  161.             oldY = anchorY;
  162.             buttonDown = 1;
  163.             break;
  164.         case MotionNotify:
  165.             if (buttonDown == 1) {
  166.                 drawOverlayLine(ERASE, anchorX, anchorY, 
  167.                         oldX, oldY);
  168.                 drawOverlayLine(DRAW, anchorX, anchorY, 
  169.                         InputEvent->xbutton.x, InputEvent->xbutton.y);
  170.                 oldX = InputEvent->xbutton.x;
  171.                 oldY = InputEvent->xbutton.y;
  172.             }
  173.             break;
  174.     }
  175. }
  176.  
  177. /* GL initialization; extracted from the original main() */
  178. static void
  179. initialize_gl() {
  180.  
  181.     short data;
  182.     float scrnaspect;            /* aspect ratio value */
  183.     long xscrnsize;              /* size of screen in x used to set globals  */
  184.  
  185.  
  186.     xscrnsize = getgdesc(GD_XPMAX);          /* get/set screen size[/aspect] */
  187.     if (xscrnsize == 1280) {
  188.         keepaspect(5, 4);
  189.         scrnaspect = 1.25;
  190.     } else if (xscrnsize = 1023) {
  191.         keepaspect(4, 3);
  192.         scrnaspect = 1.34;
  193.     } else {
  194.         fprintf(stderr, "Something's EXTREMELY wrong:  ");
  195.         fprintf(stderr, "xscrnsize=%d\n", xscrnsize);
  196.         exit(-1) ;
  197.     }
  198.  
  199. /*  initialize and set the display to double buffer mode */
  200.  
  201.     doublebuffer();
  202.     writemask((1<<getplanes())-1);
  203. }
  204.  
  205. /*
  206.  * Thanks to 4DGifts for this routine.
  207.  * This routine will install a particular gl widgets's colormap onto the
  208.  * top level window.  It may not be called until after the windows have
  209.  * been realized.
  210.  */
  211. installColormap(toplevel, glw)
  212. Widget toplevel, glw;
  213. {
  214.     Window windows[2];
  215.  
  216.     windows[0] = XtWindow(glw);
  217.     windows[1] = XtWindow(toplevel);
  218.     XSetWMColormapWindows(XtDisplay(toplevel), XtWindow(toplevel), windows, 2);
  219. }
  220.     
  221. static void
  222. initCB(w, client_data, call_data)
  223.     Widget w;
  224.     caddr_t client_data;
  225.     caddr_t call_data;
  226. {
  227.     GLXwinset(XtDisplay(w), XtWindow(w));
  228.     CopyGlColormap(w, colorInfo, XtNumber(colorInfo));
  229.     color(background);
  230.     initialize_gl();
  231.     clear();
  232.     gflush();
  233. }
  234.  
  235. /*
  236.  * Thanks to 4DGifts for this routine.
  237.  * This routine is similar to installColormap (in the file installcmap.c)
  238.  * excepth that it weill also install any auxiliary (overlay, popup and
  239.  * underlay) windows onto the top level window.  It may not be called
  240.  * until after the windows have been realized.
  241.  */
  242. installColormapWithOverlay(toplevel, glw)
  243. Widget toplevel, glw;
  244. {
  245.     Window windows[5];
  246.     Window overlay, popup, underlay;
  247.     Arg args[5];
  248.     register int i=0;
  249.  
  250.     i=0;
  251.     XtSetArg(args[i], GlxNoverlayWindow, &overlay); i++;
  252.     XtSetArg(args[i], GlxNpopupWindow, &popup); i++;
  253.     XtSetArg(args[i], GlxNunderlayWindow, &underlay); i++;
  254.     XtGetValues(glw, args, i);
  255.     i = 0;
  256.     if (overlay)
  257.     {
  258.         windows[i] = overlay;
  259.         i++;
  260.     }
  261.     if (popup)
  262.     {
  263.         windows[i] = popup;
  264.         i++;
  265.     }
  266.     if (underlay)
  267.     {
  268.         windows[i] = underlay;
  269.         i++;
  270.     }
  271.     windows[i] = XtWindow(glw); i++;
  272.     windows[i] = XtWindow(toplevel); i++;
  273.     XSetWMColormapWindows(XtDisplay(toplevel), XtWindow(toplevel), windows, i);
  274. }
  275.  
  276.  
  277. /*
  278.  * initializeGLOverlayWindow -  Returns the GL widget with the
  279.  *    overlay window enabled.
  280.  *
  281.  * parent = The widget's parent widget
  282.  */
  283.  
  284. Widget
  285. initGLWidgetWithOverlay(Widget parent)
  286. {
  287.     int    numArgs;  /* The number of arguments passed to XtCreateManagedWidget */
  288.     Arg    args[10]; /* The argument list passed to XtCreateManagedWidget */
  289.     int    configArgNum = 0;
  290.  
  291.     /*
  292.      * Set up the glxConfig structure for double buffered, RGB mode.
  293.      */
  294.     glxConfig[configArgNum++] = glxConfigDblBuf;
  295.  
  296.     /*
  297.      * Determine wether overlay planes are available.  If not, use
  298.      * popup planes
  299.      */
  300.     if (getgdesc(GD_BITS_OVER_SNG_CMODE) < 2) {
  301.         usePups = 1;
  302.         glxConfig[configArgNum++] = glxConfigPopup;
  303.     } else {
  304.         glxConfig[configArgNum++] = glxConfigOverlay;
  305.     }
  306.  
  307.  
  308.     /*
  309.      * Set up the arg structure for creation of the GL window
  310.      */
  311.     numArgs = 0;
  312.     XtSetArg(args[numArgs], GlxNglxConfig, glxConfig); 
  313.     numArgs++;
  314.     XtSetArg(args[numArgs], usePups?GlxNusePopup:GlxNuseOverlay, TRUE); 
  315.     numArgs++;
  316.  
  317.     /*
  318.      * Create the GL widget
  319.      */
  320.     glw = XtCreateManagedWidget("glwidget", glxMDrawWidgetClass, parent,
  321.                                         args, numArgs);
  322.  
  323.     /*
  324.      * Set up callback for the GL window
  325.      */
  326.     XtAddCallback(glw, GlxNexposeCallback, exposeCB, 0);
  327.     XtAddCallback(glw, GlxNinputCallback, GLInputCB, 0);
  328.     XtAddCallback(glw, GlxNginitCallback, initCB, 0);
  329.     return(glw);
  330. }
  331.  
  332.