常用Vue組件通信方式

1 - props

基礎(chǔ)使用
  • 通過(guò)屬性的方式給子組件傳遞動(dòng)態(tài)或靜態(tài)數(shù)據(jù)

  • 注意引用值的傳遞,傳遞的是地址,子組件內(nèi)改變會(huì)導(dǎo)致父組件內(nèi)也改變

  • 注意標(biāo)簽名和特性名會(huì)被自動(dòng)轉(zhuǎn)換為小寫,可使用 - 分隔長(zhǎng)的特性名,字符串模板內(nèi)不存在此限制

    • <chloe :name="name" age="20" da-sha="dasha"></chloe>

    • props: ["name", "age", "daSha"]

  • 使用v-bind傳遞一整個(gè)對(duì)象

    • <chloe v-bind="person"></chloe>

    • props: ["name", "age", "daSha"]

限制類型
  • 我們可以指定傳遞過(guò)來(lái)的prop類型

    • props: { chloe: String / Number / Boolean / Array / Object / Date / Function / Symbol / 自定義構(gòu)造函數(shù) / 前面這些組成的數(shù)組(表示滿足其中一種即可) }

    • 注意,nullundefined可通過(guò)任何類型的驗(yàn)證

  • 還可以對(duì)prop限定更多

props: {
  name: {
    type: String,   類型限定
    default: "chloe",   默認(rèn)值 若為對(duì)象則應(yīng)使用函數(shù)返回值的形式 default() {} 防止組件多次調(diào)用卻使用的是同一個(gè)默認(rèn)值 類似 data() {}
    required: true,   該prop是否必須要傳
    validator(prop) {   自定義驗(yàn)證函數(shù) 參數(shù)即為該prop的值 返回false則驗(yàn)證失敗
      return true;
    }
  }
}
單向數(shù)據(jù)流
  • 父組件向子組件傳遞props,子組件接收后不應(yīng)任意直接對(duì)其進(jìn)行修改,尤其是引用值。若隨意修改則會(huì)導(dǎo)致你的數(shù)據(jù)流向相當(dāng)混亂

  • 如果一定要改變,原始值可以直接用一個(gè)data屬性來(lái)接收,引用值則需深度克隆再接收

非prop特性
  • 傳遞給了組件,卻沒有被組件接收的特性就是非prop特性,事件除外

  • prop特性會(huì)被直接掛到組件的根元素上

    • <chloe :name="name" age="20"></chloe>

    • props: [ "name" ]

替換 / 合并已有特性
  • <chloe type="text" class="a"></chloe>

  • <input type="radio" class="b"></input> chloe組件的template

    • typeclass均未被組件接收,成為了非prop特性,掛到了組件的根元素input

    • 除了classstyle會(huì)被合并,其余則是組件上的prop值替換根元素上的prop

禁用非prop特性繼承
  • 如果不希望組件的根元素繼承非prop特性,可以給組件設(shè)置inheritAttrs: false

    • Vue.component("chloe", { inheritAttrs: false })
$attrs
  • 拿到組件上的所有非prop特性,事件除外

  • 可以和inheritAttrs: false配合使用,將這些非prop特性用到指定的元素上

2 - $emit

  • 實(shí)現(xiàn)子組件向父組件傳遞數(shù)據(jù)

  • 觸發(fā)綁定到組件上的任意事件 $emit(事件名字符串,要傳遞的參數(shù))

  • 因?yàn)槭录麜?huì)被小寫轉(zhuǎn)換,所以推薦用kebab-case形式命名,$emit時(shí)同樣要用這個(gè)

  • 事件處理函數(shù)寫在行間,可以使用$event接收子組件傳遞來(lái)的參數(shù)

    • <chloe @haha-lala="name = $event;"></chloe>

    • <button @click="$emit('haha-lala', 'chloe')">chloe</button> chloe組件的模板

  • 也可將事件處理函數(shù)寫在父組件methods內(nèi),參數(shù)名可自定義

    • <chloe @haha="changeName"></chloe>

3 - 組件上的v-model

  • 語(yǔ)法糖而已

  • 實(shí)現(xiàn)父子組件相互通信,一個(gè)組件只能用一次v-model

  • 在子組件上綁定v-model,傳遞數(shù)據(jù),默認(rèn)監(jiān)聽input事件,子組件中通過(guò)$emit觸發(fā)事件

    • <chloe v-model="searchText" /> 默認(rèn)等價(jià)于下面這種形式

    • <chloe :value="searchText" @input="searchText = $event" />

  • 在子組件中接收value,并綁定事件

Vue.component("chloe", {
  props: ["value"],
  template: `
    <input 
      :value="value"
      @input="$emit('input', $event.target.value)"
    />
  `
});
自定義監(jiān)聽事件類型及值
  • 通過(guò)子組件中的model屬性來(lái)自定義

    • model: { prop: "checked",event: "change" }

4 - .sync

  • 也是語(yǔ)法糖而已,vue1.x時(shí)便存在,2.0移除,2.3回歸

  • v-model一樣,.sync也是做雙向數(shù)據(jù)綁定的,但.sync可以綁定任意屬性

    • <chloe :inp-val.sync="searchText"></chloe>等價(jià)于下面這種形式

    • <chloe :inp-val="searchText" @update:inp-val="searchText = $event" />

  • 在子組件中接收value,并綁定事件

Vue.component("chloe", {
  props: ["inpVal"],
  template: `
    <input 
      :value="inpVal"
      @input="$emit('update:inp-val', $event.target.value)"
    />
  `
});
  • 一次設(shè)置多個(gè).sync屬性

    • <chloe v-bind.sync="obj" />
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

友情鏈接更多精彩內(nèi)容