silverlight線程與基于事件驅(qū)動javascript引擎(實現(xiàn)軌跡回放功能)
案例背景:
整個功能其實就是從數(shù)據(jù)庫取出數(shù)據(jù),然后在界面上播放,簡單地說就是類似網(wǎng)上在線看視頻,聽音樂,只不過我取的是字符串數(shù)據(jù),而他們?nèi)〉氖橇魑募?shù)據(jù)。把整體數(shù)據(jù)分成十份,十個線程同時向數(shù)據(jù)庫取數(shù)據(jù)(并發(fā)提高速度)放在十個隊列中,另外一個線程從隊列中取數(shù)據(jù)拿出來到界面上播放,可以拖動播放進度,停止,暫停,重新播放,控制播放速度。恩,功能聽起來似乎很簡單,做起來也不是很難。但是后面發(fā)現(xiàn)的一些問題,以及順著這些問題往下挖掘,挖掘了一些我認為值得記住的東西。
關(guān)鍵東西:
1. siliverlight 后臺線程 BackgroundWorker m_GetReplayData= new BackgroundWorker();
2. 跨線程訪問界面控件 ,this.Dispatcher.BeginInvoke( /訪問界面UI);
3. javascript 式的函數(shù)指針: var ShowSIngleLog = function(){} ;(在父頁面上)
4 .子頁面注冊父頁面的事件: var fatharWindow = window.opener; ;
fatharWindow .ShowSIngleLog =function(){//播放數(shù)據(jù) showTrace()};
5.javascript引擎線程,界面渲染線程,瀏覽器事件觸發(fā)線程;
6.瀏覽器引擎是單線程,也就是所有東西都是同步的,不存在兩個線程同時跑
問題所在:
通過silverlight線程的循環(huán)來調(diào)用JS方法達到播放界面數(shù)據(jù)的效果,因為silverlight只能調(diào)用本頁面的JS方法,可是軌跡回放的頁面是主頁面彈出的一個子頁面,于是我利用主頁面的一個空的函數(shù)指針,子頁面注冊父頁面的事件來達到Silverlight調(diào)用子頁面方法目(上面提到的第3點)。經(jīng)過我仔細的推敲和論證我確定沒問題,做完后的也沒什么問題。本地測試的都是用上百條,上千條數(shù)據(jù),問題不大,停止,暫停,拖動進度,問題都不大,就是父頁面界面有點卡,一開始我并沒有重視這個問題。到了測試那邊是2萬多條數(shù)據(jù)播放,播放5分鐘后主界面卡死了,軌跡回放頁面上的,停止,拖動進度,暫停,播放按鈕全部失效了?,F(xiàn)象非常地詭異,我一度認為是測試的機器問題,最后發(fā)現(xiàn)是大數(shù)據(jù)量的問題。this.Dispatcher.BeginInvoke( /訪問界面UI)這個調(diào)用看似很簡單,很普通,但是有兩 個特點:
1.它是異步的,也就是調(diào)一下不一定馬上執(zhí)行,先調(diào)不一定先執(zhí)行,需要做同步控制;
2.這個方法要搶占瀏覽器界面渲染線程,而該線程與javascript引擎線程是互斥的.
2萬多數(shù)據(jù),一開始我控制了播放速度,所以剛開始沒什么問題,到后面很多數(shù)據(jù)都卡在這個方法上,導致不斷地搶占瀏覽器界面渲染線程,導致主頁面非??ǎ钡娇ㄋ罏橹?。點擊主頁面,瀏覽器事件觸發(fā)線程要運行,但是這個時候界面渲染線程在跑,所以非??ā?br />解決方案:
this.Dispatcher.BeginInvoke( /訪問界面UI),很明是這個東西造成,那就找替代方法。原來數(shù)據(jù)隊列是放在silverlight上,我改成放在javascript 隊列上。播放數(shù)據(jù)不依賴銀光線程,利用setimeout (該方法在IE6下會內(nèi)存泄露,所以一開始被我排斥)來定時播放數(shù)據(jù)。結(jié)果很漂亮,頁面很順暢,沒有了異步的問題,不用去控制讓數(shù)據(jù)同步播放,也比較簡單。
分析原因:
為什么用silerlight來播放會很卡,但是setimeout來播不會卡,兩個都是連續(xù)播放的,而且setimeout在播放的時候,點擊頁面,頁面也能響應事件,這個問題我們要從事件驅(qū)動javascript引擎。頁面卡的原因上面已經(jīng)說了,主要是想解釋一下setimeout播放為什么不卡。瀏覽器中的JavaScript引擎是基于事件驅(qū)動的,這里的事件可看作是瀏覽器派給它的各種任務(wù),這些任務(wù)可以源自 JavaScript引擎當前執(zhí)行的代碼塊,如調(diào)用setTimeout添加一個任務(wù),也可來自瀏覽器內(nèi)核的其它線程,如界面元素鼠標點擊事件,定時觸發(fā)器時間到達通知,異步請求狀態(tài)變更通知等.從代碼角度看來任務(wù)實體就是各種回調(diào)函數(shù),JavaScript引擎一直等待著任務(wù)隊列中任務(wù)的到來.由于單線程關(guān)系,這些任務(wù)得進行排隊,一個接著一個被引擎處理。所以在播放數(shù)據(jù)的時候,操作界面的是會被加到任務(wù)隊列中,會得到執(zhí)行,自然用戶角度感受到整個頁面也不卡了。
相關(guān)文章
CSS+JS實現(xiàn)點擊文字彈出定時自動關(guān)閉DIV層菜單的方法
這篇文章主要介紹了CSS+JS實現(xiàn)點擊文字彈出定時自動關(guān)閉DIV層菜單的方法,設(shè)計javascript操作菜單的彈出與關(guān)閉的相關(guān)技巧,具有一定參考借鑒價值,需要的朋友可以參考下2015-05-05ES6中Set和Map數(shù)據(jù)結(jié)構(gòu)的簡單講解
大家心里是否產(chǎn)生過這樣的疑問,JS中既然已經(jīng)有對象這種數(shù)據(jù)結(jié)構(gòu),我們?yōu)槭裁催€要再單獨去使用Set或者Map呢?下面這篇文章主要給大家介紹了關(guān)于ES6中Set和Map數(shù)據(jù)結(jié)構(gòu)的相關(guān)資料,需要的朋友可以參考下2022-08-08xmlplus組件設(shè)計系列之分隔框(DividedBox)(8)
xmlplus 是一個JavaScript框架,用于快速開發(fā)前后端項目。這篇文章主要介紹了xmlplus布局類組件之分隔框,具有一定的參考價值,感興趣的小伙伴們可以參考一下2017-05-05Typescript tipe freshness 更嚴格對象字面量檢查
這篇文章主要為大家介紹了Typescript tipe freshness 更嚴格對象字面量檢查,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪2022-10-10詳解用Webpack與Babel配置ES6開發(fā)環(huán)境
這篇文章主要介紹了詳解用Webpack與Babel配置ES6開發(fā)環(huán)境,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧2019-03-03