【问题标题】:Error and wrong behaviour on close component from parent using Vuetify v-dialog使用 Vuetify v-dialog 关闭父组件的错误和错误行为
【发布时间】:2020-05-11 18:47:04
【问题描述】:

我有一个组件,其中包含一个简单的 v-dialog 向用户显示消息和一个 v-btn 来关闭它。场景是:

  1. 用户点击显示v-dialog的组件的按钮。
  2. 用户点击v-btn关闭组件
  3. 控制台触发错误:Vue warn]: Avoid mutating a prop directly since the value will be overwritten whenever the parent component re-renders. Instead, use a data or computed property based on the prop's value. Prop being mutated: "show"
  4. 如果再次点击按钮打开对话框,对话框不会重新打开,因为data() show不会改变组件v-btn的值。

对话框组件BasicMessageDialog.vue

<template>
  <div class="text-center">
    <v-dialog v-if="showDialog" width="500">
      <v-card>
        <v-card-title primary-title class="title">Ops...</v-card-title>
        <v-card-text class="body-1">{{message}}</v-card-text>
        <v-card-actions>
          <v-spacer></v-spacer>
          <v-btn text color="primary" @click="show = false" class="body-1">Beleza!</v-btn>
        </v-card-actions>
      </v-card>
    </v-dialog>
  </div>
</template>

<script>
export default {
  name: "BasicMessageDialog",
  computed: {
    showDialog() {
      return this.show;
    }
  },
  props: {
    show: Boolean,
    message: String
  }
};
</script>

<style>
</style>

主要组件Login.vue

<template>
...
 <BasicMessageDialog :message="messageBasicDialog" :show="showBasicMessageDialog">
...
</BasicMessageDialog>
</template>

<script>
import BasicMessageDialog from "@/components/BasicMessageDialog";

export default {
  name: "Login",
  components: {
    BasicMessageDialog
  },
data: () => ({
      showBasicMessageDialog: false,
      messageBasicDialog: "",
)},
methods: {
    forgetPassword() {
      console.log("forgetPassword");
      if (this.email == "") {
        this.messageBasicDialog = "Digite o e-mail no campo!";
        this.showBasicMessageDialog = true;
      }
    }
}

</script>

【问题讨论】:

    标签: javascript vue.js vuetify.js


    【解决方案1】:

    这是因为您更新了对话框组件中的 show 道具,其中您的节目数据来自您的父母。这就是为什么它返回Avoid mutating a prop directly since the value will be overwritten whenever the parent component re-renders.的警告

    为了解决您的问题,以下是一些防止该警告的方法。

    首先当您单击对话框按钮或单击对话框外部时,您必须在对话框组件中发出一个事件。喜欢这个。

    在您的V-dialog component 中。当用户点击按钮时

    <v-btn text color="primary" @click="this.$emit('hideModal')" class="body-1">Beleza!</v-btn>
    

    现在你的父组件应该收到这个事件。像这样的父组件

    <BasicMessageDialog :message="messageBasicDialog" :show="showBasicMessageDialog" @hideModal='showBasicMessageDialog = false'>
    ...
    </BasicMessageDialog>
    

    现在,问题又是如果用户单击对话框的外部而不是按钮怎么办?要解决这个问题,您必须注意 show prop 的值。像这个。 In your v-dialog 组件放这个。

    watch: {
       show(val) {
          if(!val) {
             this.$emit('hideModal')
          }
       }
    }
    

    现在一切正常。

    是使用vue .sync修饰符

    为方便起见,Vue js 提供了这种模式的简写, .sync 修饰符。请阅读此处的文档sync modifier。这种方法可以让您避免发出事件。不幸的是,真正的双向绑定会产生维护问题。

    最后是使用状态管理,vuex

    它作为一个集中式存储库中的所有组件 应用程序,其规则确保状态只能在其中发生变异。此处的文档vuex 一种可预测的时尚。

    【讨论】:

    • 已解决。但是,我不得不删除this&lt;v-btn text color="primary" @click="$emit('hideModal')" class="body-1"&gt;Beleza!&lt;/v-btn&gt;。使用this 我得到以下错误:[Vue warn]: Error in v-on handler: "TypeError: this is null"
    • 啊好吧抱歉,是的,你必须删除它。
    【解决方案2】:
      <v-btn text color="primary" @click="show = false" class="body-1">Beleza!</v-btn>
    

    您不能像错误所说的那样更改道具,而必须添加功能,将其作为道具发送,并在需要更改道具值时调用,父必须处理函数并更改数据。

    <template>
        ...
     <BasicMessageDialog :message="messageBasicDialog" :show="showBasicMessageDialog" :hide="showBasicMessageDialog=!showBasicMessageDialog">
    ...
    </BasicMessageDialog>
    </template>
    

    <v-btn text color="primary" @click="hide" class="body-1">Beleza!</v-btn>
    

    https://vuejs.org/v2/guide/components-props.html#One-Way-Data-Flow

    【讨论】:

    • 我无法重现您的解决方案,请改进您的答案。
    猜你喜欢
    • 2020-12-11
    • 2021-12-02
    • 2021-05-02
    • 2020-09-03
    • 2023-03-05
    • 1970-01-01
    • 2022-07-15
    • 2021-07-11
    • 2020-12-13
    相关资源
    最近更新 更多