Project showcase
Automated Chess Board

Automated Chess Board © GPL3+

Moves chess pieces around the board invisibly and seemingly magically.

  • 5,300 views
  • 6 comments
  • 66 respects

Components and supplies

Necessary tools and machines

Power Drill
Hacksaw

About this project

I wanted to make something cool while challenging my proficiency with Arduino and building electromechanical systems. I was interested in using magnets to do something to make it appear magical so I basically set out to make the 'Wizard's Chess' game from the Harry Potter series. Game is between two people sharing the computer; the computer isn't the second player unfortunately.

The board is hooked up to a computer and requires the player to input a square address of the piece to be moved and the new location for the piece. The electromagnet is moved by two stepper motors and timing belts. Each piece has a loose steel ball bearing inside to allow them to easily slide around.

The biggest problem I had was getting the vertical axis to move smoothly without catching and missing steps. It doesn't happen often but when it does I just had to close the serial monitor and reopen it which reset the Arduino and zeroed the magnet position.

Pieces are initially offset to the corner and moved along the lines between squares to avoid colliding with other pieces.

Code

Automated_chessboardArduino
Code will:
*Home magnet with end stops at position A1.
*Receive square address (Letter, Number) from Serial Monitor for piece to be moved.
*Translate input into number of steps to be completed by stepper motors.
*Receive square address (Letter, Number) from Serial Monitor for new piece location.
*Turn on electromagnet.
*Translate input into number of steps to be completed by stepper motors.
*Turn off electromagnet.

Notes:
*Stepper motors will run simultaneously (during zeroing and moving with the magnet off ) until one reaches its max steps and then the other will continue until it reaches the specified square.

*When the magnet is on and moving a piece the steppers initially offset to the corner and moves along the line between squares to prevent pieces interfering with each other. For example, this allows someone to move their knight before moving the pawns in front of it.
const int stepsBetweenSquares = 318;
const int stepPinX = 3; 
const int dirPinX = 4; 
const int stepPinY = 5;
const int dirPinY = 6;
const int limitSwitchX = 8;
const int limitSwitchY = 9;
const int magnetPinPos = 10;
const int magnetPinNeg = 11;
int x1 = 0; int x2 = 1;
int y1 = 0; int y2 = 1;
int xsteps;
int ysteps;
int x = 0;
int y = 0;

void setup() {
  Serial.begin(9600);
  pinMode(stepPinX,OUTPUT); 
  pinMode(dirPinX,OUTPUT);
  pinMode(stepPinY,OUTPUT); 
  pinMode(dirPinY,OUTPUT);
  pinMode(limitSwitchX, INPUT);
  pinMode(limitSwitchY, INPUT);
  pinMode(magnetPinPos, OUTPUT);
  pinMode(magnetPinNeg, OUTPUT);
  

//_________________________________________________________________________________________________
// Zero position to square A1
//--------------------------------------------------------------------------------------------------
  zeroDiagonal();
}


void loop() {
//___________________________________________________________________________________________________
// Recieve position adress of piece to be moved from Serial monitor (Letter, Number)
//---------------------------------------------------------------------------------------------------
  Serial.print("Piece to be moved letter adress:  ");
  while (!Serial.available());
    x1 = readSerialLetter();
      
  Serial.print("Piece to be moved number adress:  ");
  while (!Serial.available());
    y1 = readSerialNumber();      


//______________________________________________________________________________________________
// Move to Position of piece to be moved
//-----------------------------------------------------------------------------------------------
  xsteps = stepsBetweenSquares*(x1-x2);
  ysteps = stepsBetweenSquares*(y1-y2);
  
  movePieceDiagonal(xsteps, ysteps);
 

//_______________________________________________________________________________________________
// Recieve position adress of piece new location from Serial Monitor (Letter, Number)
//-----------------------------------------------------------------------------------------------
  Serial.print("New location letter adress:  ");
  while (!Serial.available());
    x2 = readSerialLetter();

  Serial.print("New location number adress:  ");
  while (!Serial.available());
    y2 = readSerialNumber();
  Serial.println();

  
//________________________________________________________________________________________________
// Turn on magnet
//------------------------------------------------------------------------------------------------
  digitalWrite(magnetPinPos, HIGH);
  digitalWrite(magnetPinNeg, LOW);

  
//________________________________________________________________________________________________
// Move piece to new location
//-------------------------------------------------------------------------------------------------
  xsteps = stepsBetweenSquares*(x2-x1);
  ysteps = stepsBetweenSquares*(y2-y1);
  
  digitalWrite(dirPinX, HIGH); digitalWrite(dirPinY, LOW);
  offsetPiece();
  delay(50);
  movePiece(xsteps, dirPinX, stepPinX);
  movePiece(-ysteps, dirPinY, stepPinY);
  delay(50);
  digitalWrite(dirPinX, LOW); digitalWrite(dirPinY, HIGH);
  offsetPiece();

//__________________________________________________________________________________________________
// Turn off magnet
//----------------------------------------------------------------------------------------------------
  digitalWrite(magnetPinPos, LOW);
  digitalWrite(magnetPinNeg, LOW);
}


