1 /*
2  * Copyright 2023 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package androidx.camera.camera2.pipe.integration.impl
18 
19 import android.hardware.camera2.CameraCharacteristics
20 import android.hardware.camera2.CaptureRequest
21 import android.os.Build
22 import androidx.camera.camera2.pipe.CameraMetadata
23 
24 /** Contains the CameraX-specific logic for [CameraMetadata]. */
25 public val CameraMetadata.availableAfModes: List<Int>
26     get() =
27         getOrDefault(
28                 CameraCharacteristics.CONTROL_AF_AVAILABLE_MODES,
29                 intArrayOf(CaptureRequest.CONTROL_AF_MODE_OFF)
30             )
31             .asList()
32 
33 public val CameraMetadata.availableAeModes: List<Int>
34     get() =
35         getOrDefault(
36                 CameraCharacteristics.CONTROL_AE_AVAILABLE_MODES,
37                 intArrayOf(CaptureRequest.CONTROL_AE_MODE_OFF)
38             )
39             .asList()
40 
41 public val CameraMetadata.availableAwbModes: List<Int>
42     get() =
43         getOrDefault(
44                 CameraCharacteristics.CONTROL_AWB_AVAILABLE_MODES,
45                 intArrayOf(CaptureRequest.CONTROL_AWB_MODE_OFF)
46             )
47             .asList()
48 
49 /** If preferredMode not available, priority is CONTINUOUS_PICTURE > AUTO > OFF */
getSupportedAfModenull50 public fun CameraMetadata.getSupportedAfMode(preferredMode: Int): Int =
51     when {
52         availableAfModes.contains(preferredMode) -> {
53             preferredMode
54         }
55         availableAfModes.contains(CaptureRequest.CONTROL_AF_MODE_CONTINUOUS_PICTURE) -> {
56             CaptureRequest.CONTROL_AF_MODE_CONTINUOUS_PICTURE
57         }
58         availableAfModes.contains(CaptureRequest.CONTROL_AF_MODE_AUTO) -> {
59             CaptureRequest.CONTROL_AF_MODE_AUTO
60         }
61         else -> {
62             CaptureRequest.CONTROL_AF_MODE_OFF
63         }
64     }
65 
66 /** If preferredMode not available, priority is AE_ON > AE_OFF */
getSupportedAeModenull67 public fun CameraMetadata.getSupportedAeMode(preferredMode: Int): Int =
68     when {
69         availableAeModes.contains(preferredMode) -> {
70             preferredMode
71         }
72         availableAeModes.contains(CaptureRequest.CONTROL_AE_MODE_ON) -> {
73             CaptureRequest.CONTROL_AE_MODE_ON
74         }
75         else -> {
76             CaptureRequest.CONTROL_AE_MODE_OFF
77         }
78     }
79 
isAeModeSupportednull80 private fun CameraMetadata.isAeModeSupported(aeMode: Int) = getSupportedAeMode(aeMode) == aeMode
81 
82 /** Returns whether [CaptureRequest.CONTROL_AE_MODE_ON_EXTERNAL_FLASH] is supported. */
83 public fun CameraMetadata.isExternalFlashAeModeSupported(): Boolean =
84     Build.VERSION.SDK_INT >= 28 &&
85         isAeModeSupported(CaptureRequest.CONTROL_AE_MODE_ON_EXTERNAL_FLASH)
86 
87 /** If preferredMode not available, priority is AWB_AUTO > AWB_OFF */
88 public fun CameraMetadata.getSupportedAwbMode(preferredMode: Int): Int =
89     when {
90         availableAwbModes.contains(preferredMode) -> {
91             preferredMode
92         }
93         availableAwbModes.contains(CaptureRequest.CONTROL_AWB_MODE_AUTO) -> {
94             CaptureRequest.CONTROL_AWB_MODE_AUTO
95         }
96         else -> {
97             CaptureRequest.CONTROL_AWB_MODE_OFF
98         }
99     }
100 
getOrDefaultnull101 public fun <T> CameraMetadata?.getOrDefault(key: CameraCharacteristics.Key<T>, default: T): T =
102     this?.getOrDefault(key, default) ?: default
103