home *** CD-ROM | disk | FTP | other *** search
/ Encyclopedia of Graphics File Formats Companion / GFF_CD.ISO / software / unix / saoimage / sao1_07.tar / mainevnt.c < prev    next >
C/C++ Source or Header  |  1991-05-15  |  9KB  |  289 lines

  1. #ifndef lint
  2. static char SccsId[] = "%W%  %G%";
  3. #endif
  4.  
  5. /* Module:    mainevnt.c (Main Event)
  6.  * Purpose:    Main Event Loop and Dispatcher
  7.  * Subroutine:    control_event_loop()        returns: void
  8.  * Xlib calls:    XPending(), XNextEvent()
  9.  * UNIX calls:    select()
  10.  * Copyright:    1989 Smithsonian Astrophysical Observatory
  11.  *        You may do anything you like with this file except remove
  12.  *        this copyright.  The Smithsonian Astrophysical Observatory
  13.  *        makes no representations about the suitability of this
  14.  *        software for any purpose.  It is provided "as is" without
  15.  *        express or implied warranty.
  16.  * Modified:    {0} Michael VanHilst    initial version           9 May 1989
  17.  *        {1} Jay Travisano (STScI) VMS,IMTOOL changes      10 Nov 1989
  18.  *        {n} <who> -- <does what> -- <when>
  19.  */
  20.  
  21. #include <stdio.h>        /* stderr, NULL, etc. */
  22. #include <sys/time.h>        /* get struct timeval */
  23. #include <X11/Xlib.h>        /* X window stuff */
  24. #include <X11/Xutil.h>        /* X window manager stuff */
  25. #include "hfiles/constant.h"    /* define codes */
  26. #include "hfiles/define.h"    /* YES, NO, MIN, MAX and more */
  27. #include "hfiles/struct.h"    /* declare structure types */
  28. #include "hfiles/cgraph.h"    /* color graph structures */
  29. #include "hfiles/extern.h"    /* extern main parameter structures */
  30. extern struct cgraphRec cgraph;    /* get access to subwindow ID's */
  31. extern struct windowRec desktop;
  32. extern Display *display;    /* server connection */
  33.  
  34. #if VMS && IMTOOL
  35. void XZ_ast();
  36. int  XZ_efn = 10;
  37. #endif
  38.  
  39. /*
  40.  * Subroutine:    control_event_loop
  41.  * Purpose:    Main event loop and dispatcher
  42.  * Xlib calls:    XNextEvent();
  43.  */
  44. void control_event_loop ( )
  45. {
  46. #ifdef SYSV
  47.   int mask[2];
  48. #else
  49.   int mask[4];
  50. #endif
  51.   GC set_gc_with_background();
  52.   int *response, *control_buttonbox();
  53.   void map_windows(), dispatch_select(), redraw_window();
  54.   void control_cursor(), control_cgraph(), control_pan(), control_color();
  55.   void magnify_disp(), magnify_pan(), map_graphbox(), close_input_pipe();
  56.   void adjust_desktop(), adjust_graphbox(), key_response(), control_blink();
  57. #ifdef VMS
  58. #ifdef IMTOOL
  59.   /* Set asynch notification for all Xwindow events and Imtool pipe
  60.    * (`Z') events.  Note that buttonbox event notification is set
  61.    * separately (see buttonlib/makebox.c and buttonlib/remotectrl.c).
  62.    * The same goes for some other dynamic window/displays (see 
  63.    * editctrl.c and grphcinit.c).
  64.    */
  65.   {
  66.     extern Window root;
  67.     int    all_events = 0xFFFFFFFF;
  68.  
  69.     sys$clref (XZ_efn);
  70.  
  71.     XSelectAsyncInput (display, root, all_events, XZ_ast, XZ_efn);
  72.   }
  73. #endif
  74. #endif
  75.   /* the event loop */
  76.   control.priority = 0;
  77.   /* set mask to screen events */
  78.   while( 1 ) {
  79.     if( control.remote_connected ) {
  80. #ifdef IMTOOL
  81. #ifndef VMS 
  82.       /*  AIX is the only UNIX we have seen which can't handle the select!!  */
  83.       if( XPending(display) ) {
  84.     XNextEvent(display, &control.event);
  85.       } else {
  86.     mask[0] = control.select_mask[0];
  87.     mask[1] = control.select_mask[1];
  88.     /* check for either pipe or X server event */
  89.     if( select(control.select_size, (fd_set *)mask,
  90.            (fd_set *)0, (fd_set *)0, (struct timeval *)0) <0 ) {
  91.       perror("select error");
  92.       continue;
  93.     }
  94.     if( (mask[0] & control.Xserver.mask[0]) ||
  95.         (mask[1] & control.Xserver.mask[1]) ) {
  96.       XNextEvent(display, &control.event);
  97.     } else {
  98.       /* call routine to read from pipe */
  99.       respond_to_connection(mask);
  100.       continue;
  101.     }
  102.       }
  103. #else
  104.      /* For VMS, do the equivalent of Unix select() by 
  105.       * using ASTs and event flags.
  106.       */
  107.       if( XPending(display) ) {
  108.     XNextEvent(display, &control.event);
  109.       } else {
  110.     int not_found, i;
  111.     struct connectRec *port = control.Xserver.next;
  112.  
  113.     not_found = 1;
  114.         for( i=0; (port != NULL) && (i<control.remote_connected); i++ ) {
  115.           if( ZPending(port->fd) ) {
  116.         respond_to_connection(&port->fd);
  117.         /* reset AST on connections for which events can be pending */
  118.         ZSelectAsyncInput(port->fd, XZ_ast, XZ_efn);
  119.         port = NULL;
  120.         not_found = 0;
  121.       } else {
  122.         port = port->next;
  123.       }
  124.     }
  125.         if( not_found ) {
  126.       /* Wait for event flag.  When set, clear it for the next go around
  127.        * and jump back to the while loop and process all the events that
  128.        * are pending.
  129.        */
  130.       sys$waitfr (XZ_efn);
  131.       sys$clref  (XZ_efn);
  132.       continue;
  133.     } else {
  134.       continue;
  135.     }
  136.       }
  137. #endif
  138. #endif
  139.     } else {
  140.       XNextEvent(display, &control.event);
  141.     }
  142.     control.completed = 0;    
  143.     /* priority event loop invoked by certain eventloop subroutines */
  144.     /* usual application is to track mouse while buttons held down */
  145.     if( control.event.type & control.priority ) {
  146.       switch( control.mode ) {
  147.       case COP:
  148.     control_cursor();
  149.     break;
  150.       case VOP:
  151.     control_color();
  152.     break;
  153.       case GOP:
  154.     control_cgraph();
  155.     break;
  156.       case ZOP:
  157.     control_pan();
  158.     break;
  159.       case SOP:
  160.     control_blink();
  161.     break;
  162.       default:
  163.     (void)fprintf(stderr, "do-nothing mode\n");
  164.       }
  165.     }
  166.     /* priority events can speed up by returning to the while(1) */
  167.     /* from here - by setting event processing completed flag */
  168.     /* if a priority event has not claimed an exclusive */
  169.     if( control.completed ) continue;
  170.     /* check for buttonbox events */
  171.     /* set the colors for the button menu bitmaps, in case it draws */
  172.     (void)set_gc_with_background(&color.gcset.menu,
  173.                  color.gcset.menu.background);
  174.     if( (response = control_buttonbox(&control.event)) != 0 ) {
  175.       /* respond to the buttonbox event (uses extern.h) */
  176.       dispatch_select (response);
  177.       /* ok, go directly for the next event */
  178.       continue;
  179.     }
  180.  
  181.     /* check the type of event */
  182.     switch( control.event.type ) {
  183.       /* if all or part of the window is newly exposed */
  184.     case Expose:
  185.       /* redraw entire window once (not parts of windows) */
  186.       if( control.event.xexpose.count == 0 )
  187.     redraw_window(control.event.xexpose.window);
  188.       break;
  189.     case MotionNotify:
  190.       /* track with magnibox if in picturbox w/o shift key */
  191.       if( control.event.xmotion.window == dispbox.ID ) {
  192.     int shift;
  193.     shift = ((control.event.xmotion.state & (ShiftMask | LockMask)) !=0);
  194.     /* if magni_track or shift, but not both */
  195.     if( control.magni_track != shift ) {
  196.       magnify_disp(&control.event, 1, control.coord_track || shift);
  197.     } else if( control.coord_track && (!shift) )
  198.       /* else if coord_track alone, just show coords */
  199.       magnify_disp(&control.event, 0, 1);
  200.       } else if( (control.event.xmotion.window == panbox.ID) &&
  201.          (control.event.xmotion.state & ShiftMask) ) {
  202.       magnify_pan(&control.event);
  203.       }
  204.       break;
  205.     case ButtonPress:
  206.       /* if a mouse button is pressed */
  207.       if( control.event.xbutton.window == dispbox.ID ) {
  208.     /* avoid duplication with same response under priority */
  209.     if( !control.priority ) {
  210.       /* simple button pressed response depends on mode */
  211.       switch( control.mode ) {
  212.       case COP:
  213.         control_cursor();
  214.         break;
  215.       case VOP:
  216.         control_color();
  217.         break;
  218.       case ZOP:
  219.         control_pan();
  220.         break;
  221.       case SOP:
  222.         control_blink();
  223.         break;
  224.       default:
  225.         (void)fprintf(stderr, "do-nothing mode\n");
  226.       }
  227.     }
  228.       } else if( control.event.xbutton.window == cgraph.graph.ID ) {
  229.     /* button pressed in color graph window */
  230.     /* avoid duplication with priority response to same */
  231.     if( !control.priority ) {
  232.       control_cgraph();
  233.     }
  234.       } else if( control.event.xbutton.window == panbox.ID ) {
  235.     /* button pressed in pan window */
  236.     /* avoid duplication with priority response to same */
  237.     if( !control.priority ) {
  238.       control_pan();
  239.     }
  240.       } else if( control.event.xbutton.window == colorbox.ID ) {
  241.     /* button pressed in color bar window */
  242.     /* this window is not used with halftone */
  243.     if( color.ncolors > 1 )
  244.       map_graphbox();
  245.       }
  246.       break;
  247.     case KeyPress:
  248.       /* if a key is pressed */
  249.       key_response();
  250.       break;
  251.     case ConfigureNotify:
  252.       /* if the main window is reconfigured */
  253.       if( control.event.xconfigure.window == desktop.ID )
  254.     adjust_desktop(&control.event.xconfigure);
  255.       else if( control.event.xconfigure.window == graphbox.ID )
  256.     adjust_graphbox(&control.event.xconfigure);
  257.       break;
  258.     default:
  259.       break;
  260.     }
  261.   }
  262. }
  263.  
  264.  
  265. #ifdef VMS
  266. #ifdef IMTOOL
  267.  
  268. /* XZ_ast - Asynchronous System Trap routine for X window and Z events.
  269.  *    Simply set the appropriate event flag.
  270.  */
  271.  
  272. void XZ_ast (int efn)
  273. {
  274.     sys$setef (efn);
  275. }
  276.  
  277. #endif
  278. #endif
  279.                               
  280.                                                                
  281.                                                                
  282.                                                                
  283.                                                                
  284.                                                                
  285.                                                               
  286.  
  287.                                                                
  288.                                  
  289.