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

Lesson 5) Detecting key-press input

Moving swiftly on

At the moment we move our character - a particularly heroic red square - randomly about the screen by updating his x and y coordinates with values between -1 and 1 every time our game function looped around. To allow the player to move the character, all we do is set up a key press detector for the keys we want to use for movement, and change the player's x or y coordinates whenever we detect that one of these keys was pressed. We'll use these familar keys:

w = up
a = left
s = down
d = right

JavaScript has a number of built in "Event Listeners" that listen out for various things that can happen on a web page. There are loads of them, but we need just one of them for now: keydown.

This does exactly what you expect - detect when a key is pressed, and which key it was.

All we need to do is check if that key code relates to one of our movement keys, and if so, update our four-cornered friend's coordinates accordingly!

Pay attention, this part is key

Remove the bits of code that made out character move randomly, and then add the following outside of the mainDraw loop:
function playerMove(e){
if ( e.key === "w" ) {
player1y -= 1;
}
if ( e.key === "s" ) {
player1y += 1;
}
if ( e.key === "a" ) {
player1x -= 1;
}
if ( e.key === "d" ) {
player1x += 1;
}
return false;
}
canvas.addEventListener('keydown', playerMove, true);
We've added an event listener to the canvas. This is important so that the user can do other things on the web page without affecting the game (the user needs to click inside the canvas before input will be detected).

If our program detects a key press, it runs the playerMove function and passes an object to it. The (e) bit of our playerMove function means we've labelled that object "e" (you could label it anything you wanted, but "e" is pretty standard). This "e" object contains parameters with information about the key that was just pressed. In fact if you send e to the console (by putting "console.log(e);" into playerMove), you'll see something like the following:
keydown { target: , key: "w", charCode: 0, keyCode: 87 })
So as you can see, e has a property called "key" (in this case, the "w" key was pressed). Our playerMove function has an if statement saying that if this property, e.key, is equaly to "w", deduct 1 from Player1.y. The next time our program loops through mainDraw the rectangle representing our player will be drawn one pixel higher than it was before (I keep saying this but remember, y=0 is at the top of the canvas, so deducting numbers from y makes the player go UP the screen). Have a go yourself (remember to click inside the canvas):


OK he's moving! That's good, but would you be happy with a game where the player moved like this? I wouldn't - changing directions is not jerky, and we can't move diagonally.

This is because the event listener is only passing one object to playerMove at a time. Whatever key was pressed most recently will be passed to playerMove, and the square will move in that direction.

Next, we'll make this movement smoother.

Go to Lesson 6 - Detecting multiple key presses at once