Committed by
GitHub
Fix CameraXSession not setting the target capture format correctly (#652)
* Fix CameraXSession not setting the target capture format correctly, and remove unused usecase * changeset and spotless
正在显示
3 个修改的文件
包含
52 行增加
和
32 行删除
.changeset/afraid-shrimps-pull.md
0 → 100644
| 1 | /* | 1 | /* |
| 2 | - * Copyright 2024 LiveKit, Inc. | 2 | + * Copyright 2024-2025 LiveKit, Inc. |
| 3 | * | 3 | * |
| 4 | * Licensed under the Apache License, Version 2.0 (the "License"); | 4 | * Licensed under the Apache License, Version 2.0 (the "License"); |
| 5 | * you may not use this file except in compliance with the License. | 5 | * you may not use this file except in compliance with the License. |
| @@ -32,10 +32,12 @@ import androidx.camera.camera2.interop.Camera2CameraInfo | @@ -32,10 +32,12 @@ import androidx.camera.camera2.interop.Camera2CameraInfo | ||
| 32 | import androidx.camera.camera2.interop.Camera2Interop | 32 | import androidx.camera.camera2.interop.Camera2Interop |
| 33 | import androidx.camera.core.Camera | 33 | import androidx.camera.core.Camera |
| 34 | import androidx.camera.core.CameraSelector | 34 | import androidx.camera.core.CameraSelector |
| 35 | -import androidx.camera.core.ImageAnalysis | 35 | +import androidx.camera.core.ExtendableBuilder |
| 36 | import androidx.camera.core.Preview | 36 | import androidx.camera.core.Preview |
| 37 | import androidx.camera.core.Preview.SurfaceProvider | 37 | import androidx.camera.core.Preview.SurfaceProvider |
| 38 | import androidx.camera.core.UseCase | 38 | import androidx.camera.core.UseCase |
| 39 | +import androidx.camera.core.resolutionselector.ResolutionSelector | ||
| 40 | +import androidx.camera.core.resolutionselector.ResolutionStrategy | ||
| 39 | import androidx.camera.lifecycle.ProcessCameraProvider | 41 | import androidx.camera.lifecycle.ProcessCameraProvider |
| 40 | import androidx.core.content.ContextCompat | 42 | import androidx.core.content.ContextCompat |
| 41 | import androidx.lifecycle.LifecycleOwner | 43 | import androidx.lifecycle.LifecycleOwner |
| @@ -154,9 +156,6 @@ internal constructor( | @@ -154,9 +156,6 @@ internal constructor( | ||
| 154 | } ?: request.willNotProvideSurface() | 156 | } ?: request.willNotProvideSurface() |
| 155 | } | 157 | } |
| 156 | 158 | ||
| 157 | - // Set image analysis - camera params | ||
| 158 | - val imageAnalysis = setImageAnalysis() | ||
| 159 | - | ||
| 160 | // Select camera by ID | 159 | // Select camera by ID |
| 161 | val cameraSelector = CameraSelector.Builder() | 160 | val cameraSelector = CameraSelector.Builder() |
| 162 | .addCameraFilter { cameraInfo -> cameraInfo.filter { Camera2CameraInfo.from(it).cameraId == cameraId } } | 161 | .addCameraFilter { cameraInfo -> cameraInfo.filter { Camera2CameraInfo.from(it).cameraId == cameraId } } |
| @@ -166,6 +165,17 @@ internal constructor( | @@ -166,6 +165,17 @@ internal constructor( | ||
| 166 | ContextCompat.getMainExecutor(context).execute { | 165 | ContextCompat.getMainExecutor(context).execute { |
| 167 | // Preview | 166 | // Preview |
| 168 | val preview = Preview.Builder() | 167 | val preview = Preview.Builder() |
| 168 | + .setResolutionSelector( | ||
| 169 | + ResolutionSelector.Builder() | ||
| 170 | + .setResolutionStrategy( | ||
| 171 | + ResolutionStrategy( | ||
| 172 | + Size(captureFormat?.width ?: width, captureFormat?.height ?: height), | ||
| 173 | + ResolutionStrategy.FALLBACK_RULE_CLOSEST_HIGHER_THEN_LOWER, | ||
| 174 | + ), | ||
| 175 | + ) | ||
| 176 | + .build(), | ||
| 177 | + ) | ||
| 178 | + .applyCameraSettings() | ||
| 169 | .build() | 179 | .build() |
| 170 | .also { | 180 | .also { |
| 171 | it.setSurfaceProvider(surfaceProvider) | 181 | it.setSurfaceProvider(surfaceProvider) |
| @@ -178,7 +188,6 @@ internal constructor( | @@ -178,7 +188,6 @@ internal constructor( | ||
| 178 | camera = cameraProvider.bindToLifecycle( | 188 | camera = cameraProvider.bindToLifecycle( |
| 179 | lifecycleOwner, | 189 | lifecycleOwner, |
| 180 | cameraSelector, | 190 | cameraSelector, |
| 181 | - imageAnalysis, | ||
| 182 | preview, | 191 | preview, |
| 183 | *useCases, | 192 | *useCases, |
| 184 | ) | 193 | ) |
| @@ -195,36 +204,34 @@ internal constructor( | @@ -195,36 +204,34 @@ internal constructor( | ||
| 195 | ) | 204 | ) |
| 196 | } | 205 | } |
| 197 | 206 | ||
| 198 | - private fun setImageAnalysis() = ImageAnalysis.Builder() | ||
| 199 | - .setTargetResolution(Size(captureFormat?.width ?: width, captureFormat?.height ?: height)) | ||
| 200 | - .setBackpressureStrategy(ImageAnalysis.STRATEGY_KEEP_ONLY_LATEST).apply { | ||
| 201 | - val cameraExtender = Camera2Interop.Extender(this) | ||
| 202 | - captureFormat?.let { captureFormat -> | ||
| 203 | - cameraExtender.setCaptureRequestOption( | ||
| 204 | - CaptureRequest.CONTROL_AE_TARGET_FPS_RANGE, | ||
| 205 | - Range( | ||
| 206 | - captureFormat.framerate.min / fpsUnitFactor, | ||
| 207 | - captureFormat.framerate.max / fpsUnitFactor, | ||
| 208 | - ), | ||
| 209 | - ) | ||
| 210 | - cameraExtender.setCaptureRequestOption(CaptureRequest.CONTROL_AE_MODE, CaptureRequest.CONTROL_AE_MODE_ON) | ||
| 211 | - cameraExtender.setCaptureRequestOption(CaptureRequest.CONTROL_AE_LOCK, false) | ||
| 212 | - when (stabilizationMode) { | ||
| 213 | - StabilizationMode.OPTICAL -> { | ||
| 214 | - cameraExtender.setCaptureRequestOption(CaptureRequest.LENS_OPTICAL_STABILIZATION_MODE, LENS_OPTICAL_STABILIZATION_MODE_ON) | ||
| 215 | - cameraExtender.setCaptureRequestOption(CaptureRequest.CONTROL_VIDEO_STABILIZATION_MODE, CONTROL_VIDEO_STABILIZATION_MODE_OFF) | ||
| 216 | - } | 207 | + private fun <T> ExtendableBuilder<T>.applyCameraSettings(): ExtendableBuilder<T> { |
| 208 | + val cameraExtender = Camera2Interop.Extender(this) | ||
| 209 | + val captureFormat = this@CameraXSession.captureFormat ?: return this | ||
| 210 | + cameraExtender.setCaptureRequestOption( | ||
| 211 | + CaptureRequest.CONTROL_AE_TARGET_FPS_RANGE, | ||
| 212 | + Range( | ||
| 213 | + captureFormat.framerate.min / fpsUnitFactor, | ||
| 214 | + captureFormat.framerate.max / fpsUnitFactor, | ||
| 215 | + ), | ||
| 216 | + ) | ||
| 217 | + cameraExtender.setCaptureRequestOption(CaptureRequest.CONTROL_AE_MODE, CaptureRequest.CONTROL_AE_MODE_ON) | ||
| 218 | + cameraExtender.setCaptureRequestOption(CaptureRequest.CONTROL_AE_LOCK, false) | ||
| 219 | + when (stabilizationMode) { | ||
| 220 | + StabilizationMode.OPTICAL -> { | ||
| 221 | + cameraExtender.setCaptureRequestOption(CaptureRequest.LENS_OPTICAL_STABILIZATION_MODE, LENS_OPTICAL_STABILIZATION_MODE_ON) | ||
| 222 | + cameraExtender.setCaptureRequestOption(CaptureRequest.CONTROL_VIDEO_STABILIZATION_MODE, CONTROL_VIDEO_STABILIZATION_MODE_OFF) | ||
| 223 | + } | ||
| 217 | 224 | ||
| 218 | - StabilizationMode.VIDEO -> { | ||
| 219 | - cameraExtender.setCaptureRequestOption(CaptureRequest.CONTROL_VIDEO_STABILIZATION_MODE, CONTROL_VIDEO_STABILIZATION_MODE_ON) | ||
| 220 | - cameraExtender.setCaptureRequestOption(CaptureRequest.LENS_OPTICAL_STABILIZATION_MODE, LENS_OPTICAL_STABILIZATION_MODE_OFF) | ||
| 221 | - } | 225 | + StabilizationMode.VIDEO -> { |
| 226 | + cameraExtender.setCaptureRequestOption(CaptureRequest.CONTROL_VIDEO_STABILIZATION_MODE, CONTROL_VIDEO_STABILIZATION_MODE_ON) | ||
| 227 | + cameraExtender.setCaptureRequestOption(CaptureRequest.LENS_OPTICAL_STABILIZATION_MODE, LENS_OPTICAL_STABILIZATION_MODE_OFF) | ||
| 228 | + } | ||
| 222 | 229 | ||
| 223 | - else -> Unit | ||
| 224 | - } | 230 | + else -> { |
| 225 | } | 231 | } |
| 226 | } | 232 | } |
| 227 | - .build() | 233 | + return this |
| 234 | + } | ||
| 228 | 235 | ||
| 229 | private fun stopInternal() { | 236 | private fun stopInternal() { |
| 230 | Logging.d(TAG, "Stop internal") | 237 | Logging.d(TAG, "Stop internal") |
| @@ -25,7 +25,15 @@ data class LocalVideoTrackOptions( | @@ -25,7 +25,15 @@ data class LocalVideoTrackOptions( | ||
| 25 | * will prefer a camera according to [position] | 25 | * will prefer a camera according to [position] |
| 26 | */ | 26 | */ |
| 27 | val deviceId: String? = null, | 27 | val deviceId: String? = null, |
| 28 | + /** | ||
| 29 | + * The camera position to use. | ||
| 30 | + */ | ||
| 28 | val position: CameraPosition? = CameraPosition.FRONT, | 31 | val position: CameraPosition? = CameraPosition.FRONT, |
| 32 | + /** | ||
| 33 | + * Video capture options such as resolution and framerate. | ||
| 34 | + * | ||
| 35 | + * See [VideoPreset169] or [VideoPreset43] for preset parameters for common resolutions. | ||
| 36 | + */ | ||
| 29 | val captureParams: VideoCaptureParameter = VideoPreset169.H720.capture, | 37 | val captureParams: VideoCaptureParameter = VideoPreset169.H720.capture, |
| 30 | ) | 38 | ) |
| 31 | 39 |
-
请 注册 或 登录 后发表评论