1 /*
2 * Copyright (c) 2023 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 "rs_frame_rate_policy.h"
17
18 #include "modifier/rs_modifier_type.h"
19 #include "platform/common/rs_log.h"
20 #include "rs_trace.h"
21 #include "transaction/rs_interfaces.h"
22 #include "ui/rs_ui_director.h"
23
24 namespace OHOS {
25 namespace Rosen {
26 namespace {
27 constexpr float INCH_2_MM = 25.4f;
28 }
29
GetInstance()30 RSFrameRatePolicy* RSFrameRatePolicy::GetInstance()
31 {
32 static RSFrameRatePolicy instance;
33 return &instance;
34 }
35
~RSFrameRatePolicy()36 RSFrameRatePolicy::~RSFrameRatePolicy()
37 {
38 }
39
RegisterHgmConfigChangeCallback()40 void RSFrameRatePolicy::RegisterHgmConfigChangeCallback()
41 {
42 auto callback =
43 [this](std::shared_ptr<RSHgmConfigData> data) { this->RSFrameRatePolicy::HgmConfigChangeCallback(data); };
44 if (RSInterfaces::GetInstance().RegisterHgmConfigChangeCallback(callback) != NO_ERROR) {
45 ROSEN_LOGE("RegisterHgmConfigChangeCallback failed");
46 }
47 }
48
HgmConfigChangeCallback(std::shared_ptr<RSHgmConfigData> configData)49 void RSFrameRatePolicy::HgmConfigChangeCallback(std::shared_ptr<RSHgmConfigData> configData)
50 {
51 if (configData == nullptr) {
52 ROSEN_LOGE("RSFrameRatePolicy configData is null");
53 return;
54 }
55
56 auto data = configData->GetConfigData();
57 if (data.empty()) {
58 return;
59 }
60 {
61 std::lock_guard<std::mutex> lock(mutex_);
62 ppi_ = configData->GetPpi();
63 xDpi_ = configData->GetXDpi();
64 yDpi_ = configData->GetYDpi();
65 for (auto item : data) {
66 if (item.animType.empty() || item.animName.empty()) {
67 return;
68 }
69 animAttributes_[item.animType][item.animName] = {item.minSpeed, item.maxSpeed, item.preferredFps};
70 ROSEN_LOGD("RSFrameRatePolicy: config item type = %{public}s, name = %{public}s, "\
71 "minSpeed = %{public}d, maxSpeed = %{public}d, preferredFps = %{public}d",
72 item.animType.c_str(), item.animName.c_str(), static_cast<int>(item.minSpeed),
73 static_cast<int>(item.maxSpeed), static_cast<int>(item.preferredFps));
74 }
75 }
76 }
77
HgmRefreshRateModeChangeCallback(int32_t refreshRateMode)78 void RSFrameRatePolicy::HgmRefreshRateModeChangeCallback(int32_t refreshRateMode)
79 {
80 RSUIDirector::PostFrameRateTask([this, refreshRateMode]() {
81 ROSEN_LOGD("HgmRefreshRateModeChangeCallback refreshRateMode: %{public}d", refreshRateMode);
82 currentRefreshRateModeName_ = refreshRateMode;
83 });
84 }
85
GetRefreshRateModeName() const86 int32_t RSFrameRatePolicy::GetRefreshRateModeName() const
87 {
88 return currentRefreshRateModeName_;
89 }
90
GetPreferredFps(const std::string & scene,float speed)91 int32_t RSFrameRatePolicy::GetPreferredFps(const std::string& scene, float speed)
92 {
93 std::lock_guard<std::mutex> lock(mutex_);
94 if (animAttributes_.count(scene) == 0 || ppi_ == 0) {
95 return 0;
96 }
97 float speedMM = speed / ppi_ * INCH_2_MM;
98 const auto& attributes = animAttributes_[scene];
99 auto iter = std::find_if(attributes.begin(), attributes.end(), [&speedMM](const auto& pair) {
100 return speedMM >= pair.second.minSpeed && (speedMM < pair.second.maxSpeed ||
101 pair.second.maxSpeed == -1);
102 });
103 if (iter != attributes.end()) {
104 RS_TRACE_NAME_FMT("GetPreferredFps: scene: %s, speed: %f, rate: %d",
105 scene.c_str(), speedMM, iter->second.preferredFps);
106 return iter->second.preferredFps;
107 }
108 return 0;
109 }
110
GetExpectedFrameRate(const RSPropertyUnit unit,float velocity)111 int32_t RSFrameRatePolicy::GetExpectedFrameRate(const RSPropertyUnit unit, float velocity)
112 {
113 switch (unit) {
114 case RSPropertyUnit::PIXEL_POSITION:
115 return GetPreferredFps("translate", velocity);
116 case RSPropertyUnit::PIXEL_SIZE:
117 case RSPropertyUnit::RATIO_SCALE:
118 return GetPreferredFps("scale", velocity);
119 case RSPropertyUnit::ANGLE_ROTATION:
120 return GetPreferredFps("rotation", velocity);
121 default:
122 return 0;
123 }
124 }
125 } // namespace Rosen
126 } // namespace OHOS