1 /*
2 * Copyright (c) 2022-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 "platform/ohos/overdraw/rs_overdraw_controller.h"
17
18 #include <mutex>
19 #include <sstream>
20
21 #include "hilog/log.h"
22 #include "parameter.h"
23
24 #include "platform/common/rs_log.h"
25
26 namespace OHOS {
27 namespace Rosen {
28 namespace {
29 // param set debug.graphic.overdraw true/false
30 constexpr const char *SWITCH_TEXT = "debug.graphic.overdraw";
31 constexpr const char *SWITCH_ENABLE_TEXT = "true";
32 /* param set debug.graphic.colors_overdraw [color...]
33 * For Example:
34 * param set debug.graphic.colors_overdraw "0 0x220000ff 0x2200ff00 0x22ff0000 0x44ff0000"
35 * means:
36 * - Drawn Once Region: 0x00000000 (transparent)
37 * - Drawn Twice Region: 0x220000ff (alpha: 13% blue)
38 * - Drawn 3 Times Region: 0x2200ff00 (alpha: 13% green)
39 * - Drawn 4 Times Region: 0x22ff0000 (alpha: 13% red)
40 * - Drawn >= 5 Times Region: 0x44ff0000 (alpha: 26% red)
41 */
42 constexpr const char *COLOR_TEXT = "debug.graphic.colors_overdraw";
43 } // namespace
44
GetInstance()45 RSOverdrawController &RSOverdrawController::GetInstance()
46 {
47 static RSOverdrawController instance;
48 return instance;
49 }
50
SetDelegate(const std::shared_ptr<RSDelegate> & delegate)51 void RSOverdrawController::SetDelegate(const std::shared_ptr<RSDelegate> &delegate)
52 {
53 delegate_ = delegate;
54 }
55
IsEnabled() const56 bool RSOverdrawController::IsEnabled() const
57 {
58 return enabled_;
59 }
60
SetEnable(bool enable)61 void RSOverdrawController::SetEnable(bool enable)
62 {
63 if (enabled_ == enable) {
64 return ;
65 }
66 if (enable) {
67 SwitchFunction(SWITCH_TEXT, SWITCH_ENABLE_TEXT, this);
68 } else {
69 SwitchFunction(SWITCH_TEXT, "", this);
70 }
71 }
72
GetColorArray() const73 OverdrawColorArray RSOverdrawController::GetColorArray() const
74 {
75 std::lock_guard lock(colorMutex_);
76 return colorArray_;
77 }
78
GetColorMap() const79 std::map<int, Drawing::ColorQuad> RSOverdrawController::GetColorMap() const
80 {
81 std::lock_guard lock(colorMutex_);
82 return colorMap_;
83 }
84
RSOverdrawController()85 RSOverdrawController::RSOverdrawController()
86 {
87 char value[0x20];
88 GetParameter(SWITCH_TEXT, "false", value, sizeof(value));
89 SwitchFunction(SWITCH_TEXT, value, this);
90 WatchParameter(SWITCH_TEXT, SwitchFunction, this);
91 WatchParameter(COLOR_TEXT, OnColorChange, this);
92 }
93
SwitchFunction(const char * key,const char * value,void * context)94 void RSOverdrawController::SwitchFunction(const char *key, const char *value, void *context)
95 {
96 auto &that = *reinterpret_cast<RSOverdrawController *>(context);
97 auto oldEnable = that.enabled_;
98 if (strncmp(value, SWITCH_ENABLE_TEXT, strlen(SWITCH_ENABLE_TEXT)) == 0) {
99 that.enabled_ = true;
100 ROSEN_LOGI("%{public}s enable", key);
101 } else {
102 that.enabled_ = false;
103 ROSEN_LOGI("%{public}s disable", key);
104 }
105
106 if (oldEnable != that.enabled_ && that.delegate_ != nullptr) {
107 that.delegate_->Repaint();
108 }
109 }
110
OnColorChange(const char * key,const char * value,void * context)111 void RSOverdrawController::OnColorChange(const char *key, const char *value, void *context)
112 {
113 auto &that = *reinterpret_cast<RSOverdrawController *>(context);
114 std::stringstream ss(value);
115 std::vector<uint32_t> colors;
116 uint32_t color;
117 while (ss >> std::hex >> color) {
118 colors.push_back(color);
119 }
120
121 if (ss.eof() && colors != that.colors_ && colors.size() > 0) {
122 // array
123 OverdrawColorArray colorArray = that.colorArray_;
124 auto colorNumber = colorArray.size();
125 for (size_t i = 0; i < colors.size() && i + 1 < colorNumber; i++) {
126 colorArray[i + 1] = colors[i];
127 }
128 for (size_t i = colors.size(); i + 1 < colorNumber; i++) {
129 colorArray[i + 1] = colors.back();
130 }
131
132 // map
133 std::map<int, Drawing::ColorQuad> colorMap;
134 for (size_t i = 0; i < colors.size(); i++) {
135 colorMap[i + 1] = colors[i];
136 }
137 colorMap[0] = colors.back();
138
139 {
140 std::lock_guard lock(that.colorMutex_);
141 that.colorArray_ = colorArray;
142 that.colorMap_ = colorMap;
143 }
144
145 if (that.delegate_ != nullptr) {
146 that.delegate_->Repaint();
147 }
148 }
149 }
150 } // namespace Rosen
151 } // namespace OHOS
152