home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1994 January / usenetsourcesnewsgroupsinfomagicjanuary1994.iso / sources / x / volume4 / aquarium / part01 next >
Encoding:
Internet Message Format  |  1989-08-18  |  30.8 KB

  1. Path: uunet!island!argv
  2. From: argv@island.uu.net (Dan Heller)
  3. Newsgroups: comp.sources.x
  4. Subject: v04i091: Aquarium, Part01/02
  5. Message-ID: <999@island.uu.net>
  6. Date: 17 Aug 89 20:18:57 GMT
  7. Organization: Island Graphics, Marin County, California
  8. Lines: 1121
  9. Approved: island!argv@sun.com
  10.  
  11. Submitted-by: uunet!umd5.umd.edu!jonnyg (Jon Greenblatt)
  12. Posting-number: Volume 4, Issue 91
  13. Archive-name: aquarium/part01
  14.  
  15.     This is a color/monocrome living aquarium program. The original
  16. author is unknown. The command line parsing needs to be fixed but
  17. other than that things seem to be in good shape. After unarchiving this
  18. and setting up the Makefile, type "make unshar" to uncompress the
  19. bitmap file.
  20.  
  21.                     JonnyG.
  22.  
  23. # This is a shell archive.  Remove anything before this line,
  24. # then unpack it by saving it in a file and typing "sh file".
  25. #
  26. # Wrapped by rover.umd.edu!jonnyg on Wed Aug 16 10:53:04 EDT 1989
  27. # Contents:  FIRST.README Imakefile Makefile xfish.c
  28.  
  29. echo x - FIRST.README
  30. sed 's/^@//' > "FIRST.README" <<'@//E*O*F FIRST.README//'
  31.  
  32. Ported from X10R4 to X11R3 by Jonathan Roger Greenblatt (jonnyg@rover.umd.edu)
  33.     8/10/89
  34.  
  35. Original Author of the X10 version is Unknown.
  36.  
  37.                  XAquarium
  38.                 ===========
  39. XAquarium is an X Windows application which creates a full-screen background
  40. window complete with color fish and translucent bubbles.  This program is
  41. not to be confused with the older 'xfish' which featured small monochrome
  42. fish on a monochrome background.  On the contrary.  XAquarium features
  43. highly detailed fish in living color, translucent bubbles, and a full color
  44. background.  With that confusion removed, the program will be referred to
  45. as 'XFish' from this point forward.
  46.  
  47. Scientific Note: Research has shown that a moving aquarium background creates
  48. a soothing and relaxing atmosphere, thereby reducing the stresses associated
  49. with day-to-day workstation usage.  A corresponding increase in productivity
  50. should result, although this is yet to be shown.
  51.  
  52.  
  53. XFish Creation
  54. --------------
  55. The package includes four files ...
  56.     * FIRST.README    (this file)
  57.     * Makefile    (makefile for complete compilation)
  58.     * xfish.c    (application code)
  59.     * xfishy.c    (fairly large file containing pixmaps and bitmaps)
  60.  
  61. After unpacking the shell archive, running 'make' is all that is required
  62. to compile XFish.
  63.  
  64.  
  65. XFish Usage
  66. -----------
  67. usage: xfish [-b limit][-c color][-f limit][-i mult][-r rate][-s][host:display]
  68.  
  69. XFish is designed to run efficiently on defaults alone, but like any good X
  70. program, command line options are provided ...
  71.     * -b specifies the bubble limit (default = 32)
  72.     * -c specifies the background color (default = MediumAquamarine)
  73.     * -f specifies the fish limit (default = 2, for historical reasons)
  74.         * -i specifies the increment multipler (default = 1.0)
  75.     * -r specifies the update rate (default = 1.0 seconds)
  76.     * -s activates secure mode, raising the window for use with xsecure
  77.     * host:display is the standard X server specifier
  78.  
  79. as well as ~/.Xdefault options for all of the above ...
  80.     * xfish.BubbleLimit:        32
  81.     * xfish.Color:            MediumAquamarine
  82.     * xfish.FishLimit:        2
  83.         * xfish.IncMult:                1.0
  84.     * xfish.Rate:            1.0
  85.     * xfish.Secure:            No
  86.  
  87. A few notes on XFish performance ...
  88.  
  89.     * Bubbles are something of a CPU drain.  Overall performance can
  90.       be improved by using low bubble limits.  If the bubbles appear
  91.       to be flashing, try fewer bubbles, or turn off bubbles using -b0.
  92.  
  93.     * Off-screen display memory is used for fish if available.  This
  94.       results in astonishing performance gains.  For this reason,
  95.       fish are not much of a CPU drain, and higher fish limits can
  96.       easily be used.
  97.  
  98.     * Changing the update rate is the most effective way to control
  99.       impact on system performance.  The default of 1 second results
  100.       in less than a 10% CPU usage on a single user 350.  Higher values
  101.       may be desirable on more burdened system.
  102.  
  103.     * A zero update rate using -r0 creates some great looking displays.
  104.       Try 'xfish -r0 -f0' and 'xfish -r0 -b0 -f8' (the latter really
  105.       shows off the capabilities of the Topcat board, and is simply
  106.       astounding on the Catseye board).
  107.  
  108.     * Decreasing the increment multiplier, using -i 0.1 for example, is
  109.       especially  useful in conjunction with a zero update rate.  If you
  110.       prefer '911 Turbo' fish, use a multiplier of greater than one.
  111.  
  112.     * The aquarium window obscures most of the root window.  A one pixel
  113.       border is provided around the window to allow quick access to the
  114.       root window.  An alternative, which proves very useful with the
  115.           secure option, is to iconize the aquarium (until ready to xsecBure).
  116.  
  117.     * Sending SIGUSR1 (16) to the XFish process (using 'kill -16 <pid>')
  118.       will toggle the raise-lower mode.  Using this technique, xsecure
  119.       can be started without the need to restart XFish.
  120.  
  121.  
  122. XFish Enhancements
  123. ------------------
  124. XFish was intended to be run as a background window, and as such it was
  125. designed to minimize CPU impact.  Although enhancement requests will be
  126. cheerfully accepted, it is unlikely that features will be added to the
  127. detriment of overall performance.  On the other hand, any recommendations
  128. which could benefit overall performance will be utilized.
  129. @//E*O*F FIRST.README//
  130. chmod u=r,g=r,o=r FIRST.README
  131.  
  132. echo x - Imakefile
  133. sed 's/^@//' > "Imakefile" <<'@//E*O*F Imakefile//'
  134.        INCLUDES = -I. -I$(TOP) -I$(TOP)/X11
  135. LOCAL_LIBRARIES = $(XLIB)
  136.   SYS_LIBRARIES = -lm
  137.  
  138.            SRCS = xfish.c xfishy.c
  139.            OBJS = xfish.o xfishy.o
  140.  
  141. ComplexProgramTarget(xfish)
  142.  
  143. # Make the export sharchive.
  144. shar: xaqua.shar
  145.  
  146. xaqua.shar: xaqua.shar1 xaqua.shar2
  147.  
  148. xaqua.shar1: FIRST.README Imakefile Makefile xfish.c
  149.     shar FIRST.README Imakefile Makefile xfish.c >xaqua.shar1
  150.  
  151. xfishy.c.Z: xfishy.c
  152.     compress -c xfishy.c >xfishy.c.Z
  153.  
  154. xfishy.c.Z.uu: xfishy.c.Z
  155.     uuencode xfishy.c.Z xfishy.c.Z >xfishy.c.Z.uu
  156.  
  157. xaqua.shar2: xfishy.c.Z.uu
  158.     shar xfishy.c.Z.uu >xaqua.shar2
  159.  
  160. # Unpack the compressed, uuencoded, shared bitmap.
  161. unshar:
  162.     uudecode xfishy.c.Z.uu
  163.     uncompress xfishy.c.Z
  164.  
  165. # Make the export tarchive.
  166. tar: xaqua.tar.Z
  167.  
  168. xaqua.tar.Z: xaqua.tar
  169.     rm -f xaqua.tar.Z
  170.     compress xaqua.tar
  171.  
  172. xaqua.tar: FIRST.README Imakefile Makefile xfish.c xfishy.c
  173.     tar chf xaqua.tar FIRST.README Imakefile Makefile xfish.c xfishy.c
  174. @//E*O*F Imakefile//
  175. chmod u=r,g=r,o=r Imakefile
  176.  
  177. echo x - Makefile
  178. sed 's/^@//' > "Makefile" <<'@//E*O*F Makefile//'
  179. # Makefile generated by imake - do not edit!
  180. # $XConsortium: imake.c,v 1.37 88/10/08 20:08:30 jim Exp $
  181.  
  182. ###########################################################################
  183. # X Window System Makefile generated from template file Imake.tmpl
  184. # $XConsortium: Imake.tmpl,v 1.91 88/10/23 22:37:10 jim Exp $
  185. #
  186. # Do not change the body of the imake template file.  Server-specific
  187. # parameters may be set in the appropriate .macros file; site-specific
  188. # parameters (but shared by all servers) may be set in site.def.  If you
  189. # make any changes, you'll need to rebuild the makefiles using
  190. # "make World" (at best) or "make Makefile; make Makefiles" (at least) in
  191. # the top level directory.
  192. #
  193. # If your C preprocessor doesn't define any unique symbols, you'll need
  194. # to set BOOTSTRAPCFLAGS when rebuilding imake (usually when doing
  195. # "make Makefile", "make Makefiles", or "make World").
  196. #
  197. # If you absolutely can't get imake to work, you'll need to set the
  198. # variables at the top of each Makefile as well as the dependencies at the
  199. # bottom (makedepend will do this automatically).
  200. #
  201.  
  202. ###########################################################################
  203. # platform-specific configuration parameters - edit Rt.macros to change
  204.  
  205. # platform:  $XConsortium: Rt.macros,v 1.47 88/10/25 18:39:43 keith Exp $
  206.  
  207. # platform:  $XConsortium: IBM.macros,v 1.22 88/10/25 18:39:31 keith Exp $
  208.  
  209.              AS = as
  210.             CPP = /lib/cpp
  211.              LD = ld
  212.            LINT = lint
  213.            MAKE = make
  214.         INSTALL = install
  215.            TAGS = ctags
  216.              RM = rm -f
  217.              MV = mv
  218.              LS = ls
  219.              CP = cp
  220. STD_CPP_DEFINES =
  221.     STD_DEFINES =
  222.  
  223. BOOTSTRAPCFLAGS =
  224.              CC = hc
  225.  LDCOMBINEFLAGS = -X -r
  226.              LN = ln -s
  227.          RANLIB = ranlib
  228. RANLIBINSTFLAGS = -t
  229.              AR = ar cq
  230.        LINTOPTS = -axz
  231.     LINTLIBFLAG = -C
  232.  
  233.             PCC = pcc
  234.  
  235. ###########################################################################
  236. # site-specific configuration parameters - edit site.def to change
  237.  
  238. # site:  $XConsortium: site.def,v 1.16 88/10/12 10:30:24 jim Exp $
  239.  
  240. ###########################################################################
  241. # definitions common to all Makefiles - do not edit
  242.  
  243.           SHELL =     /bin/sh
  244.  
  245.         DESTDIR =
  246.       USRLIBDIR = $(DESTDIR)/usr/lib
  247.          BINDIR = $(DESTDIR)/usr/bin/X11
  248.          INCDIR = $(DESTDIR)/usr/include/X11
  249.          ADMDIR = $(DESTDIR)/usr/adm
  250.          LIBDIR = $(USRLIBDIR)/X11
  251.      LINTLIBDIR = $(USRLIBDIR)/lint
  252.         FONTDIR = $(LIBDIR)/fonts
  253.        XINITDIR = $(LIBDIR)/xinit
  254.          XDMDIR = $(LIBDIR)/xdm
  255.          UWMDIR = $(LIBDIR)/uwm
  256.          AWMDIR = $(LIBDIR)/awm
  257.          TWMDIR = $(LIBDIR)/twm
  258.         MANPATH = $(DESTDIR)/usr/man
  259.   MANSOURCEPATH = $(MANPATH)/man
  260.          MANDIR = $(MANSOURCEPATH)n
  261.       LIBMANDIR = $(MANSOURCEPATH)3
  262.     XAPPLOADDIR = $(LIBDIR)/app-defaults
  263.  
  264.    INSTBINFLAGS = -m 0755
  265.    INSTUIDFLAGS = -m 4755
  266.    INSTLIBFLAGS = -m 0664
  267.    INSTINCFLAGS = -m 0444
  268.    INSTMANFLAGS = -m 0444
  269.    INSTAPPFLAGS = -m 0444
  270.   INSTKMEMFLAGS = -m 4755
  271.         FCFLAGS = -t
  272.     CDEBUGFLAGS = -O
  273.  
  274.         PATHSEP = /
  275.          DEPEND = $(DEPENDSRC)/makedepend
  276.           IMAKE = $(IMAKESRC)/imake
  277.             RGB = $(RGBSRC)/rgb
  278.              FC = $(BDFTOSNFSRC)/bdftosnf
  279.       MKFONTDIR = $(MKFONTDIRSRC)/mkfontdir
  280.       MKDIRHIER = $(SCRIPTSSRC)/mkdirhier.sh
  281.  
  282.          CFLAGS = $(CDEBUGFLAGS) $(INCLUDES) $(STD_DEFINES) $(DEFINES)
  283.       LINTFLAGS = $(LINTOPTS) $(INCLUDES) $(STD_DEFINES) $(DEFINES) -DLINT
  284.         LDFLAGS = $(CDEBUGFLAGS) $(SYS_LIBRARIES) $(SYSAUX_LIBRARIES)
  285.             TOP = ./../../..
  286.       CLIENTSRC = $(TOP)/clients
  287.         DEMOSRC = $(TOP)/demos
  288.          LIBSRC = $(TOP)/lib
  289.         FONTSRC = $(TOP)/fonts
  290.      INCLUDESRC = $(TOP)/X11
  291.       SERVERSRC = $(TOP)/server
  292.         UTILSRC = $(TOP)/util
  293.      SCRIPTSSRC = $(UTILSRC)/scripts
  294.      EXAMPLESRC = $(TOP)/examples
  295.      CONTRIBSRC = $(TOP)/contrib
  296.          DOCSRC = $(TOP)/doc
  297.          RGBSRC = $(TOP)/rgb
  298.       DEPENDSRC = $(UTILSRC)/makedepend
  299.        IMAKESRC = $(UTILSRC)/imake
  300.        IRULESRC = $(UTILSRC)/imake.includes
  301.         XLIBSRC = $(LIBSRC)/X
  302.          XMUSRC = $(LIBSRC)/Xmu
  303.      TOOLKITSRC = $(LIBSRC)/Xt
  304.      AWIDGETSRC = $(LIBSRC)/Xaw
  305.      OLDXLIBSRC = $(LIBSRC)/oldX
  306.     BDFTOSNFSRC = $(FONTSRC)/bdftosnf
  307.    MKFONTDIRSRC = $(FONTSRC)/mkfontdir
  308.    EXTENSIONSRC = $(TOP)/extensions
  309.    EXTENSIONLIB = $(EXTENSIONSRC)/lib/libXext.a
  310.            XLIB = $(XLIBSRC)/libX11.a
  311.          XMULIB = $(XMUSRC)/libXmu.a
  312.         OLDXLIB = $(OLDXLIBSRC)/liboldX.a
  313.        XTOOLLIB = $(TOOLKITSRC)/libXt.a
  314.          XAWLIB = $(AWIDGETSRC)/libXaw.a
  315.        LINTXLIB = $(XLIBSRC)/llib-lX11.ln
  316.         LINTXMU = $(XMUSRC)/llib-lXmu.ln
  317.       LINTXTOOL = $(TOOLKITSRC)/llib-lXt.ln
  318.         LINTXAW = $(AWIDGETSRC)/llib-lXaw.ln
  319.        INCLUDES = -I$(TOP)
  320.       MACROFILE = Rt.macros
  321.    ICONFIGFILES = $(IRULESRC)/Imake.tmpl \
  322.             $(IRULESRC)/$(MACROFILE) $(IRULESRC)/site.def
  323.   IMAKE_DEFINES =
  324.       IMAKE_CMD = $(NEWTOP)$(IMAKE) -TImake.tmpl -I$(NEWTOP)$(IRULESRC) \
  325.             -s Makefile $(IMAKE_DEFINES)
  326.          RM_CMD = $(RM) *.CKP *.ln *.BAK *.bak *.o core errs ,* *~ *.a \
  327.             .emacs_* tags TAGS make.log MakeOut
  328.  
  329. ###########################################################################
  330. # rules:  $XConsortium: Imake.rules,v 1.71 88/10/23 22:46:34 jim Exp $
  331.  
  332. ###########################################################################
  333. # start of Imakefile
  334.  
  335.        INCLUDES = -I. -I$(TOP) -I$(TOP)/X11
  336. LOCAL_LIBRARIES = $(XLIB)
  337.   SYS_LIBRARIES = -lm
  338.  
  339.            SRCS = xfish.c xfishy.c
  340.            OBJS = xfish.o xfishy.o
  341.  
  342.         PROGRAM = xfish
  343.  
  344. all:: xfish
  345.  
  346. xfish: $(OBJS) $(LOCAL_LIBRARIES)
  347.     $(RM) $@
  348.     $(CC) -o $@ $(OBJS) $(LOCAL_LIBRARIES) $(LDFLAGS) $(SYSLAST_LIBRARIES)
  349.  
  350. relink::
  351.     $(RM) $(PROGRAM)
  352.     $(MAKE) $(MFLAGS) $(PROGRAM)
  353.  
  354. install:: xfish
  355.     $(INSTALL) -c $(INSTALLFLAGS) xfish $(BINDIR)
  356.  
  357. install.man:: xfish.man
  358.     $(INSTALL) -c $(INSTMANFLAGS) xfish.man $(MANDIR)/xfish.n
  359.  
  360. depend:: $(DEPEND)
  361.  
  362. depend::
  363.     $(DEPEND) -s "# DO NOT DELETE" -- $(CFLAGS) -- $(SRCS)
  364.  
  365. $(DEPEND):
  366.     @echo "making $@"; \
  367.     cd $(DEPENDSRC); $(MAKE)
  368.  
  369. clean::
  370.     $(RM) $(PROGRAM)
  371.  
  372. # Make the export sharchive.
  373. shar: xaqua.shar
  374.  
  375. xaqua.shar: xaqua.shar1 xaqua.shar2
  376.  
  377. xaqua.shar1: FIRST.README Imakefile Makefile xfish.c
  378.     shar FIRST.README Imakefile Makefile xfish.c >xaqua.shar1
  379.  
  380. xfishy.c.Z: xfishy.c
  381.     compress -c xfishy.c >xfishy.c.Z
  382.  
  383. xfishy.c.Z.uu: xfishy.c.Z
  384.     uuencode xfishy.c.Z xfishy.c.Z >xfishy.c.Z.uu
  385.  
  386. xaqua.shar2: xfishy.c.Z.uu
  387.     shar xfishy.c.Z.uu >xaqua.shar2
  388.  
  389. # Unpack the compressed, uuencoded, shared bitmap.
  390. unshar:
  391.     uudecode xfishy.c.Z.uu
  392.     uncompress xfishy.c.Z
  393.  
  394. # Make the export tarchive.
  395. tar: xaqua.tar.Z
  396.  
  397. xaqua.tar.Z: xaqua.tar
  398.     rm -f xaqua.tar.Z
  399.     compress xaqua.tar
  400.  
  401. xaqua.tar: FIRST.README Imakefile Makefile xfish.c xfishy.c
  402.     tar chf xaqua.tar FIRST.README Imakefile Makefile xfish.c xfishy.c
  403.  
  404. ###########################################################################
  405. # Imake.tmpl common rules for all Makefiles - do not edit
  406.  
  407. emptyrule::
  408.  
  409. clean::
  410.     $(RM_CMD) \#*
  411.  
  412. Makefile:: $(IMAKE)
  413.  
  414. Makefile:: Imakefile \
  415.     $(IRULESRC)/Imake.tmpl \
  416.     $(IRULESRC)/Imake.rules \
  417.     $(IRULESRC)/site.def \
  418.     $(IRULESRC)/$(MACROFILE)
  419.     -@if [ -f Makefile ]; then \
  420.         echo "$(RM) Makefile.bak; $(MV) Makefile Makefile.bak"; \
  421.         $(RM) Makefile.bak; $(MV) Makefile Makefile.bak; \
  422.     else exit 0; fi
  423.     $(IMAKE_CMD) -DTOPDIR=$(TOP)
  424.  
  425. $(IMAKE):
  426.     @echo "making $@"; \
  427.     cd $(IMAKESRC); $(MAKE) BOOTSTRAPCFLAGS=$(BOOTSTRAPCFLAGS)
  428.  
  429. tags::
  430.     $(TAGS) -w *.[ch]
  431.     $(TAGS) -xw *.[ch] > TAGS
  432.  
  433. ###########################################################################
  434. # empty rules for directories that do not have SUBDIRS - do not edit
  435.  
  436. install::
  437.     @echo "install done"
  438.  
  439. install.man::
  440.     @echo "install.man done"
  441.  
  442. Makefiles::
  443.  
  444. ###########################################################################
  445. # dependencies generated by makedepend
  446.  
  447. # DO NOT DELETE
  448.  
  449. xfish.o: /usr/include/sys/time.h /usr/include/sys/time.h /usr/include/stdio.h
  450. xfish.o: /usr/include/signal.h ./../../../X11/Xlib.h /usr/include/sys/types.h
  451. xfish.o: ./../../../X11/X.h ./../../../X11/Xutil.h
  452. xfishy.o: ./../../../X11/Xlib.h /usr/include/sys/types.h ./../../../X11/X.h
  453. @//E*O*F Makefile//
  454. chmod u=rw,g=rw,o=rw Makefile
  455.  
  456. echo x - xfish.c
  457. sed 's/^@//' > "xfish.c" <<'@//E*O*F xfish.c//'
  458. static char ident[] = "@(#)$Header: XFish release 3, revision 1, 11 Aug 1989 $";
  459.  
  460. /*
  461.  
  462.   *    Original Author Unknow.
  463.  
  464.   *    8/10/88 - Ported from X10 to X11R3 by:
  465.  
  466.         Jonathan Greenblatt (jonnyg@rover.umd.edu)
  467.  
  468.   *    Cleaned up by Dave Lemke (lemke@sun.com)
  469.  
  470.   *    Ported to monocrome by Jonathan Greenblatt (jonnyg@rover.umd.edu)
  471.  
  472.   TODO:
  473.  
  474.     Parameter parsing needs to be redone.
  475.  
  476. */
  477.  
  478. #ifndef HPUX
  479. #include <sys/time.h>
  480. #else
  481. #include <time.h>
  482. #endif
  483.  
  484. #include <stdio.h>
  485. #include <signal.h>
  486. #include <X11/Xlib.h>
  487. #include <X11/Xutil.h>
  488.  
  489. /* constants are based on rand(3C) returning an integer between 0 and 32767 */
  490.  
  491. #ifndef HPUX
  492. #define  RAND_I_1_16   134217728
  493. #define  RAND_F_1_8    268435455.875
  494. #define  RAND_I_1_4    536870911
  495. #define  RAND_I_1_2   1073741823
  496. #define  RAND_I_3_4   1610612735
  497. #define  RAND_F_MAX   2147483647.0
  498. #else
  499. #define  RAND_I_1_16   2048
  500. #define  RAND_F_1_8    4096.0
  501. #define  RAND_I_1_4    8096
  502. #define  RAND_I_1_2   16384
  503. #define  RAND_I_3_4   24575
  504. #define  RAND_F_MAX   32767.0
  505. #endif
  506.  
  507. /* externals for pixmap and bimaps from xfishy.c */
  508. extern int  rwidth,
  509.             rheight,
  510.             rcolors,
  511.             rback,
  512.             rreds[],
  513.             rgreens[],
  514.             rblues[];
  515. extern short xfishRaster[];
  516. extern unsigned char xbBits[9][8];
  517. extern char fish_bits[], fishl_bits[];
  518. int mono;
  519.  
  520.  
  521. /* typedefs for bubble and fish structures, also caddr_t (not used in X.h) */
  522. typedef struct {
  523.     int         x,
  524.                 y,
  525.                 s,
  526.                 i;
  527. }           bubble;
  528. typedef struct {
  529.     int         x,
  530.                 y,
  531.                 d,
  532.                 i;
  533. }           fish;
  534. typedef unsigned char *caddrt;
  535.  
  536.  
  537. /* bubble increment and yes check tables */
  538. int         binc[] = {0, 64, 56, 48, 40, 32, 24, 16, 8};
  539. char       *yess[] = {"yes", "Yes", "YES", "on", "On", "ON"};
  540.  
  541.  
  542. char       *pname,        /* program name from argv[0] */
  543.             sname[64],        /* host:display specification */
  544.             cname[64];        /* colorname specification */
  545. int         blimit = 32,    /* bubble limit */
  546.             flimit = 2,        /* fish limit */
  547.             pmode = 1,        /* pop mode, (1 for lower, 0 for raise) */
  548.             width,        /* width of initial window in pixels */
  549.             height,        /* height of initial window in pixels */
  550.             screen;        /* Default screen of this display */
  551. Init_B,
  552. *cmap;                /* Initialize bubbles with random y value */
  553. double      rate = 1.0,        /* update interval in seconds */
  554.             smooth = 1.0;    /* smoothness increment multiplier */
  555. bubble     *binfo;        /* bubble info structures, allocated 
  556.                  * dynamically  */
  557. fish       *finfo;        /* fish info structures, allocated dynamically */
  558. Display    *Dpy;
  559. XImage     *xfish[3];        /* fish pixmaps (1 is left-fish, 2 is
  560.                  * right-fish) */
  561. Pixmap      pfish[3] = {0, 0, 0};
  562. Pixmap      xbubbles[9];    /* bubbles bitmaps (1 to 8, by size in pixels)*/
  563. Window      wid;        /* aqaurium window */
  564. unsigned long white, black,bcolor;
  565. Colormap    colormap;
  566. GC          gc,
  567.             bgc;
  568.  
  569.  
  570. /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  571. Output desired error message and exit.
  572. * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
  573. void 
  574. msgdie(message)
  575.     char       *message;
  576. {
  577.     fprintf(stderr, "%s: %s\n", pname, message);
  578.     exit(1);
  579. }
  580.  
  581.  
  582. /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  583. Set up program defaults, get X defaults, parse command line using getopts.
  584. * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
  585. void 
  586. parse(argc, argv)
  587.     int         argc;
  588.     char      **argv;
  589. {
  590.     int         c,
  591.                 i;
  592.     char       *p;
  593.     extern int  optind;
  594.     extern char *optarg;
  595.     extern double atof();
  596.  
  597.     pname = argv[0];
  598.     strcpy(sname, getenv("DISPLAY"));
  599.     strcpy(cname, "MediumAquamarine");
  600.  
  601.     if ((p = XGetDefault(Dpy, pname, "BubbleLimit")) != NULL)
  602.     blimit = atoi(p);
  603.     if ((p = XGetDefault(Dpy, pname, "Color")) != NULL)
  604.     strcpy(cname, p);
  605.     if ((p = XGetDefault(Dpy, pname, "FishLimit")) != NULL)
  606.     flimit = atoi(p);
  607.     if ((p = XGetDefault(Dpy, pname, "IncMult")) != NULL)
  608.     smooth = atof(p);
  609.     if ((p = XGetDefault(Dpy, pname, "Rate")) != NULL)
  610.     rate = atof(p);
  611.     if ((p = XGetDefault(Dpy, pname, "Secure")) != NULL)
  612.     for (i = 0; i < 6; i++)
  613.         if (strcmp(p, yess[i]) == 0)
  614.         pmode = 0;
  615.  
  616.     while ((c = getopt(argc, argv, "b:c:f:i:r:s")) != EOF) {
  617.     switch (c) {
  618.     case 'b':
  619.         blimit = atoi(optarg);
  620.         break;
  621.     case 'c':
  622.         strcpy(cname, optarg);
  623.         break;
  624.     case 'f':
  625.         flimit = atoi(optarg);
  626.         break;
  627.     case 'i':
  628.         smooth = atof(optarg);
  629.         break;
  630.     case 'r':
  631.         rate = atof(optarg);
  632.         break;
  633.     case 's':
  634.         pmode = 0;
  635.         break;
  636.     case '?':
  637.         fprintf(stderr, "usage: %s [-b limit][-c color][-f limit][-i mult][-r rate][-s][host:display]\n", pname);
  638.         exit(1);
  639.     }
  640.     }
  641.  
  642.     if (optind < argc)
  643.     strcpy(sname, argv[optind]);
  644. }
  645.  
  646. putfish(f)
  647.     fish       *f;
  648. {
  649.     if (pfish[f->d])
  650.     XCopyArea(Dpy, pfish[f->d], wid, gc, 0, 0, rwidth, rheight, f->x, f->y);
  651.     else
  652.     XPutImage(Dpy, wid, gc, xfish[f->d], 0, 0, f->x, f->y, rwidth, rheight);
  653. }
  654.  
  655. putbubble(b, s, c)
  656.     bubble     *b;
  657.     int         s;
  658.     unsigned long c;
  659. {
  660.     XGCValues   gcv;
  661.  
  662.     gcv.foreground = c;
  663.     gcv.clip_mask = xbubbles[s];
  664.     gcv.clip_x_origin = b->x;
  665.     gcv.clip_y_origin = b->y;
  666.     XChangeGC(Dpy, bgc, GCForeground | GCClipMask | GCClipXOrigin |
  667.           GCClipYOrigin, &gcv);
  668.     XFillRectangle(Dpy, wid, bgc, b->x, b->y, s, s);
  669. }
  670.  
  671. /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  672. Initialize colormap for background color and required fish colors.
  673. The fish colors are coded in xfishy.c as a trio of tables.
  674. * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
  675. void 
  676. init_colormap()
  677. {
  678.     int         i;
  679.     XColor      hdef,
  680.                 edef;
  681.     extern char *malloc();
  682.  
  683.     colormap = XDefaultColormap(Dpy, screen);
  684.  
  685.     if (colormap == NULL)
  686.     return;
  687.     cmap = (int *) malloc((rcolors + 1) * sizeof(int));
  688.     if (!mono) {
  689.     XAllocNamedColor(Dpy, colormap, cname, &hdef, &edef);
  690.     cmap[0] = hdef.pixel;
  691.  
  692.     for (i = 0; i < rcolors; i++) {
  693.         hdef.red = rreds[i];
  694.         hdef.green = rgreens[i];
  695.         hdef.blue = rblues[i];
  696.         XAllocColor(Dpy, colormap, &hdef);
  697.         cmap[i + 1] = hdef.pixel;
  698.         }
  699.     bcolor = white;
  700.     }
  701.     else {
  702.     for (i = 0; i < (rcolors+1); i++)
  703.         cmap[i] = black;
  704.     cmap[0] = cmap[rback] = white;
  705.     bcolor = black;
  706.     }
  707.     cmap[rback] = cmap[0];
  708.     }
  709.  
  710.  
  711.  
  712. /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  713. Calibrate the pixmaps and bimaps.  The left-fish data is coded in xfishy.c,
  714. this is transformed to create the right-fish.  The eight bubbles are coded
  715. in xfishy.c as a two dimensional array.
  716. * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
  717. void 
  718. init_pixmap()
  719. {
  720.     register caddrt p,
  721.                 q,
  722.                 x1,
  723.                 x2;
  724.     register int i,
  725.                 j;
  726.     extern char *malloc();
  727.  
  728.  
  729.     j = rwidth * rheight;
  730.     x1 = p = (caddrt) xfishRaster;
  731.     for (i = 0; i < j; i++, p++)
  732.     *p = cmap[*p];
  733.  
  734.     x2 = (caddrt) malloc(rwidth * rheight);
  735.  
  736.     for (i = 0; i < rheight; i++) {
  737.     p = x1 + i * rwidth;
  738.     q = x2 + (i + 1) * rwidth - 1;
  739.     for (j = 0; j < rwidth; j++)
  740.         *q-- = *p++;
  741.     }
  742.  
  743.     xfish[1] = XCreateImage(Dpy, DefaultVisual(Dpy, screen), 8, ZPixmap,
  744.     0, x1, rwidth, rheight, 8, rwidth);
  745.     xfish[2] = XCreateImage(Dpy, DefaultVisual(Dpy, screen), 8, ZPixmap, 
  746.     0, x2, rwidth, rheight, 8, rwidth);
  747.  
  748.     if (!mono) { /* Color Dislay */
  749.     i = DisplayPlanes(Dpy, screen);
  750.  
  751.     pfish[1] = XCreatePixmap(Dpy, wid, rwidth, rheight, i);
  752.     if (pfish[1])
  753.         pfish[2] = XCreatePixmap(Dpy, wid, rwidth, rheight, i);
  754.     if (pfish[1])
  755.        XPutImage(Dpy, pfish[1], gc, xfish[1], 0, 0, 0, 0, rwidth, rheight);
  756.     if (pfish[2])
  757.        XPutImage(Dpy, pfish[2], gc, xfish[2], 0, 0, 0, 0, rwidth, rheight);
  758.     if (pfish[1])
  759.         XDestroyImage(xfish[1]);
  760.     if (pfish[2])
  761.         XDestroyImage(xfish[2]);
  762.     xfish[1] = XCreateImage(Dpy, DefaultVisual(Dpy, screen), 8, ZPixmap,
  763.         0, x1, rwidth, rheight, 8, rwidth);
  764.     xfish[2] = XCreateImage(Dpy, DefaultVisual(Dpy, screen), 8, ZPixmap, 
  765.         0, x2, rwidth, rheight, 8, rwidth);
  766.     }
  767.     else { /* Mono Display */
  768.     pfish[1] = XCreateBitmapFromData(Dpy,wid,fish_bits,rwidth,rheight);
  769.     pfish[2] = XCreateBitmapFromData(Dpy,wid,fishl_bits,rwidth,rheight);
  770.     }
  771.  
  772.     for (i = 1; i <= 8; i++)
  773.     xbubbles[i] = XCreateBitmapFromData(Dpy, wid, xbBits[i], i, i);
  774. }
  775.  
  776.  
  777. /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  778. Toggle secure mode on receipt of signal
  779. * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
  780. toggle_secure()
  781. {
  782.     pmode = !pmode;
  783.     if (pmode)
  784.     XLowerWindow(Dpy, wid);
  785.     else
  786.     XRaiseWindow(Dpy, wid);
  787.     XFlush(Dpy);
  788. }
  789.  
  790.  
  791. /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  792. Initialize signal so that SIGUSR1 causes secure mode to toggle.
  793. * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
  794. void 
  795. init_signals()
  796. {
  797.     struct sigvec vec;
  798.  
  799.     vec.sv_handler = toggle_secure;
  800.     vec.sv_mask = 0;
  801.     vec.sv_onstack = 0;
  802.  
  803. #ifndef HPUX
  804.     sigvec(SIGUSR1, &vec, &vec);
  805. #else
  806.     sigvector(SIGUSR1, &vec, &vec);
  807. #endif
  808. }
  809.  
  810.  
  811. /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  812. Variety of initialization calls, including getting the window up and running.
  813. * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
  814. void 
  815. initialize()
  816. {
  817.     XWindowAttributes winfo;
  818.     XSetWindowAttributes attr;
  819.     XGCValues   vals;
  820.     extern char *malloc();
  821.     XSizeHints  xsh;
  822.  
  823.     XGetWindowAttributes(Dpy, DefaultRootWindow(Dpy), &winfo);
  824.     width = winfo.width;
  825.     height = winfo.height;
  826.  
  827.     init_colormap();
  828.     attr.override_redirect = True;
  829.     attr.background_pixel = cmap[0];
  830.  
  831.     wid = XCreateWindow(Dpy, DefaultRootWindow(Dpy),
  832.     1, 1, width - 2, height - 2, 0,
  833.     CopyFromParent, CopyFromParent, CopyFromParent, 
  834.     CWBackPixel | CWOverrideRedirect, &attr);
  835.  
  836.     if (!wid)
  837.     msgdie("XCreateWindow failed");
  838.  
  839.     vals.foreground = vals.background = cmap[0];
  840.     vals.graphics_exposures = False;
  841.     gc = XCreateGC(Dpy, wid, GCForeground | GCBackground | GCGraphicsExposures,
  842.     &vals);
  843.     bgc = XCreateGC(Dpy, wid, GCForeground | GCBackground | GCGraphicsExposures,
  844.     &vals);
  845.  
  846.     init_pixmap();
  847.     init_signals();
  848.  
  849.     XStoreName(Dpy, wid, pname);
  850.  
  851.     xsh.flags = USSize | USPosition | PPosition | PSize;
  852.     xsh.x = xsh.y = 0;
  853.     xsh.width = width;
  854.     xsh.height = height;
  855.     XSetNormalHints(Dpy, wid, &xsh);
  856.  
  857.     XMapWindow(Dpy, wid);
  858.  
  859.     binfo = (bubble *) malloc(blimit * sizeof(bubble));
  860.     finfo = (fish *) malloc(flimit * sizeof(fish));
  861. }
  862.  
  863.  
  864. /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  865. Create a new bubble.  Placement along the x axis is random, as is the size of
  866. the bubble.  Increment value is determined by speed.
  867. * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
  868. void 
  869. new_bubble(b0)
  870.     bubble     *b0;
  871. {
  872.     register int s;
  873.     register bubble *b = b0;
  874.  
  875.     b->x = width * (rand() / RAND_F_MAX);
  876.     if (Init_B)
  877.     b->y = (height / 16) * (rand() / RAND_I_1_16 + 1) - 1;
  878.     else
  879.     b->y = height - 1;
  880.     b->s = s = 1.0 + rand() / RAND_F_1_8;
  881.     if ((b->i = smooth * height / (float) binc[s]) == 0)
  882.     b->i = 1;
  883.     putbubble(b, s, bcolor);
  884. }
  885.  
  886. /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  887. Erase old bubbles, move and draw new bubbles.  Random left-right factor
  888. can move bubble one size-unit in either direction.
  889. * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
  890. void 
  891. step_bubbles()
  892. {
  893.     register int i,
  894.                 j,
  895.                 s;
  896.     register bubble *b;
  897.  
  898.     for (i = 0; i < blimit; i++) {
  899.     b = &binfo[i];
  900.     s = b->s;
  901.     /* clear */
  902.     if (b->y > 0)
  903.         putbubble(b, s, cmap[0]);
  904.     if ((b->y -= b->i) > 0) {
  905.         j = rand();
  906.         if (j < RAND_I_1_4)
  907.         b->x -= s;
  908.         else if (j > RAND_I_3_4)
  909.         b->x += s;
  910.         putbubble(b, s, bcolor);
  911.     } else {
  912.         if (rand() < RAND_I_1_4)
  913.         new_bubble(b);
  914.     }
  915.     }
  916. }
  917.  
  918. /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  919. Fish collision detection.  The specified fish is checked against all other
  920. fish for overlap.  The xt parameter specifies the x axis tolerance for overlap.
  921. * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
  922. int 
  923. collide_fish(f0, xt)
  924.     fish       *f0;
  925.     int         xt;
  926. {
  927.     int         i,
  928.                 j;
  929.     register fish *f = f0;
  930.  
  931.     for (i = 0; i < flimit; i++) {
  932.     if (&finfo[i] != f) {
  933.         j = finfo[i].y - f->y;
  934.         if ((j > -rheight) && (j < rheight)) {
  935.         j = finfo[i].x - f->x;
  936.         if ((j > -xt) && (j < xt))
  937.             return (1);
  938.         }
  939.     }
  940.     }
  941.     return (0);
  942. }
  943.  
  944.  
  945. /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  946. Create a new fish.   Placement along the y axis is random, as is the side
  947. from which the fish appears.  Direction is determined from side.  Increment
  948. is also random.
  949. * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
  950. void 
  951. new_fish(f0)
  952.     fish       *f0;
  953. {
  954.     int         i,
  955.                 collide;
  956.     fish       *f = f0;
  957.  
  958.     for (i = 0, collide = 1; (i < 16) && (collide); i++) {
  959.     f->y = (height - rheight) * (rand() / RAND_F_MAX);
  960.     if ((f->i = smooth * width / (8.0 * (1.0 + rand() / RAND_F_1_8))) == 0)
  961.         f->i = 1;
  962.     if (rand() < RAND_I_1_2) {
  963.         f->d = 1;
  964.         f->x = width;
  965.     } else {
  966.         f->d = 2;
  967.         f->x = -rwidth;
  968.     }
  969.  
  970.     collide = collide_fish(f, 2 * rwidth);
  971.     }
  972.  
  973.     if (!collide)
  974.     putfish(f);
  975.     else
  976.     f->d = 0;
  977. }
  978.  
  979.  
  980. /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  981. Move all the fish.  Clearing old fish is accomplished by masking only the
  982. exposed areas of the old fish.  Random up-down factor can move fish 1/4 a
  983. fish height in either direction, if no collisions are caused.
  984. * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
  985. void 
  986. move_fish()
  987. {
  988.     register int i,
  989.                 j,
  990.                 x,
  991.                 y,
  992.                 ofx,
  993.                 ofy,
  994.                 done;
  995.     register fish *f;
  996.  
  997.     for (i = 0; i < flimit; i++) {
  998.     f = &finfo[i];
  999.     if (f->d) {
  1000.         ofx = f->x;
  1001.         ofy = f->y;
  1002.  
  1003.         if (f->d == 1) {
  1004.         done = ((f->x -= f->i) < -rwidth);
  1005.         x = f->x + rwidth;
  1006.         } else if (f->d == 2) {
  1007.         done = ((f->x += f->i) > width);
  1008.         x = f->x - f->i;
  1009.         }
  1010.         if (!collide_fish(f, rwidth)) {
  1011.         if (!done) {
  1012.             j = rand();
  1013.             if (j < RAND_I_1_4)
  1014.             y = f->i / 4;
  1015.             else if (j > RAND_I_3_4)
  1016.             y = f->i / -4;
  1017.             else
  1018.             y = 0;
  1019.             if (y) {
  1020.             f->y += y;
  1021.             if (collide_fish(f, rwidth)) {
  1022.                 f->y -= y;
  1023.                 y = 0;
  1024.             } else {
  1025.                 if (y > 0) {
  1026.                 j = f->y - y;
  1027.                 } else {
  1028.                 j = f->y + rheight;
  1029.                 y *= -1;
  1030.                 }
  1031.             }
  1032.             }
  1033.             putfish(f);
  1034.             XClearArea(Dpy, wid, x, ofy, f->i, rheight, 0);
  1035.             if (y)
  1036.             XClearArea(Dpy, wid, ofx, j, rwidth, y, 0);
  1037.         } else {
  1038.             XClearArea(Dpy, wid, x, f->y, f->i, rheight, 0);
  1039.             new_fish(f);
  1040.         }
  1041.         } else {
  1042.         if ((f->d = 3 - f->d) == 1) {
  1043.             f->x = f->x - 2 * f->i;
  1044.             x = f->x + rwidth;
  1045.         } else {
  1046.             f->x = f->x + 2 * f->i;
  1047.             x = f->x - f->i;
  1048.         }
  1049.         putfish(f);
  1050.         XClearArea(Dpy, wid, x, f->y, f->i, rheight, 0);
  1051.         }
  1052.     } else {
  1053.         new_fish(f);
  1054.     }
  1055.     }
  1056. }
  1057.  
  1058.  
  1059. /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  1060. Higher-resolution sleep
  1061. * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
  1062. void 
  1063. high_res_sleep(seconds)
  1064.     double      seconds;
  1065. {
  1066.     int         fds = 0;
  1067.     struct timeval timeout;
  1068.  
  1069.     timeout.tv_sec = seconds;
  1070.     timeout.tv_usec = (seconds - timeout.tv_sec) * 1000000.0;
  1071.     select(0, &fds, &fds, &fds, &timeout);
  1072. }
  1073.  
  1074.  
  1075. /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  1076. * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
  1077. void 
  1078. main(argc, argv)
  1079.     int         argc;
  1080.     char      **argv;
  1081. {
  1082.     int         i;
  1083.     XEvent      ev;
  1084.  
  1085.     if ((Dpy = XOpenDisplay("")) == 0)
  1086.     msgdie("XOpenDisplay failed");
  1087.     screen = DefaultScreen(Dpy);
  1088.     if (DisplayPlanes(Dpy,screen) < 4) mono = 1;
  1089.     else mono = 0;
  1090.  
  1091.     white = WhitePixel(Dpy, screen);
  1092.     black = BlackPixel(Dpy, screen);
  1093.     parse(argc, argv);
  1094.     initialize();
  1095.  
  1096.     srand((unsigned) getpid());
  1097.  
  1098.     Init_B = 1;
  1099.     for (i = 0; i < blimit; i++)
  1100.     new_bubble(&binfo[i]);
  1101.     for (i = 0; i < flimit; i++)
  1102.     new_fish(&finfo[i]);
  1103.     if (pmode)
  1104.     XLowerWindow(Dpy, wid);
  1105.     else
  1106.     XRaiseWindow(Dpy, wid);
  1107.     XFlush(Dpy);
  1108.  
  1109.     Init_B = 0;
  1110.  
  1111.     for (;;) {
  1112.     if (XPending(Dpy))
  1113.         XNextEvent(Dpy, &ev);
  1114.  
  1115.     high_res_sleep(rate);
  1116.  
  1117.     move_fish();
  1118.  
  1119.     step_bubbles();
  1120.  
  1121.     if (pmode)
  1122.         XLowerWindow(Dpy, wid);
  1123.     else
  1124.         XRaiseWindow(Dpy, wid);
  1125.     }
  1126. }
  1127.  
  1128. @//E*O*F xfish.c//
  1129. chmod u=r,g=r,o=r xfish.c
  1130.  
  1131. exit 0
  1132.