javascript - 我如何在 TypeScript ES6 類別中擴展 Backbone.Events?
我正在嘗試把 Backbone 的 Events 屬性附加到 TypeScript 類上,然而當我這麼做時...
class Foo {
constructor () {
_.assign(this, Backbone.Events); // or _.extend()
this.stopListening(this.otherInstance);
}
}
let bar = new Foo();
bar.on("myevent", handler);
...我遇到這些編譯時錯誤:
Error TS2339: Property 'stopListening' does not exist on type 'Foo'.Error TS2339: Property 'on' does not exist on type 'Foo'.
我對 TypeScript 如何處理這個不是很熟悉,但看起來像是它能應付的事情。
注意:正在尋找一個解決方案,這個方案易於應用到多個同樣需要 Backbone.Events 功能的類別(也就是說,我不想將所有 on, off, listenTo... 方法複製/粘貼,或使用某種奇怪的代理方式,給每個需要它們的類別)。
由於 Backbone.Events 只是一個物件,我無法使用一般的 ES6 語法來擴展它。例如:
class Foo extends Backbone.Events {}
有什麼想法?
答案#1
如果你使用 _.extend 而不是 _.assign,它將可以運作,
這裡是一個 Plunker
class Foo {
constructor () {
_.extend(this, Backbone.Events);
}
}
let bar : any = new Foo();
bar.on("alert", function(msg) {
alert("Triggered " + msg);
});
bar.trigger("alert", "an event");
更新了程式碼,使其不會產生編譯時錯誤。
更新
你可以創建一個類,它包含為 Backbone.Events 定義的所有函數,其構造函數可以擴展 Backbone.Events,這將重寫所有僅為智能感知和類型檢查而定義的方法。
已更新 Plunker
class CustomEvents {
constructor() {
_.extend(this, Backbone.Events);
}
on(eventName: string, callback?: Function, context?: any): any { return; };
off(eventName?: string, callback?: Function, context?: any): any { return; };
trigger(eventName: string, ...args: any[]): any { return; };
bind(eventName: string, callback: Function, context?: any): any { return; };
unbind(eventName?: string, callback?: Function, context?: any): any { return; };
once(events: string, callback: Function, context?: any): any { return; };
listenTo(object: any, events: string, callback: Function): any { return; };
listenToOnce(object: any, events: string, callback: Function): any { return; };
stopListening(object?: any, events?: string, callback?: Function): any { return; };
}
你可以像下面這樣用 CustomEvents 類擴展任何類,
class Foo extends CustomEvents {
constructor(){
super();
}
}
答案#2
在 Backbone.Events 上,事件處理是附加在物件本身,而不是它的 .prototype 上,以下是你可以如何修正它的方法:
import {Events} from 'backbone';
interface IEventEmitter extends Events {
emit(event: string, ...args: any[]);
}
function _EventEmitter() {}
_EventEmitter.prototype = Events;
_EventEmitter.prototype.emit = (Events as any).trigger;
export const EventEmitter: new() => IEventEmitter
= _EventEmitter as any as new() => IEventEmitter;
現在將其作為繼承使用:
class Dog extends EventEmitter {
}
var dog = new Dog;
dog.on('bark', () => console.log('Dog just barked'));
dog.emit('bark');
