import java.io.FileOutputStream;import android.content.Context;import android.graphics.Bitmap;import android.graphics.Bitmap.Config;import android.graphics.Canvas;import android.graphics.Color;import android.graphics.Matrix;import android.graphics.Paint;import android.util.DisplayMetrics;import android.util.Log;import android.view.Display;import android.view.Surface;import android.view.SurfaceControl;import android.view.WindowManager;public class StackBlurManager {private static final String TAG = "StackBlurManager";private static final int DEFAULT_SCALE = 8;/** * Original set of pixels from the image */private int [] originalPixels;/** * Current set of pixels from the image (the one that will be exported */private int [] currentPixels;/** * Original width of the image */private int _width = -1;/** * Original height of the image */private int _height= -1;/** * Original image */private Bitmap _image;private boolean alpha = true;private Context mContext;public StackBlurManager(Context context){mContext = context;}private void init(Bitmap image) {_width=image.getWidth();_height=image.getHeight();_image = image;originalPixels= new int[_width*_height];_image.getPixels(originalPixels, 0, _width, 0, 0, _width, _height);}private void process(int radius) {if (radius < 1 )radius = 1;currentPixels = originalPixels.clone();int wm=_width-1;int hm=_height-1;int wh=_width*_height;int div=radius+radius+1;int r[]=new int[wh];int g[]=new int[wh];int b[]=new int[wh];int rsum,gsum,bsum,x,y,i,p,yp,yi,yw;int vmin[] = new int[Math.max(_width,_height)];int divsum=(div+1)>>1;divsum*=divsum;int dv[]=new int[256*divsum];for (i=0;i<256*divsum;i++){dv[i]=(i/divsum);}yw=yi=0;int[][] stack=new int[div][3];int stackpointer;int stackstart;int[] sir;int rbs;int r1=radius+1;int routsum,goutsum,boutsum;int rinsum,ginsum,binsum;for (y=0;y<_height;y++){rinsum=ginsum=binsum=routsum=goutsum=boutsum=rsum=gsum=bsum=0;for(i=-radius;i<=radius;i++){p=currentPixels[yi+Math.min(wm,Math.max(i,0))];sir=stack[i+radius];sir[0]=(p & 0xff0000)>>16;sir[1]=(p & 0x00ff00)>>8;sir[2]=(p & 0x0000ff);rbs=r1-Math.abs(i);rsum+=sir[0]*rbs;gsum+=sir[1]*rbs;bsum+=sir[2]*rbs;if (i>0){rinsum+=sir[0];ginsum+=sir[1];binsum+=sir[2];} else {routsum+=sir[0];goutsum+=sir[1];boutsum+=sir[2];}}stackpointer=radius;for (x=0;x<_width;x++){//if (!alpha)//alpha = (int)(Color.alpha(originalPixels[y*_height+x]))  != 255;r[yi]=dv[rsum];g[yi]=dv[gsum];b[yi]=dv[bsum];rsum-=routsum;gsum-=goutsum;bsum-=boutsum;stackstart=stackpointer-radius+div;sir=stack[stackstart%div];routsum-=sir[0];goutsum-=sir[1];boutsum-=sir[2];if(y==0){vmin[x]=Math.min(x+radius+1,wm);}p=currentPixels[yw+vmin[x]];sir[0]=(p & 0xff0000)>>16;sir[1]=(p & 0x00ff00)>>8;sir[2]=(p & 0x0000ff);rinsum+=sir[0];ginsum+=sir[1];binsum+=sir[2];rsum+=rinsum;gsum+=ginsum;bsum+=binsum;stackpointer=(stackpointer+1)%div;sir=stack[(stackpointer)%div];routsum+=sir[0];goutsum+=sir[1];boutsum+=sir[2];rinsum-=sir[0];ginsum-=sir[1];binsum-=sir[2];yi++;}yw+=_width;}for (x=0;x<_width;x++){rinsum=ginsum=binsum=routsum=goutsum=boutsum=rsum=gsum=bsum=0;yp=-radius*_width;for(i=-radius;i<=radius;i++){yi=Math.max(0,yp)+x;sir=stack[i+radius];sir[0]=r[yi];sir[1]=g[yi];sir[2]=b[yi];rbs=r1-Math.abs(i);rsum+=r[yi]*rbs;gsum+=g[yi]*rbs;bsum+=b[yi]*rbs;if (i>0){rinsum+=sir[0];ginsum+=sir[1];binsum+=sir[2];} else {routsum+=sir[0];goutsum+=sir[1];boutsum+=sir[2];}if(i<hm){yp+=_width;}}yi=x;stackpointer=radius;for (y=0;y<_height;y++){// Preserve alpha channel: ( 0xff000000 & pix[yi] )if ( alpha )currentPixels[yi] = (0xff000000 & currentPixels[yi]) | (dv[rsum] << 16) | (dv[gsum] << 8) | dv[bsum];elsecurrentPixels[yi]=0xff000000 | (dv[rsum]<<16) | (dv[gsum]<<8) | dv[bsum];rsum-=routsum;gsum-=goutsum;bsum-=boutsum;stackstart=stackpointer-radius+div;sir=stack[stackstart%div];routsum-=sir[0];goutsum-=sir[1];boutsum-=sir[2];if(x==0){vmin[y]=Math.min(y+r1,hm)*_width;}p=x+vmin[y];sir[0]=r[p];sir[1]=g[p];sir[2]=b[p];rinsum+=sir[0];ginsum+=sir[1];binsum+=sir[2];rsum+=rinsum;gsum+=ginsum;bsum+=binsum;stackpointer=(stackpointer+1)%div;sir=stack[stackpointer];routsum+=sir[0];goutsum+=sir[1];boutsum+=sir[2];rinsum-=sir[0];ginsum-=sir[1];binsum-=sir[2];yi+=_width;}}}/** * Returns the blurred image as a bitmap * @return blurred image */private Bitmap returnBlurredImage() {Bitmap newBmp = Bitmap.createBitmap(_image.getWidth(), _image.getHeight(), Config.ARGB_8888);Canvas c = new Canvas(newBmp); c.drawBitmap(_image, 0, 0, new Paint());newBmp.setPixels(currentPixels, 0, _width, 0, 0, _width, _height);return newBmp;}/** * Save the image into the file system * @param path The path where to save the image */private void saveIntoFile(String path) {Bitmap newBmp = Bitmap.createBitmap(_image.getWidth(), _image.getHeight(), Config.ARGB_8888);Canvas c = new Canvas(newBmp); c.drawBitmap(_image, 0, 0, new Paint());newBmp.setPixels(currentPixels, 0, _width, 0, 0, _width, _height);try {FileOutputStream out = new FileOutputStream(path);newBmp.compress(Bitmap.CompressFormat.PNG, 90, out);} catch (Exception e) {e.printStackTrace();}}/** * Returns the original image as a bitmap * @return the original bitmap image */private Bitmap getImage() {return this._image;}    private static Bitmap zoomBitmap(Bitmap bitmap, int w, int h) {        int width = bitmap.getWidth();        int height = bitmap.getHeight();        Matrix matrix = new Matrix();        float scaleWidht = ((float) w / width);        float scaleHeight = ((float) h / height);        matrix.postScale(scaleWidht, scaleHeight);        Bitmap newbmp = Bitmap.createBitmap(bitmap, 0, 0, width, height,                matrix, true);        return newbmp;    }//获取模糊图片  (注调用该函数后,需要在窗口销毁时调用 destroy()函数释放资源)  public Bitmap GetBlurredBitmap(int bgWidth, int bgHeight, int scale){    Bitmap bitmap;    Bitmap newBmp;    Matrix matrix = new Matrix();    int screenWidth;    int screenHeight;    int rotation;if(scale == -1){scale = DEFAULT_SCALE;}        if(_image != null){    _image.recycle();    _image = null;    }                //1、创建截屏图片    WindowManager windowManager = (WindowManager) mContext.getSystemService(Context.WINDOW_SERVICE);      Display display = windowManager.getDefaultDisplay();      DisplayMetrics displayMetrics = new DisplayMetrics();      display.getRealMetrics(displayMetrics);     screenWidth = displayMetrics.widthPixels;    screenHeight = displayMetrics.heightPixels;    rotation = display.getRotation();    Log.i(TAG, "screenWidth = "+screenWidth+" screenHeight = "+screenHeight);                  float[] dims = {screenWidth, screenHeight};          float degrees = getDegreesForRotation(rotation);          boolean requiresRotation = (degrees > 0);          if (requiresRotation) {              // Get the dimensions of the device in its native orientation          matrix.reset();          matrix.preRotate(-degrees);          matrix.mapPoints(dims);              dims[0] = Math.abs(dims[0]);              dims[1] = Math.abs(dims[1]);          }           bitmap = SurfaceControl.screenshot((int) dims[0], (int) dims[1]);          if (requiresRotation) {              // Rotate the screenshot to the current orientation              Bitmap tmpBitmap = Bitmap.createBitmap(screenWidth,  screenHeight, Bitmap.Config.ARGB_8888);              Canvas c = new Canvas(tmpBitmap);              c.translate(tmpBitmap.getWidth() / 2, tmpBitmap.getHeight() / 2);              c.rotate(degrees);              c.translate(-dims[0] / 2, -dims[1] / 2);              c.drawBitmap(bitmap, 0, 0, null);              c.setBitmap(null);                        bitmap.recycle();                        bitmap = tmpBitmap;          }        // If we couldn't take the screenshot, notify the user          if (bitmap == null) {                           return null;          }        // Optimizations          bitmap.setHasAlpha(false);          bitmap.prepareToDraw();            Log.i(TAG, "bitmap.width = "+bitmap.getWidth()+" bitmap.getHeight = "+bitmap.getHeight());    newBmp = bitmap;    /*if(bgHeight < screenHeight){            newBmp = Bitmap.createBitmap(bgWidth, bgHeight, Bitmap.Config.ARGB_8888);            newBmp.setDensity(DisplayMetrics.DENSITY_DEVICE);            Canvas canvas = new Canvas(newBmp);            canvas.setDensity(DisplayMetrics.DENSITY_DEVICE);            canvas.drawBitmap(bitmap, 0, screenHeight - bgHeight, null);            bitmap.recycle();            bitmap = null;    }*/                //2、zoom bmp        Bitmap zoomBmp = zoomBitmap(newBmp, newBmp.getWidth() / scale, newBmp.getHeight() / scale);        newBmp.recycle();        newBmp = null;            Log.i(TAG, "zoomBmp.width = "+zoomBmp.getWidth()+" zoomBmp.getHeight = "+zoomBmp.getHeight());                //3、初始化模糊参数        init(zoomBmp);                //4、模糊化        process(9);                Bitmap blurredBmp = returnBlurredImage();               Log.i(TAG, "blurredBmp.width = "+blurredBmp.getWidth()+" blurredBmp.getHeight = "+blurredBmp.getHeight());                newBmp =zoomBitmap(blurredBmp, bgWidth, bgHeight);       Log.i(TAG, "newBmp.width = "+newBmp.getWidth()+" newBmp.getHeight = "+newBmp.getHeight());        blurredBmp.recycle();        blurredBmp = null;                return newBmp;            }private float getDegreesForRotation(int value) {        switch (value) {          case Surface.ROTATION_90:              return 360f - 90f;          case Surface.ROTATION_180:              return 360f - 180f;          case Surface.ROTATION_270:              return 360f - 270f;          }          return 0f;      }public void destroy(){if(_image != null){_image.recycle();_image = null;}}}

模糊图片获取方法:
1、在窗口中导入类:import com.sios.view.StackBlurManager;
2、调用StackBlurManager(context)初始化该类,只需要初始化一次;
3、调用StackBlurManager类的成员函数GetBlurredBitmap获取模糊图片,函数中参数
bgWidth, bgHeight为获取图片的宽和高,scale为图片模糊化系数,使用系统默
认模糊画参数,
该值需要设置为-1;
4、当窗口退出时,调用destroy()函数释放资源;


使用参考代码:

StackBlurManager mStackBlurManager = new StackBlurManager(context);

Bitmap blurredBmp =
mStackBlurManager.GetBlurredBitmap(controlWidth, controlHeight, -1);
Bitmap newBmp = Bitmap.createBitmap(controlWidth, controlHeight,
Bitmap.Config.ARGB_8888);
newBmp.setDensity(DisplayMetrics.DENSITY_DEVICE);
Canvas canvas = new Canvas(newBmp);
canvas.setDensity(DisplayMetrics.DENSITY_DEVICE);
canvas.drawBitmap(blurredBmp, 0, 0, null);

blurredBmp.recycle();
blurredBmp = null;


更多相关文章

  1. Android 双击和手势的图片缩放
  2. android HttpClient 上传图片
  3. Android – 加载图片本缓存到内存与本地
  4. Android圆形图片--自定义控件
  5. Android APIDemo gif图片显示
  6. android 图片合成
  7. Android中Gallery来显示图片
  8. Android图片按比例缩放

随机推荐

  1. Android(安卓)中 EventBus 的使用
  2. android 关于屏幕的设置(FullScreen、noti
  3. Android样式和主题(一):简介
  4. Android中RxJava+Retrofit+MVP模式的整合
  5. android 娓告垙寮曟搸libgdx demo cuboc
  6. android集成支付宝sdk
  7. Android涓娇鐢ㄥ紑婧愭鏋禘ventBus3.
  8. android涔媓andler浣跨敤
  9. AsyncTask使用详解及源码分析
  10. Android(安卓)R新特性:针对Android(安卓)R