home *** CD-ROM | disk | FTP | other *** search
- Path: uunet!news.tek.com!master!saab!billr
- From: billr@saab.CNA.TEK.COM (Bill Randle)
- Newsgroups: comp.sources.games
- Subject: v15i044: gtetris3 - Generic Tetris for X11, V2.0.1, Part01/02
- Message-ID: <4205@master.CNA.TEK.COM>
- Date: 15 Jan 93 01:32:08 GMT
- Sender: news@master.CNA.TEK.COM
- Lines: 1951
- Approved: billr@saab.CNA.TEK.COM
- Xref: uunet comp.sources.games:1543
-
- Submitted-by: "Qiang Alex Zhao" <azhao@cs.arizona.edu>
- Posting-number: Volume 15, Issue 44
- Archive-name: gtetris3/Part01
- Supersedes: gtetris2: Volume 15, Issue 5-6
- Environment: X11R4/5, Xlib
-
- [This is major rewrite of the popular Generic Tetris game for X. -br]
-
- #! /bin/sh
- # This is a shell archive. Remove anything before this line, then unpack
- # it by saving it into a file and typing "sh file". To overwrite existing
- # files, type "sh file -c". You can also feed this as standard input via
- # unshar, or by typing "sh <file", e.g.. If this archive is complete, you
- # will see the following message at the end:
- # "End of archive 1 (of 2)."
- # Contents: README MANIFEST X11 bitmaps playing.c tetris.c tetris.h
- # utils.c
- # Wrapped by billr@saab on Wed Jan 13 19:41:27 1993
- PATH=/bin:/usr/bin:/usr/ucb ; export PATH
- if test -f 'README' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'README'\"
- else
- echo shar: Extracting \"'README'\" \(4720 characters\)
- sed "s/^X//" >'README' <<'END_OF_FILE'
- X GENERIC TETRIS
- X ============== Yet Another Tetris Game on X, V2.0.1
- X
- X
- XWHY ANOTHER?
- X
- X Because this one is simple, easy to build, and portable -- actually
- X the blocks are bigger, more comfortable for your eyes. It only uses
- X Xlib -- no "toolkit" kind of thing. People have tested it on the
- X following platforms:
- X
- X DEC 5000 Ultrix 4.2A X11R4
- X Iris 4D IRIX 4.0.1 Motif
- X Sun4, SPARCstation SunOS 4.1.1 X11R4, X11R5
- X Sequent S81 DYNIX 3.2.0 X11R5
- X
- X If your's is not in this list, please let me know -- thanks. The
- X most updated source could be found on export.lcs.mit.edu under
- X /contrib.
- X
- X A System V port (Sequent Dynix/ptx) for earlier versions has been
- X added by "Hans-Wolfgang Loidl" (hwloidl@risc.uni-linz.ac.at). The
- X source can be retrieved by anonymous FTP to:
- X Host: melmac.risc.uni-linz.ac.at
- X File: /pub/misc/gtetris.tar.Z
- X
- X
- XHOW TO BUILD?
- X
- X Edit the Imakefile for appropriate settings of variable SCOREFILE
- X and RANDOM, then do:
- X xmkmf
- X make
- X
- X "Tetris" is the game. It only lists the top 15 players at the end,
- X each player may has at most three scores. With the option "-s",
- X "tetris" will list all the scores.
- X
- X
- XANYTHING SPECIAL IN PLAYING?
- X
- X Use 'j' to move left; 'l' to move right; 'k' to rotate. Left-handed
- X people may want to use 's', 'd', 'f' respectively. Use the space
- X bar to drop a block quickly. Do you want to try the arrow keys?
- X
- X Use CTRL-L key combination to redraw -- in case the program messes
- X somthing up.
- X
- X As usual, '+' and '-' will speed up or lower down the speed. Note
- X that you don't need to press the SHIFT key -- '=' and '_' also
- X work. The 'b' key can be used to toggle "beep" and 'n' toggles
- X "show next".
- X
- X If you press 'p', the game will be paused, and the window will be
- X iconified -- just in case your boss suddenly appears at your door.
- X ;o) When the tetris window loses its focus, it also goes to
- X "paused" mode except it doesn't iconify itself.
- X
- X Refer to the man page for detailed command line options.
- X
- X
- XFOUND A BUG?
- X
- X Send bugs (or their reports, or fixes) to the author:
- X
- X Qiang Alex Zhao, azhao@cs.arizona.edu
- X Computer Science Department
- X University of Arizona
- X Tucson, AZ 85721
- X
- X Refter to the "COPYRIGHT" notice in the "COPYRIGHT" file (yeah, as
- X its name implies). And note: my first name is *NOT* spelled as
- X "Quiang" nor "Quang".
- X
- X
- XHISTORY -- Oh no, not again: I failed my history course!
- XWell ... ACKNOWLEDGEMENTS
- X
- X Since the days of V1.8, I have got many responses over the net.
- X Thanks go to people who helped me in improving the program.
- X
- X [Jan 12, 93] V2.0.1: added arrow keys. Changed error handling method
- X in locking score file, suggested by Hellmut Golde
- X <golde@cs.washington.edu>.
- X
- X [Jan 10, 93] V2.0.0: Complete rewrite. Enhanced layout. Added
- X resource management and "next piece". Changes made for
- X Sony workstations, suggested by Masato Ogawa
- X <ogawa@sm.sony.co.jp>. Included four X11 header files
- X in case some system doesn't have them. Fixed block
- X clearing bug found by Benjamin Kroop
- X <bkroop@sunlab.cit.cornell.edu>.
- X
- X [Nov 13, 92] Black Friday -- V1.8.1: numerious minor changes. Made
- X score listing built in.
- X
- X [Oct 08, 92] V1.8: Corrected some typos, <herbison@erlang.enet.dec.com>.
- X Added man-page. Gregg Townsend <gmt@cs.arizona.edu>
- X provided hints for some problems on HP-UX. Imakefile.
- X Richard van Denzel suggest modifications for HP-UX.
- X
- X [Sep 30, 92] V1.7: Richard van Denzel <raet-sh!richard@relay.nluug.nl>
- X reported bugs on HP-UX 8.0.
- X
- X [Sep 27, 92] V1.6: Changed speed coefficients. Improved window
- X manager hints. Several rows at once worth more points.
- X
- X [Sep 25, 92] V1.5: HP-UX fixes by "Richard van Denzel"
- X <raet-sh!richard@relay.nluug.nl>. Added 'b' to toggle
- X "beep". Rewrote window creation/initialization to fix
- X the "losing input focus" problem.
- X
- X [Sep 24, 92] V1.4: Added <sys/select.h> and -lbsd for AIX (by "Daryl
- X Green" <darylg@amex-trs.com>).
- X
- X [Sep 23, 92] V1.3: Scoring -- a line in a higher level worth more
- X points; "tscores" program. Submitted to
- X comp.sources.games (volumn 15, issues 1-2; it has
- X nothing to do with GNU, but it was called "gtetris",
- X pronounced as "Gee, tetris", by the newsgroup
- X moderator).
- X
- X [Sep ??, 92] First set of versions, 1.0 through 1.2 -- developed and
- X tested at the University of Arizona. Put on
- X export.lcs.mit.edu.
- X
- X I studied an old tetris game for X10, wrote by Wayne
- X Christopher <faustus@cs.berkeley.edu> in 1988; then I
- X adopted the ideas in representing those "blocks" and
- X rotating them, and added X11 stuff. Also I learned a
- X lot from Nathan Sidwell's great game "xmris", e.g. the
- X "iconifying pause".
- X
- END_OF_FILE
- if test 4720 -ne `wc -c <'README'`; then
- echo shar: \"'README'\" unpacked with wrong size!
- fi
- # end of 'README'
- fi
- if test -f 'MANIFEST' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'MANIFEST'\"
- else
- echo shar: Extracting \"'MANIFEST'\" \(1075 characters\)
- sed "s/^X//" >'MANIFEST' <<'END_OF_FILE'
- X File Name Archive # Description
- X-----------------------------------------------------------
- X COPYRIGHT 2
- X Imakefile 2
- X MANIFEST 1 This shipping list
- X README 1
- X X11 1
- X X11/Xfuncproto.h 2
- X X11/Xfuncs.h 2
- X X11/Xos.h 2
- X X11/Xosdefs.h 2
- X bitmaps 1
- X bitmaps/rot00.xbm 2
- X bitmaps/rot01.xbm 2
- X bitmaps/rot02.xbm 2
- X bitmaps/rot03.xbm 2
- X bitmaps/rot04.xbm 2
- X bitmaps/rot05.xbm 2
- X bitmaps/rot06.xbm 2
- X bitmaps/rot07.xbm 2
- X bitmaps/rot08.xbm 2
- X bitmaps/rot09.xbm 2
- X bitmaps/rot10.xbm 2
- X bitmaps/rot11.xbm 2
- X bitmaps/rot12.xbm 2
- X bitmaps/rot13.xbm 2
- X bitmaps/rot14.xbm 2
- X bitmaps/ticon.xbm 2
- X playing.c 1
- X tetris.c 1
- X tetris.h 1
- X tetris.man 2
- X utils.c 1
- END_OF_FILE
- if test 1075 -ne `wc -c <'MANIFEST'`; then
- echo shar: \"'MANIFEST'\" unpacked with wrong size!
- fi
- # end of 'MANIFEST'
- fi
- if test ! -d 'X11' ; then
- echo shar: Creating directory \"'X11'\"
- mkdir 'X11'
- fi
- if test ! -d 'bitmaps' ; then
- echo shar: Creating directory \"'bitmaps'\"
- mkdir 'bitmaps'
- fi
- if test -f 'playing.c' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'playing.c'\"
- else
- echo shar: Extracting \"'playing.c'\" \(9187 characters\)
- sed "s/^X//" >'playing.c' <<'END_OF_FILE'
- X/*
- X# GENERIC X-WINDOW-BASED TETRIS
- X#
- X# playing.c
- X#
- X###
- X#
- X# Copyright (C) 1992, 1993 Qiang Alex Zhao, azhao@cs.arizona.edu
- X# Computer Science Dept, University of Arizona
- X#
- X# All Rights Reserved
- X#
- X# Permission to use, copy, modify, and distribute this software and
- X# its documentation for any purpose and without fee is hereby granted,
- X# provided that the above copyright notice appear in all copies and
- X# that both that copyright notice and this permission notice appear in
- X# supporting documentation, and that the name of the author not be
- X# used in advertising or publicity pertaining to distribution of the
- X# software without specific, written prior permission.
- X#
- X# This program is distributed in the hope that it will be "playable",
- X# but WITHOUT ANY WARRANTY; without even the implied warranty of
- X# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- X#
- X*/
- X
- X#include "tetris.h"
- X
- Xstatic Bool paused = False;
- X
- Xstatic int speeds[NUM_LEVELS] = {
- X 100, 92, 84, 76, 68, 60, 53, 46, 39, 32, 26, 20, 15, 10, 6, 3, 1, 0};
- Xstatic int thresh[NUM_LEVELS] = {
- X 10, 20, 30, 40, 50, 60, 70, 80, 90,
- X 100, 110, 120, 130, 140, 150, 160, 170, 180};
- X
- Xstatic struct timeval nextFall, now, delay;
- Xstatic struct timezone tzone = {0, 0};
- X
- X/* ------------------------------------------------------------------ */
- X
- Xvoid
- Xplaying()
- X{
- X Bool resetTime = True;
- X
- X score = prefilled * level * 10;
- X while (True) {
- X if (resetTime) {
- X (void) gettimeofday(&nextFall, &tzone);
- X nextFall.tv_usec += 10000 * speeds[level];
- X realTime(&nextFall);
- X } else {
- X int writefd = 0, exceptfd = 0;
- X int readfd = 1 << ConnectionNumber(display);
- X
- X (void) gettimeofday(&now, &tzone);
- X delay.tv_sec = nextFall.tv_sec - now.tv_sec;
- X delay.tv_usec = nextFall.tv_usec - now.tv_usec;
- X realTime(&delay);
- X if (delay.tv_sec >= 0) { /* sleep */
- X (void) select(sizeof(int) * 8, (fd_set *) &readfd,
- X (fd_set *) & writefd, (fd_set *) & exceptfd, &delay);
- X }
- X }
- X (void) gettimeofday(&now, &tzone);
- X if ((now.tv_sec > nextFall.tv_sec) ||
- X ((now.tv_sec == nextFall.tv_sec) &&
- X (now.tv_usec > nextFall.tv_usec))) {
- X (void) evGotNewThing(True);
- X resetTime = True;
- X } else {
- X resetTime = evGotNewThing(False);
- X }
- X }
- X /* never come to here */
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- XBool
- XevGotNewThing(falldown)
- X Bool falldown;
- X{
- X XEvent ev;
- X Bool gotNew = False;
- X char buf[4];
- X
- X if (!paused && falldown)
- X gotNew = moveOne(FALL) || gotNew;
- X
- X while (XPending(display)) {
- X XNextEvent(display, &ev);
- X switch (ev.type) {
- X case KeyPress:
- X if (!XLookupString(&ev.xkey, buf, 4, NULL, NULL))
- X break;
- X
- X switch (buf[0]) {
- X case 'j':
- X case 's':
- X if (!paused)
- X gotNew = moveOne(LEFT) || gotNew;
- X break;
- X
- X case 'k':
- X case 'd':
- X if (!paused)
- X gotNew = moveOne(ROTATE) || gotNew;
- X break;
- X
- X case 'l':
- X case 'f':
- X if (!paused)
- X gotNew = moveOne(RIGHT) || gotNew;
- X break;
- X
- X case ' ':
- X case '\n':
- X if (!paused)
- X gotNew = moveOne(DROP) || gotNew;
- X break;
- X
- X case 'q':
- X case 'Q':
- X gameOver();
- X break;
- X
- X case '+':
- X case '=':
- X if (!paused)
- X if (level < NUM_LEVELS - 1) {
- X level++;
- X drawStatus();
- X }
- X break;
- X
- X case '-':
- X case '_':
- X if (!paused)
- X if (level > 0) {
- X level--;
- X drawStatus();
- X }
- X break;
- X
- X case 'b':
- X case 'B':
- X beep = !beep;
- X if (beep)
- X XBell(display, BVOLUME);
- X break;
- X
- X case 'p':
- X case 'P':
- X if (beep)
- X XBell(display, BVOLUME);
- X paused = !paused;
- X if (paused) {
- X /* "... Hi boss, I'm working hard as usual ..." */
- X banner(MSG_PAUSED);
- X (void) XIconifyWindow(display, mainWin, screen_num);
- X } else {
- X clearNext();
- X if (showNext)
- X drawNext();
- X }
- X XSync(display, False);
- X break;
- X
- X case '\014':
- X XClearWindow(display, mainWin);
- X XClearWindow(display, blockWin);
- X redrawAll();
- X if (paused)
- X banner(MSG_PAUSED);
- X XSync(display, False);
- X break;
- X
- X case 'n':
- X case 'N':
- X if (!paused) {
- X showNext = !showNext;
- X if (showNext) {
- X drawNext();
- X } else {
- X clearNext();
- X }
- X XSync(display, False);
- X }
- X break;
- X
- X default:
- X XBell(display, 0);
- X XSync(display, False);
- X break;
- X }
- X
- X break;
- X
- X case UnmapNotify:
- X paused = True;
- X break;
- X
- X case FocusOut:
- X paused = True;
- X banner(MSG_PAUSED);
- X break;
- X
- X case Expose:
- X if (ev.xexpose.count == 0) {
- X redrawAll();
- X if (paused)
- X banner(MSG_PAUSED);
- X }
- X break;
- X
- X case ClientMessage:
- X if ((Atom) ev.xclient.data.l[0] == delw)
- X gameOver();
- X break;
- X
- X case DestroyNotify:
- X exit(0);
- X break;
- X }
- X }
- X
- X XSync(display, False);
- X return gotNew;
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xvoid
- XredrawAll()
- X{
- X drawTitle();
- X drawStatus();
- X drawField();
- X drawThing();
- X if (showNext)
- X drawNext();
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- XBool
- XmoveOne(move)
- X move_t move;
- X{
- X XEvent ev;
- X int lines;
- X
- X if ((move == DROP) || ((move == FALL) && atBottom())) {
- X tryMove(move);
- X putBox();
- X lines = checkLines();
- X score += prefilled * prefilled + lines + 1;
- X score += (showNext ? 3 : 5) * level * level * lines * lines;
- X rows += lines;
- X if (rows > thresh[level])
- X level ++;
- X drawStatus();
- X newThing();
- X if (showNext) {
- X clearNext();
- X drawNext();
- X }
- X XSync(display, False);
- X while (XPending(display))
- X XNextEvent(display, &ev);
- X if (overlapping())
- X gameOver();
- X drawThing();
- X return True;
- X } else {
- X tryMove(move);
- X if (rows > thresh[level]) {
- X level ++;
- X drawStatus();
- X }
- X return False;
- X }
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xstatic void
- XaddScore()
- X{
- X time_t tloc;
- X char buff[2][SCORESIZE];
- X char lockfile[FILENAMELEN];
- X int fd, lfd;
- X int tmp, ptmp, s1;
- X int mycount = 0;
- X Bool saved = False, trickle = False;
- X
- X time(&tloc);
- X (void) strcpy(myscore.mydate, asctime(localtime(&tloc)));
- X (void) sprintf(myscore.score, "%9d", score);
- X (void) sprintf(myscore.level, "%3d", level);
- X (void) sprintf(myscore.rows, "%4d", rows);
- X
- X (void) fprintf(stderr, "\n- %s", myscore.mydate);
- X (void) fprintf(stderr, "- Your final score is %d,", score);
- X (void) fprintf(stderr, " at level %d with %d rows.\n\n", level, rows);
- X
- X if ((fd = open(SCOREFILE, O_CREAT | O_RDWR, 0644)) < 0) {
- X (void) fprintf(stderr, "Cannot write the score-file!\n");
- X return;
- X }
- X
- X /* lock */
- X (void) strcpy(lockfile, SCOREFILE);
- X (void) strcat(lockfile, ".lock");
- X while (((lfd = open(lockfile, O_CREAT | O_EXCL, 0644)) < 0) &&
- X errno == EEXIST)
- X sleep(1);
- X
- X if (lfd < 0) {
- X (void) perror("Error in creating the score-file lock-file");
- X (void) fprintf(stderr, "Score not recorded - sorry.\n");
- X return;
- X }
- X
- X tmp = 0;
- X ptmp = 1;
- X bcopy((char *) &myscore, buff[1], SCORESIZE);
- X
- X while (read(fd, buff[tmp], SCORESIZE) == SCORESIZE) {
- X sscanf(((score_t *)buff[tmp])->score, " %d", &s1);
- X if (!saved && (s1 <= score)) {
- X trickle = True;
- X saved = True;
- X mycount++;
- X }
- X if (!strncmp(myscore.myname, ((score_t *) buff[tmp])->myname,
- X NAMELEN)) {
- X mycount++;
- X }
- X /* Then check if we should trickle the score */
- X if (trickle) {
- X lseek(fd, (off_t) -SCORESIZE, SEEK_CUR);
- X write(fd, buff[ptmp], SCORESIZE);
- X ptmp = tmp;
- X tmp = (tmp + 1) % 2;
- X }
- X /*
- X * As we trickle, we add up records owned by me. Once we hit max,
- X * we throw it away, and stop trickling.
- X */
- X if ((mycount > MAXSCORES) || ((mycount == MAXSCORES) && !trickle)) {
- X trickle = False;
- X break;
- X }
- X } /* while */
- X
- X if (trickle) {
- X write(fd, buff[ptmp], SCORESIZE);
- X }
- X if (!saved && (mycount < MAXSCORES)) {
- X write(fd, (char *) &myscore, SCORESIZE);
- X }
- X
- X /* unlock */
- X close(lfd);
- X (void) unlink(lockfile);
- X close(fd);
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xvoid
- XgameOver()
- X{
- X banner(MSG_END);
- X XFlush(display);
- X addScore();
- X showScores(SHOWSCORES);
- X XCloseDisplay(display);
- X exit(0);
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xvoid
- XshowScores(num)
- X int num;
- X{
- X int fd, i = 0;
- X score_t curs;
- X
- X if ((fd = open(SCOREFILE, O_RDONLY, 0644)) < 0)
- X return;
- X
- X (void) fprintf(stderr, " GENERIC TETRIS HALL OF FAME\n\n");
- X (void) fprintf(stderr,
- X " # USER SCORE L R HOST DATE\n");
- X
- X while (read(fd, (char *) &curs, SCORESIZE) == SCORESIZE) {
- X i++;
- X if ((num == 0) || (i <= num))
- X (void) fprintf(stderr, "%4d %-12s%9s %3s %4s %-12s %-s",
- X i, curs.myname, curs.score, curs.level, curs.rows,
- X curs.myhost, curs.mydate);
- X }
- X close(fd);
- X (void) fprintf(stderr, "There are %d scores to date.\n", i);
- X}
- X
- X/* ------------------------------------------------------------------ */
- END_OF_FILE
- if test 9187 -ne `wc -c <'playing.c'`; then
- echo shar: \"'playing.c'\" unpacked with wrong size!
- fi
- # end of 'playing.c'
- fi
- if test -f 'tetris.c' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'tetris.c'\"
- else
- echo shar: Extracting \"'tetris.c'\" \(11770 characters\)
- sed "s/^X//" >'tetris.c' <<'END_OF_FILE'
- X/*
- X# GENERIC X-WINDOW-BASED TETRIS
- X#
- X# tetris.c
- X#
- X###
- X#
- X# Copyright (C) 1992, 1993 Qiang Alex Zhao, azhao@cs.arizona.edu
- X# Computer Science Dept, University of Arizona
- X#
- X# All Rights Reserved
- X#
- X# Permission to use, copy, modify, and distribute this software and
- X# its documentation for any purpose and without fee is hereby granted,
- X# provided that the above copyright notice appear in all copies and
- X# that both that copyright notice and this permission notice appear in
- X# supporting documentation, and that the name of the author not be
- X# used in advertising or publicity pertaining to distribution of the
- X# software without specific, written prior permission.
- X#
- X# This program is distributed in the hope that it will be "playable",
- X# but WITHOUT ANY WARRANTY; without even the implied warranty of
- X# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- X#
- X*/
- X
- X#include "tetris.h"
- X
- X/*** variables ***/
- X
- Xchar myDisplayName[256];
- XDisplay *display;
- Xint screen_num;
- XVisual *visual;
- XBool useColor = True;
- XColormap colormap;
- XWindow mainWin, blockWin;
- XCursor theCursor;
- XXFontStruct *bigFont, *tinyFont;
- Xunsigned long fg, bg;
- X
- XXSizeHints sizehints = {
- X PMinSize | PMaxSize | PPosition | PSize | USSize,
- X 0, 0, /* x, y */
- X 0, 0, /* w, h */
- X 0, 0, /* min w, min h */
- X 0, 0, /* max w, max h */
- X 0, 0, /* inc, not set */
- X 0, 0, 0, 0 /* aspect ratio, not set */
- X};
- XXSizeHints iconsizehints = {
- X PPosition | PSize,
- X 0, 0, /* x, y */
- X 48, 48, /* w, h */
- X 0, 0, /* min w, min h */
- X 0, 0, /* max w, max h */
- X 0, 0, /* inc, not set */
- X 0, 0, 0, 0 /* aspect ratio, not set */
- X};
- XXWMHints wmhints = {
- X InputHint | StateHint | IconPixmapHint,
- X True, /* input mode */
- X NormalState, /* normal */
- X 0, /* icon pixmap */
- X 0, /* icon window */
- X 0, 0, /* icon position */
- X 0 /* icon mask pixmap - not used */
- X};
- X
- Xchar myHome[FILENAMELEN];
- Xint level = 3, prefilled = 0, score = 0, rows = 0;
- XBool showNext = False, beep = False;
- Xscore_t myscore;
- X
- Xstatic int opTableEntries = 15;
- Xstatic XrmOptionDescRec opTable[] = {
- X {"-s", ".scoresOnly", XrmoptionIsArg, (caddr_t) NULL},
- X {"-l", "*startLevel", XrmoptionSepArg, (caddr_t) NULL},
- X {"-p", "*preFilledLines", XrmoptionSepArg, (caddr_t) NULL},
- X {"-showNext", "*showNext", XrmoptionNoArg, (caddr_t) "on"},
- X {"-beep", "*beep", XrmoptionNoArg, (caddr_t) "on"},
- X {"-display", ".display", XrmoptionSepArg, (caddr_t) NULL},
- X {"-geometry", "*geometry", XrmoptionSepArg, (caddr_t) NULL},
- X {"-iconGeometry", "*iconGeometry", XrmoptionSepArg, (caddr_t) NULL},
- X {"-background", "*background", XrmoptionSepArg, (caddr_t) NULL},
- X {"-bg", "*background", XrmoptionSepArg, (caddr_t) NULL},
- X {"-foreground", "*foreground", XrmoptionSepArg, (caddr_t) NULL},
- X {"-fg", "*foreground", XrmoptionSepArg, (caddr_t) NULL},
- X {"-bigFont", "*bigFont", XrmoptionSepArg, (caddr_t) NULL},
- X {"-tinyFont", "*tinyFont", XrmoptionSepArg, (caddr_t) NULL},
- X {"-xrm", NULL, XrmoptionResArg, (caddr_t) NULL}
- X};
- Xstatic XrmDatabase cmmDB = (XrmDatabase) NULL, rDB = (XrmDatabase) NULL;
- X
- Xstatic void parseOpenDisp();
- Xstatic void Usage();
- Xstatic void getDefaults();
- X
- X/* ------------------------------------------------------------------ */
- X
- Xvoid
- Xmain(argc, argv)
- X int argc;
- X char *argv[];
- X{
- X (void) fprintf(stderr,
- X " GENERIC TETRIS V2.0.1\n");
- X (void) fprintf(stderr,
- X "Copyright (C) 1992-93 Q. Alex Zhao, azhao@cs.arizona.edu\n");
- X (void) fprintf(stderr,
- X " Computer Science Dept, University of Arizona\n\n");
- X (void) fprintf(stderr,
- X "GENERIC TETRIS comes with ABSOLUTELY NO WARRANTY.\n\n");
- X
- X parseOpenDisp(&argc, argv);
- X getDefaults();
- X inits(argc, argv);
- X playing();
- X /* never come to here */
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xstatic void
- XparseOpenDisp(argc, argv)
- X int *argc;
- X char *argv[];
- X{
- X struct passwd *pw;
- X XrmValue value;
- X char *str_type[20];
- X XVisualInfo vtmp, *vinfo;
- X int n = 1;
- X
- X XrmInitialize();
- X
- X myDisplayName[0] = '\0';
- X
- X XrmParseCommand(&cmmDB, opTable, opTableEntries, argv[0], argc, argv);
- X
- X /* check for any arguments left */
- X if (*argc != 1) {
- X Usage(argv[0]);
- X }
- X /* only print out the scores? */
- X if (XrmGetResource(cmmDB, "tetris.scoresOnly", "Tetris.ScoresOnly",
- X str_type, &value) == True) {
- X showScores(0);
- X exit(0);
- X }
- X /* get display now */
- X if (XrmGetResource(cmmDB, "tetris.display", "Tetris.Display",
- X str_type, &value) == True)
- X (void) strncpy(myDisplayName, value.addr, (int) value.size);
- X
- X if (!(display = XOpenDisplay(myDisplayName))) {
- X (void) fprintf(stderr, "%s: Can't open display '%s'\n",
- X argv[0], XDisplayName(myDisplayName));
- X exit(1);
- X }
- X screen_num = DefaultScreen(display);
- X visual = DefaultVisual(display, screen_num);
- X colormap = DefaultColormap(display, screen_num);
- X vtmp.visualid = XVisualIDFromVisual(visual);
- X if ((vinfo = XGetVisualInfo(display, VisualIDMask, &vtmp, &n)) != NULL) {
- X if ((vinfo->class == GrayScale) || (vinfo->class == StaticGray)) {
- X useColor = False;
- X }
- X XFree((unsigned char *) vinfo);
- X } else {
- X useColor = False;
- X }
- X
- X /* setup user information */
- X (void) gethostname(myscore.myhost, NAMELEN);
- X setpwent();
- X pw = getpwuid(getuid());
- X endpwent();
- X if (pw == NULL) { /* impossible? */
- X (void) sprintf(myscore.myname, "%d", getuid());
- X myHome[0] = '.';
- X myHome[1] = '/';
- X myHome[2] = '\0';
- X } else {
- X (void) strncpy(myscore.myname, pw->pw_name, NAMELEN);
- X (void) strncpy(myHome, pw->pw_dir, FILENAMELEN);
- X }
- X myscore.myname[NAMELEN - 1] = '\0';
- X myscore.myhost[NAMELEN - 1] = '\0';
- X myHome[FILENAMELEN - 1] = '\0';
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xstatic void
- XUsage(argv0)
- X char *argv0;
- X{
- X (void) fprintf(stderr,
- X "Usage: %s [-s] [-l <starting level>] [-p <prefilled rows>]\n", argv0);
- X (void) fprintf(stderr,
- X " [-display <display>] [-geometry <geometry>] [-iconGeometry\n");
- X (void) fprintf(stderr,
- X " <icon geometry>] [-fg <foreground>] [-bg <background>]\n");
- X (void) fprintf(stderr,
- X " [-bigFont <font>] [-tinyFont <font>] [-showNext] [-beep]\n");
- X (void) fprintf(stderr,
- X " [-xrm <resource specifications>]\n");
- X
- X exit(1);
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xstatic void
- XgetDefaults()
- X{
- X XrmDatabase homeDB, serverDB, appDB;
- X char filenamebuf[FILENAMELEN];
- X char *filename = &filenamebuf[0];
- X char *env;
- X char *classname = "Tetris";
- X char name[255], geoStr[20], icongeoStr[20];
- X XrmValue value;
- X char *str_type[20];
- X int x, y;
- X unsigned int w, h;
- X long flags;
- X
- X (void) strcpy(name, "/usr/lib/X11/app-defaults/");
- X (void) strcat(name, classname);
- X
- X /* Get application defaults file, if any */
- X appDB = XrmGetFileDatabase(name);
- X (void) XrmMergeDatabases(appDB, &rDB);
- X
- X if (XResourceManagerString(display) != NULL) {
- X serverDB = XrmGetStringDatabase(XResourceManagerString(display));
- X } else {
- X (void) strcpy(filename, myHome);
- X (void) strcat(filename, "/.Xdefaults");
- X serverDB = XrmGetFileDatabase(filename);
- X }
- X XrmMergeDatabases(serverDB, &rDB);
- X
- X if ((env = getenv("XENVIRONMENT")) == NULL) {
- X int len;
- X
- X env = &filenamebuf[0];
- X (void) strcpy(env, myHome);
- X len = strlen(env);
- X (void) gethostname(env + len, FILENAMELEN - len);
- X }
- X homeDB = XrmGetFileDatabase(env);
- X XrmMergeDatabases(homeDB, &rDB);
- X
- X XrmMergeDatabases(cmmDB, &rDB);
- X
- X /* starting levels */
- X
- X if (XrmGetResource(cmmDB, "tetris.startLevel", "Tetris.StartLevel",
- X str_type, &value) == True) {
- X if ((sscanf(value.addr, "%d", &level) <= 0) ||
- X (level < 0) || (level >= NUM_LEVELS)) {
- X (void) fprintf(stderr, "Tetris: Invalid level.\n");
- X exit(1);
- X }
- X }
- X
- X /* prefilled lines */
- X
- X if (XrmGetResource(cmmDB, "tetris.preFilledLines", "Tetris.PreFilledLines",
- X str_type, &value) == True) {
- X if ((sscanf(value.addr, "%d", &prefilled) <= 0) ||
- X (prefilled < 0) || (prefilled >= ROWS - THINGSIZE)) {
- X (void) fprintf(stderr, "Tetris: Invalid prefilled lines.\n");
- X exit(1);
- X }
- X }
- X
- X /* show next */
- X
- X if (XrmGetResource(cmmDB, "tetris.showNext", "Tetris.ShowNext",
- X str_type, &value) == True) {
- X showNext = True;
- X }
- X
- X /* beep */
- X
- X if (XrmGetResource(cmmDB, "tetris.beep", "Tetris.Beep",
- X str_type, &value) == True) {
- X beep = True;
- X }
- X
- X /*** get foreground/background colors ***/
- X
- X if (XrmGetResource(rDB, "tetris.foreground", "Tetris.Foreground",
- X str_type, &value) == True) {
- X (void) strncpy(name, value.addr, (int) value.size);
- X fg = getColor(name);
- X } else
- X fg = BlackPixel(display, screen_num);
- X
- X if (XrmGetResource(rDB, "tetris.background", "Tetris.Background",
- X str_type, &value) == True) {
- X (void) strncpy(name, value.addr, (int) value.size);
- X bg = getColor(name);
- X } else
- X bg = WhitePixel(display, screen_num);
- X
- X if (bg == fg) {
- X bg = WhitePixel(display, screen_num);
- X fg = BlackPixel(display, screen_num);
- X }
- X
- X /*** get geometry info ***/
- X
- X if (XrmGetResource(rDB, "tetris.geometry", "Tetris.Geometry",
- X str_type, &value) == True) {
- X (void) strncpy(geoStr, value.addr, (int) value.size);
- X } else {
- X geoStr[0] = '\0';
- X }
- X
- X flags = XParseGeometry(geoStr, &x, &y, &w, &h);
- X if ((WidthValue | HeightValue) & flags)
- X Usage("tetris");
- X
- X if (XValue & flags) {
- X if (XNegative & flags)
- X x = DisplayWidth(display, screen_num) + x - sizehints.width;
- X sizehints.x = x;
- X }
- X if (YValue & flags) {
- X if (YNegative & flags)
- X y = DisplayHeight(display, screen_num) + y - sizehints.height;
- X sizehints.y = y;
- X }
- X
- X /*** get icon geometry info ***/
- X
- X if (XrmGetResource(rDB, "tetris.iconGeometry", "Tetris.IconGeometry",
- X str_type, &value) == True) {
- X (void) strncpy(icongeoStr, value.addr, (int) value.size);
- X } else {
- X icongeoStr[0] = '\0';
- X }
- X
- X flags = XParseGeometry(icongeoStr, &x, &y, &w, &h);
- X if ((WidthValue | HeightValue) & flags)
- X Usage("tetris");
- X
- X if (XValue & flags) {
- X if (XNegative & flags)
- X x = DisplayWidth(display, screen_num) + x - iconsizehints.width;
- X wmhints.flags |= IconPositionHint;
- X wmhints.icon_x = x;
- X iconsizehints.x = x;
- X }
- X if (YValue & flags) {
- X if (YNegative & flags)
- X y = DisplayHeight(display, screen_num) + y - iconsizehints.height;
- X wmhints.flags |= IconPositionHint;
- X wmhints.icon_y = y;
- X iconsizehints.y = y;
- X }
- X
- X /*** get fonts ***/
- X
- X if (XrmGetResource(rDB, "tetris.bigFont", "tetris.BigFont",
- X str_type, &value) == True) {
- X (void) strncpy(name, value.addr, (int) value.size);
- X } else {
- X (void) strcpy(name, BIGFONT);
- X }
- X if ((bigFont = XLoadQueryFont(display, name)) == NULL) {
- X (void) fprintf(stderr, "Tetris: can't open font '%s'.\n", name);
- X exit(1);
- X }
- X if (XrmGetResource(rDB, "tetris.tinyFont", "tetris.TinyFont",
- X str_type, &value) == True) {
- X (void) strncpy(name, value.addr, (int) value.size);
- X } else {
- X (void) strcpy(name, TINYFONT);
- X }
- X if ((tinyFont = XLoadQueryFont(display, name)) == NULL) {
- X (void) fprintf(stderr, "Tetris: can't open font '%s'.\n", name);
- X exit(1);
- X }
- X
- X /*
- X * clean up
- X */
- X XrmDestroyDatabase(rDB);
- X}
- X
- X/* ------------------------------------------------------------------ */
- END_OF_FILE
- if test 11770 -ne `wc -c <'tetris.c'`; then
- echo shar: \"'tetris.c'\" unpacked with wrong size!
- fi
- # end of 'tetris.c'
- fi
- if test -f 'tetris.h' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'tetris.h'\"
- else
- echo shar: Extracting \"'tetris.h'\" \(4561 characters\)
- sed "s/^X//" >'tetris.h' <<'END_OF_FILE'
- X/*
- X# GENERIC X-WINDOW-BASED TETRIS
- X#
- X# tetris.h
- X#
- X###
- X#
- X# Copyright (C) 1992, 1993 Qiang Alex Zhao, azhao@cs.arizona.edu
- X# Computer Science Dept, University of Arizona
- X#
- X# All Rights Reserved
- X#
- X# Permission to use, copy, modify, and distribute this software and
- X# its documentation for any purpose and without fee is hereby granted,
- X# provided that the above copyright notice appear in all copies and
- X# that both that copyright notice and this permission notice appear in
- X# supporting documentation, and that the name of the author not be
- X# used in advertising or publicity pertaining to distribution of the
- X# software without specific, written prior permission.
- X#
- X# This program is distributed in the hope that it will be "playable",
- X# but WITHOUT ANY WARRANTY; without even the implied warranty of
- X# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- X#
- X*/
- X
- X/*** Common headers ***/
- X
- X#include <stdio.h>
- X#include <math.h>
- X#include <pwd.h>
- X#include <errno.h>
- X
- X#include <X11/Xlib.h>
- X#include <X11/Xutil.h>
- X#include <X11/Xresource.h>
- X#include <X11/cursorfont.h>
- X#include <X11/keysym.h>
- X#include <X11/Xos.h>
- X#include <X11/Xfuncs.h>
- X#include <X11/Xfuncproto.h>
- X
- X#ifndef X_NOT_STDC_ENV
- X#include <stdlib.h>
- X#else
- Xextern char *getenv(
- X#if NeedFunctionPrototypes
- X char *
- X#endif
- X);
- X#endif
- X
- X#ifdef X_NOT_POSIX
- Xextern int getuid(
- X#if NeedFunctionPrototypes
- X void
- X#endif
- X);
- Xextern struct passwd *getpwuid(
- X#if NeedFunctionPrototypes
- X int
- X#endif
- X);
- X#endif
- X
- X#ifdef _AIX
- X#include <sys/select.h>
- X#endif
- X
- X/*** for lseek ***/
- X
- X#ifndef SEEK_SET
- X#define SEEK_SET L_SET
- X#endif
- X
- X#ifndef SEEK_CUR
- X#define SEEK_CUR L_INCR
- X#endif
- X
- X#ifndef SEEK_END
- X#define SEEK_END L_XTND
- X#endif
- X
- X/*** random generator ***/
- X
- X#if defined(HAS_48) /* Use lrand48() and srand48() */
- X#define LRAND() lrand48()
- X#define SRAND(X) srand48((long) (X))
- Xextern long lrand48(
- X#if NeedFunctionPrototypes
- X void
- X#endif
- X);
- X
- X#else
- X#if defined(HAS_RANDOM) /* Use random() and srandom() */
- X
- X#define LRAND() random()
- X#define SRAND(X) srandom((unsigned int) (X))
- Xextern long random(
- X#if NeedFunctionPrototypes
- X void
- X#endif
- X);
- X
- X#else /* Use rand() and srand() */
- X
- X#define LRAND() ((long) rand())
- X#define SRAND(X) srand(X)
- X
- X#endif
- X#endif
- X
- X/*** constants ***/
- X
- X#ifndef SCOREFILE
- X#define SCOREFILE "/usr/games/lib/tetris.scores"
- X#endif
- X
- X#define BIGFONT "12x24"
- X#define TINYFONT "6x12"
- X#define BVOLUME -90
- X#define NUM_FLASHES 16
- X
- X#define MILLION 1000000
- X#define MAXSCORES 3
- X#define SHOWSCORES 15
- X#define NAMELEN 12
- X#define FILENAMELEN 1024
- X
- X#define MSG_PAUSED "PAUSED"
- X#define MSG_END "GAME OVER"
- X#define MSG_TITLE "TETRIS"
- X#define MSG_AUTHOR "by Qiang Alex Zhao"
- X
- X#define NUM_LEVELS 18
- X#define ROWS 20
- X#define COLS 10
- X
- X#define BOXSIZE 30
- X#define OFFSET 20
- X#define THINGSIZE 4
- X#define NUM_THINGS 7
- X#define NUM_BITMAPS 15
- X
- X/*** types ***/
- X
- Xtypedef enum {FALL, DROP, ROTATE, LEFT, RIGHT} move_t;
- X
- Xtypedef struct {
- X char myname[NAMELEN], myhost[NAMELEN], mydate[27];
- X char score[10];
- X char level[4];
- X char rows[5];
- X} score_t;
- X#define SCORESIZE sizeof(score_t)
- X
- Xtypedef struct {
- X int map[THINGSIZE][THINGSIZE];
- X int xpos, ypos;
- X int size, px, py;
- X} thing_t;
- X
- X/*** variables defined in "tetris.c" ***/
- X
- Xextern Display *display;
- Xextern int screen_num;
- Xextern Visual *visual;
- Xextern Bool useColor;
- Xextern Colormap colormap;
- Xextern Window mainWin, blockWin;
- Xextern Cursor theCursor;
- Xextern XFontStruct *bigFont, *tinyFont;
- Xextern unsigned long fg, bg;
- X
- Xextern XSizeHints sizehints, iconsizehints;
- Xextern XWMHints wmhints;
- X
- Xextern char myHome[FILENAMELEN];
- Xextern int level, prefilled, score, rows;
- Xextern Bool showNext, beep;
- Xextern score_t myscore;
- X
- X/*** variables defined in "utils.c" ***/
- X
- Xextern Atom delw;
- X
- X/*** variables defined in "playing.c" ***/
- X
- X/*** functions ***/
- X
- Xextern unsigned long getColor();
- Xextern void showScores();
- Xextern void inits();
- Xextern void playing();
- Xextern void realTime();
- Xextern void newThing();
- Xextern Bool evGotNewThing();
- Xextern void redrawAll();
- Xextern void drawTitle();
- Xextern void drawStatus();
- Xextern void drawField();
- Xextern void drawThing();
- Xextern void drawThingDiff();
- Xextern void drawNext();
- Xextern void gameOver();
- Xextern void banner();
- Xextern void clearNext();
- Xextern void putBox();
- Xextern void tryMove();
- Xextern Bool atBottom();
- Xextern Bool overlapping();
- Xextern int checkLines();
- X
- END_OF_FILE
- if test 4561 -ne `wc -c <'tetris.h'`; then
- echo shar: \"'tetris.h'\" unpacked with wrong size!
- fi
- # end of 'tetris.h'
- fi
- if test -f 'utils.c' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'utils.c'\"
- else
- echo shar: Extracting \"'utils.c'\" \(18011 characters\)
- sed "s/^X//" >'utils.c' <<'END_OF_FILE'
- X/*
- X# GENERIC X-WINDOW-BASED TETRIS
- X#
- X# utils.c
- X#
- X###
- X#
- X# Copyright (C) 1992, 1993 Qiang Alex Zhao, azhao@cs.arizona.edu
- X# Computer Science Dept, University of Arizona
- X#
- X# All Rights Reserved
- X#
- X# Permission to use, copy, modify, and distribute this software and
- X# its documentation for any purpose and without fee is hereby granted,
- X# provided that the above copyright notice appear in all copies and
- X# that both that copyright notice and this permission notice appear in
- X# supporting documentation, and that the name of the author not be
- X# used in advertising or publicity pertaining to distribution of the
- X# software without specific, written prior permission.
- X#
- X# This program is distributed in the hope that it will be "playable",
- X# but WITHOUT ANY WARRANTY; without even the implied warranty of
- X# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- X#
- X*/
- X
- X#include "tetris.h"
- X
- X#include "bitmaps/ticon.xbm"
- X#include "bitmaps/rot00.xbm"
- X#include "bitmaps/rot01.xbm"
- X#include "bitmaps/rot02.xbm"
- X#include "bitmaps/rot03.xbm"
- X#include "bitmaps/rot04.xbm"
- X#include "bitmaps/rot05.xbm"
- X#include "bitmaps/rot06.xbm"
- X#include "bitmaps/rot07.xbm"
- X#include "bitmaps/rot08.xbm"
- X#include "bitmaps/rot09.xbm"
- X#include "bitmaps/rot10.xbm"
- X#include "bitmaps/rot11.xbm"
- X#include "bitmaps/rot12.xbm"
- X#include "bitmaps/rot13.xbm"
- X#include "bitmaps/rot14.xbm"
- X
- XAtom delw;
- X
- Xstatic GC revGC, bigGC, tinyGC, xorGC;
- Xstatic GC thingGCs[NUM_THINGS];
- X
- Xstatic char *winName = "GENERIC TETRIS";
- Xstatic char *iconName = "TETRIS";
- X
- Xstatic int titleLen, titleWidth, authorLen, authorWidth;
- Xstatic int titleX, titleY, authorX, authorY;
- Xstatic int sX;
- Xstatic int sLevelY, sRowsY, sScoreY;
- X
- Xstatic int topRWidth, topWidth, topHeight, topMidX, topMidY;
- Xstatic int frameX, frameY, frameW, frameH;
- X
- Xstatic char *bitmap_data[NUM_BITMAPS] = {
- X rot00_bits, rot01_bits, rot02_bits, rot03_bits, rot04_bits, rot05_bits,
- X rot06_bits, rot07_bits, rot08_bits, rot09_bits, rot10_bits, rot11_bits,
- X rot12_bits, rot13_bits, rot14_bits
- X};
- X
- Xstatic thing_t possible[][4] = {
- X {
- X {{{0, 0, 0, 0}, {4, 5, 5, 1}, {0, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 4, 0, 0},
- X {{{0, 2, 0, 0}, {0, 10, 0, 0}, {0, 10, 0, 0}, {0, 8, 0, 0}}, 0, 0, 4, 0, 1},
- X {{{0, 0, 0, 0}, {4, 5, 5, 1}, {0, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 4, 0, 2},
- X {{{0, 2, 0, 0}, {0, 10, 0, 0}, {0, 10, 0, 0}, {0, 8, 0, 0}}, 0, 0, 4, 0, 3}
- X },
- X
- X {
- X {{{0, 2, 0, 0}, {0, 10, 0, 0}, {4, 9, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 1, 0},
- X {{{2, 0, 0, 0}, {12, 5, 1, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 1, 1},
- X {{{6, 1, 0, 0}, {10, 0, 0, 0}, {8, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 1, 2},
- X {{{4, 5, 3, 0}, {0, 0, 8, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 1, 3}
- X },
- X
- X {
- X {{{2, 0, 0, 0}, {10, 0, 0, 0}, {12, 1, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 2, 0},
- X {{{6, 5, 1, 0}, {8, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 2, 1},
- X {{{4, 3, 0, 0}, {0, 10, 0, 0}, {0, 8, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 2, 2},
- X {{{0, 0, 2, 0}, {4, 5, 9, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 2, 3}
- X },
- X
- X {
- X {{{0, 2, 0, 0}, {4, 11, 0, 0}, {0, 8, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 3, 0},
- X {{{0, 2, 0, 0}, {4, 13, 1, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 3, 1},
- X {{{2, 0, 0, 0}, {14, 1, 0, 0}, {8, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 3, 2},
- X {{{4, 7, 1, 0}, {0, 8, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 3, 3}
- X },
- X
- X {
- X {{{2, 0, 0, 0}, {12, 3, 0, 0}, {0, 8, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 4, 0},
- X {{{0, 6, 1, 0}, {4, 9, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 4, 1},
- X {{{2, 0, 0, 0}, {12, 3, 0, 0}, {0, 8, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 4, 2},
- X {{{0, 6, 1, 0}, {4, 9, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 4, 3}
- X },
- X
- X {
- X {{{0, 2, 0, 0}, {6, 9, 0, 0}, {8, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 5, 0},
- X {{{4, 3, 0, 0}, {0, 12, 1, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 5, 1},
- X {{{0, 2, 0, 0}, {6, 9, 0, 0}, {8, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 5, 2},
- X {{{4, 3, 0, 0}, {0, 12, 1, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 3, 5, 3}
- X },
- X
- X {
- X {{{6, 3, 0, 0}, {12, 9, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 2, 6, 0},
- X {{{6, 3, 0, 0}, {12, 9, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 2, 6, 1},
- X {{{6, 3, 0, 0}, {12, 9, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 2, 6, 2},
- X {{{6, 3, 0, 0}, {12, 9, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}}, 0, 0, 2, 6, 3}
- X }
- X};
- X
- Xstatic char *thingFGs[NUM_THINGS] = {
- X "Magenta", "ForestGreen", "Blue", "Red", "DarkTurquoise", "Black", "Brown"
- X};
- X
- Xstatic Pixmap pms[NUM_BITMAPS];
- X
- Xstatic thing_t curThing, nextThing;
- Xstatic struct {
- X int pm_num, cid;
- X} field[ROWS][COLS];
- X
- X/* ------------------------------------------------------------------ */
- X
- Xstatic int
- Xnrand(n)
- X int n;
- X{
- X return (int) (LRAND() % n);
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xunsigned long
- XgetColor(name)
- X char name[];
- X{
- X XColor tmp;
- X
- X if (!useColor) {
- X return BlackPixel(display, screen_num);
- X }
- X if (XParseColor(display, colormap, name, &tmp) == 0) {
- X (void) fprintf(stderr, "Tetris: invalid color '%s'.\n", name);
- X return BlackPixel(display, screen_num);
- X }
- X if (XAllocColor(display, colormap, &tmp) == 0) {
- X (void) fprintf(stderr, "Tetris: can't allocate color '%s'.\n", name);
- X return BlackPixel(display, screen_num);
- X }
- X return tmp.pixel;
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xvoid
- Xinits(argc, argv)
- X int argc;
- X char *argv[];
- X{
- X XSetWindowAttributes att;
- X unsigned int attvm;
- X XTextProperty wName, iName;
- X XClassHint classhints;
- X XEvent ev;
- X XGCValues gcv;
- X unsigned long gcvm;
- X int i, j;
- X
- X SRAND(time(NULL));
- X for (i = 0; i < COLS; i++)
- X for (j = 0; j < ROWS; j++)
- X if ((j >= ROWS - prefilled) && (nrand(2) == 0)) {
- X field[j][i].pm_num = 0;
- X field[j][i].cid = nrand(NUM_THINGS);
- X } else {
- X field[j][i].pm_num = -1;
- X field[j][i].cid = 0;
- X }
- X
- X titleLen = strlen(MSG_TITLE);
- X titleWidth = XTextWidth(bigFont, MSG_TITLE, titleLen);
- X authorLen = strlen(MSG_AUTHOR);
- X authorWidth = XTextWidth(tinyFont, MSG_AUTHOR, authorLen);
- X
- X frameW = BOXSIZE * COLS;
- X frameH = BOXSIZE * ROWS;
- X topRWidth = BOXSIZE * THINGSIZE + OFFSET * 2;
- X topHeight = frameH + OFFSET * 2 + 4;
- X if (titleWidth > topRWidth)
- X topRWidth = titleWidth;
- X if (authorWidth > topRWidth)
- X topRWidth = authorWidth;
- X topMidX = frameW + OFFSET * 2 + 4;
- X topMidY = topHeight / 2 + bigFont->ascent;
- X topWidth = topMidX + topRWidth;
- X frameX = frameY = OFFSET + 2;
- X
- X titleX = (topRWidth - titleWidth) / 2 + topMidX;
- X titleY = OFFSET + 2 + bigFont->ascent;
- X authorX = (topRWidth - authorWidth) / 2 + topMidX;
- X authorY = OFFSET + 2 + bigFont->ascent + bigFont->descent + tinyFont->ascent;
- X
- X sX = topMidX + OFFSET;
- X sScoreY = topHeight - OFFSET - 2 - tinyFont->descent;
- X sRowsY = sScoreY - tinyFont->descent - tinyFont->ascent - 2;
- X sLevelY = sRowsY - tinyFont->descent - tinyFont->ascent - 2;
- X
- X sizehints.width = (sizehints.min_width =
- X (sizehints.max_width = topWidth));
- X sizehints.height = (sizehints.min_height =
- X (sizehints.max_height = topHeight));
- X
- X theCursor = XCreateFontCursor(display, XC_exchange);
- X
- X /* arrow keys */
- X XRebindKeysym(display, XK_R10, NULL, 0,
- X (unsigned char *) "j", sizeof(unsigned char));
- X XRebindKeysym(display, XK_Left, NULL, 0,
- X (unsigned char *) "j", sizeof(unsigned char));
- X XRebindKeysym(display, XK_R11, NULL, 0,
- X (unsigned char *) "k", sizeof(unsigned char));
- X XRebindKeysym(display, XK_R12, NULL, 0,
- X (unsigned char *) "l", sizeof(unsigned char));
- X XRebindKeysym(display, XK_Right, NULL, 0,
- X (unsigned char *) "l", sizeof(unsigned char));
- X
- X /* create windows */
- X attvm = CWBackPixel | CWEventMask | CWDontPropagate | CWCursor;
- X att.background_pixel = bg;
- X att.event_mask = ExposureMask | KeyPressMask |
- X StructureNotifyMask | FocusChangeMask;
- X att.do_not_propagate_mask = KeyReleaseMask |
- X ButtonPressMask | ButtonReleaseMask | PointerMotionMask |
- X ButtonMotionMask | Button1MotionMask | Button2MotionMask |
- X Button3MotionMask | Button4MotionMask | Button5MotionMask;
- X att.cursor = theCursor;
- X
- X mainWin = XCreateWindow(display, DefaultRootWindow(display),
- X sizehints.x, sizehints.y, topWidth, topHeight, 0,
- X CopyFromParent, InputOutput, CopyFromParent, attvm, &att);
- X
- X attvm = CWBackPixel | CWBorderPixel | CWEventMask;
- X att.border_pixel = fg;
- X att.event_mask = ExposureMask;
- X
- X blockWin = XCreateWindow(display, mainWin,
- X frameX-2, frameY-2, frameW, frameH, 2,
- X CopyFromParent, InputOutput, CopyFromParent, attvm, &att);
- X
- X /* WM hints */
- X XStringListToTextProperty(&winName, 1, &wName);
- X XStringListToTextProperty(&iconName, 1, &iName);
- X
- X wmhints.icon_pixmap = XCreateBitmapFromData(display,
- X mainWin, ticon_bits, ticon_width, ticon_height);
- X classhints.res_name = "tetris";
- X classhints.res_class = "Tetris";
- X
- X XSetWMProperties(display, mainWin, &wName, &iName,
- X argv, argc, &sizehints, &wmhints, &classhints);
- X
- X delw = XInternAtom(display, "WM_DELETE_WINDOW", False);
- X XSetWMProtocols(display, mainWin, &delw, 1);
- X
- X /* GC's */
- X
- X gcvm = GCForeground | GCBackground | GCFunction |
- X GCFont | GCGraphicsExposures;
- X
- X gcv.function = GXcopy;
- X gcv.foreground = fg;
- X gcv.background = bg;
- X gcv.font = bigFont->fid;
- X gcv.graphics_exposures = False;
- X bigGC = XCreateGC(display, mainWin, gcvm, &gcv);
- X
- X gcv.font = tinyFont->fid;
- X tinyGC = XCreateGC(display, mainWin, gcvm, &gcv);
- X
- X gcv.foreground = bg;
- X gcv.background = fg;
- X revGC = XCreateGC(display, mainWin, gcvm, &gcv);
- X
- X gcv.background = bg;
- X for (i = 0; i < NUM_THINGS; i++) {
- X gcv.foreground = getColor(thingFGs[i]);
- X if (gcv.foreground == bg)
- X gcv.foreground = fg;
- X thingGCs[i] = XCreateGC(display, blockWin, gcvm, &gcv);
- X }
- X
- X gcv.foreground = fg;
- X gcv.function = GXxor;
- X xorGC = XCreateGC(display, blockWin, gcvm, &gcv);
- X
- X /* pixmaps */
- X
- X for (i = 0; i < NUM_BITMAPS; i++) {
- X pms[i] = (Pixmap) XCreateBitmapFromData(display, blockWin,
- X bitmap_data[i], BOXSIZE, BOXSIZE);
- X }
- X
- X /* new things */
- X newThing();
- X newThing();
- X
- X /* the last thing is to wait for mapped */
- X XMapWindow(display, blockWin);
- X XMapRaised(display, mainWin);
- X XNextEvent(display, &ev);
- X sleep(1);
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xvoid
- XnewThing()
- X{
- X curThing = nextThing;
- X nextThing = possible[nrand(NUM_THINGS)][nrand(4)];
- X nextThing.xpos = nrand(COLS - nextThing.size + 1);
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xvoid
- XdrawTitle()
- X{
- X XDrawString(display, mainWin, bigGC,
- X titleX, titleY, MSG_TITLE, titleLen);
- X XDrawString(display, mainWin, tinyGC,
- X authorX, authorY, MSG_AUTHOR, authorLen);
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xvoid
- XdrawStatus()
- X{
- X char buf[30];
- X
- X (void) sprintf(buf, "Score: %d", score);
- X XDrawImageString(display, mainWin, tinyGC, sX, sScoreY, buf, strlen(buf));
- X
- X (void) sprintf(buf, "Level: %d ", level);
- X XDrawImageString(display, mainWin, tinyGC, sX, sLevelY, buf, strlen(buf));
- X
- X (void) sprintf(buf, "Rows: %d", rows);
- X XDrawImageString(display, mainWin, tinyGC, sX, sRowsY, buf, strlen(buf));
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xstatic void
- XdrawBox(win, pmid, cid, x, y)
- X Window win;
- X int pmid, cid, x, y;
- X{
- X XCopyPlane(display, pms[pmid], win, thingGCs[cid], 0, 0,
- X BOXSIZE, BOXSIZE, x, y, (unsigned long) 1);
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xstatic void
- XclearBox(x, y)
- X int x, y;
- X{
- X XFillRectangle(display, blockWin, revGC, x, y, BOXSIZE, BOXSIZE);
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xvoid
- XdrawField()
- X{
- X int i, j;
- X
- X for (i = 0; i < COLS; i++)
- X for (j = 0; j < ROWS; j++)
- X if (field[j][i].pm_num >= 0)
- X drawBox(blockWin, field[j][i].pm_num, field[j][i].cid,
- X i * BOXSIZE, j * BOXSIZE);
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xvoid
- XdrawThing()
- X{
- X int i, j;
- X
- X for (i = 0; i < curThing.size; i++)
- X for (j = 0; j < curThing.size; j++)
- X if (curThing.map[j][i])
- X drawBox(blockWin, curThing.map[j][i], curThing.px,
- X (curThing.xpos + i) * BOXSIZE,
- X (curThing.ypos + j) * BOXSIZE);
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xvoid
- XdrawThingDiff(old)
- X thing_t *old;
- X{
- X int i, j, ox, oy;
- X
- X for (i = 0; i < curThing.size; i++)
- X for (j = 0; j < curThing.size; j++)
- X if (curThing.map[j][i])
- X drawBox(blockWin, curThing.map[j][i], curThing.px,
- X (curThing.xpos + i) * BOXSIZE,
- X (curThing.ypos + j) * BOXSIZE);
- X
- X for (i = 0; i < curThing.size; i++)
- X for (j = 0; j < curThing.size; j++) {
- X ox = old->xpos + i - curThing.xpos;
- X oy = old->ypos + j - curThing.ypos;
- X if (old->map[j][i] &&
- X ((ox < 0) || (ox >= curThing.size) ||
- X (oy < 0) || (oy >= curThing.size) ||
- X !curThing.map[oy][ox]))
- X clearBox((old->xpos + i) * BOXSIZE, (old->ypos + j) * BOXSIZE);
- X }
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xvoid
- XdrawNext()
- X{
- X int x, y;
- X int i, j;
- X
- X x = topMidX + (topRWidth - nextThing.size * BOXSIZE) / 2;
- X y = topMidY - nextThing.size * BOXSIZE / 2;
- X for (i = 0; i < nextThing.size; i++)
- X for (j = 0; j < nextThing.size; j++)
- X if (nextThing.map[j][i])
- X drawBox(mainWin, nextThing.map[j][i], nextThing.px,
- X x + i * BOXSIZE, y + j * BOXSIZE);
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xvoid
- XclearNext()
- X{
- X XFillRectangle(display, mainWin, revGC,
- X topMidX, topMidY - BOXSIZE * 2, topRWidth, BOXSIZE * 4);
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xvoid
- Xbanner(msg)
- X char msg[];
- X{
- X int mlen = strlen(msg);
- X int w = XTextWidth(bigFont, msg, mlen);
- X int x = (topRWidth - w)/2 + topMidX;
- X
- X XFillRectangle(display, mainWin, revGC,
- X x - 60, topMidY - bigFont->ascent - 5,
- X w + 120, bigFont->ascent + bigFont->descent + 10);
- X XDrawString(display, mainWin, bigGC, x, topMidY, msg, mlen);
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xvoid
- XputBox()
- X{
- X int i, j;
- X int x = curThing.xpos, y = curThing.ypos;
- X
- X for (i = 0; i < curThing.size; i++)
- X for (j = 0; j < curThing.size; j++)
- X if (curThing.map[j][i]) {
- X field[y + j][x + i].pm_num = curThing.map[j][i];
- X field[y + j][x + i].cid = curThing.px;
- X }
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- XBool
- Xoverlapping()
- X{
- X int i, j;
- X int x = curThing.xpos, y = curThing.ypos;
- X
- X for (i = 0; i < curThing.size; i++)
- X for (j = 0; j < curThing.size; j++)
- X if (curThing.map[j][i]) {
- X if ((y + j >= ROWS) || (x + i < 0) || (x + i >= COLS))
- X return True;
- X if (field[y + j][x + i].pm_num >= 0)
- X return True;
- X }
- X
- X return False;
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- XBool
- XatBottom()
- X{
- X int i, j;
- X int x = curThing.xpos, y = curThing.ypos;
- X
- X for (i = 0; i < curThing.size; i++)
- X for (j = 0; j < curThing.size; j++)
- X if (curThing.map[j][i]) {
- X if ((y + j >= ROWS - 1) || (x + i < 0) || (x + i >= COLS))
- X return True;
- X if (field[y + j + 1][x + i].pm_num >= 0)
- X return True;
- X }
- X
- X return False;
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xvoid
- XtryMove(move)
- X move_t move;
- X{
- X thing_t old;
- X
- X old = curThing;
- X
- X switch (move) {
- X case FALL:
- X curThing.ypos ++;
- X break;
- X
- X case DROP:
- X do {
- X curThing.ypos ++;
- X score += level + prefilled;
- X } while (!overlapping());
- X curThing.ypos --;
- X break;
- X
- X case ROTATE:
- X curThing = possible[old.px][(old.py + 3) % 4];
- X curThing.xpos = old.xpos;
- X curThing.ypos = old.ypos;
- X break;
- X
- X case LEFT:
- X curThing.xpos --;
- X break;
- X
- X case RIGHT:
- X curThing.xpos ++;
- X break;
- X }
- X
- X if (!overlapping())
- X drawThingDiff(&old);
- X else
- X curThing = old;
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xint
- XcheckLines()
- X{
- X int lSet[ROWS], nset = 0;
- X int i, j, y;
- X
- X for (j = 0; j < ROWS; j++) {
- X lSet[j] = 0;
- X for (i = 0; i < COLS; i++)
- X if (field[j][i].pm_num >= 0)
- X lSet[j] ++;
- X if (lSet[j] == COLS)
- X nset ++;
- X }
- X
- X if (nset) {
- X for (i = 0; i < ((NUM_FLASHES / nset) % 2) * 2; i ++) {
- X for (j = 0; j < ROWS; j++) {
- X if (lSet[j] == COLS)
- X XFillRectangle(display, blockWin, xorGC,
- X 0, j * BOXSIZE, frameW, BOXSIZE);
- X }
- X XFlush(display);
- X }
- X
- X for (j = ROWS-1; j >= 0; j--) {
- X if (lSet[j] == COLS) {
- X for (y = j; y > 0; y--)
- X for (i = 0; i < COLS; i++)
- X field[y][i] = field[y-1][i];
- X for (i = 0; i < COLS; i++)
- X field[0][i].pm_num = -1;
- X
- X XCopyArea(display, blockWin, blockWin, tinyGC,
- X 0, 0, frameW, j * BOXSIZE, 0, BOXSIZE);
- X
- X XFillRectangle(display, blockWin, revGC,
- X 0, 0, frameW, BOXSIZE);
- X
- X for (i = j; i > 0; i--)
- X lSet[i] = lSet[i-1];
- X lSet[0] = 0;
- X
- X j++;
- X XFlush(display);
- X }
- X }
- X
- X if (beep) XBell(display, BVOLUME);
- X XSync(display, False);
- X }
- X
- X return nset;
- X}
- X
- X/* ------------------------------------------------------------------ */
- X
- Xvoid
- XrealTime(tv)
- X struct timeval *tv;
- X{
- X while (tv->tv_usec < 0) {
- X tv->tv_sec --;
- X tv->tv_usec += MILLION;
- X }
- X while (tv->tv_usec >= MILLION) {
- X tv->tv_sec ++;
- X tv->tv_usec -= MILLION;
- X }
- X}
- X
- X/* ------------------------------------------------------------------ */
- END_OF_FILE
- if test 18011 -ne `wc -c <'utils.c'`; then
- echo shar: \"'utils.c'\" unpacked with wrong size!
- fi
- # end of 'utils.c'
- fi
- echo shar: End of archive 1 \(of 2\).
- cp /dev/null ark1isdone
- MISSING=""
- for I in 1 2 ; do
- if test ! -f ark${I}isdone ; then
- MISSING="${MISSING} ${I}"
- fi
- done
- if test "${MISSING}" = "" ; then
- echo You have unpacked both archives.
- rm -f ark[1-9]isdone
- else
- echo You still need to unpack the following archives:
- echo " " ${MISSING}
- fi
- ## End of shell archive.
- exit 0
-