Rog-O-Matic XIV (part 10 of 10)

Michael Mauldin mlm at cmu-cs-cad.ARPA
Sat Feb 2 02:34:08 AEST 1985


#!/bin/sh
#
# @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
# @ Here is part of your new automatic Rogue player, Rog-O-Matic XIV! @
# @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
# 
#     [Note: this is a Beta-Test release of version XIV, and almost
#      certainly contains bugs.  A new version will be made available
#      soon.  If you experience any problems with this version, please
#      contact Michael Mauldin as soon as possible, so your input can be
#      included in the new release]
# 
# Rog-O-Matic XIV is shipped via mail in pieces, files rgm14.01, rgm14.02,
# ..., rgm14.nn.  Each piece contains some number of smaller files. To
# retrieve them, run each file through the shell 'sh', as follows:
# 
# 	sh <rgm14.01
# 	sh <rgm14.02
# 	     ...
# 	sh <rgm14.nn
# 
# or do it all at once:
# 
# 	cat rgm14.* | sh
# 
# The README file contains all necessary information to edit the "install.h"
# file, after which "make" will build the rogomatic and player binary files.
# Please note that file 'Bugreport' contains modifications you may wish to
# make to the code BEFORE you compile it.  You can safely install ALL of
# them; depending on your version of Rogue, you may HAVE to install SOME of
# them.
# 
# Rog-O-Matic is copyrighted, but permission is given to copy and modify the
# source provided that (1) it is not used for profit (2) all authorship and
# copyright notices remain intact and (3) any person or site with a copy has
# notified Michael Mauldin either by electronic mail or US Post that they
# have Rog-O-Matic XIV.
# 
# We would appreciate hearing about any interesting additions or modifi-
# cations, and would especially like to know how well the program plays
# against your Rogue.  And we really, really want to know if Rog-O-Matic
# becomes a "Total Winner" against Rogue 5.2 or Rogue 5.3 again.
# 
# 				Michael Mauldin (Fuzzy)
# 				Department of Computer Science
# 				Carnegie-Mellon University
# 				Pittsburgh, PA  15213
# 				(412) 578-3065,  mauldin at cmu-cs-a.arpa
#
echo 'Start of Rog-O-Matic XIV, part 10 of 10:'
echo 'x - database.c'
sed 's/^X//' > database.c << '/'
X/*
X * database.c: Rog-O-Matic XIV (CMU) Fri Dec 28 23:26:25 1984 - mlm
X * Copyright (C) 1985 by A. Appel, G. Jacobson, L. Hamey, and M. Mauldin
X * 
X * This file contains the code which handles the database of objects which
X * have been used, and what the real names of the items are. There are
X * five functions:
X *
X *      useobj (oldname)             enter the object type into the database
X *      infername (oldname, name)    make the real name of obj be name
X *      used (oldname)               returns TRUE if we have entered obj
X *      know (name)                  returns TRUE if we have inferred name
X *      realname (oldname)           returns the inferred name of obj
X */
X
X# include <curses.h>
X# include "types.h"
X# include "globals.h"
X
X# define TABLESIZE 101
X# define NOTFOUND  (-1)
X
Xstruct  { char  fakename[64];
X          char  roguenam[64]; } dbase[TABLESIZE];
X
Xint datalen = 0;
X
X/* 
X * findentry: find the database entry for 'string'
X */
X
Xfindentry (string)
Xchar *string;
X{ register int i;
X
X  for (i = 0; i < datalen; i++)
X    if (streq (dbase[i].fakename, string) ||
X        *dbase[i].roguenam && streq (dbase[i].roguenam, string))
X      return (i);
X
X  return (NOTFOUND);
X}
X
X/* 
X * useobj: Indicate that we have used (i.e. read, quaffed, or zapped) an
X *         object with name 'oldname'.
X */
X
Xuseobj (oldname)
Xchar *oldname;
X{ if (findentry (oldname) == NOTFOUND)
X  { strcpy (dbase[datalen].fakename, oldname);
X    strcpy (dbase[datalen++].roguenam, "");
X  }
X}
X
X/* 
X * infername: Note that we now think that the object named 'oldname' is
X * really named 'name' (e.g. scroll 'google plex' is really a scroll of
X * light).
X */
X
Xinfername (oldname, name)
Xchar *oldname;
Xchar *name;
X{ register int i;
X
X  i = findentry (oldname);
X
X  if (i == NOTFOUND)
X  { strcpy (dbase[datalen].fakename, oldname);
X    strcpy (dbase[datalen++].roguenam, name);
X  }
X  else
X  { if (*dbase[i].roguenam && strcmp (dbase[i].roguenam, name))
X      dwait (D_ERROR, "Inconsistent inference '%s', '%s'", 
X             dbase[i].roguenam, name);
X    else
X      strcpy (dbase[i].roguenam, name);
X    }
X}
X
X/* 
X * used: Return true if we have marked 'oldname' as used.
X */
X
Xint used (oldname)
Xchar *oldname;
X{ register int i;
X
X  for (i = 0; i < datalen; i++)
X    if (streq (dbase[i].fakename, oldname))
X      return (TRUE);
X
X  return (FALSE);
X}
X
X/* 
X * know: Return true if we know what the fake name for 'name' is.
X */
X
Xint know (name)
Xchar *name;
X{ register int i;
X
X  for (i = 0; i < datalen; i++)
X    if (*dbase[i].roguenam && streq (dbase[i].roguenam, name))
X      return (TRUE);
X
X  return (FALSE);
X}
X
X/* 
X * realname: Returns the real name of an object nmed 'oldname'.
X */
X
Xchar *realname (oldname)
Xchar *oldname;
X{ register int i;
X
X  for (i = 0; i < datalen; i++)
X    if (*dbase[i].roguenam && streq (dbase[i].fakename, oldname))
X      return (dbase[i].roguenam);
X
X  return ("");
X}
X
X/* 
X * dumpdatabase: Debugging, dump the database one the screen.
X */
X
Xdumpdatabase ()
X{ register int i;
X
X  for (i = 0; i < datalen; i++)
X  { at (i+1, 0);
X    printw ("%-32s '%s'", dbase[i].roguenam, dbase[i].fakename);
X  }
X}
/
echo 'x - findscore.c'
sed 's/^X//' > findscore.c << '/'
X/*
X * findscore.c: Rog-O-Matic XIV (CMU) Fri Dec 28 23:27:10 1984 - mlm
X * Copyright (C) 1985 by A. Appel, G. Jacobson, L. Hamey, and M. Mauldin
X *
X * Read the Rogue scoreboard to determine a goal score.
X */
X
X# include <stdio.h>
X# include "install.h"
X# define TEMPFL "/tmp/RscoreXXXXXX"
X# define ISDIGIT(c) ((c) >= '0' && (c) <= '9')
X
Xfindscore (rogue, roguename)
Xregister char *rogue, *roguename;
X{ register int score, best = -1;
X  char cmd[100], buffer[BUFSIZ];
X  register char *s, *tmpfname = TEMPFL;
X  FILE *tmpfil;
X
X  /* Run 'rogue -s', and put the scores into a temp file */
X  sprintf (cmd, "%s -s >%s", rogue, mktemp (tmpfname)); 
X  system (cmd); 
X
X  /* If no temp file created, return default score */
X  if ((tmpfil = fopen (tmpfname, "r")) == NULL)
X    return (best); 
X
X  /* Skip to the line starting with 'Rank...'. */
X  while (fgets (buffer, BUFSIZ, tmpfil) != NULL)
X    if (stlmatch (buffer, "Rank")) break;
X
X  if (! feof (tmpfil)) 
X  { best = BOGUS;
X    while (fgets (buffer, BUFSIZ, tmpfil) != NULL)
X    { s = buffer;				/* point s at buffer */
X      while (ISDIGIT (*s)) s++;			/* Skip over rank */
X      while (*s == ' ' || *s == '\t') s++;	/* Skip to score */
X      score = atoi (s);				/* Read score */
X      while (ISDIGIT (*s)) s++;			/* Skip over score */
X      while (*s == ' ' || *s == '\t') s++;	/* Skip to player */
X
X      if (score < best)				/* Save smallest score */
X        best = score;
X      if (stlmatch (s, roguename))		/* Found our heros name */
X        break; 
X    }
X  }
X
X  unlink (tmpfname); 
X  return (best);
X}
/
echo 'x - gene.c'
sed 's/^X//' > gene.c << '/'
X/*
X * gene.c: Rog-O-Matic XIV (CMU) Mon Jan 28 20:51:32 1985 - mlm
X * Copyright (C) 1985 by A. Appel, G. Jacobson, L. Hamey, and M. Mauldin
X *
X * Initialize and summarize the gene pool
X */
X
X# include <stdio.h>
X# include "types.h"
X# include "install.h"
X
Xint knob[MAXKNOB];
Xchar genelock[100];
Xchar genelog[100];
Xchar genepool[100];
X
Xmain (argc, argv)
Xint   argc;
Xchar *argv[];
X{ int m=10, init=0, seed=0, version=RV53A, full=0;
X
X  /* Get the options */
X  while (--argc > 0 && (*++argv)[0] == '-')
X  { while (*++(*argv))
X    { switch (**argv)
X      { when 'i':	init++;
X	when 'f':	full++;
X	when 'm':	m = atoi(*argv+1); SKIPARG;
X			printf ("Gene pool size %d.\n", m);
X	when 's':	seed = atoi(*argv+1); SKIPARG;
X			printf ("Random seed %d.\n", m);
X	when 'v':	version = atoi(*argv+1); SKIPARG;
X			printf ("Rogue version %d.\n", version);
X	otherwise:	quit (1, "Usage: gene [-i] [-msv<value>]\n");
X      }
X    }
X  }
X
X  /* Assign the gene log and pool file names */
X  sprintf (genelock, "%s/GeneLock%d", RGMDIR, version);
X  sprintf (genelog, "%s/GeneLog%d", RGMDIR, version);
X  sprintf (genepool, "%s/GenePool%d", RGMDIR, version);
X
X  critical ();				/* Disable interrupts */
X  if (lock_file (genelock, MAXLOCK))
X  { if (init) 
X    { srand (seed);			/* Set the random number generator */
X      openlog (genelog);		/* Open the gene log file */
X      initpool (MAXKNOB, m);		/* Random starting point */
X      writegenes (genepool);		/* Write out the gene pool */
X      closelog ();			/* Close the log file */
X    }
X    else if (! readgenes (genepool))	/* Read the gene pool */
X      quit (1, "Cannot read file '%s'\n", genepool);
X
X   unlock_file (genelock);
X  }
X  else
X    quit (1, "Cannot access file '%s'\n", genepool);
X
X  uncritical ();			/* Re-enable interrupts */
X  analyzepool (full);			/* Print a summary */
X}
/
echo 'x - install.h'
sed 's/^X//' > install.h << '/'
X/*
X * install.h: Rog-O-Matic XIV (CMU) Wed Jan 30 17:39:50 1985 - mlm
X * Copyright (C) 1985 by A. Appel, G. Jacobson, L. Hamey, and M. Mauldin
X *
X * This file contains (hopefully) all system dependent defines 
X * This version of Rog-O-Matic runs with Rogue version 5.2. 
X */
X
X/*
X * BSD41: Defined for 4.1bsd Unix systems (Undefined means 4.2bsd)
X */
X
X# define BSD41
X
X/*
X * Rog-O-Matic's best score against Rogue 5.3  (UTexas, Feb 1984)
X * Printed when no score file is available in dumpscore()
X */
X
X# define BEST		(11316)
X
X/* 
X * Rog-O-Matic will not try to beat scores higher than BOGUS which
X * appear on the Rogue scoreboard.
X */
X
X# define BOGUS		(50000)
X
X/* 
X * This variable defines the version of Rogue we are assumed to be playing
X * if the getrogueversion() routine can't figure it out.  This must be
X * defined, and can be either "5.2", "3.6", or "5.3"
X */
X
X# define DEFVER		"5.3"
X
X/* 
X * This file is created whenever the Rog-O-Matic score file is accessed to
X * prevent simulatneous accesses. This variable must be defined, but will
X * not be used unless RGMDIR is also defined.
X */
X
X# define LOCKFILE	"/tmp/Rgm Lock"
X
X/* 
X * This variable is the level at which we always start logging the game
X */
X
X# define GOODGAME	(16)
X
X/* 
X * This variable is the number of seconds after which a LOCKFILE is
X * considered to be invalid.  This is necessary to avoid requiring manual
X * intervention when Rog-O-Matic dies while the score file is open.
X * This variable must be defined, but will not be used unless RGMDIR
X * is also defined.
X */
X
X# define MAXLOCK	(120 /* seconds */)
X
X/* 
X * This variable defines the "local" copy of Rogue, which may have only
X * intermittent access.  This is useful at CMU, since Rogue 5.2 is not
X * supported on all machines.  First Rog-O-Matic looks for "rogue" in the
X * current directory, then this file is used.  This variable need not be
X * defined.
X */
X
X# define NEWROGUE	"/usr/mlm/bin/rogue" 
X
X/* 
X * This is the location of the player executable, which is the main
X * process for Rog-O-Matic.  If "player" does not exist in the current
X * directory, then this file is used. This variable need not be defined 
X * (but in that case there must be a "player" binary in the current 
X * directory).
X */
X
X# define PLAYER		"/usr/mlm/bin/player"
X
X/* 
X * This is the version of the "current" Rog-O-Matic, and is an uppercase
X * Roman numeral.  It must be defined.
X */
X
X# define RGMVER		"XIV"
X
X/* 
X * This is the standard system version of Rogue, and is used if "rogue"
X * and NEWROGUE are not available. It need not be defined, but if it is
X * not, and NEWROGUE is not defined, then there must be a "rogue" in the
X * current directory.
X */
X
X# define ROGUE		"/usr/games/rogue"
X
X/* 
X * This file is created in the current directory if the logging option is
X * enabled.  If the game terminates normally, this file is renamed to
X * <killer>.<level>.<score>.  This variable must be defined.
X */
X
X# define ROGUELOG	"roguelog"
X
X/* 
X * This directory must be defined.  It will contain logs of Rogomatic's
X * scores, an error.log file, and the long term memory file.  It must
X * be writeable by everyone, since score files must be created and
X * destroyed by anyone running the program.  Alternatively, the
X * player process could be made setuid, with that uid owning this
X * directory.
X */
X
X# define RGMDIR		"/usr/mlm/src/rog/ver14/rlog"
X
X/* 
X * This file is created in the current directory if the snapshot command
X * is typed during a Rogue game.  It must be defined.
X */
X
X# define SNAPSHOT	"rgm.snapshot"
/
echo 'x - makefile'
sed 's/^X//' > makefile << '/'
X# makefile: Rog-O-Matic XIV (CMU) Thu Jan 31 18:23:25 1985 - mlm
X# Copyright (C) 1985 by A. Appel, G. Jacobson, L. Hamey, and M. Mauldin
X#
XBINARIES=   rogomatic player rgmplot datesub histplot gene
XBINDIR=     /usr/mlm/bin/test
XPUBDIR=     /usr/mlm/rgm/src14
XCCFLAGS=    -g
XLDFLAGS=    
XOBJS=	    arms.o command.o database.o debug.o explore.o io.o learn.o\
X	    ltm.o main.o mess.o monsters.o pack.o rand.o replay.o rooms.o\
X	    scorefile.o search.o stats.o strategy.o survival.o tactics.o\
X	    things.o titlepage.o utility.o worth.o 
XSRCS=	    arms.c command.c database.c debug.c explore.c io.c learn.c\
X	    ltm.c main.c mess.c monsters.c pack.c rand.c replay.c rooms.c\
X	    scorefile.c search.c stats.c strategy.c survival.c tactics.c\
X	    things.c titlepage.c utility.c worth.c 
XHDRS=	    types.h globals.h install.h termtokens.h
XOTHERS=     setup.c findscore.c datesub.l histplot.c rgmplot.c gene.c\
X	    rplot Bugreport
X#
X# The following commands are declared:
X#
Xall: $(BINARIES)
X	echo -n "" >/dev/tty
X#
X#
X# General makefile stuff:
X#
Xarms.o: types.h globals.h
X	cc -c $(CCFLAGS) arms.c
Xcommand.o: types.h globals.h
X	cc -c $(CCFLAGS) command.c
Xdatabase.o: types.h globals.h
X	cc -c $(CCFLAGS) database.c
Xdatesub.c: datesub.l
X	lex datesub.l
X	mv lex.yy.c datesub.c
Xdatesub.o: datesub.c
X	cc -c $(CCFLAGS) datesub.c
Xdatesub: datesub.o
X	cc $(LDFLAGS) -o datesub datesub.o
Xdebug.o: types.h globals.h install.h
X	cc -c $(CCFLAGS) debug.c
Xexplore.o: types.h globals.h
X	cc -c $(CCFLAGS) explore.c
Xfindscore.o: install.h
X	cc -c $(CCFLAGS) findscore.c
Xgene: gene.c rand.o learn.o stats.o utility.o types.h install.h
X	cc $(CCFLAGS) $(LDFLAGS) -o gene gene.c \
X		rand.o learn.o stats.o utility.o -lm
Xhistplot: histplot.o utility.o
X	cc $(LDFLAGS) -o histplot histplot.o utility.o
Xhistplot.o:
X	cc -c histplot.c
Xio.o: types.h globals.h termtokens.h
X	cc -c $(CCFLAGS) io.c
Xmess.o: types.h globals.h
X	cc -c $(CCFLAGS) mess.c
Xlearn.o: types.h  install.h
X	cc -c $(CCFLAGS) learn.c
Xltm.o: types.h globals.h
X	cc -c $(CCFLAGS) ltm.c
Xmain.o: install.h termtokens.h types.h globals.h
X	cc -c $(CCFLAGS) main.c
Xmonsters.o: types.h globals.h
X	cc -c $(CCFLAGS) monsters.c
Xpack.o: types.h globals.h
X	cc -c $(CCFLAGS) pack.c
Xplayer: $(OBJS)
X	cc $(LDFLAGS) -o player $(OBJS) -lm -lcurses -ltermcap
X	size player
Xrand.o: rand.c
X	cc -c $(CCFLAGS) rand.c
Xreplay.o: types.h globals.h
X	cc -c $(CCFLAGS) replay.c
Xrgmplot.o: rgmplot.c
X	cc -c $(CCFLAGS) rgmplot.c
Xrgmplot: rgmplot.o utility.o
X	cc $(LDFLAGS) -o rgmplot rgmplot.o utility.o
Xrogomatic: setup.o findscore.o scorefile.o utility.o
X	cc $(LDFLAGS) -o rogomatic setup.o findscore.o scorefile.o utility.o
X	size rogomatic
Xrooms.o: types.h globals.h
X	cc -c $(CCFLAGS) rooms.c
Xscorefile.o: types.h globals.h install.h
X	cc -c $(CCFLAGS) scorefile.c
Xsearch.o: types.h globals.h
X	cc -c $(CCFLAGS) search.c
Xsetup.o: install.h
X	cc -c $(CCFLAGS) setup.c
Xstats.o: types.h
X	cc -c $(CCFLAGS) stats.c
Xstrategy.o: types.h globals.h install.h
X	cc -c $(CCFLAGS) strategy.c
Xsurvival.o: types.h globals.h
X	cc -c $(CCFLAGS) survival.c
Xtactics.o: types.h globals.h
X	cc -c $(CCFLAGS) tactics.c
Xtestfind: testfind.o findscore.o utility.o
X	cc $(LDFLAGS) -o testfind testfind.o findscore.o utility.o
Xthings.o: types.h globals.h
X	cc -c $(CCFLAGS) things.c
Xtitlepage.o: titlepage.c
X	cc -c $(CCFLAGS) titlepage.c
Xtitler.o: titler.c
X	cc -c titler.c
Xutility.o:
X	cc -c $(CCFLAGS) utility.c
Xworth.o: types.h globals.h
X	cc -c $(CCFLAGS) worth.c
X#
X# Miscellaneous useful pseduo-makes
X#
Xbackup:
X	rm -f backup.tar
X	tar cvf backup.tar *.c *.h *.l rogomatic.6 makefile
X	chmod ugo-w backup.tar
Xclean:
X	rm -f *.CKP *.o datesub.c core
X	strip $(BINARIES)
Xinstall:
X	rm -f $(BINDIR)/player
X	ln player $(BINDIR)/player
X	rm -f $(BINDIR)/rogomatic
X	ln rogomatic $(BINDIR)/rogomatic
Xtitler: titler.c
X	cc -o titler titler.c -lcurses -ltermcap
Xanim: anim.c utility.o
X	cc -o anim anim.c utility.o -lcurses -ltermcap
Xindex: $(SRCS)
X	ctags -x $(SRCS) > index
Xfluff: $(SRCS)
X	lint *.c	| grep -v 'variable # of args' \
X			| grep -v 'unused in function' \
X			| grep -v 'used inconsistently' \
X			| grep -v 'declared inconsistently' \
X			| grep -v 'multiply declared' \
X			> fluff
Xprint: $(SRCS) $(HDRS)
X	@echo $? > printit
Xdist: $(SRCS) $(HDRS) $(OTHERS) makefile rogomatic.6 README
X	rm -rf $(PUBDIR)	
X	mkdir $(PUBDIR)
X	cp $(SRCS) $(HDRS) $(OTHERS) makefile rogomatic.6 README $(PUBDIR)
X	chmod 0444 $(PUBDIR)/*
X	du $(PUBDIR)
X
Xgenetest: genetest.o learn.o rand.o stats.o utility.o types.h
X	cc -g -o genetest genetest.o learn.o rand.o stats.o utility.o -lm
X
Xgplot: gplot.c
X	cc -g -o gplot gplot.c -lm
/
echo 'x - replay.c'
sed 's/^X//' > replay.c << '/'
X/*
X * replay.c: Rog-O-Matic XIV (CMU) Fri Dec 28 22:43:54 1984 - mlm
X * Copyright (C) 1985 by A. Appel, G. Jacobson, L. Hamey, and M. Mauldin
X * 
X * Make a table of offsets to the beginning of each level of a
X * Rog-O-Matic log file.
X */
X
X# include <curses.h>
X# include <ctype.h>
X# include "types.h"
X# include "globals.h"
X
X# define MAXNUMLEV 50
X# define FIRSTLEVSTR "\nR: "
X# define NEWLEVSTR "\nR: {ff}"
X# define POSITAT   "{ff}"
X
Xstruct levstruct {
X	long pos;
X	int  level, gold, hp, hpmax, str, strmax, ac, explev, exp;
X} levpos[MAXNUMLEV];
Xint numlev = 0;
X
X/* 
X * positionreplay: Called when user has typed the 'R' command, it fills
X * the level table by calling findlevel if necessary, and then positions
X * the log file to the level requested by the user.
X */
X
Xpositionreplay ()
X{ int curlev;
X  long curpos;
X  char cmd;
X
X  /* Prompt user for a command character, read it, and lower case it */
X  saynow ("Which level (f=first, p=previous, c=current, n=next, l=last): ");
X  if (isupper ((cmd = getch ()))) cmd = tolower (cmd);
X
X  /* Clear the prompt */
X  saynow ("");
X
X  /* If command is not in the list, clear the prompt and exit. */
X  switch (cmd)
X  { case 'f': case 'p': case 'c': case 'n': case 'l': break;
X    default:  return;
X  }
X
X  /* Save the current position in the file */
X  curpos = ftell (logfile);
X
X  /* Read the log file, if we have not already done so */
X  if (!logdigested)
X  { saynow ("Reading whole log file to find levels...");
X
X    if (!findlevel (logfile, levpos, &numlev, MAXNUMLEV))
X    { saynow ("Findlevel failed! Let's try to get back to where we were...");
X      fseek (logfile, curpos, 0);
X      return;
X    }
X    logdigested++;
X  }
X
X  /* Now figure out the current level (so relative commands will work) */  
X  for (curlev = 0; curlev < numlev-1; curlev++)
X    if (levpos[curlev+1].pos > curpos) break;
X
X  /* Now clear the screen, position the log file, and return */
X  switch (cmd)
X  { case 'f': fseek (logfile, levpos[0].pos, 0); break;
X    case 'p': if (curlev > 0) fseek (logfile, levpos[curlev-1].pos);
X              else            fseek (logfile, levpos[0].pos, 0); break;
X	      break;
X    case 'c': fseek (logfile, levpos[curlev].pos); break;
X    case 'n': if (curlev < numlev-1) fseek (logfile, levpos[curlev+1].pos);
X              else            fseek (logfile, levpos[curlev].pos, 0); break;
X	      break;
X    case 'l': fseek (logfile, levpos[numlev-1].pos);
X	      break;
X    default:  fseek (logfile, 0L, 0);
X  }
X
X  clearscreen ();	/* Clear the screen */
X  Level = -1; 		/* Force a newlevel() call */
X}
X
X/* 
X * findlevel: Make a table of offsets to the various levels of a
X *             Rog-O-Matic log file.
X */
X
Xfindlevel (f, levpos, numlev, maxnum)
XFILE *f;
Xstruct levstruct *levpos;
Xint *numlev, maxnum;
X{ char ch;
X
X  int l=0;
X  *numlev = 0;
X
X  /* Position file after first newline */  
X  rewind (f);
X  while ((ch = getc (f)) != '\n' && (int) ch != EOF);
X
X  /* This is that start of level one */  
X  levpos[l].pos = ftell (f);
X  
X  if (!findmatch (f, FIRSTLEVSTR))
X  { rewind (f);
X    return (FAILURE);
X  }
X  
X  fillstruct (f, &levpos[l]);
X  
X  while (++l <= maxnum && findmatch (f, NEWLEVSTR))
X  { fseek (f, (long) -strlen (POSITAT), 1);
X    levpos[l].pos = ftell (f);
X    fillstruct (f, &levpos[l]);      
X  }
X
X  *numlev = l;
X  rewind (f);
X  return (SUCCESS);
X}
X
X/* 
X * fillstruct: scan the logfile from the current point, and fill in the
X * fields of a levstruct.
X */
X
Xfillstruct (f, lev)
XFILE *f;
Xstruct levstruct *lev;
X{ 
X  lev->level  = 0;
X  lev->gold   = 0;
X  lev->hp     = 0;
X  lev->hpmax  = 0;
X  lev->str    = 0;
X  lev->strmax = 0;
X  lev->ac     = 0;
X  lev->explev = 0;
X  lev->exp    = 0;
X  
X  if (!findmatch (f, "Level:")) return;
X  fscanf (f, "%d", &lev->level);
X
X  if (!findmatch (f, "Gold:")) return;
X  fscanf (f, "%d", &lev->gold);
X
X  if (!findmatch (f, "Hp:")) return;
X  fscanf (f, "%d(%d)", &lev->hp, &lev->hpmax);
X
X  if (!findmatch (f, "Str:")) return;
X  fscanf (f, "%d(%d)", &lev->str, &lev->strmax);
X
X  if (!findmatch (f, ":")) return;		/* Armor class */
X  fscanf (f, "%d", &lev->ac);
X
X  if (!findmatch (f, "Exp:")) return;
X  fscanf (f, "%d/%d", &lev->explev, &lev->exp);
X
X  saynow ("Found level %d, has %d gold...", lev->level, lev->gold);
X}
X
X/* 
X * findmatch: read from a stream until string 's' has been read. Returns 0
X * if EOF is read, and 1 if the match is found.  The stream is left
X * immediately after the matched string.
X *
X * Restriction: 's' must not contain prefix of itself as a substring.
X */
X
Xint findmatch (f, s)
XFILE *f;
Xchar *s;
X{ char *m = s, ch;
X
X  while (*m && (int) (ch = fgetc (f)) != EOF)
X    if (ch != *(m++)) m = s;
X  
X  if (*m) return (0);
X  else    return (1);
X}
/
echo 'x - rgmplot.c'
sed 's/^X//' > rgmplot.c << '/'
X/*
X * rgmplot.c: Rog-O-Matic XIV (CMU) Thu Jan 31 20:04:11 1985 - mlm
X * Copyright (C) 1985 by A. Appel, G. Jacobson, L. Hamey, and M. Mauldin
X * 
X * This program takes a Rog-O-Matic score file sorted by date and score, 
X * and produces a scatter plot of the scores.
X */
X
X# include <stdio.h>
X# define WIDTH 50
X# define AVLEN 7
X# define SCALE(n) (((n)+100)/200)
X# define isdigit(c) ((c) >= '0' && (c) <= '9')
X
Xchar *month[] = 
X{ "Jan", "Feb", "Mar", "Apr", "May", "Jun",
X  "Jul", "Aug", "Sep", "Oct", "Nov", "Dec" };
X
Xint doavg = 0, cheat = 0, min = -1;
X
Xmain (argc, argv)
Xint argc;
Xchar *argv[];
X{ int mm, dd, yy, score = 0, lastday = -1, lastmon = -1, h;
X  int sumscores = 0, numscores = 0, i;
X  int sum[AVLEN], num[AVLEN], rsum, rnum, davg, ravg;
X  char player[100], plot[128], cheated;  
X
X  /* Clear out the rolling average statistics */
X  for (i = 0; i < AVLEN; i++)
X    sum[i] = num[i] = 0;
X
X  /* Get the options */
X  while (--argc > 0 && (*++argv)[0] == '-')
X    while (*++(*argv))
X    { switch (**argv)
X      { case 'c': cheat++; break; /* List cheat games */
X        case 'a': doavg++; break; /* Print average */
X        default:  printf ("Usage: rgmplot [-ac] [mininum]\n");
X                  exit (1);
X      }
X    }
X
X  if (argc > 0) min = atoi (argv[0]);
X
X  /*  Print out the header */
X  printf ("           Scatter Plot of Rog-O-Matic Scores versus time\n\n");
X  if (min > 0) 
X    printf ("                      Scores greater than %d\n\n", min);
X  printf ("         0      2000      4000      6000      8000     10000\n");
X  printf ("         |----+----|----+----|----+----|----+----|----+----|\n");
X
X
X  /* Build an empty plot line */
X  strcpy (plot, "|                                                 |");
X
X  /* While more scores do action for each score */
X  while (getscore (&mm, &dd, &yy, player, &score, &cheated) != EOF)
X  { 
X    /* Change days, overprint the average for day, rolling avg */
X    if ((dd != lastday || mm != lastmon) && lastday > 0)
X    { if (doavg)
X      { rsum = *sum; rnum = *num;
X        for (i = 1; i < AVLEN; i++)
X        { rsum += sum[i]; rnum += num[i]; }
X
X        davg = SCALE ((*num > 0) ? (*sum / *num) : 0);
X        ravg = SCALE ((rnum > 0) ? (rsum / rnum) : 0);
X
X        /* Roll the daily average statistics */
X        for (i = AVLEN-1; i > 0; i--)
X        { sum[i] = sum[i-1]; num[i] = num[i-1]; } 
X        *sum = *num = 0;	  	
X
X        /* Print a '*' for the daily average */
X        if (davg > 0 && davg < WIDTH)
X	  plot[davg] = '*';
X
X        /* Print a '###' for the rolling average */
X        if (ravg > 0 && ravg < WIDTH-1)
X	  plot[ravg-1] = plot[ravg] = plot[ravg+1] = '#';
X      }
X          
X      printf ("%3s %2d   %s\n", month[lastmon-1], lastday, plot);
X      strcpy (plot, "|                                                 |");
X      
X    }
X    
X    if (score > EOF)
X    { if ((h = SCALE(score)) >= WIDTH)  sprintf (plot, "%s %d", plot, score);
X      else if (plot[h] == '9')          ;
X      else if (isdigit(plot[h]))        plot[h]++;
X      else                              plot[h] = '1';
X
X      *sum += score;
X      ++*num;
X
X      sumscores += score;
X      ++numscores;
X
X      lastday = dd; lastmon = mm;
X    }
X  }
X
X  printf ("         |----+----|----+----|----+----|----+----|----+----|\n");
X  printf ("         0      2000      4000      6000      8000     10000\n");
X  
X
X  if (numscores > 0)
X    printf ("\nAverage score %d, total games %d.\n\n", 
X            sumscores/numscores, numscores);
X
X  printf ("1-9    Number of games in range.\n");
X    
X  if (doavg)
X  { printf (" *     Average of day's scores.\n");
X    printf ("###    Rolling %d day average.\n", AVLEN);
X  }
X}
X
X
Xgetlin (s)
Xchar *s;
X{ int ch, i;
X  static int endfile = 0;
X
X  if (endfile) return (EOF);
X
X  for (i=0; (ch = getchar()) != EOF && ch != '\n'; i++)
X    s[i] = ch;
X
X  s[i] = '\0';
X  
X  if (ch == EOF)
X  { endfile = 1;
X    strcpy (s, "-1 -1, -1 string -1 ");
X    return (20);
X  }
X
X  return (i);
X}
X
Xgetscore (mm, dd, yy, player, score, cheated)
Xint *mm, *dd, *yy, *score;
Xchar *player, *cheated;
X{ char line[128], reason[32];
X  while (getlin (line) != EOF)
X  { sscanf (line, "%d %d, %d %10s%d%c%17s",
X            mm, dd, yy, player, score, cheated, reason);
X    if ((*score >= min || *score < 0) &&
X	(*cheated != '*' || cheat) &&
X        !stlmatch (reason, "saved") &&
X        (*score > 2000 || !stlmatch (reason, "user")))
X      return (1);
X  }
X  return (EOF);
X}
/
echo 'x - scorefile.c'
sed 's/^X//' > scorefile.c << '/'
X/*
X * scorefile.c: Rog-O-Matic XIV (CMU) Mon Jan  7 17:20:52 1985 - mlm
X * Copyright (C) 1985 by A. Appel, G. Jacobson, L. Hamey, and M. Mauldin
X *
X * This file contains the functions which update the rogomatic scorefile,
X * which lives in <RGMDIR>/rgmscore<versionstr>. LOCKFILE is used to
X * prevent simultaneous accesses to the file. rgmdelta<versionstr>
X * contains new scores, and whenever the score file is printed the delta
X * file is sorted and merged into the rgmscore file.
X */
X
X# include <stdio.h>
X# include <sys/types.h>
X# include <sys/stat.h>
X# include "types.h"
X# include "globals.h"
X# include "install.h"
X
X# define LINESIZE	2048
X# define SCORE(s,p)     (atoi (s+p))
X
Xstatic char lokfil[100];
X
X/* 
X * add_score: Write a new score line out to the correct rogomatic score
X * file by creating a temporary copy and inserting the new line in the
X * proper place. Be tense about preventing simultaneous access to the
X * score file and catching interrupts and things.
X */
X
Xadd_score (new_line, version, noterm)
Xchar *new_line, *version;
Xint noterm;
X{ 
X  int   wantscore = 1;
X  char  ch;
X  char  newfil[100];
X  FILE *newlog;
X
X  sprintf (lokfil, "%s %s", LOCKFILE, version);
X  sprintf (newfil, "%s/rgmdelta%s", RGMDIR, version);
X
X  /* Defer interrupts while mucking with the score file */
X  critical ();
X
X  /* 
X   * Lock the score file. If lock_file fails, asks the user whether he
X   * wishes to wait. If so, then try lock_file five times and then ask
X   * again.
X   */
X  
X  while (lock_file (lokfil, MAXLOCK) == 0)
X    if (--wantscore < 1 && !noterm)
X    { printf ("The score file is busy, do you wish to wait? [y/n] ");
X      while ((ch = getchar ()) != 'y' && ch != 'n');
X      if (ch == 'y')
X        wantscore = 5;
X      else
X      { uncritical (); return; }
X    }
X  
X  /* Now create a temporary to copy into */
X  if ((newlog = wopen (newfil, "a")) == NULL)
X  { printf ("\nUnable to write %s\n", newfil); }
X  else
X  { fprintf (newlog, "%s\n", new_line);
X    fclose (newlog);
X  }
X
X  /* Write the score to the end of the delta file */
X
X  /* Now close the file, relinquish control of scorefile, and exit */
X  unlock_file (lokfil);
X  uncritical ();
X}
X
X/* 
X * dumpscore: Print out the scoreboard.
X */
X
Xdumpscore (version)
Xchar *version;
X{ 
X  char  ch, scrfil[100], delfil[100], newfil[100], allfil[100], cmd[256];
X  FILE *scoref, *deltaf;
X  int   oldmask, intrupscore ();
X
X  sprintf (lokfil, "%s %s", LOCKFILE, version);
X  sprintf (scrfil, "%s/rgmscore%s", RGMDIR, version);
X  sprintf (delfil, "%s/rgmdelta%s", RGMDIR, version);
X  sprintf (newfil, "%s/NewScore%s", RGMDIR, version);
X  sprintf (allfil, "%s/AllScore%s", RGMDIR, version);
X
X  /* On interrupts we must relinquish control of the score file */
X  int_exit (intrupscore);
X
X  if (lock_file (lokfil, MAXLOCK) == 0)
X  { printf ("Score file busy.\n");
X    exit (1);
X  }
X  
X  deltaf = fopen (delfil, "r");
X  scoref = fopen (scrfil, "r");
X
X  /* If there are new scores, sort and merge them into the score file */
X  if (deltaf != NULL)
X  { fclose (deltaf);
X
X    /* Defer interrupts while mucking with the score file */
X    critical ();
X
X    /* Make certain any new files are world writeable */    
X    oldmask = umask (0);
X
X    /* If we have an old file and a delta file, merge them */
X    if (scoref != NULL)
X    { fclose (scoref);
X      sprintf (cmd, "sort +4nr -o %s %s; sort -m +4nr -o %s %s %s", 
X               newfil, delfil, allfil, newfil, scrfil);
X      system (cmd);
X      if (filelength (allfil) != filelength (delfil) + filelength (scrfil))
X      { fprintf (stderr, "Error, new file is wrong length!\n");
X        unlink (newfil); unlink (allfil);
X        unlock_file (lokfil);
X        exit (1);
X      }
X      else
X      { /* New file is okay, unlink old files and pointer swap score file */
X        unlink (delfil); unlink (newfil);
X	unlink (scrfil); link (allfil, scrfil); unlink (allfil);
X      }      
X      scoref = fopen (scrfil, "r");
X    }
X    else
X    /* Only have delta file, sort into scorefile and unlink delta */
X    { sprintf (cmd, "sort +4nr -o %s %s", scrfil, delfil);
X      system (cmd);
X      unlink (delfil);
X      scoref = fopen (scrfil, "r");
X    }
X 
X    /* Restore umask */
X    umask (oldmask);
X
X    /* Restore interrupt status after score file stable */
X    uncritical ();
X  }
X
X  /* Now any new scores have been put into scrfil, read it */
X  if (scoref == NULL)
X  { printf ("Can't find %s\nBest score was %d.\n", scrfil, BEST);
X    unlock_file (lokfil);
X    exit (1);
X  }
X
X  printf ("Rog-O-Matic Scores against version %s:\n\n", version);
X  printf ("%s%s", "Date         User        Gold    Killed by",
X          "      Lvl  Hp  Str  Ac  Exp\n\n");
X
X  while ((int) (ch = fgetc (scoref)) != EOF)
X    putchar (ch);
X
X  fclose (scoref);
X  unlock_file (lokfil);
X
X  exit (0);
X}
X
X/* 
X * intrupscore: We have an interrupt, clean up and unlock the score file.
X */
X
Xintrupscore ()
X{ unlock_file (lokfil);
X  exit (1);
X}
X
/
echo 'x - stats.c'
sed 's/^X//' > stats.c << '/'
X/*
X * stats.c: Rog-O-Matic XIV (CMU) Fri Dec 28 23:28:59 1984 - mlm
X * Copyright (C) 1985 by A. Appel, G. Jacobson, L. Hamey, and M. Mauldin
X * 
X * A package for maintaining probabilities and statistics.
X *
X * Functions:
X *
X *    A probability is a simple count of Bernoulli trials.
X *
X *	clearprob:	Clear a probability.
X *	addprob:	Add success/failure to a probability.
X *	prob:		Calculate p(success) of a statistic.
X *	parseprob:	Parse a probability from a string.
X *	writeprob:	Write a probability to a file.
X *
X *    A statistic is a random variable with a mean and stdev.
X *
X *	clearstat:	Clear a statistic.
X *	addstat:	Add a data point to a statistic.
X *	mean:		Calculate the mean of a statistic.
X *	stdev:		Calculate the std. dev. of a statistic.
X *	parsestat:	Parse a statistic from a string.
X *	writestat:	Write a statistic to a file.
X */
X
X# include <stdio.h>
X# include <math.h>
X# include "types.h"
X
X/* 
X * clearprob: zero a probability structure.
X */
X
Xclearprob (p)
Xregister  probability *p;
X{ p->fail = p->win = 0;
X}
X
X/* 
X * addprob: Add a data point to a probability
X */
X
Xaddprob (p, success)
Xregister probability *p;
Xregister int success;
X{ 
X  if (success)	p->win++;
X  else		p->fail++;
X}
X
X/* 
X * prob: Calculate a probability
X */
X
Xdouble prob (p)
Xregister probability *p;
X{ register int trials = p->fail + p->win;
X
X  if (trials < 1)	return (0.0);
X  else			return ((double) p->win / trials);
X}
X
X/* 
X * parseprob: Parse a probability structure from buffer 'buf'
X */
X
Xparseprob (buf, p)
Xregister char *buf;
Xregister probability *p;
X{ p->win = p->fail = 0;
X  sscanf (buf, "%d %d", &p->fail, &p->win);
X}
X
X/* 
X * writeprob. Write the value of a probability structure to file 'f'.
X */
X
Xwriteprob (f, p)
Xregister FILE *f;
Xregister probability *p;
X{ fprintf (f, "%d %d", p->fail, p->win);
X}
X
X/* 
X * clearstat: zero a statistic structure.
X */
X
Xclearstat (s)
Xregister  statistic * s;
X{ s->count = 0;
X  s->sum = s->sumsq = s->low = s->high = 0.0;
X}
X
X/* 
X * addstat: Add a data point to a statistic
X */
X
Xaddstat (s, datum)
Xregister statistic *s;
Xregister int datum;
X{ double d = (double) datum;
X
X  s->count++;
X  s->sum += d;
X  s->sumsq += d*d;
X
X  if (s->count < 2)	s->low = s->high = d;
X  else if (d < s->low)	s->low = d;
X  else if (d > s->high)	s->high = d;
X}
X
X/* 
X * mean: Return the mean of a statistic
X */
X
Xdouble mean (s)
Xregister statistic *s;
X{
X  if (s->count < 1)	return (0.0);
X  else			return (s->sum / s->count);
X}
X
X/* 
X * stdev: Return the standard deviation of a statistic
X */
X
Xdouble stdev (s)
Xregister statistic *s;
X{ register n = s->count;
X
X  if (n < 2)	return (0.0);
X  else		return (sqrt ((n * s->sumsq - s->sum * s->sum) / (n * (n-1))));
X}
X
X/* 
X * parsestat: Parse a statistic structure from buffer 'buf'
X */
X
Xparsestat (buf, s)
Xregister char *buf;
Xregister statistic *s;
X{ s->count = 0;
X  s->sum = s->sumsq = s->low = s->high = 0.0;
X  sscanf (buf, "%d %lf %lf %lf %lf",
X      &s->count, &s->sum, &s->sumsq, &s->low, &s->high);
X}
X
X/* 
X * writestat. Write the value of a statistic structure to file 'f'.
X */
X
Xwritestat (f, s)
Xregister FILE *f;
Xregister statistic *s;
X{ fprintf (f, "%d %lg %lg %lg %lg",
X           s->count, s->sum, s->sumsq, s->low, s->high);
X}
/
echo 'x - titlepage.c'
sed 's/^X//' > titlepage.c << '/'
X/*
X * titlepage.c: Rog-O-Matic XIV (CMU) Tue Jan  1 14:32:17 1985 - mlm
X * Copyright (C) 1985 by A. Appel, G. Jacobson, L. Hamey, and M. Mauldin
X *
X * This file contains the functions which display the animated copyright
X * notice on the screen.  A general movie facility is used to animate
X * the screen.
X */
X
X# include <stdio.h>
X# include <curses.h>
X# include "types.h"
X# include "globals.h"
X
Xstatic char *titlepage[]={
X/* The static part of the display */
X"  @ !@ \"@ #@ K@! @!$@!K@!P@\" @\"$@\"(@\")@\"*@\"/@\"0@\"1@\"6@\"7@\"8@",
X"\"=@\"?@\"C@\"D@\"E@\"I@\"J@\"K@\"L@\"M@\"U@\"V@\"W@\"X@\"]@\"a@\"c@\"e@",
X"\"i@# @#!@#\"@##@#'@#+@#.@#2@#5@#9@#<@#>@#@@#F@#K@#P@#T@#^@#`@#c@#e@#i@$",
X" @$$@$'@$+@$.@$2@$5@$9@$<@$@@$C@$D@$E@$F@$K@$P@$T@$_@$c@$e@$i@% @%$@%'@%",
X"+@%.@%2@%5@%9@%<@%@@%C@%F@%K@%P@%T@%^@%`@%c@%f@%h@& @&%@&(@&)@&*@&/@&0@&",
X"1@&2@&6@&7@&8@&<@&@@&D@&E@&G@&L@&Q@&U@&V@&W@&X@&]@&a@&c@&g@'2@(.@(/@(0@(",
X"1@);C)<o)=p)>y)?r)@i)Ag)Bh)Ct)E()Fc)G))I1)J9)K8)L5)Nb)Oy*'A*(n*)d**r*+e*",
X",w*.A*/p*0p*1e*2l*3,*5L*6e*7o*8n*9a*:r*;d*=H*>a*?m*@e*Ay*B,*DG*Eu*Fy*HJ*",
X"Ia*Jc*Ko*Lb*Ms*No*On*P,*Ra*Sn*Td*VM*Wi*Xc*Yh*Za*[e*\\l*^M*_a*`u*al*bd*ci",
X"*dn,)@,*@,+@,,@,[D,\\D,]D,^D,_D-(@-+ at --@-[D-`D.(@.*@.- at .[D.`D/(@/*@/+@/,",
X"@/-@/[D/`D0)@0*@0+ at 0, at 0[D0\\D0]D0^D0_D2 H2!o2\"n2#o2$r2%a2&b2'l2(e2*m2+e",
X"2,m2-b2.e2/r21o22f24t25h26e28F29i2:g2;h2<t2=e2>r2?'2 at s2BG2Cu2Di2El2Fd3 T",
X"3!o3\"t3#a3$l3&w3'i3(n3)n3*e3+r3-a3.g3/a30i31n32s33t35R36o37g38u39e3;33<",
X".3=63>,3 at S3Ae3Bp3Ct3De3Em3Fb3Ge3Hr3J23K63L,3N13O93P83Q24 T4!o4\"t4#a4$l4",
X"&w4'i4(n4)n4*e4+r4-a4.g4/a40i41n42s43t45R46o47g48u49e4;54<.4=24>,4 at O4Ac4",
X"Bt4Co4Db4Ee4Fr4H14I04J,4L14M94N84O35 T5!o5\"t5#a5$l5&w5'i5(n5)n5*e5+r5-a",
X"5.g5/a50i51n52s53t55R56o57g58u59e5;55<.5=35>,5 at F5Ae5Bb5Cr5Du5Ea5Fr5Gy5I1",
X"5J65K,5M15N95O85P4",
X
X/* The dynamic part of the display */
X"~~~~~~~~~~00/~/1/~.2)~-1\\~,0\\~~~.3>~.4=~.5=~.6=~.7=~.8=~.9>~~~.2>.3=.8",
X">.9 ~~~.1>.2=.7>.8 ~~~.0>.1=.6>.7 ~~~./>.0=.5>.6 ~~~..>./=.4>.5 ~~~~~~~~",
X"~~~~~.. ./>.4 .4=.5>~./ .0>.5=.6>~.0 .1>.6=.7>~.1 .2>.7=.8>~.2).3>.8=.9>",
X"~.3 .4>.9=.:>~.4 .5>.:=.;>~.5 .6>.;=.<>~.6 .7>.<=.=>~.7 .8>.==.>>~.8 .9>",
X".>=.?>~.9 .:>.?=.@>~.: .;>.@=.A>~.; .<>.A=.B>~.< .=>.B=.C>~.= .>>.C=.D>~",
X".> .?>.D=.E>~.? .@>.E=.F>~.@ .A>.F=.G>~.A .B>.G=.H>~.B .C>.H=.I>~.C .D>.",
X"I=.J>~.D .E>.J=.K>~.E .F>.K=.L>~.F .G>.L=.M>~.G .H>.M=.N>~.H .I>.N=.O>~.",
X"I .J>.O=.P>~.J .K>.P=.Q>~.K .L>.Q=.R>~.L .M>.R=.S>~.M .N>.S=.T>~.N .O>.T",
X"=.U>~.O .P>.U=.V>~.P .Q>.V=.W>~.Q .R>.W=.X>~.R .S>.X=.Y>~.S .T>.Y=.Z>~.T",
X" .U>.Z=.[>~.U .V>.[=.\\>~.V .W>.\\=.]>~.W .X>.]=.^>~.X .Y>.^=._>~.Y .Z>.",
X"_=.`>~.Z .[>.`=.a>~.[ .\\>.a=.b>~.\\ .]>.b=.c>~.] .^>.c=.d>~.^ ._>.d=.e>",
X"~._ .`>.e=.f>~.` .a>.f=.g>~.a .b>.g=.h>~.b .c>.h=.i>~.c .d>.i ~.d .e>~.e",
X" .f>~.f .g>~.g .h>~.h ~~~~~.[D,[ ,\\j,\\ -\\D-]d-]D-^D-_D,_ ,^ ,] ,]j,] ",
X"~-[ .ZD/ZD.[ .[L.[ .\\D.]S.]D.^D._D.`D/aD-\\ -\\L-\\ -] -^ -_ -` ~/YD.Z ",
X"/\\D/]D/^D/_D.\\ .] .^ ._ .` 0`D0aD/a ~0XD0YD0ZD/Y /Z /` ~0VD0WD/[ /\\ /",
X"^ /_ 0bD0cD/] 0UD0dD~~~~~~~~~~,0 ~~-1 ~~.2 ~~/1 ~~00 ~~~~~~~~~~~~~~~~~~~",
X"~~.5S~.6t~.7u~.8p~.9i~.:d~.<D~.=r~.>a~.?g~. at o~.An~.C!~.D!~.E!~~~~~~~~~~~",
X"~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~.5 .6 .7 .8 .9 .: .; .",
X"< .= .> .? .@ .A .B .C .D .E .F 6  ~~~~~~~~~~~~~~~~~~",
XNULL};
X
X# define NEXTCHAR (*cbf?*cbf++:(cbf=1+ *movie++)[-1])
X
X/* 
X * animate: Display a movie on the screen.  A movie is a list of strings
X * wherein each character is either a bell command '}', a synchronize
X * command '~', or a triplet <row+32, col+32, char> indicating a character
X * to be placed at a specific place on the screen.
X *
X * Movies run the same speed regardless of baudrate (if the baud rate
X * greater than 2400).
X */
X
Xanimate (movie)
Xchar *movie[];
X{ register int r, c, count = 0, delaychars = (baudrate () / 200);
X  register char *cbf = "";
X
X  if (emacs || terse) return;		/* No screen ==> no movie */
X
X  clear ();				/* Clear the screen */
X  while (*movie || *cbf)		/* While more animate commands */
X  { r = NEXTCHAR;			/* Get command character */
X
X    /* Ring the Bell */
X    if (r == '}') putchar (ctrl('G'));
X
X    /* Update the screen and delay until one timestep is gone */
X    else if (r == '~')
X    { refresh ();				/* Write out screen */
X      for (; count < delaychars; count++)	/* Pad with nulls */
X        putchar (0);
X      count = 0;				/* Reset char count */
X    }
X
X    /* Write out a single character and bump the character count */
X    else
X    { r -= 32;					/* Get screen row */
X      c = NEXTCHAR - 32;			/* Get screen col */
X      mvaddch (r, c, NEXTCHAR);			/* Write out character */
X      if (count++ < 4) count += 4;		/* Assume one cursor move */
X    }
X  }
X}
X
X/*
X * halftimeshow: If its time for a halftime show, call movie.  Variable 
X * 'nohalf' is true if the user does not want to see a halftime show.
X */
X
Xhalftimeshow (level)
Xint level;
X{ static int nextshow = 1;
X
X  /* If terminal is too slow, dont bother */
X  if (baudrate () < 1200)
X    return;
X
X  if (!nohalf && level >= nextshow)
X  { if (nextshow == 1)
X    { nextshow = 9999; animate (titlepage); }
X  }
X}
/
echo 'Part 10 of Rog-O-Matic XIV complete.'
exit



More information about the Comp.sources.unix mailing list