0

I am using Vue (2.0) in my project. WorkingArea component get a object via props. Words in the object are rendered by 'vfor' in WorkingArea component and they are create a sentence. I add external field named "status" the object in before component mounted. Object status can be active or inactive. I think that when status is active, color of word is changed red. Although the object is updated, component did not triggered for rendering. I'm sharing below WorkingArea component:

<template>
    <div id='sentence' class="drtl mt-3">
       <p  :class="word.status == 'active' ? active : inactive" v-for="(word, index) in hadithObject.hadith_words" :key="index" :id='index'>
           {{ word.kelime}}
       </p>
    </div>
    <b-button variant="danger" @click="nextWord()" >next</b-button>
</template>

<script>
export default {
    props: {
        hid:String,
        ho: Object,
    },
    data() {
        return {
            hadithObject: null,
            cursor: 0,
            //css class binding.
            inactive: 'inactive',
            active: 'active',
        }
    },
    beforeMount () {
        this.hadithObject = this.ho;
        this.hadithObject.hadith_words.forEach(item => {
            item.status = this.inactive;
        });
    },
    nextWord(){
         // when click to button, status of word is set active.
         this.hadithObject.hadith_words[this.cursor].status = this.active;
         this.cursor += 1;
    }
</script>

<style lang="scss" scoped>
@import url('https://fonts.googleapis.com/css?family=Amiri&display=swap');

.inactive{
    font-family: 'Amiri', serif;
    font-size: 23px;
    line-height: 2.0;
    display: inline-block;
    color: black;
}
.drtl{
    direction: rtl;
}

.active{
    color: red;
    font-family: 'Amiri', serif;
    font-size: 23px;
    line-height: 2.0;
    display: inline-block;
}
</style>

-------UPDATED FOR SOLUTION--------

After @Radu Diță answers, I examine shared this link. I learned that Vue cannot detect the following changes to an array:

  1. When you directly set an item with the index, e.g. vm.items[indexOfItem] = newValue
  2. When you modify the length of the array, e.g. vm.items.length = newLength

My mistake is trying first item. "newtWord" method is updated like below:

nextWord(){    
   var newItem = this.hadithObject.hadith_words[this.cursor];
   newItem.status = this.active;
   this.$set(this.hadithObject.hadith_words,this.cursor,newItem);
   this.cursor += 1;
}
3
  • to clarify the props are changing but the text on the component are not? Commented Apr 7, 2020 at 17:14
  • Yes, i see that object changing on console but color of word is still black. I think, component do not re-render. When I a little change my code and save, active words color are red. Commented Apr 7, 2020 at 17:22
  • I think using watcher or computed will help you with this problem watch & computed Commented Apr 7, 2020 at 17:33

1 Answer 1

1

You are updating hadithObject's keys. They are not reactive as they aren't added from the beginning.

Look over the caveats regarding reactivity.

You have 2 options:

  • either assign the object again this.hadithObject = Object.assign({}, ...this.hadithObject)
  • use Vue.set to set the new keys on the object.
Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.