Official patch #4 for faces v1.3; please apply it.

Rich Burridge richb at sunchat.oz
Wed Jan 18 15:37:28 AEST 1989


It fixes the following problems:

1/ It's been pure luck that the NeWS animation routines have worked.
   The add_face routine has been modified to place an "empty" face
   into the appropriate row/column of the faces display. This will be
   overwritten with the NeWS face animation at the time of the final
   display.

2/ The NeWS (0,0) redraw bug has been fixed. This was done by Neil
   Crellin and Mark Andrews {neilc,marka}@natmlab.dms.oz.au, to whom
   I'm very grateful.

3/ The README file has been modified to give details of how to compile
   faces. This was in the introductory message of the original posting,
   but needs to be added to a more obvious place. Thanks to C. P. Lai
   <daisy!cplai at munnari.oz> for pointing this out.

4/ The Makefile has been modified so that if you just type make, then a
   help message will be displayed telling you your various options.

5/ The NeWS version expected the five standard icon files to be
   available at run time. Their images are now compiled in.


It adds a graphical interface for X11.

I wish to thank Dave Lemke for helping me, and for answering a lot of
silly questions with a great deal of patience. To use the X11 version,
just type "make x11", followed by "make install".

This is my first ever X11 program and consequently I'm still learning.
As of this posting, the X11 version still has the following bugs, for
which I'd appreciate some help:

a/ Under the uwm window manager you have to place the window manually
   first off. This is the only window manager I've tested it under,
   but I expect the problem is generic.

b/ The initial position of the icon appears to be 0,0, even if you
   try to override it with the -W[Pp] option.

c/ Get it working properly in color (currently gets X11 protocol errors).

d/ The text font could cause problems if the 6x10 font is not found and
   the fixed font is large.

e/ The image is not being correctly redrawn and a window/icon closure.

To an X11 expert, I expect the fixes for these problems are trivial.

Feed this file to Larry Walls' patch program then recompile.

    Rich.

------CUT HERE------CUT HERE------
*** original/Makefile	Wed Jan  4 19:47:09 1989
--- Makefile	Wed Jan 18 16:27:44 1989
***************
*** 1,7 ****
  #
  #  Makefile for faces, an icon face server, plus associated software.
  #
! #  @(#)Makefile 1.2 89/01/04
  #
  #  Copyright (c) Rich Burridge.
  #                Sun Microsystems, Australia - All rights reserved.
--- 1,7 ----
  #
  #  Makefile for faces, an icon face server, plus associated software.
  #
! #  @(#)Makefile 1.3 89/01/18
  #
  #  Copyright (c) Rich Burridge.
  #                Sun Microsystems, Australia - All rights reserved.
***************
*** 90,100 ****
  SVOBJS          = get.o main.o mon.o rec.o sunview.o
  SVSRCS          = get.c main.c mon.c rec.c sunview.c
  
  OTHERS          = README faces.1 faces.ps machine.tab people.tab Makefile
! SRCS            = get.c main.c mon.c news.c rec.c sunview.c
  
! all:            sunview news
  
  news:           ps_faces
  		cp ps_faces faces
  
--- 90,113 ----
  SVOBJS          = get.o main.o mon.o rec.o sunview.o
  SVSRCS          = get.c main.c mon.c rec.c sunview.c
  
+ X11LIBS         = -lX11
+ X11OBJS         = get.o main.o mon.o rec.o x11.o
+ X11SRCS         = get.c main.c mon.c rec.c x11.c
+ 
  OTHERS          = README faces.1 faces.ps machine.tab people.tab Makefile
! SRCS            = get.c main.c mon.c news.c rec.c sunview.c x11.c
  
! help:
! 		@echo
! 		@echo "You need to specify one of the following three options:"
! 		@echo
! 		@echo 1/   make sunview    - to make the SunView version.
! 		@echo 2/   make news       - to make the NeWS version.
! 		@echo 3/   make x11        - to make the X11 version.
! 		@echo
  
+ all:            sunview news x11
+ 
  news:           ps_faces
  		cp ps_faces faces
  
***************
*** 101,106 ****
--- 114,122 ----
  sunview:        sv_faces
  		cp sv_faces faces
  
+ x11:            x11_faces
+ 		cp x11_faces faces
+ 
  ps_faces:       $(PSOBJS)
  		cc -o ps_faces $(CFLAGS) $(PSOBJS) $(PSLIBS)
  
***************
*** 107,112 ****
--- 123,131 ----
  sv_faces:       $(SVOBJS)
  		cc -o sv_faces $(CFLAGS) $(SVOBJS) $(SVLIBS)
  
+ x11_faces:      $(X11OBJS)
+ 		cc -o x11_faces $(CFLAGS) $(X11OBJS) $(X11LIBS)
+ 
  install:        $(BINARIES)
  		install -s -m 751 faces $(BINDIR)
  		install -c -m 644 faces.ps $(LIBDIR)
***************
*** 120,125 ****
--- 139,145 ----
  
  lint:;          lint -DNEWSGIVEN -DNEWSFILE=\"$(LIBDIR)/faces.ps\" $(PSSRCS)
  		lint $(SVSRCS) $(SVLIBS)
+ 		lint $(X11SRCS) $(X11LIBS)
  
  shar:;          shar.script $(OTHERS) $(HDRS) $(IMAGES) > archive.1
  		shar.script $(SRCS) > archive.2
***************
*** 137,140 ****
  mon.o:          mon.c faces.h extern.h
  news.o:         news.c faces.h extern.h
  rec.o:          rec.c faces.h extern.h
! sunview.o:      sunview.c extern.h $(IMAGES)
--- 157,161 ----
  mon.o:          mon.c faces.h extern.h
  news.o:         news.c faces.h extern.h
  rec.o:          rec.c faces.h extern.h
