v08i007: xbiff2, Part01/01

Filip Sawicki LAKE fs at uwasa.fi
Wed Jun 27 16:50:02 AEST 1990


Submitted-by: Filip Sawicki LAKE <fs at uwasa.fi>
Posting-number: Volume 8, Issue 7
Archive-name: xbiff2/part01

[ Moderator's note: People have been asking for the next version of
    xwatch (which is the replacement for xbiff).  I haven't had the
    time to get that together, so please be patient :-).  This posting
    has nothing to do with xwatch -- it is a slight modification to
    the original xbiff program --dan
]

  Here is my next small contribution. This time I modified Mailbox
Widget and xbiff to hide (unmap) window on empty mailbox -- I really
hate useless stuff hanging on my screen.

  New resource for Mailbox
	"hideEmpty" (Boolean), default value: false
controls hiding of the empty Mailbox. With the value of false, new
Mailbox is exactly the old one: new parts of code are skipped.

  New command line options for xbiff:
	-hide - hide empty Mailbox
	-show - always show Mailbox (works just like an old xbiff)

  These modifications were made long time ago for X11R3, and now I
ported them to X11R4. Everything works well, but, at least under TWM,
it's a good idea to set mailbox position with -geometry (check why).
Mapped window immediately gets lowered -- I had to do that to avoid
xbiff showing itself on top of xlock (and burning screen).

  One possible drawback of this version is that the modified Mailbox
cannot be used within a bigger program with hideEmpty option set on:
instead of hiding it's own window, Mailbox simply unmaps its top-level
ancestor.

  Following posting includes all needed files plus a context diffs.

/* to the group moderator: please send me info before you post, to
allow me inform comp.windows.x readers */

fi.

#!/bin/sh
# This is a shell archive (shar 3.24)
# made 06/21/1990 13:55 UTC by fs at chyde
# Source directory /home2/cc/fs/xbiff/expo
#
# existing files WILL be overwritten
#
# This shar contains:
# length  mode       name
# ------ ---------- ------------------------------------------
#    217 -rw------- Imakefile
#   4431 -rw------- diffs
#  17737 -rw------- Mailbox.c
#   1863 -rw------- Mailbox.h
#   2587 -rw------- MailboxP.h
#   3810 -rw------- xbiff.c
#
if touch 2>&1 | fgrep '[-amc]' > /dev/null
 then TOUCH=touch
 else TOUCH=true
fi
# ============= Imakefile ==============
echo "x - extracting Imakefile (Text)"
sed 's/^X//' << 'SHAR_EOF' > Imakefile &&
X       INCLUDES = -I$(TOP)
X        DEPLIBS = XawClientDepLibs
XLOCAL_LIBRARIES = XawClientLibs
X  SYS_LIBRARIES = -lm
X           SRCS = xbiff.c Mailbox.c
X           OBJS = xbiff.o Mailbox.o
X
XComplexProgramTarget(xbiff)
SHAR_EOF
$TOUCH -am 0621161090 Imakefile &&
chmod 0600 Imakefile ||
echo "restore of Imakefile failed"
set `wc -c Imakefile`;Wc_c=$1
if test "$Wc_c" != "217"; then
	echo original size 217, current size $Wc_c
