圖片預(yù)加載技術(shù)的典型應(yīng)用:
如lightbox方式展現(xiàn)照片,無疑需要提前獲得大圖的尺寸,這樣才能居中定位,由于javascript無法獲取img文件頭數(shù)據(jù),必須等待其加載完畢后才能獲取真實的大小然后展示出來,所以lightbox顯示的圖片的速度體驗要比直接輸出的差很多,而本文說提到的預(yù)加載技術(shù)主要針對獲取圖片尺寸。
一段典型的使用預(yù)加載獲取圖片大小的例子:
var imgLoad = function (url, callback) { var img = new Image(); img.src = url; if (img.complete) { callback(img.width, img.height); } else { img.onload = function () { callback(img.width, img.height); img.onload = null; }; }; };
web應(yīng)用程序區(qū)別于桌面應(yīng)用程序,響應(yīng)速度才是最好的用戶體驗。如果想要速度與優(yōu)雅兼得,那就必須提前獲得圖片尺寸,如何在圖片沒有加載完畢就能獲取圖片尺寸?
一、結(jié)合flash加載圖片,獲取圖片頭部數(shù)據(jù)的尺寸
flash雖然很強(qiáng)大,但它與生俱來的缺點讓人愛恨交織,加上很多移動設(shè)備不支持falsh無疑更是致命的傷,還是放棄吧。
二、在服務(wù)端保存圖片尺寸數(shù)據(jù)
這里不得不提到騰訊Qzone的lightbox相冊,它就是這樣做的。它能在圖片沒有加載完全的時候就居中放大圖片,速度與優(yōu)雅基本兼得。不過它仍然難以避免blog插入的外鏈圖片的問題,也只能按傳統(tǒng)的方式加載完畢才能展示。
三、javascript通過占位方式獲取圖片頭部數(shù)據(jù)的尺寸
十多年的上網(wǎng)經(jīng)驗告訴我:瀏覽器在加載圖片的時候你會看到圖片會先占用一塊地然后才慢慢加載完畢,并且這里大部分的圖片都是沒有預(yù)設(shè)width與height屬性的,因為瀏覽器能夠獲取圖片的頭部數(shù)據(jù);诖耍恍枰褂胘avascript定時偵測圖片的尺寸狀態(tài)便可得知圖片尺寸就緒的狀態(tài)。
實現(xiàn)代碼:
var imgReady = function (url, callback, error) { var width, height, intervalId, check, div, img = new Image(), body = document.body; img.src = url; // 從緩存中讀取 if (img.complete) { return callback(img.width, img.height); }; // 通過占位提前獲取圖片頭部數(shù)據(jù) if (body) { div = document.createElement('div'); div.style.cssText = 'visibility:hidden;position:absolute;left:0;top:0;width:1px; height:1px;overflow:hidden'; div.appendChild(img) body.appendChild(div); width = img.offsetWidth; height = img.offsetHeight; check = function () { if (img.offsetWidth !== width || img.offsetHeight !== height) { clearInterval(intervalId); callback(img.offsetWidth, img.clientHeight); img.onload = null; div.innerHTML = ''; div.parentNode.removeChild(div); }; }; intervalId = setInterval(check, 150); }; // 加載完畢后方式獲取 img.onload = function () { callback(img.width, img.height); img.onload = img.onerror = null; clearInterval(intervalId); body && img.parentNode.removeChild(img); }; // 圖片加載錯誤 img.onerror = function () { error && error(); clearInterval(intervalId); body && img.parentNode.removeChild(img); }; };
運(yùn)行代碼框
[Ctrl+A 全部選擇 提示:你可先修改部分代碼,再按運(yùn)行]
好了,請觀賞令人愉悅的 DEMO : http://www.planeart.cn/demo/imgReady/
(通過測試的瀏覽器:Chrome、Firefox、Safari、Opera、IE6、IE7、IE8)
經(jīng)典論壇交流: http://bbs.blueidea.com/thread-3014603-1-1.html
本文鏈接:http://m.95time.cn/tech/web/2011/8335.asp
出處:藍(lán)色理想
責(zé)任編輯:bluehearts
◎進(jìn)入論壇網(wǎng)頁制作、WEB標(biāo)準(zhǔn)化版塊參加討論,我還想發(fā)表評論。
|