Vue. js событие, испускаемое дочерним компонентом, не достигает родительского - PullRequest
0 голосов
/ 24 апреля 2020

в моем приложении vue. js у меня есть компонент, дочерние элементы которого внутри, или типа компонента "Test", или "AnotherComponent". Пользователь может добавить один из этих компонентов одним нажатием кнопки, после чего он будет добавлен в конец списка дочерних компонентов.

Каждый из этих компонентов должен иметь кнопку удаления, чтобы удалить компонент из показанный список.

Я добавил такую ​​кнопку в "AnotherComponent" и добавил источник щелчка по щелчку, потому что я хотел уведомить родительский компонент о событии, чтобы он позаботился об удалении нужного компонента из списка. Является ли этот подход корректным вообще?

Это дочерний компонент

<template>
  <div>
    <div class="container">
        <b-card
            title="Card Title"
            class="mb-2"
        >
            <b-card-text>
                This card has some text and it different from the other component.
                Also there is a nice picture.
            </b-card-text>
            <button
                type="button"
                class="btn btn-secondary"
                v-on:click="deleteComponent()"
            >
              x
            </button>
        </b-card>
  </div>
  </div>
</template>

<script>

export default {
  name: 'AnotherComponent',
  data() {
    return {
    };
  },
  methods: {
    deleteComponent(event) {
      this.$emit('delete-component', this.$vnode.key);
    },
  },
};
</script>

Это родительский компонент:

<template>
  <div>
    <div class="container">
      <h1> This is my first layout page </h1>
      <alert :message=alertText></alert>
      <button
        type="button"
        class="btn btn-primary"
        v-on:click="addComponent('test')"
      >
        add component 1
      </button>
      <button
        type="button"
        class="btn btn-primary"
        v-on:click="addComponent('another')"
      >
        add component 2
      </button>
      <div class="row">
        <template
          v-for="block in content.body">
            <div class="col-3" v-bind:key="`col-${block._uid}`">
              <component
                :is="block.component"
                :block="block"
                :key="block._uid"
                v-on:delete-component="onDeleteChildComponent($event)">
              </component>
            </div>
        </template>
      </div>
  </div>
  </div>
</template>

<script>
/* eslint-disable vue/no-unused-components */
import axios from 'axios';

import TestComponent from './TestComponent.vue';
import AnotherComponent from './AnotherComponent.vue';
import Alert from './Alert.vue';

export default {
  name: 'FirstPage',
  data() {
    return {
      alertText: 'this is a test!',
      content: {
        body: [], /* holds the array of objects that are components */
      },
    };
  },
  components: {
    alert: Alert,
    test: TestComponent,
    another: AnotherComponent,
    // AnotherComponent,
  },
  methods: {
    getComponents() {
      const path = 'http://localhost:8080/components';
      axios.get(path)
        .then((res) => {
          console.log('res.data');
          this.content.body = res.data.components;
        })
        .catch((error) => {
          // eslint-disable-next-line
          console.error(error);
        });
    },
    addComponent(componentType) {
      const path = 'http://localhost:8080/components';
      const payload = {
        component: componentType,
        headline: 'Bar',
      };
      axios.post(path, payload)
        .then(() => {
          this.getComponents();
          this.message = 'Component added!';
        })
        .catch((error) => {
          // eslint-disable-next-line
          console.log(error);
          this.getComponents();
        });
    },
  },
  onDeleteChildComponent(id) {
    console.log('delete child');
    console.log(id);
  },
  created() {
    console.log('fetching components from backend');
    this.getComponents();
  },
};
</script>

К сожалению в родительском компоненте это событие от дочернего элемента вообще не вызывается . Я только начинаю с vue. js, так что я здесь не так делаю? Заранее спасибо!

1 Ответ

1 голос
/ 24 апреля 2020

Вы излучаете 'deleteComponent' и слушаете 'delete-component'. Это преобразование не работает с регистрациями событий, только для преобразования имен компонентов.

https://vuejs.org/v2/guide/components-custom-events.html

Попробуйте вместо этого:

// child component

methods: {
    deleteComponent(event) {
      this.$emit('delete-component', this.$vnode.key);
    },
  },

РЕДАКТИРОВАТЬ: Как правильно отметил Эльдар в комментариях, ваш слушатель также слушает не тот элемент. Переместите слушатель к вашему динамическому c компоненту следующим образом:

// parent component

<!-- template tags not necessary unless you're trying to render more than 1 root node per v-for element -->

            <div class="col-3" v-for="block in content.body" :key="`col-${block._uid}`">
              <component
                @delete-component="onDeleteChildComponent($event)"
                :is="block.component"
                :block="block"
                :key="block._uid">
              </component>
            </div>

EDIT 2: метод, который вы пытаетесь прослушать, не указан в ваших методах, но он на один уровень выше. Следите за своими скобками! ;)

methods: {
    getComponents() {
      ...
    },
    addComponent(componentType) {
      ...
    },
  },
  onDeleteChildComponent(id) {
    console.log('delete child');
    console.log(id);
  },

должно быть:

methods: {
    getComponents() {
      ...
    },
    addComponent(componentType) {
      ...
    },
    onDeleteChildComponent(id) {
      console.log('delete child');
      console.log(id);
    },
  },
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...