166f3657fSopenharmony_ci/* 266f3657fSopenharmony_ci * Copyright (c) 2022-2024 Huawei Device Co., Ltd. 366f3657fSopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License"); 466f3657fSopenharmony_ci * you may not use this file except in compliance with the License. 566f3657fSopenharmony_ci * You may obtain a copy of the License at 666f3657fSopenharmony_ci * 766f3657fSopenharmony_ci * http://www.apache.org/licenses/LICENSE-2.0 866f3657fSopenharmony_ci * 966f3657fSopenharmony_ci * Unless required by applicable law or agreed to in writing, software 1066f3657fSopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS, 1166f3657fSopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1266f3657fSopenharmony_ci * See the License for the specific language governing permissions and 1366f3657fSopenharmony_ci * limitations under the License. 1466f3657fSopenharmony_ci */ 1566f3657fSopenharmony_ci 1666f3657fSopenharmony_ci#include "dscreen_handler.h" 1766f3657fSopenharmony_ci 1866f3657fSopenharmony_ci#include "avcodec_info.h" 1966f3657fSopenharmony_ci#include "avcodec_list.h" 2066f3657fSopenharmony_ci#include "nlohmann/json.hpp" 2166f3657fSopenharmony_ci#include "screen.h" 2266f3657fSopenharmony_ci#include "histreamer_query_tool.h" 2366f3657fSopenharmony_ci 2466f3657fSopenharmony_ci#include "dscreen_constants.h" 2566f3657fSopenharmony_ci#include "dscreen_errcode.h" 2666f3657fSopenharmony_ci#include "dscreen_log.h" 2766f3657fSopenharmony_ci#include "dscreen_util.h" 2866f3657fSopenharmony_ci 2966f3657fSopenharmony_ciusing json = nlohmann::json; 3066f3657fSopenharmony_ci 3166f3657fSopenharmony_cinamespace OHOS { 3266f3657fSopenharmony_cinamespace DistributedHardware { 3366f3657fSopenharmony_cinamespace { 3466f3657fSopenharmony_ciconst std::string KEY_HISTREAMER_VIDEO_ENCODER = "histmVidEnc"; 3566f3657fSopenharmony_ciconst std::string KEY_HISTREAMER_VIDEO_DECODER = "histmVidDec"; 3666f3657fSopenharmony_ci} 3766f3657fSopenharmony_ciIMPLEMENT_SINGLE_INSTANCE(DScreenHandler); 3866f3657fSopenharmony_ci 3966f3657fSopenharmony_ciDScreenHandler::DScreenHandler() 4066f3657fSopenharmony_ci{ 4166f3657fSopenharmony_ci DHLOGI("DScreenHandler constructor."); 4266f3657fSopenharmony_ci} 4366f3657fSopenharmony_ci 4466f3657fSopenharmony_ciDScreenHandler::~DScreenHandler() 4566f3657fSopenharmony_ci{ 4666f3657fSopenharmony_ci DHLOGI("~DScreenHandler"); 4766f3657fSopenharmony_ci Rosen::ScreenManager::GetInstance().UnregisterScreenListener(screenListener_); 4866f3657fSopenharmony_ci} 4966f3657fSopenharmony_ci 5066f3657fSopenharmony_ciint32_t DScreenHandler::Initialize() 5166f3657fSopenharmony_ci{ 5266f3657fSopenharmony_ci DHLOGI("DScreenHandler Initialize"); 5366f3657fSopenharmony_ci if (screenListener_ == nullptr) { 5466f3657fSopenharmony_ci screenListener_ = new (std::nothrow) ScreenListener(); 5566f3657fSopenharmony_ci } 5666f3657fSopenharmony_ci Rosen::DMError ret = Rosen::ScreenManager::GetInstance().RegisterScreenListener(screenListener_); 5766f3657fSopenharmony_ci if (ret != Rosen::DMError::DM_OK) { 5866f3657fSopenharmony_ci DHLOGE("register screen listener failed."); 5966f3657fSopenharmony_ci return DSCREEN_INIT_ERR; 6066f3657fSopenharmony_ci } 6166f3657fSopenharmony_ci return DH_SUCCESS; 6266f3657fSopenharmony_ci} 6366f3657fSopenharmony_ci 6466f3657fSopenharmony_ciuint32_t ScreenListener::ByteCalculate(std::uint32_t screenWidth) 6566f3657fSopenharmony_ci{ 6666f3657fSopenharmony_ci if (screenWidth % BYTE_ALIGNMENT == 0) { 6766f3657fSopenharmony_ci return screenWidth; 6866f3657fSopenharmony_ci } 6966f3657fSopenharmony_ci uint32_t alignedInt = (screenWidth + BYTE_ALIGNMENT_CALCULATION) / BYTE_ALIGNMENT * BYTE_ALIGNMENT; 7066f3657fSopenharmony_ci return alignedInt; 7166f3657fSopenharmony_ci} 7266f3657fSopenharmony_ci 7366f3657fSopenharmony_civoid ScreenListener::OnConnect(uint64_t screenId) 7466f3657fSopenharmony_ci{ 7566f3657fSopenharmony_ci DHLOGI("on screen connect"); 7666f3657fSopenharmony_ci if (screenId != SCREEN_ID_DEFAULT) { 7766f3657fSopenharmony_ci DHLOGI("screenId is invalid, screenId is: %{public}" PRIu64, screenId); 7866f3657fSopenharmony_ci return; 7966f3657fSopenharmony_ci } 8066f3657fSopenharmony_ci sptr<Rosen::Screen> screen = Rosen::ScreenManager::GetInstance().GetScreenById(screenId); 8166f3657fSopenharmony_ci if (screen == nullptr) { 8266f3657fSopenharmony_ci DHLOGE("screen not found, screenId is: %{public}" PRIu64, screenId); 8366f3657fSopenharmony_ci return; 8466f3657fSopenharmony_ci } 8566f3657fSopenharmony_ci if (!screen->IsReal()) { 8666f3657fSopenharmony_ci DHLOGI("screen is not real"); 8766f3657fSopenharmony_ci return; 8866f3657fSopenharmony_ci } 8966f3657fSopenharmony_ci std::string dhId = DSCREEN_PREFIX + SEPERATOR + std::to_string(screenId); 9066f3657fSopenharmony_ci uint32_t screenWidth = screen->GetWidth(); 9166f3657fSopenharmony_ci screenWidth = ByteCalculate(screenWidth); 9266f3657fSopenharmony_ci uint32_t screenHeight = screen->GetHeight(); 9366f3657fSopenharmony_ci 9466f3657fSopenharmony_ci json attrJson; 9566f3657fSopenharmony_ci attrJson[KEY_VERSION] = DSCREEN_VERSION; 9666f3657fSopenharmony_ci attrJson[KEY_SCREEN_WIDTH] = screenWidth; 9766f3657fSopenharmony_ci attrJson[KEY_SCREEN_HEIGHT] = screenHeight; 9866f3657fSopenharmony_ci attrJson[KEY_CODECTYPE] = DScreenHandler::GetInstance().QueryCodecInfo(); 9966f3657fSopenharmony_ci std::string subtype = "screen"; 10066f3657fSopenharmony_ci 10166f3657fSopenharmony_ci DScreenHandler::GetInstance().PluginHardware(dhId, attrJson.dump(), subtype); 10266f3657fSopenharmony_ci} 10366f3657fSopenharmony_ci 10466f3657fSopenharmony_civoid ScreenListener::OnDisconnect(uint64_t screenId) 10566f3657fSopenharmony_ci{ 10666f3657fSopenharmony_ci DHLOGI("on screen disconnect"); 10766f3657fSopenharmony_ci std::string dhId = DSCREEN_PREFIX + SEPERATOR + std::to_string(screenId); 10866f3657fSopenharmony_ci DScreenHandler::GetInstance().UnPluginHardware(dhId); 10966f3657fSopenharmony_ci} 11066f3657fSopenharmony_ci 11166f3657fSopenharmony_civoid DScreenHandler::PluginHardware(const std::string &dhId, const std::string &attr, const std::string &subtype) 11266f3657fSopenharmony_ci{ 11366f3657fSopenharmony_ci DHLOGI("DScreenHandler PluginHardware"); 11466f3657fSopenharmony_ci if (listener_ != nullptr) { 11566f3657fSopenharmony_ci listener_->PluginHardware(dhId, attr, subtype); 11666f3657fSopenharmony_ci } 11766f3657fSopenharmony_ci} 11866f3657fSopenharmony_ci 11966f3657fSopenharmony_civoid DScreenHandler::UnPluginHardware(const std::string &dhId) 12066f3657fSopenharmony_ci{ 12166f3657fSopenharmony_ci DHLOGI("DScreenHandler UnPluginHardware"); 12266f3657fSopenharmony_ci if (listener_ != nullptr) { 12366f3657fSopenharmony_ci listener_->UnPluginHardware(dhId); 12466f3657fSopenharmony_ci } 12566f3657fSopenharmony_ci} 12666f3657fSopenharmony_ci 12766f3657fSopenharmony_cistd::vector<DHItem> DScreenHandler::QueryMeta() 12866f3657fSopenharmony_ci{ 12966f3657fSopenharmony_ci DHLOGI("DScreenHandler query meta hardware info"); 13066f3657fSopenharmony_ci return RealQuery(); 13166f3657fSopenharmony_ci} 13266f3657fSopenharmony_ci 13366f3657fSopenharmony_cistd::vector<DHItem> DScreenHandler::Query() 13466f3657fSopenharmony_ci{ 13566f3657fSopenharmony_ci DHLOGI("DScreenHandler query full hardware info"); 13666f3657fSopenharmony_ci return RealQuery(); 13766f3657fSopenharmony_ci} 13866f3657fSopenharmony_ci 13966f3657fSopenharmony_cistd::vector<DHItem> DScreenHandler::RealQuery() 14066f3657fSopenharmony_ci{ 14166f3657fSopenharmony_ci DHLOGI("DScreenHandler RealQuery"); 14266f3657fSopenharmony_ci std::vector<DHItem> dhItemVec; 14366f3657fSopenharmony_ci std::vector<sptr<Rosen::Screen>> screens; 14466f3657fSopenharmony_ci Rosen::ScreenManager::GetInstance().GetAllScreens(screens); 14566f3657fSopenharmony_ci DHLOGI("screens size is: %{public}zu", screens.size()); 14666f3657fSopenharmony_ci for (const auto &screen : screens) { 14766f3657fSopenharmony_ci if (screen == nullptr) { 14866f3657fSopenharmony_ci DHLOGE("screen is nullptr."); 14966f3657fSopenharmony_ci continue; 15066f3657fSopenharmony_ci } 15166f3657fSopenharmony_ci if (screen->GetWidth() <= 0) { 15266f3657fSopenharmony_ci continue; 15366f3657fSopenharmony_ci } 15466f3657fSopenharmony_ci if (!screen->IsReal()) { 15566f3657fSopenharmony_ci continue; 15666f3657fSopenharmony_ci } 15766f3657fSopenharmony_ci std::string dhId = DSCREEN_PREFIX + SEPERATOR + std::to_string(screen->GetId()); 15866f3657fSopenharmony_ci uint32_t screenWidth = screen->GetWidth(); 15966f3657fSopenharmony_ci if (screenListener_ == nullptr) { 16066f3657fSopenharmony_ci screenListener_ = new (std::nothrow) ScreenListener(); 16166f3657fSopenharmony_ci } 16266f3657fSopenharmony_ci screenWidth = screenListener_->ByteCalculate(screenWidth); 16366f3657fSopenharmony_ci uint32_t screenHeight = screen->GetHeight(); 16466f3657fSopenharmony_ci 16566f3657fSopenharmony_ci json attrJson; 16666f3657fSopenharmony_ci attrJson[KEY_VERSION] = DSCREEN_VERSION; 16766f3657fSopenharmony_ci attrJson[KEY_SCREEN_WIDTH] = screenWidth; 16866f3657fSopenharmony_ci attrJson[KEY_SCREEN_HEIGHT] = screenHeight; 16966f3657fSopenharmony_ci attrJson[KEY_CODECTYPE] = QueryCodecInfo(); 17066f3657fSopenharmony_ci std::string videoEncoders = 17166f3657fSopenharmony_ci HiStreamerQueryTool::GetInstance().QueryHiStreamerPluginInfo(HISTREAM_PLUGIN_TYPE::VIDEO_ENCODER); 17266f3657fSopenharmony_ci DHLOGI("DScreen QueryVideoEncoderAbility info: %{public}s", videoEncoders.c_str()); 17366f3657fSopenharmony_ci attrJson[KEY_HISTREAMER_VIDEO_ENCODER] = videoEncoders; 17466f3657fSopenharmony_ci std::string videoDecoders = 17566f3657fSopenharmony_ci HiStreamerQueryTool::GetInstance().QueryHiStreamerPluginInfo(HISTREAM_PLUGIN_TYPE::VIDEO_DECODER); 17666f3657fSopenharmony_ci DHLOGI("DScreen QueryVideoDecoderAbility info: %{public}s", videoDecoders.c_str()); 17766f3657fSopenharmony_ci attrJson[KEY_HISTREAMER_VIDEO_DECODER] = videoDecoders; 17866f3657fSopenharmony_ci 17966f3657fSopenharmony_ci DHItem dhItem; 18066f3657fSopenharmony_ci dhItem.dhId = dhId; 18166f3657fSopenharmony_ci dhItem.subtype = "screen"; 18266f3657fSopenharmony_ci dhItem.attrs = attrJson.dump(); 18366f3657fSopenharmony_ci dhItemVec.push_back(dhItem); 18466f3657fSopenharmony_ci DHLOGD("query result: dhId: %{public}s, attrs: %{public}s", dhId.c_str(), attrJson.dump().c_str()); 18566f3657fSopenharmony_ci } 18666f3657fSopenharmony_ci return dhItemVec; 18766f3657fSopenharmony_ci} 18866f3657fSopenharmony_ci 18966f3657fSopenharmony_cistd::map<std::string, std::string> DScreenHandler::QueryExtraInfo() 19066f3657fSopenharmony_ci{ 19166f3657fSopenharmony_ci DHLOGD("DScreenHandler queryExtraInfo"); 19266f3657fSopenharmony_ci std::map<std::string, std::string> extraInfo; 19366f3657fSopenharmony_ci return extraInfo; 19466f3657fSopenharmony_ci} 19566f3657fSopenharmony_ci 19666f3657fSopenharmony_cibool DScreenHandler::IsSupportPlugin() 19766f3657fSopenharmony_ci{ 19866f3657fSopenharmony_ci DHLOGD("DScreenHandler IsSupportPlugin"); 19966f3657fSopenharmony_ci return true; 20066f3657fSopenharmony_ci} 20166f3657fSopenharmony_ci 20266f3657fSopenharmony_civoid DScreenHandler::RegisterPluginListener(std::shared_ptr<PluginListener> listener) 20366f3657fSopenharmony_ci{ 20466f3657fSopenharmony_ci DHLOGD("DScreenHandler register plugin listener"); 20566f3657fSopenharmony_ci if (listener == nullptr) { 20666f3657fSopenharmony_ci DHLOGE("DScreenHandler unregistering plugin listener"); 20766f3657fSopenharmony_ci return; 20866f3657fSopenharmony_ci } 20966f3657fSopenharmony_ci listener_ = listener; 21066f3657fSopenharmony_ci} 21166f3657fSopenharmony_ci 21266f3657fSopenharmony_civoid DScreenHandler::UnRegisterPluginListener() 21366f3657fSopenharmony_ci{ 21466f3657fSopenharmony_ci DHLOGI("DScreenHandler unRegister plugin listener"); 21566f3657fSopenharmony_ci listener_ = nullptr; 21666f3657fSopenharmony_ci} 21766f3657fSopenharmony_ci 21866f3657fSopenharmony_cistd::string DScreenHandler::QueryCodecInfo() 21966f3657fSopenharmony_ci{ 22066f3657fSopenharmony_ci DHLOGD("DScreenHandler QueryCodecInfo"); 22166f3657fSopenharmony_ci if (!codecInfoStr_.empty()) { 22266f3657fSopenharmony_ci return codecInfoStr_; 22366f3657fSopenharmony_ci } 22466f3657fSopenharmony_ci 22566f3657fSopenharmony_ci // query codec info 22666f3657fSopenharmony_ci std::shared_ptr<MediaAVCodec::AVCodecList> codecList = MediaAVCodec::AVCodecListFactory::CreateAVCodecList(); 22766f3657fSopenharmony_ci if (codecList == nullptr) { 22866f3657fSopenharmony_ci DHLOGE("Create avCodecList failed."); 22966f3657fSopenharmony_ci return codecInfoStr_; 23066f3657fSopenharmony_ci } 23166f3657fSopenharmony_ci const std::vector<std::string> encoderName = {std::string(MediaAVCodec::CodecMimeType::VIDEO_AVC), 23266f3657fSopenharmony_ci std::string(MediaAVCodec::CodecMimeType::VIDEO_HEVC)}; 23366f3657fSopenharmony_ci json codecTypeArray = json::array(); 23466f3657fSopenharmony_ci 23566f3657fSopenharmony_ci for (const auto &coder : encoderName) { 23666f3657fSopenharmony_ci MediaAVCodec::CapabilityData *capData = codecList->GetCapability(coder, true, 23766f3657fSopenharmony_ci MediaAVCodec::AVCodecCategory::AVCODEC_HARDWARE); 23866f3657fSopenharmony_ci if (capData == nullptr) { 23966f3657fSopenharmony_ci continue; 24066f3657fSopenharmony_ci } 24166f3657fSopenharmony_ci std::string mimeType = capData->mimeType; 24266f3657fSopenharmony_ci codecTypeArray.push_back(mimeType); 24366f3657fSopenharmony_ci } 24466f3657fSopenharmony_ci 24566f3657fSopenharmony_ci codecInfoStr_ = codecTypeArray.dump(); 24666f3657fSopenharmony_ci return codecInfoStr_; 24766f3657fSopenharmony_ci} 24866f3657fSopenharmony_ci 24966f3657fSopenharmony_ciIHardwareHandler* GetHardwareHandler() 25066f3657fSopenharmony_ci{ 25166f3657fSopenharmony_ci DHLOGI("DScreenHandler::GetHardwareHandler"); 25266f3657fSopenharmony_ci return &DScreenHandler::GetInstance(); 25366f3657fSopenharmony_ci} 25466f3657fSopenharmony_ci} // namespace DistributedHardware 25566f3657fSopenharmony_ci} // namespace OHOS