HTML5-Breakout

It was a time to move onward from the Pong implementations and now concentrate on a “new” game. I decided to pick a natural successor for the Pong implementation, where I could study and bring up some more advanced techniques while still maintaining a simple and small game structure. As an old Arkanoid fan, I decided that I should make an implementation of the legendary Breakout game where it all began.

At the beginning…

When this project was started, I already knew that I could reuse some parts from my previous HTML5-Pong implementation. There quite many similar parts that could be almost identically reused. For example, both games have a ball, paddle and score markers which almost have an identical behavior with some exceptions. However, Breakout also brings up some new elements along with some complexity as we need to handle brick destruction and to maintain a bit more detailed scene state especially when the game is played with two players.

This time I also decided to draw a small plan about what kind of elements are required within the court scene i.e. the scene where the players play the game. Here’s what I got.

breakout-plan (1)
A court scene plan for the Breakout game implementation.

I derived this plan by collecting information from different sources around the internet. In all implementations, the court scene has three walls i.e. at the top, right and left side of the court. These walls can be collided with the ball in a similar way that was used in Pong. Court also contains bricks that must be destroyed after the ball hits them. The color of the destructed brick defines the amount of points player receives. The player index, ball index and score indicators at the top of the scene are visible objects that cannot be collided with.

Note that there is an exception (i.e. exclamation mark) at the player score indicators. This means that the leftmost number is actually being hidden until the corresponding player receives >= 1000 points. The game typically contains two identically constructed levels, which correspond to the image shown above. Players gain points from bricks with the following definitions.

  • 1 point from yellow bricks.
  • 3 points from green bricks.
  • 5 points from orange bricks.
  • 7 points from red bricks.

This means that players can get (28 * 1) + (28 * 3) + (28 * 5) + (28 * 7) = 448 points from each level. As each player may normally play two full levels, they may achieve the total of 2 * 448 = 896 points from the game. However, there is a secret way to get even more points (i.e. over 1000 points) in the two player mode. This is possible by finishing the first level as the first player with the third (i.e. the last ball) and allowing the ball to go off the screen before it hits anything. After this happens, the second player receives a third level that he/she can play after finishing the second level where the game normally ends. This secret trick allows the second player to achieve over 1000 points, where we would also need to make the fourth score indicator to became visible.

Well… That was a quite long start for this journey. However, this game has a bit more complex logic so I think it’s quite good to go deeply through the plans before we step into some implementation details.

Game structure

The structure of the game contains only two global scenes. One scene for the welcome view and one for the gameplay. Welcome view contains the play instructions i.e. controls and a transition into the court scene where the gameplay magic happens. The transition to court scene is applied after the user selects the desired amount of players i.e 1 or 2.

I first started to implement game components in a similar way than I did with the Pong. However, I decided to switch into a different construction strategy after a while as I also wanted to try something different this time. This led the game implementation to use construct entities in the court scene are JavaScript constructor functions. I’m still not quite sure whether this approach is technically better or worse than the previous. But it made some parts of the code a bit more easier to read and follow.

This time I also wanted to use a bit more advanced version of the main loop. Now the main loop uses delta times to maintain a consistent game execution. Each main loop iteration will call scene update with a constant frame update value. Iteration delta is accumulated into a delta accumulator, which is used to consume constant frame update values. The procedure looks looks like following.

  function run(tickTime) {
    // calculate delta time and store current tick time.
    var dt = (tickTime - prevTickTime);
    prevTickTime = tickTime;

    // update and draw the scene only when we have reasonable delta.
    if (dt < 100) {
      deltaAccumulator += dt;
      while (deltaAccumulator >= FPS) {
        scene.update(FPS);
        deltaAccumulator -= FPS;
      }

      // swipe old contents from the draw buffer and draw the scene.
      ctx.clearRect(0, 0, canvas.width, canvas.height);
      scene.draw();
    }

    // perform a main loop iteration.
    requestAnimationFrame(run);
  }

The game ends in a bit differently than Pong. Quite many implementations seemed to follow a similar functionality when the game ends i.e. when the last player loses the third ball. When this happens, the paddle is stretched to fit the whole width of the court scene and the ball is left randomly bouncing around the court. In this state, the ball does cannot break any bricks anymore and cannot leave the court. This end simulation runs until the game gets a reset which can be applied by reloading the page.

Game entities

Some game entities could be almost copy-pasted from the original Pong implementation. Entities again use simple AABBs for collision detection and the movement of the ball and the paddle and the ball-wall collisions work in a similar way than what we used in Pong.

However, this time I wanted to make some things a bit differently. Our Pong implementation handled paddle-ball collisions simply by mirroring the ball movement direction. In contrast, our new paddle-ball collision does now support a relative position detection to select the new movement direction for the ball. This makes the paddle-ball hit detection a bit more interesting as the player has more control over the ball. Here’s the formula that was used in the algorithm.

breakout-paddle
A formula for calculating a new x-direction for the ball in a ball-paddle collision.

Collisions between the ball and the bricks were quite interesting. It was quite easy to handle simple collisions where the ball collides with a brick from the top or bottom side of the brick. Here we could simply just mirror the ball direction and make the brick to disappear. However, when the ball hit a brick from the side, the new direction would require some fancy logic to avoid being just randomly mirrored regarding the current direction of the ball. I had some good LOL moments when I played the game with the first version of the ball-brick collision behavior. Ball was somewhat messed up while the collisions were handled in a totally weird way. Then… I figured out that quite many Breakout clones (not sure if also the original) uses a technique which allows the ball to only break one brick at a time. This means that the ball can hit with one brick and then it requires either a hit with the paddle or any of the three walls before it can break an another brick. I decided to take this as a shortcut and it saved my day.

Summary

breakout-ingame

Again, I’m quite satisfied with the overall results. Game can be played with either one or two players and the simulation seems to run in consistently. Players can achieve points and compete against each other. I even managed to implement the logic required for the “secret” way to achieve the third level for the second player as was mentioned at the beginning part of this post.

It was nice to try some new tricks with JavaScript with object constructions and with the requestAnimationFrame function. However, the best part of this project was absolutely to get more familiar with the rules and tricks from of original Breakout game. I somehow now feel that I like these games even more! Damn… Game development is fun!

Thanks for reading!

Game is playable in GitHub Pages: https://toivjon.github.io/html5-breakout/

Game source code in GitHub: https://github.com/toivjon/html5-breakout

 

2 thoughts on “HTML5-Breakout

Leave a comment