Chaos Project

RPG Maker => RPG Maker Scripts => Topic started by: Abigail on May 18, 2014, 08:27:45 pm

Title: [VX/VX Ace] Chess Engine v2
Post by: Abigail on May 18, 2014, 08:27:45 pm
Chess Engine
For RPG Maker VX
by Abigaila

Download Chess.dll (http://www.sendspace.com/file/yq80j5)




What is this?
Spoiler: ShowHide
This is a chess engine for RPG Maker.





How to use? IMPORTANT
Spoiler: ShowHide

1. Download the attached Chess.dll and place it in your game directory. Make sure the name of the file doesn't change. This is the actual engine that does the thinking.

2a. Install the interface script like you would any other script, invoke it by calling Scene_Chess

-- Or --

2b. You can use the chess engine for some other functionality, or make your own interface. Here is a list of commands. (You must have an understanding of Win32API.)

1. Starting position: Win32API.new("Chess.dll", "reset", "", "V")
2. Does a move exist?: Win32API.new("Chess.dll", "move_exists", ['I','I'], "I")
3. Make a move: Win32API.new("Chess.dll", "do_move", ['I','I'], "I")
4. Take back move: Win32API.new("Chess.dll", "undo_move", "", "I")
5. Computer moves: Win32API.new("Chess.dll", "best_move", "", "L")
6. Get piece on given square (or empty): Win32API.new("Chess.dll", "get_square", "I", "I")
7. Get side to move: Win32API.new("Chess.dll", "side_to_move", "", "I")
@console = Win32API.new("Chess.dll", "console", "", "V")







Script (graphical interface)

Put this image in your game folder, name it pieces.png:
(http://.png)
Spoiler: ShowHide

#==============================================================================
# ** Scene_Chess
#------------------------------------------------------------------------------
#  This class performs chess game UI and AI
#==============================================================================

class Scene_Chess < Scene_Base
  #--------------------------------------------------------------------------
  # * Constants
  #--------------------------------------------------------------------------
  WHITE = 0; BLACK = 1;
 
  W_PAWN=0; W_ROOK=1; W_KNIGHT=2; W_BISHOP=3; W_QUEEN=4; W_KING=5;
  B_PAWN=6; B_ROOK=7; B_KNIGHT=8; B_BISHOP=9; B_QUEEN=10; B_KING=11;
  EMPTY = 12;
 
  BOARD_SIZE = 480
  SQ_SIZE = BOARD_SIZE/8
  #--------------------------------------------------------------------------
  # * Start Processing
  #--------------------------------------------------------------------------
  def start
    super
    setup_engine
    setup_graphics
   
    @new_game.call()
    #@console.call()
    refresh
  end
     
  #--------------------------------------------------------------------------
  # * Setup Engine
  #--------------------------------------------------------------------------                     
  def setup_engine
    @new_game = Win32API.new("Chess.dll", "reset", "", "V")
    @move_exists = Win32API.new("Chess.dll", "move_exists", ['I','I'], "I")
    @do_move = Win32API.new("Chess.dll", "do_move", ['I','I'], "I")
    @undo_move = Win32API.new("Chess.dll", "undo_move", "", "I")
    @best_move = Win32API.new("Chess.dll", "best_move", "", "L")
    @get_square = Win32API.new("Chess.dll", "get_square", "I", "I")
    @side_to_move = Win32API.new("Chess.dll", "side_to_move", "", "I")
    @console = Win32API.new("Chess.dll", "console", "", "V")
  end
     
  #--------------------------------------------------------------------------
  # * Setup Graphics
  #--------------------------------------------------------------------------                     
  def setup_graphics
    Graphics.resize_screen(640, 480)
   
    # Cursor
    @cursor = 55
    @cursor_spr = Sprite.new
    @cursor_spr.z = 50
    @cursor_spr.opacity = 200
    @cursor_spr.bitmap = Bitmap.new(SQ_SIZE, SQ_SIZE)
    @cursor_spr.bitmap.fill_rect(0, 0, SQ_SIZE, SQ_SIZE, Color.new(255,255,100))
   
    # From (blue indicating which piece has been selected)
    @from = -1
    @from_spr = Sprite.new
    @from_spr.visible = false
    @from_spr.z = 50
    @from_spr.opacity = 255
    @from_spr.bitmap = Bitmap.new(SQ_SIZE, SQ_SIZE)
    @from_spr.bitmap.fill_rect(0, 0, SQ_SIZE, SQ_SIZE, Color.new(50,100,255))
   
    # Board grid bitmap
    @board_spr = Sprite.new
    @board_spr.bitmap = Bitmap.new(BOARD_SIZE, BOARD_SIZE)
   
    i = 0;
    while(i < 64)
      odd = (i/8+i%8) % 2
      odd = 1 - odd;
     
      x = SQ_SIZE * (i % 8)
      y = SQ_SIZE * (i / 8)
      color = Color.new(100+155*odd, 140+115*odd, 140+115*odd)
     
      @board_spr.bitmap.fill_rect(x, y, SQ_SIZE, SQ_SIZE, color);
      i+=1;
    end
   
    # Pieces bitmap
    @piece_bitmap = Bitmap.new("pieces.png")
   
    # Pieces sprite
    @piece_sprite = Sprite.new()
    @piece_sprite.x = 0; @piece_sprite.y = 0;
    @piece_sprite.z = 100;
    @piece_sprite.bitmap = Bitmap.new(BOARD_SIZE, BOARD_SIZE)
  end
 
 
  #--------------------------------------------------------------------------
  # * Update
  #--------------------------------------------------------------------------
  def update
    super
   
    # Enter pressed
    if(Input.trigger?(Input::C))
      move_is_legal = move_exists?(@from, @cursor)
     
      if(move_is_legal || !square_selectable?)
        if(move_is_legal)
          # Player move
          do_move(@from, @cursor)
          refresh
          Graphics.update
         
          # Computer move
          best_move
          refresh
        else
          @from = -1;
          @from_spr.visible = false;
        end
       
      else #square holds your piece
        @from = @cursor
       
        @from_spr.x = SQ_SIZE * (@from % 8)
        @from_spr.y = SQ_SIZE * (@from / 8)
        @from_spr.visible = true;
      end
    end
   
    # Undo pressed
    if(Input.trigger?(Input::B))
      @undo_move.call()
      @undo_move.call()
      refresh
      Graphics.update
    end
   
    # Move cursor
    @cursor -= 1 if(Input.trigger?(Input::LEFT))
    @cursor += 1 if(Input.trigger?(Input::RIGHT))
    @cursor -= 8 if(Input.trigger?(Input::UP))
    @cursor += 8 if(Input.trigger?(Input::DOWN))
   
    @cursor_spr.x = SQ_SIZE * (@cursor % 8)
    @cursor_spr.y = SQ_SIZE * (@cursor / 8)
  end
 
  #--------------------------------------------------------------------------
  # * Refresh
  #--------------------------------------------------------------------------
  def refresh
    @piece_sprite.bitmap.clear
   
    i = 0
    while(i < 64)
      pce_id = @get_square.call(i)
     
      if(pce_id != EMPTY)
        x = SQ_SIZE * (i % 8)
        y = SQ_SIZE * (i / 8)
     
        col = pce_id > W_KING ? 1 : 0
        pce = pce_id - (col * B_PAWN)
        source = Rect.new(pce*60, col*60, 60, 60)
     
        @piece_sprite.bitmap.blt(x, y, @piece_bitmap, source);
      end
     
      i += 1
    end
  end
 
  #--------------------------------------------------------------------------
  # * Do  Move
  #--------------------------------------------------------------------------
  def do_move(from, to)
    @do_move.call(from, to)
   
    @from_spr.visible = true
    @from_spr.x = (to % 8) * SQ_SIZE;
    @from_spr.y = (to / 8) * SQ_SIZE;
  end
 
  #--------------------------------------------------------------------------
  # * Do Best Move
  #--------------------------------------------------------------------------
  def best_move()
    best_move = @best_move.call
     
    # From and To are stored in bits
    from = 63 & (best_move >> 6);
    to = 63 & best_move;
     
    do_move(from, to)
  end
 
  #--------------------------------------------------------------------------
  # * Move Exists
  #--------------------------------------------------------------------------
  def move_exists?(from, to)
    result = @move_exists.call(from, to)
    return result == 1
  end
 
  #--------------------------------------------------------------------------
  # * Square is Selectable
  #--------------------------------------------------------------------------
  def square_selectable?
    if(@get_square.call(@cursor) == EMPTY)
      return false
     
    elsif(@get_square.call(@cursor) <= W_KING && @side_to_move.call() == WHITE)
      return true
     
    elsif(@get_square.call(@cursor) >= B_PAWN && @side_to_move.call() == BLACK)
      return true
     
    else
      return false
    end
  end
end







DLL-free version (V1):
This version is made entirely with RPG Maker scripts and doesn't rely on a dll. It is much weaker as a player though.
Spoiler: ShowHide

Chess_Constants:
module Chess
 
  #--------------------------------------------------------------------------
  # * Color
  #--------------------------------------------------------------------------
  WHITE     = true
  BLACK     = false
 
  #--------------------------------------------------------------------------
  # * Pieces
  #--------------------------------------------------------------------------
  W_PAWN    = 0
  W_ROOK    = 1
  W_KNIGHT  = 2
  W_BISHOP  = 3
  W_QUEEN   = 4
  W_KING    = 5
 
  B_PAWN    = 6
  B_ROOK    = 7
  B_KNIGHT  = 8
  B_BISHOP  = 9
  B_QUEEN   = 10
  B_KING    = 11
 
  NO_PIECE = 12
  OFF_BOARD = -2;
 
  #--------------------------------------------------------------------------
  # * Squares
  #--------------------------------------------------------------------------
  A8 = 21; B8 = 22; C8 = 23; D8 = 24; E8 = 25; F8 = 26; G8 = 27; H8 = 28;
  A7 = 31; B7 = 32; C7 = 33; D7 = 34; E7 = 35; F7 = 36; G7 = 37; H7 = 38;
  A6 = 41; B6 = 42; C6 = 43; D6 = 44; E6 = 45; F6 = 46; G6 = 47; H6 = 48;
  A5 = 51; B5 = 52; C5 = 53; D5 = 54; E5 = 55; F5 = 56; G5 = 57; H5 = 58;
  A4 = 61; B4 = 62; C4 = 63; D4 = 64; E4 = 65; F4 = 66; G4 = 67; H4 = 68;
  A3 = 71; B3 = 72; C3 = 73; D3 = 74; E3 = 75; F3 = 76; G3 = 77; H3 = 78;
  A2 = 81; B2 = 82; C2 = 83; D2 = 84; E2 = 85; F2 = 86; G2 = 87; H2 = 88;
  A1 = 91; B1 = 92; C1 = 93; D1 = 94; E1 = 95; F1 = 96; G1 = 97; H1 = 98;
 
  NO_SQUARE = -1;
 
  #--------------------------------------------------------------------------
  # * Ranks
  #--------------------------------------------------------------------------
  RANK_1 = 8; RANK_2 = 7; RANK_3 = 6; RANK_4 = 5;
  RANK_5 = 4; RANK_6 = 3; RANK_7 = 2; RANK_8 = 1;
 
  #--------------------------------------------------------------------------
  # * Files
  #--------------------------------------------------------------------------
  FILE_A = 1; FILE_B = 2; FILE_C = 3; FILE_D = 4;
  FILE_E = 5; FILE_F = 6; FILE_G = 7; FILE_H = 8;
 
  #--------------------------------------------------------------------------
  # * Strings
  #--------------------------------------------------------------------------
  SFILES = []
  SFILES[FILE_A] = "a"; SFILES[FILE_B] = "b"; SFILES[FILE_C] = "c";
  SFILES[FILE_D] = "d"; SFILES[FILE_E] = "e"; SFILES[FILE_F] = "f";
  SFILES[FILE_G] = "g"; SFILES[FILE_H] = "h";
 
  #--------------------------------------------------------------------------
  # * Values
  #--------------------------------------------------------------------------
  PVALUE = []
  PVALUE[NO_PIECE]   = 0
 
  PVALUE[W_PAWN]     = 100
  PVALUE[W_KNIGHT]   = 300
  PVALUE[W_BISHOP]   = 300
  PVALUE[W_ROOK]     = 600
  PVALUE[W_QUEEN]    = 900
  PVALUE[W_KING]     = 0
 
  PVALUE[B_PAWN]     = -100
  PVALUE[B_KNIGHT]   = -300
  PVALUE[B_BISHOP]   = -300
  PVALUE[B_ROOK]     = -600
  PVALUE[B_QUEEN]    = -900
  PVALUE[B_KING]     = 0
 
  DRAW = 0
  CHECKMATE = 1000
  INFINITY = CHECKMATE + 1
end


Chess_MoveGeneration:

class Chess_MoveGeneration
  #--------------------------------------------------------------------------
  # * Move exists?
  #--------------------------------------------------------------------------
  def move_exists(pos, move)
    legalMoves = []
    legalMoves += generateCapture(pos)
    legalMoves += generateQuiet(pos)
   
    legalMoves.each_index do |i|
      if(legalMoves[i][0] == move[0] && legalMoves[i][1] == move[1])
        return true
      end
    end
   
    return false
  end
 
  #--------------------------------------------------------------------------
  # * Generate quiet moves
  #--------------------------------------------------------------------------
  def generateQuiet(pos)
    moves = []
    i = -1
    while(i < 120)
      i += 1
      p = pos.board[i]
     
      next if(p == nil || p == Chess::OFF_BOARD || p == Chess::NO_PIECE)     
      color = (p <= Chess::W_KING) ? Chess::WHITE : Chess::BLACK
     
      next if(color != pos.side_to_move)
     
      is_rook = (p == Chess::W_ROOK || p == Chess::B_ROOK)
      is_knight = (p == Chess::W_KNIGHT || p == Chess::B_KNIGHT)
      is_bishop = (p == Chess::W_BISHOP || p == Chess::B_BISHOP)
      is_queen = (p == Chess::W_QUEEN || p == Chess::B_QUEEN)
      is_king = (p == Chess::W_KING || p == Chess::B_KING)
     
      #
      # Pawns
      #
      if(p == Chess::W_PAWN)
        if(pos.board[i - 10] == Chess::NO_PIECE)
          moves.push([i, i - 10])
         
          if(i >= Chess::A2 && pos.board[i - 20] == Chess::NO_PIECE)
            moves.push([i, i - 20])
          end
        end
      end
      if(p == Chess::B_PAWN)
        if(pos.board[i + 10] == Chess::NO_PIECE)
          moves.push([i, i + 10])
         
          if(i <= Chess::H7 && pos.board[i + 20] == Chess::NO_PIECE)
            moves.push([i, i + 20])
          end
        end
      end
     
     
      #
      # Knight movement
      #
      if(is_knight)
        moves.push([i, i+21]) if(pos.board[i+21] == Chess::NO_PIECE)
        moves.push([i, i+19]) if(pos.board[i+19] == Chess::NO_PIECE)
        moves.push([i, i+12]) if(pos.board[i+12] == Chess::NO_PIECE)
        moves.push([i, i+8]) if(pos.board[i+8] == Chess::NO_PIECE)
       
        moves.push([i, i-21]) if(pos.board[i-21] == Chess::NO_PIECE)
        moves.push([i, i-19]) if(pos.board[i-19] == Chess::NO_PIECE)
        moves.push([i, i-12]) if(pos.board[i-12] == Chess::NO_PIECE)
        moves.push([i, i-8]) if(pos.board[i-8] == Chess::NO_PIECE)
      end
     
     
      #
      # Linear movement
      #
      if(is_rook || is_queen)
        j = 1
        while(pos.board[i + j] == Chess::NO_PIECE)
          moves.push([i, i+j])
          j += 1
        end
       
        j = 1
        while(pos.board[i - j] == Chess::NO_PIECE)
          moves.push([i, i-j])
          j += 1
        end
       
        j = 1
        while(pos.board[i + j*10] == Chess::NO_PIECE)
          moves.push([i, i+j*10])
          j += 1
        end
       
        j = 1
        while(pos.board[i - j*10] == Chess::NO_PIECE)
          moves.push([i, i-j*10])
          j += 1
        end
      end
     
      #
      # Diagonal movement
      #
      if(is_bishop || is_queen)
        j = 1
        while(pos.board[i + j*10 + j] == Chess::NO_PIECE)
          moves.push([i, i+j*10 + j])
          j += 1
        end
       
        j = 1
        while(pos.board[i - j*10 + j] == Chess::NO_PIECE)
          moves.push([i, i-j*10 + j])
          j += 1
        end
       
        j = 1
        while(pos.board[i + j*10 - j] == Chess::NO_PIECE)
          moves.push([i, i+j*10 - j])
          j += 1
        end
       
        j = 1
        while(pos.board[i - j*10 - j] == Chess::NO_PIECE)
          moves.push([i, i-j*10 - j])
          j += 1
        end
      end
     
      #
      # King movement
      #
      if(is_king)
        moves.push([i, i+1]) if(pos.board[i+1] == Chess::NO_PIECE)
        moves.push([i, i-1]) if(pos.board[i-1] == Chess::NO_PIECE)
        moves.push([i, i+10]) if(pos.board[i+10] == Chess::NO_PIECE)
        moves.push([i, i-10]) if(pos.board[i-10] == Chess::NO_PIECE)
       
        moves.push([i, i+11]) if(pos.board[i+11] == Chess::NO_PIECE)
        moves.push([i, i-11]) if(pos.board[i-11] == Chess::NO_PIECE)
        moves.push([i, i+9]) if(pos.board[i+9] == Chess::NO_PIECE)
        moves.push([i, i-9]) if(pos.board[i-9] == Chess::NO_PIECE)
      end
     
    end
   
    return moves
  end
  #--------------------------------------------------------------------------
  # * Generate capture moves
  #--------------------------------------------------------------------------
  def generateCapture(pos)
    moves = []
    i = -1
    while(i < 120)
      i += 1
      p = pos.board[i]
     
      next if(p == nil || p == Chess::OFF_BOARD || p == Chess::NO_PIECE)     
      color = (p <= Chess::W_KING) ? Chess::WHITE : Chess::BLACK
     
      next if(color != pos.side_to_move)
     
      #
      # Pawns
      #
      if(p == Chess::W_PAWN)
        moves.push([i, i - 11]) if pos.is_black(pos.board[i - 11])
        moves.push([i, i - 9]) if pos.is_black(pos.board[i - 9])
      end
      if(p == Chess::B_PAWN)
        moves.push([i, i + 11]) if pos.is_white(pos.board[i + 11])
        moves.push([i, i + 9]) if pos.is_white(pos.board[i + 9])
      end
     
     
      #
      # Knight movement
      #
      if(p == Chess::W_KNIGHT)
        moves.push([i, i+21]) if pos.is_black(pos.board[i+21])
        moves.push([i, i+19]) if pos.is_black(pos.board[i+19])
        moves.push([i, i+12]) if pos.is_black(pos.board[i+12])
        moves.push([i, i+8]) if pos.is_black(pos.board[i+8])
       
        moves.push([i, i-21]) if pos.is_black(pos.board[i-21])
        moves.push([i, i-19]) if pos.is_black(pos.board[i-19])
        moves.push([i, i-12]) if pos.is_black(pos.board[i-12])
        moves.push([i, i-8]) if pos.is_black(pos.board[i-8])
      end
     
      if(p == Chess::B_KNIGHT)
        moves.push([i, i+21]) if pos.is_white(pos.board[i+21])
        moves.push([i, i+19]) if pos.is_white(pos.board[i+19])
        moves.push([i, i+12]) if pos.is_white(pos.board[i+12])
        moves.push([i, i+8]) if pos.is_white(pos.board[i+8])
       
        moves.push([i, i-21]) if pos.is_white(pos.board[i-21])
        moves.push([i, i-19]) if pos.is_white(pos.board[i-19])
        moves.push([i, i-12]) if pos.is_white(pos.board[i-12])
        moves.push([i, i-8]) if pos.is_white(pos.board[i-8])
      end
     
     
      #
      # Linear movement
      #
      if(p == Chess::W_ROOK || p == Chess::W_QUEEN)
        j = 1
        j += 1 while(pos.board[i + j] == Chess::NO_PIECE)
        moves.push([i, i+j]) if pos.is_black(pos.board[i + j])
       
       
        j = 1
        j += 1 while(pos.board[i - j] == Chess::NO_PIECE)
        moves.push([i, i-j]) if pos.is_black(pos.board[i - j])
       
       
        j = 1
        j += 1 while(pos.board[i + j*10] == Chess::NO_PIECE)
        moves.push([i, i+j*10]) if pos.is_black(pos.board[i + j*10])
       
       
        j = 1
        j += 1 while(pos.board[i - j*10] == Chess::NO_PIECE)
        moves.push([i, i-j*10]) if pos.is_black(pos.board[i - j*10])
      end
     
      if(p == Chess::B_ROOK || p == Chess::B_QUEEN)
        j = 1
        j += 1 while(pos.board[i + j] == Chess::NO_PIECE)
        moves.push([i, i+j]) if pos.is_white(pos.board[i + j])
       
       
        j = 1
        j += 1 while(pos.board[i - j] == Chess::NO_PIECE)
        moves.push([i, i-j]) if pos.is_white(pos.board[i - j])
       
       
        j = 1
        j += 1 while(pos.board[i + j*10] == Chess::NO_PIECE)
        moves.push([i, i+j*10]) if pos.is_white(pos.board[i + j*10])
       
       
        j = 1
        j += 1 while(pos.board[i - j*10] == Chess::NO_PIECE)
        moves.push([i, i-j*10]) if pos.is_white(pos.board[i - j*10])
      end
     
     
      #
      # Diagonal movement
      #
      if(p == Chess::W_BISHOP || p == Chess::W_QUEEN)
        j = 1
        j += 1 while(pos.board[i + j*10 + j] == Chess::NO_PIECE)
        moves.push([i, i+j*10+j]) if pos.is_black(pos.board[i + j*10+j])
       
       
        j = 1
        j += 1 while(pos.board[i - j*10+j] == Chess::NO_PIECE)
        moves.push([i, i-j*10+j]) if pos.is_black(pos.board[i - j*10+j])
       
       
        j = 1
        j += 1 while(pos.board[i + j*10-j] == Chess::NO_PIECE)
        moves.push([i, i+j*10-j]) if pos.is_black(pos.board[i + j*10-j])
       
       
        j = 1
        j += 1 while(pos.board[i - j*10-j] == Chess::NO_PIECE)
        moves.push([i, i-j*10-j]) if pos.is_black(pos.board[i - j*10-j])
      end
     
      if(p == Chess::B_BISHOP || p == Chess::B_QUEEN)
        j = 1
        j += 1 while(pos.board[i + j*10 + j] == Chess::NO_PIECE)
        moves.push([i, i+j*10+j]) if pos.is_white(pos.board[i + j*10+j])
       
       
        j = 1
        j += 1 while(pos.board[i - j*10+j] == Chess::NO_PIECE)
        moves.push([i, i-j*10+j]) if pos.is_white(pos.board[i - j*10+j])
       
       
        j = 1
        j += 1 while(pos.board[i + j*10-j] == Chess::NO_PIECE)
        moves.push([i, i+j*10-j]) if pos.is_white(pos.board[i + j*10-j])
       
       
        j = 1
        j += 1 while(pos.board[i - j*10-j] == Chess::NO_PIECE)
        moves.push([i, i-j*10-j]) if pos.is_white(pos.board[i - j*10-j])
      end
     
     
      #
      # King movement
      #
      if(p == Chess::W_KING)
        moves.push([i, i+1]) if pos.is_black(pos.board[i+1])
        moves.push([i, i-1]) if pos.is_black(pos.board[i-1])
        moves.push([i, i+10]) if pos.is_black(pos.board[i+10])
        moves.push([i, i-10]) if pos.is_black(pos.board[i-10])
       
        moves.push([i, i+11]) if pos.is_black(pos.board[i+11])
        moves.push([i, i-11]) if pos.is_black(pos.board[i-11])
        moves.push([i, i+9]) if pos.is_black(pos.board[i+9])
        moves.push([i, i-9]) if pos.is_black(pos.board[i-9])
      end
      if(p == Chess::B_KING)
        moves.push([i, i+1]) if pos.is_white(pos.board[i+1])
        moves.push([i, i-1]) if pos.is_white(pos.board[i-1])
        moves.push([i, i+10]) if pos.is_white(pos.board[i+10])
        moves.push([i, i-10]) if pos.is_white(pos.board[i-10])
       
        moves.push([i, i+11]) if pos.is_white(pos.board[i+11])
        moves.push([i, i-11]) if pos.is_white(pos.board[i-11])
        moves.push([i, i+9]) if pos.is_white(pos.board[i+9])
        moves.push([i, i-9]) if pos.is_white(pos.board[i-9])
      end
    end
   
    return moves
  end
end


Chess_Search:

class Chess_Search
  attr_reader :best_move
 
  #--------------------------------------------------------------------------
  # * Search
  #--------------------------------------------------------------------------
  def search(pos)
    @move_gen = Chess_MoveGeneration.new
   
    @best_move = [Chess::NO_SQUARE, Chess::NO_SQUARE]
   
    negamax(pos, 4, -Chess::INFINITY, Chess::INFINITY)
  end
 
  #--------------------------------------------------------------------------
  # * NegaMax
  #--------------------------------------------------------------------------
  def negamax(pos, depth, alpha, beta)
   
    # Leaf Node
    if(depth == 0)
      if(pos.side_to_move == Chess::WHITE)
        return pos.score
      elsif(pos.side_to_move == Chess::BLACK)
        return -pos.score
      end
    end
   
    # Generate legal moves
    moves = []
    moves += @move_gen.generateCapture(pos)
    moves += @move_gen.generateQuiet(pos)
   
    if(moves.length == 0)
      return Chess::DRAW
    end
   
   
    # Browse legal moves
    moves.each_index do |i|
      pos.make_move( moves[i] )
      score = -negamax(pos, depth - 1, -beta, -alpha)
      pos.unmake_move()
     
      if(score >= beta)
        return beta
      end
     
      if(score > alpha)
        alpha = score
       
        if(depth == 4)
          @best_move = moves[i]
        end
      end
    end
   
    return alpha
  end
 
end


Chess_Position:

class Chess_Position
  #--------------------------------------------------------------------------
  # * Public Variables
  #--------------------------------------------------------------------------
  attr_accessor :board
  attr_reader :side_to_move
  attr_reader :score
 
  #--------------------------------------------------------------------------
  # * Start
  #--------------------------------------------------------------------------
  def initialize
    @side_to_move = Chess::WHITE
    @board = []
    @score = 0
   
    @history = []
    @history_capture = []
   
    starting_position
  end
 
  #--------------------------------------------------------------------------
  # * Start
  #--------------------------------------------------------------------------
  def clear
    @score = 0
   
    # 120
    i = 0
    while(i < 120)
      @board[i] = Chess::OFF_BOARD
      i += 1
    end
   
    # Real 64 board
    i = 0
    while(i < 64)
      @board[sq120(i)] = Chess::NO_PIECE
      i += 1
    end
  end
 
  #--------------------------------------------------------------------------
  # * Move
  #--------------------------------------------------------------------------
  def make_move(move)
    # Update game score
    @score -= Chess::PVALUE[@board[move[1]]]
   
    # Record history
    @history.push(move)
    @history_capture.push(@board[move[1]])
   
    # Move piece
    @board[move[1]] = @board[move[0]]
    @board[move[0]] = Chess::NO_PIECE
   
    @side_to_move = !@side_to_move
  end
 
  #--------------------------------------------------------------------------
  # * Undo Move
  #--------------------------------------------------------------------------
  def unmake_move()
    move = @history.pop
    captured = @history_capture.pop
   
    # Refactor game score
    @score += Chess::PVALUE[captured]
   
    # Move back piece
    @board[move[0]] = @board[move[1]]
    @board[move[1]] = captured
   
    @side_to_move = !@side_to_move
  end
 
  #--------------------------------------------------------------------------
  # * Color
  #--------------------------------------------------------------------------
  def is_white(piece)
    (piece >= Chess::W_PAWN &&  piece <= Chess::W_KING)
  end
 
  def is_black(piece)
    (piece >= Chess::B_PAWN && piece <= Chess::B_KING)
  end
 
  #--------------------------------------------------------------------------
  # * Square 64 => 120
  #--------------------------------------------------------------------------
  def sq120(s)
    x = (s % 8)
    y = (s / 8)
   
    21 + y * 10 + x
  end
 
  #--------------------------------------------------------------------------
  # * Square 120 => 64
  #--------------------------------------------------------------------------
  def sq64(s)
    s -= 21;
   
    x = (s % 10)
    y = (s / 10)
   
    y * 8 + x
  end
 
  #--------------------------------------------------------------------------
  # * Starting position
  #--------------------------------------------------------------------------
  def starting_position
    clear
   
    # White
    @board[Chess::A1] = Chess::W_ROOK
    @board[Chess::B1] = Chess::W_KNIGHT
    @board[Chess::C1] = Chess::W_BISHOP
    @board[Chess::D1] = Chess::W_QUEEN
    @board[Chess::E1] = Chess::W_KING
    @board[Chess::F1] = Chess::W_BISHOP
    @board[Chess::G1] = Chess::W_KNIGHT
    @board[Chess::H1] = Chess::W_ROOK
   
    @board[Chess::A2] = Chess::W_PAWN
    @board[Chess::B2] = Chess::W_PAWN
    @board[Chess::C2] = Chess::W_PAWN
    @board[Chess::D2] = Chess::W_PAWN
    @board[Chess::E2] = Chess::W_PAWN
    @board[Chess::F2] = Chess::W_PAWN
    @board[Chess::G2] = Chess::W_PAWN
    @board[Chess::H2] = Chess::W_PAWN
   
    # Black
    @board[Chess::A8] = Chess::B_ROOK
    @board[Chess::B8] = Chess::B_KNIGHT
    @board[Chess::C8] = Chess::B_BISHOP
    @board[Chess::D8] = Chess::B_QUEEN
    @board[Chess::E8] = Chess::B_KING
    @board[Chess::F8] = Chess::B_BISHOP
    @board[Chess::G8] = Chess::B_KNIGHT
    @board[Chess::H8] = Chess::B_ROOK
   
    @board[Chess::A7] = Chess::B_PAWN
    @board[Chess::B7] = Chess::B_PAWN
    @board[Chess::C7] = Chess::B_PAWN
    @board[Chess::D7] = Chess::B_PAWN
    @board[Chess::E7] = Chess::B_PAWN
    @board[Chess::F7] = Chess::B_PAWN
    @board[Chess::G7] = Chess::B_PAWN
    @board[Chess::H7] = Chess::B_PAWN
  end
 
end


Scene_Chess: (VXA Version)

#==============================================================================
# ** Scene_Chess
#------------------------------------------------------------------------------
#  This class performs chess game UI and AI
#==============================================================================

class Scene_Chess < Scene_Base
  #--------------------------------------------------------------------------
  # * Start Processing
  #--------------------------------------------------------------------------
  def start
    super
    @position = Chess_Position.new
    @move_gen = Chess_MoveGeneration.new
    @search = Chess_Search.new
   
    @selected_square = @position.sq64(Chess::E2)
    @from_square = Chess::NO_SQUARE
   
    load_piece_sprite
    create_chessboard_sprite
    create_piece_sprite
    redraw_pieces
  end
  #--------------------------------------------------------------------------
  # * Make move
  #--------------------------------------------------------------------------
  def make_move(from, to)
    from = @position.sq120(from)
    to = @position.sq120(to)
   
    move = [from, to]
    move_legal = @move_gen.move_exists(@position, move)
   
    if(move_legal)
      # Make player move
      @position.make_move(move)
      redraw_pieces
     
      # Pick computer move
      @search.search(@position)
     
      # Make move
      @position.make_move(@search.best_move)
      redraw_pieces
     
      dx = (@position.sq64(@search.best_move[1]) % 8)
      dy = (@position.sq64(@search.best_move[1]) / 8)
     
      @last_move_sprite.x = dx * @square_size + @board_padding
      @last_move_sprite.y = dy * @square_size
      @last_move_sprite.visible = true
    end
  end
  #--------------------------------------------------------------------------
  # * Frame Update
  #--------------------------------------------------------------------------
  def update
    # Move cursor
    if(Input.trigger?(:UP))
      @selected_square -= 8
    elsif(Input.trigger?(:RIGHT))
      @selected_square += 1
    elsif(Input.trigger?(:LEFT))
      @selected_square -= 1
    elsif(Input.trigger?(:DOWN))
      @selected_square += 8
    end
   
    @selected_square = 0 if(@selected_square < 0)
    @selected_square = 63 if(@selected_square > 63)
   
   
    # Enter
    if(Input.trigger?(:C))
      if(@from_square != Chess::NO_SQUARE)
        make_move(@from_square, @selected_square)
        @from_square = Chess::NO_SQUARE
      else
        @from_square = @selected_square
      end
    end
   
    # Position sprite
    @cursor_sprite.x = @square_size * (@selected_square % 8) + @board_padding
    @cursor_sprite.y = @square_size * (@selected_square / 8)
   
    @from_sprite.x = @square_size * (@from_square % 8) + @board_padding
    @from_sprite.y = @square_size * (@from_square / 8)
    super
  end
  #--------------------------------------------------------------------------
  # * create_piece_sprite
  #--------------------------------------------------------------------------
  def create_piece_sprite
    @piece_sprite = Sprite.new
    @piece_sprite.x = @board_padding
    @piece_sprite.y = 0
    @piece_sprite.z = 150
    @piece_sprite.bitmap = Bitmap.new(@board_size, @board_size)
  end
  #--------------------------------------------------------------------------
  # * Redraw piece
  #--------------------------------------------------------------------------
  def redraw_pieces
    @piece_sprite.bitmap.clear
   
    x = 0; y = 0;
    while(y < 8)
      while(x < 8)
        square64 = y * 8 + x
        square120 = @position.sq120(square64)
        piece = @position.board[square120]
       
        if(piece != Chess::NO_PIECE)
          dx = @square_size * x
          dy = @square_size * y
          rect = Rect.new(0, 0, @board_size, @board_size)
         
          @piece_sprite.bitmap.blt(dx, dy, @piece_bitmaps[piece], rect)
        end
       
        x += 1
      end
     
      x = 0
      y += 1
    end
  end
  #--------------------------------------------------------------------------
  # * Load Piece Sprite
  #--------------------------------------------------------------------------
  def load_piece_sprite
    @piece_bitmaps = []
   
    @piece_bitmaps[Chess::W_PAWN] = Bitmap.new("ChessPieces/white_pawn.png")
    @piece_bitmaps[Chess::W_ROOK] = Bitmap.new("ChessPieces/white_rook.png")
    @piece_bitmaps[Chess::W_KNIGHT] = Bitmap.new("ChessPieces/white_knight.png")
    @piece_bitmaps[Chess::W_BISHOP] = Bitmap.new("ChessPieces/white_bishop.png")
    @piece_bitmaps[Chess::W_QUEEN] = Bitmap.new("ChessPieces/white_queen.png")
    @piece_bitmaps[Chess::W_KING] = Bitmap.new("ChessPieces/white_king.png")
   
    @piece_bitmaps[Chess::B_PAWN] = Bitmap.new("ChessPieces/black_pawn.png")
    @piece_bitmaps[Chess::B_ROOK] = Bitmap.new("ChessPieces/black_rook.png")
    @piece_bitmaps[Chess::B_KNIGHT] = Bitmap.new("ChessPieces/black_knight.png")
    @piece_bitmaps[Chess::B_BISHOP] = Bitmap.new("ChessPieces/black_bishop.png")
    @piece_bitmaps[Chess::B_QUEEN] = Bitmap.new("ChessPieces/black_queen.png")
    @piece_bitmaps[Chess::B_KING] = Bitmap.new("ChessPieces/black_king.png")
  end
 
  #--------------------------------------------------------------------------
  # * Create chessboard sprite
  #--------------------------------------------------------------------------
  def create_chessboard_sprite
    Graphics.resize_screen(640, 480)
   
    # Size constants
    @board_size = 480
    @board_padding = (640 - @board_size) / 2
    @square_size = @board_size / 8
   
    # Create board sprite
    @board_gfx = Sprite.new
    @board_gfx.z = 10
    @board_gfx.x = @board_padding
    @board_gfx.bitmap = Bitmap.new(@board_size, @board_size)
   
    y = 0
    while(y < 8)
      x = 0
      while(x < 8)
        x2 = x * @square_size
        y2 = y * @square_size
       
        if((x + y) % 2 == 0)
          col = Color.new(255, 255, 255)
        else
          col = Color.new(80, 30, 0)
        end
       
        @board_gfx.bitmap.fill_rect(x2, y2, @square_size, @square_size, col)
        x += 1
      end
      y += 1
    end
   
    # Create square cursor sprite
    @cursor_sprite = Sprite.new
    @cursor_sprite.bitmap = Bitmap.new(@square_size, @square_size)
    @cursor_sprite.bitmap.fill_rect(0, 0, 640, 480, Color.new(255, 255, 100))
    @cursor_sprite.z = 50
   
    # Create from_square sprite
    @from_sprite = Sprite.new
    @from_sprite.bitmap = Bitmap.new(@square_size, @square_size)
    @from_sprite.bitmap.fill_rect(0, 0, 640, 480, Color.new(100, 255, 100))
    @from_sprite.z = 51
   
    # Create last_move_to sprite
    @last_move_sprite = Sprite.new
    @last_move_sprite.bitmap = Bitmap.new(@square_size, @square_size)
    @last_move_sprite.bitmap.fill_rect(0, 0, 640, 480, Color.new(200, 200, 100))
    @last_move_sprite.z = 51
    @last_move_sprite.visible = false
  end
  #--------------------------------------------------------------------------
  # * Termination Processing
  #--------------------------------------------------------------------------
  def terminate
    super
  end
end



Scene_Chess (VX Version)

#==============================================================================
# ** Scene_Chess
#------------------------------------------------------------------------------
#  This class performs chess game UI and AI
#==============================================================================

class Scene_Chess < Scene_Base
  #--------------------------------------------------------------------------
  # * Start Processing
  #--------------------------------------------------------------------------
  def start
    super
    Graphics.resize_screen(640, 480)
   
    @position = Chess_Position.new
    @move_gen = Chess_MoveGeneration.new
    @search = Chess_Search.new
   
    @selected_square = @position.sq64(Chess::E2)
    @from_square = Chess::NO_SQUARE
   
    load_piece_sprite
    create_chessboard_sprite
    create_piece_sprite
    redraw_pieces
  end
  #--------------------------------------------------------------------------
  # * Make move
  #--------------------------------------------------------------------------
  def make_move(from, to)
    from = @position.sq120(from)
    to = @position.sq120(to)
   
    move = [from, to]
    move_legal = @move_gen.move_exists(@position, move)
   
    if(move_legal)
      # Make player move
      @position.make_move(move)
      redraw_pieces
     
      # Pick computer move
      @search.search(@position)
     
      # Make move
      @position.make_move(@search.best_move)
      redraw_pieces
     
      dx = (@position.sq64(@search.best_move[1]) % 8)
      dy = (@position.sq64(@search.best_move[1]) / 8)
     
      @last_move_sprite.x = dx * @square_size + @board_padding
      @last_move_sprite.y = dy * @square_size
      @last_move_sprite.visible = true
    end
  end
  #--------------------------------------------------------------------------
  # * Frame Update
  #--------------------------------------------------------------------------
  def update
    super
    # Move cursor
    if(Input.trigger?(Input::UP))
      @selected_square -= 8
    elsif(Input.trigger?(Input::RIGHT))
      @selected_square += 1
    elsif(Input.trigger?(Input::LEFT))
      @selected_square -= 1
    elsif(Input.trigger?(Input::DOWN))
      @selected_square += 8
    end
   
    @selected_square = 0 if(@selected_square < 0)
    @selected_square = 63 if(@selected_square > 63)
   
    # Enter
    if(Input.trigger?(Input::C))
      if(@from_square != Chess::NO_SQUARE)
        make_move(@from_square, @selected_square)
        @from_square = Chess::NO_SQUARE
      else
        @from_square = @selected_square
      end
    end
   
    # Position sprite
    @cursor_sprite.x = @square_size * (@selected_square % 8) + @board_padding
    @cursor_sprite.y = @square_size * (@selected_square / 8)
   
    @from_sprite.x = @square_size * (@from_square % 8) + @board_padding
    @from_sprite.y = @square_size * (@from_square / 8)
  end
  #--------------------------------------------------------------------------
  # * create_piece_sprite
  #--------------------------------------------------------------------------
  def create_piece_sprite
    @piece_sprite = Sprite.new
    @piece_sprite.x = @board_padding
    @piece_sprite.y = 0
    @piece_sprite.z = 150
    @piece_sprite.bitmap = Bitmap.new(@board_size, @board_size)
  end
  #--------------------------------------------------------------------------
  # * Redraw piece
  #--------------------------------------------------------------------------
  def redraw_pieces
    @piece_sprite.bitmap.clear
   
    x = 0; y = 0;
    while(y < 8)
      while(x < 8)
        square64 = y * 8 + x
        square120 = @position.sq120(square64)
        piece = @position.board[square120]
       
        if(piece != Chess::NO_PIECE)
          dx = @square_size * x
          dy = @square_size * y
          rect = Rect.new(0, 0, @board_size, @board_size)
         
          @piece_sprite.bitmap.blt(dx, dy, @piece_bitmaps[piece], rect)
        end
       
        x += 1
      end
     
      x = 0
      y += 1
    end
  end
  #--------------------------------------------------------------------------
  # * Load Piece Sprite
  #--------------------------------------------------------------------------
  def load_piece_sprite
    @piece_bitmaps = []
   
    @piece_bitmaps[Chess::W_PAWN] = Bitmap.new("ChessPieces/white_pawn.png")
    @piece_bitmaps[Chess::W_ROOK] = Bitmap.new("ChessPieces/white_rook.png")
    @piece_bitmaps[Chess::W_KNIGHT] = Bitmap.new("ChessPieces/white_knight.png")
    @piece_bitmaps[Chess::W_BISHOP] = Bitmap.new("ChessPieces/white_bishop.png")
    @piece_bitmaps[Chess::W_QUEEN] = Bitmap.new("ChessPieces/white_queen.png")
    @piece_bitmaps[Chess::W_KING] = Bitmap.new("ChessPieces/white_king.png")
   
    @piece_bitmaps[Chess::B_PAWN] = Bitmap.new("ChessPieces/black_pawn.png")
    @piece_bitmaps[Chess::B_ROOK] = Bitmap.new("ChessPieces/black_rook.png")
    @piece_bitmaps[Chess::B_KNIGHT] = Bitmap.new("ChessPieces/black_knight.png")
    @piece_bitmaps[Chess::B_BISHOP] = Bitmap.new("ChessPieces/black_bishop.png")
    @piece_bitmaps[Chess::B_QUEEN] = Bitmap.new("ChessPieces/black_queen.png")
    @piece_bitmaps[Chess::B_KING] = Bitmap.new("ChessPieces/black_king.png")
  end
 
  #--------------------------------------------------------------------------
  # * Create chessboard sprite
  #--------------------------------------------------------------------------
  def create_chessboard_sprite
    # Size constants
    @board_size = 480
    @board_padding = (640 - @board_size) / 2
    @square_size = @board_size / 8
   
    # Create board sprite
    @board_gfx = Sprite.new
    @board_gfx.z = 10
    @board_gfx.x = @board_padding
    @board_gfx.bitmap = Bitmap.new(@board_size, @board_size)
   
    y = 0
    while(y < 8)
      x = 0
      while(x < 8)
        x2 = x * @square_size
        y2 = y * @square_size
       
        if((x + y) % 2 == 0)
          col = Color.new(255, 255, 255)
        else
          col = Color.new(80, 30, 0)
        end
       
        @board_gfx.bitmap.fill_rect(x2, y2, @square_size, @square_size, col)
        x += 1
      end
      y += 1
    end
   
    # Create square cursor sprite
    @cursor_sprite = Sprite.new
    @cursor_sprite.bitmap = Bitmap.new(@square_size, @square_size)
    @cursor_sprite.bitmap.fill_rect(0, 0, 640, 480, Color.new(255, 255, 100))
    @cursor_sprite.z = 50
   
    # Create from_square sprite
    @from_sprite = Sprite.new
    @from_sprite.bitmap = Bitmap.new(@square_size, @square_size)
    @from_sprite.bitmap.fill_rect(0, 0, 640, 480, Color.new(100, 255, 100))
    @from_sprite.z = 51
   
    # Create last_move_to sprite
    @last_move_sprite = Sprite.new
    @last_move_sprite.bitmap = Bitmap.new(@square_size, @square_size)
    @last_move_sprite.bitmap.fill_rect(0, 0, 640, 480, Color.new(200, 200, 100))
    @last_move_sprite.z = 51
    @last_move_sprite.visible = false
  end
  #--------------------------------------------------------------------------
  # * Termination Processing
  #--------------------------------------------------------------------------

Title: Re: [VX/VX Ace] Chess Engine
Post by: Zexion on May 18, 2014, 10:26:35 pm
Great first impression on this forum Abigail. I know you from Rmrk, sooo I know of the way you came to the scene lol!
Seems cool, I'll check this out in a little while when im not as distracted :b
Title: Re: [VX/VX Ace] Chess Engine
Post by: G_G on May 18, 2014, 11:02:54 pm
I'm going to move this to RGSS forums. Since this is a script and it's RPG Maker. If you'd like to apply the template (http://forum.chaos-project.com/index.php/topic,17.0.html), we can move it to the database.

This is a pretty cool idea, definitely going to have to play around with it. :3
Title: Re: [VX/VX Ace] Chess Engine
Post by: Abigail on May 19, 2014, 04:50:18 am
Quote from: Zexion on May 18, 2014, 10:26:35 pm
Great first impression on this forum Abigail. I know you from Rmrk, sooo I know of the way you came to the scene lol!
Seems cool, I'll check this out in a little while when im not as distracted :b


Thanks, hoping to not do the same mistakes :)
Title: Re: [VX/VX Ace] Chess Engine
Post by: PhoenixFire on May 19, 2014, 06:34:05 pm
Did you find the link I sent you to on here helpful? Hopefully it gave you an idea where to start with removing the dependencies.
Title: Re: [VX/VX Ace] Chess Engine
Post by: ShadowSaber on May 21, 2014, 03:15:55 pm
can someone upload the file to other filehosting?
it seems my isp won't allow download from speedyshare
Title: Re: [VX/VX Ace] Chess Engine
Post by: Blizzard on May 21, 2014, 03:29:45 pm
The VX or VXA one?
Title: Re: [VX/VX Ace] Chess Engine
Post by: ShadowSaber on May 23, 2014, 12:02:58 am
VXA one, please  :shy:
Title: Re: [VX/VX Ace] Chess Engine
Post by: orochii on May 23, 2014, 01:32:37 am
Just wanted to pass and congratulate you, because making a real AI is one of those things that I fear the most. xD.
Title: Re: [VX/VX Ace] Chess Engine
Post by: Blizzard on May 23, 2014, 01:45:31 am
Here you go. http://www.sendspace.com/file/q5gca4

EDIT: How did I not see this.

Quote from: Abigail on May 19, 2014, 04:50:18 am
Quote from: Zexion on May 18, 2014, 10:26:35 pm
Great first impression on this forum Abigail. I know you from Rmrk, sooo I know of the way you came to the scene lol!
Seems cool, I'll check this out in a little while when im not as distracted :b


Thanks, hoping to not do the same mistakes :)


