再谈javascript图片预加载技术
图片预加载技术的典型应用:
如lightbox方式展现照片,无疑需要提前获得大图的尺寸,这样才能居中定位,由于javascript无法获取img文件头数据,必须等待其加载完毕后才能获取真实的大小然后展示出来,所以lightbox显示的图片的速度体验要比直接输出的差很多,而本文说提到的预加载技术主要针对获取图片尺寸。
一段典型的使用预加载获取图片大小的例子:
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应用程序区别于桌面应用程序,响应速度才是最好的用户体验。如果想要速度与优雅兼得,那就必须提前获得图片尺寸,如何在图片没有加载完毕就能获取图片尺寸?
一、结合flash加载图片,获取图片头部数据的尺寸
flash虽然很强大,但它与生俱来的缺点让人爱恨交织,加上很多移动设备不支持falsh无疑更是致命的伤,还是放弃吧。
二、在服务端保存图片尺寸数据
这里不得不提到腾讯Qzone的lightbox相册,它就是这样做的。它能在图片没有加载完全的时候就居中放大图片,速度与优雅基本兼得。不过它仍然难以避免blog插入的外链图片的问题,也只能按传统的方式加载完毕才能展示。
三、javascript通过占位方式获取图片头部数据的尺寸
十多年的上网经验告诉我:浏览器在加载图片的时候你会看到图片会先占用一块地然后才慢慢加载完毕,并且这里大部分的图片都是没有预设width与height属性的,因为浏览器能够获取图片的头部数据。基于此,只需要使用javascript定时侦测图片的尺寸状态便可得知图片尺寸就绪的状态。
实现代码:
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); }; // 通过占位提前获取图片头部数据 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); }; };
好了,请观赏令人愉悦的 DEMO :http://www.planeart.cn/demo/imgReady/
(通过测试的浏览器:Chrome、Firefox、Safari、Opera、IE6、IE7、IE8)
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
· 基于Microsoft.Extensions.AI核心库实现RAG应用
· 10年+ .NET Coder 心语 ── 封装的思维:从隐藏、稳定开始理解其本质意义
· 地球OL攻略 —— 某应届生求职总结
· 提示词工程——AI应用必不可少的技术
· Open-Sora 2.0 重磅开源!
· 字符编码:从基础到乱码解决