2017-07-18 51 views
1

在我的vuejs程序中,我正在嘗試創建一個警報/通知系統的全局實例。這將在應用程序的最根本的實例。然後我的計劃是推送到一個對象數組,並將其傳遞給組件。 這隻有一半工程。vuejs原型數組沒有被監視

我app.vue

我有

<template> 
    <div id="app"> 
    <alert-queue :alerts="$alerts"></alert-queue> 
    <router-view></router-view> 
    </div> 
</template> 
我main.js

我有

exports.install = function (Vue, options) { 
    Vue.prototype.$alerts = [] 
} 

和我alert_queue.vue是

<template> 
    <div id="alert-queue"> 
    <div v-for="alert in alerts" > 

    <transition name="fade"> 
     <div> 
     <div class="alert-card-close"> 
      <span @click="dismissAlert(alert)"> &times; </span> 
     </div> 
     <div class="alert-card-message"> 
      {{alert.message}} 
     </div> 
     </div> 
    </transition> 

    </div> 
    </div> 
</template> 

<script> 
export default { 
    name: 'alert', 
    props: { 
    alerts: { 
     default: [] 
    } 
    }, 
    data() { 
    return { 
    } 
    }, 
    methods: { 
    dismissAlert (alert) { 
     for (let i = 0; i < this.alerts.length; i++) { 
     if (this.alerts[i].message === alert.message) { 
      this.alerts.splice([i], 1) 
     } 
     } 
    } 
    } 
} 

</script> 

我可以添加到這個列表現在通過使用this.$alerts.push({}),我可以看到他們通過console.logging結果添加。

問題是,組件不識別它們,除非我手動進去,並通過更改代碼中的某些內容並使webpack重新加載結果來強制刷新。據我所知,沒有辦法做到這一點編程....有沒有辦法讓原型組件像應用程序的其餘部分一樣觀看?

我試過讓大多數文件都有$ alerts對象,但是當我使用$root.$alerts.push({})時,它不起作用,因爲$ root是隻讀的。

有沒有另外一種方法可以解決這個問題?

+0

https://vuejs.org/v2/guide/list.html#Caveats – Jeff

+0

@Jeff Vue的可推到陣列寄存器,它只是不能註冊更新陣列的已有索引 – thanksd

+0

你說得對,我沒有仔細閱讀你的請求! – Jeff

回答

2

你可以做一個$alerts Vue公司實例,並使用它作爲一個事件總線:

exports.install = function (Vue, options) { 
    Vue.prototype.$alerts = new Vue({ 
    data: {alerts: []}, 
    events: { ... }, 
    methods: { ... } 
    }) 
} 

然後在你的組件,你可以調用一個方法this.$alerts.addAlert()這反過來又推到數組和廣播事件alert-added。在其他地方,你可以使用this.$alerts.on('alert-added', (alert) => { ... }

除此之外,我覺得這是一個很好的使用情況Vuex,這是相當多設計這樣的:在Vue.prototype定義https://github.com/vuejs/vuex

+0

謝謝。這是一個好的開始。它的功能。有一些偏差。但我認爲我可以熨燙出來。 – 173901

0

屬性是不喜歡的Vue實例的反應數據屬性。

我同意,在大多數情況下,傑夫的方法或使用Vuex是要走的路。


但是,你可以簡單地設置this.$alerts爲Vue的實例的數據屬性,然後更新該屬性(是反應性)會,由協會,更新全局$alerts陣列:

Vue.prototype.$alerts = ['Alert #1']; 
 

 
Vue.component('child', { 
 
    template: `<div><div v-for="i in items">{{ i }}</div></div>`, 
 
    props: ['items'], 
 
}) 
 

 
new Vue({ 
 
    el: '#app', 
 
    data() { 
 
    return { 
 
     globalAlerts: this.$alerts, 
 
    } 
 
    }, 
 
    methods: { 
 
    addToArray() { 
 
     this.globalAlerts.push('Alert #' + (this.globalAlerts.length + 1)); 
 
    } 
 
    } 
 
})
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.4.1/vue.min.js"></script> 
 
<div id="app"> 
 
    <child :items="$alerts"></child> 
 
    <button @click="addToArray">Add alert</button> 
 
</div>