/* * Copyright (c) 2020-2021 Huawei Device Co., Ltd. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ #include "camera_manager.h" #include "camera_impl.h" #include "camera_service_client.h" #include "camera_service_callback.h" #include "media_log.h" #include <cstdio> #include <map> using namespace std; namespace OHOS { namespace Media { class CameraManagerImpl : public CameraManager, public CameraServiceCallback { public: CameraManagerImpl() { cameraServiceClient_ = CameraServiceClient::GetInstance(); cameraServiceClient_->InitCameraServiceClient(this); } ~CameraManagerImpl() { for (const auto &i : cameraMapCache_) { delete i.second; } } void OnCameraServiceInitialized(list<string> &availCameraIdList) override { /* cameraService_ cannot be nullptr as OnCameraServiceInitialized is a callback of cameraService_ */ for (auto &cameraId : availCameraIdList) { InitCameraAbility(cameraId); } } void OnCameraStatusChange(string &cameraId, CameraStatus status) override { auto p = cameraMapCache_.find(cameraId); switch (status) { case CAMERA_STATUS_UNAVAIL: if (p != cameraMapCache_.end()) { for (auto &i : deviceCbList_) { i.second->Post( [i, cameraId]() { i.first->OnCameraStatus(cameraId, CAMERA_DEVICE_STATE_UNAVAILABLE); }); } // User may still using icamera now delete p->second; cameraMapCache_.erase(p); } break; case CAMERA_STATUS_AVAIL: InitCameraAbility(cameraId); if (p == cameraMapCache_.end()) { for (auto &i : deviceCbList_) { i.second->Post( [i, cameraId]() { i.first->OnCameraStatus(cameraId, CAMERA_DEVICE_STATE_AVAILABLE); }); } } break; case CAMERA_STATUS_CREATED: if (p != cameraMapCache_.end()) { p->second->OnCreate(cameraId); } break; case CAMERA_STATUS_CREATE_FAILED: if (p != cameraMapCache_.end()) { p->second->OnCreateFailed(); } break; default: break; } } void RegisterCameraDeviceCallback(CameraDeviceCallback &callback, EventHandler &handler) override { deviceCbList_.emplace_back(make_pair(&callback, &handler)); for (const auto &i : cameraMapCache_) { string cameraId = i.first; handler.Post([&callback, cameraId]() { callback.OnCameraStatus(cameraId, CAMERA_DEVICE_STATE_AVAILABLE); }); } } void UnregisterCameraDeviceCallback(CameraDeviceCallback &callback) override { for (auto p = deviceCbList_.begin(); p != deviceCbList_.end(); p++) { if (p->first == &callback) { deviceCbList_.erase(p); break; } } } uint8_t GetCameraModeNum() override { return cameraServiceClient_->GetCameraModeNum(); } int32_t SetCameraMode(uint8_t modeIndex) override { return cameraServiceClient_->SetCameraMode(modeIndex); } list<string> GetCameraIds() override { list<string> cameraList; for (auto &i : cameraMapCache_) { MEDIA_DEBUG_LOG("%s", i.first.c_str()); cameraList.emplace_back(i.first); } return cameraList; } const CameraAbility *GetCameraAbility(const string &cameraId) override { auto camera = cameraMapCache_.find(cameraId); if (camera == cameraMapCache_.end()) { return nullptr; } return camera->second->GetAbility(); } const CameraInfo *GetCameraInfo(const string &cameraId) override { auto camera = cameraMapCache_.find(cameraId); if (camera == cameraMapCache_.end()) { return nullptr; } return camera->second->GetInfo(); } void CreateCamera(const string &cameraId, CameraStateCallback &callback, EventHandler &handler) override { auto p = cameraMapCache_.find(cameraId); if (p == cameraMapCache_.end()) { MEDIA_ERR_LOG("The cameraId %s is not available", cameraId.c_str()); handler.Post([&callback, &cameraId] { callback.OnCreateFailed(cameraId, MEDIA_ERR); }); return; } p->second->RegistCb(callback, handler); cameraServiceClient_->CreateCamera(cameraId); } private: CameraServiceClient *cameraServiceClient_; map<string, CameraImpl *> cameraMapCache_; list<pair<CameraDeviceCallback *, EventHandler *>> deviceCbList_; void InitCameraAbility(string &cameraId) { auto ability = cameraServiceClient_->GetCameraAbility(cameraId); auto info = cameraServiceClient_->GetCameraInfo(cameraId); CameraImpl *cam = new (nothrow) CameraImpl(cameraId, ability, info); if (cam == nullptr) { MEDIA_FATAL_LOG("New object failed."); return; } cameraMapCache_[cameraId] = cam; } }; CameraManager *CameraManager::GetInstance() { static CameraManagerImpl cameraManagerImpl; return &cameraManagerImpl; } } // namespace Media } // namespace OHOS