4.vue組件通訊

1. 父組件給子組件傳值

父組件給子組件通訊的步驟:

1.父組件調用子組件的時候綁定動態屬性。vue

<v-header :title="title"></v-header>

二、在子組件裏面經過props接收父組件傳過來的數據。數組

//兩種方式
props:['title']

props:{
    'title':String      
}

父組件給子組件通訊的形式:

  1. 父組件給子組件傳值。
  2. 父組件給子組件傳方法。
  3. 父組件把整個實例傳給子組件。

注意:函數

  1. 不要使得父子組件中的屬性/方法重複了。當重複時,會使用父組件的屬性/方法。
  2. prop 是單向綁定的:當父組件的屬性變化時,將傳導給子組件,可是不會反過來。

示例:ui

Home.vue(父組件)
<template>
    <div>
        <p class="first">我是Home組件:{{msg}}</p>
        <hr>
        <v-info v-bind:homeTitle="title" :homeRun="run" :homeThis="this"></v-info>
    </div>
</template>

<script>
    import Info from "./Info";

    export default {
        name: "Home",
        components: {
            "v-info": Info,
        },
        data() {
            return {
                msg: "我是Home組件",
                title: "首頁"
            }
        },
        methods: {
            run: function (data) {
                alert("這是Home組件的方法" + data);
            }
        },

    }
</script>

<style scoped>
    p {
        color: #42b983;
    }
</style>
Info.vue(子組件)
<template>
    <div id="info">
        <p>我是Home的子組件info</p>
        <button @click="getTitle">獲取父組件的title</button>
        <button @click="getParentRun(123)">調用父組件的run方法</button>
        <button @click="getHome">父組件經過this把整個實例傳給子組件</button>
    </div>
</template>

<script>
    export default {
        name: "Info",
        data() {
            return {
                
            }
        },
        methods: {
            getTitle: function () {
                alert(this.homeTitle);
            },
            getHome: function () {
                alert(this.homeThis.msg);
            },
            getParentRun: function (data) {
                this.homeRun(data);
            }
        },
        props: {
            "homeTitle": {
                type: String,
                required: true,
                default: "HomeA"
            },
            "homeRun": {
                type: Function,
                required: true,
            },
            "homeThis": {
                type: Object,
                required: true,
            },
        }
        //props: ["homeTitle", "homeRun", "homeThis"],
    }
</script>

Prop 驗證

組件能夠爲 props 指定驗證要求。
爲了定製 prop 的驗證方式,你能夠爲 props 中的值提供一個帶有驗證需求的對象,而不是一個字符串數組。
例如:this

Vue.component('my-component', {
  props: {
    // 基礎的類型檢查 (`null` 和 `undefined` 會經過任何類型驗證)
    propA: Number,
    // 多個可能的類型
    propB: [String, Number],
    // 必填的字符串
    propC: {
      type: String,
      required: true
    },
    // 帶有默認值的數字
    propD: {
      type: Number,
      default: 100
    },
    // 帶有默認值的對象
    propE: {
      type: Object,
      // 對象或數組默認值必須從一個工廠函數獲取
      default: function () {
        return { message: 'hello' }
      }
    },
    // 自定義驗證函數
    propF: {
      validator: function (value) {
        // 這個值必須匹配下列字符串中的一個
        return ['success', 'warning', 'danger'].indexOf(value) !== -1
      }
    }
  }
})

當 prop 驗證失敗的時候,(開發環境構建版本的) Vue 將會產生一個控制檯的警告。
type 能夠是下面原生構造器:code

  • String
  • Number
  • Boolean
  • Array
  • Object
  • Date
  • Function
  • Symbol

type 也能夠是一個自定義構造器,使用 instanceof 檢測。component

2.父子組件主動通訊

父組件主動獲取子組件的數據和方法:

1.調用子組件的時候定義一個ref對象

<v-header ref="header"></v-header>

2.在父組件裏面經過事件

this.$refs.header.屬性
this.$refs.header.方法

子組件主動獲取父組件的數據和方法:

this.$parent.數據
this.$parent.方法

示例:ip

Home.vue
<template>
    <div>
        <p class="first">我是Home組件:{{msg}}</p>
        <button @click="getChildMsg">獲取子組件Info的msg</button>
        <button @click="getChildRun">獲取子組件Info的run()</button>
        <hr>
        <v-info ref="info" v-bind:homeTitle="title" :homeRun="run" :homeThis="this"></v-info>
    </div>
</template>

<script>
    import Info from "./Info";

    export default {
        name: "Home",
        components: {
            "v-info": Info,
        },
        data() {
            return {
                msg: "我是Home組件",
                title: "首頁",
                color: "red",
            }
        },
        methods: {
            run: function (data) {
                alert("這是Home組件的方法" + data);
            },
            getChildMsg: function () {
                alert(this.$refs.info.msg);
            },
            getChildRun: function () {
                this.$refs.info.run();
            }
        },

    }
</script>
Info.vue
<template>
    <div id="info">
        <p>我是Home的子組件info</p>
        <button @click="autoGetParent">子組件主動獲取父組件的數據和方法</button>
    </div>
</template>

<script>
    export default {
        name: "Info",
        data() {
            return {
                msg:"我是Home的子組件info",
            }
        },
        methods: {
            run:function(){
                alert("我是子組件info的方法");
            },
            autoGetParent:function(){
                alert(this.$parent.color);
                this.$parent.run('123');
            }
        },
    }
</script>

非父子組件傳值

使用 \$on(eventName) 監聽事件
使用 \$emit(eventName) 觸發事件

一、新建一個js文件,而後引入vue,實例化vue,最後暴露這個實例。

VueEvent.js
import Vue from "vue";

const VueEvent = new Vue();
export default VueEvent;

二、在要廣播的文件中引入剛纔定義的實例。並在 methods:{}中,經過 VueEmit.$emit('名稱','數據') 進行廣播。
三、在接收收數據的文件mounted(){}中經過 VueEmit.$on('名稱',function(){}) 接收廣播的數據。

Home.vue
<template>
    <div>
        <p>我是Home組件</p>
        <button @click="emitNews">點擊給News傳消息</button>
    </div>
</template>

<script>
    import VueEvent from "../../model/VueEvent"

    export default {
        name: "Home",
        data() {
            return {
                msg: "我是Home組件",
            }
        },
        methods: {
            emitNews: function () {
                VueEvent.$emit("to-news", this.msg);
            }
        },
        mounted() {
            VueEvent.$on("to-home", (data) => {
                alert(data);
            })
        }
    }
</script>

News.vue

<template>
    <div id="news">
        <p>我是新聞組件</p>
        <button @click="emitHome">點擊給home傳消息</button>
    </div>
</template>

<script>
    //引入vue實例
    import VueEvent from "../../model/VueEvent"
    export default {
        name: "News",
        data(){
            return {
                msg:"我是新聞組件"
            }
        },
        methods:{
            emitHome:function(){
                VueEvent.$emit("to-home",this.msg);
            }
        },
        mounted() {
            VueEvent.$on("to-news",(data)=>{
                alert(data);
            })
        }
    }
</script>
相關文章
相關標籤/搜索