fi
# ============= diffs ==============
echo "x - extracting diffs (Text)"
sed 's/^X//' << 'SHAR_EOF' > diffs &&
X*** xbiff.c.orig	Thu Jun 21 16:51:54 1990
X--- xbiff.c	Thu Jun 21 16:12:50 1990
X***************
X*** 20,26 ****
X  #include <X11/Xatom.h>
X  #include <X11/Intrinsic.h>
X  #include <X11/StringDefs.h>
X! #include <X11/Xaw/Mailbox.h>
X  #include <X11/Xaw/Cardinals.h>
X  
X  extern void exit();
X--- 20,26 ----
X  #include <X11/Xatom.h>
X  #include <X11/Intrinsic.h>
X  #include <X11/StringDefs.h>
X! #include "Mailbox.h"
X  #include <X11/Xaw/Cardinals.h>
X  
X  extern void exit();
X***************
X*** 33,38 ****
X--- 33,40 ----
X  { "-file",   "*mailbox.file", XrmoptionSepArg, (caddr_t) NULL },
X  { "-volume", "*mailbox.volume", XrmoptionSepArg, (caddr_t) NULL },
X  { "-shape",  "*mailbox.shapeWindow", XrmoptionNoArg, (caddr_t) "on" },
X+ { "-hide",   "*mailbox.hideEmpty",  XrmoptionNoArg, (caddr_t) "true" },
X+ { "-show",   "*mailbox.hideEmpty",  XrmoptionNoArg, (caddr_t) "false" },
X  };
X  
X  static XtActionsRec xbiff_actions[] = {
X***************
X*** 53,58 ****
X--- 55,62 ----
X  "    -fg color                      foreground color",
X  "    -rv                            reverse video",
X  "    -shape                         shape the window",
X+ "    -hide                          hide (unmap) empty mailbox",
X+ "    -show                          always show empty mailbox",
X  NULL};
X      char **cpp;
X  
X*** MailboxP.h.orig	Thu Jun 21 16:52:11 1990
X--- MailboxP.h	Thu Jun 21 16:14:06 1990
X***************
X*** 19,25 ****
X  #ifndef _XawMailboxP_h
X  #define _XawMailboxP_h
X  
X! #include <X11/Xaw/Mailbox.h>
X  
X  #ifdef SYSV
X  #define MAILBOX_DIRECTORY "/usr/mail"
X--- 19,25 ----
X  #ifndef _XawMailboxP_h
X  #define _XawMailboxP_h
X  
X! #include "Mailbox.h"
X  
X  #ifdef SYSV
X  #define MAILBOX_DIRECTORY "/usr/mail"
X***************
X*** 42,47 ****
X--- 42,48 ----
X      long last_size;			/* size in bytes of mailboxname */
X      XtIntervalId interval_id;		/* time between checks */
X      Boolean flag_up;			/* is the flag up? */
X+     Boolean hide_empty;			/* hide empty mailbox ? */
X      struct _mbimage {
X  	Pixmap bitmap, mask;		/* depth 1, describing shape */
X  	Pixmap pixmap;			/* full depth pixmap */
X*** Mailbox.h.orig	Thu Jun 21 16:52:23 1990
X--- Mailbox.h	Thu Jun 21 16:14:40 1990
X***************
X*** 39,44 ****
X--- 39,45 ----
X  #define XtNemptyPixmapMask "emptyPixmapMask"
X  #define XtNflip "flip"
X  #define XtNshapeWindow "shapeWindow"
X+ #define XtNhideEmpty "hideEmpty"
X  
X  #define XtCCheckCommand "CheckCommand"
X  #define XtCVolume "Volume"
X*** Mailbox.c.orig	Thu Jun 21 16:52:36 1990
X--- Mailbox.c	Thu Jun 21 16:24:03 1990
X***************
X*** 34,40 ****
X  #include <X11/bitmaps/mailempty>	/* for flag down (mail not here) */
X  
X  #include <X11/Xaw/XawInit.h>
X! #include <X11/Xaw/MailboxP.h>		/* for implementation mailbox stuff */
X  
X  #include <X11/Xmu/Converters.h>		/* for XmuCvtStringToBitmap */
X  
X--- 34,40 ----
X  #include <X11/bitmaps/mailempty>	/* for flag down (mail not here) */
X  
X  #include <X11/Xaw/XawInit.h>
X! #include "MailboxP.h"			/* for implementation mailbox stuff */
X  
X  #include <X11/Xmu/Converters.h>		/* for XmuCvtStringToBitmap */
X  
X***************
X*** 100,105 ****
X--- 100,107 ----
X  	offset (empty.mask), XtRBitmap, (caddr_t) &nopix },
X      { XtNflip, XtCFlip, XtRBoolean, sizeof(Boolean),
X  	offset (flipit), XtRString, "true" },
X+     { XtNhideEmpty, XtCBoolean, XtRBoolean, sizeof(Boolean),
X+ 	offset(hide_empty), XtRImmediate, (caddr_t)False },
X  #ifdef SHAPE
X      { XtNshapeWindow, XtCShapeWindow, XtRBoolean, sizeof(Boolean),
X          offset (shapeit), XtRString, "false" },
X***************
X*** 547,552 ****
X--- 549,558 ----
X  	redisplay = TRUE;
X      }
X  
X+     if (current->mailbox.hide_empty != new->mailbox.hide_empty &&
X+ 	! new->mailbox.flag_up)
X+ 	redisplay = TRUE;	/* either will hide or show */
X+ 
X      return (redisplay);
X  }
X  
X***************
X*** 564,569 ****
X--- 570,576 ----
X      GC gc = w->mailbox.gc;
X      Pixel back = w->core.background_pixel;
X      struct _mbimage *im;
X+     Widget par;
X  
X      /* center the picture in the window */
X  
X***************
X*** 605,610 ****
X--- 612,629 ----
X  	}
X      }
X  #endif
X+ 
X+     if (w->mailbox.hide_empty) {
X+ 	for (par=(Widget)w; XtParent(par); par = XtParent(par)) ;	
X+ 	/* should look for windows, instead */
X+ 	if (w->mailbox.flag_up) {
X+ 	    XtMapWidget(par);
X+ 	    XLowerWindow(XtDisplay(par), XtWindow(par));
X+ 	    /* to avoid hanging on top of xlock */
X+ 	}
X+ 	else
X+ 	    XtUnmapWidget(par);
X+     }
X  
X      return;
X  }
SHAR_EOF
$TOUCH -am 0621165290 diffs &&
chmod 0600 diffs ||
echo "restore of diffs failed"
set `wc -c diffs`;Wc_c=$1
if test "$Wc_c" != "4431"; then
	echo original size 4431, current size $Wc_c
