import { toArray } from '../utils';
import pointOnFeature from '@turf/point-on-feature';
import helpers from '@turf/helpers';
export class Popup {
    constructor() {
        this.features = [];
        this.clickEventDelay = 50;
        this.closeKey = 27;
        this.maxWidth = 'none';
    }
    getOptions() {
        if (typeof this.componentOptions === 'string')
            return JSON.parse(this.componentOptions);
        return this.componentOptions || {};
    }
    handleFeatureClick(e) {
        let style = this.el.closest('gl-style');
        let layers = toArray(this.layers).map((layer) => `${style.id}:${layer}`);
        let features = e.detail.features
            .filter((feature) => layers.indexOf(feature.layer.id) !== -1);
        if (!features.length)
            return;
        if (this.clickEventDelay) {
            Array.prototype.push.apply(this.features, features);
            if (!this.popupTimeout) {
                this.popupTimeout = window.setTimeout(async () => {
                    this.popupTimeout = null;
                    if (this.features.length)
                        this.openPopup(this.features);
                    this.features = [];
                }, this.clickEventDelay);
            }
        }
        else {
            this.openPopup(features);
        }
    }
    handleKeyup(e) {
        if (e.keyCode === this.closeKey)
            this.removePopup();
    }
    async isOpen() {
        return (this.popup) ? this.popup.isOpen() : false;
    }
    async removePopup() {
        if (this.popup)
            this.popup.remove();
    }
    openPopup(features) {
        let featureCollection = helpers.featureCollection(features);
        let point = pointOnFeature(featureCollection);
        let component = document.createElement(this.component);
        component['features'] = features;
        let options = this.getOptions();
        for (let propName in this.getOptions())
            component[propName] = options[propName];
        this.popup = new mapboxgl.Popup({ maxWidth: this.maxWidth })
            .setLngLat(point.geometry.coordinates)
            .setDOMContent(component)
            .addTo(this.el.closest('gl-map').map);
    }
    static get is() { return "gl-popup"; }
    static get properties() { return {
        "clickEventDelay": {
            "type": Number,
            "attr": "click-event-delay"
        },
        "closeKey": {
            "type": Number,
            "attr": "close-key"
        },
        "component": {
            "type": String,
            "attr": "component"
        },
        "componentOptions": {
            "type": "Any",
            "attr": "component-options"
        },
        "el": {
            "elementRef": true
        },
        "isOpen": {
            "method": true
        },
        "layers": {
            "type": String,
            "attr": "layers"
        },
        "maxWidth": {
            "type": String,
            "attr": "max-width"
        },
        "removePopup": {
            "method": true
        }
    }; }
    static get listeners() { return [{
            "name": "body:glFeatureClick",
            "method": "handleFeatureClick"
        }, {
            "name": "body:keyup",
            "method": "handleKeyup"
        }]; }
    static get style() { return "/**style-placeholder:gl-popup:**/"; }
}