I started out at RMRK as well.
Title: Re: [VX/VX Ace] Chess Engine
Post by: Abigail on May 23, 2014, 11:00:17 am
Quote from: orochii on May 23, 2014, 01:32:37 am
Just wanted to pass and congratulate you, because making a real AI is one of those things that I fear the most. xD.


Thanks :) I'm working on a new version that will be much stronger and C++ powered via Win32API.

Quote from: Blizzard on May 23, 2014, 01:45:31 am
Here you go. http://www.sendspace.com/file/q5gca4

EDIT: How did I not see this.

Quote from: Abigail on May 19, 2014, 04:50:18 am
Quote from: Zexion on May 18, 2014, 10:26:35 pm
Great first impression on this forum Abigail. I know you from Rmrk, sooo I know of the way you came to the scene lol!
Seems cool, I'll check this out in a little while when im not as distracted :b


Thanks, hoping to not do the same mistakes :)


I started out at RMRK as well.


:D

Sorry for being lazy and not fixing the thread up with template and downloads and whatnot, but It'll all be much prettier when I put up the new version in a few days.
Title: Re: [VX/VX Ace] Chess Engine
Post by: Heretic86 on May 23, 2014, 08:26:16 pm
I know you had Finals recently, which are far more important.  Just take your time and do it right.  That also means dont edit the post for proper Template Formatting at the expense of your Finals.
Title: Re: [VX/VX Ace] Chess Engine v2
Post by: Abigail on May 30, 2014, 06:50:20 pm
I updated this. It now uses C++ for all of the calculations and does the interface in RGSS. This not only makes the engine much stronger, it also makes the scripts cleaner in my opinion.

