• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2024 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 #include "view_abstract.h"
16 
17 #include <regex>
18 
19 #include "cj_lambda.h"
20 
21 #include "base/geometry/calc_dimension.h"
22 #include "base/geometry/dimension.h"
23 #include "core/components_ng/base/view_abstract.h"
24 #include "core/components_ng/base/view_abstract_model.h"
25 #include "core/components_ng/base/view_stack_processor.h"
26 #include "core/components_v2/extensions/events/on_area_change_extension.h"
27 #include "core/gestures/long_press_gesture.h"
28 #include "core/pipeline/base/constants.h"
29 
30 using namespace OHOS::Ace;
31 using namespace OHOS::Ace::Framework;
32 
33 namespace OHOS::Ace::Framework {
34 namespace {
35 const char DEFAULT_HAR_BUNDLE_NAME[] = "__harDefaultBundleName__";
36 const char DEFAULT_HAR_MODULE_NAME[] = "__harDefaultModuleName__";
37 const std::regex RESOURCE_APP_STRING_PLACEHOLDER(R"(\%((\d+)(\$)){0,1}([dsf]))", std::regex::icase);
38 const std::regex FLOAT_PATTERN(R"(-?(0|[1-9]\d*)(\.\d+))", std::regex::icase);
39 const std::string RESOURCE_TOKEN_PATTERN = "(app|sys|\\[.+?\\])\\.(\\S+?)\\.(\\S+)";
40 const std::string RESOURCE_NAME_PATTERN = "\\[(.+?)\\]";
41 constexpr int32_t UNKNOWN_RESOURCE_ID = -1;
42 constexpr int32_t UNKNOWN_RESOURCE_TYPE = -1;
43 constexpr uint32_t COLOR_ALPHA_OFFSET = 24;
44 constexpr uint32_t COLOR_ALPHA_VALUE = 0xFF000000;
45 
ColorAlphaAdapt(uint32_t origin)46 uint32_t ColorAlphaAdapt(uint32_t origin)
47 {
48     uint32_t result = origin;
49     if ((origin >> COLOR_ALPHA_OFFSET) == 0) {
50         result = origin | COLOR_ALPHA_VALUE;
51     }
52     return result;
53 }
54 
GetBundleNameFromContainer()55 std::string GetBundleNameFromContainer()
56 {
57     auto container = Container::Current();
58     CHECK_NULL_RETURN(container, "");
59     return container->GetBundleName();
60 }
61 
GetModuleNameFromContainer()62 std::string GetModuleNameFromContainer()
63 {
64     auto container = Container::Current();
65     CHECK_NULL_RETURN(container, "");
66     return container->GetModuleName();
67 }
68 
CompleteResourceObjectFromParams(int32_t resId,NativeResourceObject & obj,std::string & targetModule,ResourceType & resType,std::string & resName)69 void CompleteResourceObjectFromParams(
70     int32_t resId, NativeResourceObject& obj, std::string& targetModule, ResourceType& resType, std::string& resName)
71 {
72     auto params = JsonUtil::ParseJsonString(obj.paramsJsonStr);
73     if (!params->IsArray()) {
74         LOGE("Resource params type error.");
75         return;
76     }
77     if (resId != UNKNOWN_RESOURCE_ID) {
78         return;
79     }
80     auto identityValue = params->GetArrayItem(0);
81     if (!identityValue->IsString()) {
82         return;
83     }
84     auto identity = identityValue->GetString();
85     if (!ViewAbstract::ParseDollarResource(
86             identity, targetModule, resType, resName, obj.type == UNKNOWN_RESOURCE_TYPE)) {
87         return;
88     }
89     std::regex resNameRegex(RESOURCE_NAME_PATTERN);
90     std::smatch resNameResults;
91     if (std::regex_match(targetModule, resNameResults, resNameRegex)) {
92         obj.moduleName = std::string(resNameResults[1]).c_str();
93     }
94     if (obj.type == UNKNOWN_RESOURCE_TYPE) {
95         obj.type = static_cast<int32_t>(resType);
96     }
97 }
98 
GetReplaceContentStr(int pos,const std::string & type,std::unique_ptr<JsonValue> & params,int32_t containCount)99 std::string GetReplaceContentStr(
100     int pos, const std::string& type, std::unique_ptr<JsonValue>& params, int32_t containCount)
101 {
102     auto index = pos + containCount;
103     if (index < 0) {
104         return std::string();
105     }
106     auto item = params->GetArrayItem(index);
107     if (type == "d") {
108         if (item->IsNumber()) {
109             return std::to_string(item->GetInt());
110         }
111     } else if (type == "s") {
112         if (item->IsString()) {
113             return item->GetString();
114         }
115     } else if (type == "f") {
116         if (item->IsNumber()) {
117             return std::to_string(item->GetDouble());
118         }
119     }
120     return std::string();
121 }
122 
ReplaceHolder(std::string & originStr,std::unique_ptr<JsonValue> & params,int32_t containCount)123 void ReplaceHolder(std::string& originStr, std::unique_ptr<JsonValue>& params, int32_t containCount)
124 {
125     auto size = params->GetArraySize();
126     if (containCount == size) {
127         return;
128     }
129     std::string::const_iterator start = originStr.begin();
130     std::string::const_iterator end = originStr.end();
131     std::smatch matches;
132     bool shortHolderType = false;
133     bool firstMatch = true;
134     int searchTime = 0;
135     while (std::regex_search(start, end, matches, RESOURCE_APP_STRING_PLACEHOLDER)) {
136         std::string pos = matches[2];
137         std::string type = matches[4];
138         if (firstMatch) {
139             firstMatch = false;
140             shortHolderType = pos.length() == 0;
141         } else {
142             if (shortHolderType ^ (pos.length() == 0)) {
143                 return;
144             }
145         }
146 
147         std::string replaceContentStr;
148         if (shortHolderType) {
149             replaceContentStr = GetReplaceContentStr(searchTime, type, params, containCount);
150         } else {
151             replaceContentStr = GetReplaceContentStr(StringUtils::StringToInt(pos) - 1, type, params, containCount);
152         }
153 
154         originStr.replace(matches[0].first - originStr.begin(), matches[0].length(), replaceContentStr);
155         start = originStr.begin() + matches.prefix().length() + replaceContentStr.length();
156         end = originStr.end();
157         searchTime++;
158     }
159 }
160 } // namespace
161 
GetResourceObject(const NativeResourceObject & obj)162 RefPtr<ResourceObject> GetResourceObject(const NativeResourceObject& obj)
163 {
164     auto params = JsonUtil::ParseJsonString(obj.paramsJsonStr);
165     if (!params->IsArray()) {
166         return nullptr;
167     }
168     std::vector<ResourceObjectParams> resObjParamsList;
169     auto size = params->GetArraySize();
170     for (int32_t i = 0; i < size; i++) {
171         auto item = params->GetArrayItem(i);
172         ResourceObjectParams resObjParams {};
173         if (item->IsString()) {
174             resObjParams.value = item->GetString();
175             resObjParams.type = ResourceObjectParamType::STRING;
176         } else if (item->IsNumber()) {
177             if (std::regex_match(std::to_string(item->GetDouble()), FLOAT_PATTERN)) {
178                 resObjParams.value = std::to_string(item->GetDouble());
179                 resObjParams.type = ResourceObjectParamType::FLOAT;
180             } else {
181                 resObjParams.value = std::to_string(item->GetInt());
182                 resObjParams.type = ResourceObjectParamType::INT;
183             }
184         }
185         resObjParamsList.push_back(resObjParams);
186     }
187     auto resourceObject = AceType::MakeRefPtr<ResourceObject>(
188         obj.id, obj.type, resObjParamsList, obj.bundleName, obj.moduleName, Container::CurrentIdSafely());
189     return resourceObject;
190 }
191 
GetResourceObjectByBundleAndModule(const NativeResourceObject & obj)192 RefPtr<ResourceObject> GetResourceObjectByBundleAndModule(const NativeResourceObject& obj)
193 {
194     auto resourceObject =
195         AceType::MakeRefPtr<ResourceObject>(obj.bundleName, obj.moduleName, Container::CurrentIdSafely());
196     return resourceObject;
197 }
198 
CreateResourceWrapper(const NativeResourceObject & obj,RefPtr<ResourceObject> & resourceObject)199 RefPtr<ResourceWrapper> CreateResourceWrapper(const NativeResourceObject& obj, RefPtr<ResourceObject>& resourceObject)
200 {
201     RefPtr<ResourceAdapter> resourceAdapter = nullptr;
202     RefPtr<ThemeConstants> themeConstants = nullptr;
203     if (SystemProperties::GetResourceDecoupling()) {
204         resourceAdapter = ResourceManager::GetInstance().GetOrCreateResourceAdapter(resourceObject);
205         if (!resourceAdapter) {
206             return nullptr;
207         }
208     } else {
209         themeConstants = ViewAbstract::GetThemeConstants(obj.bundleName, obj.moduleName);
210         if (!themeConstants) {
211             return nullptr;
212         }
213     }
214     auto resourceWrapper = AceType::MakeRefPtr<ResourceWrapper>(themeConstants, resourceAdapter);
215     return resourceWrapper;
216 }
217 
CreateResourceWrapper()218 RefPtr<ResourceWrapper> CreateResourceWrapper()
219 {
220     RefPtr<ResourceAdapter> resourceAdapter = nullptr;
221     RefPtr<ThemeConstants> themeConstants = nullptr;
222     if (SystemProperties::GetResourceDecoupling()) {
223         resourceAdapter = ResourceManager::GetInstance().GetResourceAdapter(Container::CurrentIdSafely());
224         if (!resourceAdapter) {
225             return nullptr;
226         }
227     } else {
228         themeConstants = ViewAbstract::GetThemeConstants();
229         if (!themeConstants) {
230             return nullptr;
231         }
232     }
233     auto resourceWrapper = AceType::MakeRefPtr<ResourceWrapper>(themeConstants, resourceAdapter);
234     return resourceWrapper;
235 }
236 
GetThemeConstants(const std::string & bundleName,const std::string & moduleName)237 RefPtr<ThemeConstants> ViewAbstract::GetThemeConstants(const std::string& bundleName, const std::string& moduleName)
238 {
239     auto currentObj = Container::Current();
240     if (!currentObj) {
241         LOGW("container is null");
242         return nullptr;
243     }
244     auto pipelineContext = currentObj->GetPipelineContext();
245     if (!pipelineContext) {
246         LOGE("pipeline context is null!");
247         return nullptr;
248     }
249     auto themeManager = pipelineContext->GetThemeManager();
250     if (!themeManager) {
251         LOGE("theme manager is null!");
252         return nullptr;
253     }
254     return themeManager->GetThemeConstants(bundleName, moduleName);
255 }
256 
CjEnabled(bool enabled)257 void ViewAbstract::CjEnabled(bool enabled)
258 {
259     ViewAbstractModel::GetInstance()->SetEnabled(enabled);
260 }
261 
CompleteResourceObject(NativeResourceObject & obj,std::string & bundleName,std::string & moduleName)262 void ViewAbstract::CompleteResourceObject(NativeResourceObject& obj, std::string& bundleName, std::string& moduleName)
263 {
264     int32_t resId = UNKNOWN_RESOURCE_ID;
265     CompleteResourceObjectInner(obj, bundleName, moduleName, resId);
266 }
267 
CompleteResourceObjectWithBundleName(NativeResourceObject & obj,std::string & bundleName,std::string & moduleName,int32_t & resId)268 void ViewAbstract::CompleteResourceObjectWithBundleName(
269     NativeResourceObject& obj, std::string& bundleName, std::string& moduleName, int32_t& resId)
270 {
271     CompleteResourceObjectInner(obj, bundleName, moduleName, resId);
272 }
273 
CompleteResourceObjectInner(NativeResourceObject & obj,std::string & bundleName,std::string & moduleName,int32_t & resIdValue)274 void ViewAbstract::CompleteResourceObjectInner(
275     NativeResourceObject& obj, std::string& bundleName, std::string& moduleName, int32_t& resIdValue)
276 {
277     ResourceType resType;
278     std::string targetModule;
279     std::string resName;
280     resIdValue = obj.id;
281     if (resIdValue == UNKNOWN_RESOURCE_ID) {
282         CompleteResourceObjectFromParams(resIdValue, obj, targetModule, resType, resName);
283     }
284     bundleName = obj.bundleName;
285     moduleName = obj.moduleName;
286 
287     if ((bundleName.empty() && !moduleName.empty()) || bundleName == DEFAULT_HAR_BUNDLE_NAME) {
288         bundleName = GetBundleNameFromContainer();
289         obj.bundleName = bundleName.c_str();
290     }
291     if (moduleName == DEFAULT_HAR_MODULE_NAME) {
292         moduleName = GetModuleNameFromContainer();
293         obj.moduleName = moduleName.c_str();
294     }
295 }
296 
ConvertResourceType(const std::string & typeName,ResourceType & resType)297 bool ViewAbstract::ConvertResourceType(const std::string& typeName, ResourceType& resType)
298 {
299     static const std::unordered_map<std::string, ResourceType> resTypeMap {
300         { "color", ResourceType::COLOR },
301         { "media", ResourceType::MEDIA },
302         { "float", ResourceType::FLOAT },
303         { "string", ResourceType::STRING },
304         { "plural", ResourceType::PLURAL },
305         { "pattern", ResourceType::PATTERN },
306         { "boolean", ResourceType::BOOLEAN },
307         { "integer", ResourceType::INTEGER },
308         { "strarray", ResourceType::STRARRAY },
309         { "intarray", ResourceType::INTARRAY },
310         { "symbol", ResourceType::SYMBOL },
311     };
312     auto it = resTypeMap.find(typeName);
313     if (it == resTypeMap.end()) {
314         return false;
315     }
316     resType = it->second;
317     return true;
318 }
319 
ParseDollarResource(const std::string & resPath,std::string & targetModule,ResourceType & resType,std::string & resName,bool isParseType)320 bool ViewAbstract::ParseDollarResource(const std::string& resPath, std::string& targetModule, ResourceType& resType,
321     std::string& resName, bool isParseType)
322 {
323     std::smatch results;
324     std::regex tokenRegex(RESOURCE_TOKEN_PATTERN);
325     if (!std::regex_match(resPath, results, tokenRegex)) {
326         return false;
327     }
328     targetModule = results[1];
329     std::string typeName = results[2];
330     if (isParseType && !ConvertResourceType(typeName, resType)) {
331         return false;
332     }
333     resName = resPath;
334     return true;
335 }
336 
ParseCjString(NativeResourceObject & obj,std::string & result)337 bool ViewAbstract::ParseCjString(NativeResourceObject& obj, std::string& result)
338 {
339     std::string bundleName;
340     std::string moduleName;
341     CompleteResourceObject(obj, bundleName, moduleName);
342     if (obj.type == UNKNOWN_RESOURCE_TYPE) {
343         return false;
344     }
345     auto resourceObject = GetResourceObjectByBundleAndModule(obj);
346     auto resourceWrapper = CreateResourceWrapper(obj, resourceObject);
347     if (!resourceWrapper) {
348         return false;
349     }
350     auto params = JsonUtil::ParseJsonString(obj.paramsJsonStr);
351     if (!params->IsArray()) {
352         LOGE("Resource params type error.");
353         return false;
354     }
355     if (obj.id == UNKNOWN_RESOURCE_ID) {
356         if (!obj.paramsJsonStr) {
357             return false;
358         }
359         auto param = params->GetArrayItem(0);
360         if (obj.type == static_cast<int32_t>(ResourceType::STRING)) {
361             auto originStr = resourceWrapper->GetStringByName(param->GetString());
362             ReplaceHolder(originStr, params, 1);
363             result = originStr;
364         } else if (obj.type == static_cast<int32_t>(ResourceType::PLURAL)) {
365             auto countVal = params->GetArrayItem(1);
366             if (!countVal->IsNumber()) {
367                 return false;
368             }
369             int count = countVal->GetInt();
370             auto pluralStr = resourceWrapper->GetPluralStringByName(param->GetString(), count);
371             ReplaceHolder(pluralStr, params, 2);
372             result = pluralStr;
373         } else {
374             return false;
375         }
376         return true;
377     }
378     if (obj.type == static_cast<int32_t>(ResourceType::STRING)) {
379         auto originStr = resourceWrapper->GetString(static_cast<uint32_t>(obj.id));
380         ReplaceHolder(originStr, params, 0);
381         result = originStr;
382     } else if (obj.type == static_cast<int32_t>(ResourceType::PLURAL)) {
383         auto countVal = params->GetArrayItem(0);
384         if (!countVal->IsNumber()) {
385             return false;
386         }
387         int count = countVal->GetInt();
388         auto pluralStr = resourceWrapper->GetPluralString(static_cast<uint32_t>(obj.id), count);
389         ReplaceHolder(pluralStr, params, 1);
390         result = pluralStr;
391     } else if (obj.type == static_cast<int32_t>(ResourceType::FLOAT)) {
392         result = std::to_string(resourceWrapper->GetDouble(static_cast<uint32_t>(obj.id)));
393     } else if (obj.type == static_cast<int32_t>(ResourceType::INTEGER)) {
394         result = std::to_string(resourceWrapper->GetInt(static_cast<uint32_t>(obj.id)));
395     } else {
396         return false;
397     }
398     return true;
399 }
400 
ParseCjMedia(NativeResourceObject & obj,std::string & result)401 bool ViewAbstract::ParseCjMedia(NativeResourceObject& obj, std::string& result)
402 {
403     std::string bundleName;
404     std::string moduleName;
405     CompleteResourceObject(obj, bundleName, moduleName);
406     return ParseCjMediaInternal(obj, result);
407 }
408 
ParseCjMediaInternal(NativeResourceObject & obj,std::string & result)409 bool ViewAbstract::ParseCjMediaInternal(NativeResourceObject& obj, std::string& result)
410 {
411     if (obj.type == UNKNOWN_RESOURCE_TYPE) {
412         return false;
413     }
414     auto resourceObject = GetResourceObjectByBundleAndModule(obj);
415     auto resourceWrapper = CreateResourceWrapper(obj, resourceObject);
416     if (!resourceWrapper) {
417         return false;
418     }
419     if (obj.type == static_cast<int32_t>(ResourceType::RAWFILE)) {
420         auto params = JsonUtil::ParseJsonString(obj.paramsJsonStr);
421         if (!params->IsArray()) {
422             return false;
423         }
424         auto param = params->GetArrayItem(0);
425         if (!param->IsString()) {
426             return false;
427         }
428         auto fileName = param->GetString();
429         result = resourceWrapper->GetRawfile(fileName);
430         return true;
431     }
432     if (obj.id == -1) {
433         if (!obj.paramsJsonStr) {
434             return false;
435         }
436         auto params = JsonUtil::ParseJsonString(obj.paramsJsonStr);
437         if (!params->IsArray()) {
438             return false;
439         }
440         auto param = params->GetArrayItem(0);
441         if (obj.type == static_cast<int32_t>(ResourceType::MEDIA)) {
442             result = resourceWrapper->GetMediaPathByName(param->GetString());
443             return true;
444         }
445         if (obj.type == static_cast<int32_t>(ResourceType::STRING)) {
446             result = resourceWrapper->GetStringByName(param->GetString());
447             return true;
448         }
449         return false;
450     } else if (obj.type == static_cast<int32_t>(ResourceType::MEDIA)) {
451         result = resourceWrapper->GetMediaPath(static_cast<uint32_t>(obj.id));
452         return true;
453     } else if (obj.type == static_cast<int32_t>(ResourceType::STRING)) {
454         result = resourceWrapper->GetString(static_cast<uint32_t>(obj.id));
455         return true;
456     }
457     return false;
458 }
459 
ParseCjSymbolId(NativeResourceObject & obj,uint32_t & result)460 bool ViewAbstract::ParseCjSymbolId(NativeResourceObject& obj, uint32_t& result)
461 {
462     std::string bundleName;
463     std::string moduleName;
464     CompleteResourceObject(obj, bundleName, moduleName);
465     if (obj.type == UNKNOWN_RESOURCE_TYPE) {
466         return false;
467     }
468     auto resourceObject = GetResourceObjectByBundleAndModule(obj);
469     auto resourceWrapper = CreateResourceWrapper(obj, resourceObject);
470     if (!resourceWrapper) {
471         return false;
472     }
473     if (obj.id == -1) {
474         if (!obj.paramsJsonStr) {
475             return false;
476         }
477         auto params = JsonUtil::ParseJsonString(obj.paramsJsonStr);
478         if (!params->IsArray()) {
479             return false;
480         }
481         auto param = params->GetArrayItem(0);
482         auto symbol = resourceWrapper->GetSymbolByName(param->GetString().c_str());
483         if (!symbol) {
484             return false;
485         }
486         result = symbol;
487         return true;
488     }
489     if (obj.type == static_cast<int32_t>(ResourceType::SYMBOL)) {
490         result = resourceWrapper->GetSymbolById(static_cast<uint32_t>(obj.id));
491         return true;
492     }
493     return false;
494 }
495 
ParseCjColor(NativeResourceObject & obj,Color & result)496 bool ViewAbstract::ParseCjColor(NativeResourceObject& obj, Color& result)
497 {
498     std::string bundleName;
499     std::string moduleName;
500     CompleteResourceObject(obj, bundleName, moduleName);
501     if (obj.type == UNKNOWN_RESOURCE_TYPE) {
502         return false;
503     }
504     auto resourceObject = GetResourceObjectByBundleAndModule(obj);
505     auto resourceWrapper = CreateResourceWrapper(obj, resourceObject);
506     if (!resourceWrapper) {
507         return false;
508     }
509     if (obj.id == -1) {
510         if (!obj.paramsJsonStr) {
511             return false;
512         }
513         auto params = JsonUtil::ParseJsonString(obj.paramsJsonStr);
514         if (!params->IsArray()) {
515             return false;
516         }
517         auto param = params->GetArrayItem(0);
518         result = resourceWrapper->GetColorByName(param->GetString());
519         return true;
520     }
521     if (obj.type == static_cast<int32_t>(ResourceType::STRING)) {
522         auto value = resourceWrapper->GetString(static_cast<uint32_t>(obj.id));
523         return Color::ParseColorString(value, result);
524     }
525     if (obj.type == static_cast<int32_t>(ResourceType::INTEGER)) {
526         auto value = resourceWrapper->GetInt(static_cast<uint32_t>(obj.id));
527         result = Color(ColorAlphaAdapt(value));
528         return true;
529     }
530     if (obj.type == static_cast<int32_t>(ResourceType::COLOR)) {
531         result = resourceWrapper->GetColor(static_cast<uint32_t>(obj.id));
532         result.SetResourceId(static_cast<uint32_t>(obj.id));
533         return true;
534     }
535     return false;
536 }
537 
ParseCjDimension(NativeResourceObject & obj,CalcDimension & result,DimensionUnit defaultUnit,bool isSupportPercent)538 bool ViewAbstract::ParseCjDimension(
539     NativeResourceObject& obj, CalcDimension& result, DimensionUnit defaultUnit, bool isSupportPercent)
540 {
541     std::string bundleName;
542     std::string moduleName;
543     CompleteResourceObject(obj, bundleName, moduleName);
544     if (obj.type == UNKNOWN_RESOURCE_TYPE) {
545         return false;
546     }
547     auto resourceObject = GetResourceObjectByBundleAndModule(obj);
548     auto resourceWrapper = CreateResourceWrapper(obj, resourceObject);
549     if (!resourceWrapper) {
550         return false;
551     }
552     if (obj.id == -1) {
553         if (!obj.paramsJsonStr) {
554             return false;
555         }
556         auto params = JsonUtil::ParseJsonString(obj.paramsJsonStr);
557         if (!params->IsArray()) {
558             return false;
559         }
560         auto param = params->GetArrayItem(0);
561         if (obj.type == static_cast<int32_t>(ResourceType::STRING)) {
562             auto value = resourceWrapper->GetStringByName(param->GetString());
563             return StringUtils::StringToCalcDimensionNG(value, result, false, defaultUnit);
564         }
565         if (obj.type == static_cast<int32_t>(ResourceType::INTEGER)) {
566             auto value = std::to_string(resourceWrapper->GetIntByName(param->GetString()));
567             return StringUtils::StringToDimensionWithUnitNG(value, result, defaultUnit);
568         }
569         result = resourceWrapper->GetDimensionByName(param->GetString());
570         return true;
571     }
572     if (obj.type == static_cast<int32_t>(ResourceType::STRING)) {
573         auto value = resourceWrapper->GetString(static_cast<uint32_t>(obj.id));
574         return StringUtils::StringToCalcDimensionNG(value, result, false, defaultUnit);
575     }
576     if (obj.type == static_cast<int32_t>(ResourceType::INTEGER)) {
577         auto value = std::to_string(resourceWrapper->GetInt(static_cast<uint32_t>(obj.id)));
578         return StringUtils::StringToDimensionWithUnitNG(value, result, defaultUnit);
579     }
580     if (obj.type == static_cast<int32_t>(ResourceType::FLOAT)) {
581         result = resourceWrapper->GetDimension(static_cast<uint32_t>(obj.id));
582         return true;
583     }
584     return false;
585 }
586 
ParseCjDimensionVP(NativeResourceObject & obj,CalcDimension & result,bool isSupportPercent)587 bool ViewAbstract::ParseCjDimensionVP(NativeResourceObject& obj, CalcDimension& result, bool isSupportPercent)
588 {
589     return ParseCjDimension(obj, result, DimensionUnit::VP, isSupportPercent);
590 }
591 
ParseCjDimensionFP(NativeResourceObject & obj,CalcDimension & result,bool isSupportPercent)592 bool ViewAbstract::ParseCjDimensionFP(NativeResourceObject& obj, CalcDimension& result, bool isSupportPercent)
593 {
594     return ParseCjDimension(obj, result, DimensionUnit::FP, isSupportPercent);
595 }
596 
ParseCjDouble(NativeResourceObject & obj,double & result)597 bool ViewAbstract::ParseCjDouble(NativeResourceObject& obj, double& result)
598 {
599     std::string bundleName;
600     std::string moduleName;
601     CompleteResourceObject(obj, bundleName, moduleName);
602     if (obj.type == UNKNOWN_RESOURCE_TYPE) {
603         return false;
604     }
605     auto resourceObject = GetResourceObjectByBundleAndModule(obj);
606     auto resourceWrapper = CreateResourceWrapper(obj, resourceObject);
607     if (!resourceWrapper) {
608         return false;
609     }
610     if (obj.id == -1) {
611         if (!obj.paramsJsonStr) {
612             return false;
613         }
614         auto params = JsonUtil::ParseJsonString(obj.paramsJsonStr);
615         if (!params->IsArray()) {
616             return false;
617         }
618         auto param = params->GetArrayItem(0);
619         if (obj.type == static_cast<int32_t>(ResourceType::STRING)) {
620             auto value = resourceWrapper->GetStringByName(param->GetString());
621             return StringUtils::StringToDouble(value, result);
622         }
623         if (obj.type == static_cast<int32_t>(ResourceType::FLOAT)) {
624             result = resourceWrapper->GetDoubleByName(param->GetString());
625             return true;
626         }
627         if (obj.type == static_cast<int32_t>(ResourceType::INTEGER)) {
628             result = resourceWrapper->GetIntByName(param->GetString());
629             return true;
630         }
631         return false;
632     }
633     if (obj.type == static_cast<int32_t>(ResourceType::STRING)) {
634         auto value = resourceWrapper->GetString(static_cast<uint32_t>(obj.id));
635         return StringUtils::StringToDouble(value, result);
636     }
637     if (obj.type == static_cast<int32_t>(ResourceType::FLOAT)) {
638         result = resourceWrapper->GetDouble(static_cast<uint32_t>(obj.id));
639         return true;
640     }
641     if (obj.type == static_cast<int32_t>(ResourceType::INTEGER)) {
642         result = resourceWrapper->GetInt(static_cast<uint32_t>(obj.id));
643         return true;
644     }
645     return false;
646 }
647 
ParseCjInteger(NativeResourceObject & obj,int32_t & result)648 bool ViewAbstract::ParseCjInteger(NativeResourceObject& obj, int32_t& result)
649 {
650     return ParseCjInteger<int32_t>(obj, result);
651 }
652 
ParseCjInteger(NativeResourceObject & obj,uint32_t & result)653 bool ViewAbstract::ParseCjInteger(NativeResourceObject& obj, uint32_t& result)
654 {
655     return ParseCjInteger<uint32_t>(obj, result);
656 }
657 
ParseCjBool(NativeResourceObject & obj,bool & result)658 bool ViewAbstract::ParseCjBool(NativeResourceObject& obj, bool& result)
659 {
660     std::string bundleName;
661     std::string moduleName;
662     CompleteResourceObject(obj, bundleName, moduleName);
663     if (obj.type == UNKNOWN_RESOURCE_TYPE) {
664         return false;
665     }
666     auto resourceObject = GetResourceObjectByBundleAndModule(obj);
667     auto resourceWrapper = CreateResourceWrapper(obj, resourceObject);
668     if (!resourceWrapper) {
669         return false;
670     }
671     if (obj.id == -1) {
672         if (!obj.paramsJsonStr) {
673             return false;
674         }
675         auto params = JsonUtil::ParseJsonString(obj.paramsJsonStr);
676         if (!params->IsArray()) {
677             return false;
678         }
679         auto param = params->GetArrayItem(0);
680         if (obj.type == static_cast<int32_t>(ResourceType::BOOLEAN)) {
681             result = resourceWrapper->GetBooleanByName(param->GetString());
682             return true;
683         }
684         return false;
685     }
686 
687     if (obj.type == static_cast<int32_t>(ResourceType::BOOLEAN)) {
688         result = resourceWrapper->GetBoolean(static_cast<uint32_t>(obj.id));
689         return true;
690     }
691     return false;
692 }
693 
ParseCjIntegerArray(NativeResourceObject & obj,std::vector<uint32_t> & result)694 bool ViewAbstract::ParseCjIntegerArray(NativeResourceObject& obj, std::vector<uint32_t>& result)
695 {
696     std::string bundleName;
697     std::string moduleName;
698     CompleteResourceObject(obj, bundleName, moduleName);
699     if (obj.type == UNKNOWN_RESOURCE_TYPE) {
700         return false;
701     }
702     auto resourceObject = GetResourceObjectByBundleAndModule(obj);
703     auto resourceWrapper = CreateResourceWrapper(obj, resourceObject);
704     if (!resourceWrapper) {
705         return false;
706     }
707     if (obj.id == -1) {
708         if (!obj.paramsJsonStr) {
709             return false;
710         }
711         auto params = JsonUtil::ParseJsonString(obj.paramsJsonStr);
712         if (!params->IsArray()) {
713             return false;
714         }
715         auto param = params->GetArrayItem(0);
716         if (obj.type == static_cast<int32_t>(ResourceType::INTARRAY)) {
717             result = resourceWrapper->GetIntArrayByName(param->GetString());
718             return true;
719         }
720         return false;
721     }
722     if (obj.type == static_cast<int32_t>(ResourceType::INTARRAY)) {
723         result = resourceWrapper->GetIntArray(static_cast<uint32_t>(obj.id));
724         return true;
725     }
726     return false;
727 }
728 
ParseCjStringArray(NativeResourceObject & obj,std::vector<std::string> & result)729 bool ViewAbstract::ParseCjStringArray(NativeResourceObject& obj, std::vector<std::string>& result)
730 {
731     std::string bundleName;
732     std::string moduleName;
733     CompleteResourceObject(obj, bundleName, moduleName);
734     if (obj.type == UNKNOWN_RESOURCE_TYPE) {
735         return false;
736     }
737     auto resourceObject = GetResourceObjectByBundleAndModule(obj);
738     auto resourceWrapper = CreateResourceWrapper(obj, resourceObject);
739     if (!resourceWrapper) {
740         return false;
741     }
742     if (obj.id == -1) {
743         if (!obj.paramsJsonStr) {
744             return false;
745         }
746         auto params = JsonUtil::ParseJsonString(obj.paramsJsonStr);
747         if (!params->IsArray()) {
748             return false;
749         }
750         auto param = params->GetArrayItem(0);
751         if (obj.type == static_cast<int32_t>(ResourceType::STRARRAY)) {
752             result = resourceWrapper->GetStringArrayByName(param->GetString());
753             return true;
754         }
755         return false;
756     }
757     if (obj.type == static_cast<int32_t>(ResourceType::STRARRAY)) {
758         result = resourceWrapper->GetStringArray(static_cast<uint32_t>(obj.id));
759         return true;
760     }
761     return false;
762 }
763 
ParseOnCreateMenu(CjOnCreateMenu & cjOnCreateMenu,NG::OnCreateMenuCallback & onCreateMenuCallback)764 void ViewAbstract::ParseOnCreateMenu(CjOnCreateMenu& cjOnCreateMenu, NG::OnCreateMenuCallback& onCreateMenuCallback)
765 {
766     WeakPtr<NG::FrameNode> frameNode = AceType::WeakClaim(NG::ViewStackProcessor::GetInstance()->GetMainFrameNode());
767     auto cjCallback = [func = CJLambda::Create(cjOnCreateMenu), node = frameNode, instanceId = Container::CurrentId()](
768                           const std::vector<NG::MenuItemParam>& systemMenuItems) -> std::vector<NG::MenuOptionsParam> {
769         ContainerScope scope(instanceId);
770         auto pipelineContext = PipelineContext::GetCurrentContext();
771         std::vector<NG::MenuOptionsParam> menuParams;
772         CHECK_NULL_RETURN(pipelineContext, menuParams);
773         pipelineContext->UpdateCurrentActiveNode(node);
774         auto cjMenuItems = new std::vector<FfiTextMenuItem>(systemMenuItems.size());
775         for (size_t i = 0; i < systemMenuItems.size(); i++) {
776             FfiTextMenuItem item;
777             auto content = systemMenuItems[i].menuOptionsParam.content;
778             auto icon = systemMenuItems[i].menuOptionsParam.icon;
779             item.content = content.has_value() ? Utils::MallocCString(content.value()) : Utils::MallocCString("");
780             item.icon = icon.has_value() ? Utils::MallocCString(icon.value()) : Utils::MallocCString("");
781             item.id = Utils::MallocCString(systemMenuItems[i].menuOptionsParam.id);
782             (*cjMenuItems)[i] = item;
783         }
784         auto vectorResult = func(cjMenuItems);
785         auto menuItemsArray = reinterpret_cast<std::vector<FfiTextMenuItem>*>(vectorResult);
786         for (size_t i = 0; i < menuItemsArray->size(); i++) {
787             auto ffiMenuItem = (*menuItemsArray)[i];
788             NG::MenuOptionsParam menuOptionsParam;
789             menuOptionsParam.content =
790                 ffiMenuItem.content.value ? std::make_optional(ffiMenuItem.content.value) : std::nullopt;
791             menuOptionsParam.icon = ffiMenuItem.icon.value ? std::make_optional(ffiMenuItem.icon.value) : std::nullopt;
792             menuOptionsParam.id = ffiMenuItem.id.value;
793             menuParams.emplace_back(menuOptionsParam);
794         }
795         delete menuItemsArray;
796         return menuParams;
797     };
798     onCreateMenuCallback = cjCallback;
799 }
800 
ParseOnMenuItemClick(CjOnMenuItemClick & cjOnMenuItemClick,NG::OnMenuItemClickCallback & onMenuItemClick)801 void ViewAbstract::ParseOnMenuItemClick(
802     CjOnMenuItemClick& cjOnMenuItemClick, NG::OnMenuItemClickCallback& onMenuItemClick)
803 {
804     WeakPtr<NG::FrameNode> frameNode = AceType::WeakClaim(NG::ViewStackProcessor::GetInstance()->GetMainFrameNode());
805     auto cjCallback = [func = CJLambda::Create(cjOnMenuItemClick), node = frameNode,
806                           instanceId = Container::CurrentId()](NG::MenuItemParam menuOptionsParam) -> bool {
807         ContainerScope scope(instanceId);
808         auto pipelineContext = PipelineContext::GetCurrentContext();
809         CHECK_NULL_RETURN(pipelineContext, false);
810         pipelineContext->UpdateCurrentActiveNode(node);
811         auto content = menuOptionsParam.menuOptionsParam.content;
812         auto icon = menuOptionsParam.menuOptionsParam.icon;
813         FfiTextMenuItem ffiTextMenuItem;
814         ffiTextMenuItem.content =
815             content.has_value() ? Utils::MallocCString(content.value()) : Utils::MallocCString("");
816         ffiTextMenuItem.icon = icon.has_value() ? Utils::MallocCString(icon.value()) : Utils::MallocCString("");
817         ffiTextMenuItem.id = Utils::MallocCString(menuOptionsParam.menuOptionsParam.id);
818         return func(ffiTextMenuItem, menuOptionsParam.start, menuOptionsParam.end);
819     };
820     onMenuItemClick = cjCallback;
821 }
822 
ParseEditMenuOptions(CjOnCreateMenu & cjOnCreateMenu,CjOnMenuItemClick & cjOnMenuItemClick,NG::OnCreateMenuCallback & onCreateMenuCallback,NG::OnMenuItemClickCallback & onMenuItemClick)823 bool ViewAbstract::ParseEditMenuOptions(CjOnCreateMenu& cjOnCreateMenu, CjOnMenuItemClick& cjOnMenuItemClick,
824     NG::OnCreateMenuCallback& onCreateMenuCallback, NG::OnMenuItemClickCallback& onMenuItemClick)
825 {
826     ParseOnCreateMenu(cjOnCreateMenu, onCreateMenuCallback);
827     ParseOnMenuItemClick(cjOnMenuItemClick, onMenuItemClick);
828     return true;
829 }
830 } // namespace OHOS::Ace::Framework
831