import { AxisChangeCallback, ButtonChangeCallback, GamepadApiWrapper, buttonChangeDetails } from './GamepadApiWrapper.js';
import { gamepadButtonType, gamepadDirection } from './enums.js';
export type GamepadDisplayButton = GamepadDisplayOnOffButton | GamepadDisplayVariableButton;
export type ButtonDisplayFunction = (buttonConfig: GamepadDisplayButton, value: number, touched: boolean, pressed: boolean, changes: buttonChangeDetails, btnIndex: number) => void;
export type JoystickDisplayFunction = (stickConfig: GamepadDisplayJoystick, xAxisValue: number, yAxisValue: number) => void;
export interface GamepadDisplayOnOffButton {
    type: gamepadButtonType.onOff;
    /** The element to add the touch and press classses, to represent touching or pressing on this button */
    highlight: HTMLElement | SVGElement;
    /** optional, for your own use */
    extraData?: any;
}
export interface GamepadDisplayVariableButton {
    type: gamepadButtonType.variable;
    /** The element to add the touch and press classses to - to represent touching or pressing on this button,
     * defaults to the same element as buttonElement */
    highlight?: HTMLElement | SVGElement;
    /** The element to move to represent pressing on this button */
    buttonElement: HTMLElement | SVGElement;
    /** How far the {@link GamepadDisplayVariableButton.buttonElement} should move to represent being pressed fully in HTML or SVG pixels */
    movementRange: number;
    /** Direction the {@link GamepadDisplayVariableButton.buttonElement} should move to represent being pressed */
    direction: gamepadDirection;
    /** Drag direction indicator / highlight element for this variable button */
    directionHighlight?: HTMLElement | SVGElement;
    /** optional, for your own use */
    extraData?: any;
}
export interface GamepadDisplayJoystick {
    joystickElement: HTMLElement | SVGElement;
    movementRange: number;
    /** Axis index (as returned by the browser gamepad api) to track for the horizontal movement of the display joystick
     * see {@link standardGpadAxesMap}  */
    xAxisIndex?: number;
    /** Axis index (as returned by the browser gamepad api) to track for the vertical movement of the display joystick
     * see {@link standardGpadAxesMap}  */
    yAxisIndex?: number;
    /** @deprecated
     * use {@link GamepadDisplayJoystick.extraData} with a custom {@link DisplayGamepadConfig.joystickDisplayFunction} instead, see the custom gamepads example/demo */
    highlights?: {
        [gamepadDirection.up]?: HTMLElement | SVGElement | null;
        [gamepadDirection.down]?: HTMLElement | SVGElement | null;
        [gamepadDirection.left]?: HTMLElement | SVGElement | null;
        [gamepadDirection.right]?: HTMLElement | SVGElement | null;
    };
    /** optional, for your own use */
    extraData?: any;
}
export interface DisplayGamepadConfig {
    /** The index of the gamepad this Gamepad Display should track as returned from `navigator.GetGamepads()` */
    gamepadIndex: number;
    /** Configuration for Buttons and Variable Pressure Buttons (eg: shoulder triggers) to represent in the gamepad display
     * - The index of the button in the array corresponds to the index of the button as returned by the browser gamepad api.
     * - Add null in the array for any button you don't want to track.
     * - @see {@link GamepadDisplayButton} and {@link GamepadDisplayVariableButton} {@link standardGpadButtonMap} for more information */
    buttons?: (GamepadDisplayButton | null | undefined)[];
    /** Configuration for Joysticks to represent in the gamepad display (based on gamepad axes indecies as as returned by the browser gamepad api) */
    sticks?: GamepadDisplayJoystick[];
    /** The class to add to the corresponding highlight element when a gamepad button is touched (whether or not its pressed) */
    touchedHighlightClass?: string;
    /** The class to add to the corresponding highlight element when a gamepad button is pressed */
    pressedHighlightClass?: string;
    /** The class to add to the corresponding direction indicator element when a gamepad joystick is moved in a direction or a variable button is pressed */
    moveDirectionHighlightClass?: string;
    /** If provided, this function will be called for each button with a state change (pressed, touched, released, etc...)
     * @see {@link GamepadDisplay.DefaultButtonDisplayFunction} for an example */
    buttonDisplayFunction?: ButtonDisplayFunction;
    /** If provided, this function will be called when the gamepad axies change for a joystick instead of the default display function.
     * @see {@link GamepadDisplay.DefaultJoystickDisplayFunction} for an example */
    joystickDisplayFunction?: JoystickDisplayFunction;
}
/**
 * Class to handle displaying the state of a gamepad on the screen.
 * This class will not draw anything to the screen. Instead it will update the classes / transforms of the elements
 * you provide to represent the buttons and axes of the gamepad. See the examples for more information.
 */
