Tutorial: How to make a top-down shooter in JavaScript

Lesson 2) Drawing on the canvas

Experimenting with form and colour… aka drawing rectangles and stuff

For the main canvas area, we can make some basic changes to the CSS just as with any other HTML element. Let’s add some colour by adding:

background: green;

This creates a nice grassy area in which our epic battle will take place.

Now let’s try drawing some stuff on the canvas. To do so, we need to add JavaScript code — since we’re making this game in a single file, we’ll put that between our <script> tags. However, we also need to tell the browser to go read it.

To do this, we’ll put all of our code in a function. A function is simply a snippet of code that we’ve put aside and given a name. At any point in our program, we can run the function by invoking its name. The browser will the go off, run that bit of code, and then come back to where it was before.

So in the script tags, add this code:

function init() {

}

We’ve called this function init, short for initialise, which is the conventional name for a function that does this job. Then edit the body tag to look like this:

<body onload="init()">

You could run init() from anywhere in your HTML file by putting it inside script tags, for example:

<script>init();</script>

However, because our program will refer to the canvas we drew earlier, we need to load the canvas before we run our JavaScript program. Otherwise, the browser will say “canvas is null”, which could be roughly translated as “canvas? What canvas?” If you put it in the body tag like this, the browser will run init() after everything inside the body tags has been loaded — including, of course, the canvas.

Now that we’ve told the HTML about the JavaScript code, we need to define the canvas. So add the following inside the init() function:

var canvas = document.getElementById("canvas");
canvas.width = 800;
canvas.height = 600;
var c = canvas.getContext("2d");

This creates a variable called “canvas” linked to the element we created in the previous lesson. We set the width and height of the canvas to what we want them to be — 800 by 600, in this case.

Next we create a variable called “c”, also known as the “context.” Some people call this variable “ctx” but I like just “c” because it’s quicker to type. You need to use this object anytime you draw anything on the canvas. Think of it as your brush.

With a real canvas, you need to dab your brush in some paint and then decide what you are going to do before you actually do it. So it is with a digital canvas.

Let’s draw a rectangle with one of the context’s built in functions, “rect”:

c.fillStyle="red";
c.strokeStyle="blue";
c.rect(10,10,10,100);
c.lineWidth=4;
c.stroke();
c.fill();

With fillStyle, you’re choosing what color you want to fill the rectangle with (dipping the brush in the red paint pot, in this case), but you don’t put your brush to the canvas, as it were, until you use fill(). The other two commands, strokeStyle and stroke() do the same thing for the border around the rectangle. Remember to add the parentheses after fill() and stroke(), and remember your semi-colons. One character out of place will mess up your whole program.

As for the c.rect command itself, the numbers represent the x and y coordinates of the upper-left corner of the rectangle (important note: on the canvas the coordinates 0,0 are in the upper-left corner. So as y coordinates increase, elements move further down the the screen). The last two numbers are its width and height in pixels relative to its coordinates – again its height goes DOWN the canvas.

The canvas has many functions to draw things – rectangles, lines, arcs (and therefore circles), text — it can even import images. If you can get some good sprites you’ll want to use them in your game, but for this lesson we’re going retro, and drawing simple shapes with these built in methods.

Look up these methods online and have a play around, see if you can draw something, even just a few shapes, on the canvas. I’ve done the same, here’s what I came up with:

A note on scale

You may have noticed we’ve got two sets of width and height variables for the canvas: one in the JavaScript code (this bit: canvas.width = 800;), and one in the HTML tag (this bit: <canvas id=”canvas” width=”800″ height=”600″ tabindex=’1′>). This is actually redundant. Try removing one of these, and reload the page. No effect. Now put it back, and remove the other one. No effect again. (Note: the JavaScript one takes precedence if both are present, because the JavaScript code was run most recently)

Now, remove both. The canvas shrinks down to 300 x 150 pixels – this is the default size that gets used if you don’t define it yourself. But notice that you can only see the elements that exist within this 300 x 150 pixel window.  So if you draw something outside of this area (like my box), it won’t appear.

However, if you set the canvas back to 800 by 600, and then go to the CSS code for the canvas and add the following:

canvas {
 display:block;
 border: solid 1px black;
 position:relative;
 margin: 0 auto 0 auto;
 background: url('background.png');
 width: 300px;
 height: 150px;
}

You’ll find that everything within the canvas has been scaled to fit the 300 x 150 pixel size that you specified.

This method works just the same as if you had a JPEG image which was 800px by 600px, and you told the browser to display it as 300px by 150px. The browser doesn’t just crop the image to that size – it resizes it. Only in this case you have a canvas instead of a JPEG file.

If you’ve used both an actual width and a CSS width, remember to refer to the actual width when you’re creating and positioning things within the canvas, and the CSS width when positioning things around it (that is, the other things on the web page besides the canvas). Thanks VeryAngryBeaver for the suggestion to add this section on scale!

Leave a Reply

Your email address will not be published. Required fields are marked *