Vue通訊

前端小二&沐沐 發表於 2022-07-18
Vue

什麼是通訊

通訊是元件或模組之間的資料互動,多重通訊就形成了資料流,資料流管理的優劣決定了產品能否上線,資料流(通訊)越混亂,程式碼越難維護。

在Vue中常見的通訊方式

父子元件通訊

父傳子使用自定義屬性(props),子傳父使用自定義事件($emit())。

狀態提示

當兄弟元件之間需要共享資料時,我們通常的做法是把這個資料定義它們的共同父元件中,在通過自定義屬性實現資料共享。

provide/inject

這是元件樹中,自上而下的一種資料通訊方案,也就是隻能父元件向後代元件傳遞。需要注意的是:當provide提供動態資料(宣告式變數)時,動態資料發生變化,後代元件不會自動更新。

ref

ref是vue中一個內建屬性,每一個html元素或元件都有這個屬性,ref作用在元件上得到元件例項。使用ref訪問元件例項,進一步可以訪問元件中的資料和方法。(說明:ref是一種快速的DOM訪問方式,當然ref可以作用在元件上得到元件例項,這些ref得到的DOM例項或元件例項,使用this.$refs來訪問)

插槽通訊

藉助<slot>元件實現從子元件向父元件傳遞資料,藉助this.$slots訪問訪問父元件中的插槽例項,在自定義元件使用this.$slots訪問父元件的插槽例項;在父元件插槽中使用#default=‘scopet’訪問子元件<slot>回傳的資料

$parent/$children

 藉助$parent/$children可以實現在任一元件中訪問元件樹中的其它任意元件例項,可以做到在元件中隨意穿梭。($parent表示當前元件父元件例項,$children表示當前元件的子元件)

$attrs/$listteners

藉助$attrs可以訪問父元件傳遞過來的自定義屬性(除class和style外)藉助$listenrs可以訪問父元件給的自定義事件,在某些場景下,$attrs與$listeners可以替代props/$emit()這種通訊方案。

事件匯流排

藉助vue內建的事件系統($on/$emit()/$off/$once)實現“訂閱-釋出”通訊,這種通訊方式是一種與元件層級無關的“一對多”的通訊。

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
    <script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/vue.js"></script>
    <style>
        #app{
            display: flex;
        }
        .box{
            width: 650px;
            height: 400px;
            border: 1px solid #333;
            /* background-color: aqua; */
        }
        .msgbox{
            width: 649px;
            height: 100px;
            position: relative;
        }

        .msgbox>input{
            width: 580px;
            height: 20px;
        }
    </style>
</head>
<body>
    <div id="app">
        <el-user1></el-user1>
        <el-user2></el-user2>
        <!-- <div>
            <div class="box"></div>
            <div class="msgbox">
                <input type="text">
                <button>傳送</button>
            </div>
        </div> -->
    </div>

    <script>
        const bus = new Vue()
        Vue.component('el-user1',{
            template:`
            <div>
                <div class="box" v-html='content'></div>
                <div class="msgbox">
                    <input type="text" v-model='msg' @keyup.enter='send'>
                    <button @click='send'>傳送</button>
                </div>
            </div>
            `,
            data(){
                return{
                    msg:'',
                    content:''
                }
            },
            mounted(){
                bus.$on('elme',msg=>{
                    this.content += `<div>miss說:${msg}</div>`
                })
            },
            methods:{
                send(){
                    bus.$emit('el',this.msg)
                    this.msg = ''
                }
            }
           
        })

        Vue.component('el-user2',{
            template:`
            <div>
                <div class="box" v-html='content'></div>
                <div class="msgbox">
                    <input type="text" v-model='msg' @keyup.enter='send'>
                    <button @click='send'>傳送</button>
                </div>
            </div>
            `,
            data(){
                return{
                    msg:'',
                    content:''
                }
            },
            mounted(){
                bus.$on('el',msg=>{
                    this.content += `<div>me:${msg}</div>`
                })
            },
            methods:{
                send(){
                    bus.$emit('elme',this.msg)
                    this.msg = ''
                }
            }
           
        })

        const app = new Vue({
                el:'#app'
            })

    </script>
</body>
</html>

 

vuex通訊

是vue架構中終極通訊方案,也是vue架構中用的最多的一種通訊方案。