2017-01-08 2 views
0

Я составляю список элементов с циклом v-for. Внутри каждого элемента цикла есть кнопка с методом события щелчка, которая показывает текст описания. Когда я нажимаю на кнопку, она должна переключаться только внутри собственного элемента, но она затрагивает все элементы в списке v-for.Переключение между элементами v-for влияет на весь список, как я могу заставить каждый переключатель влиять только на содержащий элемент списка?

Итак, как сделать метод переключения, который повлияет только на его собственный элемент?

<template> 
    <div> 

    <div v-for="item in items" :class="{ activeclass: isActive }"> 

     <div class="item-text"> 
     {{item.text}} 
     </div> 
     <button @click="toggle()">show</button> 

     <div v-show="isActive" class="item-desc"> 
     {{item.desc}} 
     </div> 

    </div> 


    </div> 
</template> 

<script> 
    export default { 

    data() { 

     return { 

     items: [ 
      { 
      text: 'Foo', 
      desc: 'The Array.from() method creates a new Array instance from an array-like or iterable object.', 
      }, 
      { 
      text: 'Bar', 
      desc: 'The Array.from() method creates a new Array instance from an array-like or iterable object.', 

      } 
     ], 

     isActive: false 
     } 
    }, 

    methods: { 

     toggle: function() { 
     this.isActive = !this.isActive; 
     } 

    }, 


    } 
</script> 

ответ

3

Как @Nora сказал, что вы можете (и, вероятно, должны) создать отдельный компонент для каждого элемента списка, поэтому у вас будет компонент, который принимает item в качестве опоры, тогда каждый компонент может иметь свой собственный флаг isActive, который сохраняет славная разметки и чистый:

Компонент:

Vue.component('toggle-list-item', { 
    template: '#list-item', 
    props: ['item'], 
    methods: { 
    toggle() { 
     this.isActive = !this.isActive; 
    } 
    }, 
    data() { 
    return { 
     isActive: false 
    } 
    }, 
}) 

Markup

Теперь вы можете просто поместить компонент внутри вашего v-for:

<div id="app"> 
    <div v-for="item in items"> 
    <toggle-list-item :item="item"></toggle-list-item> 
    </div> 
</div> 

Вот JSFiddle: https://jsfiddle.net/w10qx0dv/

2

Вы можете добавить свойство каждого элемента в списке, если описание должно быть показано:

<template> 
    <ul> 
    <li v-for="item in items" :class="{ activeclass: item.isActive }"> 
     <div class="item-text"> 
     {{ item.text }} 
     </div> 
     <button @click="toggle(item)">show</button> 
     <div v-show="item.isActive" class="item-desc"> 
     {{ item.desc }} 
     </div> 
    </li> 
    </ul> 
</template> 

<script> 
    export default { 
    data() { 
     return { 
     items: [ 
      { 
      isActive: false, 
      text: 'Foo', 
      desc: 'The Array.from() method creates a new Array instance from an array-like or iterable object.', 
      }, 
      { 
      isActive: false, 
      text: 'Bar', 
      desc: 'The Array.from() method creates a new Array instance from an array-like or iterable object.', 
      } 
     ], 
     } 
    }, 
    methods: { 
     toggle: function (item) { 
     item.isActive = !item.isActive; 
     } 
    }, 
    } 
</script> 

В качестве альтернативы, вы можете извлечь li в качестве отдельного компонента.

+0

Я использовал этот путь. Оно работает! Нет другого способа, более чистого сделать это? –

+0

'@ click =" item.isActive =! Item.isActive "' –