📄 gammontool.c
字号:
message(ERR, ""); switch (state) { case STARTGAME: message(ERR, "The game hasn't started yet!"); break; case COMPUTERDOUBLING: message(ERR, "You must accept or refuse the computer's double!"); break; case HUMANDOUBLING: message(ERR, "Hold on, the computer is thinking about whether to accept your double!"); break; case ROLL: message(ERR, "You haven't moved yet!"); break; case MOVE: if (movesmade <= 0) message(ERR, "You haven't moved yet!"); else undoonemove(); break; case THINKING: message(ERR, "It's not your turn!"); break; case GAMEOVER: message(ERR, "The game is over!"); break; }}staticredoall_proc(item, event) Panel_item item; struct intputevent *event;{ message(ERR, ""); switch (state) { case STARTGAME: message(ERR, "The game hasn't started yet!"); break; case COMPUTERDOUBLING: message(ERR, "You must accept or refuse the computer's double!"); break; case HUMANDOUBLING: message(ERR, "Hold on, the computer is thinking about whether to accept your double!"); break; case ROLL: message(ERR, "You haven't moved yet!"); break; case MOVE: if (movesmade <= 0) message(ERR, "You haven't moved yet!"); else undowholemove(); break; case THINKING: message(ERR, "It's not your turn!"); break; case GAMEOVER: message(ERR, "The game is over!"); break; }}staticforfeit_proc(item, event) Panel_item item; struct intputevent *event;{ message(ERR, ""); if (state == STARTGAME) { message(ERR, "The game hasn't started yet!"); } else if (state == GAMEOVER) { message(ERR, "The game is over!"); } else if (state == COMPUTERDOUBLING) { win(COMPUTER, REFUSEDDBLE); } else { message(ERR, "Please confirm that you want to forfeit this game with the left button."); if (!cursor_confirm(brdsw->ts_windowfd)) { message(ERR, ""); return; } message(ERR, ""); win(COMPUTER, RESIGNED); }}staticquit_proc(item, event) Panel_item item; struct intputevent *event;{ message(ERR, ""); if (state != GAMEOVER && state != STARTGAME) { message(ERR, "If you want to quit the game you must forfeit first."); return; } quit();}staticnewgame_proc(item, event) Panel_item item; struct intputevent *event;{ message(ERR, ""); if (state == STARTGAME) { message(MSG, "To begin the game, roll the dice by clicking the left or middle buttons."); message(ERR, "(The mouse cursor may be anywhere over the board when rolling the dice.)"); } else if (state != GAMEOVER) { message(ERR, "If you want to restart the game, you must forfeit this one first."); } else { startgammon(); replacepieces(); initpieces(); numhdice = numcdice = 0; drawdice(BOTH, NOFLASH); if (gamevalue != 1) { gamevalue = 1; clearcube(); } lastdoubled = NOBODY; drawcube(); state = STARTGAME; message(MSG, "To begin the game, roll the dice by clicking the left or middle buttons."); message(ERR, "(The mouse cursor may be anywhere over the board when rolling the dice.)"); }}staticnewcolor_proc(item, value, event) Panel_item item; struct inputevent *event;{ int newcolor; message(ERR, ""); if (panel_get_value(item) == 0) newcolor = WHITE; else newcolor = BLACK; if (newcolor != humancolor) { humancolor = newcolor; drawpieces(); }}message(kind, str)int kind;char *str;{ int height = kind * msgfont->pf_defaultsize.y; pw_writebackground(msgwin, 0, height, msgrect.r_width, msgfont->pf_defaultsize.y, PIX_SRC); pw_text(msgwin, 0, height - msgfont->pf_char['n'].pc_home.y, PIX_SRC, msgfont, str); cached_msg[kind] = str;}redisplay_message(){ int c, height; pw_writebackground(msgwin, 0, 0, msgrect.r_width, msgrect.r_height, PIX_SRC); for (c=0, height=0; c < 2; c++, height += msgfont->pf_defaultsize.y) pw_text(msgwin, 0, height - msgfont->pf_char['n'].pc_home.y, PIX_SRC, msgfont, cached_msg[c]);}setcursor(which)int which;{ win_setcursor(brdsw->ts_windowfd, &cursors[which]);}initgame(){ if (logfp != NULL) fprintf(logfp, "New game.\n"); initpieces(); gamevalue = 1; lastdoubled = NOBODY; diddouble = 0; rolldice(BOTH); /* initial roll; doubles not allowed */ while (humandieroll[0] == computerdieroll[0]) rolldice(BOTH); if (humandieroll[0] > computerdieroll[0]) { sendtogammon(HUMANFIRST); message(MSG, "You go first."); dicedisplayed = HUMAN; starthumanturn(); } else { sendtogammon(COMPUTERFIRST); alreadyrolled = 1; message(MSG, "The computer goes first. Thinking..."); state = THINKING; dicedisplayed = COMPUTER; setcursor(THINKING_CUR); }}initpieces(){ int index; for (index = 0; index < 26; index++) humanboard[index] = computerboard[index] = 0; for (index = 0; index < NUMPOINTS; index++) { humanboard[humanpieces[index][0]] = humanpieces[index][1]; computerboard[computerpieces[index][0]] = computerpieces[index][1]; }}rolldice(who)int who;{ int d0, d1; /* save dice currently displayed for show-last-move */ lastroll[0][0] = numhdice; lastroll[0][1] = humandieroll[0]; lastroll[0][2] = humandieroll[1]; lastroll[1][0] = numcdice; lastroll[1][1] = computerdieroll[0]; lastroll[1][2] = computerdieroll[1]; /* generate numbers for new dice */ d0 = random() % 6 + 1; d1 = random() % 6 + 1; /* assign numbers depending on whose turn it is */ switch (who) { case HUMAN: humandieroll[0] = d0; humandieroll[1] = d1; numhdice = 2; numcdice = 0; dicedisplayed = HUMAN; drawdice(COMPUTER, NOFLASH); /* erase computer's dice */ break; case COMPUTER: computerdieroll[0] = d0; computerdieroll[1] = d1; numcdice = 2; numhdice = 0; dicedisplayed = COMPUTER; drawdice(HUMAN, NOFLASH); /* erase human's dice */ break; case BOTH: /* special case for first roll */ humandieroll[0] = d0; humandieroll[1] = d1; computerdieroll[0] = d1; computerdieroll[1] = d0; numhdice = numcdice = 1; break; } drawdice(who, FLASH);}win(who, how)int who, how;{ int points = gamevalue; if (who == HUMAN) { switch (how) { case STRAIGHT: message(MSG, "You beat the computer!"); if (logfp != NULL) fprintf(logfp, "Human won.\n"); break; case GAMMON: message(MSG, "You gammoned the computer!"); points *= 2; if (logfp != NULL) fprintf(logfp, "Human gammoned computer.\n"); break; case BACKGAMMON: message(MSG, "You backgammoned the computer!!!"); points *= 3; if (logfp != NULL) fprintf(logfp, "Human backgammoned computer.\n"); break; case REFUSEDDBLE: message(MSG, "The computer refused your double!"); if (logfp != NULL) fprintf(logfp, "Computer refused double.\n"); break; case RESIGNED: message(MSG, "The computer resigned!"); points *= 3; if (logfp != NULL) fprintf(logfp, "Computer resigned\n"); break; } humanscore += points; drawscore(HUMAN); } else { switch (how) { case STRAIGHT: message(MSG, "The computer beat you!"); if (logfp != NULL) fprintf(logfp, "Computer won.\n"); break; case GAMMON: message(MSG, "The computer gammoned you!"); points *= 2; if (logfp != NULL) fprintf(logfp, "Computer gammoned human.\n"); break; case BACKGAMMON: message(MSG, "The computer backgammoned you!!!"); points *= 3; if (logfp != NULL) fprintf(logfp, "Computer backgammoned human.\n"); break; case REFUSEDDBLE: message(MSG, "The computer wins!"); if (logfp != NULL) fprintf(logfp, "Human refused double.\n"); break; case RESIGNED: message(MSG, "The computer takes triple the stakes!"); points *= 3; if (logfp != NULL) fprintf(logfp, "Human resigned\n"); break; } computerscore += points; drawscore(COMPUTER); } state = GAMEOVER; setcursor(ORIGINAL_CUR); savescore(humanscore, computerscore); if (logfp != NULL) fprintf(logfp, "Score: %d (human), %d (computer)\n", humanscore, computerscore);}movepiece(from, to, who)int from, to, who;{ int color, fromnum, tonum; if (who == HUMAN) { fromnum = humanboard[from]--; tonum = humanboard[to]++; color = humancolor; } else { fromnum = computerboard[from]--; tonum = computerboard[to]++; color = computercolor; } erasepiece(from, color, fromnum); drawpiece(to, color, tonum);}/* * novel type of redisplay when restarting game: moves each piece back * to where it goes rather than erasing and redisplaying the entire board */replacepieces(){ int c, p, pmax, pc, moves[30][5], movcntr = 0, pnt; for (c = 0; c < 26; c++) { pc = pointcount(c, humancolor); if (humanboard[c] > 0 && humanboard[c] > pc) { pmax = humanboard[c] - pc; for (p = 0; p < pmax; p++) { pnt = findapoint(humancolor); moves[movcntr][0] = c; moves[movcntr][1] = pnt; moves[movcntr][2] = humanboard[c]--; moves[movcntr][3] = humanboard[pnt]++; moves[movcntr][4] = humancolor; movcntr++; } } pc = pointcount(c, computercolor); if (computerboard[c] > 0 && computerboard[c] > pc) { pmax = computerboard[c] - pc; for (p = 0; p < pmax; p++) { pnt = findapoint(computercolor); moves[movcntr][0] = c; moves[movcntr][1] = pnt; moves[movcntr][2] = computerboard[c]--; moves[movcntr][3] = computerboard[pnt]++; moves[movcntr][4] = computercolor; movcntr++; } } } /* * we can't use movepiece() because if a white piece on point 1 * must trade with a black piece on point 24, it can't be done * unless both pieces are removed first */ for (c = 0; c < movcntr; c++) erasepiece(moves[c][0], moves[c][4], moves[c][2]); for (c = 0; c < movcntr; c++) drawpiece(moves[c][1], moves[c][4], moves[c][3]);}pointcount(point, color)int point, color;{ int index; for (index = 0; index < NUMPOINTS; index++) { if (color == humancolor) { if (humanpieces[index][0] == point) return(humanpieces[index][1]); } else { if (computerpieces[index][0] == point) return(computerpieces[index][1]); } } return(0);}findapoint(color)int color;{ int index; for (index = 0; index < NUMPOINTS; index++) { if (humancolor == color) { if (humanboard[humanpieces[index][0]] < humanpieces[index][1]) return(humanpieces[index][0]); } else { if (computerboard[computerpieces[index][0]] < computerpieces[index][1]) return(computerpieces[index][0]); } }}/* display the die rolls which were last on the screen *//* a second call to showlastdice redisplays the original dice */showlastdice(){ int currentroll[2][3]; /* save current roll */ currentroll[0][0] = numhdice; currentroll[0][1] = humandieroll[0]; currentroll[0][2] = humandieroll[1]; currentroll[1][0] = numcdice; currentroll[1][1] = computerdieroll[0]; currentroll[1][2] = computerdieroll[1]; /* insert last roll */ numhdice = lastroll[0][0]; humandieroll[0] = lastroll[0][1]; humandieroll[1] = lastroll[0][2]; numcdice = lastroll[1][0]; computerdieroll[0] = lastroll[1][1]; computerdieroll[1] = lastroll[1][2]; /* set up current roll so it can be redisplayed later */ lastroll[0][0] = currentroll[0][0]; lastroll[0][1] = currentroll[0][1]; lastroll[0][2] = currentroll[0][2]; lastroll[1][0] = currentroll[1][0]; lastroll[1][1] = currentroll[1][1]; lastroll[1][2] = currentroll[1][2]; /* display last roll */ drawdice(BOTH, NOFLASH);}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -