StackBlur 是一个快速高斯模糊算法,原作者是由 Mario Klingemann 开发的 Javascript 版本。Victor Laskin 实现了一个 C++多线程版本,Android 上我们基于 Victor Laskin
的版本进行 JNI 移植。 这个算法应用非常广泛 iOS 上 Camera+ 也是用的这套算法,还有 CUDA 版本等…
移植 这里我们可以直接借用 android-stackblur 的代码,注意这个版本并不支持带透明度的图片,且不要使用多线程来处理图片。
CMakeLists Android Studio
2.2 以上的版本支持使用 CMake 来编译 JNI 了,具体操作可以参考官方文档
https://developer.android.com/studio/projects/add-native-code.html
流程没什么难点,官网上有的就不再赘述,对于没有接触过CMake
的人来说,编写 CMakeLists 文件是很懵逼的事情,想要完整学完 CMake,学习曲线还是蛮陡峭的,下面就是移植后的 CMakeLists 文件。以后自己编写其他的 CMakeLists 参照例子依葫芦画瓢即可。
CMakeLists.txt 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 cmake_minimum_required (VERSION 3.4 .1 )add_library ( StackBlur SHARED src/main/cpp/StackBlur.c ) find_library ( log-lib log ) find_library ( m-lib m ) find_library ( jnigraphics-lib jnigraphics ) target_link_libraries ( StackBlur ${log-lib} ${m-lib} ${jnigraphics-lib} )
集成 glide glide 是一个优秀的图片加载库,具有强大的可扩展性,对于图片的处理 Gilde 使用 Transformation 进行图片的转换功能,我们就只需要实现一个模糊功能的 Transformation 即可。
GlideStackBlur.java 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 public class GlideStackBlur extends BitmapTransformation { private TintColorGenerator mTintColorGenerator; public GlideStackBlur (Context context) { super (context); } public GlideStackBlur (Context context, TintColorGenerator tintColorGenerator) { super (context); mTintColorGenerator = tintColorGenerator; } @Override protected Bitmap transform (BitmapPool pool, Bitmap toTransform, int outWidth, int outHeight) { if (toTransform != null ) { long startTime = System.currentTimeMillis(); BlurUtils blurManager = new BlurUtils (toTransform); Bitmap blur = blurManager.process(40 ); final Bitmap result = Bitmap.createBitmap(blur.getWidth(), blur.getHeight(), Bitmap.Config.ARGB_8888); Canvas canvas = new Canvas (result); Paint paint = new Paint (); paint.setAntiAlias(true ); paint.setFilterBitmap(true ); canvas.drawBitmap(blur, 0 , 0 , paint); blurManager.recycle(); if (BuildConfig.DEBUG) { Log.d("GlideStackBlur" , outWidth + "," + outHeight + " Time: " + (System.currentTimeMillis() - startTime)); } return result; } return null ; } @Override public String getId () { String id = "cn.gavinliu.android.lib.glide.stackblur.GlideStackBlur" ; if (mTintColorGenerator != null ) { id += mTintColorGenerator.getId(); } return id; } }
1 2 3 Glide.with(this ).load(url) .transform(new GlideStackBlur (this )) .into(imageView);
扩展染色功能 使用 ColorFilter 功能可以在图片上在叠加一个颜色。
1 2 3 4 5 6 7 ... if (mTintColorGenerator != null ) { int color = mTintColorGenerator.generate(toTransform); PorterDuffColorFilter colorFilter = new PorterDuffColorFilter ((color), PorterDuff.Mode.SRC_OVER); paint.setColorFilter(colorFilter); } ...
1 2 3 4 5 6 7 8 9 10 11 12 13 14 Glide.with(this ).load(url) .transform(new GlideStackBlur (this , new TintColorGenerator () { @Override public int generate (Bitmap bitmap) { return 0x803F51B5 ; } @Override public String getId () { return ".TintColorGenerator" ; } })) .into(imageView);
源码 https://github.com/gavinliu/glide-stackblur