I've got a rather strange problem. I'm extending a class, and for some reason none of the extended class's properties or methods are accessible. Here's my class:
import "pixi";
import "p2";
import Phaser from "phaser";
export class MyGameState extends Phaser.State {
// More stuff [...]
create() {
this.game.add.sprite(400, 300, "./assets/paddle.png");
}
}
This actually does seem to successfully compile and run, but outputs an error about how it can't access game
in this.game
:
ERROR in ./src/my-game/MyGameState.ts
(17,14): error TS2339: Property 'game' does not exist on type 'MyGameState'.
Intellij is also confused. It seems to recognize that create()
is overriding a base class function, but also thinks game
doesn't exist.
It's perfectly happy to access game
off of Phaser.State
inside that class, though, as long as it's not the extended version. So this compiles and works fine:
const workingState = new Phaser.State();
workingState.game.boot();
Here's a foreshortened version of the class in phaser.d.ts
I'm extending:
declare module "phaser-ce" {
export = Phaser;
}
declare class Phaser {
class State {
game: Phaser.Game;
create(): void;
}
}
And the horribly hairy configuration I've got to get Phaser working with Typescript this well ...
package.json
{
"name": "MyGame",
"main": "index.js",
"scripts": {
"dev": "webpack"
},
"devDependencies": {
"browser-sync": "^2.18.12",
"browser-sync-webpack-plugin": "^1.1.4",
"expose-loader": "^0.7.3",
"source-map-loader": "^0.2.1",
"ts-loader": "^2.2.2",
"tslint": "^5.5.0",
"tslint-loader": "^3.5.3",
"typescript": "^2.4.1",
"webpack": "^2.6.1"
},
"dependencies": {
"phaser-ce": "^2.8.1",
"webfontloader": "^1.6.28"
}
}
tsconfig.json
{
"compilerOptions": {
"outDir": "./dist/",
"sourceMap": true,
"strictNullChecks": false,
"module": "es6",
"moduleResolution": "node",
"target": "es5",
"allowJs": true
},
"include": [
"./src/"
]
}
webpack.config.js
var path = require('path')
var webpack = require('webpack')
var BrowserSyncPlugin = require('browser-sync-webpack-plugin')
// Phaser webpack config
var phaserModule = path.join(__dirname, '/node_modules/phaser-ce/')
var phaser = path.join(phaserModule, 'build/custom/phaser-split.js')
var pixi = path.join(phaserModule, 'build/custom/pixi.js')
var p2 = path.join(phaserModule, 'build/custom/p2.js')
var definePlugin = new webpack.DefinePlugin({
__DEV__: JSON.stringify(JSON.parse(process.env.BUILD_DEV || 'true'))
})
module.exports = {
entry: {
app: [
path.resolve(__dirname, './src/main2.ts')
],
vendor: ['pixi', 'p2', 'phaser', 'webfontloader']
},
devtool: 'source-map',
output: {
pathinfo: true,
path: path.resolve(__dirname, 'dist'),
publicPath: './dist/',
filename: 'bundle.js'
},
watch: true,
plugins: [
definePlugin,
new webpack.optimize.CommonsChunkPlugin(
{name: 'vendor'/* chunkName= */, filename: 'vendor.bundle.js'/* filename= */}),
new BrowserSyncPlugin({
host: process.env.IP || 'localhost',
port: process.env.PORT || 3000,
server: {
baseDir: ['./', './build']
}
})
],
module: {
rules: [
{test: /\.ts$/, enforce: 'pre', loader: 'tslint-loader', options: {emitErrors: true, failOnHint: true}},
{test: /\.ts$/, loader: 'ts-loader'},
{test: /pixi\.js/, use: ['expose-loader?PIXI']},
{test: /phaser-split\.js$/, use: ['expose-loader?Phaser']},
{test: /p2\.js/, use: ['expose-loader?p2']},
{enforce: "pre", test: /\.js$/, loader: "source-map-loader"}
]
},
node: {
fs: 'empty',
net: 'empty',
tls: 'empty'
},
resolve: {
alias: {
'phaser': phaser,
'pixi': pixi,
'p2': p2
},
extensions: [".ts", ".tsx", ".js", ".jsx"]
}
}
It seems like the fancy combined phaser my webpack config creates must be broken in some way shape or form.
I discovered I could prevent the typescript error by importing phaser in a different way:
import * as Phaser from "phaser-ce";
When imported this way I do not get errors and can use the members of the base class.