Project showcase

Create a Game with Arduino and Processing

Create a game with processing and its controller with an accelerometer and a button.

  • 1,495 views
  • 3 comments
  • 5 respects

Components and supplies

Apps and online services

About this project

Overview

First of all we build the game controller, using a button and an accelerometer. I use a GY-521, so if you use a different accelerometer you will need to change part of the code.

Connections for the accelerometer and the button

  • VCC -> 5 V
  • GND -> GND
  • SCL -> A5
  • SDA -> A4

Connect the button to the digital pin 7 and connect it to ground with a 10 Kohm resistor. Then connect the supply to 5 V.

How to make it

In the code we use the Bounce library in order to avoid the bounce of the signal of the button. Download the library and copy the unzipped folder in the libraries folder of Arduino.

I use a standard breadboard but it's a bit difficult moving the controller. It would be better to use an Arduino Prototyping shield.

To create the game we use Processing, which can be downloaded here. First you run the Arduino code. Then run the Processing code.

Wait for the accelerometer to stabilize. Press the button and the game will start. Moving the accelerometer along the X axis the paddle will move.

Be mindful of port

Check the Processing code. Maybe you need to change the instruction: arduinoPort=new Serial(this, "COM3", 19200); Instead of COM3 you have to use the port you are using with Arduino. Also Processing and Ardruino must have the same baud rate.

Schematics

circuit diagram
Game controller bb v6yjrqcnub

Code

Processing codeProcessing
import processing.serial.*;

Serial arduinoPort;

final int COLUMNS=7;
final int ROWS=4;
final int BALL_RADIUS=8;
final int BALL_DIAMETER=BALL_RADIUS*2;
final int MAX_VELOCITY=8;
final int MARGIN=10;
final int PADDLE_WIDTH=60;
final int PADDLE_HEIGHT=15;
final int BRICK_WIDTH=40;
final int BRICK_HEIGHT=20;
final int HEIGHT=300;
final int LINE_FEED=10;

int px, py;
int vx, vy;
int xpos=150;
int[][] bricks= new int[COLUMNS][ROWS];

boolean buttonPressed=false;
boolean paused=true;
boolean done=true;

void setup(){
  size(300, 300);
  noCursor();
  textFont(loadFont("Verdana-Bold-36.vlw"));
  initGame();
  println(Arduino.list());
  arduinoPort=new Serial(this, "COM3", 19200);
  arduinoPort.bufferUntil(10);
}

void initGame(){
  initBricks();
  initBall();
}

void initBricks(){
  for(int x=0; x<COLUMNS; x++)
  for(int y=0; y<ROWS; y++)
  bricks[x][y]=1;
}

void initBall(){
  px=width/2;
  py=height/2;
  vx=int(random(-MAX_VELOCITY, MAX_VELOCITY));
  vy=-2;
}

void draw(){
  background(0);
  stroke(255);
  strokeWeight(3);
  
  done=drawBricks();
  if(done){
    paused=true;
    printWinMessage();
  }
  if(paused)
    printPauseMessage();
  else
    updateGame();
  
  drawBall();
  drawPaddle();
}

boolean drawBricks(){
  boolean allEmpty=true;
  for(int x=0; x<COLUMNS; x++){
    for(int y=0; y<ROWS; y++){
      if(bricks[x][y]>0){
        allEmpty=false;
        fill(0, 0, 100+y*8);
        rect(
          MARGIN+x*BRICK_WIDTH,
          MARGIN+y*BRICK_HEIGHT,
          BRICK_WIDTH,
          BRICK_HEIGHT
        );
      }
    }
  }
  return allEmpty;
}

void drawBall(){
  strokeWeight(1);
  fill(128, 0, 0);
  ellipse(px, py, BALL_DIAMETER,  BALL_DIAMETER);
}

void drawPaddle(){
  int x=xpos - PADDLE_WIDTH/2;
  int y=height - 25;
  strokeWeight(1);
  fill(128);
  rect(x, y, 60, 15);
}

void printWinMessage(){
  fill(225);
  textSize(36);
  textAlign(CENTER);
  text("YOU WIN", width/2, height*2/3);
}

void printPauseMessage(){
  fill(128);
  textSize(16);
  textAlign(CENTER);
  text("Press button to continue", width/2, height*5/6);
}

void updateGame(){
  if(ballDropped()){
    initBall();
    paused=true;
  } else{
    checkBrickCollision();
    checkWallCollision();
    checkPaddleCollision();
    px+=vx;
    py+=vy;
  }
}

boolean ballDropped(){
  return py+vy> height - BALL_RADIUS;
}