! sunview.o:      sunview.c faces.h extern.h $(IMAGES)
! x11.o:          x11.c faces.h extern.h $(IMAGES)
*** original/README	Wed Jan  4 19:47:09 1989
--- README	Wed Jan 18 16:27:42 1989
***************
*** 9,17 ****
  This is the second general release of a "faces" server for
  monitoring mail or print jobs.
  
! It contains graphical interfaces for SunView and NeWS. The X11 and
! blit versions are being worked on. Expect them in the near future.
  
  Faces has four different modes of operation:
  
  The default will monitor for new mail. Only the last ten messages are
--- 9,32 ----
  This is the second general release of a "faces" server for
  monitoring mail or print jobs.
  
! It contains graphical interfaces for SunView, NeWS and X11.
  
+ Note that you need to specify one of the following three options to
+ compile faces:
+ 
+  1/     make sunview      - to make the SunView version.
+  2/     make news         - to make the NeWS version.
+  3/     make x11          - to make the X11 version.
+ 
+ This should then be followed by a make install. You might need super-user
+ permission to do this successfully. Create your face directory, hostname
+ sub-directories username ikons/icons, machine and people tables, and you're
+ set.
+ 
+ If you are compiling faces under v3.x of the SunOS, then there is a line in
+ the Makefile starting with OSTYPE, that needs to be uncommented.
+ 
+ 
  Faces has four different modes of operation:
  
  The default will monitor for new mail. Only the last ten messages are
***************
*** 63,76 ****
  Acknowledgements.
   
  Thanks go to Guy Harris for the basis of the latest manual page, Dave
! Lemke for many excellent suggestions, to Heather Rose for suggesting the
! animated NeWS faces, to Andrew Nicholson for help with some of the trickier
! NeWS code, to Dan Heller for writing the 'watch' program which was consulted
! in the early days, to Rob Pike for sending me a copy of the Pike/Presotto
! paper "Face the Nation", which I used to get vismon compatibility, to
! Jonathan Bowen for suggesting the rusers monitoring addition, and to
! everybody else who suggested enhancements, and fixed bugs in the previous
! version.
  
      Rich.
  
--- 78,92 ----
  Acknowledgements.
   
  Thanks go to Guy Harris for the basis of the latest manual page, Dave
! Lemke for many excellent suggestions and a lot of help with the X11 code,
! to Heather Rose for suggesting the animated NeWS faces, to Andrew Nicholson
! for help with some of the trickier NeWS code, to Dan Heller for writing the
! 'watch' program which was consulted in the early days, to Rob Pike for
! sending me a copy of the Pike/Presotto paper "Face the Nation", which I used
! to get vismon compatibility, to Jonathan Bowen for suggesting the rusers
! monitoring addition, and to everybody else who suggested enhancements, and
! fixed bugs in the previous version. And finally thanks to Neil Crellin and
! Mark Andrews for a fix to the (0,0) redraw bug with the NeWS version.
  
      Rich.
  
*** original/extern.h	Wed Jan  4 19:46:59 1989
--- extern.h	Wed Jan 18 16:27:40 1989
***************
*** 1,5 ****
  
! /*  @(#)extern.h 1.3 89/01/04
   *
   *  Contains the external variable definitions used by faces.
   *
--- 1,5 ----
  
! /*  @(#)extern.h 1.4 89/01/18
   *
   *  Contains the external variable definitions used by faces.
   *
***************
*** 34,40 ****
--- 34,42 ----
  
  extern char bgicon[] ;     /* Alternate background pattern. */
  extern char community[] ;  /* Community name ("real" host name). */
+ extern char display[] ;    /* X11 display information. */
  extern char facedir[] ;    /* Directory containing face images. */
+ extern char geometry[] ;   /* X11 geometry information. */
  extern char hostname[] ;   /* Machine name to monitor. */
  extern char iconname[] ;   /* Name of the icon file for this person. */
  extern char machfile[] ;   /* Name of the machine/community file. */
*** original/faces.1	Wed Jan  4 19:47:09 1989
--- faces.1	Wed Jan 18 16:27:43 1989
***************
*** 1,7 ****
! .\" @(#)faces.1 1.3 89/01/04
  .TH FACES 1L "2 December 1988"
  .SH NAME
