天天看點

設定setInterval定時器、postMessage、addEventListener監聽器

項目中經常會使用到addEventListener,setInterval,非常好用,但也會有一些意想不到的bug。

場景:項目中在mounted中綁定了一個監聽器

window.addEventListener('message', this.getList)

,父子頁面間通過

postMessage

發送消息,然後就出現了bug,

this.getList

調用了好幾次,剛開始沒有規律,以為代碼有問題,postMessage發送了好幾條消息,又以為是監聽到了其他頁面發的消息,排查後發現都不是,并且發現規律,每跳轉一次頁面就會多發送一次消息,才想到是監聽器沒有銷毀,于是每次進頁面都會綁定一次監聽,導緻getList執行多次。

設定後一定要銷毀,否則監聽會一直存在。

設定定時器

setinterval 不會自動關閉

在要設定定時器的地方

this.timer = setInterval(function() {
  self.getList()
}, 1000 * 60)
           

定時器最好不要直接寫在mounted,建議寫在methods裡

然後一定要銷毀定時器,避免浪費資源。

也可以在methods中銷毀定時器,但是不銷毀的話就會一直執行

beforeDestroy(){
  if (this.timer) {
     clearInterval(this.timer); // 在Vue執行個體銷毀前,清除我們的定時器
   }
 },
           

addEventListener監聽

在一個項目的頁面中嵌入另一個項目的頁面,需要實作父子,子父頁面的通信。

window.postMessage() 方法可以安全地實作跨源通信。

但是一定要清除監聽

設定setInterval定時器、postMessage、addEventListener監聽器

頁面監聽一般寫在mounted中

window.addEventListener('message', this.getList)
this.iframeWin = this.$refs.iframe.contentWindow  //擷取到iframe的contentWindow屬性
           

iframe與頁面間傳消息一般采用postMessage

// 向父vue頁面發送資訊
this.iframeWin.postMessage({
  cmd:'writeDeviceName',
  params:{
    data:{
      msg:this.msg
    }
  },
}, '*')
           

beforeRouteLeave:離開路由之前執行的函數,可用于頁面的反向傳值,頁面跳轉。

離開路由前銷毀監聽,也可以寫在methods中,自行判斷并銷毀

beforeRouteLeave(to,from,next){
  window.removeEventListener('message', this.handleMessage)
  next()
},