boolean inXRange(final int row, final int v){
  return px + v > row*BRICK_WIDTH&&
         px+v < (row+1)*BRICK_WIDTH+BALL_DIAMETER;
}

boolean inYRange(final int col, final int v){
  return py+v> col*BRICK_HEIGHT&&
         py+v< (col+1)*BRICK_HEIGHT+BALL_DIAMETER;
}

void checkBrickCollision(){
  for(int x=0; x<COLUMNS; x++){
    for(int y=0; y<ROWS; y++){
      if(bricks[x][y]>0){
        if(inXRange(x, vx)&& inYRange(y, vy)){
          bricks[x][y]=0;
          if(inXRange(x, 0))
          vy=-vy;
          if(inYRange(y, 0))
          vx=-vx;
        }
      }
    }
  }
}

void checkWallCollision(){
  if(px+vx < BALL_RADIUS || px+vx > width - BALL_RADIUS)
  vx=-vx;
  
  if(py+vy < BALL_RADIUS || py+vy > height - BALL_RADIUS)
  vy=-vy;
}

void checkPaddleCollision(){
  final int cx=xpos;
  if(py+vy >=height - (PADDLE_HEIGHT + MARGIN + 6)&&
    px >= cx - PADDLE_WIDTH/2 &&
    px <= cx + PADDLE_WIDTH/2)
    {
      vy=-vy;
      vx=int(
        map(
          px - cx,
          -(PADDLE_WIDTH/2), PADDLE_WIDTH/2,
          -MAX_VELOCITY,
          MAX_VELOCITY
        )
      );
    }
}

void serialEvent(Serial port){
  final String arduinoData=port.readStringUntil(LINE_FEED);
  if(arduinoData!=null){
   println(arduinoData);
   final int[] data=int(split(trim(arduinoData), ' '));
    if(data.length==4){
      buttonPressed=(data[3]==1);
    if(buttonPressed){
        paused= !paused;
        if(done){
          done=false;
          initGame();
        }
      }
      
      if(!paused)
      xpos=int(map(data[0]-2000, 252, 443, 0, 300));
    }
  }
}
Arduino codeArduino
#include <Bounce.h>
#include <Wire.h>

const unsigned int Button_Pin=7;
const int MPU=0x68; 
int16_t AcX,AcY,AcZ;
const int NUM_AXES=3;
  
const int BUFFER_SIZE=16;
int buffer[NUM_AXES][BUFFER_SIZE];
int buffer_pos[NUM_AXES]={0};
Bounce button(Button_Pin, 20);

void setup(){
  Wire.begin();
  Wire.beginTransmission(MPU);
  Wire.write(0x6B); 
  Wire.write(0);    
  Wire.endTransmission(true);
  Serial.begin(19200);
  pinMode(Button_Pin, INPUT);
}

int get_axis(const int axis){
  delay(1);
  buffer[axis][buffer_pos[axis]]=Wire.read()<<8|Wire.read();
  buffer_pos[axis]=(buffer_pos[axis]+1)%BUFFER_SIZE;
  long sum=0;
  for(int i=0; i<BUFFER_SIZE; i++)
  sum+= buffer[axis][i];
  return round(sum/BUFFER_SIZE);
  }
  
  int get_x(){return get_axis(0);}
  int get_y(){return get_axis(1);}
  int get_z(){return get_axis(2);}
    
void loop(){
  Wire.beginTransmission(MPU);
  Wire.write(0x3B);  
  Wire.endTransmission(false);
  Wire.requestFrom(MPU,6,true);
  Serial.print(get_x());
  Serial.print(" ");
  Serial.print(get_y());
  Serial.print(" ");
  Serial.print(get_z());
  Serial.print(" ");
  if(button.update())
    Serial.println(button.read()==HIGH ? "1" : "0");
  else
    Serial.println("0");
    
  delay(50);
}

Comments

Similar projects you might like

Hacking My Toaster

Project tutorial by javier muñoz sáez

  • 362 views
  • 5 comments
  • 9 respects

Rickroll Box

Project showcase by slagestee

  • 1,294 views
  • 0 comments
  • 4 respects

Gyroscope Fun with NeoPixel Ring

Project tutorial by danionescu

  • 1,443 views
  • 0 comments
  • 5 respects

START: A STandalone ARduino Terminal

Project tutorial by Alessio Villa

  • 1,039 views
  • 0 comments
  • 6 respects

Music Reactive LED Strip

Project showcase by buzzandy

  • 406 views
  • 2 comments
  • 10 respects

Pavlov's Cat

Project tutorial by Arduino

  • 755 views
  • 0 comments
  • 2 respects
Add projectSign up / Login