Android高斯模糊的应用场景

1,479 阅读1分钟

最近有高斯模糊方面的需求,记录一下应用的场景。

defaultConfig {
    applicationId "com.example.testapplication"
    minSdkVersion 21
    targetSdkVersion 31
    versionCode 1
    versionName "1.0.0.1.30"
    //      以下是高斯模糊相关的API
**    renderscriptTargetApi 31
    renderscriptSupportModeEnabled true**
    testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
}
//高斯模糊
implementation 'com.eightbitlab:supportrenderscriptblur:1.0.0'
implementation 'com.eightbitlab:blurview:1.3.3'

使用高斯模糊的layout

<eightbitlab.com.blurview.BlurView
    android:id="@+id/blurView"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_centerInParent="true"
    android:layout_marginLeft="20dp"
    android:layout_marginRight="20dp"
    >
private fun blur() {
    val radius = 20f
    val decorView: View = this.window.decorView
    val rootView = decorView.findViewById<ViewGroup>(android.R.id.content)
    val windowBackground: Drawable = decorView.background
    blurView.setupWith(rootView)
        .windowBackground(windowBackground)
        .blurAlgorithm(SupportRenderScriptBlur(this))
        .blurRadius(radius)
}

ImageView控件设置高斯模糊的背景

private fun blur2(bitmap: Bitmap,radius: Float) : Bitmap{
    val output = Bitmap.createBitmap(bitmap)
    val rs = androidx.renderscript.RenderScript.create(context)// 构建一个RenderScript渲染对象
    val gaussianBlue = androidx.renderscript.ScriptIntrinsicBlur.create(rs, Element.U8_4(rs))// 创建高斯模糊脚本
    val allIn = androidx.renderscript.Allocation.createFromBitmap(rs,bitmap)// 开辟输入内存
    val allOut = androidx.renderscript.Allocation.createFromBitmap(rs,output)// 开辟输出内存
    gaussianBlue.setRadius(radius)
    gaussianBlue.setInput(allIn)
    gaussianBlue.forEach(allOut)
    allOut.copyTo(output)

    rs.destroy()// 关闭RenderScript对象,API>=23则使用rs.releaseAllContexts()
    return output
}
val res = BitmapFactory.decodeResource(resources, R.drawable.bg_download_background)
fragment3_iv1.setImageBitmap(blur2(res, 25f))

获取头像的图片再设置为背景

/**
 * 添加模糊效果
 */
private fun applyBlur() {
    circleIv_headshot.viewTreeObserver.addOnPreDrawListener(object : ViewTreeObserver.OnPreDrawListener {
            override fun onPreDraw(): Boolean {
                circleIv_headshot.viewTreeObserver.removeOnPreDrawListener(this)
                circleIv_headshot.buildDrawingCache()
                val bmp: Bitmap = circleIv_headshot.drawingCache
                blur(bmp, Rl_userdata)
                return true
            }
        })
}
private fun blur(bkg: Bitmap, view: View) {
    val radius = 20f
    val overlay = Bitmap.createBitmap(
        view.measuredWidth,
        view.measuredHeight,
        Bitmap.Config.ARGB_8888
    )
    val scaleW = view.measuredWidth.toFloat() / bkg.width.toFloat()
    val scaleH = view.measuredHeight.toFloat() / bkg.height.toFloat()

    val matrix = Matrix()
    matrix.postScale(scaleW, scaleH)
    val resizeBmp = Bitmap.createBitmap(bkg, 0, 0, bkg.width, bkg.height, matrix, true)

    val canvas = Canvas(overlay)
    canvas.translate((-view.left).toFloat(), (-view.top).toFloat())
    canvas.drawBitmap(resizeBmp, 0f, 0f, null)
    val rs: RenderScript = RenderScript.create(this@MineActivity)
    val overlayAlloc: Allocation = Allocation.createFromBitmap(rs, overlay)
    val blur: ScriptIntrinsicBlur = ScriptIntrinsicBlur.create(rs, overlayAlloc.element)
    blur.setInput(overlayAlloc)
    blur.setRadius(radius)
    blur.forEach(overlayAlloc)
    overlayAlloc.copyTo(overlay)

    view.background = BitmapDrawable(resources, overlay)
    rs.destroy()
}