/////////////////////////////////////////////////////////////////////////////////////////////////////////
// FUNCTIONS ////////////////////////////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////////////////////////////////////

int readSerialLetter(){
  int i;
  while(i < 1 || i > 8){
    i = Serial.read(); 
    i = i - 64;
    }
  Serial.println(i);
  Serial.parseInt();
  return i;
  }

//////////////////////////////////////////////////////////////////////////////////////////////////////

int readSerialNumber(){
  int i;
  while (i < 1 || i > 8){
    i = Serial.parseInt();
    }
  Serial.println(i);
  Serial.parseInt();
  return i;
  }

////////////////////////////////////////////////////////////////////////////////////////////////////////

void zeroDiagonal(){
  digitalWrite(dirPinX, LOW);
  digitalWrite(dirPinY, HIGH);
  while (digitalRead(limitSwitchX) == HIGH && digitalRead(limitSwitchY) == HIGH){
    moveDiagonal(1.5);
  }
  while (digitalRead(limitSwitchX) == HIGH){
    moveLinear(stepPinX, 1.5);
  }
  while (digitalRead(limitSwitchY) == HIGH){
    moveLinear(stepPinY, 1.5);
  }
  while (digitalRead(limitSwitchX) == LOW){         //Backoff switch
    digitalWrite(dirPinX, HIGH);
    moveLinear(stepPinX, 1);
  }
  while (digitalRead(limitSwitchY) == LOW){         //Backoff switch
    digitalWrite(dirPinY, LOW);
    moveLinear(stepPinY, 1);
  }
}

///////////////////////////////////////////////////////////////////////////////////////////////////

void movePiece(int steps, int dirPin, int stepPin){
  if (steps > 0){
    digitalWrite(dirPin,HIGH);
  }
  else{
    steps = abs(steps);
    digitalWrite(dirPin, LOW);
  }
  for(int i = 0; i < steps; i++) {
    moveLinear(stepPin, 2.5);
  }
  }

////////////////////////////////////////////////////////////////////////////////////////////////////////

void movePieceDiagonal(int xsteps, int ysteps){
  if (ysteps > 0){
    digitalWrite(dirPinY, LOW);
  }
  else{
    ysteps = abs(ysteps);
    digitalWrite(dirPinY, HIGH);
  }
  if (xsteps > 0){
    digitalWrite(dirPinX, HIGH);
  } 
  else{
    xsteps = abs(xsteps);
    digitalWrite(dirPinX, LOW);
  }
  x = 0; y = 0; 
  while (x < xsteps && y < ysteps){
    moveDiagonal(1.5);
    x++; y++;
  }
  for(x; x < xsteps; x++){
    moveLinear(stepPinX, 1.5);
  }
  for(y; y < ysteps; y++){
    moveLinear(stepPinY, 1.5);
  }
}

/////////////////////////////////////////////////////////////////////////////////////////////////////////

void offsetPiece(){
  for (int i=0; i < stepsBetweenSquares/2; i++){
    moveDiagonal(2.5);
  }
}

///////////////////////////////////////////////////////////////////////////////////////////////////////////

void moveDiagonal(int delayTime){
    digitalWrite(stepPinX, HIGH);
    digitalWrite(stepPinY, HIGH);
    delay(delayTime);
    digitalWrite(stepPinX, LOW);
    digitalWrite(stepPinY, LOW);
    delay(delayTime);
}

////////////////////////////////////////////////////////////////////////////////////////////////////////////////

void moveLinear(int stepPin, int delayTime){
  digitalWrite(stepPin, HIGH);
  delay(delayTime);
  digitalWrite(stepPin, LOW);
  delay(delayTime);
}

Schematics

Automated_chessboard_Layout
Board powered from USB cable for all logic devices. Steppers and electromagnet (Solenoid) are powered from external power brick that is 9 volts and max 5 amps.
Fritzing diagram gavkojw0gk

Comments

Similar projects you might like

Wooden Chess Board with Piece Recognition

Project showcase by MaxChess

  • 27,669 views
  • 41 comments
  • 79 respects

Automated Chess Play Using Alexa

Project in progress by Team Automaters

  • 10,694 views
  • 2 comments
  • 50 respects

Playing Smartphone Games with a Relay Touch Board

Project showcase by HomeMadeGarbage

  • 5,641 views
  • 6 comments
  • 11 respects

CNC drawing machine with joysticks

Project showcase by TechnoFabrique

  • 2,057 views
  • 0 comments
  • 5 respects

DC Motors Controller Board

Project showcase by Shahariar

  • 1,897 views
  • 0 comments
  • 6 respects

Automated Garden

Project tutorial by Thomas sxt

  • 19,531 views
  • 15 comments
  • 65 respects
Add projectSign up / Login