我在做SharePoster的時候遇到一個問題,我想讓使用者可以使用不同的字型在canvas上面寫字,但是中文字型檔太大,直接載入瀏覽器會太久,所以如何動態提供字型給canvas作圖使用呢?
問題可以分成幾個部分:
1. 動態切割字型檔
一個完整中文字型檔大概要5~20mb,假如我們只使用幾個中文字就要下載全部檔案很不划算,所以如果可以讓server提供一個根據需要的文字來提供瘦身過的字型檔,這個字型檔可能只有幾kb,是原來千分之一的大小,專門用來顯示特定的文字所需要的字型。
實際上已經有一些open source project提供這樣的切割能力,像是FontForge (Python), Sfntly (Java)。
2. 根據所需要的文字要求字型檔
一般比較正常的作法是這樣,第一次送post給server告訴server準備哪些字,換取一個hash token,如果這裡是使用jQuery cross-domain post,發post之前會先發一個options詢問server是否允許哪些method的cross-domain request,確認許可之後才會發post,client根據這個token組成一個url交給css的font-face,server端必須藉由Access-Control-Allow-Origin和Access-Control-Allow-Method兩個header來回應cross-domain的請求。
這裡需要一些改進,我原本以為字型可以像圖片一樣使用javascript拿到字型的object,或許html5要可以,事實上是無法的,規則的制定者看來沒有這樣的需求,我們只能夠組成url交給css去處理,其實這樣造成了request的浪費,比較好的狀態應該一次request就能夠拿到字型,所以在實作上我加了另一種方法,當需求文字少的時候,在client端組成font url就直接較給css處理,這樣就少了options和post這兩個request,只剩下css會發出的get request,但是換來的限制是url長度大概要在2000以下比較安全(不管舊版IE的話至少也要在4000以下)也就是encode 之前大概200個中文字比較保險。
然後我們用一個jQuery plugin把這些方法包起來。
3. 使用字型
還有一個問題,什麼時候可以使用字型了?
字型載入需要時間,而且我們沒有任何獲得css font request的callback或類似onload事件的方法,如果在字型載入之前使用該字型,我們只會得到瀏覽器備用的字型(fallback font),不過或許我們可以利用這個機制來測試字型是否載入了,無法拿到event就polling吧,當字型載入的時候文字寬度和fallback字型的寬度會不同,就用這樣來測試字型是否載入了。
這個方法也把它包在jQuery plugin裡面。
綜合以上這是一個我目前正在開發的開源項目fonten,他同時包含一個可上傳字型的server和一組API以及一個比較方便的jQuery plugin。
fonten on Github
2013年4月12日
2012年10月19日
增加網頁讀取速度
這篇主要討論靜態檔案下載,首先先裝Google PageSpeed ,有chrome版和firefox版,而且有貼心的正體中文,也可以用一些測速網站工具像是http://tools.pingdom.com/fpt/來當做評量參考,真的只要參考就好,拿個90分就可以了
另外檔案合併有一個明顯的壞處,當修改部分檔案的時候,使用者必須重新下載整份檔案,喪失快取的好處,所以什麼時候要合併哪些檔案還是要自己思考一下
compress javascript首推uglify-js,自己寫個bash來做combine,也有一些線上工具可以使用http://jscompress.com/
簡單說增加網頁讀取速度不外乎平行下載、壓縮、快取和把檔案放近一點
先挑一個dynamic js loader來做平行下載
超多的,百家爭鳴,但是每個套件製作的背景目的不同,也適用不同場合,大部分套件都可以幫忙做到parallel loading, conditional executing,有些還會動態幫忙讀取css,任君挑選,不會選就先用$LAB爽一下,有在用RequireJS的當然繼續用,需要fall back機制可以用YepNope
這裡我有一個問題,傳統上認為靜態檔案合併比較好,因為節省訪問和處理時間,但是當平行下載是可行的(瀏覽器現在根本都原生支援平行下載),在給定延遲時間和反應時間下,應該會有一個檔案大小的臨界點,超過這個臨界點之後整體下載速度就會輸給平行下載了吧?所以這個臨界點是我們需要關心的嗎?
另外檔案合併有一個明顯的壞處,當修改部分檔案的時候,使用者必須重新下載整份檔案,喪失快取的好處,所以什麼時候要合併哪些檔案還是要自己思考一下
『壓縮』的部份主要是compress和gzip
compress css 大家應該都用scss/sass, compass或是less了,當然也可以用線上工具像是
http://www.csscompressor.com/
http://www.csscompressor.com/
compress javascript首推uglify-js,自己寫個bash來做combine,也有一些線上工具可以使用http://jscompress.com/
gzip和cache就交給nginx來設定。設定cache的時候有個兩難,一般來說會設定有query_string的request做cache,不然萬一檔案需要修改,又清除不了瀏覽器cache,可能要改路徑或檔名了,但是另一方面有些proxy對於有query_string的請求不會做cache,所以也是要思考一下
『檔案放近一點』原來說的是用類似Google CDN的服務,只有非常有名的套件像是jQuery之輩有救援到。自從Amazon S3+CloudFront出現後,一般平民也可以是可以享用高級全球化部屬,其中js和css等當然也可以壓縮後放在S3上面,但是有個小問題就是S3到目前還不會做gzip,摳憐喔,解決方法就是直接先gzip -9之後再丟上去,順便改一下Accept-Encoding就行了,但是衍生的問題是有些使用者還在用民國初年不會解壓縮的瀏覽器,這部分就是需要偉大的開發者使用愛心判斷式+fall back strategy來救使用者於水火了。
以上方法僅供參考,沒事不需要做網頁讀取加速,一方面網站會慢通常不是靜態檔案在慢,而且沒用的網站也不會因為加速2秒後就突然變得有用了。
標籤:
網頁加速,
CloudFront,
compass,
CSS,
Javascript,
jQuery,
Nginx,
S3,
sass,
YepNope
訂閱:
文章 (Atom)