export declare class GamepadDisplay {
    protected config: DisplayGamepadConfig;
    protected apiWrapper: GamepadApiWrapper;
    /** Create a new GamepadDisplay instance
    * @param config The config to use for the gamepad display
    * @param apiWrapper (OPTIONAL) The gamepad api will use this GamepadApiWrapper instance to listen for gamepad events, otherwise it will create a new gamepad wrapper under the hood.
    */
    constructor(config: DisplayGamepadConfig, apiWrapper?: GamepadApiWrapper);
    /**
     * Function called by default when the gamepad axies change for a joystick (as configured in this GamepadDisplay)
     * If you specify your own {@link DisplayGamepadConfig.joystickDisplayFunction} in the config, this function won't get called.
     * Instead, you can call this function with the same parameters as passed to the {@link DisplayGamepadConfig.joystickDisplayFunction}
     * if you want to keep the default behaviour (and then you can add your own custom behaviour on top)
     * @param stickConfig The config for the joystick that has changed (as configured in {@link DisplayGamepadConfig.sticks})
     * @param xValue The new x axis value
     * @param yValue The new y axis value
     */
    readonly DefaultJoystickDisplayFunction: (stickConfig: GamepadDisplayJoystick, xValue: number, yValue: number) => void;
    /**
     * Function called by default when any gamepad buttons change (called separately for each button (as configured in this GamepadDisplay))
     * If you specify your own {@link DisplayGamepadConfig.buttonDisplayFunction} in the config, this function won't get called.
     * Instead, you can call this function with the same parameters as passed to the {@link DisplayGamepadConfig.buttonDisplayFunction}
     * if you want to keep the default behaviour (and then you can add your own custom behaviour on top)
     * @param buttonConfig The config for the button that has changed as configured in {@link DisplayGamepadConfig.buttons}
     * @param value The new value of the button
     * @param touched Whether the button is currently being touched (unused, but included for consistency with the {@link ButtonDisplayFunction} signature)
     * @param pressed Whether the button is currently being pressed (unused, but included for consistency with the {@link ButtonDisplayFunction} signature)
     * @param changes The changes that have occurred since the last update
     * @param btnIndex The index of the button that has changed (unused, but included for consistency with the {@link ButtonDisplayFunction} signature)
     */
    readonly DefaultButtonDisplayFunction: (buttonConfig: GamepadDisplayButton, value: number, touched: boolean, pressed: boolean, changes: buttonChangeDetails, btnIndex: number) => void;
    /**
     * This function is registered as the callback for {@link GamepadApiWrapper.onGamepadAxisChange()}
     * it calls the {@link DisplayGamepadConfig.joystickDisplayFunction} (if specified) or the {@link GamepadDisplay.DefaultJoystickDisplayFunction} otherwise
     * for each configured joystick with axies that have changed
     * @param gpadIndex The index of the gamepad that has changed
     * @param gpadState The new state of the gamepad as reported by the browser
     * @param axisChangesMask An array of booleans, where each true indicates that the corresponding axis has changed since the last update
     */
    protected displayJoystickChanges: AxisChangeCallback;
    /**
     * This function is registered as the callback for {@link GamepadApiWrapper.onGamepadButtonChange()}
     * it calls the {@link DisplayGamepadConfig.buttonDisplayFunction} (if specified) or the {@link GamepadDisplay.DefaultButtonDisplayFunction} otherwise
     * for every button that has changed since the last update
     * @param gpadIndex The index of the gamepad that has changed
     * @param gpadState The new state of the gamepad as reported by the browser  / {@link GamepadApiWrapper.onGamepadButtonChange}
     * @param buttonChangesMask An array of buttonChangeDetails or false, where each false in the array indicates that the corresponding button index has not changed since the last update.
     * @returns
     */
    protected displayButtonChanges: ButtonChangeCallback;
    /**
     * Cleanup function to remove all event listeners created by the {@link GamepadDisplay}
     * Call this function before removing the gamepad display from the DOM or deleting
     * the {@link GamepadDisplay} instance to prevent memory leaks
     */
    Cleanup(): void;
}