! faces \- visual mail, user and print face server for the Sun workstation
  .SH SYNOPSIS
  .B "faces
  [
--- 1,7 ----
! .\" @(#)faces.1 1.4 89/01/18
  .TH FACES 1L "2 December 1988"
  .SH NAME
! faces \- visual mail, user and print face server.
  .SH SYNOPSIS
  .B "faces
  [
***************
*** 16,25 ****
--- 16,33 ----
  .I background
  ]
  [
+ .B \-d
+ .I display
+ ]
+ [
  .B \-f
  .I facedir
  ]
  [
+ .B \-g
+ .I geometry
+ ]
+ [
  .B \-h
  .I hostname
  ]
***************
*** 60,66 ****
  .SH DESCRIPTION
  .B faces
  is a window based tool for monitoring mail, users or print queues. It contains
! graphical interfaces for SunView and NeWS. It has four different modes
  of operation:
  .LP
  The default will monitor for new mail. Only the last ten messages are
--- 68,74 ----
  .SH DESCRIPTION
  .B faces
  is a window based tool for monitoring mail, users or print queues. It contains
! graphical interfaces for SunView, NeWS and X11. It has four different modes
  of operation:
  .LP
  The default will monitor for new mail. Only the last ten messages are
***************
*** 214,223 ****
--- 222,237 ----
  Sun icon file containing an alternate background pattern. The default is
  root grey.
  .TP
+ .BI \-d " display"
+ Used with the X11 variant of faces to give a display type.
+ .TP
  .BI \-f " facedir"
  Use an alternate name for the faces directory. The default is
  .BR /usr/local/faces .
  .TP
+ .BI \-g " geometry"
+ Used with the X11 variant of faces to give geometry information.
+ .TP
  .BI \-h " hostname"
  Name of the machine to monitor. Faces will be displayed for each user
  logged in.
***************
*** 289,299 ****
  .B /usr/local/faces/machine.tab
  machine/community equivalences
  .SH BUGS
  The machine and people table lookup is hopelessly inefficient and
  will need to be improved as the faces database gets larger.
- .br
- If the window/icon for the NeWS version is moved, then the window or
- icon is redrawn at the original position.
  .SH AUTHOR
  Rich Burridge,        DOMAIN: richb at sunaus.oz.au
  .nf
--- 303,313 ----
  .B /usr/local/faces/machine.tab
  machine/community equivalences
  .SH BUGS
+ The X11 version will not run on a color screen. Currently there are also
+ several other minor problems with this implementation.
+ .br
  The machine and people table lookup is hopelessly inefficient and
  will need to be improved as the faces database gets larger.
  .SH AUTHOR
  Rich Burridge,        DOMAIN: richb at sunaus.oz.au
  .nf
*** original/faces.h	Wed Jan  4 19:46:59 1989
--- faces.h	Wed Jan 18 16:27:42 1989
***************
*** 1,5 ****
  
! /*  @(#)faces.h 1.5 89/01/04
   *
   *  Contains all the global definitions used by faces.
   *
--- 1,5 ----
  
! /*  @(#)faces.h 1.6 89/01/18
   *
   *  Contains all the global definitions used by faces.
   *
***************
*** 58,64 ****
  enum mon_type { MONALL, MONNEW, MONPRINTER, MONUSERS } ;
  
  /* Different graphics systems appropriate one set in gtype. */
! enum gr_type { SVIEW, NEWS } ;
  
  /* Determine order for face type lookup. */
  #define  NEWSTYPE        0
--- 58,64 ----
  enum mon_type { MONALL, MONNEW, MONPRINTER, MONUSERS } ;
  
  /* Different graphics systems appropriate one set in gtype. */
! enum gr_type { SVIEW, NEWS, X11 } ;
  
  /* Determine order for face type lookup. */
  #define  NEWSTYPE        0
*** original/faces.ps	Sun Dec 11 15:05:47 1988
--- faces.ps	Wed Jan 18 16:27:44 1989
***************
*** 1,11 ****
  
  %  These are NeWS dependent graphics routines used by faces.
  %
! %  @(#)faces.ps 1.3 88/12/11
  %
  %  Copyright (c) Rich Burridge - Sun Microsystems Australia.
  %                                All rights reserved.
  %
  %  Permission is given to distribute these sources, as long as the
  %  copyright messages are not removed, and no monies are exchanged.
  %
--- 1,15 ----
  
  %  These are NeWS dependent graphics routines used by faces.
  %
! %  @(#)faces.ps 1.4 89/01/18
  %
  %  Copyright (c) Rich Burridge - Sun Microsystems Australia.
  %                                All rights reserved.
  %
+ %  Modifications to MakeFrame and ShowDisplay by Neil Crellin and
+ %  Mark Andrews {neilc,marka}@natmlab.dms.oz.au to fix the (0,0)
+ %  redraw bug.
+ %
  %  Permission is given to distribute these sources, as long as the
  %  copyright messages are not removed, and no monies are exchanged.
  %
***************
*** 65,73 ****
    MPR /Retained true put
  
    /Frame framebuffer /new DefaultWindow send def
      {
!       /IconX IconX def
!       /IconY IconY def
        /BorderTop 5 def
        /BorderLeft 5 def
        /BorderBottom 5 def
--- 69,77 ----
    MPR /Retained true put
  
    /Frame framebuffer /new DefaultWindow send def
+   FrameX FrameY IconX IconY
      {
!       [ /IconY /IconX /FrameY /FrameX ] { exch def } forall
        /BorderTop 5 def
        /BorderLeft 5 def
        /BorderBottom 5 def
***************
*** 102,107 ****
--- 106,112 ----
        /PaintIcon
          {
            gsave
+             clippath pathbbox pop pop translate
              1 fillcanvas
              IconWidth IconHeight scale
              0 setgray
***************
*** 108,113 ****
--- 113,128 ----
              Invert MPR imagemaskcanvas
            grestore
          } def
+       /ShapeIconCanvas
+         {
+           gsave
+             ParentCanvas setcanvas
+             IconX null eq IconY null eq or
+             { 0 0 }
+             { IconX IconY } ifelse
+             IconWidth IconHeight IconPath IconCanvas reshapecanvas
+           grestore
+         } def
      } Frame send
    IsIcon 1 eq { /flipiconic Frame send } if
  } def
***************
*** 152,158 ****
    /FrameHeight ClientHeight 10 add def
    /FrameWidth ClientWidth 10 add def
  
!   FrameX FrameY
    FrameWidth FrameHeight /reshape Frame send
  
    Frame /IconWidth IconWidth put
--- 167,173 ----
    /FrameHeight ClientHeight 10 add def
    /FrameWidth ClientWidth 10 add def
  
!   { FrameX FrameY } Frame send
    FrameWidth FrameHeight /reshape Frame send
  
    Frame /IconWidth IconWidth put
*** original/get.c	Wed Jan  4 19:46:59 1989
--- get.c	Wed Jan 18 16:27:37 1989
***************
*** 1,6 ****
  /*LINTLIBRARY*/
  #ifndef lint
! static char sccsid[] = "@(#)get.c 1.4 89/01/04" ;
  #endif
  	
  /*  Extraction routines used by faces.
--- 1,6 ----
  /*LINTLIBRARY*/
  #ifndef lint
! static char sccsid[] = "@(#)get.c 1.5 89/01/18" ;
  #endif
  	
  /*  Extraction routines used by faces.
***************
*** 163,173 ****
--- 163,179 ----
              case 'b' : INC ;                 /* Alternate background pattern. */
                         getparam(bgicon, argv, "-b needs background icon") ;
                         break ;
+             case 'd' : INC ;                 /* X11 display information. */
+                        getparam(display, argv, "-d needs display information") ;
+                        break ;
              case 'f' : INC ;                 /* New directory for face icons. */
                         getparam(facedir, argv, "-f needs face directory") ;
                         SPRINTF(machfile, "%s/machine.tab", facedir) ;
                         SPRINTF(peopfile, "%s/people.tab", facedir) ;
                         break ;
+             case 'g' : INC ;                 /* X11 geometry information. */
+                        getparam(geometry, argv, "-g needs geometry information") ;
+                        break ;
              case 'h' : mtype = MONUSERS ;    /* Monitor users on a machine. */
                         INC ;
                         getparam(hostname, argv, "-h needs hostname") ;
***************
*** 239,245 ****
                         break ;
              default  : FPRINTF(stderr, "Usage: %s [-P printer] ", progname) ;
                         FPRINTF(stderr, "[-Wi] [-Wp x y] [-WP x y] ") ;
!                        FPRINTF(stderr, "[-b background] [-f facedir] [-i] [-n] ") ;
                         FPRINTF(stderr, "[-p period] [-s spoolfile] [-u] [-t] [-v]\n") ;
                         exit(1) ;
            }
--- 245,252 ----
                         break ;
              default  : FPRINTF(stderr, "Usage: %s [-P printer] ", progname) ;
                         FPRINTF(stderr, "[-Wi] [-Wp x y] [-WP x y] ") ;
!                        FPRINTF(stderr, "[-b background] [-d display] [-f facedir] ") ;
!                        FPRINTF(stderr, "[-g geometry] [-i] [-n] ") ;
                         FPRINTF(stderr, "[-p period] [-s spoolfile] [-u] [-t] [-v]\n") ;
                         exit(1) ;
            }
*** original/main.c	Wed Jan  4 19:46:59 1989
--- main.c	Wed Jan 18 16:27:39 1989
***************
*** 1,5 ****
  #ifndef lint
! static char sccsid[] = "@(#)main.c 1.4 89/01/04" ;
  #endif
  
  /*  Icon face server for monitoring mail and print jobs.
--- 1,5 ----
  #ifndef lint
! static char sccsid[] = "@(#)main.c 1.5 89/01/18" ;
  #endif
  
  /*  Icon face server for monitoring mail and print jobs.
***************
*** 39,46 ****
--- 39,48 ----
  
  char bgicon[MAXLINE] ;           /* Alternate background pattern. */
  char community[MAXLINE] ;        /* Community name ("real" host name). */
+ char display[MAXLINE] ;          /* X11 display information. */
  char facedir[MAXLINE] ;          /* Directory containing face images. */
  char fname[MAXTYPES][MAXLINE] ;  /* Array of various face name types. */
+ char geometry[MAXLINE] ;    /* X11 geometry information. */
  char hostname[MAXLINE] ;    /* Machine name to monitor. */
  char iconname[MAXLINE] ;    /* Name of the icon file for this person. */
  char machfile[MAXLINE] ;    /* Name of the machine/community file. */
***************
*** 128,133 ****
--- 130,137 ----
    STRCPY(fname[BLITTYPE], "48x48x1") ;
    STRCPY(fname[SUNTYPE], "sun.icon") ;
    STRCPY(fname[NEWSTYPE], "face.ps") ;
+   STRCPY(display, "") ;       /* X11 display type. */
+   STRCPY(geometry, "") ;      /* X11 geometry information. */
    wx = wy = ix = iy = 0 ;
  
  #ifdef FBMONTYPE
*** original/news.c	Wed Jan  4 19:46:59 1989
--- news.c	Wed Jan 18 16:27:40 1989
***************
*** 1,6 ****
  /*LINTLIBRARY*/
  #ifndef lint
! static char sccsid[] = "@(#)news.c 1.4 89/01/04" ;
  #endif
  
  /*  NeWS dependent graphics routines used by faces,
--- 1,6 ----
  /*LINTLIBRARY*/
  #ifndef lint
! static char sccsid[] = "@(#)news.c 1.5 89/01/18" ;
  #endif
  
  /*  NeWS dependent graphics routines used by faces,
***************
*** 22,27 ****
--- 22,47 ----
  #include <sundev/kbd.h>
  #include <sundev/kbio.h>
  
+ static unsigned short noface_image[] = {
+ #include "noface.icon"
+ } ;
+ 
+ static unsigned short nomail_image[] = {
+ #include "nomail.icon"
+ } ;
+ 
+ static unsigned short nopaper_image[] = {
+ #include "nopaper.icon"
+ } ;
+ 
+ static unsigned short noprint_image[] = {
+ #include "noprint.icon"
+ } ;
+ 
+ static unsigned short nousers_image[] = {
+ #include "nousers.icon"
+ } ;
+ 
  #ifdef SUNOS3.x
  int fullmask ;               /* Full mask of file descriptors to check on. */
  int readmask ;               /* Readmask used in select call. */
***************
*** 61,67 ****
                              case BLITTYPE :
                              case SUNTYPE  : load_icon("Curface") ;
                                              STRCPY(face, "CurfaceIcon") ;
!                             case NEWSTYPE : break ;
                            }
                        else STRCPY(face, "NofaceIcon") ;
                        break ;
