亚洲乱码中文字幕综合,中国熟女仑乱hd,亚洲精品乱拍国产一区二区三区,一本大道卡一卡二卡三乱码全集资源,又粗又黄又硬又爽的免费视频

Vue中實現(xiàn)父子組件雙向數(shù)據(jù)流的三種方案分享

 更新時間:2023年08月04日 10:46:23   作者:FEF前端團(tuán)隊  
通常情況下,父子組件的通信都是單向的,或父組件使用props向子組件傳遞數(shù)據(jù),或子組件使用emit函數(shù)向父組件傳遞數(shù)據(jù),本文將嘗試講解Vue中常用的幾種雙向數(shù)據(jù)流的使用,需要的朋友可以參考下

1. 背景

通常情況下,父子組件的通信都是單向的,或父組件使用props向子組件傳遞數(shù)據(jù),或子組件使用emit函數(shù)向父組件傳遞數(shù)據(jù)。

但在有些場景下,免不了需要父子組件之間進(jìn)行雙向數(shù)據(jù)流,從而讓我們的業(yè)務(wù)代碼更加簡潔。很常見的場景之一:父組件引入了一個子組件,子組件是個dialog彈窗,在父組件可以點(diǎn)擊某個按鈕顯示dialog,但是dialog組件的關(guān)閉操作是在組件里面的。這個時候使用雙向數(shù)據(jù)流管理dialog組件的顯隱狀態(tài),不僅讓代碼顯得優(yōu)雅,還能少寫不少業(yè)務(wù)。

那我們能不能直接在子組件修改props來實現(xiàn)上述功能呢?當(dāng)然是不行的,因為在Vueprops屬性是只讀的。官方文檔給出的解釋如下:

所有的 props 都遵循著單向綁定原則,props 因父組件的更新而變化,自然地將新的狀態(tài)向下流往子組件,而不會逆向傳遞。這避免了子組件意外修改父組件的狀態(tài)的情況,不然應(yīng)用的數(shù)據(jù)流將很容易變得混亂而難以理解。本文將嘗試講解Vue中常用的幾種雙向數(shù)據(jù)流的使用。

2. 雙向數(shù)據(jù)流

2.1. 什么是雙向數(shù)據(jù)流

簡而言之,雙向數(shù)據(jù)流就是model的更新會觸發(fā)view的更新,view的更新會觸發(fā)model的更新,它們的作用是相互的。

tips: 這里只討論父子組件傳值時的雙向數(shù)據(jù)流,對框架數(shù)據(jù)的雙向數(shù)據(jù)流不做展開。

2.2. Vue提供的解決方案

2.2.1. 方案一:v-model

父組件代碼如下:

<template>
  <div class="container">
    <a-button type="primary" @click="handleClick">改變子組件的狀態(tài)</a-button>
    <p>父組件狀態(tài):{{ message }}</p>
    <!-- 子組件 -->
    <child-view v-model="message"></child-view>
		<!-- 也可以使用多個v-model,子組件里面用props正常接收就可以了 -->
		<!-- <child-view v-model:message="message" v-model:msg="msg"></child-view> -->
  </div>
</template>
<script>
import ChildView from '@/components/ChildView.vue'
export default {
  name: 'HomeView',
  components: {
    ChildView
  },
  data () {
    return {
      message: ''
    }
  },
  methods: {
    handleClick () {
      this.message = '我是用v-model修改的狀態(tài)'
    }
  }
}
</script>

子組件代碼如下:

<template>
  <div>
    <a-button type="primary" @click="handleClick">改變父組件的狀態(tài)</a-button>
    <p>子組件狀態(tài):{{ value }}</p>
  </div>
