本人已运用vue.js半年多了,在做一些Html5页面的时刻发明许多页面都是图片构成的,如果能有用的紧缩图片的体积那末悉数项目体积就会削减许多,这是为何写这个简朴东西的出发点。
Webp 百度百科上已讲清楚在坚持原画质的状况呀体积能够紧缩到本来的60%这是很牛逼的一件事。看看webp的兼容状况,下图是caniuse上面最新的webp支撑状况
兼容状况照样不那末乐观,不过chrome和安卓阵营已悉数支撑。所以我照样做了这件事。
源码github
Vue.js
的自定义指令系统异常壮大是我做这件事的根本原因之一,所以我的想象是在一个指令中传入图片链接,然后在页面衬着的时刻依据浏览器是不是支撑webp
花样的图片挑选下载谁人图片,这里就需要推断浏览器是不是支撑webp
了,这里我用到的是canvas
要领,代码以下
var canUseWebp = (function() {
var elem = document.createElement('canvas');
if (!!(elem.getContext && elem.getContext('2d'))) {
return elem.toDataURL('image/webp').indexOf('data:image/webp') === 0;
} else {
return false;
}
})();
这时刻就异常简朴了指令在update
的时刻依据是不是支撑然后挑选差别的图片
function update(el, option) {
var attr = option.arg || 'src';
if (el.tagName.toLowerCase() === 'img' && option.value) {
el.setAttribute(attr, option.value);
}
};
但是事变的这个时刻发明一些小的图标不见了,本来我的webpack
设置中设置了小于10k
的图片运用base64
编码,
所以终究我的更新代码是如许的
function update(el, option) {
var attr = option.arg || 'src';
if (el.tagName.toLowerCase() === 'img' && option.value) {
if (option.value.indexOf('data:image') < 0) {
var tmp = option.value.substring(0, option.value.lastIndexOf('.')) + '.webp';
el.setAttribute(attr, canUseWebp ? tmp : option.value);
} else {
el.setAttribute(attr, option.value);
}
}
};
这个时刻vue.js 2.0
宣布了。我有针对 2.0版本做了支撑,因为我的指令异常简朴,所以代码很轻松
var isVueNext = Vue.version.split('.')[0] === '2';
if (isVueNext) {
Vue.directive('webp', function(el, binding) {
update(el, {
arg: binding.arg,
value: binding.value
});
})
} else {
Vue.directive('webp', {
bind: function() {},
update: function(val, old) {
update(this.el, {
arg: this.arg,
value: val
});
},
unbind: function() {}
})
}
};
如许我的vue-webp
指令就算完成了。
只要指令可不行,每次都要本身天生一份webp
花样的图片,这太不友好了。我有查找一番,发明一个webp-loader
能够在webpack
打包和dev的时刻自动天生响应的webp
文件,太好了。运用原作者的webp-loader
发明文件的hash
不一样,我又用imagemin
最新版本晋级了一下,上传到npm
叫webpn-loader
(谅解我不会定名),
详细运用要领能够参考我的 Vue.js 2.0 背景项目 模板项目
感谢人人,看到这里。迎接种种star