1

在我的应用程序中Vue.JS,我尝试使用两个框架。出于某种原因,我的下一个代码引发了错误。就我而言,每个侧边栏都在一个单独的组件中。如何解决此类错误?v-navigation-drawerVuetify

错误:

vue.esm.js?efeb:628 [Vue 警告]:避免直接改变 prop,因为只要父组件重新渲染,该值就会被覆盖。相反,使用基于道具值的数据或计算属性。正在变异的道具:“开放”

BaseLayout.vue:

<template>
  <div>
    <v-app-bar app>
      <v-btn
        icon
        @click.stop="openLeftNavigationDrawer=!openLeftNavigationDrawer">
        <v-icon>mdi-map-clock-outline</v-icon>
      </v-btn>

      <v-spacer></v-spacer>

      <v-btn
        icon
        @click.stop="openRightNavigationDrawer=!openRightNavigationDrawer">
        <v-icon>mdi-filter</v-icon>
      </v-btn>
    </v-app-bar>

    <left-navigation-drawer
      :open="openLeftNavigationDrawer">
    </left-navigation-drawer>

    <right-navigation-drawer
      :open="openRightNavigationDrawer">
    </right-navigation-drawer>

    <v-content style="padding:unset!important;">
      <slot></slot>
    </v-content>
  </div>
</template>

<script>
import LeftNavigationDrawer from '../elements/LeftNavigationDrawer'
import RightNavigationDrawer from '../elements/RightNavigationDrawer'

export default {
  name: 'BaseLayout',
  components: {
    LeftNavigationDrawer,
    RightNavigationDrawer
  },
  data: function () {
    return {
      openLeftNavigationDrawer: false,
      openRightNavigationDrawer: false
    }
  }
}
</script>

LeftNavigationDrawer.vue:

<template>
  <v-navigation-drawer
    v-model="open"
    absolute
    left>
  </v-navigation-drawer>
</template>

<script>
export default {
  name: 'LeftNavigationDrawer',
  props: {
    open: false
  }
}
</script>

RightNavigationDrawer.vue:

<template>
  <v-navigation-drawer
    v-model="open"
    absolute
    right>
  </v-navigation-drawer>
</template>

<script>
export default {
  name: 'RightNavigationDrawer',
  props: {
    open: false
  }
}
</script>
4

1 回答 1

2

在您LeftNavigationDrawerRightNavigationDrawer组件中,当您编写 时v-model="open",它允许v-navigation-drawer组件更改 的值open

但是,在 VueJS 中,组件不允许更改其 props 的值。只有父母才能做到这一点。由于,open是一个道具并且v-navigation-bar正在尝试更改它,因此您会看到错误Avoid mutating a prop...

为了修复它,您可以data在您的组件中定义一个发送到v-navigation-drawer. 像这样的东西:

// RightNavigationDrawer.vue/LeftNavigationDrawer
<template>
  <v-navigation-drawer
    v-model="drawerOpen"
    @input="onInput"
    absolute
    right>
  </v-navigation-drawer>
</template>

<script>
export default {
  name: 'RightNavigationDrawer',
  props: {
    open: {
       type: Boolean,
       default: false
    }

  },
 data(){
   return {
      drawerOpen: this.open
   }
 },
 watch:{
   open(newVal){
      this.drawerOpen = newVal
   }
 },
 methods:{
   onInput(isOpen){
      this.$emit('drawerOpened', isOpen)
   }
 }
}
</script>
  • 数据drawerOpen存储 Vuetifyv-navigation-drawer是否打开。
  • 监视open允许您在open道具更改时更改抽屉状态(父子通信)
  • @input处理程序允许您将新抽屉状态发送到父组件(子到父通信)

对左右导航抽屉组件进行更改后,您BaseLayout.vue将需要侦听该drawerOpened事件。

// BaseLayout.vue
<template>
  <div>
    <v-app-bar app>
      <v-btn
        icon
        @click.stop="openLeftNavigationDrawer=!openLeftNavigationDrawer">
        <v-icon>mdi-map-clock-outline</v-icon>
      </v-btn>

      <v-spacer></v-spacer>

      <v-btn
        icon
        @click.stop="openRightNavigationDrawer=!openRightNavigationDrawer">
        <v-icon>mdi-filter</v-icon>
      </v-btn>
    </v-app-bar>

    <left-navigation-drawer
      :open="openLeftNavigationDrawer"
      @drawer-opened="handleDrawerChange("left", $event)"   // Add these event handlers
    >
    </left-navigation-drawer>

    <right-navigation-drawer
      :open="openRightNavigationDrawer"
      @drawer-opened="handleDrawerChange("right", $event)"
    >
    </right-navigation-drawer>

    <v-content style="padding:unset!important;">
      <slot></slot>
    </v-content>
  </div>
</template>

<script>
import LeftNavigationDrawer from '../elements/LeftNavigationDrawer'
import RightNavigationDrawer from '../elements/RightNavigationDrawer'

export default {
  name: 'BaseLayout',
  components: {
    LeftNavigationDrawer,
    RightNavigationDrawer
  },
  data: function () {
    return {
      openLeftNavigationDrawer: false,
      openRightNavigationDrawer: false
    }
  },
  methods:{
    handleDrawerChange(type, isOpen){
       if(type === "left"){
          this.openLeftNavigationDrawer = isOpen
       }else{
          this.openRightNavigationDrawer = isOpen
       }
    }

  }
}
</script>

  • 在您的 HTML 中,您监听drawer-opened事件。
  • 在事件处理程序中,您传递 2 个参数:一个是抽屉是左还是右。另一个参数是从组件接收到的值。
  • 根据抽屉是左还是右,你改变适当数据的值BaseLayout.vue
于 2019-12-03T06:54:39.157 回答