/*
 *
 * critique.h -- header file for game critiquer
 *
 * This code is copyright 1995 by James A. Cherry, jac@doe.carleton.ca.
 * It is not to be redistributed or modified without his permission.
 *
 */

/* Type of critique */

typedef enum { CRIT_BOARD, CRIT_LOG2, CRIT_NONE } crit_t;
crit_t CritType;

/* Which dictionary is being used */

typedef enum { CDICT_OSPD, CDICT_DD } dict_t;
dict_t DictFile;

/* Whether batch mode is on */

typedef enum { BATCH_NO, BATCH_YES } batch_t;
batch_t BatchMode;

/* Whether full screen mode is on */

typedef enum { FS_NO, FS_YES } fs_t;
fs_t FullScreen;

/* Whether or not to print dots in single-letter squares */

typedef enum { DOTS_NO, DOTS_YES } dots_t;
dots_t DotsMode;

/* Whether or not to print the number of moves on the queue */
typedef enum { PLL_NO, PLL_YES } pll_t;
pll_t PrintListLen;

/* Which player's output to show in batch mode */
int ShowPlayer[2];

/* Window numbers in full screen mode */

typedef enum { W_BOARD, W_INPUT, W_RACKS, W_MOVES, W_WORDS, W_OUTPUT,
	       W_COUNT } window_t;

WINDOW *Wind[W_COUNT];     /* pointers to curses window structures */
int TRows, TCols;          /* size of terminal window */
int LineSp, NoCr;          /* line spacing and whether to print `\n's */
extern int WinRC[W_COUNT][2], WinYX[W_COUNT][2]; /* window sizes & locs */

char BoardOut[18][40];     /* storage for board */
char TrackOut[4][50];      /* storage for tracking */
char PlrNm[2][20], PlrMove[20];  /* storage for names and move */
char RackOut[2][50];       /* storage for racks */
int TrackWidth;            /* width of tracking display */
int MoveWidth;             /* width of move display */

/* Size of input buffer in full screen mode */

#define IBUF_SIZE 255

/* Types of keyboard modes for full screen mode */

typedef enum { MODE_INPUT, MODE_MOVES, MODE_WORDS } kmode_t;
kmode_t KeyMode;

char InpBuf[IBUF_SIZE];    /* storage for input buffer */
int CrPos, LStart, EBuf;   /* cursor position, start of line, end of buffer */
int Esc;                   /* escape key status */

/* Maximum size of log2 or board */

#define MAX_GRID_SIZE  50

char *Grid[MAX_GRID_SIZE]; /* grid of input lines */
int LNum;                  /* number of lines input */
int MaxL;                  /* max length of move list to be displayed */

char Frv[7];               /* storage for fractional numbers */

/* Max size of list of moves */

#define C_MAXL   20
#define MSTR_LEN 45

char MStr[C_MAXL][MSTR_LEN];  /* storage for move list */
char MHeader[50];          /* move list header */
int MCount, MPages;        /* count of moves, and number of pages of moves */
compmove **PageL;          /* pointer to beginning of each page */
int *RankL;                /* array of ranks */
int MPageNum, MNum;        /* current move page and number */

int PCount, PPages;        /* count of plays, and number of pages of plays */
int PPageNum, PNum;        /* current play page and number */

/* Types of entries in moves window */

typedef enum { MWM_MOVES, MWM_PLAYS } mwm_t;
mwm_t MoveWindowMode;

/* Possible log2 entry errors */

typedef enum { LERR_NONE, LERR_OVERLAP, LERR_NONCONNECT, LERR_BADDUMP } lerr_t;

/* Maximum length of log2 */

#define C_MAXL2  100

int Log2Len;               /* actual length of log2 */
int IndLog2[C_MAXL2];      /* player 0 or 1, for each entry in log2 */
char ExpLog2[C_MAXL2][40]; /* expanded log2 into log format */
lerr_t Log2Err[C_MAXL2];   /* type of error in log2 entry, if any */
int JustDidMM;             /* did we just do an `m' command on a move list? */
int JustDidMP;             /* did we just do an `m' command on a play list? */

/* Stuctures for moves */

/* Types of log2 entries */

typedef enum { LOG2_MOVE, LOG2_FORFEIT, LOG2_PASS, LOG2_EXCHANGE,
	       LOG2_TILES_LEFT, LOG2_TIME_PENALTY } log2_t;

typedef struct {
    int num;                 /* player number */
    char name[20];           /* player name */
    char tiles[7];           /* rack before play is made */
    char tleft[7];           /* rack after play is made */
    int oldscore;            /* current score */
    int turnscore;           /* score for play as calculated by critiquer */
    int newscore;            /* new score as calculated by critiquer */
    int l2oldscore;          /* same as above, only for log2 values */
    int l2turnscore;
    int l2newscore;
    char movels[5];          /* location of move */
    char movews[16];         /* move itself */
    int wordsformed;         /* number of new words made */
    char words[8][16];       /* words themselves */
    int phony[8];            /* 0 for not phony, 1 for phony */
    log2_t etype;            /* LOG2_EXCHANGE, etc. */
    compmove cmove;
} playent;

typedef struct {
    char board[16][16];
    int b1x, b1y, b2x, b2y;
    char plrnm[2][20];
    char plr_tiles[2][7];
    int plr_scores[2];
    int myplrnum;
    int theirplrnum;
} boardent;

typedef union {
    playent *play;
    boardent *board;
} punion;

/* Play structure types */

typedef enum { PTYPE_PLAY, PTYPE_BOARD, PTYPE_FIRST } ptype_t;

typedef struct pe {
    ptype_t ptype;
    punion pptr;
    struct pe *next;        /* pointer to next play */
    struct pe *prev;        /* pointer to previous play */
} pent;

#define PE_SIZE    ( sizeof( playent ) )
#define BE_SIZE    ( sizeof( boardent ) )
#define PENT_SIZE  ( sizeof( pent ) )

pent *PlayHead;      /* head of play list */
pent *PlayTail;      /* tail of play list */
pent *PlayCurr;      /* NOTE: points to one entry _after_ current entry! */

compmove *ThPl;      /* pointer in compmove list to play */
int ThNum;           /* number in list their move is */
playent *PlayTemp;   /* pointer to play after `mr' command */

/* Function prototypes */

/* Library calls */

extern system();
extern endwin();
extern wmove();
extern waddstr();
extern wrefresh();
extern wclear();
extern ioctl();
extern idlok();
extern stty();
extern void bzero();
extern bcopy();
extern select();
extern usleep();

/* critio.c */

void MHeaderLine();
void WHeaderLine();
void CritGridShow();
void InitTerminal();
void ExitTerminal();
void FastExit();
void CursorRefresh();
void OPrint( const char *, ... );
int GetChars();
int ReadLoop();
void LookForStart();
int LookForEnd();
void MakeTileList( int * );
void DispBoard( int );
void PrintMoveList();

/* critbl.c */

pent *GetCurrPtr();
void WalkThruPlayList( pent *, int );
pent *CreateBoardEnt();
void CritiqueBoard();
int CritiqueLog2();

/* critlist.c */

void GenMoveList();
void GenPlayList();
void FreeMoveList();
void ResetPlayList( int );
void ShowMoveList();
void ShowPlayList();

/* critmain.c */

void CommandMPage( int );
void CommandMLine( int );
void CommandM();
void UndoM( int );
void CommandBi( int );

/* critbatch.c */

void RunBatch();
