|
看到有些同学需要滤镜功能,而官方的滤镜功能暂时又是那么强大,我就给大家分享一个纯js实现的滤镜功能基于canvas开发的滤镜功能,其实原理也很简单,不多说,上代码
// module: 滤镜模块
var offscreenCanvas=document.createElement('canvas'),
context=offscreenCanvas.getContext('2d');
var image=new Image(),imageData,imageDataDefault,userPhoto=$('#userPhoto')[0];
// image.crossOrigin="anonymous";
image.src=photoData.fsDir;
image.onload=function(){
offscreenCanvas.width=image.width;
offscreenCanvas.height=image.height;
context.drawImage(image,0,0,image.width,image.height,0,0,offscreenCanvas.width,offscreenCanvas.height);
imageData=context.getImageData(0,0,offscreenCanvas.width,offscreenCanvas.height);
setImage();
// selectFilter(5);
};
首先,因为滤镜的处理过程是用户不需要感知的,所以创建一个离屏的canvas,以优化性能
然后,读取一张原图,这里可以做一些你想做的操作,显示图片呀,等等的,如下
function setImage(){
if(image.width>image.height) $('head').append('<style>.b-tiezi__photo>img{ width: '+window.innerWidth+'px;}</style>');
else if(image.width<image.height) $('head').append('<style>.b-tiezi__photo>img{ height: '+window.innerWidth+'px;}</style>');
else $('head').append('<style>.b-tiezi__photo>img{ width: '+window.innerWidth+'px; height: '+window.innerWidth+'px;}</style>');
userPhoto.src=photoData.base64;
// alert(photoData.fsDir)
}
接着,用户选择了某种滤镜的效果
// 选择滤镜效果
// type = 1:负片 2:黑白 3:浮雕 4:马赛克 5:怀旧
function selectFilter(type){
$('#loading').show();
// imageData=imageDataDefault;
setTimeout(function(){
context.drawImage(image,0,0,image.width,image.height,0,0,offscreenCanvas.width,offscreenCanvas.height);
imageData=context.getImageData(0,0,offscreenCanvas.width,offscreenCanvas.height);
switch(type){
case 0: filterNone();break;
case 1: filterFupian();break;
case 2: filterHeibai();break;
case 3: filterFudiao();break;
case 4: filterMasaike();break;
case 5: filterHuaijiu();break;
}
context.putImageData(imageData,0,0);
userPhoto.src=offscreenCanvas.toDataURL(); //这里是把滤镜处理后的图像转化为base64,可用于上传和展示
},100);
}
这里获取到原图的对象,绘制到离屏的canvas里面,转化为imageData,然后进行data的处理
下面我实现了5种常见的滤镜,自己也可以扩展想要的滤镜效果
// 负片滤镜
function filterFupian(){
var data=imageData.data;
for(var i=0;i<data.length-4;i+=4){
data[i]=255-data[i];
data[i+1]=255-data[i+1];
data[i+2]=255-data[i+2];
}
}
// 黑白滤镜
function filterHeibai(){
var data=imageData.data;
var average;
for(var i=0;i<data.length-4;i+=4){
average=( data[i] + data[i+1] + data[i+2] ) / 3;
data[i]=average;
data[i+1]=average;
data[i+2]=average;
}
}
// 浮雕滤镜
function filterFudiao(){
var data=imageData.data,
width=imageData.width,
length=data.length;
for(var i=0;i<length;i++){
if(i<=length-width*4){
if( (i+1)%4 !==0 ){
if( (i+4)%(width*4) ==0 ){
data[i]=data[i-4];
data[i+1]=data[i-3];
data[i+2]=data[i-2];
data[i+3]=data[i-1];
i+=4;
}else{
data[i]=255/2+2*data[i]-data[i+4]-data[i+width*4];
}
}
}else{
if( (i+1)%4!==0 ) data[i]=data[i-width*4];
}
}
}
// 马赛克滤镜
function filterMasaike(){
var data=imageData.data;
var mosaic={x:10,y:10};
for(var i=0;i<image.height;i+=mosaic.y){
for(var j=0;j<image.width;j+=mosaic.x){
var num=Math.random();
var randomPixel={
x:Math.floor(num*mosaic.x+i),
y:Math.floor(num*mosaic.y+j)
};
for(var k=j;k<j+mosaic.x;k++){
for(var l=i;l<i+mosaic.y;l++){
data[(l*image.width+k)*4]=data[(randomPixel.x*image.width+randomPixel.y)*4];
data[(l*image.width+k)*4+1]=data[(randomPixel.x*image.width+randomPixel.y)*4+1];
data[(l*image.width+k)*4+2]=data[(randomPixel.x*image.width+randomPixel.y)*4+2];
data[(l*image.width+k)*4+3]=data[(randomPixel.x*image.width+randomPixel.y)*4+3];
}
}
}
}
}
// 怀旧滤镜
function filterHuaijiu(){
var data=imageData.data;
for(var i=0;i<data.length-4;i+=4){
data[i]=data[i]*0.393 + data[i+1]*0.769 + data[i+2]*0.189;
data[i+1]=data[i]*0.349 + data[i+1]*0.686 + data[i+2]*0.168;
data[i+2]=data[i]*0.272 + data[i+1]*0.534 + data[i+2]*0.131;
}
}
分享就到这里了,要认真看代码哦,加油
|
评分
-
3
查看全部评分
-
|