</template>
<script>
export default {
  props: {
    // 這里框架默認(rèn)屬性名就是value
    value: {
      type: String,
      default: ''
    },
    // 接收多個props
    message: {
      type: String,
      default: ''
    },
    msg: {
      type: String,
      default: ''
    }
  },
  methods: {
    handleClick () {
      // 這里框架默認(rèn)事件名就是input
      // 發(fā)送的數(shù)據(jù)會被父級v-model="message"接收到,再被value=message傳回來
      this.$emit('input', '我是在子組件里面修改父組件v-model的值')
    }
  }
}
</script>

自定義v-modelprops屬性:

Vue 允許一個自定義組件在使用 v-model 時定制 prop 和 event。默認(rèn)情況下,一個組件上的 v-model 會把 value 用作 prop 且把 input 用作 event,但是一些輸入類型比如單選框和復(fù)選框按鈕可能想使用 value prop 來達(dá)到不同的目的。使用 model 選項可以回避這些情況產(chǎn)生的沖突。

<template>
  <div>
    <a-button type="primary" @click="handleClick">改變父組件的狀態(tài)</a-button>
    <p>子組件狀態(tài):{{ msg }}</p>
  </div>
</template>
<script>
export default {
  // 自定義prop名稱和事件
  model: {
    prop: 'msg',
    event: 'update'
  },
  props: {
    msg: {
      type: String,
      default: ''
    }
  },
  methods: {
    handleClick () {
      this.$emit('update', '我是在子組件里面修改父組件v-model的值')
    }
  }
}
</script>

瀏覽器運(yùn)行效果:

2.2.2. 方案二:sync修飾符

父組件代碼如下:

<template>
  <div class="container">
    <a-button type="primary" @click="handleClick">改變子組件的狀態(tài)</a-button>
    <p>父組件狀態(tài):{{ message }}</p>
    <child-view :msg.sync="message"></child-view>
  </div>
</template>
<script>
import ChildView from '@/components/ChildView.vue'
export default {
  name: 'HomeView',
  components: {
    ChildView
  },
  data () {
    return {
      message: ''
    }
  },
  methods: {
    handleClick () {
      this.message = '十里平湖霜滿天'
    }
  }
}
</script>

子組件代碼如下:

<template>
  <div>
    <a-button type="primary" @click="handleClick">改變父組件的狀態(tài)</a-button>
    <p>子組件狀態(tài):{{ msg }}</p>
  </div>
</template>
<script>
export default {
  props: {
    msg: String
  },
  methods: {
    handleClick () {
      this.$emit('update:msg', '寸寸青絲愁華年')
    }
  }
}
</script>

瀏覽器運(yùn)行效果:

2.2.3. 方案三:通過JS引用類型特性繞過props

父組件代碼如下:

<template>
  <div class="container">
    <a-button type="primary" @click="handleClick">改變子組件的狀態(tài)</a-button>
    <p>父組件狀態(tài):{{ config.message }}</p>
    <child-view :config="config"></child-view>
  </div>
</template>
<script>
import ChildView from '@/components/ChildView.vue'
export default {
  name: 'HomeView',
  components: {
    ChildView
  },
  data () {
    return {
      config: {
        message: ''
      }
    }
  },
  methods: {
    handleClick () {
      this.config.message = '我是用v-model修改的狀態(tài)'
    }
  }
}
</script>

子組件代碼如下:

通過JS引用類型特性繞過props

運(yùn)行效果和v-model一樣,這里就不貼圖了。

3. 總結(jié)

Vue父子組件通信,都是單向的,在需要雙向通信的時候,我們有三種方式達(dá)到目的:

  1. 使用v-model
  2. 使用sync修飾符
  3. 通過JS引用類型特性繞過props單向數(shù)據(jù)流

以上就是Vue中實現(xiàn)父子組件雙向數(shù)據(jù)流的三種方案分享的詳細(xì)內(nèi)容,更多關(guān)于Vue實現(xiàn)父子組件雙向數(shù)據(jù)流的資料請關(guān)注腳本之家其它相關(guān)文章!

相關(guān)文章

最新評論