1 /*
2  * Copyright (c) 2021-2022 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 #include "input/camera_info.h"
16 #include <securec.h>
17 #include "camera_metadata_info.h"
18 #include "camera_log.h"
19 
20 using namespace std;
21 
22 namespace OHOS {
23 namespace CameraStandard {
24 const std::unordered_map<camera_type_enum_t, CameraType> CameraInfo::metaToFwCameraType_ = {
25     {OHOS_CAMERA_TYPE_WIDE_ANGLE, CAMERA_TYPE_WIDE_ANGLE},
26     {OHOS_CAMERA_TYPE_ULTRA_WIDE, CAMERA_TYPE_ULTRA_WIDE},
27     {OHOS_CAMERA_TYPE_TELTPHOTO, CAMERA_TYPE_TELEPHOTO},
28     {OHOS_CAMERA_TYPE_TRUE_DEAPTH, CAMERA_TYPE_TRUE_DEPTH},
29     {OHOS_CAMERA_TYPE_LOGICAL, CAMERA_TYPE_UNSUPPORTED},
30     {OHOS_CAMERA_TYPE_UNSPECIFIED, CAMERA_TYPE_DEFAULT}
31 };
32 
33 const std::unordered_map<camera_position_enum_t, CameraPosition> CameraInfo::metaToFwCameraPosition_ = {
34     {OHOS_CAMERA_POSITION_FRONT, CAMERA_POSITION_FRONT},
35     {OHOS_CAMERA_POSITION_BACK, CAMERA_POSITION_BACK},
36     {OHOS_CAMERA_POSITION_OTHER, CAMERA_POSITION_UNSPECIFIED}
37 };
38 
39 const std::unordered_map<camera_connection_type_t, ConnectionType> CameraInfo::metaToFwConnectionType_ = {
40     {OHOS_CAMERA_CONNECTION_TYPE_REMOTE, CAMERA_CONNECTION_REMOTE},
41     {OHOS_CAMERA_CONNECTION_TYPE_USB_PLUGIN, CAMERA_CONNECTION_USB_PLUGIN},
42     {OHOS_CAMERA_CONNECTION_TYPE_BUILTIN, CAMERA_CONNECTION_BUILT_IN}
43 };
44 
CameraInfo(std::string cameraID,std::shared_ptr<Camera::CameraMetadata> metadata)45 CameraInfo::CameraInfo(std::string cameraID, std::shared_ptr<Camera::CameraMetadata> metadata)
46 {
47     cameraID_ = cameraID;
48     metadata_ = metadata;
49     init(metadata->get());
50 }
51 
~CameraInfo()52 CameraInfo::~CameraInfo()
53 {
54     metadata_.reset();
55     metadata_ = nullptr;
56 }
57 
init(common_metadata_header_t * metadata)58 void CameraInfo::init(common_metadata_header_t* metadata)
59 {
60     camera_metadata_item_t item;
61 
62     int ret = Camera::FindCameraMetadataItem(metadata, OHOS_ABILITY_CAMERA_POSITION, &item);
63     if (ret == CAM_META_SUCCESS) {
64         auto itr = metaToFwCameraPosition_.find(static_cast<camera_position_enum_t>(item.data.u8[0]));
65         if (itr != metaToFwCameraPosition_.end()) {
66             cameraPosition_ = itr->second;
67         }
68     }
69 
70     ret = Camera::FindCameraMetadataItem(metadata, OHOS_ABILITY_CAMERA_TYPE, &item);
71     if (ret == CAM_META_SUCCESS) {
72         auto itr = metaToFwCameraType_.find(static_cast<camera_type_enum_t>(item.data.u8[0]));
73         if (itr != metaToFwCameraType_.end()) {
74             cameraType_ = itr->second;
75         }
76     }
77 
78     ret = Camera::FindCameraMetadataItem(metadata, OHOS_ABILITY_CAMERA_CONNECTION_TYPE, &item);
79     if (ret == CAM_META_SUCCESS) {
80         auto itr = metaToFwConnectionType_.find(static_cast<camera_connection_type_t>(item.data.u8[0]));
81         if (itr != metaToFwConnectionType_.end()) {
82             connectionType_ = itr->second;
83         }
84     }
85 
86     MEDIA_INFO_LOG("camera position: %{public}d, camera type: %{public}d, camera connection type: %{public}d",
87                    cameraPosition_, cameraType_, connectionType_);
88 }
89 
GetID()90 std::string CameraInfo::GetID()
91 {
92     return cameraID_;
93 }
94 
GetMetadata()95 std::shared_ptr<Camera::CameraMetadata> CameraInfo::GetMetadata()
96 {
97     return metadata_;
98 }
99 
SetMetadata(std::shared_ptr<Camera::CameraMetadata> metadata)100 void CameraInfo::SetMetadata(std::shared_ptr<Camera::CameraMetadata> metadata)
101 {
102     metadata_ = metadata;
103 }
104 
GetPosition()105 CameraPosition CameraInfo::GetPosition()
106 {
107     return cameraPosition_;
108 }
109 
GetCameraType()110 CameraType CameraInfo::GetCameraType()
111 {
112     return cameraType_;
113 }
114 
GetConnectionType()115 ConnectionType CameraInfo::GetConnectionType()
116 {
117     return connectionType_;
118 }
119 
CalculateZoomRange()120 std::vector<float> CameraInfo::CalculateZoomRange()
121 {
122     camera_metadata_item_t item;
123     int32_t ret = Camera::FindCameraMetadataItem(metadata_->get(), OHOS_ABILITY_ZOOM_CAP, &item);
124     CHECK_ERROR_RETURN_RET_LOG(ret != CAM_META_SUCCESS, {},
125         "Failed to get zoom cap with return code %{public}d", ret);
126     uint32_t zoomRangeCount = 2;
127     CHECK_ERROR_RETURN_RET_LOG(item.count != zoomRangeCount, {}, "Invalid zoom cap count: %{public}d", item.count);
128     int32_t minIndex = 0;
129     int32_t maxIndex = 1;
130     constexpr float factor = 100.0;
131     MEDIA_DEBUG_LOG("Zoom cap min: %{public}d, max: %{public}d",
132                     item.data.i32[minIndex], item.data.i32[maxIndex]);
133     float minZoom = item.data.i32[minIndex] / factor;
134     float maxZoom = item.data.i32[maxIndex] / factor;
135 
136     ret = Camera::FindCameraMetadataItem(metadata_->get(), OHOS_ABILITY_SCENE_ZOOM_CAP, &item);
137     CHECK_ERROR_RETURN_RET_LOG(ret != CAM_META_SUCCESS, {},
138         "Failed to get scene zoom cap with return code %{public}d", ret);
139     CHECK_ERROR_RETURN_RET_LOG(item.count != zoomRangeCount, {}, "Invalid zoom cap count: %{public}d", item.count);
140     MEDIA_DEBUG_LOG("Scene zoom cap min: %{public}d, max: %{public}d",
141                     item.data.i32[minIndex], item.data.i32[maxIndex]);
142     float tempZoom = item.data.i32[minIndex] / factor;
143     if (minZoom < tempZoom) {
144         minZoom = tempZoom;
145     }
146     tempZoom = item.data.i32[maxIndex] / factor;
147     if (maxZoom > tempZoom) {
148         maxZoom = tempZoom;
149     }
150     return {minZoom, maxZoom};
151 }
152 
GetZoomRatioRange()153 std::vector<float> CameraInfo::GetZoomRatioRange()
154 {
155     if (!zoomRatioRange_.empty()) {
156         return zoomRatioRange_;
157     }
158 
159     camera_metadata_item_t item;
160     int32_t ret = Camera::FindCameraMetadataItem(metadata_->get(), OHOS_ABILITY_ZOOM_RATIO_RANGE, &item);
161     CHECK_ERROR_RETURN_RET_LOG(ret != CAM_META_SUCCESS, {},
162         "Failed to get zoom ratio range with return code %{public}d", ret);
163     uint32_t zoomRangeCount = 2;
164     CHECK_ERROR_RETURN_RET_LOG(item.count != zoomRangeCount, {},
165         "Invalid zoom ratio range count: %{public}d", item.count);
166     int32_t minIndex = 0;
167     int32_t maxIndex = 1;
168     std::vector<float> range = {item.data.f[minIndex], item.data.f[maxIndex]};
169     CHECK_ERROR_RETURN_RET_LOG(range[minIndex] > range[maxIndex], {},
170         "Invalid zoom range. min: %{public}f, max: %{public}f", range[minIndex], range[maxIndex]);
171 
172     MEDIA_DEBUG_LOG("Zoom range min: %{public}f, max: %{public}f", range[minIndex], range[maxIndex]);
173 
174     zoomRatioRange_ = range;
175     return zoomRatioRange_;
176 }
177 
GetExposureBiasRange()178 std::vector<float> CameraInfo::GetExposureBiasRange()
179 {
180     if (!exposureBiasRange_.empty()) {
181         return exposureBiasRange_;
182     }
183 
184     camera_metadata_item_t item;
185     int32_t ret = Camera::FindCameraMetadataItem(metadata_->get(), OHOS_ABILITY_AE_COMPENSATION_RANGE, &item);
186     CHECK_ERROR_RETURN_RET_LOG(ret != CAM_META_SUCCESS, {},
187         "Failed to get exposure compensation range with return code %{public}d", ret);
188     uint32_t biasRangeCount = 2;
189     CHECK_ERROR_RETURN_RET_LOG(item.count != biasRangeCount, {},
190         "Invalid exposure compensation range count: %{public}d", item.count);
191     int32_t minIndex = 0;
192     int32_t maxIndex = 1;
193     std::vector<int32_t> range = {item.data.i32[minIndex], item.data.i32[maxIndex]};
194     CHECK_ERROR_RETURN_RET_LOG(range[minIndex] > range[maxIndex], {},
195         "Invalid exposure compensation range. min: %{public}d, max: %{public}d", range[minIndex], range[maxIndex]);
196     MEDIA_DEBUG_LOG("Exposure hdi compensation min: %{public}d, max: %{public}d", range[minIndex], range[maxIndex]);
197 
198     ret = Camera::FindCameraMetadataItem(metadata_->get(), OHOS_ABILITY_AE_COMPENSATION_STEP, &item);
199     CHECK_ERROR_RETURN_RET_LOG(ret != CAM_META_SUCCESS, {},
200         "Failed to get exposure compensation step with return code %{public}d", ret);
201     int32_t stepNumerator = item.data.r->numerator;
202     int32_t stepDenominator = item.data.r->denominator;
203     float step = static_cast<float>(stepNumerator) / static_cast<float>(stepDenominator);
204     MEDIA_DEBUG_LOG("Exposure step numerator: %{public}d, denominatormax: %{public}d, step: %{public}f",
205         stepNumerator, stepDenominator, step);
206 
207     exposureBiasRange_ = {step * range[minIndex], step * range[maxIndex]};
208 
209     MEDIA_DEBUG_LOG("Exposure compensation min: %{public}f, max: %{public}f",
210         exposureBiasRange_[minIndex], exposureBiasRange_[maxIndex]);
211     return exposureBiasRange_;
212 }
213 } // CameraStandard
214 } // OHOS
215