import { getLabelText } from '/components/common/utils.js?v=3.6'

export const VueMultiSelect = {
    components: { getLabelText },
    props: {
        items: { type: Array, required: true },
        id: { type: String, required: false, default: "VueMultiSelect" },
        useTranslation: { type: Boolean, required: false, default: false },
        searchPhrase: { type: String, required: false, default: null },
        isOrderable: { type: Boolean, required: false, default: false },
        sortByValue: { type: Boolean, required: false, default: false }
    },
    data() {
        return {
            selectedItems: [],
            itemsData: [],
            overrideDefaultSort: false,
            doSearch: true
        }
    },
    emits: ['selectionChange'],
    mounted() {
        // Initialize tooltip with manual trigger when component mounts
        if (this.$refs.copyToClipboardBtn) {
            $(this.$refs.copyToClipboardBtn).tooltip({
                placement: 'top'
            });
        }
    },
    beforeUnmount() {
        // Clean up to prevent memory leaks
        if (this.$refs.copyToClipboardBtn) {
            $(this.$refs.copyToClipboardBtn).tooltip('destroy');
        }
    },
    created: function () {
        this.selectedItems = this.items ? this.items.filter(i => i.selected).map(i => i.value) : [];
        this.itemsData = this.items;
        if (this.useTranslation)
            this.itemsData.forEach(i => { i.text = this.getLabelText(i.text) });
    },
    beforeUpdate: function () {
        if (this.doSearch)
            this.searchAndSelect();
    },
    updated: function () {

        this.itemsData = this.items;
        this.doSearch = true;

        if (!this.isOrderable)
            if (this.useTranslation)
                this.itemsData.forEach(i => { i.text = this.getLabelText(i.text) });
    },
    computed: {
        options() {
            if (this.isOrderable || this.overrideDefaultSort)
                return this.itemsData;
            else
                return this.itemsData.sort((a, b) => {
                    if (this.sortByValue)
                        if (a.value > b.value)
                            return 1;
                        else
                            return -1;
                    else
                        if (a.text > b.text)
                            return 1;
                        else
                            return -1;
                });
        }
    },
    methods: {
        getLabelText,
        raiseChangeEvent: function () {
            if (this.itemsData && this.itemsData.length > 0) {

                let itemsSelected = [];

                if (this.useTranslation)
                    itemsSelected = this.itemsData.filter(i => this.selectedItems.includes(i.value.toString())).map(i => {
                        return { text: this.getLabelText(i.text), value: i.value, selected: true }
                    });
                else
                    itemsSelected = this.itemsData.filter(i => this.selectedItems.includes(i.value.toString())).map(i => {
                        return { text: i.text, value: i.value, selected: true }
                    });

                if (!this.overrideDefaultSort && !this.isOrderable)
                    this.selectedItems = [];

                this.$emit('selectionChange', itemsSelected);
            }
        },
        changeHandler: function (event) {

            this.selectedItems = Array.from(event.target.selectedOptions).map(o => o.value);
            this.doSearch = false;
            this.raiseChangeEvent();
            this.doSearch = true; //after rais event, allow to search

        },
        searchAndSelect: function () {

            if (this.searchPhrase && !this.searchPhrase == '') {

                this.overrideDefaultSort = false;
                if (!this.isOrderable)
                    this.selectedItems = [];

                let matchExpression = new RegExp(this.searchPhrase, "gi");
                this.selectedItems = [];

                this.itemsData.forEach((i) => {
                    if (i.text.match(matchExpression)) {
                        this.selectedItems.push(i.value.toString());
                        i.selected = true;
                    }
                    else
                        i.selected = false;
                });

                this.overrideDefaultSort = true;

                //scroll select to first selected element
                if (this.selectedItems.length > 0) {
                    let firstSelectedOption = document.querySelector("#" + this.id + " > option[value='" + this.selectedItems[0] + "']");
                    if (firstSelectedOption)
                        firstSelectedOption.scrollIntoView({ behavior: "smooth", block: "start", inline: "nearest" });
                }

                if (this.selectedItems.length > 0)
                    document.getElementById(this.id).selectedIndex = -1; //clear dom selection when search phrase is matched and items found for selection.

                if (!this.isOrderable) {
                    this.itemsData.sort((a, b) => {
                        if (this.sortByValue)
                            if (a.value > b.value)
                                return 1;
                            else
                                return -1;
                        else
                            if (a.text > b.text)
                                return 1;
                            else
                                return -1;
                    });
                    this.moveToTopSelected();

                }
                else {
                    this.raiseChangeEvent();
                }
            }
        },
        moveUpSelected: function () {
            this.overrideDefaultSort = true;
            this.itemsData
                .map(i => i)
                .forEach((i, x) => {
                    if (x > 0 && this.selectedItems.includes(i.value.toString())) {
                        this.itemsData.move(x, x - 1);
                    }
                });
            this.raiseChangeEvent();
        },
        moveToTopSelected: function () {

            this.overrideDefaultSort = true;
            let localTop = 0;
            this.itemsData
                .map(i => i)
                .forEach((i, x) => {
                    if (x > 0 && this.selectedItems.includes(i.value.toString())) {
                        this.itemsData.move(x, localTop);
                        localTop++;
                    }
                });
            this.raiseChangeEvent();
        },
        moveDownSelected: function () {
            this.overrideDefaultSort = true;
            this.itemsData
                .reverse()
                .map(i => i)
                .forEach((i, x) => {
                    if (x > 0 && this.selectedItems.includes(i.value.toString())) {
                        this.itemsData.move(x, x - 1);
                    }
                });
            this.itemsData.reverse();
            this.raiseChangeEvent();
        },
        moveToBottomSelected: function () {
            this.overrideDefaultSort = true;
            let localTop = 0;
            this.itemsData
                .reverse()
                .map(i => i)
                .forEach((i, x) => {
                    if (x > 0 && this.selectedItems.includes(i.value.toString())) {
                        this.itemsData.move(x, localTop);
                        localTop++;
                    }
                });
            this.itemsData.reverse();
            this.raiseChangeEvent();
        },
        mouseLeftHandler: function () {

            this.selectedItems = [];
            this.itemsData
                .forEach((i) => {
                    i.selected = false;
                });

        },
        copyToClipboard: function (e) {
            const buttonElement = e.currentTarget;
            var text = Array.prototype.slice.call(this.options).map(function (o) { return o.text }).join('\n');
            if (navigator.clipboard) {
                navigator.clipboard.writeText(text);
                //buttonElement.innerHTML = getLabelText('Copied');
                $(buttonElement).removeClass('icon-copy');
                $(buttonElement).addClass('icon-active-subscriptions');
                setTimeout(() => { buttonElement.innerHTML = ''; $(buttonElement).removeClass('icon-active-subscriptions').addClass('icon-copy'); }, 5000);
            } else {
                var t = document.createElement('textarea');
                t.value = text; t.style.position = 'fixed'; t.style.opacity = '0';
                document.body.appendChild(t); t.select();
                document.execCommand('copy'); document.body.removeChild(t);
                //buttonElement.innerHTML = getLabelText('Copied');
                $(buttonElement).removeClass('icon-copy');
                $(buttonElement).addClass('icon-active-subscriptions');
                setTimeout(() => { buttonElement.innerText = ''; $(buttonElement).removeClass('icon-active-subscriptions').addClass('icon-copy'); }, 5000);
            }
        }
    },
    template: `
    <span class='pull-right p-r-10'>
    <span
        @click.left.prevent="copyToClipboard($event)"
        ref="copyToClipboardBtn"
        data-toggle="tooltip"
        data-placement="top"
        title="Click to copy"
        href='javascrip:void(0)'
        class='text-info mp-icons icon-copy'
        style="border: none;background: transparent;font-size: 20px;cursor:pointer;">
     </span>
     </span>
        <div v-if="isOrderable">
            <a @click.left.prevent="moveUpSelected" :id="moveUpSelectedId" :title="getLabelText('SMI0456')" class="LinkButtonUp"></a>
            <a @click.left.prevent="moveToTopSelected" id="moveToTopSelectedId" title="Move Top" class="LinkButtonTop"></a>
            <a @click.left.prevent="moveDownSelected" id="moveDownSelectedId" :title="getLabelText('SMI0457')" class="LinkButtonDown" ></a>
            <a @click.left.prevent="moveToBottomSelected" id="moveToBottomSelectedId" title="Move Bottom" class="LinkButtonBottom"></a>
        </div>
        
        <div>
            <select class="ms vue-multi-select" multiple @click.left="mouseLeftHandler" @change="changeHandler" :id="id">
                <option v-for="o in options" :value="o.value" :key="o.value" :selected="o.selected" >{{ o.text }}</option>
            </select>
        </div>
    `
}