Question

In: Electrical Engineering

This is a code for a bouncing ball on an 8X8 LED. How can i change...

This is a code for a bouncing ball on an 8X8 LED. How can i change the code to make it a ping pong game against AI by adding 1 potentionmeter to control it?

#include <TimerOne.h>//this is a library that uses timer 1 of the arduino to trigger interrupts in certain time intervals

//This defines a matrix defining a smiley face for the 8x8 LED matrix display
#define BALL { \
{1, 0, 0, 0, 0, 0, 0, 0}, \
{0, 0, 0, 0, 0, 0, 0, 0}, \
{0, 0, 0, 0, 0, 0, 0, 0}, \
{0, 0, 0, 0, 0, 0, 0, 0}, \
{0, 0, 0, 0, 0, 0, 0, 0}, \
{0, 0, 0, 0, 0, 0, 0, 0}, \
{0, 0, 0, 0, 0, 0, 0, 0}, \
{0, 0, 0, 0, 0, 0, 0, 0} \
}


/*Arduino pin --> Display pin----->8x8 matrix row and column coordinates (1;1) origin
D2-------------->9---------------------->row 1
D3-------------->10-------------------->col 4
D4-------------->11-------------------->col 6
D5-------------->12--------------------->row 4
D6-------------->13-------------------->col 1
D7-------------->14--------------------->row 2
D8-------------->15-------------------->col 7
D9-------------->16-------------------->col 8
D10------------->4--------------------->col 3
D11------------->3--------------------->col 2
D12------------->2---------------------->row 7
D13------------->1---------------------->row 5
A0 (D14)-------->5---------------------->row 8
A1 (D15)-------->6--------------------->col 5
A2 (D16)-------->7---------------------->row 6
A3 (D17)-------->8---------------------->row 3

*/


//rows:
const int col[8] = {
2,7,17,5,13,16,12,14 };//these are the Arduino pins that connect to the anodes (1-8) of the LEDs

//columns:
const int row[8] = {
6,11,10,3,15,4,8,9 };//these are the Arduino pins that connect to the cathodes (1-8) of the LEDs

int x = 0;
int y = 0;
int dx = 1;
int dy = 1;

volatile byte c,r,flag,counter;//interrupt routine variables, they need to be specified as 'volatile'

// 2-dimensional array that contains the currently 'ON' LEDs in the matrix ('1'='ON'); this is used in the refreshScreen() ISR below:
byte pattern[8][8] = BALL;

unsigned long previousMillis = 0; //last time we switched patterns [ms]
unsigned long interval = 1000; //time between switching [ms]
int currentPattern = 0; //0 for "Ball", 1 for "Ball2", 2 for "Ball3", 3 for "Ball4"

void setup() {
// initialize the row and column pins as outputs
// iterate through the pins:
for (int pin = 0; pin < 8; pin++) {
// initialize the output pins:
pinMode(col[pin], OUTPUT);
digitalWrite(col[pin], HIGH);
pinMode(row[pin], OUTPUT);
digitalWrite(row[pin], LOW);
// take the col pins (i.e. the cathodes) high and the row pins (anodes) low to ensure that
// the LEDS are off:   
}
Timer1.initialize(100); // initialize timer1, and set a 100 us second period for the interrupt interval (i.e. the ISR will be called
//every 100 us - this seems to be a good frequency to achieve a flicker-free LED display.
//experiment with this parameter. If it gets too small the ISR starts 'eating up' all the processor time, and the main loop becomes very slow
Timer1.attachInterrupt(refreshScreen); // attaches the refreshScreen() function as 'Interrupt Service Routine' (ISR) to the interrupt
//this means that every time 100 us have passed, the refreshScreen() routine will be called.
}

