• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 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 "updater_ui_config.h"
17 #include "common/screen.h"
18 #include "control/callback_manager.h"
19 #include "language/language_ui.h"
20 #include "layout/layout_parser.h"
21 #include "log/log.h"
22 #include "utils.h"
23 
24 namespace Updater {
25 namespace Fs = std::filesystem;
26 namespace {
27 constexpr auto UI_CFG_FILE = "/resources/pages/config.json";
28 constexpr auto UI_CFG_KEY = "config";
29 constexpr auto WIDTH_KEY = "screenWidth";
30 constexpr auto HEIGHT_KEY = "screenHeight";
31 constexpr auto FOCUS_CFG_FIELD = "enableFoucs";
32 
CanonicalPagePath(PagePath & pagePath)33 bool CanonicalPagePath(PagePath &pagePath)
34 {
35     if (!Utils::PathToRealPath(pagePath.dir, pagePath.dir)) {
36         LOG(ERROR) << "page path canonical failed, please check your config, dir = " << pagePath.dir;
37         return false;
38     }
39     for (auto &file : pagePath.pages) {
40         file = pagePath.dir + "/" + file;
41     }
42     return true;
43 }
44 
operator <<(std::ostream & os,const UxViewCommonInfo & info)45 std::ostream &operator<<(std::ostream &os, const UxViewCommonInfo &info)
46 {
47     os << "x=" << info.x << ", y=" << info.y << ", w=" << info.w << ", h=" << info.h << ", id=";
48     os << info.id << ", type=" << info.type << ", visible=" << info.visible;
49     return os;
50 }
51 
operator <<(std::ostream & os,const UxPageInfo & info)52 std::ostream &operator<<(std::ostream &os, const UxPageInfo &info)
53 {
54     LOG(INFO) << "page:" << info.id;
55     for (auto &it : info.viewInfos) {
56         LOG(INFO) << it.commonInfo;
57     }
58     return os;
59 }
60 
PrintInfoVec(const std::vector<UxPageInfo> & infoVec)61 void PrintInfoVec(const std::vector<UxPageInfo> &infoVec)
62 {
63     LOG(INFO) << "=====print start=====";
64     for (auto &iter : infoVec) {
65         LOG(INFO) << iter;
66     }
67     LOG(INFO) << "=====print end=====";
68 }
69 
SelectConfig(const JsonNode & node)70 std::string SelectConfig(const JsonNode &node)
71 {
72     using namespace OHOS;
73     for (const auto &iter : node) {
74         const JsonNode &subCfgPathNode = iter.get();
75         auto optStr = subCfgPathNode.As<std::string>();
76         if (!optStr.has_value()) {
77             LOG(ERROR) << "config array's element should be string";
78             return "";
79         }
80         std::string subConfigPath = *optStr;
81         const JsonNode &subCfg = JsonNode { Fs::path { subConfigPath }};
82         auto screenW = subCfg[WIDTH_KEY].As<int16_t>();
83         auto screenH = subCfg[HEIGHT_KEY].As<int16_t>();
84         if (!screenW.has_value() || !screenH.has_value()) {
85             LOG(ERROR) << "real config file should has screenW and screenH key";
86             return "";
87         }
88         if (screenW != Screen::GetInstance().GetWidth() || screenH != Screen::GetInstance().GetHeight()) {
89             LOG(INFO) << "screen size not matched" << subConfigPath;
90             continue;
91         }
92         LOG(INFO) << "select config: " << subConfigPath;
93         return subConfigPath;
94     }
95     LOG(ERROR) << "no config matched";
96     return "";
97 }
98 } // namespace
99 
100 bool UpdaterUiConfig::isFocusEnable_ {false};
101 
Init()102 bool UpdaterUiConfig::Init()
103 {
104     JsonNode node { Fs::path { UI_CFG_FILE }};
105     const JsonNode &cfgNode = node[UI_CFG_KEY];
106     switch (cfgNode.Type()) {
107         case NodeType::STRING: {
108             auto optString = cfgNode.As<std::string>();
109             if (!optString.has_value()) {
110                 LOG(ERROR) << "config path should be string";
111                 break;
112             }
113             JsonNode realNode { Fs::path { *optString }};
114             return Init(realNode);
115         }
116         case NodeType::ARRAY: {
117             std::string realConfig = SelectConfig(cfgNode);
118             if (realConfig.empty()) {
119                 break;
120             }
121             JsonNode realNode { Fs::path { realConfig }};
122             return Init(realNode);
123         }
124         default:
125             break;
126     }
127     LOG(ERROR) << "config file parse failed: " << UI_CFG_FILE;
128     return false;
129 }
130 
Init(const JsonNode & node)131 bool UpdaterUiConfig::Init(const JsonNode &node)
132 {
133     static bool res = [&node] () {
134         return LoadLangRes(node) && LoadStrategy(node) && LoadCallbacks(node) && LoadFocusCfg(node) && LoadPages(node);
135     } ();
136     return res;
137 }
138 
GetStrategy()139 const std::unordered_map<UpdaterMode, UiStrategyCfg> &UpdaterUiConfig::GetStrategy()
140 {
141     return UiStrategy::GetStrategy();
142 }
143 
GetFocusCfg()144 bool UpdaterUiConfig::GetFocusCfg()
145 {
146     return isFocusEnable_;
147 }
148 
LoadPages(const JsonNode & node)149 bool UpdaterUiConfig::LoadPages(const JsonNode &node)
150 {
151     PagePath pagePath {};
152     if (!Visit<SETVAL>(node, pagePath)) {
153         LOG(ERROR) << "parse page path error: " << pagePath.dir;
154         return false;
155     }
156 
157     if (!CanonicalPagePath(pagePath)) {
158         return false;
159     }
160 
161     std::vector<UxPageInfo> pageInfos {};
162     if (!LayoutParser::GetInstance().LoadLayout(pagePath.pages, pageInfos)) {
163         LOG(ERROR) << "load layout error: " << UI_CFG_FILE;
164         return false;
165     }
166     if (!PageManager::GetInstance().Init(pageInfos, pagePath.entry)) {
167         LOG(ERROR) << "page manager init error";
168         return false;
169     }
170     PrintInfoVec(pageInfos);
171     return true;
172 }
173 
LoadLangRes(const JsonNode & node)174 bool UpdaterUiConfig::LoadLangRes(const JsonNode &node)
175 {
176     return Lang::LanguageUI::GetInstance().LoadLangRes(node);
177 }
178 
LoadStrategy(const JsonNode & node)179 bool UpdaterUiConfig::LoadStrategy(const JsonNode &node)
180 {
181     return UiStrategy::LoadStrategy(node);
182 }
183 
LoadCallbacks(const JsonNode & node)184 bool UpdaterUiConfig::LoadCallbacks(const JsonNode &node)
185 {
186     return CallbackManager::LoadCallbacks(node);
187 }
188 
LoadFocusCfg(const JsonNode & node)189 bool UpdaterUiConfig::LoadFocusCfg(const JsonNode &node)
190 {
191     // disable focus by default
192     isFocusEnable_ = node[FOCUS_CFG_FIELD].As<bool>().value_or(false);
193     return true;
194 }
195 } // namespace Updater