fi
# ============= Mailbox.c ==============
echo "x - extracting Mailbox.c (Text)"
sed 's/^X//' << 'SHAR_EOF' > Mailbox.c &&
X/*
X * $XConsortium: Mailbox.c,v 1.35 89/10/09 16:51:44 jim Exp $
X *
X * Copyright 1988 Massachusetts Institute of Technology
X *
X * Permission to use, copy, modify, and distribute this software and its
X * documentation for any purpose and without fee is hereby granted, provided
X * that the above copyright notice appear in all copies and that both that
X * copyright notice and this permission notice appear in supporting
X * documentation, and that the name of M.I.T. not be used in advertising or
X * publicity pertaining to distribution of the software without specific,
X * written prior permission.  M.I.T. makes no representations about the
X * suitability of this software for any purpose.  It is provided "as is"
X * without express or implied warranty.
X *
X * Author:  Jim Fulton, MIT X Consortium
X *
X * I recommend that you use the new mailfull and mailempty bitmaps instead of
X * the ugly mailboxes:
X *
X *         XBiff*fullPixmap:  mailfull
X *         XBiff*emptyPixmap:  mailempty
X */
X
X#include <stdio.h>			/* for printing error messages */
X#include <pwd.h>			/* for getting username */
X
X#include <X11/cursorfont.h>		/* for cursor constants */
X#include <X11/StringDefs.h>		/* for useful atom names */
X#include <X11/IntrinsicP.h>		/* for toolkit stuff */
X#include <sys/stat.h>			/* for stat() ** needs types.h ***/
X
X#include <X11/bitmaps/mailfull>		/* for flag up (mail present) bits */
X#include <X11/bitmaps/mailempty>	/* for flag down (mail not here) */
X
X#include <X11/Xaw/XawInit.h>
X#include "MailboxP.h"			/* for implementation mailbox stuff */
X
X#include <X11/Xmu/Converters.h>		/* for XmuCvtStringToBitmap */
X
X#ifdef SHAPE
X#include <X11/extensions/shape.h>
X#endif
X
X/*
X * The default user interface is to have the mailbox turn itself off whenever
X * the user presses a button in it.  Expert users might want to make this 
X * happen on EnterWindow.  It might be nice to provide support for some sort of
X * exit callback so that you can do things like press q to quit.
X */
X
Xstatic char defaultTranslations[] = 
X  "<ButtonPress>:  unset()";
X
Xstatic void Check(), Set(), Unset();
X
Xstatic XtActionsRec actionsList[] = { 
X    { "check",	Check },
X    { "unset",	Unset },
X    { "set",	Set },
X};
X
X
X/* Initialization of defaults */
X
X#define offset(field) XtOffset(MailboxWidget,mailbox.field)
X#define goffset(field) XtOffset(Widget,core.field)
X
Xstatic Dimension defDim = 48;
Xstatic Pixmap nopix = None;
X
Xstatic XtResource resources[] = {
X    { XtNwidth, XtCWidth, XtRDimension, sizeof (Dimension), 
X	goffset (width), XtRDimension, (caddr_t)&defDim },
X    { XtNheight, XtCHeight, XtRDimension, sizeof (Dimension),
X	goffset (height), XtRDimension, (caddr_t)&defDim },
X    { XtNupdate, XtCInterval, XtRInt, sizeof (int),
X	offset (update), XtRString, "30" },
X    { XtNforeground, XtCForeground, XtRPixel, sizeof (Pixel),
X	offset (foreground_pixel), XtRString, "black" },
X    { XtNbackground, XtCBackground, XtRPixel, sizeof (Pixel),
X	goffset (background_pixel), XtRString, "white" },
X    { XtNreverseVideo, XtCReverseVideo, XtRBoolean, sizeof (Boolean),
X	offset (reverseVideo), XtRString, "FALSE" },
X    { XtNfile, XtCFile, XtRString, sizeof (String),
X	offset (filename), XtRString, NULL },
X    { XtNcheckCommand, XtCCheckCommand, XtRString, sizeof(char*),
X	offset (check_command), XtRString, NULL},
X    { XtNvolume, XtCVolume, XtRInt, sizeof(int),
X	offset (volume), XtRString, "33"},
X    { XtNonceOnly, XtCBoolean, XtRBoolean, sizeof(Boolean),
X	offset (once_only), XtRImmediate, (caddr_t)False },
X    { XtNfullPixmap, XtCPixmap, XtRBitmap, sizeof(Pixmap),
X	offset (full.bitmap), XtRString, "flagup" },
X    { XtNfullPixmapMask, XtCPixmapMask, XtRBitmap, sizeof(Pixmap),
X	offset (full.mask), XtRBitmap, (caddr_t) &nopix },
X    { XtNemptyPixmap, XtCPixmap, XtRBitmap, sizeof(Pixmap),
X	offset (empty.bitmap), XtRString, "flagdown" },
X    { XtNemptyPixmapMask, XtCPixmapMask, XtRBitmap, sizeof(Pixmap),
X	offset (empty.mask), XtRBitmap, (caddr_t) &nopix },
X    { XtNflip, XtCFlip, XtRBoolean, sizeof(Boolean),
X	offset (flipit), XtRString, "true" },
X    { XtNhideEmpty, XtCBoolean, XtRBoolean, sizeof(Boolean),
X	offset(hide_empty), XtRImmediate, (caddr_t)False },
X#ifdef SHAPE
X    { XtNshapeWindow, XtCShapeWindow, XtRBoolean, sizeof(Boolean),
X        offset (shapeit), XtRString, "false" },
X#endif
X};
X
X#undef offset
X#undef goffset
X
Xstatic void GetMailFile(), CloseDown();
Xstatic void check_mailbox(), redraw_mailbox(), beep();
Xstatic void ClassInitialize(), Initialize(), Realize(), Destroy(), Redisplay();
Xstatic Boolean SetValues();
X
XMailboxClassRec mailboxClassRec = {
X    { /* core fields */
X    /* superclass		*/	&widgetClassRec,
X    /* class_name		*/	"Mailbox",
X    /* widget_size		*/	sizeof(MailboxRec),
X    /* class_initialize		*/	ClassInitialize,
X    /* class_part_initialize	*/	NULL,
X    /* class_inited		*/	FALSE,
X    /* initialize		*/	Initialize,
X    /* initialize_hook		*/	NULL,
X    /* realize			*/	Realize,
X    /* actions			*/	actionsList,
X    /* num_actions		*/	XtNumber(actionsList),
X    /* resources		*/	resources,
X    /* resource_count		*/	XtNumber(resources),
X    /* xrm_class		*/	NULL,
X    /* compress_motion		*/	TRUE,
X    /* compress_exposure	*/	TRUE,
X    /* compress_enterleave	*/	TRUE,
X    /* visible_interest		*/	FALSE,
X    /* destroy			*/	Destroy,
X    /* resize			*/	NULL,
X    /* expose			*/	Redisplay,
X    /* set_values		*/	SetValues,
X    /* set_values_hook		*/	NULL,
X    /* set_values_almost	*/	XtInheritSetValuesAlmost,
X    /* get_values_hook		*/	NULL,
X    /* accept_focus		*/	NULL,
X    /* version			*/	XtVersion,
X    /* callback_private		*/	NULL,
X    /* tm_table			*/	defaultTranslations,
X    /* query_geometry		*/	XtInheritQueryGeometry,
X    /* display_accelerator	*/	XtInheritDisplayAccelerator,
X    /* extension		*/	NULL
X    }
X};
X
XWidgetClass mailboxWidgetClass = (WidgetClass) &mailboxClassRec;
X
X
X/*
X * widget initialization
X */
X
Xstatic void ClassInitialize ()
X{
X    static XtConvertArgRec screenConvertArg[] = {
X    { XtWidgetBaseOffset, (caddr_t) XtOffset(Widget, core.screen), sizeof(Screen *) }
X    };
X
X    XawInitializeWidgetSet();
X    XtAddConverter (XtRString, XtRBitmap, XmuCvtStringToBitmap,
X		    screenConvertArg, XtNumber(screenConvertArg));
X    return;
X}
X
Xstatic GC get_mailbox_gc (w)
X    MailboxWidget w;
X{
X    XtGCMask valuemask;
X    XGCValues xgcv;
X
X    valuemask = GCForeground | GCBackground | GCFunction | GCGraphicsExposures;
X    xgcv.foreground = w->mailbox.foreground_pixel;
X    xgcv.background = w->core.background_pixel;
X    xgcv.function = GXcopy;
X    xgcv.graphics_exposures = False;	/* this is Bool, not Boolean */
X    return (XtGetGC ((Widget) w, valuemask, &xgcv));
X}
X
X
X/* ARGSUSED */
Xstatic void Initialize (request, new)
X    Widget request, new;
X{
X    MailboxWidget w = (MailboxWidget) new;
X#ifdef SHAPE
X    int shape_event_base, shape_error_base;
X#endif
X
X    if (!w->mailbox.filename) GetMailFile (w);
X
X    if (w->core.width <= 0) w->core.width = 1;
X    if (w->core.height <= 0) w->core.height = 1;
X
X    if (w->mailbox.reverseVideo) {
X	Pixel tmp;
X
X	tmp = w->mailbox.foreground_pixel;
X	w->mailbox.foreground_pixel = w->core.background_pixel;
X	w->core.background_pixel = tmp;
X    }
X
X#ifdef SHAPE
X    if (w->mailbox.shapeit && !XShapeQueryExtension (XtDisplay (w),
X						     &shape_event_base,
X						     &shape_error_base))
X      w->mailbox.shapeit = False;
X    w->mailbox.shape_cache.mask = None;
X#endif
X
X    w->mailbox.gc = get_mailbox_gc (w);
X    w->mailbox.interval_id = (XtIntervalId) 0;
X    w->mailbox.full.pixmap = None;
X    w->mailbox.empty.pixmap = None;
X
X    return;
X}
X
X
X/*
X * action procedures
X */
X
X/*
X * pretend there is new mail; put widget in flagup state
X */
X
X/* ARGSUSED */
Xstatic void Set (gw, event, params, nparams)
X    Widget gw;
X    XEvent *event;
X    String *params;
X    Cardinal *nparams;
X{
X    MailboxWidget w = (MailboxWidget) gw;
X
X    w->mailbox.last_size = -1;
X
X    check_mailbox (w, TRUE, FALSE);	/* redraw, no reset */
X
X    return;
X}
X
X
X/*
X * ack the existing mail; put widget in flagdown state
X */
X
X/* ARGSUSED */
Xstatic void Unset (gw, event, params, nparams)
X    Widget gw;
X    XEvent *event;
X    String *params;
X    Cardinal *nparams;
X{
X    MailboxWidget w = (MailboxWidget) gw;
X
X    check_mailbox (w, TRUE, TRUE);	/* redraw, reset */
X
X    return;
X}
X
X
X/*
X * look to see if there is new mail; if so, Set, else Unset
X */
X
X/* ARGSUSED */
Xstatic void Check (gw, event, params, nparams)
X    Widget gw;
X    XEvent *event;
X    String *params;
X    Cardinal *nparams;
X{
X    MailboxWidget w = (MailboxWidget) gw;
X
X    check_mailbox (w, TRUE, FALSE);	/* redraw, no reset */
X
X    return;
X}
X
X
X/* ARGSUSED */
Xstatic void clock_tic (client_data, id)
X    caddr_t client_data;
X    XtIntervalId *id;
X{
X    MailboxWidget w = (MailboxWidget) client_data;
X
X    check_mailbox (w, FALSE, FALSE);	/* no redraw, no reset */
X
X    /*
X     * and reset the timer
X     */
X
X    w->mailbox.interval_id = XtAddTimeOut (w->mailbox.update * 1000,
X					   clock_tic, (caddr_t) w);
X
X    return;
X}
X
Xstatic Pixmap make_pixmap (dpy, w, bitmap, depth, flip, widthp, heightp)
X    Display *dpy;
X    MailboxWidget w;
X    Pixmap bitmap;
X    Boolean flip;
X    int depth;
X    int *widthp, *heightp;
X{
X    Window root;
X    int x, y;
X    unsigned int width, height, bw, dep;
X    unsigned long fore, back;
X
X    if (!XGetGeometry (dpy, bitmap, &root, &x, &y, &width, &height, &bw, &dep))
X      return None;
X
X    *widthp = (int) width;
X    *heightp = (int) height;
X    if (flip) {
X	fore = w->core.background_pixel;
X	back = w->mailbox.foreground_pixel;
X    } else {
X	fore = w->mailbox.foreground_pixel;
X	back = w->core.background_pixel;
X    }
X    return XmuCreatePixmapFromBitmap (dpy, w->core.window, bitmap, 
X				      width, height, depth, fore, back);
X}
X
Xstatic void Realize (gw, valuemaskp, attr)
X    Widget gw;
X    XtValueMask *valuemaskp;
X    XSetWindowAttributes *attr;
X{
X    MailboxWidget w = (MailboxWidget) gw;
X    register Display *dpy = XtDisplay (w);
X    int depth = w->core.depth;
X
X    *valuemaskp |= (CWBitGravity | CWCursor);
X    attr->bit_gravity = ForgetGravity;
X    attr->cursor = XCreateFontCursor (dpy, XC_top_left_arrow);
X
X    XtCreateWindow (gw, InputOutput, (Visual *) CopyFromParent,
X		    *valuemaskp, attr);
X
X    /*
X     * build up the pixmaps that we'll put into the image
X     */
X    if (w->mailbox.full.bitmap == None) {
X	w->mailbox.full.bitmap = 
X	  XCreateBitmapFromData (dpy, w->core.window, mailfull_bits,
X				 mailfull_width, mailfull_height);
X    }
X    if (w->mailbox.empty.bitmap == None) {
X	w->mailbox.empty.bitmap =
X	  XCreateBitmapFromData (dpy, w->core.window, mailempty_bits,
X				 mailempty_width, mailempty_height);
X    }
X
X    w->mailbox.empty.pixmap = make_pixmap (dpy, w, w->mailbox.empty.bitmap,
X					   depth, False,
X					   &w->mailbox.empty.width,
X					   &w->mailbox.empty.height);
X    w->mailbox.full.pixmap = make_pixmap (dpy, w, w->mailbox.full.bitmap,
X					  depth, w->mailbox.flipit,
X					  &w->mailbox.full.width,
X					  &w->mailbox.full.height);
X			 
X#ifdef SHAPE
X    if (w->mailbox.empty.mask == None && w->mailbox.full.mask == None)
X      w->mailbox.shapeit = False;
X#endif
X
X    w->mailbox.interval_id = XtAddTimeOut (w->mailbox.update * 1000,
X					   clock_tic, (caddr_t) w);
X
X#ifdef SHAPE
X    w->mailbox.shape_cache.mask = None;
X#endif
X
X    return;
X}
X
X
Xstatic void Destroy (gw)
X    Widget gw;
X{
X    MailboxWidget w = (MailboxWidget) gw;
X    Display *dpy = XtDisplay (gw);
X
X    XtFree (w->mailbox.filename);
X    if (w->mailbox.interval_id) XtRemoveTimeOut (w->mailbox.interval_id);
X    XtDestroyGC (w->mailbox.gc);
X#define freepix(p) if (p) XFreePixmap (dpy, p)
X    freepix (w->mailbox.full.bitmap);		/* until cvter does ref cnt */
X    freepix (w->mailbox.full.mask);		/* until cvter does ref cnt */
X    freepix (w->mailbox.full.pixmap);
X    freepix (w->mailbox.empty.bitmap);		/* until cvter does ref cnt */
X    freepix (w->mailbox.empty.mask);		/* until cvter does ref cnt */
X    freepix (w->mailbox.empty.pixmap);
X#ifdef SHAPE
X    freepix (w->mailbox.shape_cache.mask);
X#endif
X#undef freepix
X    return;
X}
X
X
Xstatic void Redisplay (gw)
X    Widget gw;
X{
X    MailboxWidget w = (MailboxWidget) gw;
X
X    check_mailbox (w, TRUE, FALSE);
X}
X
X
Xstatic void check_mailbox (w, force_redraw, reset)
X    MailboxWidget w;
X    Boolean force_redraw, reset;
X{
X    long mailboxsize = 0;
X
X    if (w->mailbox.check_command != NULL) {
X	switch (system(w->mailbox.check_command)) {
X	  case 0:
X	    mailboxsize = w->mailbox.last_size + 1;
X	    break;
X	  /* case 1 is no change */
X	  case 2:
X	    mailboxsize = 0;
X	  /* treat everything else as no change */
X	}
X    }
X    else {
X	struct stat st;
X
X	if (stat (w->mailbox.filename, &st) == 0) {
X	    mailboxsize = st.st_size;
X	}
X    }
X
X    /*
X     * Now check for changes.  If reset is set then we want to pretent that
X     * there is no mail.  If the mailbox is empty then we want to turn off
X     * the flag.  Otherwise if the mailbox has changed size then we want to
X     * put the flag up.
X     *
X     * The cases are:
X     *    o  forced reset by user                        DOWN
X     *    o  no mailbox or empty (zero-sized) mailbox    DOWN
X     *    o  same size as last time                      no change
X     *    o  bigger than last time                       UP
X     *    o  smaller than last time but non-zero         UP
X     *
X     * The last two cases can be expressed as different from last
X     * time and non-zero.
X     */
X
X    if (reset) {			/* forced reset */
X	w->mailbox.flag_up = FALSE;
X	force_redraw = TRUE;
X    } else if (mailboxsize == 0) {	/* no mailbox or empty */
X	w->mailbox.flag_up = FALSE;
X	if (w->mailbox.last_size > 0) force_redraw = TRUE;  /* if change */
X    } else if (mailboxsize != w->mailbox.last_size) {  /* different size */
X	if (!w->mailbox.once_only || !w->mailbox.flag_up)
X	    beep(w); 
X	w->mailbox.flag_up = TRUE;
X	force_redraw = TRUE;
X    } 
X
X    w->mailbox.last_size = mailboxsize;
X    if (force_redraw) redraw_mailbox (w);
X    return;
X}
X
X/*
X * get user name for building mailbox
X */
X
Xstatic void GetMailFile (w)
X    MailboxWidget w;
X{
X    char *getlogin();
X    char *username;
X
X    username = getlogin ();
X    if (!username) {
X	struct passwd *pw = getpwuid (getuid ());
X
X	if (!pw) {
X	    fprintf (stderr, "%s:  unable to find a username for you.\n",
X		     "Mailbox widget");
X	    CloseDown (w, 1);
X	}
X	username = pw->pw_name;
X    }
X    w->mailbox.filename = (String) XtMalloc (strlen (MAILBOX_DIRECTORY) + 1 +
X				   	     strlen (username) + 1);
X    strcpy (w->mailbox.filename, MAILBOX_DIRECTORY);
X    strcat (w->mailbox.filename, "/");
X    strcat (w->mailbox.filename, username);
X    return;
X}
X
Xstatic void CloseDown (w, status)
X    MailboxWidget w;
X    int status;
X{
X    Display *dpy = XtDisplay (w);
X
X    XtDestroyWidget (w);
X    XCloseDisplay (dpy);
X    exit (status);
X}
X
X
X/* ARGSUSED */
Xstatic Boolean SetValues (gcurrent, grequest, gnew)
X    Widget gcurrent, grequest, gnew;
X{
X    MailboxWidget current = (MailboxWidget) gcurrent;
X    MailboxWidget new = (MailboxWidget) gnew;
X    Boolean redisplay = FALSE;
X
X    if (current->mailbox.update != new->mailbox.update) {
X	if (current->mailbox.interval_id) 
X	  XtRemoveTimeOut (current->mailbox.interval_id);
X	new->mailbox.interval_id = XtAddTimeOut (new->mailbox.update * 1000,
X						 clock_tic,
X						 (caddr_t) gnew);
X    }
X
X    if (current->mailbox.foreground_pixel != new->mailbox.foreground_pixel ||
X	current->core.background_pixel != new->core.background_pixel) {
X	XtDestroyGC (current->mailbox.gc);
X	new->mailbox.gc = get_mailbox_gc (new);
X	redisplay = TRUE;
X    }
X
X    if (current->mailbox.hide_empty != new->mailbox.hide_empty &&
X	! new->mailbox.flag_up)
X	redisplay = TRUE;	/* either will hide or show */
X
X    return (redisplay);
X}
X
X
X/*
X * drawing code
X */
X
Xstatic void redraw_mailbox (w)
X    MailboxWidget w;
X{
X    register Display *dpy = XtDisplay (w);
X    register Window win = XtWindow (w);
X    register int x, y;
X    GC gc = w->mailbox.gc;
X    Pixel back = w->core.background_pixel;
X    struct _mbimage *im;
X    Widget par;
X
X    /* center the picture in the window */
X
X    if (w->mailbox.flag_up) {		/* paint the "up" position */
X	im = &w->mailbox.full;
X	if (w->mailbox.flipit) back = w->mailbox.foreground_pixel;
X    } else {				/* paint the "down" position */
X	im = &w->mailbox.empty;
X    }
X    x = (((int)w->core.width) - im->width) / 2;
X    y = (((int)w->core.height) - im->height) / 2;
X
X    XSetWindowBackground (dpy, win, back);
X    XClearWindow (dpy, win);
X    XCopyArea (dpy, im->pixmap, win, gc, 0, 0, im->width, im->height, x, y);
X
X#ifdef SHAPE
X    /*
X     * XXX - temporary hack; walk up widget tree to find top most parent (which
X     * will be a shell) and mash it to have our shape.  This will be replaced
X     * by a special shell widget.
X     */
X    if (w->mailbox.shapeit) {
X	Widget parent;
X
X	for (parent = (Widget) w; XtParent(parent);
X	     parent = XtParent(parent)) {
X	    x += parent->core.x + parent->core.border_width;
X	    y += parent->core.y + parent->core.border_width;
X	}
X
X	if (im->mask != w->mailbox.shape_cache.mask ||
X	    x != w->mailbox.shape_cache.x || y != w->mailbox.shape_cache.y) {
X	    XShapeCombineMask (XtDisplay(parent), XtWindow(parent),
X			       ShapeBounding, x, y, im->mask, ShapeSet);
X	    w->mailbox.shape_cache.mask = im->mask;
X	    w->mailbox.shape_cache.x = x;
X	    w->mailbox.shape_cache.y = y;
X	}
X    }
X#endif
X
X    if (w->mailbox.hide_empty) {
X	for (par=(Widget)w; XtParent(par); par = XtParent(par)) ;	
X	/* should look for windows, instead */
X	if (w->mailbox.flag_up) {
X	    XtMapWidget(par);
X	    XLowerWindow(XtDisplay(par), XtWindow(par));
X	    /* to avoid hanging on top of xlock */
X	}
X	else
X	    XtUnmapWidget(par);
X    }
X
X    return;
X}
X
X
Xstatic void beep (w)
X    MailboxWidget w;
X{
X    XBell (XtDisplay (w), w->mailbox.volume);
X    return;
X}
SHAR_EOF
$TOUCH -am 0621162490 Mailbox.c &&
chmod 0600 Mailbox.c ||
echo "restore of Mailbox.c failed"
set `wc -c Mailbox.c`;Wc_c=$1
if test "$Wc_c" != "17737"; then
	echo original size 17737, current size $Wc_c