:)
Title: Re: [VX/VX Ace] Chess Engine v2
Post by: Blizzard on May 30, 2014, 08:52:42 pm
Nice work. Did you use some simple look-ahead algorithm with a certain number of turns to check or did you implement some more advanced heuristics for the AI?
Title: Re: [VX/VX Ace] Chess Engine v2
Post by: Abigail on May 30, 2014, 09:06:38 pm
Quote from: Blizzard on May 30, 2014, 08:52:42 pm
Nice work. Did you use some simple look-ahead algorithm with a certain number of turns to check or did you implement some more advanced heuristics for the AI?


Thanks :)

The heart of it is a simple negamax algorithm. It uses iterative deepening and stops after time runs out. I tried implementing a principal variation heuristic but I am unsure whether it worked or not. Any and all tips are very appreciated :D
Title: Re: [VX/VX Ace] Chess Engine v2
Post by: G_G on May 30, 2014, 09:45:55 pm
It'd be kind of cool to release the source code for the C++ too. It might help/inspire some people.
Title: Re: [VX/VX Ace] Chess Engine v2
Post by: WhiteRose on May 30, 2014, 09:54:03 pm
Quote from: gameus on May 30, 2014, 09:45:55 pm
It'd be kind of cool to release the source code for the C++ too. It might help/inspire some people.


