2011年11月8日 星期二

用了JavaScript framework就不會有跨瀏覽器的問題?!

即使我們有了『甘道夫』講了很多JavaScript的東西,yahoo UI團隊和許多JavaScript高手也寫了很多JavaScript的書來讓我們正確的認識這個有趣的語言。但是很多人都認為只要用了JavaScript Framework如jQuery, YUI, MooTools...就可以解決跨瀏覽器和要花時間瞭解JavaScript避免寫出有問題或效能不佳的程式碼。真的是如此嗎?
且不論JavaScript只有global, function scope變數這個議題。在工作當中可以發現,很多人都認為JavaScript的變數是不需要宣告的。但其實不是如此,只是當function scope找不到變數的時候,JavaScript engine會找到global scope,在瀏覽器執行環境global context通常就是window物件。反之,如果在function裡的變數沒有宣告的話,也會跑到global context去。(題外話,object resovle也帶來先把重復使用的object先cache到function scope裡的寫法,比如說native array的一些function object在JavaScript framework可以看到都會做cache)回到主題,大家都知道不同瀏覽器Browser Object Model (BOM)有一些許的差別,所以很多人都鄉愿的認為讓寫framework的搞定就好。但是即使用framework,寫程式的人如果不瞭解JavaScript也一樣會發生,跑起來IE不行,其他都行的類似事情。
來看個活生生的例子,因為SEO很多設計人員都會加上meta element,很容易看到類似下面的東西
<meta name="title" content="this is title@meta element" />
然後,用jQuery(其實這個例子用任何一個JavaScript framework這樣寫都會出事)寫一個簡單的程式如下
$( function() {
   $( '#titleContent' ).text( '>>' + title );
} );
有沒有注意到,沒有宣告title,會發生啥事?JavaScript error?在chrome, firefox會看到JavaScript Error,但是IE呢?

看到了吧,因為我沒有IE,所以是用公司配的PC上的IE9測試。如果扯到variable hoisting就更複雜(已經寫過就不想再寫以前的筆記)。這個例子是trace實際程式碼簡化呈現問題點的寫法,其實真實的程式碼是沒宣告title,然後就針對title設定值和做其他處理,因此在chrome/firefox變成操作window裡的title attribute,不會看到JavaScript Error;但是在IE卻變成嘗試對HTMLMetaElement作改變,所以產生錯誤導致後續的JavaScript程式碼都無法正確執行。