Vue入門 ---- 組件通信

##組件通信:

  1. 子組件獲取父組件的數據
  2. 父組件獲取子組件的數據
  3. 平行組件之間的通信
  4. vue2.0中用子組件修改父組件數據報錯問題
  5. 一定需要通過子組件修改父組件

子組件獲取父組件的數據
通過子組件中的屬性props,以與父組件數據的綁定。(注意:1.0版本允許子組件修改父組件的數據,使用sync進行同步。2.0不再支持)

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>Document</title>
    
    <script src="lib\vue.js"></script>
    <style>
    [v-cloak] {display: none;}
    </style>
  
    <script>
        window.onload = function() {
            Vue.component('parent', {
                template: `
                    <div>
                        <h1>父組件-->{{msg1}}, {{msg2}}</h1>
                        <child :m1="msg1" :m2="msg2"></child>
                    </div>`,
                data() {
                    return {
                        msg1: "父組件數據1",
                        msg2: "父組件數據2",
                    }
                }
            })
            Vue.component('child', {
                template: `
                    <h2>子組件-->{{m1}}, {{m2}}</h2>`,
                props: ['m1', 'm2'],
            })

            new Vue ({
                el: '#box',
                data: {
                },
            })
            
        }
    </script>
</head>
<body>
    <div id="box" v-cloak>
        <parent></parent>
    </div>
</body>
</html>

父組件獲取子組件的數據
利用子組件的事件調用$emit(事件名,數據參數)進行事件監聽,並傳遞參數給父組件。

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>Document</title>
    
    <script src="lib\vue.js"></script>
    <style>
    [v-cloak] {display: none;}
    </style>
  
    <script>
        window.onload = function() {
            Vue.component('parent', {
                template: `
                    <div>
                        <h1>父組件-->{{msgc}}</h1>
                        <child @m3="get"></child>
                    </div>`,
                data() {
                    return {
                        msgc: ""
                    }
                },
                methods: {
                    get(msg) {
                        this.msgc = msg;
                    }
                },
            }),
            Vue.component('child', {
                template:`
                    <div>
                        <h2>子組件-->{{msg3}}</h2>
                        <input type="button" name="" id="" value="按鈕" @click="send">
                    </div>`,
                data() {
                    return {
                        msg3: "子組件數據",
                    }
                },
                methods: {
                    send() {
                        this.$emit('m3', this.msg3);
                    }
                }
            })

            new Vue ({
                el: '#box',
                data: {
                },
            })
            
        }
    </script>
</head>
<body>
    <div id="box" v-cloak>
        <parent></parent>
    </div>
</body>
</html>

平行組件之間的通信
通過定義事件調度器,用emit()emit()傳遞,用on()接收

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>Document</title>

    <script src="lib\vue.js"></script>
    <style>
    [v-cloak] {display: none;}
    </style>

    <script>
        window.onload = function() {
            // 事件調度器
            var Event = new Vue();
            Vue.component('First', {
                template: `
                <div>
                    First說:<input @keyup="onChange" v-model="fir">
                </div>`,
                data() {
                    return {
                        fir: '',
                    }
                },
                methods: {
                    onChange() {
                        Event.$emit('sec_said', this.fir);
                    }
                }
            })
            Vue.component('Second', {
                template: `
                <div>
                    Second重複First說的話:{{sec}}
                </div>`,
                data() {
                    return {
                        sec: '',
                    }
                },
                mounted() {
                    // 用變量存下this的指向
                    var me = this;
                    Event.$on('sec_said', function(data) {
                        me.sec = data
                    })
                }
            })
            new Vue ({
                el: '#box',
                data: {
                },
            })

        }
    </script>
</head>
<body>
    <div id="box" v-cloak>
        <First></First>
        <second></second>
    </div>
</body>
</html>

vue2.0中用子組件修改父組件數據報錯問題
可以利用mounted()進行中轉,變爲單純的對子組件進行修改,這樣可以不產生錯誤信息,但是並不能將更改同步到父組件身上

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>Document</title>
    
    <script src="lib\vue.js"></script>
    <style>
    [v-cloak] {display: none;}
    </style>
  
    <script>
        window.onload = function() {
            Vue.component('child', {
                template: `
                    <div>
                        <h3>子組件</h3>
                        <input type="button" name="" id="" value="按鈕" @click="change()">
                        <strong>{{b}}</strong>
                    </div>`,
                data() {
                    return {
                        b: '',
                    }
                },
                props:['msg'],
                // 通過mounted進行中轉,變爲對子集元素的操作
                mounted() {
                    this.b = this.msg;
                },
                methods: {
                    change() {
                        this.b = '被更改了';
                    }
                }
            })
            new Vue ({
                el: '#box',
                data: {
                    a: "父組件數據",
                },
            })
            
        }
    </script>
</head>
<body>
    <div id="box" v-cloak>
        父級: -> {{a}}
        <child :msg="a"></child>
    </div>
</body>
</html>

一定需要通過子組件修改父組件
那麼可以採用下面的方法,將數據封裝成一個對象傳遞給子組件,由於js對象之間是引用的關係,所以改變引用必然改變數據。

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>Document</title>
    
    <script src="lib\vue.js"></script>
    <style>
    [v-cloak] {display: none;}
    </style>
  
    <script>
        window.onload = function() {
            Vue.component('child', {
                template: `
                    <div>
                        <h3>子組件</h3>
                        <input type="button" name="" id="" value="按鈕" @click="change()">
                        <strong>{{msg.a}}</strong>
                    </div>`,
                props:['msg'],
                mounted() {
                    this.b = this.msg;
                },
                methods: {
                    change() {
                        this.msg.a = '被更改了';
                    }
                }
            })
            new Vue ({
                el: '#box',
                data: {
                    giveData: {
                        a: "父組件數據",
                    }
                },
            })
        }
    </script>
</head>
<body>
    <div id="box" v-cloak>
        父級: -> {{giveData.a}}
        <child :msg="giveData"></child>
    </div>
</body>
</html>
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章