简体   繁体   中英

Re-render component content in Vue Js

I made a 'read more' component in Vue Js and when the text passed via props changes, the component doesn't re-render showing the new content.

That's the component's code:

Vue.component('readmore', {
    template: 
            `
            <span>
                {{ part1 }}<span v-if="leia.mais">...
                    <span class="text-info ml-2" style="cursor:pointer;" v-on:click="readMore"> Leia mais</span>
                </span><span v-if="!leia.mais">{{ part2 }}
                    <span class="text-info ml-2" style="cursor:pointer;" v-if="leia.menos"  v-on:click="readLess">Leia menos</span>
                </span>
            </span>
            `,
    data: function () {
        return {
            part1: '',
            part2: '',
            leia: {},
            defaultMaxChr: 200
        }
    },
    
    props: ['maxchr', 'text'],

    created: function () {
        var text = this.text;
        var maxchr = this.maxchr ? this.maxchr : this.defaultMaxChr;
        if ((undefined === text) || (0 === text.length)) {
            console.warn('COMPONENTE LEIA MAIS: Parâmetro text indefinido ou foi passada uma string vazia.');
            return;
        }

        if (text.length <= maxchr) {
            this.part1 = text;
            this.part2 = '';

            this.leia = {mais: false, menos: false};
        } else {
            this.part1 = text.substr(0, maxchr);
            this.part2 = text.substr(maxchr);

            this.leia = {mais: true, menos: false};
        }
    },
    methods: {
        readMore: function()
        {
            this.leia.mais = false;
            this.leia.menos = true;
        },

        readLess: function()
        {
            this.leia.mais = true;
            this.leia.menos = false;
        },

    },

});

If I have the code below and change the input, nothing happen.

<readmore> and <input> are inside another component, which defines text in its data attribute.

<input v-model="text">

<readmore
    v-bind:text="text"
    v-bind:maxchr="100"
></readmore>

That's because you execute your logic inside the created function which will only be executed once on the component's initial load. and will not execute again when the text prop change, you need to use watch with immediate execution to check changes on text.

watch: {
  text: {
    handler() {
        var text = this.text;
        var maxchr = this.maxchr ? this.maxchr : this.defaultMaxChr;
        if ((undefined === text) || (0 === text.length)) {
            console.warn('COMPONENTE LEIA MAIS: Parâmetro text indefinido ou foi passada uma string vazia.');
            return;
        }

        if (text.length <= maxchr) {
            this.part1 = text;
            this.part2 = '';

            this.leia = {mais: false, menos: false};
        } else {
            this.part1 = text.substr(0, maxchr);
            this.part2 = text.substr(maxchr);

            this.leia = {mais: true, menos: false};
        }
    },
    immediate: true
  }
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM