Vincent
Vincent

Reputation: 169

How to declare nested functions in a TypeScript declaration source file?

I'm in the process of building a declaration source file for KeyboardJS. The API is referenced from a static object (KeyboardJS) instantiated when the JavaScript file is loaded. A few of the methods of the API are nested under other methods. For example:

KeyboardJS.clear(keyCombo);

and

KeyboardJS.clear.key(key);

Here is my interface definition:

interface KeyboardJSStatic {
    enable(): void;
    disable(): void;
    activeKeys(): string[];
    on(keyCombo:string, onDownCallback?: (keyEvent: Event, keysPressed: string[], keyCombo: string) => {}, onUpCallback?: (keyEvent: Event, keysPressed: string[], keyCombo: string) => {}): KeyboardJSBinding;
    clear(keyCombo: string): void;
    clear.key(keyName: string): void;
    locale(localeName: string): KeyboardJSLocale;
    locale.register(localeName: string, localeDefinition: KeyboardJSLocale): void;
    macro(keyCombo:string , keyNames: string[]): void;
    macro.remove(keyCombo: string): void;
    key: KeyboardJSKey;
    combo: KeyboardJSCombo; 
}

The TypeScript plugin for Visual Studio 2012 is generating and error on the clear.key line, recommending a semicolon for where the period is. Has anyone built a definition file with a similar scenario? Thanks!

Upvotes: 3

Views: 4535

Answers (2)

Fenton
Fenton

Reputation: 250942

Genius comment from Ryan. Using the same pattern as the jQuery definition you could do:

interface KeyboardJSClear {
    (keyCombo: string) : void;
    key(keyName: string): void;
}

interface KeyboardJSLocale {
    (localeName: string) : KeyboardJSLocale;
    register(localeName: string, localeDefinition: KeyboardJSLocale): void;
}

interface KeyboardJSMacro {
    (keyCombo:string , keyNames: string[]): void;
    remove(keyCombo: string): void;
}

interface KeyboardJSStatic {
    enable(): void;
    disable(): void;
    activeKeys(): string[];
    on(keyCombo:string, onDownCallback?: (keyEvent: Event, keysPressed: string[], keyCombo: string) => {}, onUpCallback?: (keyEvent: Event, keysPressed: string[], keyCombo: string) => {}): KeyboardJSBinding;
    clear: KeyboardJSClear;
    locale: KeyboardJSLocale;
    macro: KeyboardJSMacro;
    key: KeyboardJSKey;
    combo: KeyboardJSCombo; 
}

declare var KeyboardJS: KeyboardJSStatic;

KeyboardJS.clear('');
KeyboardJS.clear.key('');

Upvotes: 2

Ryan Cavanaugh
Ryan Cavanaugh

Reputation: 221014

You can declare call signatures on types like this:

interface KeyboardJSStatic {
    // ...
    clear: {
        (keyCombo: string): void; // Call signature
        key(keyName: string): void; // Method
    };
    // ...
}

var n: KeyboardJSStatic;
n.clear('a'); // OK
n.clear.key('b'); // OK

Upvotes: 9

Related Questions