src/components/Navigation.js

goog.module('gep.components.Navigation');

const {Component} = goog.require('clulib.cm');

const {WorldProvider,WorldEventType} = goog.require('gep.provider.WorldProvider');
const {LayerProvider} = goog.require('gep.provider.LayerProvider');
const ControlProvider = goog.require('gep.provider.ControlProvider');

const {listen,EventType} = goog.require('goog.events');
const classlist = goog.require('goog.dom.classlist');
const {setStyle} = goog.require('goog.style');

/**
 * This component takes care of the control and display of the main navigation elements
 * (logo, top view switcher, info and guiding button).
 * Component is used from {@Link https://www.npmjs.com/package/clulib}
 * @extends {Component}
 */
class Navigation extends Component
{
    constructor()
    {
        super();

        /**
         * Reference to the WorldProvider for monitoring actions, loading processes and status changes of the created THREE.Scene.
         * @type {WorldProvider}
         * @private
         */
        this.worldProvider_ = WorldProvider.getInstance();

        /**
         * Reference to LayerProvider for monitoring and controlling layer appearance and disappearance.
         * @type {LayerProvider}
         * @private
         */
        this.layerProvider_ = LayerProvider.getInstance();

        /**
         * Reference to ControlProvider to monitor the activation of a gamepad controller so that the application's control is adapted to it.
         * @type {ControlProvider}
         * @private
         */
        this.controlProvider_ = ControlProvider.getInstance();

        /**
         * Dom element of the visitor info button.
         * @type {Element}
         * @private
         */
        this.visitorInfoOpener_ = null;

        /**
         * Dom element of the top view switcher.
         * @type {Element}
         * @private
         */
        this.topviewSwitcher_ = null;

        /**
         * Dom element of the exit/reset button. Only visible in the gamepad mode with the url parameter `gamepad=1`.
         * @type {Element}
         * @private
         */
        this.exitButton_ = null;

        /**
         * Dom element of the gamepad guide button. Only visible in the gamepad mode with the url parameter `gamepad=1`.
         * @type {Element}
         * @private
         */
        this.gamepadGuideButton_ = null;
    }

    /**
     * Component is ready and had loaded all dependencies (inherit method waitFor and sub components).
     * Adds listener for active elements.
     * @inheritDoc
     */
    onInit()
    {
        super.onInit();

        this.visitorInfoOpener_ = this.getElement().querySelector('.visitor-opener');
        this.topviewSwitcher_ = this.getElement().querySelector('.topview-switcher');
        this.exitButton_ = this.getElement().querySelector('.exit-exhibition');
        this.gamepadGuideButton_ = this.getElement().querySelector('.hint-gamepad-guide');

        if(this.gamepadGuideButton_) setStyle(this.gamepadGuideButton_, {'left': 'calc(100vw - '+(this.exitButton_.offsetWidth + 110)+'px)'});

        listen(this.visitorInfoOpener_, EventType.CLICK, this.openVisitorInfo_, false, this);
        listen(this.topviewSwitcher_, EventType.CLICK, this.switchWorldView_, false, this);
        if(this.exitButton_) listen(this.exitButton_, EventType.CLICK, this.exhitExhibition_, false, this);
        if(this.gamepadGuideButton_) listen(this.gamepadGuideButton_, EventType.CLICK, this.showGamepadGuide_, false, this);

        listen(this.worldProvider_, WorldEventType.ACTIVATE, this.handleWorldActivation_, false, this);
        listen(this.controlProvider_, EventType.UPDATE, this.checkControlling_, false, this);
    }

    /**
     * After the world is activated {@Link WorldEventType} `ACTIVATE`
     * specific navigation elements are displayed.
     * @private
     */
    handleWorldActivation_()
    {
        classlist.add(this.visitorInfoOpener_, 'is-visible');
        if(!this.worldProvider_.isMobileDevice)
            classlist.add(this.topviewSwitcher_, 'is-visible');
        this.checkControlling_();
    }

    /**
     * When the gamepad mode is activated (url parameter `gamepad=1`), the guiding and exit buttons are displayed.
     * @private
     */
    checkControlling_()
    {
        if(window['GAMEPAD_MODE'] === 'on') {
            if(this.gamepadGuideButton_) classlist.add(this.gamepadGuideButton_, 'is-visible');
            if(this.exitButton_) classlist.add(this.exitButton_, 'is-visible');
        }
    }

    /**
     * Opens the visitor layer
     * @private
     */
    openVisitorInfo_()
    {
        this.layerProvider_.show('visitor', {'id': 'info'});
    }

    /**
     * Init the changes the world view
     * @private
     */
    switchWorldView_()
    {
        this.worldProvider_.switchWorldView();
    }

    /**
     * Opens the guiding layer
     * @private
     */
    showGamepadGuide_()
    {
        this.layerProvider_.show('guiding');
    }

    /**
     * Resets the whole application by a window reload.
     * @private
     */
    exhitExhibition_()
    {
        window.location.reload();
    }
}

exports = Navigation;