Using Phaser 3 with TypeScript, RequireJS library and AMD module system

The solution of this problem is to rename ‘phaser’ to ‘Phaser’ in the file “node_modules/phaser/types/phaser.d.ts” like this:

declare module 'Phaser' {
    export = Phaser;

}

If you do not make this and you will try to run this simple example in your browser:

import * as Phaser from "phaser";

function main()
{
    console.log("Phaser Version: " + Phaser.VERSION);
}

main();

you will get this error: Uncaught TypeError: Cannot read property 'VERSION' of undefined

RequireJS and AMD are required for running multifile examples in Plunker: https://plnkr.co/edit/eKPfohFnoKQUwyos?preview

Read the book for details: Mastering TypeScript 3 - Third Edition

Issue

Full code: https://github.com/8Observer8/using-phaser3-with-requirejs-typescript

How to build:

npm run debug-build

npm run release-build

package.json

{
  "name": "using-phaser3-with-requirejs-typescript",
  "version": "1.0.0",
  "description": "",
  "scripts": {
    "test": "echo \"Error: no test specified\" && exit 1",
    "debug-build": "tsc -p tsconfigs/tsconfig.debug.json",
    "compile": "tsc -p tsconfigs/tsconfig.release.json",
    "browserify": "browserify public/js/main.js -o public/js/bundle.js",
    "uglifyjs": "uglifyjs public/js/bundle.js -o public/js/bundle.min.js",
    "release-build": "npm run compile && npm run browserify && npm run uglifyjs"
  },
  "keywords": [],
  "author": "",
  "license": "ISC",
  "dependencies": {
    "phaser": "^3.23.0"
  }
}

tsconfig/tsconfig.json

{
    "compilerOptions": {
        "target": "ES5",
        "outDir": "../public/js",
        "types": [
            "requirejs",
            "phaser"
        ]
    },
    "include": [
        "../src/**/*.ts"
    ]
}

tsconfig/tsconfig.debug.json

{
    "extends": "./tsconfig.json",
    "compilerOptions": {
        "module": "AMD",
        "sourceMap": true
    }
}

tsconfig/tsconfig.release.json

{
    "extends": "./tsconfig.json",
    "compilerOptions": {
        "module": "CommonJS",
        "sourceMap": false
    },
    "exclude": [
        "../src/RequireConfig.ts"
    ]
}

public/index.html

<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">

    <title>Using Phaser 3 with TypeScript, RequireJS library and AMD module system</title>

    <!-- Debug build (AMD module system, RequireJS) -->
    <script data-main="js/RequireConfig"
        src="https://cdnjs.cloudflare.com/ajax/libs/require.js/2.3.6/require.min.js"></script>

    <!-- Release build (bundle.min.js, Browserify, UglifyJS) -->
    <!-- <script src="js/bundle.min.js"></script> -->
</head>

<body>
    <p><a href="https://plnkr.co/edit/eKPfohFnoKQUwyos?preview">Playground</a></p>
    <p><a href="https://github.com/8Observer8/using-phaser3-with-requirejs-typescript">GitHub</a></p>
</body>

</html>

src/RequireConfig.ts

requirejs.config({
    "baseUrl": "js",
    paths: {
        "Phaser": "https://cdn.jsdelivr.net/npm/phaser@3.23.0/dist/phaser.min"
    }
});

requirejs(["main"], () => { });

src/main.ts

import * as Phaser from "Phaser";
import MyGame from "./MyGame";
import MainScene from "./MainScene";

function main()
{
    console.log(`Phaser Version: ${Phaser.VERSION}`);

    const config: Phaser.Types.Core.GameConfig = {
        title: "Using Phaser 3 with TypeScript, RequireJS library and AMD module system",
        width: 256, height: 256,
        type: Phaser.AUTO,
        scene: [ MainScene ]
    }
    
    const myGame = new MyGame(config);
}

// Run debug build (AMD module system, RequireJS)
main();

// Run release build (bundle.min.js, Browserify, UglifyJS)
// window.onload = () => main();

src/MyGame.ts

import * as Phaser from "Phaser";

export default class MyGame extends Phaser.Game
{
    public constructor(config: Phaser.Types.Core.GameConfig)
    {
        super(config);
    }
}

src/MainScene.ts

import * as Phaser from "Phaser";

export default class MainScene extends Phaser.Scene
{
    private _sprite: Phaser.GameObjects.Sprite;

    public constructor()
    {
        super({ key: "MainScene" });
    }

    protected preload(): void
    {
        this.load.image("logo", "./images/logo-download.png");
    }

    protected create(): void
    {
        this._sprite = this.add.sprite(128, 128, "logo");
    }

    public update(): void
    {
        this._sprite.angle += 1;
    }
}

Issue: https://github.com/photonstorm/phaser/issues/5205