Using Phaser in an Angular 8 Component

Braelyn Sullivan
5 min readSep 20, 2019

--

I have spent the last year developing HTML5/JavaScript games for my professional career as well as personal passion projects. One of my favorite tools for creating these games is Phaser (https://phaser.io).

Phaser is a powerful JavaScript library for building HTML5 games for mobile & desktop. It renders to WebGL & Canvas, and provides a lot of valuable tools: a built-in physics engine, animation & sprite support, input controllers, device scaling, etc.

The official Phaser logo — an animated planet with a spaceship, aliens and a hero pointing a laser gun.
The official Phaser logo

Aside from inserting the Canvas or WebGL elements to run the game, Phaser stays out of the DOM and makes no effort to host or style the presentation. Luckily, there is no shortage of other tools to address these concerns.

Angular (https://angular.io) is a very popular web framework for creating robust applications for web, mobile & desktop. It uses TypeScript in later versions and handles creating an application, structuring the presentation and bundling for deployment. It is one of the most commonly used tools to create Single Page Applications (SPAs).

The official Angular shield logo. A red shield with a large white A on it.
The official Angular logo

Phaser handles the rendering and logic of a JS game. Angular handles the presentation and structure of an application. The opportunity for integration seems natural.

Unfortunately, the actual integration is far from natural. There are slight differences in the implementation of Phaser & Angular that make integration more challenging and can initially be discouraging. These two tools can work together though, and I will show you how.

Banner vector created by roserodionova — www.freepik.com

For the rest of this article, I am assuming you’ve setup NPM and are familiar with the Angular CLI.

Create an Angular application

First, we need to create our Angular application using the Angular CLI. If you’re planning to incorporate Phaser into an existing Angular application, you can skip this step.

ng new phaser-angular-app

When prompted, add routing if you want and select the stylesheet format of your preference. Then, change directories into your newly created app:

cd phaser-angular-app/

Install and Copy Phaser files

Once we’re in our project directory, we want to install Phaser with npm:

npm i phaser

Then, we need to copy some files into our project to make Phaser work with Angular.

  • Copy phaser.d.ts from the directory /node_modules/phaser/types and paste it into your root project* folder. This provides TypeScript typings for Phaser.
  • Copy phaser.min.js from the directory /node_modules/phaser/dist and paste it into your project’s src/assets folder. This avoids the hassle of finding the correct way to constantly import Phaser into your components.

*This post has been updated to the correct folder location. Also, as noted below by Brandon, you can skip the copy steps by adding "scripts": ["node_modules/phaser/dist/phaser.min.js"] to the build settings in your angular.json file.

Update index.html

In your index.html file, we need to add a static reference to the phaser.min.js file so add this somewhere in between your <head> tags:

<script src="assets/phaser.min.js">

Additionally, Phaser’s TypeScript typings require a global variable, so we need a default in case this variable isn’t set elsewhere in our application.

<script>
if (global === undefined) {
var global = window;
}
</script>

Creating a game component

Next, we need to create a component to hold our Phaser game.

ng generate component game

When you navigate to your newly-created game.component.ts file, you should see something like this:

import { Component, OnInit } from '@angular/core';@Component({
selector: 'app-game',
templateUrl: './game.component.html',
styleUrls: ['./game.component.scss']
})
export class GameComponent implements OnInit {
constructor() { }

ngOnInit() {
}
}

Now, let’s add our newly created component to the landing page of our application. Open app.component.html and delete everything (except <router-outlet></router-outlet> if you chose to add routing). Add our new component by placing <app-game></app-game> somewhere in this file.

When we run our application with ng serve --open, we’ll be taken to localhost:4200 and you should see a blank page. We’ve got our app up and running!

Importing Phaser into our game component

In game.component.ts, add the following import under the other import statements:

import Phaser from 'phaser';

If you’re using a TypeScript compiler in your IDE, TypeScript will likely complain and throw an error here: “This module is declared with using ‘export =’, and can only be used with a default import when using the ‘allowSyntheticDefaultImports’ flag.

This error means that the Phaser module does not have a default export, and TypeScript usually does not like to let that slide. However, we can disable this warning by modifying our tsconfig.json file.

"compilerOptions": {
"allowSyntheticDefaultImports": true,
...
}

Setting this flag to true will disable that check and allow the Phaser module to be imported. While we’re in tsconfig.json, there’s one other change we need to make. We need to add "scripthost" to our "lib": [] array:

"lib": [
"es2018",
"dom",
"scripthost"
]

This needs to be added because otherwise we’ll get an error later on about Phaser not being able to find ActiveXObject.

Creating our game

Finally, we’re ready to start creating our game in our GameComponent.

In our game.component.ts file, we’re going to declare a new class and create our first scene.

class MainScene extends Phaser.Scene {
constructor() {
super({ key: 'main' });
}
create() {
console.log('create method');
}
preload() {
console.log('preload method');
}
update() {
console.log('update method');
}
}

We have a scene! Now, we need to configure and create our game.

@Component({
selector: 'app-game',
templateUrl: './game.component.html',
styleUrls: ['./game.component.scss']
})
export class GameComponent implements OnInit {
phaserGame: Phaser.Game;
config: Phaser.Types.Core.GameConfig;
constructor() {
this.config = {
type: Phaser.AUTO,
height: 600,
width: 800,
scene: [ MainScene ],
parent: 'gameContainer',
physics: {
default: 'arcade',
arcade: {
gravity: { y: 100 }
}
}
};
}
ngOnInit() {
this.phaserGame = new Phaser.Game(this.config);
}
}

Now that we’ve set everything up, when we run our application with ng serve —-open, we should see a blank canvas when we access our component. Phaser has successfully integrated with our Angular app and now you can focus on building your game!

Our blank canvas ready to be molded into a game!

There are tons of useful tutorials on building games with Phaser, but I’d recommend sticking to TypeScript tutorials like this one or this one. Keep in mind as you follow along with these that the webpack parts assume we aren’t bundling our Phaser game inside another app.

I have created a GitHub repository with a completed version of this tutorial. You can find it here: https://github.com/brsullivan/phaser-angular-app-step1

*A previous version of this story directed to this repository instead: https://github.com/brsullivan/phaser3-angular8. The content is similar but not an exact match to the steps in this tutorial.

--

--

Braelyn Sullivan

Front End Solutions Consultant & Full-Stack developer. Avid crafter & cat lover. Charlotte, NC