Vue: лучший способ отправить форму дочернего компонента из родительского компонента через метод

У меня 2 компонента.

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

 Vue.component('parent', {
              template: '<div><child :counter="counter" :isSubmit="isSubmit" showButton="true"></child>'+
              '<button v-on:click="changeCounter">Change Counter</button></div>',
              data () {
                return {
                    counter: 2,
                    isSubmit : false
                }
              },
              methods : {
                changeCounter () {
                    //retrieve value of counter dynamically let's say through ajax call.
                    this.counter = 9;
                    this.isSubmit = true;
                }
              }
            })

Дочерний компонент:

Vue.component('child', {
          template: '<form action="test.php" method="GET" ref="childForm">'+
          '<input type="hidden" v-model="counter" name="counter" />'+
          '<input type="submit" v-if="showButton" /></form>',
          props: {
            counter : {
                type: Number,
                default: 0
            },
            showButton:false,
            isSubmit: false
          },
          watch : {
            isSubmit (val) {
                   console.log("Inside watcher");
                    this.submitForm();
            }
          },
          methods : {
            submitForm () {
                console.log(this.counter);// output-9
                this.$refs.childForm.submit();
            },
         
          }

        })

index.html

....
<div id="app>">
   <parent></parent>
   <parent></parent>
</div>
....

В этом примере, когда я нажимаю кнопку "Изменить счетчик", форма отправляется со старым значением счетчика (т.е. отправляется в /test.php?counter=2). Хотя свойства дочернего компонента являются реактивными в инструментах разработки (counter = 9), они не отражаются при отправке формы. Но это действительно работает, если я отправляю форму с помощью кнопки отправки в дочернем компоненте (т.е. отправляю в /test.php?counter=9).

Ваша помощь очень ценится. Пожалуйста, помогите мне понять, почему проявляется такое поведение, а также поиск решений.

Заранее спасибо.

1 ответ

Решение

Быстрая заметка

Поскольку вы используете запросы GET, вы можете пропустить весь <form> вещь и просто перейдите прямо к URL-адресу

methods: {
  changeCounter () {
    this.counter = 9
    window.location = `test.php?counter=${this.counter}`
  }
}

Более длинный ответ

Вам нужно дождаться counter изменить, чтобы обновить DOM, чтобы использовать обычную отправку формы.

Чтобы дождаться изменения состояния, чтобы повлиять на DOM, используйте $nextTick. Я бы также посоветовал отправить форму черезsubmitFormвместо просмотра логического значения. Вы можете получить доступ к методу, используя ссылки.

Vue.component('child', {
  template: `<form action="test.php" method="GET" ref="childForm">
    <input type="hidden" :value="counter" name="counter" />
    <input type="submit" v-if="showButton" />
  </form>`,
  props: {
    counter : {
      type: Number,
      default: 0
    },
    showButton: Boolean
  },
  methods: {
    async submitForm () {
      await this.$nextTick() // wait for the DOM to update
      this.$refs.childForm.submit()
    }
  }
})
Vue.component("parent", {
  template: `<div>
    <child :counter="counter" :show-button="true" ref="form"></child>
    <button @click="changeCounter">Change Counter</button>
  </div>`,
  data: () => ({ counter: 2 }),
  methods: {
    changeCounter () {
      this.counter = 9
      this.$refs.form.submitForm() // call the child component method
    }
  }
})
Другие вопросы по тегам