//main loop...here we can simply busy ourselves with changing the pattern[][] array; nothing deals with the LED display.
//this is all handled via the ISR
void loop() {
if (x>=7)
{ dx = -1;
dy = random(-1,1);
}
if(x<=0)
{
dx = 1;
dy = random(-1,1);
}
if (y>=7)
{dy = -1;
dx = random(-1,1);
}
if (y<=0)
{ dy = 1;
dx = random(-1,1);
}
pattern[x][y] = 0;
pattern[x+dx][y+dy]=1;
x=x+dx;
y=y+dy;
delay(50);

Solutions

Expert Solution

#include "LedControl.h"
#include "Timer.h"
 
#define POTPIN A5 // Potentiometer
#define PADSIZE 3
#define BALL_DELAY 200
#define GAME_DELAY 10
#define BOUNCE_VERTICAL 1
#define BOUNCE_HORIZONTAL -1
#define NEW_GAME_ANIMATION_SPEED 50
#define HIT_NONE 0
#define HIT_CENTER 1
#define HIT_LEFT 2
#define HIT_RIGHT 3
 
//#define DEBUG 1
 
byte sad[] = {
B00000000,
B01000100,
B00010000,
B00010000,
B00000000,
B00111000,
B01000100,
B00000000
};
 
byte smile[] = {
B00000000,
B01000100,
B00010000,
B00010000,
B00010000,
B01000100,
B00111000,
B00000000
};
 
Timer timer;
 
LedControl lc = LedControl(12,11,10,1);
 
byte direction; // Wind rose, 0 is north
int xball;
int yball;
int yball_prev;
byte xpad;
int ball_timer;
 
void setSprite(byte *sprite){
    for(int r = 0; r < 8; r++){
        lc.setRow(0, r, sprite[r]);
    }
}
 
void newGame() {
    lc.clearDisplay(0);
    // initial position
    xball = random(1, 7);
    yball = 1;
    direction = random(3, 6); // Go south
    for(int r = 0; r < 8; r++){
        for(int c = 0; c < 8; c++){
            lc.setLed(0, r, c, HIGH);
            delay(NEW_GAME_ANIMATION_SPEED);
        }
    }
    setSprite(smile);
    delay(1500);
    lc.clearDisplay(0);
}
 
void setPad() {
    xpad = map(analogRead(POTPIN), 0, 1020, 8 - PADSIZE, 0);
}
 
void debug(const char* desc){
#ifdef DEBUG
    Serial.print(desc);
    Serial.print(" XY: ");
    Serial.print(xball);
    Serial.print(", ");
    Serial.print(yball);
    Serial.print(" XPAD: ");
    Serial.print(xpad);
    Serial.print(" DIR: ");
    Serial.println(direction);
#endif
}
 
int checkBounce() {
    if(!xball || !yball || xball == 7 || yball == 6){
        int bounce = (yball == 0 || yball == 6) ? BOUNCE_HORIZONTAL : BOUNCE_VERTICAL;
#ifdef DEBUG
        debug(bounce == BOUNCE_HORIZONTAL ? "HORIZONTAL" : "VERTICAL");
#endif
        return bounce;
    }
    return 0;
}
 
int getHit() {
    if(yball != 6 || xball < xpad || xball > xpad + PADSIZE){
        return HIT_NONE;
    }
    if(xball == xpad + PADSIZE / 2){
        return HIT_CENTER;
    }
    return xball < xpad + PADSIZE / 2 ? HIT_LEFT : HIT_RIGHT;
}
 
bool checkLoose() {
    return yball == 6 && getHit() == HIT_NONE;
}
 
void moveBall() {
    debug("MOVE");
    int bounce = checkBounce();
    if(bounce) {
        switch(direction){
            case 0:
                direction = 4;
            break;
            case 1:
                direction = (bounce == BOUNCE_VERTICAL) ? 7 : 3;
            break;
            case 2:
                direction = 6;
            break;
            case 6:
                direction = 2;
            break;
            case 7:
                direction = (bounce == BOUNCE_VERTICAL) ? 1 : 5;
            break;
            case 5:
                direction = (bounce == BOUNCE_VERTICAL) ? 3 : 7;
            break;
            case 3:
                direction = (bounce == BOUNCE_VERTICAL) ? 5 : 1;
            break;
            case 4:
                direction = 0;
            break;
        }
        debug("->");
    }
 
    // Check hit: modify direction is left or right
    switch(getHit()){
        case HIT_LEFT:
            if(direction == 0){
                direction =  7;
            } else if (direction == 1){
                direction = 0;
            }
        break;
        case HIT_RIGHT:
            if(direction == 0){
                direction = 1;
            } else if(direction == 7){
                direction = 0;
            }
        break;
    }
 
    // Check orthogonal directions and borders ...
    if((direction == 0 && xball == 0) || (direction == 4 && xball == 7)){
        direction++;
    }
    if(direction == 0 && xball == 7){
        direction = 7;
    }
    if(direction == 4 && xball == 0){
        direction = 3;
    }
    if(direction == 2 && yball == 0){
        direction = 3;
    }
    if(direction == 2 && yball == 6){
        direction = 1;
    }
    if(direction == 6 && yball == 0){
        direction = 5;
    }
    if(direction == 6 && yball == 6){
        direction = 7;
    }
    
    // "Corner" case
    if(xball == 0 && yball == 0){
        direction = 3;
    }
    if(xball == 0 && yball == 6){
        direction = 1;
    }
    if(xball == 7 && yball == 6){
        direction = 7;
    }
    if(xball == 7 && yball == 0){
        direction = 5;
    }
 
    yball_prev = yball;
    if(2 < direction && direction < 6) {
        yball++;
    } else if(direction != 6 && direction != 2) {
        yball--;
    }
    if(0 < direction && direction < 4) {
        xball++;
    } else if(direction != 0 && direction != 4) {
        xball--;
    }
    xball = max(0, min(7, xball));
    yball = max(0, min(6, yball));
    debug("AFTER MOVE");
}
 
void gameOver() {
    setSprite(sad);
    delay(1500);
    lc.clearDisplay(0);
}
 
void drawGame() {
    if(yball_prev != yball){
        lc.setRow(0, yball_prev, 0);
    }
    lc.setRow(0, yball, byte(1 << (xball)));
    byte padmap = byte(0xFF >> (8 - PADSIZE) << xpad) ;
#ifdef DEBUG
    //Serial.println(padmap, BIN);
#endif
    lc.setRow(0, 7, padmap);
}
 
void setup() {
  // The MAX72XX is in power-saving mode on startup,
  // we have to do a wakeup call
  pinMode(POTPIN, INPUT);
 
  lc.shutdown(0,false);
  // Set the brightness to a medium values
  lc.setIntensity(0, 8);
  // and clear the display
  lc.clearDisplay(0);
  randomSeed(analogRead(0));
#ifdef DEBUG
  Serial.begin(9600);
  Serial.println("Pong");
#endif
  newGame();
  ball_timer = timer.every(BALL_DELAY, moveBall);
}
 
void loop() {
    timer.update();
    // Move pad
    setPad();
#ifdef DEBUG
    Serial.println(xpad);
#endif
    // Update screen
    drawGame();
    if(checkLoose()) {
        debug("LOOSE");
        gameOver();
        newGame();
    }
    delay(GAME_DELAY);
}

Related Solutions

analysis of the trajectory of a bouncing ball?(theoretical) step by step for senior.
analysis of the trajectory of a bouncing ball?(theoretical) step by step for senior.
how can I change the Gauss-Seidel method to SOR method code in Matlab? The question has...
how can I change the Gauss-Seidel method to SOR method code in Matlab? The question has shows that In implementing SOR method in MATLAB, one should not calculate Tw and cw by formulas Tw = (D -wL)^(-1)[(1-w)D+wU)] and Cw = w(D-wL)^(-1)b , where w stands for omega and using MATLAB's built-in inv function, since this function requires O(n^3) flops and therefore the whole matter loses its point. I have tried for many times but I can't get the correct answers....
MatLab Bouncing ball When a ball is dropped from 2 m, it only has potential energy...
MatLab Bouncing ball When a ball is dropped from 2 m, it only has potential energy initially. When it hits the ground all that energy is converted to kinetic energy. Write a program that will calclate the position of the ball (y) as a function of time. Calculate y when the ball is always higher than 0.5 m. Note that every time the ball hits the ground it loses 10% of the total energy. Plot y vs. t. The mass...
a)derive the equation of motion of a bouncing ball dropped from rest (with air resistance )...
a)derive the equation of motion of a bouncing ball dropped from rest (with air resistance ) b) trajectory-- time it take to stop step by step please .
Write a VHDL code for a 8x8 bit multiplier. use structural approach. write the design code...
Write a VHDL code for a 8x8 bit multiplier. use structural approach. write the design code and testbench. Use for-generate if possible
Question 2: (2pts) Prediction of Gravitational, Kinetic and Total energy for a bouncing ball. Based on...
Question 2: (2pts) Prediction of Gravitational, Kinetic and Total energy for a bouncing ball. Based on your predictions of position and velocity vs time, explain how the energy changes during the motion of the ball. (a) Where on your position vs. time graph is the Gravitational Potential Energy at a maximum during each bounce? Where is it a minimum? What is the velocity when the gravitational potential energy is maximum? What about when the gravitational potential energy is minimum? Explain...
Change the following code to where it adds an image(leave the image blank, I can add...
Change the following code to where it adds an image(leave the image blank, I can add the image) to the question and to generate the questions and answers in a different order each time you begin the quiz. <!DOCTYPE html> <html lang="en" xmlns=""> <head> <meta charset="utf-8" /> <title>World Cup Quiz</title> </head> <body> <style> #flashcards001 { background-color: white; border: 4px solid black; width: 400px; height: 400px; border-radius: 10px; padding: 10px; margin: 10px; } .buttons001 { background-color: blue; color: white; padding: 5px;...
Change the following code to where it adds an image(leave the image blank, I can add...
Change the following code to where it adds an image(leave the image blank, I can add the image) to the question and to generate the questions and answers in a different order each time you begin the quiz. I have 10 questions but due to chegg not allowing me to post all of my code I shorted it to one question. <!DOCTYPE html> <html lang="en" xmlns=""> <head> <meta charset="utf-8" /> <title>World Cup Quiz</title> </head> <body> <style> #flashcards001 { background-color: white;...
Using Python 3 graphics, create a bouncing ball within a box. Allow the user to control...
Using Python 3 graphics, create a bouncing ball within a box. Allow the user to control the ball using their keyboard.
1. A 0.4 kg ball hits the ground (vertically) at a speed of 6 m/s, bouncing...
1. A 0.4 kg ball hits the ground (vertically) at a speed of 6 m/s, bouncing back in the opposite direction at 4 m/s. Calculate the magnitude of the impulse provided by the ground to the ball. A. 2 Ns B. 10 Ns C. 4 Ns D. 0.8 Ns 2.Calculate the recoil speed of a 1.4 kg rifle shooting 0.006 kg bullets with muzzle speed of 800 m/s A. 3.43 m/s B. 571 m/s C. 1.22 m/s D. 6.42 m/s...
ADVERTISEMENT
ADVERTISEMENT
ADVERTISEMENT