fi
# ============= Mailbox.h ==============
echo "x - extracting Mailbox.h (Text)"
sed 's/^X//' << 'SHAR_EOF' > Mailbox.h &&
X/*
X * $XConsortium: Mailbox.h,v 1.19 89/07/21 01:55:46 kit Exp $
X *
X * Copyright 1988 Massachusetts Institute of Technology
X *
X * Permission to use, copy, modify, and distribute this software and its
X * documentation for any purpose and without fee is hereby granted, provided
X * that the above copyright notice appear in all copies and that both that
X * copyright notice and this permission notice appear in supporting
X * documentation, and that the name of M.I.T. not be used in advertising or
X * publicity pertaining to distribution of the software without specific,
X * written prior permission.  M.I.T. makes no representations about the
X * suitability of this software for any purpose.  It is provided "as is"
X * without express or implied warranty.
X *
X * Author:  Jim Fulton, MIT X Consortium
X */
X
X#ifndef _XawMailbox_h
X#define _XawMailbox_h
X
X/*
X * Mailbox widget; looks a lot like the clock widget, don't it...
X */
X
X/* resource names used by mailbox widget that aren't defined in StringDefs.h */
X
X#define XtNupdate "update"
X
X/* command to exec */
X#define XtNcheckCommand "checkCommand"
X#define XtNonceOnly "onceOnly"
X
X/* Int: volume for bell */
X#define XtNvolume "volume"
X#define XtNfullPixmap "fullPixmap"
X#define XtNfullPixmapMask "fullPixmapMask"
X#define XtNemptyPixmap "emptyPixmap"
X#define XtNemptyPixmapMask "emptyPixmapMask"
X#define XtNflip "flip"
X#define XtNshapeWindow "shapeWindow"
X#define XtNhideEmpty "hideEmpty"
X
X#define XtCCheckCommand "CheckCommand"
X#define XtCVolume "Volume"
X#define XtCPixmapMask "PixmapMask"
X#define XtCFlip "Flip"
X#define XtCShapeWindow "ShapeWindow"
X
X
X/* structures */
X
Xtypedef struct _MailboxRec *MailboxWidget;  /* see MailboxP.h */
Xtypedef struct _MailboxClassRec *MailboxWidgetClass;  /* see MailboxP.h */
X
X
Xextern WidgetClass mailboxWidgetClass;
X
X#endif /* _XawMailbox_h */
X/* DON'T ADD STUFF AFTER THIS #endif */
SHAR_EOF
$TOUCH -am 0621161490 Mailbox.h &&
chmod 0600 Mailbox.h ||
echo "restore of Mailbox.h failed"
set `wc -c Mailbox.h`;Wc_c=$1
if test "$Wc_c" != "1863"; then
	echo original size 1863, current size $Wc_c
