<ruby id="bdb3f"></ruby>

    <p id="bdb3f"><cite id="bdb3f"></cite></p>

      <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
        <p id="bdb3f"><cite id="bdb3f"></cite></p>

          <pre id="bdb3f"></pre>
          <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

          <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
          <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

          <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                <ruby id="bdb3f"></ruby>

                ??碼云GVP開源項目 12k star Uniapp+ElementUI 功能強大 支持多語言、二開方便! 廣告
                Vue組件數據通訊常常會有父子組件,兄弟組件之間的數據通訊。也就是說在Vue中組件通訊有一定的原則。 ## 父子組件通訊原則 為了提高組件的獨立性與重用性,父組件會通過 `props` 向下傳數據給子組件,當子組件有事情要告訴父組件時會通過 `$emit` 事件告訴父組件。如此確保每個組件都是獨立在相對隔離的環境中運行,可以大幅提高組件的維護性。 ![](//upload-images.jianshu.io/upload_images/13341631-cb2bbed4c7ccb92d.png!web?imageMogr2/auto-orient/strip%7CimageView2/2/w/539/format/webp) 在《Vue組件通訊》一文中有詳細介紹過這部分。但這套通訊原則對于兄弟組件之間的數據通訊就有一定的詬病。當然,在Vue中有其他的方式來處理兄弟組件之間的數據通訊,比如Vuex這樣的庫。但在很多情況之下,咱們的應用程序不需要類似Vuex這樣的庫來處理組件之間的數據通訊,而可以考慮Vue中的 **事件總線** ,即 \*\*`EventBus` \*\*。 ## EventBus的簡介 `EventBus` 又稱為事件總線。在Vue中可以使用 `EventBus` 來作為溝通橋梁的概念,就像是所有組件共用相同的事件中心,可以向該中心注冊發送事件或接收事件,所以組件都可以上下平行地通知其他組件,但也就是太方便所以若使用不慎,就會造成難以維護的災難,因此才需要更完善的Vuex作為狀態管理中心,將通知的概念上升到共享狀態層次。 ## 如何使用EventBus 在Vue的項目中怎么使用 `EventBus` 來實現組件之間的數據通訊呢?具體可以通過下面幾個步驟來完成。 ### 初始化 首先你需要做的是創建事件總線并將其導出,以便其它模塊可以使用或者監聽它。我們可以通過兩種方式來處理。先來看第一種,新創建一個 `.js` 文件,比如 `event-bus.js` : ~~~ // event-bus.js import Vue from 'vue' export const EventBus = new Vue() ~~~ 你需要做的只是引入 Vue 并導出它的一個實例(在這種情況下,我稱它為 `EventBus` )。實質上它是一個不具備 DOM 的組件,它具有的僅僅只是它實例方法而已,因此它非常的輕便。 另外一種方式,可以直接在項目中的 `main.js` 初始化 `EventBus` : ~~~ // main.js Vue.prototype.$EventBus = new Vue() ~~~ 注意,這種方式初始化的 `EventBus` 是一個 **全局的事件總線** 。稍后我們會花點時間專門聊一聊全局的事件總線。 現在我們已經創建了 `EventBus` ,接下來你需要做到的就是在你的組件中加載它,并且調用同一個方法,就如你在父子組件中互相傳遞消息一樣。 ### 發送事件 假設你有兩個子組件: `DecreaseCount` 和 `IncrementCount` ,分別在按鈕中綁定了 `decrease()`和 `increment()` 方法。這兩個方法做的事情很簡單,就是數值遞減(增) `1` ,以及角度值遞減(增) `180` 。在這兩個方法中,通過 `EventBus.$emit(channel: string, callback(payload1,…))` 監聽 `decreased` (和 `incremented` )頻道。 ~~~ <!-- DecreaseCount.vue --> <template> <button @click="decrease()">-</button> </template> <script> import { EventBus } from "../event-bus.js"; export default { name: "DecreaseCount", data() { return { num: 1, deg:180 }; }, methods: { decrease() { EventBus.$emit("decreased", { num:this.num, deg:this.deg }); } } }; </script> <!-- IncrementCount.vue --> <template> <button @click="increment()">+</button> </template> <script> import { EventBus } from "../event-bus.js"; export default { name: "IncrementCount", data() { return { num: 1, deg:180 }; }, methods: { increment() { EventBus.$emit("incremented", { num:this.num, deg:this.deg }); } } }; </script> ~~~ 上面的示例,在 `DecreaseCount` 和 `IncrementCount` 分別發送出了 `decreased` 和 `incremented`頻道。接下來,我們需要在另一個組件中接收這兩個事件,保持數據在各組件之間的通訊。 ### 接收事件 現在我們可以在組件 `App.vue` 中使用 `EventBus.$on(channel: string, callback(payload1,…))`監聽 `DecreaseCount` 和 `IncrementCount` 分別發送出了 `decreased` 和 `incremented` 頻道。 ~~~ <!-- App.vue --> <template> <div id="app"> <div class="container" :style="{transform: 'rotateY(' + degValue + 'deg)'}"> <div class="front"> <div class="increment"> <IncrementCount /> </div> <div class="show-front"> {{fontCount}} </div> <div class="decrement"> <DecreaseCount /> </div> </div> <div class="back"> <div class="increment"> <IncrementCount /> </div> <div class="show-back"> {{backCount}} </div> <div class="decrement"> <DecreaseCount /> </div> </div> </div> </div> </template> <script> import IncrementCount from "./components/IncrementCount"; import DecreaseCount from "./components/DecreaseCount"; import { EventBus } from "./event-bus.js"; export default { name: "App", components: { IncrementCount, DecreaseCount }, data() { return { degValue:0, fontCount:0, backCount:0 }; }, mounted() { EventBus.$on("incremented", ({num,deg}) => { this.fontCount += num this.$nextTick(()=>{ this.backCount += num this.degValue += deg; }) }); EventBus.$on("decreased", ({num,deg}) => { this.fontCount -= num this.$nextTick(()=>{ this.backCount -= num this.degValue -= deg; }) }); } }; </script> ~~~ 最終得到的效果如下: 最后用一張圖來描述示例中用到的 `EventBus` 之間的關系: ![](//upload-images.jianshu.io/upload_images/13341631-f03169d19423387e.png!web?imageMogr2/auto-orient/strip%7CimageView2/2/w/550/format/webp) 如果你只想監聽一次事件的發生,可以使用 `EventBus.$once(channel: string, callback(payload1,…))` 。 ### 移除事件監聽者 如果想移除事件的監聽,可以像下面這樣操作: ~~~ import { eventBus } from './event-bus.js' EventBus.$off('decreased', {}) ~~~ 你也可以使用 `EventBus.$off(‘decreased’)` 來移除應用內所有對此事件的監聽。或者直接調用`EventBus.$off()` 來移除所有事件頻道, **注意不需要添加任何參數** 。 上面就是 `EventBus` 的使用方式,是不是很簡單。上面的示例中我們也看到了,每次使用 `EventBus` 時都需要在各組件中引入 `event-bus.js` 。事實上,我們還可以通過別的方式,讓事情變得簡單一些。那就是創建一個全局的 `EventBus` 。接下來的示例向大家演示如何在Vue項目中創建一個全局的 `EventBus` 。 ## 全局EventBus 全局EventBus,雖然在某些示例中不提倡使用,但它是一種非常漂亮且簡單的方法,可以跨組件之間共享數據。 它的工作原理是發布/訂閱方法,通常稱為 `Pub/Sub` 。 這整個方法可以看作是一種設計模式,因為如果你查看它周圍的東西,你會發現它更像是一種體系結構解決方案。我們將使用普通的JavaScript,并創建兩個組件,并演示EventBus的工作方式。 讓我們看看下圖,并試著了解在這種情況下究竟發生了什么。 ![](//upload-images.jianshu.io/upload_images/13341631-40d2629faddb7b76.png!web?imageMogr2/auto-orient/strip%7CimageView2/2/w/550/format/webp) 我們從上圖中可以得出以下幾點: * 有一個全局EventBus * 所有事件都訂閱它 * 所有組件也發布到它,訂閱組件獲得更新 * 總結一下。所有組件都能夠將事件發布到總線,然后總線由另一個組件訂閱,然后訂閱它的組件將得到更新 在代碼中,我們將保持它非常小巧和簡潔。我們將它分為兩部分,將展示兩個組件以及生成事件總線的代碼。 ### 創建全局EventBus 全局事件總線只不過是一個簡單的 `vue` 組件。代碼如下: ~~~ var EventBus = new Vue(); Object.defineProperties(Vue.prototype, { $bus: { get: function () { return EventBus } } }) ~~~ 現在,這個特定的總線使用兩個方法 `$on` 和 `$emit` 。一個用于創建發出的事件,它就是`$emit` ;另一個用于訂閱 `$on` : ~~~ var EventBus = new Vue(); this.$bus.$emit('nameOfEvent',{ ... pass some event data ...}); this.$bus.$on('nameOfEvent',($event) => { // ... }) ~~~ 現在,我們創建兩個簡單的組件,以便最終得出結論。 接下來的這個示例中,我們創建了一個 `ShowMessage` 的組件用來顯示信息,另外創建一個 `UpdateMessage` 的組件,用來更新信息。 在 `UpdateMessage` 組件中觸發需要的事件。在這個示例中,將觸發一個 `updateMessage` 事件,這個事件發送了 `updateMessage` 的頻道: ~~~ <!-- UpdateMessage.vue --> <template> <div class="form"> <div class="form-control"> <input v-model="message" > <button @click="updateMessage()">更新消息</button> </div> </div> </template> <script> export default { name: "UpdateMessage", data() { return { message: "這是一條消息" }; }, methods: { updateMessage() { this.$bus.$emit("updateMessage", this.message); } }, beforeDestroy () { $this.$bus.$off('updateMessage') } }; </script> ~~~ 同時在 `ShowMessage` 組件中監聽該事件: ~~~ <!-- ShowMessage.vue --> <template> <div class="message"> <h1>{{ message }}</h1> </div> </template> <script> export default { name: "ShowMessage", data() { return { message: "我是一條消息" }; }, created() { var self = this this.$bus.$on('updateMessage', function(value) { self.updateMessage(value); }) }, methods: { updateMessage(value) { this.message = value } } }; </script>< ~~~ 最終的效果如下: 從上面的代碼中,我們可以看到 `ShowMessage` 組件偵聽一個名為 `updateMessage` 的特定事件,這個事件在組件實例化時被觸發,或者你可以在創建組件時觸發。另一方面,我們有另一個組件`UpdateMessage` ,它有一個按鈕,當有人點擊它時會發出一個事件。這導致訂閱組件偵聽發出的事件。這產生了 `Pub/Sub` 模型,該模型在兄弟姐妹之間持續存在并且非常容易實現。 ## 總結 本文主要通過兩個實例學習了Vue中有關于 `EventBus` 相關的知識點。主要涉及了 `EventBus` 如何實例化,又是怎么通過 `$emit` 發送頻道信號,又是如何通過 `$on` 來接收頻道信號。最后簡單介紹了怎么創建全局的 `EventBus` 。從實例中我們可以了解到, `EventBus` 可以較好的實現兄弟組件之間的數據通訊。
                  <ruby id="bdb3f"></ruby>

                  <p id="bdb3f"><cite id="bdb3f"></cite></p>

                    <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
                      <p id="bdb3f"><cite id="bdb3f"></cite></p>

                        <pre id="bdb3f"></pre>
                        <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

                        <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
                        <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

                        <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                              <ruby id="bdb3f"></ruby>

                              哎呀哎呀视频在线观看