使用 CameraX Extensions API 将特效应用到照片上
Android CameraX
https://android-developers.googleblog.com/2019/05/whats-new-with-android-jetpack.htmlExtensionsManager
https://developer.android.google.cn/reference/androidx/camera/extensions/ExtensionsManager
CameraX Extensions
CameraX Extensions 涵盖的内容
1.0.0 版本的 CameraX Extensions 包括一些最常见的内置相机特效:
BOKEH (焦外成像): 在人像模式下拍摄照片时,让前景人物更清晰。 HDR (高动态范围): 拍照时使用不同的自动曝光 (AE) 配置,以获得最佳效果。 NIGHT (夜间): 在低照度环境下 (通常是在夜间) 捕获最佳静态图像。 FACE RETOUCH (脸部照片修复): 拍摄静态图像时,修饰脸部肤色、轮廓等。 AUTO (自动): 根据周围的景色自动调整最终图像。
让我们来看几组在 Android 手机上拍摄的照片,拍照时分别启用和禁用了由 CameraX Extensions API 提供的特效。
BOKEH 模式的例子
△ 图 1: 右侧照片启用了 BOKEH 特效。
HDR 模式的例子
△ 图 2: 右侧照片启用了 HDR 特效。
NIGHT 模式例子
△ 图 3: 右侧照片启用了 NIGHT 特效。
视觉上的差异是很明显的。您可以使用 CameraX Extensions API 在您自己的应用中实现这些图像的效果。
现在让我们看看如何将 CameraX 的 API 集成到您的应用中。
Extensions API
在现有的 CameraX 应用中,首先您可以引入 camera-extensions Jetpack 库来添加 CameraX Extensions:
dependencies {
// 与 Extensions 库版本号相匹配的 CameraX 核心库
implementation 'androidx.camera:camera-core:1.1.0-alpha08'
implementation 'androidx.camera:camera-camera2:1.1.0-alpha08'
implementation 'androidx.camera:camera-lifecycle:1.1.0-alpha08'
// CameraX Extensions 库
implementation 'androidx.camera:camera-extensions:1.0.0-alpha28'
// 其他依赖项
implementation('androidx.concurrent:concurrent-futures-ktx:1.1.0')
…
}
获取 ExtensionsManager 实例: https://developer.android.google.cn/reference/androidx/camera/extensions/ExtensionsManager
检查目标设备是否支持需要用到的扩展模式; 获取一个启用扩展的 CameraSelector; 使用启用扩展的 CameraSelector 调用 bindToLifecycle: https://developer.android.google.cn/reference/androidx/camera/lifecycle/ProcessCameraProvider#bindToLifecycle(androidx.lifecycle.LifecycleOwner,%20androidx.camera.core.CameraSelector,%20androidx.camera.core.UseCase...)
获取 ExtensionsManager 实例
第一步是用扩展库的 getInstance(Context) API 获得一个 ExtensionsManager 实例。这个 API 返回一个 ListenableFuture,我们可以在 Kotlin 挂起函数中使用 await() 来获取结果以避免阻塞主线程。(注意: 在 ListenableFuture 上使用 await() 须引入 androidx.concurrent:concurrent-futures-ktx: 1.1.0 依赖项。)
// 创建扩展管理器(使用 Jetpack Concurrent 库)
val extensionsManager = ExtensionsManager.getInstance(context).await()
getInstance(Context)
https://developer.android.google.cn/reference/androidx/camera/extensions/ExtensionsManager#getInstance(android.content.Context)
ExtensionsManager
https://developer.android.google.cn/reference/androidx/camera/extensions/ExtensionsManager
通过 ExtensionsManager,您可以确定设备是否支持某一特定的扩展模式,并为其获取一个启用扩展的 CameraSelector。请注意以下几点:
ExtensionsManager 是一个进程范围的全局资源: 一个进程中只存在一个 ExtensionsManager 实例。
ExtensionsManager 始终存在: 无论底层设备是否支持扩展,CameraX 都提供一个有效的 ExtensionsManager 实例。
检查扩展模式可用性
// 获取相机设备来检查是否支持扩展
val cameraSelector = CameraSelector.DEFAULT_BACK_CAMERA
// 检查是否支持 BOKEH
if (extensionsManager.isExtensionAvailable(
cameraProvider,
cameraSelector,
ExtensionMode.BOKEH
)) {
...
}
isExtensionAvailable(CameraProvider, CameraSelector, int)
https://developer.android.google.cn/reference/androidx/camera/extensions/ExtensionsManager#isExtensionAvailable(androidx.camera.core.CameraProvider,%20androidx.camera.core.CameraSelector,%20int)
获取启用扩展的 CameraSelector
val bokehCameraSelector = extensionsManager
.getExtensionEnabledCameraSelector(
cameraProvider, cameraSelector, ExtensionMode.BOKEH)
getExtensionEnabledCameraSelector(CameraProvider, CameraSelector, int)
https://developer.android.google.cn/reference/androidx/camera/extensions/ExtensionsManager#getExtensionEnabledCameraSelector(androidx.camera.core.CameraProvider,%20androidx.camera.core.CameraSelector,%20int)
使用启用扩展的 CameraSelector 调用 bindToLifecycle()
// 将开启了 BOKEH 的相机选择器绑定到用例上
val imageCapture = ImageCapture.Builder().build()
val preview = Preview.Builder().build()
cameraProvider.bindToLifecycle(
lifecycleOwner,
bokehCameraSelector,
imageCapture,
preview
)
bindToLifecycle()
https://developer.android.google.cn/reference/androidx/camera/lifecycle/ProcessCameraProvider#bindToLifecycle(androidx.lifecycle.LifecycleOwner,%20androidx.camera.core.CameraSelector,%20androidx.camera.core.UseCase...)DEFAULT_BACK_CAMERA
https://developer.android.google.cn/reference/androidx/camera/core/CameraSelector#DEFAULT_BACK_CAMERADEFAULT_FRONT_CAMERA
https://developer.android.google.cn/reference/androidx/camera/core/CameraSelector#DEFAULT_FRONT_CAMERA
使用 Extensions API 的样例代码
fun onCreate() {
lifecycleScope.launch {
// 创建 cameraProvider
val cameraProvider = ProcessCameraProvider.getInstance(context).await()
// 创建 extensionsManager(使用 Jetpack Concurrent 库)
val extensionsManager =
ExtensionsManager.getInstance(context).await()
// 获取相机设备来检查是否支持扩展
val cameraSelector = CameraSelector.DEFAULT_BACK_CAMERA
// 检查是否支持 BOKEH
if (extensionsManager.isExtensionAvailable(
cameraProvider,
cameraSelector,
ExtensionMode.BOKEH
)) {
// 在启用不同扩展模式之前解除所有用例的绑定
cameraProvider.unbindAll()
// 获取启用了 BOKEH 的相机选择器
val bokehCameraSelector = extensionsManager
.getExtensionEnabledCameraSelector(
cameraProvider,
cameraSelector,
ExtensionMode.BOKEH
)
// 将开启了 BOKEH 的相机选择器绑定到用例上
val imageCapture = ImageCapture.Builder().build()
val preview = Preview.Builder().build()
cameraProvider.bindToLifecycle(
lifecycleOwner,
bokehCameraSelector,
imageCapture,
preview
)
}
}
}
Extensions API 对核心模块的依赖
CameraX Extensions API 是在 camera-extensions 库中实现的,并且它依赖 CameraX 核心模块 (core、camera2 和 lifecycle)。使用 CameraX Extensions 时,请务必使用与您正在使用的 CameraX 核心模块相同的发布包中的版本。例如,要使用 camera-extensions:1.0.0-alpha28,则您必须在应用的依赖列表中包含 1.0.0-alpha08 版本的 camera-lifecycle、camera-core 和 camera-camera2,因为它们是于 2021 年 8 月 18 日在同一软件包中发布的。
相同的发布包
https://developer.android.google.cn/jetpack/androidx/releases/camera
支持扩展的设备
CameraX Vendor Extensions 接口
https://source.android.com/devices/camera/camerax-vendor-extensionsCameraX 设备页面
https://developer.android.google.cn/training/camerax/devices
移除旧版 Extensions API
2019 年 8 月发布的旧版 Extensions API 现已废弃。这个旧版的 Extensions API 提供了扩展器类,需要将扩展相关的配置应用到每个 Preview 和 ImageCapture 用例上。旧版的扩展器设计可能会导致开发人员忘记要在 Preview 或 ImageCapture 上启用扩展模式,并可能导致非预期的行为。
新的 CameraX Extensions 库在 1.0.0-alpha26 中引入。较新的 Extensions API 将扩展绑定从用例切换到目标相机,使用起来更加方便。请务必迁移以利用新的 Extensions API。
我们特别感谢那些帮助实现 CameraX Extensions API 的出色的 Android 相机开发者和设备制造商!如果您想了解 CameraX 的最新进展,请加入 Android CameraX 讨论组:
更多信息
CameraX Extensions API 指南 https://developer.android.google.cn/training/camerax/vendor-extensions
Extensions API 参考
https://developer.android.google.cn/reference/androidx/camera/extensions/ExtensionsManager扩展测试应用
https://android.googlesource.com/platform/frameworks/support/+/androidx-main/camera/integration-tests/extensionstestapp/CameraX 发布说明
https://developer.android.google.cn/jetpack/androidx/releases/camera开始使用 CameraX
https://developer.android.google.cn/codelabs/camerax-getting-started#0CameraX Github 样例代码
https://github.com/android/camera-samples
推荐阅读