vue-tagsinput icon indicating copy to clipboard operation
vue-tagsinput copied to clipboard

Tag input drops down in all of the components it is used

Open Marchiuzzz opened this issue 3 years ago • 2 comments

Hi, I'm using this input in many of my components and I have noticed that after running axios request to save data, all of the inputs get expanded (shown in the gif). I have also noticed that this started happening after I added the "typeahead-activation-threshold="0" " prop, if I remove it, this issue doesn't happen. Perhaps someone has faced a similar issue or might have some insight on what might be causing this and how to fix it? Is there a way to manually trigger dropdown?

Here's my custom component using tags input

<template>
    <div>
        <tags-input element-id="tags"
            v-model="selectedTags"
            :existing-tags="availableTags"
            :before-adding-tag="checkIfExists"
            :delete-on-backspace="false"
            :typeahead-activation-threshold="0"
            typeahead-style="dropdown"
            placeholder="Tags"
            @tag-removed="remove"
            @tag-added="add"
            :typeahead="true" v-if="!loading"></tags-input>
    </div>
</template>

<script>
import Tag from '../Models/Tag'
export default {
    watch: {
        selectedTags: function(newValue, oldValue){
            this.$emit('input', this.selectedTags);
        },
        inputtags: {
            handler: function(newValue, oldValue) {
                if(!_.isEqual(oldValue, newValue)){
                    this.selectedTags = newValue;
                }
            },
            deep: true,
            immediate: true
        }
    },
    computed: {
        tags(){
            return Tag.query().orderBy('value').get();
        },
        availableTags(){
            return this.tags.map(function(a){
                return {key: a.key, value: a.value};
            });
        }
    },
    props: [
        'inputtags'
    ],
    data(){
        return {
            tagLabel: 'tags',
            tagInput: '',
            selectedTags: [],
            loading: true,
        }
    },
    mounted(){
        this.fetchTags();
    },
    methods:{
        fetchTags(){
            //checking if tags have not yet been loaded
            if(!Tag.exists()){
                var promises = [];
                promises.push(Tag.api().fetch());
                var self = this;
                Promise.all(promises).then(function (res) {
                    self.loading = false;
                });
            }else{
                this.loading = false;
            }
        },
        checkIfExists(item){
            if(!item.key){
                if(confirm(window.translate('dictionary.addNewTag'))){
                    axios.post('/api/tags/create', {tagname: item.value})
                    .then(response => {
                        var respTag = response.data.data;
                        Tag.insert({
                            data: respTag
                        });
                        this.selectedTags.push(respTag);
                        this.add(respTag);
                    });
                }
                return false;
            }else{
                return true;
            }
        },
        remove(slug){
            this.$emit('remove', slug)
        },
        add(slug){
            this.$emit('add', slug)
        }
    }
}
</script>

<style lang="scss">
    .typeahead-dropdown{
        max-height:16rem;
        overflow: auto;
    }
</style>

ezgif com-gif-maker (3)

Marchiuzzz avatar Oct 22 '21 10:10 Marchiuzzz

Found a hack-ish way to solve this. That's by controlling typeahead-activation-threshold with a variable and changing this variable on @focus and @blur events. Here's my working example of the fix

<template>
    <div>
        <tags-input element-id="tags"
            v-model="selectedTags"
            @focus="threshold = 0"
            @blur="threshold = 1"
            :existing-tags="availableTags"
            :before-adding-tag="checkIfExists"
            :delete-on-backspace="false"
            :typeahead-activation-threshold="threshold"
            :typeahead-show-on-focus="true"
            :typeahead-hide-discard="true"
            typeahead-style="dropdown"
            placeholder="Tags"
            @tag-removed="remove"
            @tag-added="add"
            :typeahead="true" v-if="!loading"></tags-input>
    </div>
</template>
...
data(){
        return {
            ...
            threshold: 1,
        }
    },
...

Marchiuzzz avatar Oct 22 '21 11:10 Marchiuzzz

Yep, also happening to me. If the threshold is 0, once the tags are loaded the typeahead dropdown pops up uncalled. As a solution I've set the threshold to 1, but it is not ideal.

NilLlisterri avatar Jan 05 '23 12:01 NilLlisterri