home *** CD-ROM | disk | FTP | other *** search
Text File | 1997-11-18 | 50.1 KB | 2,063 lines |
- #include "comment.header"
-
- /* $Id: Board.m,v 1.4 1997/11/04 16:49:20 ergo Exp $ */
-
- /*
- * $Log: Board.m,v $
- * Revision 1.4 1997/11/04 16:49:20 ergo
- * ported to OpenStep
- *
- * Revision 1.3 1997/07/06 19:37:55 ergo
- * actual version
- *
- * Revision 1.5 1997/06/03 23:01:55 ergo
- * *** empty log message ***
- *
- * Revision 1.4 1997/05/30 18:44:13 ergo
- * Added an Inspector
- *
- * Revision 1.3 1997/05/04 18:56:50 ergo
- * added time control for moves
- *
- */
-
- #import "Board.h"
- #import "gnugo.h"
- #include "igs.h"
-
- #import <libc.h>
- #import <math.h>
- #import <sys/time.h>
- #import <AppKit/psopsOpenStep.h> // PSxxx functions
- #import <SoundKit/Sound.h>
- #import <AppKit/AppKit.h>
-
- #define EMPTY 0
- #define WHITESTONE 1
- #define BLACKSTONE 2
- #define NEUTRAL_TERR 3
- #define WHITE_TERR 4
- #define BLACK_TERR 5
- #define SPECIAL_CHAR 6
- #define KOMI 5.5
-
- // The following values are the default sizes for the various pieces.
-
- #define RADIUS 14.5 // Stone radius
- #define STONEWIDTH 29.0 // Stone width
- #define STONEHEIGHT 29.0 // Stone height
-
- // SHADOWOFFSET defines the amount the shadow is offset from the piece.
-
- #define SHADOWOFFSET 2.0
-
- #define BASEBOARDX 19.0
- #define BASEBOARDY 19.0
- #define WINDOWOFFSETX 12.0
- #define WINDOWOFFSETY 12.0
-
- #define PSLine(a, b, x, y) PSmoveto(a, b); PSlineto(x, y)
-
- float stoneX, stoneY;
- int blackStones, whiteStones;
- char currentCharacter;
- unsigned char oldBoard[19][19];
-
- void setStoneLoc(int x, int y)
- {
- stoneX = ((19.0 - MAXX)/2.0)*STONEWIDTH + BASEBOARDX - RADIUS + (x*STONEWIDTH);
- stoneY = BASEBOARDY - RADIUS + ((18 - y)*STONEHEIGHT) - ((19.0 - MAXY)/2.0)*STONEHEIGHT;
- }
-
- @implementation GoView
-
- - initWithFrame:(NSRect)frm
- {
- NSSize stoneSize;
-
- stoneSize.width = STONEWIDTH;
- stoneSize.height = STONEHEIGHT;
-
- te = 0;
- startZeit = 0;
-
- [super initWithFrame:frm];
-
- [self allocateGState]; // For faster lock/unlockFocus
-
- [(blackStone = [[NSImage allocWithZone:[self zone]] init]) setScalesWhenResized:NO];
- [blackStone addRepresentation:[[[NSCustomImageRep alloc] initWithDrawSelector:@selector(drawBlackStone:) delegate:self] autorelease]];
- [blackStone setSize:stoneSize];
-
- [(whiteStone = [[NSImage allocWithZone:[self zone]] init]) setScalesWhenResized:NO];
- [whiteStone addRepresentation:[[[NSCustomImageRep alloc] initWithDrawSelector:@selector(drawWhiteStone:) delegate:self] autorelease]];
- [whiteStone setSize:stoneSize];
-
- [(grayStone = [[NSImage allocWithZone:[self zone]] init]) setScalesWhenResized:NO];
- [grayStone addRepresentation:[[[NSCustomImageRep alloc] initWithDrawSelector:@selector(drawGrayStone:) delegate:self] autorelease]];
- [grayStone setSize:stoneSize];
-
- [(upperLeft = [[NSImage allocWithZone:[self zone]] init]) setScalesWhenResized:NO];
- [upperLeft addRepresentation:[[[NSCustomImageRep alloc] initWithDrawSelector:@selector(drawUpperLeft:) delegate:self] autorelease]];
- [upperLeft setSize:stoneSize];
-
- [(upperRight = [[NSImage allocWithZone:[self zone]] init]) setScalesWhenResized:NO];
- [upperRight addRepresentation:[[[NSCustomImageRep alloc] initWithDrawSelector:@selector(drawUpperRight:) delegate:self] autorelease]];
- [upperRight setSize:stoneSize];
-
- [(lowerLeft = [[NSImage allocWithZone:[self zone]] init]) setScalesWhenResized:NO];
- [lowerLeft addRepresentation:[[[NSCustomImageRep alloc] initWithDrawSelector:@selector(drawLowerLeft:) delegate:self] autorelease]];
- [lowerLeft setSize:stoneSize];
-
- [(lowerRight = [[NSImage allocWithZone:[self zone]] init]) setScalesWhenResized:NO];
- [lowerRight addRepresentation:[[[NSCustomImageRep alloc] initWithDrawSelector:@selector(drawLowerRight:) delegate:self] autorelease]];
- [lowerRight setSize:stoneSize];
-
- [(midLeft = [[NSImage allocWithZone:[self zone]] init]) setScalesWhenResized:NO];
- [midLeft addRepresentation:[[[NSCustomImageRep alloc] initWithDrawSelector:@selector(drawMidLeft:) delegate:self] autorelease]];
- [midLeft setSize:stoneSize];
-
- [(midRight = [[NSImage allocWithZone:[self zone]] init]) setScalesWhenResized:NO];
- [midRight addRepresentation:[[[NSCustomImageRep alloc] initWithDrawSelector:@selector(drawMidRight:) delegate:self] autorelease]];
- [midRight setSize:stoneSize];
-
- [(midTop = [[NSImage allocWithZone:[self zone]] init]) setScalesWhenResized:NO];
- [midTop addRepresentation:[[[NSCustomImageRep alloc] initWithDrawSelector:@selector(drawMidTop:) delegate:self] autorelease]];
- [midTop setSize:stoneSize];
-
- [(midBottom = [[NSImage allocWithZone:[self zone]] init]) setScalesWhenResized:NO];
- [midBottom addRepresentation:[[[NSCustomImageRep alloc] initWithDrawSelector:@selector(drawMidBottom:) delegate:self] autorelease]];
- [midBottom setSize:stoneSize];
-
- [(innerSquare = [[NSImage allocWithZone:[self zone]] init]) setScalesWhenResized:NO];
- [innerSquare addRepresentation:[[[NSCustomImageRep alloc] initWithDrawSelector:@selector(drawInnerSquare:) delegate:self] autorelease]];
- [innerSquare setSize:stoneSize];
-
- [(innerHandicap = [[NSImage allocWithZone:[self zone]] init]) setScalesWhenResized:NO];
- [innerHandicap addRepresentation:[[[NSCustomImageRep alloc] initWithDrawSelector:@selector(drawInnerHandicap:) delegate:self] autorelease]];
- [innerHandicap setSize:stoneSize];
-
- [self setBackgroundFile:[[[NSUserDefaults standardUserDefaults] objectForKey:@"BackGround"] cString]
- andRemember:NO];
-
- [self startNewGame];
-
- historyFont = [ [NSFont fontWithName:@"Helvetica" size:9.0] retain];
- blackTerrFont = [ [NSFont fontWithName:@"Helvetica" size:25.0] retain];
- whiteTerrFont = [ [NSFont fontWithName:@"Helvetica" size:22.5] retain];
- #warning
- stoneClick = [Sound findSoundFor:@"Pop"];
-
- {
- struct timeval tp;
- struct timezone tzp;
- gettimeofday(&tp, &tzp);
- time = tp.tv_sec;
- }
- return self;
- }
-
- // free simply gets rid of everything we created for MainGoView, including
- // the instance of MainGoView itself. This is how nice objects clean up.
-
- - (void)dealloc {
- [backGround release];
- { [super dealloc]; return; };
- }
-
-
-
- // This methods allows changing the file used to paint the background of the
- // playing field. Set fileName to NULL to revert to the default. Set
- // remember to YES if you wish the write the value out in the defaults.
-
- - setBackgroundFile:(const char *)fileName andRemember:(BOOL)remember {
- [backGround release];
- if (fileName) {
- backGround = [NSImage alloc];
- [backGround initWithContentsOfFile:[NSString stringWithCString:fileName]];
- [backGround setSize:[self bounds].size];
- if (remember)
- [[NSUserDefaults standardUserDefaults] setObject:[NSString stringWithCString:fileName] forKey:@"Background"];
- } else {
- backGround = [ [NSImage imageNamed:@"Background.tiff"] retain];
- [backGround setSize:[self bounds].size];
- if (remember)
- [[NSUserDefaults standardUserDefaults] removeObjectForKey:@"Background"];
- }
- [backGround setBackgroundColor:[NSColor whiteColor]];
- [backGround setScalesWhenResized:NO];
- [self display];
-
- return self;
- }
-
- // The following two methods allow changing the background image from
- // menu items or buttons.
-
- - changeBackground:sender {
-
- NSString *fileType1 = @"tiff",
- *fileType2 = @"eps";
-
- id fileTypes = [NSArray arrayWithObjects:fileType1, fileType2, nil];
-
- if ([[NSOpenPanel new] runModalForTypes:fileTypes]) {
- [self setBackgroundFile:[[[NSOpenPanel new] filename] cString] andRemember:YES];
- [self display];
- }
-
- return self;
- }
-
- - revertBackground:sender
- {
- [self setBackgroundFile:NULL andRemember:YES];
- [self display];
- return self;
- }
-
- - resetButtons
- {
- if (SmartGoGameFlag)
- {
- [startButton setEnabled:NO];
- [stopButton setEnabled:NO];
- [passButton setEnabled:NO];
-
- return self;
- }
-
- if (bothSides)
- [passButton setEnabled:NO];
- else
- [passButton setEnabled:YES];
-
- if (neitherSide)
- {
- [startButton setEnabled:NO];
- [stopButton setEnabled:NO];
- }
- else
- {
- [startButton setEnabled:YES];
- [stopButton setEnabled:YES];
- }
-
- return self;
- }
-
- // The following method will initialize all the variables for a new game.
-
- - startNewGame {
-
- int i, j;
-
- gameRunning = NO;
- finished = NO;
- gameScored = NO;
- resultsDisplayed = NO;
- scoringGame = NO;
- lastMove = 0;
- blackCaptured = whiteCaptured = 0;
- manualScoring = manScoreTemp;
-
- seed(&rd);
-
- for (i = 0; i < MAXX; i++)
- for (j = 0; j < MAXY; j++)
- oldBoard[i][j] = p[i][j] = hist[i][j] = 0;
-
- for (i = 0; i < 9; i++)
- opn[i] = 1;
- opn[4] = 0;
-
-
- if (gameType == LOCAL) {
- sethand(handicap);
- currentStone = (handicap == 0)?BLACKSTONE:WHITESTONE;
- opposingStone = (currentStone == BLACKSTONE)?WHITESTONE:BLACKSTONE;
-
- if (currentStone == BLACKSTONE)
- [gameMessage setStringValue:@"Black's Turn"];
- else
- [gameMessage setStringValue:@"White's Turn"];
-
- [self resetButtons];
-
- if (((currentStone == BLACKSTONE) && blackSide) ||
- ((currentStone == WHITESTONE) && whiteSide))
- [gameMessage2 setStringValue:@"Press START to begin..."];
- else
- [gameMessage2 setStringValue:@"You move first..."];
- }
- else {
- [gameMessage2 setStringValue:@"Internet Go Server"];
- [gameMessage setStringValue:@""];
- [self setblacksPrisoners:0];
- [self setwhitesPrisoners:0];
- [passButton setEnabled:YES];
- [startButton setEnabled:NO];
- [stopButton setEnabled:NO];
- [self removeTE];
- {
- struct timeval tp;
- struct timezone tzp;
- gettimeofday(&tp, &tzp);
- time = tp.tv_sec;
- }
- }
-
- [ScoringWindow close];
- PSWait();
-
- return self;
- }
-
- // The stop method will pause a running game. The go method will start it up
- // again.
-
- - go:sender
- {
- if (gameType == IGSGAME)
- return self;
-
- if ((scoringGame) && (manualScoring))
- {
- int i, j;
-
- find_owner();
- blackTerritory = 0;
- whiteTerritory = 0;
-
- for (i = 0; i < MAXX; i++)
- for (j = 0; j < MAXY; j++)
- {
- if (ownermat[i][j] == BLACKSTONE)
- {
- blackTerritory++;
- p[i][j] = BLACK_TERR;
- }
- if (ownermat[i][j] == WHITESTONE)
- {
- whiteTerritory++;
- p[i][j] = WHITE_TERR;
- }
- if (ownermat[i][j] == NEUTRAL_TERR)
- {
- p[i][j] = NEUTRAL_TERR;
- }
- }
-
- gameScored = YES;
- [self displayScoringInfo];
- PSWait();
- }
-
- if ((gameRunning == 0) && (finished == 0)) {
- gameRunning = YES;
- [self step];
- }
- return 0;
- }
-
- - (void)stop:(id)sender {
- if (gameType == IGSGAME)
- return;
-
- if (gameRunning)
- gameRunning = NO;
- }
-
- - showLastMove:sender
- {
- int i;
-
- if (SmartGoGameFlag)
- return self;
-
- if (finished)
- {
- NSRunAlertPanel(@"NeXTGo", @"The game has concluded. The last move was\n\
- the scoring.", @"OK", nil, nil);
-
- return self;
- }
-
- if (lastMove == 0)
- {
- NSRunAlertPanel(@"NeXTGo", @"The game has not yet started.", @"OK", nil, nil);
-
- return self;
- }
-
- for (i = 0; i < gameMoves[lastMove-1].numchanges; i++)
- {
- if (gameMoves[lastMove-1].changes[i].x < 0)
- {
- NSRunAlertPanel(@"NeXTGo", @"The last move was a pass.", @"OK", nil, nil);
-
- return self;
- }
- }
-
- [self lockFocus];
- for (i = 0; i < gameMoves[lastMove-1].numchanges; i++)
- {
- if (gameMoves[lastMove-1].changes[i].added)
- {
- setStoneLoc(gameMoves[lastMove-1].changes[i].x,
- gameMoves[lastMove-1].changes[i].y);
- [self showGrayStone];
- }
- }
- [self unlockFocus];
- PSWait();
-
- [self lockFocus];
- [[self window] flushWindow];
- [self drawRect:[self bounds]];
- [self display];
- [self unlockFocus];
- PSWait();
-
- return self;
- }
-
- - undo
- {
- int i, j, x, y;
-
- if (finished)
- return self;
-
- if (lastMove == 1)
- {
- [self startNewGame];
- [self display];
-
- return self;
- }
-
- if (lastMove > 0)
- {
- lastMove--;
-
- for (i = 0; i < MAXX; i++)
- for (j = 0; j < MAXY; j++)
- p[i][j] = oldBoard[i][j];
- blackCaptured = gameMoves[lastMove].blackCaptured;
- whiteCaptured = gameMoves[lastMove].whiteCaptured;
-
- for (i = 0; i < gameMoves[lastMove-1].numchanges; i++)
- {
- x = gameMoves[lastMove-1].changes[i].x;
- y = gameMoves[lastMove-1].changes[i].y;
- if (gameMoves[lastMove-1].changes[i].added)
- {
- oldBoard[x][y] = EMPTY;
- }
- else
- {
- oldBoard[x][y] = gameMoves[lastMove-1].changes[i].color;
- }
- }
- [self refreshIO];
-
- currentStone = opposingStone;
- opposingStone = (currentStone == BLACKSTONE)?WHITESTONE:BLACKSTONE;
-
- if (gameType == LOCAL)
- {
- [gameMessage setStringValue:(currentStone == BLACKSTONE) ? @"Black's Turn" : @"White's Turn"];
-
- if ((bothSides) || (((currentStone == BLACKSTONE) && (blackSide)) ||
- ((currentStone == WHITESTONE) && (whiteSide))))
- {
- [gameMessage2 setStringValue:@"Press START to continue..."];
- gameRunning = 0;
- }
- else
- [gameMessage2 setStringValue:@"Your move..."];
- }
- }
-
- return self;
- }
-
- - undoLastMove:sender {
- if (SmartGoGameFlag)
- return self;
-
- if (gameType == LOCAL) {
- [self undo];
- }
- else {
- sendstr("undo\n");
- }
-
- return self;
- }
-
- - toggleShowHistFlag:sender {
- [self lockFocus];
- [self display];
- [self unlockFocus];
-
- return self;
- }
-
- - toggleSound:sender {
-
- return self;
- }
-
- - doClick {
- if ([playSounds intValue])
- [stoneClick play];
- PSWait();
-
- return self;
- }
-
- - toggleCoords:sender {
- [self lockFocus];
- [self display];
- [self unlockFocus];
-
- return self;
- }
-
- - (void)mouseDown:(NSEvent *)event
- {
- NSPoint pickedP;
-
- if (gameType == LOCAL) {
- if ((((currentStone == BLACKSTONE) && blackSide) ||
- ((currentStone == WHITESTONE) && whiteSide)) &&
- (!scoringGame) && (!manualScoring))
- return;
-
- if (SmartGoGameFlag)
- return;
-
- if ((!gameRunning) && (!finished))
- gameRunning = YES;
-
- if (!finished) {
- int i, j, x, y;
-
- pickedP = [event locationInWindow];
-
- x = floor((pickedP.x - ((19.0 - MAXX)/2.0)*STONEWIDTH - BASEBOARDX
- - WINDOWOFFSETX + RADIUS)/STONEWIDTH);
- y = 18 - floor((pickedP.y - BASEBOARDY - WINDOWOFFSETY + RADIUS +
- ((19.0 - MAXY)/2.0)*STONEHEIGHT)/STONEHEIGHT);
-
- if (x < 0) x = 0;
- if (x > MAXX - 1) x = MAXX - 1;
- if (y < 0) y = 0;
- if (y > MAXY - 1) y = MAXY - 1;
-
- if ((p[x][y] == 0) && (!suicide(x,y))) {
- for (i = 0; i < MAXX; i++)
- for (j = 0; j < MAXY; j++)
- oldBoard[i][j] = p[i][j];
-
- p[x][y] = currentStone;
- if (currentStone == BLACKSTONE)
- blackPassed = 0;
- else
- whitePassed = 0;
-
- setStoneLoc(x,y);
-
- [self lockFocus];
- switch (p[x][y]) {
- case WHITESTONE:
- [self showWhiteStone];
- break;
- case BLACKSTONE:
- [self showBlackStone];
- break;
- default:
- break;
- }
- [self unlockFocus];
-
- // commented out because of double clicks [self doClick];
-
- [self updateInfo];
-
- [self addMoveToGameMoves: currentStone: x: y];
-
- if ([showHistFlag intValue]) {
- NSRect tmpRect = {{floor(stoneX), floor(stoneY)},
- {floor(STONEWIDTH), floor(STONEHEIGHT)}};
-
- [self lockFocus];
- [self drawRect:tmpRect];
- [self unlockFocus];
- }
-
- if (!neitherSide)
- [self step];
- [self setNeedsDisplay:YES];
- }
- }
- else {
- if ((scoringGame) && (manualScoring) && (!gameScored)) {
- int x, y;
-
- pickedP = [event locationInWindow];
-
- x = floor((pickedP.x - ((19.0 - MAXX)/2.0)*STONEWIDTH - BASEBOARDX
- - WINDOWOFFSETX + RADIUS)/STONEWIDTH);
- y = 18 - floor((pickedP.y - BASEBOARDY - WINDOWOFFSETY + RADIUS +
- ((19.0 - MAXY)/2.0)*STONEHEIGHT)/STONEHEIGHT);
-
- if (x < 0) x = 0;
- if (x > MAXX - 1) x = MAXX - 1;
- if (y < 0) y = 0;
- if (y > MAXY - 1) y = MAXY - 1;
-
- if (p[x][y] != EMPTY) {
- int k, l;
-
- currentStone = p[x][y];
-
- find_pattern_in_board(x, y);
- for (k = 0; k < MAXX; k++)
- for (l = 0; l < MAXY; l++)
- if (patternmat[k][l]) {
- p[k][l] = EMPTY;
- if (currentStone == BLACKSTONE)
- blackCaptured++;
- else
- whiteCaptured++;
- }
-
- [self setblacksPrisoners:blackCaptured];
- [self setwhitesPrisoners:whiteCaptured];
-
- [self setNeedsDisplay:YES];
- }
- }
- }
- }
- else {
- int x, y;
- char s[50], n[50];
- extern int observing, ingame;
-
- if (observing || (ingame == -1)) {
- NSRunAlertPanel(@"IGS Error", @"You cannot make a move unless you are playing.", @"OK", nil, nil); return;
- }
-
- pickedP = [event locationInWindow];
-
- x = floor((pickedP.x - ((19.0 - MAXX)/2.0)*STONEWIDTH - BASEBOARDX -
- WINDOWOFFSETX + RADIUS)/STONEWIDTH);
- y = 18 - floor((pickedP.y - BASEBOARDY - WINDOWOFFSETY + RADIUS +
- ((19.0 - MAXY)/2.0)*STONEHEIGHT)/STONEHEIGHT);
-
- if (x < 0) x = 0;
- if (x > MAXX - 1)
- x = MAXX - 1;
- if (y < 0) y = 0;
- if (y > MAXY - 1)
- y = MAXY - 1;
-
- s[0] = x + 'a';
- if (x > 7)
- s[0] = x + 'b';
- s[1] = 0;
- sprintf(n, "%d", MAXY-y);
- strcat(s, n);
- {
- struct timeval tp;
- struct timezone tzp;
- gettimeofday(&tp, &tzp);
- time = tp.tv_sec - time;
- }
-
- sprintf(n, " %d", ingame);
- strcat(s, n);
-
- sprintf(n, " %ld", time);
- strcat(s, n);
- strcat(s, "\n");
- sendstr(s);
- }
- }
-
-
- - passMove {
- if (gameType == LOCAL) {
- if (((currentStone == BLACKSTONE) && blackSide) ||
- ((currentStone == WHITESTONE) && whiteSide)) {
- return self;
- }
- if (currentStone == BLACKSTONE) {
- blackPassed = 1;
- if (AGAScoring) blackCaptured++;
- }
- else {
- whitePassed = 1;
- if (AGAScoring) whiteCaptured++;
- }
-
- [self updateInfo];
-
- [self addMoveToGameMoves: currentStone: -1: -1];
-
- if ((!neitherSide) && (!finished))
- [self step];
- }
- else {
- sendstr("pass\n");
- }
-
- return self;
- }
-
- - refreshIO {
- [self setblacksPrisoners:blackCaptured];
- [self setwhitesPrisoners:whiteCaptured];
-
- [self lockFocus];
- [[self window] flushWindow];
- [self drawRect:[self bounds]];
- [self display];
- [self unlockFocus];
-
- PSWait();
-
- return self;
- }
-
- - addMoveToGameMoves: (int)color: (int)x: (int)y {
- int i, j, k, numchanges;
-
- numchanges = 0;
- for (i = 0; i < MAXX; i++)
- for (j = 0; j < MAXY; j++)
- if (p[i][j] != oldBoard[i][j])
- numchanges++;
- if (x < 0 || y < 0)
- numchanges++;
- gameMoves[lastMove].numchanges = numchanges;
- gameMoves[lastMove].changes = (struct change *)
- malloc((size_t)sizeof(struct change)*numchanges);
- k = 0;
- if (x < 0 || y < 0) {
- gameMoves[lastMove].changes[0].added = NO;
- gameMoves[lastMove].changes[0].x = x;
- gameMoves[lastMove].changes[0].y = y;
- gameMoves[lastMove].changes[0].color = color;
- k++;
- }
- for (i = 0; i < MAXX; i++)
- for (j = 0; j < MAXY; j++)
- if (p[i][j] != oldBoard[i][j]) {
- gameMoves[lastMove].changes[k].x = i;
- gameMoves[lastMove].changes[k].y = j;
- if (p[i][j] != EMPTY) {
- gameMoves[lastMove].changes[k].added = YES;
- gameMoves[lastMove].changes[k].color = p[i][j];
- }
- else {
- gameMoves[lastMove].changes[k].added = NO;
- gameMoves[lastMove].changes[k].color = oldBoard[i][j];
- }
- k++;
- }
- gameMoves[lastMove].blackCaptured = blackCaptured;
- gameMoves[lastMove].whiteCaptured = whiteCaptured;
-
- lastMove++;
-
- if (x >= 0)
- hist[x][y] = lastMove;
-
- return self;
- }
-
- - makeMove: (int)color: (int)x: (int)y {
- int oldwhitesPrisoners, oldblacksPrisoners, i, j;
-
- currentStone = color;
- opposingStone = (currentStone == BLACKSTONE)?WHITESTONE:BLACKSTONE;
-
- if ((x >= 0) && (y >= 0)) {
- for (i = 0; i < MAXX; i++)
- for (j = 0; j < MAXX; j++)
- oldBoard[i][j] = p[i][j];
-
- p[x][y] = color;
-
- setStoneLoc(x,y);
-
- [self lockFocus];
- switch (p[x][y]) {
- case WHITESTONE:
- [self showWhiteStone];
- break;
- case BLACKSTONE:
- [self showBlackStone];
- break;
- default:
- break;
- }
- [self unlockFocus];
-
- oldblacksPrisoners = blackCaptured;
- oldwhitesPrisoners = whiteCaptured;
-
- examboard(opposingStone);
-
- [self setblacksPrisoners:blackCaptured];
- [self setwhitesPrisoners:whiteCaptured];
-
- if (((oldblacksPrisoners != blackCaptured) ||
- (oldwhitesPrisoners != whiteCaptured))) {
- [self lockFocus];
- [self display];
- [self unlockFocus];
-
- }
-
- if ([showHistFlag intValue]) {
- NSRect tmpRect = {{floor(stoneX), floor(stoneY)},
- {floor(STONEWIDTH), floor(STONEHEIGHT)}};
-
- [self lockFocus];
- [self drawRect:tmpRect];
- [self display];
- [self unlockFocus];
- }
-
- if (blackPassed) {
- blackPassed = 0;
- [gameMessage2 setStringValue:@""];
- }
-
- if (whitePassed) {
- whitePassed = 0;
- [gameMessage2 setStringValue:@""];
- }
- }
- [self addMoveToGameMoves: color: x: y];
-
- [gameMessage setStringValue:(opposingStone == BLACKSTONE) ? @"Black's Turn" : @"White's Turn"];
-
- if ((-1 == x) && (-1 == y)) { /* opponent has passed */
- if (currentStone == BLACKSTONE) {
- blackPassed = 1;
- [gameMessage2 setStringValue:@"Black has passed."];
- }
- else {
- whitePassed = 1;
- [gameMessage2 setStringValue:@"White has passed."];
- }
- }
- {
- struct timeval tp;
- struct timezone tzp;
- gettimeofday(&tp, &tzp);
- time = tp.tv_sec;
- }
- [self doClick];
- [self setNeedsDisplay:YES];
- return self;
- }
-
- - makeMoveSilent: (int)color: (int)x: (int)y
- {
- int i, j;
-
- if ((x >= 0) && (y >= 0))
- {
- for (i = 0; i < MAXX; i++)
- for (j = 0; j < MAXY; j++)
- oldBoard[i][j] = p[i][j];
-
- p[x][y] = color;
-
- currentStone = color;
- opposingStone = (currentStone == BLACKSTONE)?WHITESTONE:BLACKSTONE;
-
- examboard(opposingStone);
-
- [self addMoveToGameMoves: color: x: y];
- }
-
- return self;
- }
-
- - setTimeAndByo: (int)btime: (int)bbyo: (int)wtime: (int)wbyo {
- #ifdef DEBUG
- printf("setTimeAndByo: BlackTime = %d, BlackByo = %d, WhitTime = %d, Whitebyo = %d\n", btime, bbyo, wtime, wbyo);
- #endif
- if (bTime != -1) {
- if (bTime < 0)
- bTime = 0;
- if (wTime < 0)
- wTime = 0;
- [self removeTE];
- startZeit = 0;
- if (currentStone == WHITESTONE) { /* Black moved */
- ts.byo = bbyo;
- ts.time = btime;
- ts.timeToHandle = blackTime;
- }
- else { /* White moved */
- ts.byo = wbyo;
- ts.time = wtime;
- ts.timeToHandle = whiteTime;
- }
- te = [[NSTimer scheduledTimerWithTimeInterval:0.2 target:self selector:@selector(TEHandler:) userInfo:self repeats:YES] retain];
- bTime = btime;
- bByo = bbyo;
- wTime = wtime;
- wByo = wbyo;
- }
- return self;
- }
-
- - dispTime
- {
- char bltime[25], whtime[25];
-
- sprintf(bltime, "%d:%02d", bTime / 60, bTime % 60);
- if (bByo != -1)
- sprintf(bltime, "%s, %d", bltime, bByo);
- sprintf(whtime, "%d:%02d", wTime / 60, wTime % 60);
- if (wByo != -1)
- sprintf(whtime, "%s, %d", whtime, wByo);
- [blackTime setStringValue:[NSString stringWithCString:bltime]];
- [blackTime display];
- [whiteTime setStringValue:[NSString stringWithCString:whtime]];
- [whiteTime display];
- return self;
- }
-
- - setGameNumber: (int)n
- {
- [IGSGameNumber setIntValue:n];
- [IGSGameNumber display];
-
- return self;
- }
-
- - updateTitle {
- id buf = [ NSString stringWithString:[IGSBlackPlayer stringValue]];
- buf = [buf stringByAppendingString:[NSString stringWithString:@" - "] ];
- buf = [buf stringByAppendingString:[IGSWhitePlayer stringValue]];
- [[self window] setTitle:buf];
-
- return self;
- }
-
- - setWhiteName: (char *)wname {
-
- [IGSWhitePlayer setStringValue:[NSString stringWithCString:wname]];
- [IGSWhitePlayer display];
- [self updateTitle];
-
- return self;
- }
-
- - setBlackName: (char *)bname {
-
- [IGSBlackPlayer setStringValue:[NSString stringWithCString:bname]];
- [IGSBlackPlayer display];
- [self updateTitle];
-
- return self;
- }
-
- - setIGSHandicap: (int)h
- {
- [IGShandicap setIntValue:h];
- [IGShandicap display];
-
- return self;
- }
-
- - setIGSKomi: (char *)k
- {
- [IGSkomi setStringValue:[NSString stringWithCString:k]];
- [IGSkomi display];
-
- return self;
- }
-
- - setByoTime: (int)aByoTime {
- ByoTime = aByoTime;
-
- return self;
- }
-
- - (int) ByoTime {
- return ByoTime;
- }
-
- - updateInfo {
- int oldblacksPrisoners, oldwhitesPrisoners, i, j;
-
- if (finished && gameScored && resultsDisplayed) {
- [startButton setEnabled:NO];
- [stopButton setEnabled:NO];
- [passButton setEnabled:NO];
- return self;
- }
-
- oldblacksPrisoners = blackCaptured;
- oldwhitesPrisoners = whiteCaptured;
-
- examboard(opposingStone);
-
- if (currentStone == BLACKSTONE) {
- opposingStone = BLACKSTONE;
- currentStone = WHITESTONE;
- [gameMessage setStringValue:@"White's Turn"];
- }
- else {
- opposingStone = WHITESTONE;
- currentStone = BLACKSTONE;
- [gameMessage setStringValue:@"Black's Turn"];
- }
-
- [self setblacksPrisoners:blackCaptured];
- [self setwhitesPrisoners:whiteCaptured];
-
- if (((oldblacksPrisoners != blackCaptured) ||
- (oldwhitesPrisoners != whiteCaptured))) {
- [self lockFocus];
- for (i = 0; i < MAXX; i++)
- for (j = 0; j < MAXX; j++)
- if ((oldBoard[i][j] != EMPTY) && (p[i][j] == EMPTY)) {
- setStoneLoc(i, j);
- [self eraseStone];
- [self showBackgroundPiece: i: j];
- }
- [self unlockFocus];
- }
-
- if ([showHistFlag intValue]) {
- NSRect tmpRect = {{floor(stoneX), floor(stoneY)},
- {floor(STONEWIDTH), floor(STONEHEIGHT)}};
-
- [self lockFocus];
- [self drawRect:tmpRect];
- [self display];
- [self unlockFocus];
- }
-
- if ((blackPassed) && (opposingStone == BLACKSTONE))
- [gameMessage2 setStringValue:@"Black has passed."];
-
- if ((whitePassed) && (opposingStone == WHITESTONE))
- [gameMessage2 setStringValue:@"White has passed."];
-
- if ((!blackPassed) && (!whitePassed))
- [gameMessage2 setStringValue:@""];
-
- if ((blackPassed) && (whitePassed) && (!manualScoring) && (!gameScored)) {
- [self lockFocus];
- [[self window] flushWindow];
- [gameMessage setStringValue:@"Scoring Game, Please Wait"];
- [gameMessage2 setStringValue:@"Removing Dead Groups..."];
- [self display];
- [self unlockFocus];
- finished = 1;
- score_game();
- // [self scoreGame];
- manualScoring = 1;
- }
-
- if ((blackPassed) && (whitePassed) && (manualScoring) && (!gameScored)) {
- [self lockFocus];
- [[self window] flushWindow];
- [gameMessage setStringValue:@"Please remove dead groups"];
- [gameMessage2 setStringValue:@"When finished, press Start..."];
- [self display];
- [self unlockFocus];
- [passButton setEnabled:NO];
- [stopButton setEnabled:NO];
- finished = 1;
- scoringGame = YES;
- }
-
- return self;
-
- }
-
- - displayScoringInfo
- {
- char s[35];
- int i, j;
-
- if (gameScored)
- {
- resultsDisplayed = YES;
- if (typeOfScoring == 0)
- {
- black_Score = (float)blackTerritory - (float)blackCaptured;
- white_Score = (float)whiteTerritory - (float)whiteCaptured;
- white_Score += (handicap == 0)?KOMI:0.5;
- [TypeOfScoring setStringValue:@"Japanese Scoring Method"];
- [BlackTerrString setStringValue:@"Territory"];
- [WhiteTerrString setStringValue:@"Territory"];
- [BlackTerrValue setIntValue:blackTerritory];
- [WhiteTerrValue setIntValue:whiteTerritory];
- [BlackPrisonString setStringValue:@"Prisoners"];
- [WhitePrisonString setStringValue:@"Prisoners"];
- [BlackPrisonValue setIntValue:blackCaptured];
- [WhitePrisonValue setIntValue:whiteCaptured];
- [BlackTotalValue setFloatValue:black_Score];
- [WhiteTotalValue setFloatValue:white_Score];
- }
- else
- {
- blackStones = whiteStones = 0;
- for (i = 0; i < MAXX; i++)
- for (j = 0; j < MAXY; j++)
- {
- if (p[i][j] == BLACKSTONE) blackStones++;
- if (p[i][j] == WHITESTONE) whiteStones++;
- }
- black_Score = (float)blackTerritory + (float)blackStones;
- white_Score = (float)whiteTerritory + (float)whiteStones;
- white_Score += (handicap == 0)?KOMI:0.5;
- [TypeOfScoring setStringValue:@"Chinese Scoring Method"];
- [BlackTerrString setStringValue:@"Territory"];
- [WhiteTerrString setStringValue:@"Territory"];
- [BlackTerrValue setIntValue:blackTerritory];
- [WhiteTerrValue setIntValue:whiteTerritory];
- [BlackPrisonString setStringValue:@"Stones"];
- [WhitePrisonString setStringValue:@"Stones"];
- [BlackPrisonValue setIntValue:blackStones];
- [WhitePrisonValue setIntValue:whiteStones];
- [BlackTotalValue setFloatValue:black_Score];
- [WhiteTotalValue setFloatValue:white_Score];
- }
- if (black_Score > white_Score)
- sprintf(s, "Result: Black wins by %3.1f points.", black_Score - white_Score);
- if (white_Score > black_Score)
- sprintf(s, "Result: White wins by %3.1f points.", white_Score - black_Score);
- if (black_Score == white_Score)
- sprintf(s, "Result: The game was a tie.");
- [KomiValue setFloatValue:((handicap == 0)?KOMI:0.5)];
- [GameResult setStringValue:[NSString stringWithCString:s]];
- [ScoringWindow makeKeyAndOrderFront:self];
- [gameMessage setStringValue:@"Game Over"];
- [self lockFocus];
- [self display];
- [self unlockFocus];
- }
-
- return self;
- }
-
- - scoreGame
- {
- int i, j, k, l, changes = 1, num_in_pattern;
-
- for (i = 0; i < MAXX; i++)
- for (j = 0; j < MAXY; j++)
- scoringmat[i][j] = 0;
-
- while (changes)
- {
- changes = 0;
- find_owner();
-
- for (i = 0; i < MAXX; i++)
- for (j = 0; j < MAXY; j++)
- if ((p[i][j] != 0) && (scoringmat[i][j] == 0))
- {
- if (surrounds_territory(i, j))
- {
- find_pattern_in_board(i, j);
-
- for (k = 0; k < MAXX; k++)
- for (l = 0; l < MAXY; l++)
- if (patternmat[k][l])
- scoringmat[k][l] = p[k][l];
- }
- else
- {
- find_pattern_in_board(i, j);
- set_temp_to_p();
- num_in_pattern = 0;
-
- for (k = 0; k < MAXX; k++)
- for (l = 0; l < MAXY; l++)
- if (patternmat[k][l])
- {
- p[k][l] = EMPTY;
- [self flashStone:k:l];
- num_in_pattern++;
- }
-
- find_owner();
-
- if ((ownermat[i][j] != NEUTRAL_TERR) &&
- (ownermat[i][j] != tempmat[i][j]))
- {
- if (tempmat[i][j] == BLACKSTONE)
- blackCaptured += num_in_pattern;
- else
- whiteCaptured += num_in_pattern;
- changes++;
- [self lockFocus];
- [self display];
- [self unlockFocus];
- }
- else
- {
- set_p_to_temp();
- find_owner();
- }
- }
- }
- }
-
- /* blackTerritory = 0;
- whiteTerritory = 0;
-
- [self lockFocus];
- for (i = 0; i < MAXX; i++)
- for (j = 0; j < MAXY; j++)
- {
- if (ownermat[i][j] == BLACKSTONE)
- {
- blackTerritory++;
- p[i][j] = BLACK_TERR;
- }
- if (ownermat[i][j] == WHITESTONE)
- {
- whiteTerritory++;
- p[i][j] = WHITE_TERR;
- }
- if (ownermat[i][j] == NEUTRAL_TERR)
- {
- [self flashStone:i:j];
- p[i][j] = NEUTRAL_TERR;
- }
- }
- [self unlockFocus]; */
-
- return self;
- }
-
- // The following methods draw the pieces.
-
- - drawBlackStone:imageRep
- {
- // PSscale (1.0, 1.0);
-
- // First draw the shadow under the stone.
-
- // PSarc (RADIUS+SHADOWOFFSET/2, RADIUS-SHADOWOFFSET/2,
- // RADIUS-SHADOWOFFSET, 0.0, 360.0);
- // PSsetgray (NX_DKGRAY);
- // if (NXDrawingStatus == NX_DRAWING) {
- // PSsetalpha (0.666);
- // }
- // PSfill ();
- if ([[NSDPSContext currentContext] isDrawingToScreen]) {
- PSsetalpha (1.0);
- }
-
- // Draw the stone.
-
- PSarc (RADIUS, RADIUS,
- RADIUS, 0.0, 360.0);
- PSsetgray (NSBlack);
- PSfill ();
-
- // And the lighter & darker spots on the stone...
-
- PSarcn (RADIUS, RADIUS,
- RADIUS-SHADOWOFFSET-3.0, 170.0, 100.0);
- PSarc (RADIUS, RADIUS,
- RADIUS-SHADOWOFFSET-2.0, 100.0, 170.0);
- PSsetgray (NSDarkGray);
- PSfill ();
- PSarcn (RADIUS, RADIUS,
- RADIUS-SHADOWOFFSET-3.0, 350.0, 280.0);
- PSarc (RADIUS, RADIUS,
- RADIUS-SHADOWOFFSET-2.0, 280.0, 350.0);
- PSsetgray (NSLightGray);
- PSfill ();
-
- return self;
- }
-
- - drawWhiteStone:imageRep
- {
- // PSscale (1.0, 1.0);
-
- // First draw the shadow under the stone.
-
- // PSarc (RADIUS+SHADOWOFFSET/2, RADIUS-SHADOWOFFSET/2,
- // RADIUS-SHADOWOFFSET, 0.0, 360.0);
- // PSsetgray (NX_DKGRAY);
- // if (NXDrawingStatus == NX_DRAWING) {
- // PSsetalpha (0.666);
- // }
- // PSfill ();
- if ([[NSDPSContext currentContext] isDrawingToScreen]) {
- PSsetalpha (1.0);
- }
-
- // Draw the stone.
-
- PSarc (RADIUS, RADIUS,
- RADIUS, 0.0, 360.0);
- PSsetgray (NSWhite);
- PSfill ();
-
- // And the lighter & darker spots on the stone...
-
- PSarcn (RADIUS, RADIUS,
- RADIUS-SHADOWOFFSET-3.0, 170.0, 100.0);
- PSarc (RADIUS, RADIUS,
- RADIUS-SHADOWOFFSET-2.0, 100.0, 170.0);
- PSsetgray (NSLightGray);
- PSfill ();
- PSarcn (RADIUS, RADIUS,
- RADIUS-SHADOWOFFSET-3.0, 350.0, 280.0);
- PSarc (RADIUS, RADIUS,
- RADIUS-SHADOWOFFSET-2.0, 280.0, 350.0);
- PSsetgray (NSDarkGray);
- PSfill ();
-
- return self;
- }
-
- - drawGrayStone:imageRep
- {
- // PSscale (1.0, 1.0);
-
- // First draw the shadow under the stone.
-
- // PSarc (RADIUS+SHADOWOFFSET/2, RADIUS-SHADOWOFFSET/2,
- // RADIUS-SHADOWOFFSET, 0.0, 360.0);
- // PSsetgray (NX_DKGRAY);
- // if (NXDrawingStatus == NX_DRAWING) {
- // PSsetalpha (0.666);
- // }
- // PSfill ();
- if ([[NSDPSContext currentContext] isDrawingToScreen]) {
- PSsetalpha (1.0);
- }
-
- // Draw the stone.
-
- // PSarc (RADIUS-SHADOWOFFSET/2, RADIUS+SHADOWOFFSET/2,
- // RADIUS-SHADOWOFFSET, 0.0, 360.0);
- PSarc (RADIUS, RADIUS,
- RADIUS, 0.0, 360.0);
- PSsetgray (NSDarkGray);
- PSfill ();
-
- // And the lighter & darker spots on the stone...
-
- PSarcn (RADIUS, RADIUS,
- RADIUS-SHADOWOFFSET-3.0, 170.0, 100.0);
- PSarc (RADIUS, RADIUS,
- RADIUS-SHADOWOFFSET-2.0, 100.0, 170.0);
- PSsetgray (NSLightGray);
- PSfill ();
- PSarcn (RADIUS, RADIUS,
- RADIUS-SHADOWOFFSET-3.0, 350.0, 280.0);
- PSarc (RADIUS, RADIUS,
- RADIUS-SHADOWOFFSET-2.0, 280.0, 350.0);
- PSsetgray (NSWhite);
- PSfill ();
-
- return self;
- }
-
- - drawUpperLeft:imageRep
- {
- PSsetgray(NSBlack);
- PSsetlinewidth(0.0);
- if ([[NSDPSContext currentContext] isDrawingToScreen]) {
- PSsetalpha (1.0);
- }
-
- PSnewpath();
- PSmoveto(RADIUS, RADIUS);
- PSlineto([self bounds].size.width,RADIUS);
- PSmoveto(RADIUS, RADIUS);
- PSlineto(RADIUS, 0.0);
- PSmoveto(RADIUS-SHADOWOFFSET, RADIUS+SHADOWOFFSET);
- PSlineto([self bounds].size.width, RADIUS+SHADOWOFFSET);
- PSmoveto(RADIUS-SHADOWOFFSET, RADIUS+SHADOWOFFSET);
- PSlineto(RADIUS-SHADOWOFFSET, 0.0);
- PSstroke();
-
- return self;
- }
-
- - drawUpperRight:imageRep
- {
- PSsetgray(NSBlack);
- PSsetlinewidth(0.0);
- if ([[NSDPSContext currentContext] isDrawingToScreen]) {
- PSsetalpha (1.0);
- }
-
- PSnewpath();
- PSmoveto(RADIUS, RADIUS);
- PSlineto(0.0,RADIUS);
- PSmoveto(RADIUS, RADIUS);
- PSlineto(RADIUS, 0.0);
- PSmoveto(RADIUS+SHADOWOFFSET, RADIUS+SHADOWOFFSET);
- PSlineto(0.0, RADIUS+SHADOWOFFSET);
- PSmoveto(RADIUS+SHADOWOFFSET, RADIUS+SHADOWOFFSET);
- PSlineto(RADIUS+SHADOWOFFSET, 0.0);
- PSstroke();
-
- return self;
- }
-
- - drawLowerLeft:imageRep
- {
- PSsetgray(NSBlack);
- PSsetlinewidth(0.0);
- if ([[NSDPSContext currentContext] isDrawingToScreen]) {
- PSsetalpha (1.0);
- }
-
- PSnewpath();
- PSmoveto(RADIUS, RADIUS);
- PSlineto([self bounds].size.width,RADIUS);
- PSmoveto(RADIUS, RADIUS);
- PSlineto(RADIUS, [self bounds].size.height);
- PSmoveto(RADIUS-SHADOWOFFSET, RADIUS-SHADOWOFFSET);
- PSlineto([self bounds].size.width, RADIUS-SHADOWOFFSET);
- PSmoveto(RADIUS-SHADOWOFFSET, RADIUS-SHADOWOFFSET);
- PSlineto(RADIUS-SHADOWOFFSET, [self bounds].size.height);
- PSstroke();
-
- return self;
- }
-
- - drawLowerRight:imageRep
- {
- PSsetgray(NSBlack);
- PSsetlinewidth(0.0);
- if ([[NSDPSContext currentContext] isDrawingToScreen]) {
- PSsetalpha (1.0);
- }
-
- PSnewpath();
- PSmoveto(RADIUS, RADIUS);
- PSlineto(0.0,RADIUS);
- PSmoveto(RADIUS, RADIUS);
- PSlineto(RADIUS, [self bounds].size.height);
- PSmoveto(RADIUS+SHADOWOFFSET, RADIUS-SHADOWOFFSET);
- PSlineto(0.0, RADIUS-SHADOWOFFSET);
- PSmoveto(RADIUS+SHADOWOFFSET, RADIUS-SHADOWOFFSET);
- PSlineto(RADIUS+SHADOWOFFSET, [self bounds].size.height);
- PSstroke();
-
- return self;
- }
-
- - drawMidLeft:imageRep
- {
- PSsetgray(NSBlack);
- PSsetlinewidth(0.0);
- if ([[NSDPSContext currentContext] isDrawingToScreen]) {
- PSsetalpha (1.0);
- }
-
- PSnewpath();
- PSmoveto(RADIUS, RADIUS);
- PSlineto([self bounds].size.width,RADIUS);
- PSmoveto(RADIUS, [self bounds].size.height);
- PSlineto(RADIUS, 0.0);
- PSmoveto(RADIUS-SHADOWOFFSET, [self bounds].size.height);
- PSlineto(RADIUS-SHADOWOFFSET, 0.0);
- PSstroke();
-
- return self;
- }
-
- - drawMidRight:imageRep
- {
- PSsetgray(NSBlack);
- PSsetlinewidth(0.0);
- if ([[NSDPSContext currentContext] isDrawingToScreen]) {
- PSsetalpha (1.0);
- }
-
- PSnewpath();
- PSmoveto(RADIUS, RADIUS);
- PSlineto(0.0,RADIUS);
- PSmoveto(RADIUS, [self bounds].size.height);
- PSlineto(RADIUS, 0.0);
- PSmoveto(RADIUS+SHADOWOFFSET, [self bounds].size.height);
- PSlineto(RADIUS+SHADOWOFFSET, 0.0);
- PSstroke();
-
- return self;
- }
-
- - drawMidTop:imageRep
- {
- PSsetgray(NSBlack);
- PSsetlinewidth(0.0);
- if ([[NSDPSContext currentContext] isDrawingToScreen]) {
- PSsetalpha (1.0);
- }
-
- PSnewpath();
- PSmoveto(RADIUS, RADIUS);
- PSlineto(RADIUS,0.0);
- PSmoveto(0.0, RADIUS);
- PSlineto([self bounds].size.width, RADIUS);
- PSmoveto(0.0, RADIUS+SHADOWOFFSET);
- PSlineto([self bounds].size.width, RADIUS+SHADOWOFFSET);
- PSstroke();
-
- return self;
- }
-
- - drawMidBottom:imageRep
- {
- PSsetgray(NSBlack);
- PSsetlinewidth(0.0);
- if ([[NSDPSContext currentContext] isDrawingToScreen]) {
- PSsetalpha (1.0);
- }
-
- PSnewpath();
- PSmoveto(RADIUS, RADIUS);
- PSlineto(RADIUS,[self bounds].size.height);
- PSmoveto(0.0, RADIUS);
- PSlineto([self bounds].size.width, RADIUS);
- PSmoveto(0.0, RADIUS-SHADOWOFFSET);
- PSlineto([self bounds].size.width, RADIUS-SHADOWOFFSET);
- PSstroke();
-
- return self;
- }
-
- - drawInnerSquare:imageRep
- {
- PSsetgray(NSBlack);
- PSsetlinewidth(0.0);
- if ([[NSDPSContext currentContext] isDrawingToScreen]) {
- PSsetalpha (1.0);
- }
-
- PSnewpath();
- PSmoveto(0.0, RADIUS);
- PSlineto([self bounds].size.width,RADIUS);
- PSmoveto(RADIUS, [self bounds].size.height);
- PSlineto(RADIUS, 0.0);
- PSstroke();
-
- return self;
- }
-
- - drawInnerHandicap:imageRep
- {
- PSsetgray(NSBlack);
- PSsetlinewidth(0.0);
- if ([[NSDPSContext currentContext] isDrawingToScreen]) {
- PSsetalpha (1.0);
- }
-
- PSnewpath();
- PSmoveto(0.0, RADIUS);
- PSlineto([self bounds].size.width,RADIUS);
- PSmoveto(RADIUS, [self bounds].size.height);
- PSlineto(RADIUS, 0.0);
- PSstroke();
-
- PSarc(RADIUS, RADIUS, SHADOWOFFSET, 0.0, 360.0);
- PSfill();
-
- return self;
- }
-
- // The following methods show or erase the stones from the board.
-
- - showBlackStone
- {
- NSRect tmpRect = {{floor(stoneX), floor(stoneY)},
- {floor(STONEWIDTH), floor(STONEHEIGHT)}};
- [blackStone compositeToPoint:tmpRect.origin operation:NSCompositeSourceOver];
- return self;
- }
-
- - showWhiteStone
- {
- NSRect tmpRect = {{floor(stoneX), floor(stoneY)},
- {floor(STONEWIDTH), floor(STONEHEIGHT)}};
- [whiteStone compositeToPoint:tmpRect.origin operation:NSCompositeSourceOver];
- return self;
- }
-
- - showGrayStone
- {
- NSRect tmpRect = {{floor(stoneX), floor(stoneY)},
- {floor(STONEWIDTH), floor(STONEHEIGHT)}};
- [grayStone compositeToPoint:tmpRect.origin operation:NSCompositeSourceOver];
- return self;
- }
-
- - eraseStone
- {
- NSRect tmpRect = {{floor(stoneX), floor(stoneY)}, {floor(STONEWIDTH), floor(STONEHEIGHT)}};
- return [self drawBackground:&tmpRect];
- }
-
- // drawBackground: just draws the specified piece of the background by
- // compositing from the background image.
-
- - showBackgroundPiece: (int)x: (int)y {
- int q;
- NSRect tmpRect = {{floor(stoneX), floor(stoneY)}, {floor(STONEWIDTH), floor(STONEHEIGHT)}};
-
- if ((x == 0) && (y == 0))
- [upperLeft compositeToPoint:tmpRect.origin operation:NSCompositeSourceOver];
-
- if ((x == 0) && (y == MAXY - 1))
- [lowerLeft compositeToPoint:tmpRect.origin operation:NSCompositeSourceOver];
-
- if ((x == MAXX - 1) && (y == 0))
- [upperRight compositeToPoint:tmpRect.origin operation:NSCompositeSourceOver];
-
- if ((x == MAXX - 1) && (y == MAXY - 1))
- [lowerRight compositeToPoint:tmpRect.origin operation:NSCompositeSourceOver];
-
- if ((x == 0) && (y > 0) && (y < MAXY - 1))
- [midLeft compositeToPoint:tmpRect.origin operation:NSCompositeSourceOver];
-
- if ((x == MAXX - 1) && (y > 0) && (y < MAXY - 1))
- [midRight compositeToPoint:tmpRect.origin operation:NSCompositeSourceOver];
-
- if ((x > 0) && (x < MAXX - 1) && (y == 0))
- [midTop compositeToPoint:tmpRect.origin operation:NSCompositeSourceOver];
-
- if ((x > 0) && (x < MAXX - 1) && (y == MAXY - 1))
- [midBottom compositeToPoint:tmpRect.origin operation:NSCompositeSourceOver];
-
- if ((x > 0) && (x < MAXX - 1) && (y > 0) && (y < MAXY - 1))
- [innerSquare compositeToPoint:tmpRect.origin operation:NSCompositeSourceOver];
-
- if (MAXX < 13)
- q = 2;
- else
- q = 3;
-
- if (((x == q) && (y == q)) || ((x == q) && (y == MAXY/2)) ||
- ((x == q) && (y == MAXY-q-1)) || ((x == MAXX/2) && (y == q)) ||
- ((x == MAXX/2) && (y == MAXY/2)) || ((x == MAXX/2) && (y == MAXY-q-1)) ||
- ((x == MAXX-q-1) && (y == q)) || ((x == MAXX-q-1) && (y == MAXY/2)) ||
- ((x == MAXX-q-1) && (y == MAXY-q-1)))
- [innerHandicap compositeToPoint:tmpRect.origin operation:NSCompositeSourceOver];
-
- return self;
- }
-
- - drawBackground:(NSRect *)rect
- {
- NSRect tmpRect = *rect;
-
- (&tmpRect)->origin.x = floor(NSMinX(tmpRect));
- (&tmpRect)->origin.y = floor(NSMinY(tmpRect));
- if ([[NSDPSContext currentContext] isDrawingToScreen]) {
- PSsetgray (NSWhite);
- PScompositerect (NSMinX(tmpRect), NSMinY(tmpRect),
- NSWidth(tmpRect), NSHeight(tmpRect), NSCompositeCopy);
- }
- [backGround compositeToPoint:tmpRect.origin fromRect:tmpRect operation:NSCompositeSourceOver];
- return self;
- }
-
- // drawSelf::, a method every decent View should have, redraws the game
- // in its current state. This allows us to print the game very easily.
-
- - (void)drawRect:(NSRect)rects {
- int xcnt, ycnt;
- char s[5], specialChar;
- NSRect aRect = [self bounds];
- [self drawBackground:(&rects ? &rects : &aRect)];
-
- specialChar = 'a';
-
- for (xcnt = 0; xcnt < MAXX; xcnt++)
- {
- for (ycnt = 0; ycnt < MAXY; ycnt++)
- {
- setStoneLoc(xcnt, ycnt);
-
- switch (p[xcnt][ycnt])
- {
- case EMPTY: currentCharacter = 0;
- [self showBackgroundPiece: xcnt: ycnt];
- break;
- case WHITESTONE: [self showWhiteStone];
- if ([showHistFlag intValue])
- {
- char s[5];
-
- [historyFont set];
- PSsetgray(NSBlack);
- PSmoveto(stoneX+RADIUS -
- (floor(log(hist[xcnt][ycnt]+0.5)/log(10))+1.0)*3,
- stoneY+RADIUS - 4);
- if (hist[xcnt][ycnt] > 0)
- {
- sprintf(s, "%d", hist[xcnt][ycnt]);
- PSshow(s);
- }
- else
- {
- PSmoveto(stoneX + RADIUS - 4, stoneY + RADIUS - 4);
- PSshow("H");
- }
- }
- break;
- case BLACKSTONE: [self showBlackStone];
- if ([showHistFlag intValue])
- {
- char s[5];
-
- [historyFont set];
- PSsetgray(NSWhite);
- PSmoveto(stoneX+RADIUS -
- (floor(log(hist[xcnt][ycnt]+0.5)/log(10))+1.0)*3,
- stoneY+RADIUS - 4);
- if (hist[xcnt][ycnt] > 0)
- {
- sprintf(s, "%d", hist[xcnt][ycnt]);
- PSshow(s);
- }
- else
- {
- PSmoveto(stoneX + RADIUS - 4, stoneY + RADIUS - 4);
- PSshow("H");
- }
- }
- break;
- case NEUTRAL_TERR: [self showGrayStone];
- break;
- case WHITE_TERR: [self showBackgroundPiece: xcnt: ycnt];
- [whiteTerrFont set];
- PSsetgray(NSWhite);
- PSmoveto(stoneX+RADIUS/3, stoneY+RADIUS/3+2);
- PSshow("W");
- break;
- case BLACK_TERR: [self showBackgroundPiece: xcnt: ycnt];
- [blackTerrFont set];
- PSsetgray(NSDarkGray);
- PSmoveto(stoneX+RADIUS/3+1, stoneY+RADIUS/3);
- PSshow("B");
- break;
- case SPECIAL_CHAR: [self showBackgroundPiece: xcnt: ycnt];
- PSselectfont("Helvetica", 25.0);
- PSsetgray(NSDarkGray);
- PSmoveto(stoneX+RADIUS/3+1, stoneY+RADIUS/3);
- sprintf(s,"%c",specialChar);
- specialChar++;
- PSshow(s);
- break;
- default: currentCharacter = 0;
- [self showBackgroundPiece: xcnt: ycnt];
- break;
- }
- }
- }
-
- if ([showCoords intValue])
- {
- for (xcnt = 0; xcnt < MAXX; xcnt++)
- {
- setStoneLoc(xcnt, 0);
-
- [historyFont set];
- PSsetgray(NSDarkGray);
- PSmoveto(stoneX + RADIUS - 3, stoneY + RADIUS + 11);
- s[0] = 'A' + xcnt;
- if (xcnt > 7) s[0]++;
- s[1] = 0;
- PSshow(s);
-
- setStoneLoc(xcnt, MAXY - 1);
- PSmoveto(stoneX + RADIUS - 3, stoneY - 3);
- PSshow(s);
- }
- for (ycnt = 0; ycnt < MAXX; ycnt++)
- {
- setStoneLoc(0, ycnt);
-
- [historyFont set];
- PSsetgray(NSDarkGray);
- PSmoveto(stoneX - 4, stoneY + RADIUS - 4);
- sprintf(s, "%d", MAXY-ycnt);
- PSshow(s);
-
- setStoneLoc(MAXX - 1, ycnt);
- if (xcnt < 10)
- {
- PSmoveto(stoneX + STONEWIDTH, stoneY + RADIUS - 4);
- }
- else
- {
- PSmoveto(stoneX + STONEWIDTH - 6, stoneY + RADIUS - 4);
- }
- PSshow(s);
- }
- }
- }
-
- - step {
- // NSEvent *peek_ev, *get_ev;
-
- if (gameType == IGSGAME) {
- return self;
- }
-
- if (neitherSide)
- return self;
-
- if (((currentStone == BLACKSTONE) && !blackSide) ||
- ((currentStone == WHITESTONE) && !whiteSide))
- return self;
-
- if (bothSides) {
- while ((gameRunning) && (!finished)) {
- [self selectMove];
- PSWait();
- /*
- if( peek_ev = [NSApp nextEventMatchingMask:NSLeftMouseDownMask untilDate:[NSDate distantFuture] inMode:NSEventTrackingRunLoopMode dequeue:NO] ){
- get_ev = [ [self window] nextEventMatchingMask:NSLeftMouseDownMask untilDate:[NSDate distantFuture] inMode:NSEventTrackingRunLoopMode dequeue:YES];
- [NSApp sendEvent: get_ev];
- }
- */
- }
-
- PSWait();
- }
- else {
- [passButton setEnabled:NO];
- [self selectMove];
-
- PSWait();
-
- PSWait();
- [passButton setEnabled:YES];
- PSWait();
- }
- return self;
- }
-
- - selectMove {
- int i, j;
-
- PSWait();
-
- if( !bothSides )
- [stopButton setEnabled:NO];
- else
- [stopButton setEnabled:YES];
-
- for (i = 0; i < MAXX; i++)
- for (j = 0; j < MAXY; j++)
- oldBoard[i][j] = p[i][j];
-
- genmove( &i, &j );
- if (i >= 0)
- {
- p[i][j] = currentStone;
-
- [self flashStone: i: j];
- }
-
- if (((i < 0) || (j < 0)) && (AGAScoring))
- {
- if (currentStone == BLACKSTONE)
- blackCaptured++;
- else
- whiteCaptured++;
- }
-
- [self selectMoveEnd];
-
- if (i >= 0)
- {
- [self lockFocus];
- if (currentStone == BLACKSTONE)
- [self showBlackStone];
- else
- [self showWhiteStone];
- [self unlockFocus];
-
- [self doClick];
- }
-
- [self updateInfo];
-
- [self addMoveToGameMoves: currentStone: i: j];
-
- if ([showHistFlag intValue])
- {
- NSRect tmpRect = {{floor(stoneX), floor(stoneY)},
- {floor(STONEWIDTH), floor(STONEHEIGHT)}};
-
- [self lockFocus];
- [self drawRect:tmpRect];
- [self display];
- [self unlockFocus];
- }
-
- PSWait();
- return self;
- }
-
- - selectMoveEnd
- {
- PSWait();
-
- [startButton setEnabled:YES];
- [stopButton setEnabled:YES];
- PSWait();
-
- return self;
- }
-
- - flashStone: (int)x :(int)y
- {
-
- setStoneLoc(x, y);
-
- [self lockFocus];
- [self showGrayStone];
- [self unlockFocus];
-
- return self;
- }
-
- - setMess1:(char *)s
- {
- [gameMessage setStringValue:[NSString stringWithCString:s]];
- [gameMessage display];
-
- return self;
- }
-
- - setMess2:(char *)s
- {
- [gameMessage2 setStringValue:[NSString stringWithCString:s]];
- [gameMessage2 display];
-
- return self;
- }
-
- - setblacksPrisoners:(int)bp
- {
- [blacksPrisoners setIntValue:bp];
- [blacksPrisoners display];
-
- return self;
- }
-
- - setwhitesPrisoners:(int)wp
- {
- [whitesPrisoners setIntValue:wp];
- [whitesPrisoners display];
-
- return self;
- }
-
- - (long)startZeit {
- return startZeit;
- }
-
- - setStartZeit:(long)aTime {
- startZeit = aTime;
- return self;
- }
-
- - (int)bByo {
- return bByo;
- }
-
- - (TimeStruct*)ts {
- return &ts;
- }
-
- - gameCompleted {
-
- [self removeTE];
- [self setblacksPrisoners:0];
- [self setwhitesPrisoners:0];
- [IGSGameNumber setStringValue:@""];
- [IGSBlackPlayer setStringValue:@""];
- [IGSWhitePlayer setStringValue:@""];
- [IGShandicap setStringValue:@""];
- [IGSkomi setStringValue:@""];
- [blackTime setStringValue:@""];
- [whiteTime setStringValue:@""];
-
- return self;
- }
-
- - removeTE {
- if (te) {
- [te invalidate];
- [te release];
- te = 0;
- }
- return self;
- }
-
- - (void) TEHandler:(NSTimer *)aTimer {
- id obj;
- NSString *buf;
- int myTime, now;
- struct timeval tp;
- struct timezone tzp;
- gettimeofday(&tp, &tzp);
- now = tp.tv_sec;
-
- obj = [aTimer userInfo];
-
- if ([obj startZeit] == 0L) {
- [obj setStartZeit:now];
- }
- myTime = ts.time - (now - [obj startZeit]);
- #ifdef TIMEDEBUG
- printf("TEHandler: now = %ld, startZeit = %ld, ts.time = %d, myTime = %d\n", now, [obj startZeit], ts.time, myTime);
- #endif
- if (myTime < 0) {
- if (ts.byo == -1 || /* player is in normal game time */
- ts.byo == 25) { /* player is in byo-yomi but did */
- /* not yet move */
- myTime += [obj ByoTime] * 60;
- ts.byo = 25;
- }
- }
- buf = [NSString stringWithFormat:@"%d:%02d", myTime / 60, myTime % 60];
- if (ts.byo != -1) {
- buf = [buf stringByAppendingFormat:@", %d", ts.byo];
- }
- [ts.timeToHandle setStringValue:buf];
- [ts.timeToHandle display];
- }
-
- @end
-
-