fi
# ============= MailboxP.h ==============
echo "x - extracting MailboxP.h (Text)"
sed 's/^X//' << 'SHAR_EOF' > MailboxP.h &&
X/*
X * $XConsortium: MailboxP.h,v 1.16 89/05/11 01:05:56 kit Exp $
X *
X * Copyright 1988 Massachusetts Institute of Technology
X *
X * Permission to use, copy, modify, and distribute this software and its
X * documentation for any purpose and without fee is hereby granted, provided
X * that the above copyright notice appear in all copies and that both that
X * copyright notice and this permission notice appear in supporting
X * documentation, and that the name of M.I.T. not be used in advertising or
X * publicity pertaining to distribution of the software without specific,
X * written prior permission.  M.I.T. makes no representations about the
X * suitability of this software for any purpose.  It is provided "as is"
X * without express or implied warranty.
X *
X * Author:  Jim Fulton, MIT X Consortium
X */
X
X#ifndef _XawMailboxP_h
X#define _XawMailboxP_h
X
X#include "Mailbox.h"
X
X#ifdef SYSV
X#define MAILBOX_DIRECTORY "/usr/mail"
X#else
X#define MAILBOX_DIRECTORY "/usr/spool/mail"
X#endif
X
Xtypedef struct {			/* new fields for mailbox widget */
X    /* resources */
X    int update;				/* seconds between updates */
X    Pixel foreground_pixel;		/* color index of normal state fg */
X    String filename;			/* filename to watch */
X    String check_command;		/* command to exec for mail check */
X    Boolean reverseVideo;		/* do reverse video? */
X    Boolean flipit;			/* do flip of full pixmap */
X    int volume;				/* bell volume */
X    Boolean once_only;			/* ring bell only once on new mail */
X    /* local state */
X    GC gc;				/* normal GC to use */
X    long last_size;			/* size in bytes of mailboxname */
X    XtIntervalId interval_id;		/* time between checks */
X    Boolean flag_up;			/* is the flag up? */
X    Boolean hide_empty;			/* hide empty mailbox ? */
X    struct _mbimage {
X	Pixmap bitmap, mask;		/* depth 1, describing shape */
X	Pixmap pixmap;			/* full depth pixmap */
X	int width, height;		/* geometry of pixmaps */
X    } full, empty;
X#ifdef SHAPE
X    Boolean shapeit;			/* do shape extension */
X    struct {
X	Pixmap mask;
X	int x, y;
X    } shape_cache;			/* last set of info */
X#endif
X} MailboxPart;
X
Xtypedef struct _MailboxRec {		/* full instance record */
X    CorePart core;
X    MailboxPart mailbox;
X} MailboxRec;
X
X
Xtypedef struct {			/* new fields for mailbox class */
X    int dummy;				/* stupid C compiler */
X} MailboxClassPart;
X
Xtypedef struct _MailboxClassRec {	/* full class record declaration */
X    CoreClassPart core_class;
X    MailboxClassPart mailbox_class;
X} MailboxClassRec;
X
Xextern MailboxClassRec mailboxClassRec;	 /* class pointer */
X
X#endif /* _XawMailboxP_h */
SHAR_EOF
$TOUCH -am 0621161490 MailboxP.h &&
chmod 0600 MailboxP.h ||
echo "restore of MailboxP.h failed"
set `wc -c MailboxP.h`;Wc_c=$1
if test "$Wc_c" != "2587"; then
	echo original size 2587, current size $Wc_c