--- 81,89 ----
                              case BLITTYPE :
                              case SUNTYPE  : load_icon("Curface") ;
                                              STRCPY(face, "CurfaceIcon") ;
!                                             break ;
!                             case NEWSTYPE : STRCPY(face, "EmptyIcon") ;
!                                             break ;
                            }
                        else STRCPY(face, "NofaceIcon") ;
                        break ;
***************
*** 245,255 ****
  
  make_icon()
  {
!   if (get_sun_icon("noface.icon", ibuf) == 0) load_icon("Noface") ;
!   if (get_sun_icon("nomail.icon", ibuf) == 0) load_icon("Nomail") ;
!   if (get_sun_icon("nopaper.icon", ibuf) == 0) load_icon("Nopaper") ;
!   if (get_sun_icon("noprint.icon", ibuf) == 0) load_icon("Noprint") ;
!   if (get_sun_icon("nousers.icon", ibuf) == 0) load_icon("Nousers") ;
  }
  
  
--- 267,286 ----
  
  make_icon()
  {
!   int i ;
! 
!   for (i = 0; i < 256; i++) ibuf[i] = noface_image[i] ;
!   load_icon("Noface") ;
!   for (i = 0; i < 256; i++) ibuf[i] = nomail_image[i] ;
!   load_icon("Nomail") ;
!   for (i = 0; i < 256; i++) ibuf[i] = nopaper_image[i] ;
!   load_icon("Nopaper") ;
!   for (i = 0; i < 256; i++) ibuf[i] = noprint_image[i] ;
!   load_icon("Noprint") ;
!   for (i = 0; i < 256; i++) ibuf[i] = nousers_image[i] ;
!   load_icon("Nousers") ;
!   for (i = 0; i < 256; i++) ibuf[i] = 0 ;
!   load_icon("Empty") ;
  }
  
  
