Seb Lee-Delisle


Multi-touch game controller in JavaScript/HTML5 for iPad

Now that browser-based games running on touch devices are becoming a reality, it’s time to figure out how to implement easy to use and tactile game controls in these new keyboard-less environments.

I’ve long been a fan of how the twin-stick touch controls work in Geometry Wars Touch, so I wasn’t surprised to find that Brighton game UX expert Graham McAllistair also considered this “dynamic display on touch” interface to be the best option for analogue controls.

So last week at my creativeJS training course in Brighton (only four tickets left for the San Francisco event ๐Ÿ™‚ ) we started experimenting with multi-touch points in JavaScript with the aim of making a game controller that works on iPhone and iPad.

The natural first step : figure out how to get the touch data in JS. It’s actually pretty easy – there are three events that are broadcast by any DOM element that can be touched, touchstart, touchmove and touchend. But before you do that, you probably want to check that you’re running in a touch-able environment. And you can do that by checking that createTouch is a property of the document:

	var touchable = 'createTouch' in document;

If this is true, you can add event listeners to your canvas element like this :

if(touchable) {
	canvas.addEventListener( 'touchstart', onTouchStart, false );
	canvas.addEventListener( 'touchmove', onTouchMove, false );
	canvas.addEventListener( 'touchend', onTouchEnd, false );

And then you define each of the functions specified :

function onTouchStart(event) {
	//do stuff
function onTouchMove(event) {
	 // Prevent the browser from doing its default thing (scroll, zoom)
function onTouchEnd(event) { 
	//do stuff

In each touch listener, event is the object that provides all the touch data, and it contains three arrays:

event.touches : all of the current touches
event.targetTouches : all the touches that originated from the DOM element
event.changedTouches : only the touches that triggered the event.

For touchstart and touchend, changedTouches usually only contains one touch event (unless you just happened to touch two fingers at exactly the same time).

Each array contains touch data objects with the following properties :

identifier: An unique number that allows you to track touch events as they move
target: the DOM element that broadcast that event
clientX, clientY: touch position relative to the viewport
screenX, screenY: touch position relative to the screen
pageX, pageY: touch position relative to the full page

Call event.preventDefault(); on a touchmove event to disable the automatic scrolling you normally get on touch devices.

I found this full explanation on SitePen really helpful.

So a quick test for iPad revealed that you could have 11 concurrent touch points (cue infantile jokes about what to use after you’ve run out of fingers…)

Try it here on a touch device or if you don’t have one handy you can watch this video:

So how to turn this into a game controller? Easy! If we pick up a touch down on the left side of the screen, we’ll use that as the centre point of our analogue control, and keep track of that touch ID. I use my 2D vector class to work out the vector between the current touch position and the original touch down position. We can then use that difference vector to dictate the velocity of the ship.

While we have a touch on the left we can ignore other touches on that side of the screen. If we get a touch on the right side, we assume that’s a fire button. It’s a pretty simple system.

Try it here on a touch device.

I’ve started to optimise this for iOS by converting the ship into a single canvas that I’m moving around, but didn’t finish yet. Currently the bullets and the touch circles are being drawn into canvas every frame, so it’s not quite as performant on the iPad1 (pre iOS update) as it could be.

The source is on git hub – I expect I’ll be improving it over the coming months, but please feel free to fork it if you have any suggestions!

This entry was posted in HTML5 Canvas, iOS, javascript. Bookmark the permalink.

33 Responses to Multi-touch game controller in JavaScript/HTML5 for iPad