fi
# ============= xbiff.c ==============
echo "x - extracting xbiff.c (Text)"
sed 's/^X//' << 'SHAR_EOF' > xbiff.c &&
X/*
X * $XConsortium: xbiff.c,v 1.15 89/12/12 13:55:33 rws Exp $
X *
X * Copyright 1988 Massachusetts Institute of Technology
X *
X * Permission to use, copy, modify, and distribute this software and its
X * documentation for any purpose and without fee is hereby granted, provided
X * that the above copyright notice appear in all copies and that both that
X * copyright notice and this permission notice appear in supporting
X * documentation, and that the name of M.I.T. not be used in advertising or
X * publicity pertaining to distribution of the software without specific,
X * written prior permission.  M.I.T. makes no representations about the
X * suitability of this software for any purpose.  It is provided "as is"
X * without express or implied warranty.
X *
X * Author:  Jim Fulton, MIT X Consortium
X */
X
X#include <stdio.h>
X#include <X11/Xatom.h>
X#include <X11/Intrinsic.h>
X#include <X11/StringDefs.h>
X#include "Mailbox.h"
X#include <X11/Xaw/Cardinals.h>
X
Xextern void exit();
Xstatic void quit();
X
Xchar *ProgramName;
X
Xstatic XrmOptionDescRec options[] = {
X{ "-update", "*mailbox.update", XrmoptionSepArg, (caddr_t) NULL },
X{ "-file",   "*mailbox.file", XrmoptionSepArg, (caddr_t) NULL },
X{ "-volume", "*mailbox.volume", XrmoptionSepArg, (caddr_t) NULL },
X{ "-shape",  "*mailbox.shapeWindow", XrmoptionNoArg, (caddr_t) "on" },
X{ "-hide",   "*mailbox.hideEmpty",  XrmoptionNoArg, (caddr_t) "true" },
X{ "-show",   "*mailbox.hideEmpty",  XrmoptionNoArg, (caddr_t) "false" },
X};
X
Xstatic XtActionsRec xbiff_actions[] = {
X    { "quit", quit },
X};
Xstatic Atom wm_delete_window;
X
Xstatic void Usage ()
X{
X    static char *help_message[] = {
X"where options include:",
X"    -display host:dpy              X server to contact",
X"    -geometry geom                 size of mailbox",
X"    -file file                     file to watch",
X"    -update seconds                how often to check for mail",
X"    -volume percentage             how loud to ring the bell",
X"    -bg color                      background color",
X"    -fg color                      foreground color",
X"    -rv                            reverse video",
X"    -shape                         shape the window",
X"    -hide                          hide (unmap) empty mailbox",
X"    -show                          always show empty mailbox",
XNULL};
X    char **cpp;
X
X    fprintf (stderr, "usage:  %s [-options ...]\n", ProgramName);
X    for (cpp = help_message; *cpp; cpp++) {
X	fprintf (stderr, "%s\n", *cpp);
X    }
X    fprintf (stderr, "\n");
X    exit (1);
X}
X
X
Xvoid main (argc, argv)
X    int argc;
X    char **argv;
X{
X    Widget toplevel, w;
X
X    ProgramName = argv[0];
X
X    toplevel = XtInitialize ("main", "XBiff", options, XtNumber (options),
X			     &argc, argv);
X    if (argc != 1) Usage ();
X
X    /*
X     * This is a hack so that f.delete will do something useful in this
X     * single-window application.
X     */
X    XtAppAddActions (XtWidgetToApplicationContext(toplevel),
X                     xbiff_actions, XtNumber(xbiff_actions));
X    XtOverrideTranslations(toplevel,
X		   XtParseTranslationTable ("<Message>WM_PROTOCOLS: quit()"));
X
X    w = XtCreateManagedWidget ("mailbox", mailboxWidgetClass, toplevel,
X			       NULL, 0);
X    XtRealizeWidget (toplevel);
X    wm_delete_window = XInternAtom (XtDisplay(toplevel), "WM_DELETE_WINDOW",
X                                    False);
X    (void) XSetWMProtocols (XtDisplay(toplevel), XtWindow(toplevel),
X                            &wm_delete_window, 1);
X    XtMainLoop ();
X}
X
Xstatic void quit (w, event, params, num_params)
X    Widget w;
X    XEvent *event;
X    String *params;
X    Cardinal *num_params;
X{
X    if (event->type == ClientMessage &&
X        event->xclient.data.l[0] != wm_delete_window) {
X        XBell (XtDisplay(w), 0);
X        return;
X    }
X    XCloseDisplay (XtDisplay(w));
X    exit (0);
X}
SHAR_EOF
$TOUCH -am 0621161290 xbiff.c &&
chmod 0600 xbiff.c ||
echo "restore of xbiff.c failed"
set `wc -c xbiff.c`;Wc_c=$1
if test "$Wc_c" != "3810"; then
	echo original size 3810, current size $Wc_c
fi
exit 0

dan
----------------------------------------------------
O'Reilly && Associates   argv at sun.com / argv at ora.com
Opinions expressed reflect those of the author only.



More information about the Comp.sources.x mailing list