animation n.
Skip this Video
Loading SlideShow in 5 Seconds..
Animation PowerPoint Presentation


113 Views Download Presentation
Download Presentation


- - - - - - - - - - - - - - - - - - - - - - - - - - - E N D - - - - - - - - - - - - - - - - - - - - - - - - - - -
Presentation Transcript

  1. Animation • Most games have moving components, how do we make things move? • We will track the location of an object using an x,y coordinate • We will draw the item onto a Graphics object in paintComponent • But we need to change x,y from time to time to give it movement • How? • Java has a built-in class called Timer • The Timer generates an ActionEvent every few milliseconds • The ActionEvent calls the actionPerformed method • In actionPerformed, we change x,y and then do repaint() • This requires adding to our program • ActionListener and actionPerformed method • Timer object • paintComponent method

  2. Timer class • A Timer object is instantiated by: • Timer t = new Timer(duration, handler); • duration is the time (in milliseconds) that elapses between Timer-generated events, such as 20 or 50 ms • handler is the object that handles the Timer-generated events – we will use this just like we have for our addActionListener statements • The steps are to add • import java.awt.event.*; • “implements ActionListener” to our class header • declare the Timer as a class variable: private Timer t; • instantiate the Timer: t = new Timer(10, this); • but use whatever value you want for the duration, 10 or 20 would be adequate for most applications • start the timer: t.start( ); • if we need to stop the timer: t.stop( ); • That’s about all there is to it!

  3. import javax.swing.*; import java.awt.event.*; public class TimerSkeleton implements ActionListener { private Timer t; // other instance data go here as needed public TimerSkeleton( ) { t = new Timer(10, this); t.start( ); // other initialization operations go here as needed } // other methods go here as needed public void actionPerformed(ActionEvent e) { // whatever you want to happen when the Timer pulses go here } } TimerSkeleton

  4. What Should actionPerformed Do? • This depends on why you are using a Timer • To move an object in a Graphics panel (e.g., a ball) • alter the x and y coordinates of the ball and call repaint( ) • For a Game • calculate where game objects (say a spacecraft or a missile) have moved and redraw them • you might have multiple objects to move, move them all • if you have a variable number of objects, use an array (or two arrays, x[] and y[]) • For Animation • if our item being drawn is represented by an array of different figures • then just increment the array index and repaint( ) • you might pre-load an array of Images for drawImage where each image is slightly different from the previous one • In any case, in actionPerformed, also make sure the object has not been moved off the screen

  5. Moving an Image to Create Motion • Imagine that your class draws on a JPanel an ImageIcon (say of a spaceship) • currently, the spaceship is located at coordinates x, y • the following actionPerformed method will randomly move the spaceship on the screen • x and y should be class variables so that you could do g.drawImage(image, x, y, this); in your paintComponent method public void actionPerformed(ActionEvent e) { int dx = generator.nextInt(2); // generate a # from -1 to +1 int dy = generator.nextInt(2); // generate a # from -1 to +1 x += dx; // move the piece in a random x direction y += dy; // move the piece in a random y direction repaint( ); // assume repaint does drawImage at x, y }

  6. Full Example Code public TimerExample( ) { t = new Timer(10, this); t.start( ); x = 150; y = 150; repaint( ); } public void actionPerformed(ActionEvent ev) { int distanceX = generator.nextInt(2)); int distanceY = generator.nextInt(2)); x += distanceX; y += distanceY; repaint( ); } public void paintComponent(Graphics g) { super.paintComponent(g); g.setColor(; g.fillOval(x, y, 5, 5); } At each Timer Event, randomly move the object (a red circle) up/down/left/right by 0 or 1 unit Note: we could make it more realistic by generating a random int from 1-9 and move it in one of 8 directions or leave it stationary (1 = upper left, or subtract 1 from x and y, 2 = straight up, etc)

  7. Better Motion • The random motion from the previous example would make the object on the screen look like a bee, buzzing around • What if we wanted a more purposeful movement? For instance in a straight line? • Lets add 2 more variables, dx and dy • (delta x means “change in x”, delta y means “change in y”, we use d because we don’t have the Greek letter delta) • For actionPerformed, just do x=x+dx; y=y+dy; • If dx=1 and dy=2, then our object will move in a straight line to the right 1 pixel and down 2 pixels at each movement, or a diagonal downward line • If dx=0 and dy=-1, then the object moves straight up • We do not want dx=0 and dy=0, why not?

  8. Dealing With Edges/Borders • Imagine we start our object at x=0, y=0 and use dx=1, dy=1 • The animation will move the object steadily down to the right but eventually (quickly) the object will move right off the screen • this does not cause an error, but it removes the object from our graphics panel • We want to deal with borders, how? • Wrap-around: if(x>=X_SIZE-20) x=20; if(x<=20) x=X_SIZE-20; • Stop: if(x>=X_SIZE-20||x<=20) dx=0; • Bounce: if(x>=X_SIZE||x<=20) dx*=-1; • Random bounce: if(x>=X_SIZE||x<=20) dx=gen.nextInt(5)-2; • we would similarly handle y and dy • we might change dx and dy whenever the object hits any edge

  9. Handling Multiple ActionEvents private static class ExamplePanel extends JPanel implements ActionListener { private Timer t; private JButton b; public ExamplePanel( ) { t = new Timer(1000, this); t.start(); b = new JButton("Button"); b.addActionListener(this); add(b); } public void actionPerformed(ActionEvent e) { if(e.getSource( )==t) System.out.println("Timer pulsed"); else if(e.getSource( )==b) System.out.println("Button pressed"); } }

  10. Moving Multiple Items • How would a game like Asteroids work? • we need to keep track of the <x, y> coordinates of multiple values, just like we did with our paint program • so we create an array of x, y, dx and dy int values • private int[ ] x, y, dx, dy; // dx, dy – velocity of x, y • private int num; // number of items in the arrays • actionPerformed now manipulates all items in the array and paintComponent draws them all public void actionPerformed(ActionEvent e) { for(int i=0;i<num;i++) { x[i]+=dx[i]; y[i]+=dy[i]; } } If x[i] or y[i] reaches a boundary (0 or max X/Y) then change dx or dy to be the opposite (multiply by -1)

  11. Determining Collisions • For a shooting game, we want to see if we actually successfully shot the object, how? • We will have two x,y values, we will call them mx, my (for me) and ex, ey (for enemy) • We can’t just see if mx==ex&&my==ey because those compare individual pixels and our objects will be larger • Assume that the “enemy” is a circle whose bounding box starts at ex,ey and is 10x10 • the center of the enemy is actually ex+5,ey+5 • our “missile”, mx, my needs to touch some part of that circle, which means that Math.abs(mx-(ex+5))<=5&&Math.abs(my-(ey+5))<=5 – that is, our object is somewhere within the radius of the enemy • If our object is something different from a small missile/bullet or the enemy is different from a round shape, it becomes a bit more challenging

  12. Bouncing Balls • Today we will work with a ball class and make several of them bounce around the screen • A ball will comprise its current location (x, y), its velocity (dx, dy), a size and a color • The ball will be able to move itself • x+=dx; y+=dy; but also check to see if it is at a border • The ball will be able to change direction or rebound • change dx and dy, either multiply them by -1, or change them randomly • The ball will be able to draw itself on a Graphics object • The ball will be able to determine if it has collided with another ball (passed as a parameter) • The ball will be able to change its own size • The ball will have to be able to return its own x value, y value and size (to be used later)

  13. Bouncing Balls Program • We will start with an array of balls • We can either randomly generate their initial locations or we can use the MouseListener so that the user can place them on the Graphics Panel by clicking • The timer starts and in actionPerformed, we use a for loop to iterate through each ball and do b[i].move(); (assuming our balls are stored in an array b) • If we want to handle collisions • In actionPerformed, each time we move a ball, we use another (nested) for loop to iterate through the other balls and text b[i].collide(b[j]) – this is true if b[i] and b[j] overlap at all • If true, we want to change one or both balls’ directions by doing b[i].bounce(); b[j].bounce();

  14. Ball Game • The game for today is similar to the BouncingBalls program • The user, using the mouse, places several balls in the graphics area • As a ball collides with another, one ball disappears and the other grows in size • if(b[i].collide(b[j])) { b[i].grow(b[j].size/2); b[j]=null;) • notice that with each collision, there is 1 fewer balls but the other ball remaining has grown, so what we get as time goes on are fewer and fewer but larger and larger balls • The game goes until there is only 1 ball left on the screen • We can output the amount of time that has elapsed, the idea is to see how long you can go before you are down to 1 ball