• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 
16 #include "hstream_capture.h"
17 
18 #include "camera_util.h"
19 #include "camera_log.h"
20 #include "metadata_utils.h"
21 
22 namespace OHOS {
23 namespace CameraStandard {
24 static const int32_t CAPTURE_ROTATE_360 = 360;
HStreamCapture(sptr<OHOS::IBufferProducer> producer,int32_t format,int32_t width,int32_t height)25 HStreamCapture::HStreamCapture(sptr<OHOS::IBufferProducer> producer, int32_t format, int32_t width, int32_t height)
26     : HStreamCommon(StreamType::CAPTURE, producer, format, width, height)
27 {}
28 
~HStreamCapture()29 HStreamCapture::~HStreamCapture()
30 {}
31 
LinkInput(sptr<OHOS::HDI::Camera::V1_1::IStreamOperator> streamOperator,std::shared_ptr<OHOS::Camera::CameraMetadata> cameraAbility,int32_t streamId)32 int32_t HStreamCapture::LinkInput(sptr<OHOS::HDI::Camera::V1_1::IStreamOperator> streamOperator,
33                                   std::shared_ptr<OHOS::Camera::CameraMetadata> cameraAbility, int32_t streamId)
34 {
35     return HStreamCommon::LinkInput(streamOperator, cameraAbility, streamId);
36 }
37 
SetStreamInfo(StreamInfo_V1_1 & streamInfo)38 void HStreamCapture::SetStreamInfo(StreamInfo_V1_1 &streamInfo)
39 {
40     HStreamCommon::SetStreamInfo(streamInfo);
41     streamInfo.v1_0.intent_ = STILL_CAPTURE;
42     streamInfo.v1_0.encodeType_ = ENCODE_TYPE_JPEG;
43     HDI::Camera::V1_1::ExtendedStreamInfo extendedStreamInfo;
44     extendedStreamInfo.type = HDI::Camera::V1_1::EXTENDED_STREAM_INFO_QUICK_THUMBNAIL;
45     extendedStreamInfo.bufferQueue = thumbnailBufferQueue_;
46     // quickThumbnial do not need these param
47     extendedStreamInfo.width = 0;
48     extendedStreamInfo.height = 0;
49     extendedStreamInfo.format = 0;
50     extendedStreamInfo.dataspace = 0;
51     streamInfo.extendedStreamInfos = {extendedStreamInfo};
52 }
53 
SetThumbnail(bool isEnabled,const sptr<OHOS::IBufferProducer> & producer)54 int32_t HStreamCapture::SetThumbnail(bool isEnabled, const sptr<OHOS::IBufferProducer> &producer)
55 {
56     if (isEnabled && producer != nullptr) {
57         thumbnailSwitch_ = 1;
58         thumbnailBufferQueue_ = new BufferProducerSequenceable(producer);
59     } else {
60         thumbnailSwitch_ = 0;
61         thumbnailBufferQueue_ = nullptr;
62     }
63     return CAMERA_OK;
64 }
65 
Capture(const std::shared_ptr<OHOS::Camera::CameraMetadata> & captureSettings)66 int32_t HStreamCapture::Capture(const std::shared_ptr<OHOS::Camera::CameraMetadata> &captureSettings)
67 {
68     CAMERA_SYNC_TRACE;
69     {
70         std::lock_guard<std::mutex> lock(streamOperatorLock_);
71         if (streamOperator_ == nullptr) {
72             return CAMERA_INVALID_STATE;
73         }
74     }
75     int32_t ret = AllocateCaptureId(curCaptureID_);
76     if (ret != CAMERA_OK) {
77         MEDIA_ERR_LOG("HStreamCapture::Capture Failed to allocate a captureId");
78         return ret;
79     }
80     CaptureInfo captureInfoPhoto;
81     captureInfoPhoto.streamIds_ = {streamId_};
82     std::vector<uint8_t> setting;
83     if (!OHOS::Camera::GetCameraMetadataItemCount(captureSettings->get())) {
84         std::lock_guard<std::mutex> lock(cameraAbilityLock_);
85         OHOS::Camera::MetadataUtils::ConvertMetadataToVec(cameraAbility_, setting);
86         captureInfoPhoto.captureSetting_ = setting;
87     } else {
88         OHOS::Camera::MetadataUtils::ConvertMetadataToVec(captureSettings, setting);
89         captureInfoPhoto.captureSetting_ = setting;
90     }
91     captureInfoPhoto.enableShutterCallback_ = true;
92 
93     // debug log for jpeg quality
94     std::shared_ptr<OHOS::Camera::CameraMetadata> captureMetadataSetting_ = nullptr;
95     OHOS::Camera::MetadataUtils::ConvertVecToMetadata(captureInfoPhoto.captureSetting_, captureMetadataSetting_);
96     if (captureMetadataSetting_ != nullptr) {
97         // print quality, mirror log
98         PrintDebugLog(captureMetadataSetting_);
99         // convert rotation with application set rotation
100         SetRotation(captureMetadataSetting_);
101 
102         // update settings
103         std::vector<uint8_t> finalSetting;
104         OHOS::Camera::MetadataUtils::ConvertMetadataToVec(captureMetadataSetting_, finalSetting);
105         captureInfoPhoto.captureSetting_ = finalSetting;
106     }
107     MEDIA_INFO_LOG("HStreamCapture::Capture Starting photo capture with capture ID: %{public}d", curCaptureID_);
108     CamRetCode rc;
109     {
110         std::lock_guard<std::mutex> lock(streamOperatorLock_);
111         rc = (CamRetCode)(streamOperator_->Capture(curCaptureID_, captureInfoPhoto, false));
112     }
113     if (rc != HDI::Camera::V1_0::NO_ERROR) {
114         MEDIA_ERR_LOG("HStreamCapture::Capture failed with error Code: %{public}d", rc);
115         ret = HdiToServiceError(rc);
116     }
117     ReleaseCaptureId(curCaptureID_);
118     curCaptureID_ = 0;
119     return ret;
120 }
121 
PrintDebugLog(const std::shared_ptr<OHOS::Camera::CameraMetadata> & captureMetadataSetting_)122 void HStreamCapture::PrintDebugLog(const std::shared_ptr<OHOS::Camera::CameraMetadata> &captureMetadataSetting_)
123 {
124     camera_metadata_item_t item;
125     int result = OHOS::Camera::FindCameraMetadataItem(captureMetadataSetting_->get(), OHOS_JPEG_QUALITY, &item);
126     if (result != CAM_META_SUCCESS) {
127         MEDIA_DEBUG_LOG("HStreamCapture::Failed to find OHOS_JPEG_QUALITY tag");
128     } else {
129         MEDIA_DEBUG_LOG("HStreamCapture::find OHOS_JPEG_QUALITY value = %{public}d", item.data.u8[0]);
130     }
131 
132     // debug log for capture mirror
133     result = OHOS::Camera::FindCameraMetadataItem(captureMetadataSetting_->get(),
134                                                    OHOS_CONTROL_CAPTURE_MIRROR, &item);
135     if (result != CAM_META_SUCCESS) {
136         MEDIA_DEBUG_LOG("HStreamCapture::Failed to find OHOS_CONTROL_CAPTURE_MIRROR tag");
137     } else {
138         MEDIA_DEBUG_LOG("HStreamCapture::find OHOS_CONTROL_CAPTURE_MIRROR value = %{public}d", item.data.u8[0]);
139     }
140 }
141 
SetRotation(const std::shared_ptr<OHOS::Camera::CameraMetadata> & captureMetadataSetting_)142 void HStreamCapture::SetRotation(const std::shared_ptr<OHOS::Camera::CameraMetadata> &captureMetadataSetting_)
143 {
144     // set orientation for capture
145     // sensor orientation, counter-clockwise rotation
146     int32_t sensorOrientation = 0;
147     int result;
148     camera_metadata_item_t item;
149     {
150         std::lock_guard<std::mutex> lock(cameraAbilityLock_);
151         if (cameraAbility_ == nullptr) {
152             return;
153         }
154         result = OHOS::Camera::FindCameraMetadataItem(cameraAbility_->get(), OHOS_SENSOR_ORIENTATION, &item);
155         if (result == CAM_META_SUCCESS && item.count > 0) {
156             sensorOrientation = item.data.i32[0];
157         }
158         MEDIA_INFO_LOG("set rotation sensor orientation %{public}d", sensorOrientation);
159 
160         camera_position_enum_t cameraPosition = OHOS_CAMERA_POSITION_BACK;
161         result = OHOS::Camera::FindCameraMetadataItem(cameraAbility_->get(), OHOS_ABILITY_CAMERA_POSITION, &item);
162         if (result == CAM_META_SUCCESS && item.count > 0) {
163             cameraPosition = static_cast<camera_position_enum_t>(item.data.u8[0]);
164         }
165         MEDIA_INFO_LOG("set rotation camera position %{public}d", cameraPosition);
166     }
167 
168     // rotation from application
169     int32_t rotationValue = 0;
170     result = OHOS::Camera::FindCameraMetadataItem(captureMetadataSetting_->get(), OHOS_JPEG_ORIENTATION, &item);
171     if (result == CAM_META_SUCCESS && item.count > 0) {
172         rotationValue = item.data.i32[0];
173     }
174     MEDIA_INFO_LOG("set rotation app rotationValue %{public}d", rotationValue);
175 
176     // real rotation
177     int32_t rotation = sensorOrientation + rotationValue;
178     if (rotation >= CAPTURE_ROTATE_360) {
179         rotation = rotation - CAPTURE_ROTATE_360;
180     }
181     MEDIA_INFO_LOG("set rotation camera real rotation %{public}d", rotation);
182 
183     bool status = false;
184     if (result == CAM_META_ITEM_NOT_FOUND) {
185         status = captureMetadataSetting_->addEntry(OHOS_JPEG_ORIENTATION, &rotation, 1);
186     } else if (result == CAM_META_SUCCESS) {
187         status = captureMetadataSetting_->updateEntry(OHOS_JPEG_ORIENTATION, &rotation, 1);
188     }
189     result = OHOS::Camera::FindCameraMetadataItem(captureMetadataSetting_->get(), OHOS_JPEG_ORIENTATION, &item);
190     if (result != CAM_META_SUCCESS) {
191         MEDIA_ERR_LOG("set rotation Failed to find OHOS_JPEG_ORIENTATION tag");
192     }
193     if (!status) {
194         MEDIA_ERR_LOG("set rotation Failed to set Rotation");
195     }
196 }
197 
CancelCapture()198 int32_t HStreamCapture::CancelCapture()
199 {
200     // Cancel cature is dummy till continuous/burst mode is supported
201     return CAMERA_OK;
202 }
203 
Release()204 int32_t HStreamCapture::Release()
205 {
206     if (curCaptureID_) {
207         ReleaseCaptureId(curCaptureID_);
208     }
209     std::lock_guard<std::mutex> lock(callbackLock_);
210     streamCaptureCallback_ = nullptr;
211     return HStreamCommon::Release();
212 }
213 
SetCallback(sptr<IStreamCaptureCallback> & callback)214 int32_t HStreamCapture::SetCallback(sptr<IStreamCaptureCallback> &callback)
215 {
216     if (callback == nullptr) {
217         MEDIA_ERR_LOG("HStreamCapture::SetCallback callback is null");
218         return CAMERA_INVALID_ARG;
219     }
220     std::lock_guard<std::mutex> lock(callbackLock_);
221     streamCaptureCallback_ = callback;
222     return CAMERA_OK;
223 }
224 
OnCaptureStarted(int32_t captureId)225 int32_t HStreamCapture::OnCaptureStarted(int32_t captureId)
226 {
227     CAMERA_SYNC_TRACE;
228     std::lock_guard<std::mutex> lock(callbackLock_);
229     if (streamCaptureCallback_ != nullptr) {
230         streamCaptureCallback_->OnCaptureStarted(captureId);
231     }
232     return CAMERA_OK;
233 }
234 
OnCaptureEnded(int32_t captureId,int32_t frameCount)235 int32_t HStreamCapture::OnCaptureEnded(int32_t captureId, int32_t frameCount)
236 {
237     CAMERA_SYNC_TRACE;
238     std::lock_guard<std::mutex> lock(callbackLock_);
239     if (streamCaptureCallback_ != nullptr) {
240         streamCaptureCallback_->OnCaptureEnded(captureId, frameCount);
241     }
242     return CAMERA_OK;
243 }
244 
OnCaptureError(int32_t captureId,int32_t errorCode)245 int32_t HStreamCapture::OnCaptureError(int32_t captureId, int32_t errorCode)
246 {
247     std::lock_guard<std::mutex> lock(callbackLock_);
248     if (streamCaptureCallback_ != nullptr) {
249         int32_t captureErrorCode;
250         if (errorCode == BUFFER_LOST) {
251             captureErrorCode = CAMERA_STREAM_BUFFER_LOST;
252         } else {
253             captureErrorCode = CAMERA_UNKNOWN_ERROR;
254         }
255         CAMERA_SYSEVENT_FAULT(CreateMsg("Photo OnCaptureError! captureId:%d & "
256                                         "errorCode:%{public}d", captureId, captureErrorCode));
257         streamCaptureCallback_->OnCaptureError(captureId, captureErrorCode);
258     }
259     return CAMERA_OK;
260 }
261 
OnFrameShutter(int32_t captureId,uint64_t timestamp)262 int32_t HStreamCapture::OnFrameShutter(int32_t captureId, uint64_t timestamp)
263 {
264     CAMERA_SYNC_TRACE;
265     std::lock_guard<std::mutex> lock(callbackLock_);
266     if (streamCaptureCallback_ != nullptr) {
267         streamCaptureCallback_->OnFrameShutter(captureId, timestamp);
268     }
269     return CAMERA_OK;
270 }
271 
DumpStreamInfo(std::string & dumpString)272 void HStreamCapture::DumpStreamInfo(std::string& dumpString)
273 {
274     dumpString += "capture stream:\n";
275     dumpString += "ThumbnailSwitch:[" + std::to_string(thumbnailSwitch_);
276     if (thumbnailBufferQueue_) {
277         dumpString += "] ThumbnailBuffer producer Id:["
278             + std::to_string(thumbnailBufferQueue_->producer_->GetUniqueId());
279     }
280     dumpString += "]\n";
281     HStreamCommon::DumpStreamInfo(dumpString);
282 }
283 } // namespace CameraStandard
284 } // namespace OHOS
285