BroadcastChannel API 現已進入 Firefox 38

BroadcastChannel API 最近已經進入 Firefox 38。若網頁內容的來源及其所使用的瀏覽器均相同,則此 API 就能在瀏覽器之間進行簡單的訊息傳遞作業。此 API 現已擴充到 Windows 與 Worker 之上,並可於 iframes、瀏覽器分頁、Worker 的執行緒之間進行通訊。

BroadcastChannel API 本來是想在 Web App 的瀏覽器內容之間,進行簡易的訊息通訊作業。舉例來說,只要使用者登入 App 的網頁之一,即可依其個人資訊而更新其他所有的內容 (如分頁或獨立視窗)。或是使用者將照片上傳到瀏覽器視窗,亦可一併傳送到該 App 之內所開啟的其他頁面。此 API 本不是為了處理複雜作業所設計。如鎖定已分享的資源,或透過伺服器同步多個用戶端等的複雜作業,則 shared worker 還更適合。

API 概述

我們可用下列程式碼建立 BroadcastChannel 物件:

var myChannel = new BroadcastChannel("channelname");

channelname 的大小寫有別。BroadcastChannel 實例包含兩組函式,即 postMessage 與 close。函式 postMessage 可寄送訊息到 channel。而訊息內容可為任何物件,包含圖片、陣列、物件陣列等的複雜物件。只要網頁內容的來源、使用的瀏覽器、BroadcastChannel 的頻道名稱均相同,都會收到訊息。舉例來說,下列程式碼就會送出簡單字串:

myChannel.postMessage("Simple String");

任何頁面只要搭配 BroadcastChannel 物件的 onmessage 事件處理器來開啟頻道,都能處理所分派出的訊息。

myChannel.onmessage = function(event) {
    console.log(event.data);
}

另請注意,事件的資料屬性包含了訊息資料,且你也可能想了解事件的其他屬性。舉例來說,你可透過 event.origin 屬性,或 event.target.name 屬性中看到的頻道名稱來檢查 Web App 的來源。

而 close 函式可關閉特定瀏覽器內容的頻道,只要以下程式碼即可呼叫:

broadCastChannel.close();

 張貼 Blob 訊息

傳送字串或其他基本型別的資料都很簡單,但其實 BroadcastChannel API 仍可支援更複雜的物件。舉例來說,如果要將圖片傳送到另一組內容中,可使用下列程式碼:

var broadcastExample = {};
broadcastExample.setupChannel = function() {
    if ("BroadcastChannel" in window) {
        if (typeof broadcastExample.channel === 'undefined' ||
           !broadcastExample.channel) {
            //create channel
            broadcastExample.channel = new BroadcastChannel("foo");
        }
    }
}
broadcastExample.pMessage = function() {
    broadcastExample.setupChannel();
    //get image element
    var img = document.getElementById("ffimg");
    //create canvas with image
    var canvas = document.createElement("canvas");
    canvas.width = img.width;
    canvas.height = img.height;
    var ctx = canvas.getContext("2d");
    ctx.drawImage(img, 0, 0);
    //get blob of canvas
    canvas.toBlob(function(blob) {
        //broadcast blob
        broadcastExample.channel.postMessage(blob);
    });
}

上列程式碼包含兩組函式,代表 BroadcastChannel 的傳送端。setupChannel 函式僅會開啟 BroadcastChannel,而 pMessage 函式則檢查頁面的圖素並將之轉換為 Blob。最後將 Blob 張貼到 BroadcastChannel。接收頁面必須已準備監聽 BroadcastChannel 完畢以利接收訊息,且可將接收頁面撰寫如下:

var broadcastFrame = {};
 
//setup broadcast channel
broadcastFrame.setup = function() {
    if ("BroadcastChannel" in window) {
        if (typeof broadcastFrame.channel === 'undefined' || !broadcastFrame.channel) {
            broadcastFrame.channel = new BroadcastChannel("foo");
        }
        //function to process broadcast messages
        function func(e) {
            if (e.data instanceof Blob) {
                //if message is a blob create a new image element and add to page
                var blob = e.data;
                var newImg = document.createElement("img"),
                    url = URL.createObjectURL(blob);
                newImg.onload = function() {
                    // no longer need to read the blob so it's revoked
                    URL.revokeObjectURL(url);
               };
                newImg.src = url;
                var content = document.getElementById("content");
                content.innerHTML = "";
                content.appendChild(newImg);
            }
        };
        //set broadcast channel message handler
        broadcastFrame.channel.onmessage = func;
    }
}
window.onload = broadcastFrame.setup();

此程式碼可從廣播訊息中取得 Blob 並建立圖素,再加入接收端頁面。

Workers BroadcastChannel 訊息

BroadcastChannel API 亦可搭配專屬與共用的 workers。先簡單假設現已啟動 worker,且已透過主要指令碼傳送一則訊息到該 worker,接著就會由 worker 廣播訊息到 BroadcastChannel。

var broadcastExample = {};
broadcastExample.setupChannel = function() {
    if ("BroadcastChannel" in window) {
        if (typeof broadcastExample.channel === 'undefined' ||
           !broadcastExample.channel) {
            //create channel
            broadcastExample.channel = new BroadcastChannel("foo");
        }
    }
}
 
function callWorker() {
    broadcastExample.setupChannel();
    //verify compat
    if (!!window.Worker) {
        var myWorker = new Worker("worker.js");
        //ping worker to post to Broadcast Channel
        myWorker.postMessage("Broadcast from Worker");
    }
}
 
 
//Worker.js
onmessage = function(e) {
    //Broadcast Channel Message with Worker
    if ("BroadcastChannel" in this) {
        var workerChannel = new BroadcastChannel("foo");
        workerChannel.postMessage("BroadcastChannel Message Sent from Worker");
        workerChannel.close();
    }
}

接著就會依本文前述過的相同方式,於主頁面中處理該則訊息。

以 Worker 廣播訊息至 iframe

更多資訊

如果要進一步了解該如何於 iframe 中使用,則可到 github 找到本文所提的另一組範例程式碼。另可透過到規格bugzilla 討論串MDN 進一步了解BroadcastChannel API。亦可到 gecko 原始碼找到此 API 的程式碼與測試頁面。

 

 

原文連結:BroadcastChannel API in Firefox 38

 

 

0 則回應

Yahoo一紙荒唐合約 讓Mozilla Firefox每年爽拿3.75億美金 Yahoo一紙荒唐合約 讓Mozilla Firefox每年爽拿3.75億美金 11 天前
網站被駭留記錄 Firefox給你貼心小提醒 網站被駭留記錄 Firefox給你貼心小提醒 24 天前
Google再次成為Firefox新版瀏覽器默認搜索引擎 Google再次成為Firefox新版瀏覽器默認搜索引擎 1 個月前
新版Firefox預設搜尋引擎恢復與Google合作 新版Firefox預設搜尋引擎恢復與Google合作 1 個月前
新版Firefox瀏覽器正式導入量子引擎 新版Firefox瀏覽器正式導入量子引擎 1 個月前
Firefox Quantum釋出測試版 將比前版瀏覽效率提昇兩倍 Firefox Quantum釋出測試版 將比前版瀏覽效率提昇兩倍 2 個月前

熱門文章

最新消息