1 /*
2 * Copyright (c) 2025 Huawei Device Co., Ltd.. All rights reserved.
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 "symbol_config_parser.h"
17
18 #include <cstdlib>
19 #include <functional>
20 #include <utility>
21 namespace OHOS {
22 namespace Rosen {
23 namespace Symbol {
24 namespace {
25
26 constexpr char SPECIAL_ANIMATIONS[] = "special_animations";
27 constexpr char COMMON_ANIMATIONS[] = "common_animations";
28 constexpr char SYMBOL_LAYERS_GROUPING[] = "symbol_layers_grouping";
29 constexpr char NATIVE_GLYPH_ID[] = "native_glyph_id";
30 constexpr char SYMBOL_GLYPH_ID[] = "symbol_glyph_id";
31 constexpr char LAYERS[] = "layers";
32 constexpr char COMPONENTS[] = "components";
33 constexpr char RENDER_MODES[] = "render_modes";
34 constexpr char MODE[] = "mode";
35 constexpr char RENDER_GROUPS[] = "render_groups";
36 constexpr char GROUP_INDEXES[] = "group_indexes";
37 constexpr char DEFAULT_COLOR[] = "default_color";
38 constexpr char FIX_ALPHA[] = "fix_alpha";
39 constexpr char LAYER_INDEXES[] = "layer_indexes";
40 constexpr char MASK_INDEXES[] = "mask_indexes";
41 constexpr char GROUP_SETTINGS[] = "group_settings";
42 constexpr char ANIMATION_INDEX[] = "animation_index";
43 constexpr char ANIMATION_SETTINGS[] = "animation_settings";
44 constexpr char ANIMATION_TYPES[] = "animation_types";
45 const char ANIMATION_TYPE[] = "animation_type";
46 const char ANIMATION_PARAMETERS[] = "animation_parameters";
47 const char ANIMATION_MODE[] = "animation_mode";
48 const char COMMON_SUB_TYPE[] = "common_sub_type";
49 const char GROUP_PARAMETERS[] = "group_parameters";
50 const char CURVE[] = "curve";
51 const char CURVE_ARGS[] = "curve_args";
52 const char DURATION[] = "duration";
53 const char DELAY[] = "delay";
54 const char PROPERTIES[] = "properties";
55 const char SLOPE[] = "slope";
56
57 constexpr uint32_t DEFAULT_COLOR_HEX_LEN = 9;
58 constexpr uint32_t DEFAULT_COLOR_STR_LEN = 7;
59 constexpr uint32_t HEX_FLAG = 16;
60 constexpr uint32_t BYTE_LEN = 8;
61
62 using SymbolKeyFunc = std::function<void(const char*, const Json::Value&, RSSymbolLayersGroups&)>;
63 using SymbolKeyFuncMap = std::unordered_map<std::string, SymbolKeyFunc>;
64 using SymnolAniFunc = std::function<void(const char*, const Json::Value&, RSAnimationPara&)>;
65 using SymnolAniFuncMap = std::unordered_map<std::string, SymnolAniFunc>;
66 using PiecewiseParaKeyFunc = std::function<void(const char*, const Json::Value&, RSPiecewiseParameter&)>;
67 using PiecewiseFuncMap = std::unordered_map<std::string, PiecewiseParaKeyFunc>;
68
69 const std::unordered_map<std::string, RSAnimationType> ANIMATIONS_TYPES = {
70 {"scale", RSAnimationType::SCALE_TYPE},
71 {"appear", RSAnimationType::APPEAR_TYPE},
72 {"disappear", RSAnimationType::DISAPPEAR_TYPE},
73 {"bounce", RSAnimationType::BOUNCE_TYPE},
74 {"variable_color", RSAnimationType::VARIABLE_COLOR_TYPE},
75 {"pulse", RSAnimationType::PULSE_TYPE},
76 {"replace_appear", RSAnimationType::REPLACE_APPEAR_TYPE},
77 {"replace_disappear", RSAnimationType::REPLACE_DISAPPEAR_TYPE},
78 {"disable", RSAnimationType::DISABLE_TYPE},
79 {"quick_replace_appear", RSAnimationType::QUICK_REPLACE_APPEAR_TYPE},
80 {"quick_replace_disappear", RSAnimationType::QUICK_REPLACE_DISAPPEAR_TYPE}
81 };
82
83 const std::unordered_map<std::string, RSDrawing::DrawingCurveType> CURVE_TYPES = {
84 {"spring", RSDrawing::DrawingCurveType::SPRING},
85 {"linear", RSDrawing::DrawingCurveType::LINEAR},
86 {"friction", RSDrawing::DrawingCurveType::FRICTION},
87 {"sharp", RSDrawing::DrawingCurveType::SHARP}
88 };
89
90 const std::unordered_map<std::string, RSSymbolRenderingStrategy> RENDER_STRATEGY = {
91 {"monochrome", RSSymbolRenderingStrategy::SINGLE},
92 {"multicolor", RSSymbolRenderingStrategy::MULTIPLE_COLOR},
93 {"hierarchical", RSSymbolRenderingStrategy::MULTIPLE_OPACITY},
94 };
95
96 const std::unordered_map<std::string, RSCommonSubType> SYMBOL_ANIMATION_DIRECTION = {
97 {"up", RSCommonSubType::UP},
98 {"down", RSCommonSubType::DOWN},
99 };
100 };
101
ParseSymbolConfig(const Json::Value & root,std::unordered_map<uint16_t,RSSymbolLayersGroups> & symbolConfig,std::unordered_map<RSAnimationType,RSAnimationInfo> & animationInfos)102 bool SymbolConfigParser::ParseSymbolConfig(const Json::Value& root,
103 std::unordered_map<uint16_t, RSSymbolLayersGroups>& symbolConfig,
104 std::unordered_map<RSAnimationType, RSAnimationInfo>& animationInfos)
105 {
106 const char* key = nullptr;
107 std::vector<std::string> tags = {COMMON_ANIMATIONS, SPECIAL_ANIMATIONS, SYMBOL_LAYERS_GROUPING};
108 for (unsigned int i = 0; i < tags.size(); i++) {
109 key = tags[i].c_str();
110 if (!root.isMember(key) || !root[key].isArray()) {
111 continue;
112 }
113 if (!strcmp(key, COMMON_ANIMATIONS) || !strcmp(key, SPECIAL_ANIMATIONS)) {
114 if (!ParseSymbolAnimations(root[key], animationInfos)) {
115 return false;
116 }
117 } else if (!strcmp(key, SYMBOL_LAYERS_GROUPING)) {
118 if (!ParseSymbolLayersGrouping(root[key], symbolConfig)) {
119 return false;
120 }
121 }
122 }
123 return true;
124 }
125
ParseSymbolLayersGrouping(const Json::Value & root,std::unordered_map<uint16_t,RSSymbolLayersGroups> & symbolConfig)126 bool SymbolConfigParser::ParseSymbolLayersGrouping(const Json::Value& root,
127 std::unordered_map<uint16_t, RSSymbolLayersGroups>& symbolConfig)
128 {
129 if (!root.isArray()) {
130 return false;
131 }
132 for (uint32_t i = 0; i < root.size(); i++) {
133 if (!root[i].isObject()) {
134 continue;
135 }
136 ParseOneSymbol(root[i], symbolConfig);
137 }
138 return true;
139 }
140
ParseOneSymbolNativeCase(const char * key,const Json::Value & root,uint16_t & nativeGlyphId)141 bool SymbolConfigParser::ParseOneSymbolNativeCase(const char* key, const Json::Value& root, uint16_t& nativeGlyphId)
142 {
143 if (!root[key].isInt()) {
144 return false;
145 }
146 nativeGlyphId = root[key].asInt();
147 return true;
148 }
149
ParseComponets(const Json::Value & root,std::vector<size_t> & components)150 void SymbolConfigParser::ParseComponets(const Json::Value& root, std::vector<size_t>& components)
151 {
152 for (uint32_t i = 0; i < root.size(); i++) {
153 if (!root[i].isInt()) {
154 continue;
155 }
156 components.push_back(root[i].asInt());
157 }
158 }
159
SymbolGlyphCase(const char * key,const Json::Value & root,RSSymbolLayersGroups & symbolLayersGroups)160 void SymbolConfigParser::SymbolGlyphCase(const char* key, const Json::Value& root,
161 RSSymbolLayersGroups& symbolLayersGroups)
162 {
163 if (!root[key].isInt()) {
164 return;
165 }
166 symbolLayersGroups.symbolGlyphId = root[key].asInt();
167 }
168
ParseLayers(const Json::Value & root,std::vector<std::vector<size_t>> & layers)169 void SymbolConfigParser::ParseLayers(const Json::Value& root, std::vector<std::vector<size_t>>& layers)
170 {
171 for (uint32_t i = 0; i < root.size(); i++) {
172 if (!root[i].isObject()) {
173 continue;
174 }
175
176 if (!root[i].isMember(COMPONENTS)) {
177 continue;
178 }
179 if (!root[i][COMPONENTS].isArray()) {
180 continue;
181 }
182 std::vector<size_t> components;
183 ParseComponets(root[i][COMPONENTS], components);
184 layers.push_back(components);
185 }
186 }
187
ParseOneSymbolLayerCase(const char * key,const Json::Value & root,RSSymbolLayersGroups & symbolLayersGroups)188 void SymbolConfigParser::ParseOneSymbolLayerCase(const char* key, const Json::Value& root,
189 RSSymbolLayersGroups& symbolLayersGroups)
190 {
191 if (!root[key].isArray()) {
192 return;
193 }
194 ParseLayers(root[key], symbolLayersGroups.layers);
195 }
196
ParseOneSymbolRenderCase(const char * key,const Json::Value & root,RSSymbolLayersGroups & symbolLayersGroups)197 void SymbolConfigParser::ParseOneSymbolRenderCase(const char* key, const Json::Value& root,
198 RSSymbolLayersGroups& symbolLayersGroups)
199 {
200 if (!root[key].isArray()) {
201 return;
202 }
203 ParseRenderModes(root[key], symbolLayersGroups.renderModeGroups);
204 }
205
ParseRenderModes(const Json::Value & root,std::map<RSSymbolRenderingStrategy,std::vector<RSRenderGroup>> & renderModesGroups)206 void SymbolConfigParser::ParseRenderModes(const Json::Value& root,
207 std::map<RSSymbolRenderingStrategy, std::vector<RSRenderGroup>>& renderModesGroups)
208 {
209 for (uint32_t i = 0; i < root.size(); i++) {
210 if (!root[i].isObject()) {
211 continue;
212 }
213
214 RSSymbolRenderingStrategy renderingStrategy;
215 if (root[i].isMember(MODE)) {
216 if (!root[i][MODE].isString()) {
217 continue;
218 }
219 std::string modeValue = root[i][MODE].asString();
220 if (RENDER_STRATEGY.count(modeValue) == 0) {
221 continue;
222 }
223 renderingStrategy = RENDER_STRATEGY.at(modeValue);
224 }
225
226 std::vector<RSRenderGroup> renderGroups;
227 if (root[i].isMember(RENDER_GROUPS)) {
228 if (!root[i][RENDER_GROUPS].isArray()) {
229 continue;
230 }
231 ParseRenderGroups(root[i][RENDER_GROUPS], renderGroups);
232 }
233 renderModesGroups.emplace(renderingStrategy, renderGroups);
234 }
235 }
236
ParseRenderGroups(const Json::Value & root,std::vector<RSRenderGroup> & renderGroups)237 void SymbolConfigParser::ParseRenderGroups(const Json::Value& root, std::vector<RSRenderGroup>& renderGroups)
238 {
239 for (uint32_t i = 0; i < root.size(); i++) {
240 if (!root[i].isObject()) {
241 continue;
242 }
243
244 RSRenderGroup renderGroup;
245 if (root[i].isMember(GROUP_INDEXES) && root[i][GROUP_INDEXES].isArray()) {
246 ParseGroupIndexes(root[i][GROUP_INDEXES], renderGroup.groupInfos);
247 }
248 if (root[i].isMember(DEFAULT_COLOR) && root[i][DEFAULT_COLOR].isString()) {
249 ParseDefaultColor(root[i][DEFAULT_COLOR].asString().c_str(), renderGroup);
250 }
251 if (root[i].isMember(FIX_ALPHA) && root[i][FIX_ALPHA].isDouble()) {
252 renderGroup.color.a = root[i][FIX_ALPHA].asDouble();
253 }
254 renderGroups.push_back(renderGroup);
255 }
256 }
257
ParseDefaultColor(const char * defaultColorStr,RSRenderGroup & renderGroup)258 void SymbolConfigParser::ParseDefaultColor(const char* defaultColorStr, RSRenderGroup& renderGroup)
259 {
260 char defaultColorHex[DEFAULT_COLOR_HEX_LEN];
261 defaultColorHex[0] = '0';
262 defaultColorHex[1] = 'X';
263 if (defaultColorStr == nullptr || strlen(defaultColorStr) != DEFAULT_COLOR_STR_LEN) {
264 return;
265 }
266
267 for (uint32_t i = 1; i < DEFAULT_COLOR_STR_LEN; i++) {
268 defaultColorHex[i + 1] = defaultColorStr[i];
269 }
270 defaultColorHex[DEFAULT_COLOR_HEX_LEN - 1] = '\0';
271 char* end = nullptr;
272 uint32_t defaultColor = std::strtoul(defaultColorHex, &end, HEX_FLAG);
273 if (end == nullptr || *end != '\0') {
274 return;
275 }
276 renderGroup.color.r = (defaultColor >> (BYTE_LEN + BYTE_LEN)) & 0xFF;
277 renderGroup.color.g = (defaultColor >> BYTE_LEN) & 0xFF;
278 renderGroup.color.b = defaultColor & 0xFF;
279 }
280
ParseGroupIndexes(const Json::Value & root,std::vector<RSGroupInfo> & groupInfos)281 void SymbolConfigParser::ParseGroupIndexes(const Json::Value& root, std::vector<RSGroupInfo>& groupInfos)
282 {
283 for (uint32_t i = 0; i < root.size(); i++) {
284 RSGroupInfo groupInfo;
285 if (root[i].isMember(LAYER_INDEXES)) {
286 if (!root[i][LAYER_INDEXES].isArray()) {
287 continue;
288 }
289 ParseLayerOrMaskIndexes(root[i][LAYER_INDEXES], groupInfo.layerIndexes);
290 }
291 if (root[i].isMember(MASK_INDEXES)) {
292 if (!root[i][MASK_INDEXES].isArray()) {
293 continue;
294 }
295 ParseLayerOrMaskIndexes(root[i][MASK_INDEXES], groupInfo.maskIndexes);
296 }
297 groupInfos.push_back(groupInfo);
298 }
299 }
300
ParseLayerOrMaskIndexes(const Json::Value & root,std::vector<size_t> & indexes)301 void SymbolConfigParser::ParseLayerOrMaskIndexes(const Json::Value& root, std::vector<size_t>& indexes)
302 {
303 for (uint32_t i = 0; i < root.size(); i++) {
304 if (!root[i].isInt()) {
305 continue;
306 }
307 indexes.push_back(root[i].asInt());
308 }
309 }
310
ParseOneSymbolAnimateCase(const char * key,const Json::Value & root,RSSymbolLayersGroups & symbolLayersGroups)311 void SymbolConfigParser::ParseOneSymbolAnimateCase(const char* key, const Json::Value& root,
312 RSSymbolLayersGroups& symbolLayersGroups)
313 {
314 if (!root[key].isArray()) {
315 return;
316 }
317 ParseAnimationSettings(root[key], symbolLayersGroups.animationSettings);
318 }
319
ParseAnimationSettings(const Json::Value & root,std::vector<RSAnimationSetting> & animationSettings)320 void SymbolConfigParser::ParseAnimationSettings(const Json::Value& root,
321 std::vector<RSAnimationSetting>& animationSettings)
322 {
323 for (uint32_t i = 0; i < root.size(); i++) {
324 if (!root[i].isObject()) {
325 continue;
326 }
327 RSAnimationSetting animationSetting;
328 ParseAnimationSetting(root[i], animationSetting);
329 animationSettings.push_back(animationSetting);
330 }
331 }
332
ParseAnimationSetting(const Json::Value & root,RSAnimationSetting & animationSetting)333 void SymbolConfigParser::ParseAnimationSetting(const Json::Value& root, RSAnimationSetting& animationSetting)
334 {
335 if (root.isMember(ANIMATION_TYPES) && root[ANIMATION_TYPES].isArray()) {
336 ParseAnimationTypes(root[ANIMATION_TYPES], animationSetting.animationTypes);
337 }
338
339 if (root.isMember(GROUP_SETTINGS) && root[GROUP_SETTINGS].isArray()) {
340 ParseGroupSettings(root[GROUP_SETTINGS], animationSetting.groupSettings);
341 }
342
343 if (root.isMember(COMMON_SUB_TYPE) && root[COMMON_SUB_TYPE].isString()) {
344 const std::string subTypeStr = root[COMMON_SUB_TYPE].asString();
345 MatchCommonSubType(subTypeStr, animationSetting.commonSubType);
346 }
347
348 if (root.isMember(SLOPE) && root[SLOPE].isDouble()) {
349 animationSetting.slope = root[SLOPE].asDouble();
350 }
351 }
352
ParseAnimationTypes(const Json::Value & root,std::vector<RSAnimationType> & animationTypes)353 void SymbolConfigParser::ParseAnimationTypes(const Json::Value& root, std::vector<RSAnimationType>& animationTypes)
354 {
355 for (uint32_t i = 0; i < root.size(); i++) {
356 if (!root[i].isString()) {
357 continue;
358 }
359 const std::string animationTypeStr = root[i].asString();
360 RSAnimationType animationType;
361 ParseAnimationType(animationTypeStr, animationType);
362 animationTypes.push_back(animationType);
363 }
364 }
365
ParseAnimationType(const std::string & animationTypeStr,RSAnimationType & animationType)366 void SymbolConfigParser::ParseAnimationType(const std::string& animationTypeStr, RSAnimationType& animationType)
367 {
368 auto iter = ANIMATIONS_TYPES.find(animationTypeStr);
369 if (iter != ANIMATIONS_TYPES.end()) {
370 animationType = iter->second;
371 }
372 }
373
ParseGroupSettings(const Json::Value & root,std::vector<RSGroupSetting> & groupSettings)374 void SymbolConfigParser::ParseGroupSettings(const Json::Value& root, std::vector<RSGroupSetting>& groupSettings)
375 {
376 for (uint32_t i = 0; i < root.size(); i++) {
377 if (!root[i].isObject()) {
378 continue;
379 }
380 RSGroupSetting groupSetting;
381 ParseGroupSetting(root[i], groupSetting);
382 groupSettings.push_back(groupSetting);
383 }
384 }
385
MatchCommonSubType(const std::string & subTypeStr,RSCommonSubType & commonSubType)386 void SymbolConfigParser::MatchCommonSubType(const std::string& subTypeStr, RSCommonSubType& commonSubType)
387 {
388 if (SYMBOL_ANIMATION_DIRECTION.count(subTypeStr) == 0) {
389 return;
390 }
391 commonSubType = SYMBOL_ANIMATION_DIRECTION.at(subTypeStr);
392 }
393
ParseGroupSetting(const Json::Value & root,RSGroupSetting & groupSetting)394 void SymbolConfigParser::ParseGroupSetting(const Json::Value& root, RSGroupSetting& groupSetting)
395 {
396 if (root.isMember(GROUP_INDEXES) && root[GROUP_INDEXES].isArray()) {
397 ParseGroupIndexes(root[GROUP_INDEXES], groupSetting.groupInfos);
398 }
399
400 if (root.isMember(ANIMATION_INDEX) && root[ANIMATION_INDEX].isInt()) {
401 groupSetting.animationIndex = root[ANIMATION_INDEX].asInt();
402 }
403 }
404
ParseOneSymbol(const Json::Value & root,std::unordered_map<uint16_t,RSSymbolLayersGroups> & symbolConfig)405 void SymbolConfigParser::ParseOneSymbol(const Json::Value& root,
406 std::unordered_map<uint16_t, RSSymbolLayersGroups>& symbolConfig)
407 {
408 if (!root.isMember(NATIVE_GLYPH_ID)) {
409 return;
410 }
411
412 uint16_t nativeGlyphId = 0;
413 if (!ParseOneSymbolNativeCase(NATIVE_GLYPH_ID, root, nativeGlyphId)) {
414 return;
415 }
416 RSSymbolLayersGroups symbolLayersGroups;
417 // The default value for symbol_glyph_id is the value for native_glyph_id
418 symbolLayersGroups.symbolGlyphId = nativeGlyphId;
419
420 std::vector<std::string> tags = {SYMBOL_GLYPH_ID, LAYERS, RENDER_MODES, ANIMATION_SETTINGS};
421 static SymbolKeyFuncMap funcMap = {
422 {SYMBOL_GLYPH_ID, &SymbolConfigParser::SymbolGlyphCase},
423 {LAYERS, &SymbolConfigParser::ParseOneSymbolLayerCase},
424 {RENDER_MODES, &SymbolConfigParser::ParseOneSymbolRenderCase},
425 {ANIMATION_SETTINGS, &SymbolConfigParser::ParseOneSymbolAnimateCase}
426 };
427 for (uint32_t i = 0; i < tags.size(); i++) {
428 const char* key = tags[i].c_str();
429 if (!root.isMember(key)) {
430 continue;
431 }
432 if (funcMap.count(key) > 0) {
433 funcMap[key](key, root, symbolLayersGroups);
434 }
435 }
436 symbolConfig.emplace(nativeGlyphId, symbolLayersGroups);
437 }
438
EncodeAnimationAttribute(uint16_t groupSum,uint16_t animationMode,RSCommonSubType commonSubType)439 uint32_t SymbolConfigParser::EncodeAnimationAttribute(uint16_t groupSum,
440 uint16_t animationMode, RSCommonSubType commonSubType)
441 {
442 uint32_t result = static_cast<uint32_t>(groupSum);
443 result = (result << BYTE_LEN) + static_cast<uint32_t>(animationMode);
444 result = (result << BYTE_LEN) + static_cast<uint32_t>(commonSubType);
445 return result;
446 }
447
ParseSymbolAnimations(const Json::Value & root,std::unordered_map<RSAnimationType,RSAnimationInfo> & animationInfos)448 bool SymbolConfigParser::ParseSymbolAnimations(const Json::Value& root,
449 std::unordered_map<RSAnimationType, RSAnimationInfo>& animationInfos)
450 {
451 if (!root.isArray()) {
452 return false;
453 }
454 for (uint32_t i = 0; i < root.size(); i++) {
455 if (!root[i].isObject()) {
456 continue;
457 }
458
459 if (!root[i].isMember(ANIMATION_TYPE) || !root[i].isMember(ANIMATION_PARAMETERS)) {
460 continue;
461 }
462 RSAnimationInfo animationInfo;
463 if (!root[i][ANIMATION_TYPE].isString()) {
464 continue;
465 }
466 const std::string animationType = root[i][ANIMATION_TYPE].asString();
467 ParseAnimationType(animationType, animationInfo.animationType);
468
469 if (!root[i][ANIMATION_PARAMETERS].isArray()) {
470 continue;
471 }
472 ParseSymbolAnimationParas(root[i][ANIMATION_PARAMETERS], animationInfo.animationParas);
473 animationInfos.emplace(animationInfo.animationType, animationInfo);
474 }
475 return true;
476 }
477
ParseSymbolAnimationParas(const Json::Value & root,std::map<uint32_t,RSAnimationPara> & animationParas)478 void SymbolConfigParser::ParseSymbolAnimationParas(const Json::Value& root,
479 std::map<uint32_t, RSAnimationPara>& animationParas)
480 {
481 for (uint32_t i = 0; i < root.size(); i++) {
482 if (!root[i].isObject()) {
483 continue;
484 }
485 RSAnimationPara animationPara;
486 ParseSymbolAnimationPara(root[i], animationPara);
487 uint32_t attributeKey = EncodeAnimationAttribute(animationPara.groupParameters.size(),
488 animationPara.animationMode, animationPara.commonSubType);
489 animationParas.emplace(attributeKey, animationPara);
490 }
491 }
492
ParseSymbolAnimationPara(const Json::Value & root,RSAnimationPara & animationPara)493 void SymbolConfigParser::ParseSymbolAnimationPara(const Json::Value& root, RSAnimationPara& animationPara)
494 {
495 std::vector<std::string> tags = {ANIMATION_MODE, COMMON_SUB_TYPE, GROUP_PARAMETERS};
496 static SymnolAniFuncMap funcMap = {
497 {ANIMATION_MODE, [](const char* key, const Json::Value& root, RSAnimationPara& animationPara)
498 {
499 if (!root[key].isInt()) {
500 return;
501 }
502 animationPara.animationMode = root[key].asInt();
503 }
504 },
505 {COMMON_SUB_TYPE, &SymbolConfigParser::ParseSymbolCommonSubType},
506 {GROUP_PARAMETERS, &SymbolConfigParser::ParseSymbolGroupParas}
507 };
508 for (uint32_t i = 0; i < tags.size(); i++) {
509 const char* key = tags[i].c_str();
510 if (!root.isMember(key)) {
511 continue;
512 }
513 if (funcMap.count(key) > 0) {
514 funcMap[key](key, root, animationPara);
515 }
516 }
517 }
518
ParseSymbolCommonSubType(const char * key,const Json::Value & root,RSAnimationPara & animationPara)519 void SymbolConfigParser::ParseSymbolCommonSubType(const char* key, const Json::Value& root,
520 RSAnimationPara& animationPara)
521 {
522 if (!root[key].isString()) {
523 return;
524 }
525
526 std::string subTypeStr = root[key].asString();
527 MatchCommonSubType(subTypeStr, animationPara.commonSubType);
528 }
529
ParseSymbolGroupParas(const char * key,const Json::Value & root,RSAnimationPara & animationPara)530 void SymbolConfigParser::ParseSymbolGroupParas(const char* key, const Json::Value& root,
531 RSAnimationPara& animationPara)
532 {
533 if (!root[key].isArray()) {
534 return;
535 }
536
537 for (uint32_t i = 0; i < root[key].size(); i++) {
538 if (!root[key][i].isArray()) {
539 continue;
540 }
541 std::vector<RSPiecewiseParameter> piecewiseParameters;
542 for (uint32_t j = 0; j < root[key][i].size(); j++) {
543 if (!root[key][i][j].isObject()) {
544 continue;
545 }
546 RSPiecewiseParameter piecewiseParameter;
547 ParseSymbolPiecewisePara(root[key][i][j], piecewiseParameter);
548 piecewiseParameters.push_back(piecewiseParameter);
549 }
550
551 animationPara.groupParameters.push_back(piecewiseParameters);
552 }
553 }
554
ParseSymbolPiecewisePara(const Json::Value & root,RSPiecewiseParameter & piecewiseParameter)555 void SymbolConfigParser::ParseSymbolPiecewisePara(const Json::Value& root, RSPiecewiseParameter& piecewiseParameter)
556 {
557 std::vector<std::string> tags = {CURVE, CURVE_ARGS, DURATION, DELAY, PROPERTIES};
558 static PiecewiseFuncMap funcMap = {
559 {CURVE, &SymbolConfigParser::PiecewiseParaCurveCase},
560 {CURVE_ARGS, &SymbolConfigParser::ParseSymbolCurveArgs},
561 {DURATION, &SymbolConfigParser::PiecewiseParaDurationCase},
562 {DELAY, &SymbolConfigParser::PiecewiseParaDelayCase},
563 {PROPERTIES, &SymbolConfigParser::ParseSymbolProperties}
564 };
565
566 for (uint32_t i = 0; i < tags.size(); i++) {
567 const char* key = tags[i].c_str();
568 if (!root.isMember(key)) {
569 continue;
570 }
571 if (funcMap.count(key) > 0) {
572 funcMap[key](key, root, piecewiseParameter);
573 }
574 }
575 }
576
PiecewiseParaCurveCase(const char * key,const Json::Value & root,RSPiecewiseParameter & piecewiseParameter)577 void SymbolConfigParser::PiecewiseParaCurveCase(const char* key, const Json::Value& root,
578 RSPiecewiseParameter& piecewiseParameter)
579 {
580 if (!root[key].isString()) {
581 return;
582 }
583 const std::string curveTypeStr = root[key].asString();
584 if (CURVE_TYPES.count(curveTypeStr) == 0) {
585 return;
586 }
587 piecewiseParameter.curveType = CURVE_TYPES.at(curveTypeStr);
588 }
589
PiecewiseParaDurationCase(const char * key,const Json::Value & root,RSPiecewiseParameter & piecewiseParameter)590 void SymbolConfigParser::PiecewiseParaDurationCase(const char* key, const Json::Value& root,
591 RSPiecewiseParameter& piecewiseParameter)
592 {
593 if (!root[key].isDouble()) {
594 return;
595 }
596 piecewiseParameter.duration = static_cast<uint32_t>(root[key].asDouble());
597 }
598
PiecewiseParaDelayCase(const char * key,const Json::Value & root,RSPiecewiseParameter & piecewiseParameter)599 void SymbolConfigParser::PiecewiseParaDelayCase(const char* key, const Json::Value& root,
600 RSPiecewiseParameter& piecewiseParameter)
601 {
602 if (!root[key].isDouble()) {
603 return;
604 }
605 piecewiseParameter.delay = static_cast<int>(root[key].asDouble());
606 }
607
ParseSymbolCurveArgs(const char * key,const Json::Value & root,RSPiecewiseParameter & piecewiseParameter)608 void SymbolConfigParser::ParseSymbolCurveArgs(const char* key, const Json::Value& root,
609 RSPiecewiseParameter& piecewiseParameter)
610 {
611 if (!root[key].isObject() || root[key].empty()) {
612 return;
613 }
614
615 for (Json::Value::const_iterator iter = root[key].begin(); iter != root[key].end(); ++iter) {
616 std::string name = iter.name();
617 const char* memberName = name.c_str();
618 if (!root[key][memberName].isDouble()) {
619 continue;
620 }
621 piecewiseParameter.curveArgs.emplace(std::string(memberName), root[key][memberName].asDouble());
622 }
623 }
624
ParseSymbolProperties(const char * key,const Json::Value & root,RSPiecewiseParameter & piecewiseParameter)625 void SymbolConfigParser::ParseSymbolProperties(const char* key, const Json::Value& root,
626 RSPiecewiseParameter& piecewiseParameter)
627 {
628 if (!root[key].isObject()) {
629 return;
630 }
631 for (Json::Value::const_iterator iter = root[key].begin(); iter != root[key].end(); ++iter) {
632 std::string name = iter.name();
633 const char* memberName = name.c_str();
634 if (!root[key][memberName].isArray()) {
635 continue;
636 }
637
638 std::vector<float> propertyValues;
639 for (uint32_t i = 0; i < root[key][memberName].size(); i++) {
640 if (!root[key][memberName][i].isNumeric()) {
641 continue;
642 }
643 propertyValues.push_back(root[key][memberName][i].asFloat());
644 }
645 piecewiseParameter.properties.emplace(std::string(memberName), propertyValues);
646 }
647 }
648 } // namespace Symbol
649 } // namespace Rosen
650 } // namespace OHOS