*** original/patchlevel.h	Wed Jan  4 19:47:08 1989
--- patchlevel.h	Wed Jan 18 16:27:42 1989
***************
*** 1,5 ****
   
! /*  @(#)patchlevel.h 1.4 89/01/04
   *
   *  This is the current patch level for this version of faces.
   *
--- 1,5 ----
   
! /*  @(#)patchlevel.h 1.5 89/01/18
   *
   *  This is the current patch level for this version of faces.
   *
***************
*** 14,17 ****
   *  reported to me then an attempt will be made to fix them.
   */
  
! #define  PATCHLEVEL  3
--- 14,17 ----
   *  reported to me then an attempt will be made to fix them.
   */
  
! #define  PATCHLEVEL  4
*** original/x11.c	Thu Jan 12 23:15:31 1989
--- x11.c	Wed Jan 18 16:27:45 1989
***************
*** 0 ****
--- 1,489 ----
+ /*LINTLIBRARY*/
+ #ifndef lint
+ static char sccsid[] = "@(#)x11.c 1.2 89/01/18" ;
+ #endif
+ 
+ /*  X11 dependent graphics routines used by faces,
+  *  the visual mail and print job monitor.
+  * 
+  *  Copyright (c) Rich Burridge - Sun Microsystems Australia.
+  *                                All rights reserved.
+  *
+  *  Permission is given to distribute these sources, as long as the
+  *  copyright messages are not removed, and no monies are exchanged. 
+  * 
+  *  No responsibility is taken for any errors or inaccuracies inherent
+  *  either to the comments or the code of this program, but if reported
+  *  to me, then an attempt will be made to fix them.
+  *
+  */
+  
+ #include "faces.h"
+ #include "extern.h"
+ #include <X11/Xlib.h>
+ #include <X11/Xutil.h>
+  
+ #define  DEF_FONT    "fixed"
+ #define  FONT        "6x10b"
+ #define  FRAME_MASK  (ButtonPressMask | ButtonReleaseMask | ExposureMask | ButtonMotionMask)
+ 
+ Pixmap load_icon() ;
+ 
+ Display *dpy ;
+ GC gc ;
+ Pixmap background ;          /* Background pattern (used for tiling.) */
+ Pixmap faces_icon, noface_icon, nomail_icon, nopaper_icon ;
+ Pixmap noprint_icon, nousers_icon ;
+ Pixmap mpr, pr ;             /* Current memory Pixmaps. */
+ Pixmap old_mpr, old_pr ;     /* Previous memory Pixmaps. */
+ Window frame ;
+ Window frame_icon ;
+ XFontStruct *sfont ;
+ XGCValues gc_val ;
+ XSizeHints size ;
+ XWMHints wm_hints ;
+  
+ #ifdef SUNOS3.x
+ int fullmask ;               /* Full mask of file descriptors to check on. */
+ int readmask ;               /* Readmask used in select call. */
+ #else
+ fd_set fullmask ;            /* Full mask of file descriptors to check on. */
+ fd_set readmask ;            /* Readmask used in select call. */
+ #endif SUNOS3.x
+ 
+ unsigned long gc_mask ;
+ int screen ;
+ int xfd ;                    /* File descriptor for X11 server connection. */
+ unsigned long mask ;
+ long backgnd, foregnd ;
+  
+ /*  256-byte table for quickly reversing the bits in an unsigned 8-bit char,
+  *  used to convert between MSBFirst and LSBFirst image formats.
+  */
+ 
+ static char revtable[256] = {
+             0, -128,   64,  -64,   32,  -96,   96,  -32,
+            16, -112,   80,  -48,   48,  -80,  112,  -16,
+             8, -120,   72,  -56,   40,  -88,  104,  -24,
+            24, -104,   88,  -40,   56,  -72,  120,   -8,
+             4, -124,   68,  -60,   36,  -92,  100,  -28,
+            20, -108,   84,  -44,   52,  -76,  116,  -12,
+            12, -116,   76,  -52,   44,  -84,  108,  -20,
+            28, -100,   92,  -36,   60,  -68,  124,   -4,
+             2, -126,   66,  -62,   34,  -94,   98,  -30,
+            18, -110,   82,  -46,   50,  -78,  114,  -14,
+            10, -118,   74,  -54,   42,  -86,  106,  -22,
+            26, -102,   90,  -38,   58,  -70,  122,   -6,
+             6, -122,   70,  -58,   38,  -90,  102,  -26,
+            22, -106,   86,  -42,   54,  -74,  118,  -10,
+            14, -114,   78,  -50,   46,  -82,  110,  -18,
+            30,  -98,   94,  -34,   62,  -66,  126,   -2,
+             1, -127,   65,  -63,   33,  -95,   97,  -31,
+            17, -111,   81,  -47,   49,  -79,  113,  -15,
+             9, -119,   73,  -55,   41,  -87,  105,  -23,
+            25, -103,   89,  -39,   57,  -71,  121,   -7,
+             5, -123,   69,  -59,   37,  -91,  101,  -27,
+            21, -107,   85,  -43,   53,  -75,  117,  -11,
+            13, -115,   77,  -51,   45,  -83,  109,  -19,
+            29,  -99,   93,  -35,   61,  -67,  125,   -3,
+             3, -125,   67,  -61,   35,  -93,   99,  -29,
+            19, -109,   83,  -45,   51,  -77,  115,  -13,
+            11, -117,   75,  -53,   43,  -85,  107,  -21,
+            27, -101,   91,  -37,   59,  -69,  123,   -5,
+             7, -121,   71,  -57,   39,  -89,  103,  -25,
+            23, -105,   87,  -41,   55,  -73,  119,   -9,
+            15, -113,   79,  -49,   47,  -81,  111,  -17,
+            31,  -97,   95,  -33,   63,  -65,  127,   -1,
+ };
+ 
+ 
+ static unsigned short noface_image[] = {
+ #include "noface.icon"
+ } ;
+ 
+ static unsigned short nomail_image[] = {
+ #include "nomail.icon"
+ } ;
+  
+ static unsigned short nopaper_image[] = {
+ #include "nopaper.icon"
+ } ;
+  
+ static unsigned short noprint_image[] = {
+ #include "noprint.icon"
+ } ;
+ 
+ static unsigned short nousers_image[] = {
+ #include "nousers.icon"
+ } ;
+ 
+ 
+ add_face(display, itype, name)
+ enum disp_type display ;
+ enum icon_type itype ;
+ char *name ;
+ {
+   Pixmap face_pr ;
+   unsigned short buf[256] ;  /* Ikon/icon image. */
+   int freeit ;               /* Set if we should destroy this pixrect. */
+  
+   freeit = 0 ;
+   switch ((int) itype)
+     {
+       case NOMAIL   : face_pr = nomail_icon ;
+                       break ;
+       case NOPAPER  : face_pr = nopaper_icon ;
+                       break ;
+       case NOPRINT  : face_pr = noprint_icon ;
+                       break ;
+       case NOUSERS  : face_pr = nousers_icon ;
+                       break ;
+       case ORDINARY : if (get_icon(name, buf) == -1) face_pr = noface_icon ;
+                       else
+                         {
+                           face_pr = load_icon(buf) ;
+                           freeit = 1 ;
+                         }
+                       break ;
+     }
+   if (display == ICON)
+     if (mtype == MONPRINTER) adjust_image(mpr, face_pr, 0, 0) ;
+     else adjust_image(mpr, face_pr, row, column) ;
+   else if (display == WINDOW) adjust_image(pr, face_pr, row, column) ;
+   else
+     { 
+       adjust_image(mpr, face_pr, row, column) ;
+       adjust_image(pr, face_pr, row, column) ;
+     }
+   if (freeit) XFreePixmap(dpy, face_pr) ;
+ }
+ 
+  
+ adjust_image(fpr, face_pr, row, column)    /* Place new face in memory pixrect. */
+ Pixmap fpr, face_pr ;
+ int row, column ;
+ {
+   switch ((int) mtype)
+     {
+       case MONNEW     : XCopyArea(dpy, fpr, fpr, gc, 0, 0,
+                           (NO_PER_ROW-1)*ICONWIDTH, ICONHEIGHT, ICONWIDTH, 0) ;
+       case MONALL     :
+       case MONPRINTER :
+       case MONUSERS   : XCopyArea(dpy, face_pr, fpr, gc, 0, 0,
+                           ICONWIDTH, ICONHEIGHT, column*ICONWIDTH, row*ICONHEIGHT) ;
+     }
+ }
+ 
+  
+ beep_flash(beeps, flashes)    /* Perform visual feedback. */
+ int beeps, flashes ;
+ {
+   static struct timeval btime = { 0, 250000 } ;   /* Beep timer. */
+ 
+   while (beeps > 0)
+     {
+       XBell(dpy, 56) ;
+       SELECT(0, (fd_set *) 0, (fd_set *) 0, (fd_set *) 0, &btime) ;
+       beeps-- ;
+     }
+   while (flashes > 0)
+     {
+       XSetFunction(dpy, gc, GXcopyInverted) ;
+       XCopyArea(dpy, frame, frame, gc, 0, 0,
+                 (unsigned int) width, (unsigned int) height, 0, 0) ;
+       XCopyArea(dpy, frame, frame, gc, 0, 0,
+                 (unsigned int) width, (unsigned int) height, 0, 0) ;
+ 
+       XCopyArea(dpy, frame_icon, frame_icon, gc, 0, 0,
+                 (unsigned int) width, (unsigned int) height, 0, 0) ;
+       XCopyArea(dpy, frame_icon, frame_icon, gc, 0, 0,
+                 (unsigned int) width, (unsigned int) height, 0, 0) ;
+       flashes-- ;
+     }
+   XSetFunction(dpy, gc, GXcopy) ;
+ }
+ 
+ 
+ create_pixrects(width, height)   /* Create pixrects for the face images. */
+ int width, height ;
+ {
+   int i, j ;
+ 
+   old_pr = pr ;
+   pr = XCreatePixmap(dpy, frame,
+                      (unsigned int) width, (unsigned int) height, 1) ;
+  
+   for (i = 0; i < (height / ICONHEIGHT); i++)
+     for (j = 0; j < (width / ICONWIDTH); j++)
+       XCopyArea(dpy, background, pr, gc, 0, 0, ICONWIDTH, ICONHEIGHT,
+                                          j*ICONWIDTH, i*ICONHEIGHT) ;
+  
+   old_mpr = mpr ;
+   if (mtype == MONPRINTER)
+     mpr = XCreatePixmap(dpy, frame, ICONWIDTH, ICONHEIGHT, 1) ;
+   else
+     {
+       mpr = XCreatePixmap(dpy, frame,
+                           (unsigned int) width, (unsigned int) height, 1) ;
+       for (i = 0; i < (height / ICONHEIGHT); i++)
+         for (j = 0; j < (width / ICONWIDTH); j++)
+           XCopyArea(dpy, background, mpr, gc, 0, 0, ICONWIDTH, ICONHEIGHT,
+                                               j*ICONWIDTH, i*ICONHEIGHT) ;
+     }
+  
+   if (mtype == MONNEW && old_pr != NULL)
+     XCopyArea(dpy, old_pr, pr, gc, 0, 0,
+               (unsigned int) width, (unsigned int) height, 0, 0) ;
+   if (mtype == MONNEW && old_mpr != NULL)
+     XCopyArea(dpy, old_mpr, mpr, gc, 0, 0,
+               (unsigned int) width, (unsigned int) height, 0, 0) ;
+ }
+ 
+ 
+ init_ws_type()
+ {
+   gtype = X11 ;
+   return(0) ;
+ }
+ 
+ 
+ Pixmap
+ load_icon(sbuf)
+ unsigned short sbuf[256] ;
+ {
+   char cbuf[512] ;
+   int i ;
+ 
+   for (i = 0; i < 256; i++)
+     {
+       cbuf[i*2+0] = revtable[(sbuf[i] >> 8) & 0xFF] ;
+       cbuf[i*2+1] = revtable[sbuf[i] & 0xFF] ;
+     }
+   return(XCreateBitmapFromData(dpy, RootWindow(dpy, screen), cbuf,
+                                      ICONWIDTH, ICONHEIGHT)) ;
+ }
+ 
+ 
+ /*ARGSUSED*/
+ make_frame(argc,argv)
+ int argc ;
+ char *argv[] ;
+ {
+   unsigned short buf[256] ;  /* For background pattern. */
+   unsigned int h, w ;        /* Window dimensions. */
+   int flags, i, j ;
+   int x, y ;                 /* Window position. */
+ 
+   x = wx ;
+   y = wy ;
+   w = NO_PER_ROW * ICONWIDTH ;
+   h = ICONHEIGHT * 10 ;
+ 
+   if ((dpy = XOpenDisplay(display)) == NULL)
+     {
+       FPRINTF(stderr,"%s: Couldn't open display %s\n", progname,
+               (getenv ("DISPLAY") ? getenv("DISPLAY") : display)) ;
+       exit(1) ;
+     }
+   xfd = ConnectionNumber(dpy) ;
+ 
+ #ifdef SUNOS3.x
+   fullmask = 1 << xfd ;
+ #else
+   FD_ZERO(&fullmask) ;
+   FD_SET(xfd, &fullmask) ;
+ #endif SUNOS3.x
+ 
+   screen = DefaultScreen(dpy) ;
+   foregnd = BlackPixel(dpy, screen) ;
+   backgnd = WhitePixel(dpy, screen) ;
+ 
+   if (mtype == MONPRINTER) faces_icon = noprint_icon ;
+   else faces_icon = nomail_icon ;
+ 
+   sfont = XLoadQueryFont(dpy, FONT) ;
+   if (sfont == NULL)
+     sfont = XLoadQueryFont(dpy, DEF_FONT) ;
+   if (sfont == NULL)
+     {
+       perror("couldn't get a font.") ;
+       exit(1) ;
+     }
+ 
+   gc_mask = GCFont | GCForeground | GCBackground ;
+   gc_val.font = sfont->fid ;
+   gc_val.foreground = foregnd ;
+   gc_val.background = backgnd ;
+   gc = XCreateGC(dpy, RootWindow(dpy, screen), gc_mask, &gc_val) ;
+   XSetFunction(dpy, gc, GXcopy) ;
+ 
+   for (i = 0; i < 16; i++)    /* Load default gray background. */
+     {
+       for (j = 0; j < 4; j++) buf[i*16+j] = 0x7777 ;
+       for (j = 0; j < 4; j++) buf[i*16+4+j] = 0xDDDD ;
+       for (j = 0; j < 4; j++) buf[i*16+8+j] = 0xBBBB ;
+       for (j = 0; j < 4; j++) buf[i*16+12+j] = 0xEEEE ;
+     }
+   if (strlen(bgicon)) GET_SUN_ICON(bgicon, buf) ;
+   background = load_icon(buf) ;
+ 
+   if (geometry)
+     {
+       flags = XParseGeometry(geometry, &x, &y, &w, &h) ;
+       if ((flags & XValue) && (flags & XNegative))
+         x += DisplayWidth(dpy, screen) - w ;
+       if ((flags & YValue) && (flags & YNegative))
+         y += DisplayHeight(dpy, screen) - h ;
+     }
+ 
+   frame = XCreateSimpleWindow(dpy, RootWindow(dpy, screen), x, y,
+                 w, h, 2, foregnd, backgnd) ;
+   XSelectInput(dpy, frame, FRAME_MASK) ;
+ 
+   frame_icon =  XCreateSimpleWindow(dpy, RootWindow(dpy, screen), 0, 0,
+                 w, h, 2, foregnd, backgnd) ;
+   XSelectInput(dpy, frame_icon, FRAME_MASK) ;
+ 
+   wm_hints.icon_x = ix ;
+   wm_hints.icon_y = iy ;
+   wm_hints.flags = IconPositionHint | IconPixmapHint | IconWindowHint ;
+   wm_hints.icon_window = frame_icon ;
+   if (iconic)
+     {
+       wm_hints.initial_state = IconicState ;
+       wm_hints.flags |= StateHint ;
+     }
+   XSetWMHints(dpy, frame, &wm_hints) ;
+ 
+   size.flags = (PPosition | PSize | PMinSize | PMaxSize) ;
+   size.x = x ;
+   size.y = y ;
+   size.width = size.min_width = size.max_width = w ;
+   size.height = size.min_height = size.max_height = h ;
+   XSetStandardProperties(dpy, frame, (char *) NULL, (char *) NULL, None,
+                 argv, argc, &size) ;
+  
+   noface_icon = load_icon(noface_image) ;
+   nomail_icon = load_icon(nomail_image) ;
+   nopaper_icon = load_icon(nopaper_image) ;
+   noprint_icon = load_icon(noprint_image) ;
+   nousers_icon = load_icon(nousers_image) ;
+ 
+   width = NO_PER_ROW * ICONWIDTH ;
+   height = ICONHEIGHT ;
+ }
+  
+ 
+ make_icon()   /* Null routine. Icons are loaded in make_frame. */
+ {}
+ 
+ 
+ show_display()    /* Show the latest set of mail icon faces. */
+ {
+   if (invert)     /* Invert the memory pixrects before displaying. */
+     {
+       XSetFunction(dpy, gc, GXcopyInverted) ;
+       XCopyArea(dpy, pr, pr, gc, 0, 0,
+                 (unsigned int) width, (unsigned int) height, 0, 0) ;
+       XCopyArea(dpy, mpr, mpr, gc, 0, 0,
+                 (unsigned int)  width, (unsigned int) height, 0, 0) ;
+     }
+   XSetFunction(dpy, gc, GXcopy) ; 
+   XMapWindow(dpy, frame) ;
+ 
+   if (mtype != MONPRINTER)
+     XResizeWindow(dpy, frame_icon,
+                   (unsigned int) width, (unsigned int) height) ;
+ 
+   XCopyArea(dpy, mpr, frame_icon, gc, 0, 0,
+             (unsigned int) width, (unsigned int) height, 0, 0) ;
+ 
+   XResizeWindow(dpy, frame, (unsigned int) width, (unsigned int) height) ;
+   XCopyArea(dpy, pr, frame, gc, 0, 0,
+             (unsigned int) width, (unsigned int) height, 0, 0) ;
+  
+   if (newmail) beep_flash(beeps, flashes) ;
+   if (old_pr) XFreePixmap(dpy, old_pr) ;
+   if (old_mpr) XFreePixmap(dpy, old_mpr) ;
+   XSync(dpy, 0) ;
+ }
+  
+ 
+ start_tool()
+ {
+   struct timeval tval ;    /* To set checking period. */
+   XEvent event ;           /* For events received. */
+  
+   tval.tv_usec = 0 ;
+   tval.tv_sec = period ;
+ 
+   for (;;)
+     {
+       readmask = fullmask ;
+ #ifdef SUNOS3.x
+       SELECT(32, &readmask, 0, 0, &tval) ;
+       if (readmask && (1 << xfd))
+ #else
+       SELECT(FD_SETSIZE, &readmask, (fd_set *) 0, (fd_set *) 0, &tval) ;
+       if (FD_ISSET(xfd, &readmask))
+ #endif SUNOS3.x
+         {
+           XNextEvent(dpy, &event) ;
+           if (event.type == Expose && event.xexpose.count == 0)
+             {
+               while (XCheckTypedEvent(dpy, Expose, &event)) /* do nothing. */ ;
+               XCopyArea(dpy, pr, frame, gc, 0, 0,
+                         (unsigned int) width, (unsigned int) height, 0, 0) ;
+               XCopyArea(dpy, mpr, frame_icon, gc, 0, 0,
+                         (unsigned int) width, (unsigned int) height, 0, 0) ;
+             }
+         }
+       else do_check() ;     /* Check the mail/printer/user queue again. */
+     }
+ }
+  
+ 
+ text(display, just, str)
+ enum disp_type display ;
+ enum just_type just ;
+ char *str ;
+ {
+   int len ;
+   int c, r ;         /* Column and row position for this face. */
+   int x, y ;         /* Position of start of this text string. */
+   Pixmap tpr ;
+  
+   c = column ;
+   r = row ;
+   switch ((int) display)
+     {
+       case BOTH   : text(ICON, just, str) ;
+                     text(WINDOW, just, str) ;
+                     return ;
+       case ICON   : tpr = mpr ;
+                     if ((mtype == MONNEW) || (mtype == MONPRINTER))
+                       c = r = 0 ;
+                     break ;
+       case WINDOW : tpr = pr ;
+     }
+  
+   len = strlen(str) ;    /* Character length of text. */
+   if (len > 10)
+     {
+       len = 10 ;
+       str[10] = '\0' ;   /* Maximum of 10 characters. */
+     }
+   switch ((int) just)
+     {
+       case LEFT  : x = c*ICONWIDTH+2 ;
+                    y = (r+1)*ICONHEIGHT-2 ;
+                    break ;
+       case RIGHT : x = (c+1)*ICONWIDTH-(len*6)-2 ;
+                    y = (r+1)*ICONHEIGHT-2 ;
+     }
+   XSetFunction(dpy, gc, GXandInverted) ;
+   XFillRectangle(dpy, tpr, gc, x, y-9, (unsigned int) len*6+2, 10) ;
+   XSetFunction(dpy, gc, GXxor) ;
+   XDrawImageString(dpy, tpr, gc, x, y, str, strlen(str)) ;
+   XSetFunction(dpy, gc, GXcopy) ;
+ }



More information about the Comp.sources.bugs mailing list