//
//  ThinkAheadGame.m
//  Gridlock
//
//  Created by Brian on 3/26/05.
//  Copyright 2005 __MyCompanyName__. All rights reserved.
//

#import "ThinkAheadGame.h"

static int MOVE_START_VALUE = -10;
static int USED_CELL_VALUE  = -11;

static id valueStrings[] = {
  @"-9", @"-7", @"-6", @"-6", @"-5", @"-5", @"-4", @"-4", @"-4", @"-3", @"-3", @"-3", @"-2", @"-2", @"-2", 
  @"-2", @"-1", @"-1", @"-1", @"-1", @"-1", @"0", @"0", @"0", @"0", @"0", @"1", @"1", @"1", @"1", @"1", @"2", 
  @"2", @"2", @"2", @"2", @"2", @"3", @"3", @"3", @"3", @"3", @"4", @"4", @"4", @"4", @"5", @"5", @"5", @"5", 
  @"6", @"6", @"6", @"7", @"7", @"7", @"8", @"8", @"9", @"9", @"10", @"15", 
  @"-10", @"0"}; // -10 is starting position, last one should eventually be "mystery box"

static NSArray *gGridValues=nil;

static NSArray *gridValues() {
  if (!gGridValues) {
    gGridValues = [[NSArray alloc] initWithObjects:valueStrings count:64];
  }
  return gGridValues;
}

@implementation ThinkAheadGame

-(void)reset {
  [super reset];
  [self setGrid:[DCHypergrid gridWithRows:8 columns:8]];
  
  NSArray *randomValues = [gridValues() arrayWithObjectsInRandomOrder_];
  NSEnumerator *pe = [[self grid] positionEnumerator];
  id pos;
  int index=0;
  while((pos=[pe nextObject])) {
    [self setValue:[[randomValues objectAtIndex:index++] intValue] atPosition:pos];
  }
  p1Score = p2Score = 0;
}

-(NSArray *)allValidMoveSequences {
  id startpos = [[self grid] positionWithValue:MOVE_START_VALUE];
  if (!startpos) return nil;
  NSMutableArray *moves = [NSMutableArray array];
  // player 1 moves horizontally, 2 moves vertically
  if ([self currentPlayerNumber]==1) {
    int r = [startpos row];
    int c;
    for(c=0; c<[self numberOfColumns]; c++) {
      if ([self valueAtRow:r column:c]>MOVE_START_VALUE) {
        [moves addObject:[[DCHypergridPosition positionWithRow:r column:c] arrayWithSelf_]];
      }
    }
  }
  else {
    int c = [startpos column];
    int r;
    for(r=0; r<[self numberOfRows]; r++) {
      if ([self valueAtRow:r column:c]>MOVE_START_VALUE) {
        [moves addObject:[[DCHypergridPosition positionWithRow:r column:c] arrayWithSelf_]];
      }
    }
  }
  return moves;
}

-(BOOL)prepareMoveSequence:(NSArray *)positions {
  if ([positions count]!=1) return NO;
  id movepos  = [positions lastObject];
  id startpos = [[self grid] positionWithValue:MOVE_START_VALUE];
  [self resetFutureGrid];
  [[self futureGrid] setValue:USED_CELL_VALUE atPosition:startpos];
  [[self futureGrid] setValue:MOVE_START_VALUE atPosition:movepos];
  return YES;
}

-(void)updateFromPreparedMove {
  id movepos = [[self futureGrid] positionWithValue:MOVE_START_VALUE];
  if (movepos) {
    int value = [self valueAtPosition:movepos];
    if ([self currentPlayerNumber]==1) p1Score+=value;
    else p2Score+=value;
  }
  [super updateFromPreparedMove];
}


-(BOOL)isGameOver {
  return [[self allValidMoveSequences] count]==0;
}


-(BOOL)showScores {
  return YES;
}

-(int)scoreForPlayer:(int)pnum {
  return (pnum==1) ? p1Score : p2Score;
}

// these methods deal with the score ivars (since they can't be derived from the state of the board)
-(Game *)copy {
  ThinkAheadGame *newGame = (ThinkAheadGame *)[super copy];
  newGame->p1Score = p1Score;
  newGame->p2Score = p2Score;
  return newGame;
}

-(void)copyValuesToGame:(ThinkAheadGame *)newGame {
  [super copyValuesToGame:newGame];
  newGame->p1Score = p1Score;
  newGame->p2Score = p2Score;
}

-(id)propertyList {
  id plist = [super propertyList];
  // assume mutable?
  [plist setObject:[[NSNumber numberWithInt:p1Score] stringValue] forKey:@"p1Score"];
  [plist setObject:[[NSNumber numberWithInt:p2Score] stringValue] forKey:@"p2Score"];
  return plist;
}

-(void)updateFromPropertyList:(id)plist {
  [super updateFromPropertyList:plist];
  p1Score = [[plist objectForKey:@"p1Score"] intValue];
  p2Score = [[plist objectForKey:@"p2Score"] intValue];
}

@end