Unless you're opposed to it, I also think this is a good idea. I'm no C++ expert, but I'd love to look over your code and see what I can learn. :)
Title: Re: [VX/VX Ace] Chess Engine v2
Post by: Blizzard on May 31, 2014, 02:50:22 am
In this case you probably want to put the entire setup for compilation in a rar file or something as well. xD
Title: Re: [VX/VX Ace] Chess Engine v2
Post by: Abigail on May 31, 2014, 03:39:19 am
Sure I can put that up :) I'll do it when I get home
Title: Re: [VX/VX Ace] Chess Engine v2
Post by: orochii on May 31, 2014, 12:01:28 pm
Heheh, excuse me but, what is the format for the pieces.png, a.k.a. the image with the piece graphics? I think it's missing at the main post. :P.
Title: Re: [VX/VX Ace] Chess Engine v2
Post by: Abigail on May 31, 2014, 01:16:48 pm
Quote from: orochii on May 31, 2014, 12:01:28 pm
Heheh, excuse me but, what is the format for the pieces.png, a.k.a. the image with the piece graphics? I think it's missing at the main post. :P.


Oops sorry :) Added it
Title: Re: [VX/VX Ace] Chess Engine v2
Post by: LiTTleDRAgo on July 15, 2014, 04:57:35 pm
it seems the dll can't be used in Windows XP

(http://i.imgur.com/Rwy8Rxk.jpg)
Title: Re: [VX/VX Ace] Chess Engine v2
Post by: Blizzard on July 16, 2014, 01:26:40 am
Yeah, Windows XP's kernel doesn't have this function. You have to use GetTickCount().