无法访问 Typescript 中的基础 class 属性
Cannot access base class properties in Typescript
我遇到了一个很奇怪的问题。我正在扩展 class,出于某种原因,扩展 class 的属性或方法中的 none 是可访问的。这是我的 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.game
:
中的 game
的错误
ERROR in ./src/my-game/MyGameState.ts
(17,14): error TS2339: Property 'game' does not exist on type 'MyGameState'.
Intellij也是一头雾水。它似乎认识到 create()
正在覆盖基础 class 函数,但也认为 game
不存在。
很高兴在 class 中访问 Phaser.State
的 game
,只要它不是扩展版本。所以这个编译并且工作正常:
const workingState = new Phaser.State();
workingState.game.boot();
这是 phaser.d.ts
中的 class 的缩短版本,我正在扩展:
declare module "phaser-ce" {
export = Phaser;
}
declare class Phaser {
class State {
game: Phaser.Game;
create(): void;
}
}
我必须让 Phaser 与 Typescript 一起工作的可怕的毛茸茸的配置...
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"]
}
}
这不是针对 Phaser 的特定答案,而是更笼统的 "where to start" 答案。
第一步是,查看 this
:
export class MyGameState extends Phaser.State {
// More stuff [...]
create() {
console.log(this);
this.game.add.sprite(400, 300, "./assets/paddle.png");
}
}
TypeScript(和 JavaScript)中最常见的问题之一是 this
不是您所期望的。当在不同的上下文(例如事件)中调用 class 方法时,在 TypeScript 中会发生这种情况。
如果你发现 this
是一个元素,或者其他一些上下文,你可能可以用粗箭头(=>
)解决问题,which preserves the lexical scope.
看来我的 webpack 配置创建的花哨的组合相位器必须以某种方式被破坏。
我发现我可以通过以不同的方式导入移相器来防止打字稿错误:
import * as Phaser from "phaser-ce";
当以这种方式导入时,我不会出错并且可以使用基础 class 的成员。
我遇到了一个很奇怪的问题。我正在扩展 class,出于某种原因,扩展 class 的属性或方法中的 none 是可访问的。这是我的 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.game
:
game
的错误
ERROR in ./src/my-game/MyGameState.ts
(17,14): error TS2339: Property 'game' does not exist on type 'MyGameState'.
Intellij也是一头雾水。它似乎认识到 create()
正在覆盖基础 class 函数,但也认为 game
不存在。
很高兴在 class 中访问 Phaser.State
的 game
,只要它不是扩展版本。所以这个编译并且工作正常:
const workingState = new Phaser.State();
workingState.game.boot();
这是 phaser.d.ts
中的 class 的缩短版本,我正在扩展:
declare module "phaser-ce" {
export = Phaser;
}
declare class Phaser {
class State {
game: Phaser.Game;
create(): void;
}
}
我必须让 Phaser 与 Typescript 一起工作的可怕的毛茸茸的配置...
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"]
}
}
这不是针对 Phaser 的特定答案,而是更笼统的 "where to start" 答案。
第一步是,查看 this
:
export class MyGameState extends Phaser.State {
// More stuff [...]
create() {
console.log(this);
this.game.add.sprite(400, 300, "./assets/paddle.png");
}
}
TypeScript(和 JavaScript)中最常见的问题之一是 this
不是您所期望的。当在不同的上下文(例如事件)中调用 class 方法时,在 TypeScript 中会发生这种情况。
如果你发现 this
是一个元素,或者其他一些上下文,你可能可以用粗箭头(=>
)解决问题,which preserves the lexical scope.
看来我的 webpack 配置创建的花哨的组合相位器必须以某种方式被破坏。
我发现我可以通过以不同的方式导入移相器来防止打字稿错误:
import * as Phaser from "phaser-ce";
当以这种方式导入时,我不会出错并且可以使用基础 class 的成员。