HTML5 網路工作者LOGIN

HTML5 網路工作者

Web Workers

在html5規格中引入了web workers概念,解決客戶端JavaScript無法多執行緒的問題,其定義的worker是指程式碼的平行線程,不過web worker處於一個自包含的環境中,無法存取主線程的window對象和document對象,和主線程通訊只能透過非同步訊息傳遞機制

我們需要把希望單獨執行的javascript程式碼放到一個單獨的js檔案中,然後在頁面中呼叫Worker建構函式來建立一個線程,參數是該檔案路徑,參數存放如果是相對位址,那麼要以包含呼叫Worker建構函式語句所在腳本為參照,如果是絕對路徑,需要保證同源(協定+主機+連接埠)。這個檔案不需要我們在頁面使用script標籤顯示引用

var worker=new Worker('js/worker.js');

##簡單的小例子

在一個頁面顯示0~10000內所有可以被n整除的數,當然我們不用i*n這種,要略微使計算顯得複雜一些嘛

index.html

<!DOCTYPE html>
<html>
<head>
    <title>Web Workers</title>
</head>
<body>
  <h1>Web Workers</h1>
      <div id="test" style="width:500px;"></div>
    <script type="text/javascript">
        var worker=new Worker('js/worker.js');
        worker.postMessage({
            n:69
        });
        worker.onmessage=function(e){
            var test=document.getElementById('test').innerHTML=e.data;        
        };
    </script>
</body>
</html>

/js/worker.js

function calc(n){
    var result=[];
    for(var i=1;i<10000;i++){
        var tem=i;
        if(i%n==0){
            if(i%(10*n)==0){
                tem+='<br/>';
            }
            result.push(tem);
        }
    }

    self.postMessage(result.join(' '));
    self.close();
}

onmessage=function(e){
    calc(e.data.n);
};

顯示效果:

1018.png

建立web worker 檔案

現在,讓我們在一個外部JavaScript 中建立我們的web worker。

在這裡,我們建立了計數腳本。此腳本儲存於"demo_workers.js" 檔案:

var i=0;
function timedCount()
{
    i=i+1;
    postMessage(i);
    setTimeout("timedCount()",500);
}

timedCount();

以上程式碼中重要的部分程式碼中重要的部分碼中重要的部分中重要部分是postMessage() 方法- 它用於向HTML 頁面傳回一段訊息。

注意: web worker 通常不用於如此簡單的腳本,而是用於更耗費 CPU 資源的任務。

建立 Web Worker 物件

我們已經有了 web worker 文件,現在我們需要從 HTML 頁面呼叫它。

下面的程式碼偵測是否存在worker,如果不存在,- 它會建立一個新的web worker 對象,然後執行"demo_workers.js" 中的程式碼:

##i

f(typeof (w)=="undefined"){
    w=new Worker("demo_workers.js");
}

然後我們就可以從web worker 發生和接收訊息了。

向web worker 新增一個"onmessage" 事件監聽器:

w.onmessage=function(event){    document.getElementById("result").innerHTML= event.data;
};

<p當web="" worker="" 傳遞訊息時,就會執行事件監聽器中的程式碼。 event.data="" 中存有來自="" event.data="" 的資料。

終止Web Worker

當我們建立web worker 物件後,它會繼續監聽訊息(即使在外部腳本完成之後)直到其被終止為止。

如需終止web worker,並釋放瀏覽器/電腦資源,請使用terminate() 方法:

w.terminate();




#下一節

<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>Insert title here</title> </head> <body> <!-- web worker是运行在后台的javascript,不会影响页面的性能 --> <p>计数:<output id="result"></output></p> <button onclick="startWorker()">开始worker</button> <button onclick="endWorker()">停止worker</button> <br><br> <script type="text/javascript"> var w; function startWorker(){ if(typeof(Worker)!="undefined"){//浏览器支持web worker if(typeof(w)=="undefined"){//w是未定义的,还没有开始计数 w = new Worker("webworker.js");//创建一个Worker对象,利用Worker的构造函数 } //onmessage是Worker对象的properties w.onmessage = function(event){//事件处理函数,用来处理后端的web worker传递过来的消息 document.getElementById("result").innerHTML=event.data; }; }else{ document.getElementById("result").innerHTML="sorry,your browser does not support web workers"; } } function endWorker(){ w.terminate();//利用Worker对象的terminated方法,终止 w=undefined; } </script> <p>在后台运行的web worker js文件,webworker.js 才能实现效果<br> var i = 0; <br> function timeCount(){ <br> i = i + 1; <br> postMessage(i);//postMessage是Worker对象的方法,用于向html页面回传一段消息 <br> setTimeout("timeCount()",500);//定时任务 <br> } <br> timeCount();//加1计数,每500毫秒调用一次</p> </body> </html>
章節課件