Judixel
@Judixel
Front-end Engineer

Как передать значение аттрибута в метод Vue?

Есть три таба, по наведению на один из них - должен всплывает соответствующий блок. Связываться они должны по data-attr.

<template>
  <li data-rel="ex-1" @click="expand">
  <li data-rel="ex-2" @click="expand">
  <li data-rel="ex-3" @click="expand">

  <div v-show="isActive" :class="{ active: isActive }" data-rel="ex-1" @mouseleave="expand">
  <div v-show="isActive" :class="{ active: isActive }" data-rel="ex-2" @mouseleave="expand">
  <div v-show="isActive" :class="{ active: isActive }" data-rel="ex-3" @mouseleave="expand">
</template>

<script>
export default {
  data() {
    return {
      isActive: false,
    };
  },
  methods: {
    expand() {
      this.isActive = !this.isActive;
    },
  },
};
</script>


Сейчас всплывают все блоки.
Подскажите как передать аттрибут в метод или возможно есть другой способ реализовать expanded?

Upd: Не совсем правильно задал вопрос. Как передать знаю(через $event), а как связать элементы через аттрибуты?
  • Вопрос задан
  • 494 просмотра
Решения вопроса 4
amux
@amux
alp.ac
В data храните номер активного таба, а в эвентах используйте его:

Эвент:
@mouseleave="expand(1)"

В табах:
:class="{ active: active == 1 }"

data:
data() {
    return {
      acitve: 1,
    };
 },


а в методах:
methods: {
    expand(number) {
      Vue.set(this, 'active', number); //this.active = number
    },
  },
Ответ написан
Комментировать
nikichv
@nikichv
Frontend dev. Current stack: Next.js/RTK/Saga
Я бы сделал что-то типа этого. Суть в том, что у каждого разворачиваемого элемента должен быть свой флаг isActive. Ну и кстати, для разворачивания табов не обязательно использовать какие-то data- атрибуты. Ну и плюс в темплейте у тебя верстка неполная какая-то, тэги не закрыты, например.
<template>
  <div>
    <li v-for="(item, index) in itemsVisibility" 
        :data-rel="`ex-${index}`" 
        @click="expand(index)"></li>

    <div v-for="(item, index) in itemsVisibility" 
         v-show="itemsVisibility[index]" 
         :class="{ active: itemsVisibility[index] }"
         :data-rel="`ex-${index}`"
         @mouseleave="expand(index)"></div>
  </div>
</template>

<script>
  export default {
    data() {
      return {
        itemsVisibility: [
          true, // первый таб по дефолту открыт
          false,
          false,
        ],
      };
    },
    methods: {
      expand(index) {
        this.itemsVisibility[index] = !this.itemsVisibility[index];
      },
    },
  };
</script>
Ответ написан
0xD34F
@0xD34F Куратор тега Vue.js
Неудивительно, что "всплывают все блоки". Ведь блоков у вас три, а свойство, отвечающее за активность блока - одно, общее для всех. Никакие атрибуты тут не помогут. Вместо логического значения активности работайте с номером активного блока:

<ul>
  <li
    v-for="(n, i) in items"
    :data-rel="`ex-${i + 1}`"
    @click="active = i"
  >item #{{ i + 1 }}</li>
</ul>

<div
  v-if="active !== null"
  @mouseleave="active = null"
>{{ items[active] }}</div>

data() {
  return {
    active: null,
    items: [
      'hello, world!!',
      'fuck the world',
      'fuck everything'
    ]
  }
}

https://jsfiddle.net/fh9nvt5b/
Ответ написан
Комментировать
Fragster
@Fragster
помогло? отметь решением!
Связываться они должны по data-attr.

Это вам не к vue. В vue должно быть как-то так https://jsfiddle.net/fm4utx33/ (очень приближенно. на самом деле это скорее даже антипаттерн :) , но смысл тот, что ввод влияет на данные, а уже они влияют на отображение)
Ну и если табы не единообразны, то вот тут надо почитать и попереходить по ссылкам: https://ru.vuejs.org/v2/guide/routing.html
Ответ написан
Пригласить эксперта
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы