VueJs 3 中的祖父組件向其祖父組件發送事件
P粉251903163
P粉251903163 2023-11-03 16:03:06
0
2
745

我對 Vue 比較陌生,正在開發我的第一個專案。我正在努力創建一個包含多個子組件和孫組件的表單。我遇到了一個問題,我需要能夠產生表單的多個副本。因此,我將一些資料屬性上移了 1 級。目前,表單為ApplicationPage.Vue > TheApplication.Vue > PersonalInformation.Vue > BaseInput.Vue。我的問題是我需要透過 TheApplication 發出從 PersonalInformation 到 ApplicationPage 的變更。我很難弄清楚如何處理這種情況。我一直在尋找 Vue2 的解決方案,但沒有找到 Vue3 的解決方案。

ApplicationPage.vue

template
      <TheApplication :petOptions="petOptions"
                      :stateOptions='stateOptions'
                      v-model="data.primary"
                      applicant="Primary"/>

script
data() {
    return {
      data: {
        primary: {
          personalInformation: {
            first_name: "",
            middle_name: "",
            last_name: "",
            date_of_birth: "",
            phone: null,
            email: "",
            pets: "",
            driver_license: null,
            driver_license_state: "",
            number_of_pets: null,
            additional_comments: ""
          },
        },
      },
    }
  },

TheApplication.Vue

<personal-information :petOptions="petOptions"
                                  :stateOptions='stateOptions'
                                  :personalInformation="modelValue.personalInformation"
                                  @updateField="UpdateField"
            />
methods: {
    UpdateField(field, value) {
      this.$emit('update:modelValue', {...this.modelValue, [field]: value})
    },

個人資訊.vue

#
<base-input :value="personalInformation.first_name"
                  @change="onInput('personalInformation.first_name', $event.target.value)"
                  label="First Name*"
                  type="text" class=""
                  required/>
methods: {
    onInput(field, value) {
      console.log(field + " " + value)
      // this.$emit('updateField', { ...this.personalInformation, [field]: value })
      this.$emit('updateField', field, value)
    },
  }


#
P粉251903163
P粉251903163

全部回覆(2)
P粉037880905

對於任何不想連結事件發出的人,子對像上都有父對象,它也可用於發出事件。請務必在父級中註冊發射,以避免控制台中出現警告。

子項

在此處呼叫直接父級的 $emit

Child.vue

#
<input @input="$parent.$emit('custom-event', e.target.value) />

或使用方法:

<input @input="handleInput" />
export default {
  methods: {
    handleInput(e) {
      this.$parent.$emit('custom-event', e.target.value)
    }
  }
}

父級

由於是父級向祖先發出信號,因此請在此處聲明發射。對於 ,只需使用 defineEmits() 方法來宣告發射。請參閱文件

Parent.vue

#
<Child /> <!-- No need to listen to the event here -->
export default {
   emits: ['custom-event'] // Register the emits
}

如果使用

<script setup>
  defineEmits(['custom-event']) // Register the emits
</script>

祖父母

然後在祖父母元件中監聽事件。

GrandParent.vue

<Parent @custom-event="doSomething()" /> <!-- The event is being listened to in the grandparent component -->
P粉842215006

這就是我的做法: codesandbox

Emits 只接受兩個參數,即發出的名稱和發出的值。如果發出多個值,則必須將這些值作為單一物件發出。 在我的解決方案中,孫組件將欄位名稱和值作為單一物件發出

孫子

<input
    :value="personalInformation.first_name"
    @input="onInput('first_name', $event.target.value)"
    ...
>
onInput(field, value) {
  this.$emit("update-field", { field: field, value: value });
},

子物件捕獲並重新發出,但是首先註意以父組件期望的格式發出(它需要整個data.primary 物件因為這就是被設定為v 模型的內容)

孩子

<grandchild
    :personalInformation="modelValue.personalInformation"
    @updateField="UpdateField"
  />
UpdateField({ field, value }) {
  const newVal = this.modelValue;
  newVal.personalInformation[field] = value;
  this.$emit("update:modelValue", newVal);
}

然後父元件會自動接收並更新 v-model data.primary 物件。

,我必須提到,您始終可以使用Pinia,Vue 的官方狀態管理庫(在一個元件中保存一些狀態,從任何其他元件讀取相同的狀態)。當然有一個學習曲線,但它絕對值得學習,並且正是為了簡化這種類型的情況。

熱門教學
更多>
最新下載
更多>
網站特效
網站源碼
網站素材
前端模板