1 /*
2 * Copyright (c) 2021 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 "core/components/declaration/svg/svg_base_declaration.h"
17
18 #include "base/utils/string_utils.h"
19 #include "core/components/declaration/common/declaration_constants.h"
20 #include "frameworks/bridge/common/utils/utils.h"
21
22 namespace OHOS::Ace {
23 namespace {
24
25 const char LINECAP_ROUND[] = "round";
26 const char LINECAP_SQUARE[] = "square";
27 const char LINEJOIN_BEVEL[] = "bevel";
28 const char LINEJOIN_ROUND[] = "round";
29
30 const char DOM_SVG_SRC_FILL_OPACITY[] = "fill-opacity";
31 const char DOM_SVG_SRC_FILL_RULE[] = "fill-rule";
32 const char DOM_SVG_SRC_STROKE_DASHARRAY[] = "stroke-dasharray";
33 const char DOM_SVG_SRC_STROKE_DASHOFFSET[] = "stroke-dashoffset";
34 const char DOM_SVG_SRC_STROKE_LINECAP[] = "stroke-linecap";
35 const char DOM_SVG_SRC_STROKE_LINEJOIN[] = "stroke-linejoin";
36 const char DOM_SVG_SRC_STROKE_MITERLIMIT[] = "stroke-miterlimit";
37 const char DOM_SVG_SRC_STROKE_OPACITY[] = "stroke-opacity";
38 const char DOM_SVG_SRC_STROKE_WIDTH[] = "stroke-width";
39 const char DOM_SVG_SRC_CLIP_PATH[] = "clip-path";
40 const char DOM_SVG_SRC_CLIP_RULE[] = "clip-rule";
41 const char DOM_SVG_SRC_TRANSFORM_ORIGIN[] = "transform-origin";
42
43 const LinearMapNode<Color> COLOR_TABLE[] = {
44 { "aliceblue", Color(0xfff0f8ff) },
45 { "antiquewhite", Color(0xfffaebd7) },
46 { "aqua", Color(0xff00ffff) },
47 { "aquamarine", Color(0xff7fffd4) },
48 { "azure", Color(0xfff0ffff) },
49 { "beige", Color(0xfff5f5dc) },
50 { "bisque", Color(0xffffe4c4) },
51 { "black", Color(0XFF000000) },
52 { "blanchedalmond", Color(0xffffebcd) },
53 { "blue", Color(0xff0000ff) },
54 { "blueviolet", Color(0xff8a2be2) },
55 { "brown", Color(0xffa52a2a) },
56 { "burlywood", Color(0xffdeb887) },
57 { "cadetblue", Color(0xff5f9ea0) },
58 { "chartreuse", Color(0xff7fff00) },
59 { "chocolate", Color(0xffd2691e) },
60 { "coral", Color(0xffff7f50) },
61 { "cornflowerblue", Color(0xff6495ed) },
62 { "cornsilk", Color(0xfffff8dc) },
63 { "crimson", Color(0xffdc143c) },
64 { "cyan", Color(0xff00ffff) },
65 { "darkblue", Color(0xff00008b) },
66 { "darkcyan", Color(0xff008b8b) },
67 { "darkgoldenrod", Color(0xffb8860b) },
68 { "darkgray", Color(0xffa9a9a9) },
69 { "darkgreen", Color(0xff006400) },
70 { "darkgrey", Color(0xffa9a9a9) },
71 { "darkkhaki", Color(0xffbdb76b) },
72 { "darkmagenta", Color(0xff8b008b) },
73 { "darkolivegreen", Color(0xff556b2f) },
74 { "darkorange", Color(0xffff8c00) },
75 { "darkorchid", Color(0xff9932cc) },
76 { "darkred", Color(0xff8b0000) },
77 { "darksalmon", Color(0xffe9967a) },
78 { "darkseagreen", Color(0xff8fbc8f) },
79 { "darkslateblue", Color(0xff483d8b) },
80 { "darkslategray", Color(0xff2f4f4f) },
81 { "darkslategrey", Color(0xff2f4f4f) },
82 { "darkturquoise", Color(0xff00ced1) },
83 { "darkviolet", Color(0xff9400D3) },
84 { "deeppink", Color(0xffff1493) },
85 { "deepskyblue", Color(0xff00bfff) },
86 { "dimgray", Color(0xff696969) },
87 { "dimgrey", Color(0xff696969) },
88 { "dodgerblue", Color(0xff1e90ff) },
89 { "firebrick", Color(0xffb22222) },
90 { "floralwhite", Color(0xfffffaf0) },
91 { "forestgreen", Color(0xff228b22) },
92 { "fuchsia", Color(0xffff00ff) },
93 { "gainsboro", Color(0xffdcdcdc) },
94 { "ghostwhite", Color(0xfff8f8ff) },
95 { "gold", Color(0xffffd700) },
96 { "goldenrod", Color(0xffdaa520) },
97 { "gray", Color(0xff808080) },
98 { "green", Color(0xff008000) },
99 { "greenyellow", Color(0xffadff2f) },
100 { "grey", Color(0xff808080) },
101 { "honeydew", Color(0xfff0fff0) },
102 { "hotpink", Color(0xffff69b4) },
103 { "indianred", Color(0xffcd5c5c) },
104 { "indigo", Color(0xff4b0082) },
105 { "ivory", Color(0xfffffff0) },
106 { "khaki", Color(0xfff0e68c) },
107 { "lavender", Color(0xffe6e6fa) },
108 { "lavenderblush", Color(0xfffff0f5) },
109 { "lawngreen", Color(0xff7cfc00) },
110 { "lemonchiffon", Color(0xfffffacd) },
111 { "lightblue", Color(0xffadd8e6) },
112 { "lightcoral", Color(0xfff08080) },
113 { "lightcyan", Color(0xffe0ffff) },
114 { "lightgoldenrodyellow", Color(0xfffafad2) },
115 { "lightgray", Color(0xffd3d3d3) },
116 { "lightgreen", Color(0xff90ee90) },
117 { "lightgrey", Color(0xffd3d3d3) },
118 { "lightpink", Color(0xffffb6c1) },
119 { "lightsalmon", Color(0xffffa07a) },
120 { "lightseagreen", Color(0xff20b2aa) },
121 { "lightskyblue", Color(0xff87cefa) },
122 { "lightslategray", Color(0xff778899) },
123 { "lightslategrey", Color(0xff778899) },
124 { "lightsteelblue", Color(0xffb0c4de) },
125 { "lightyellow", Color(0xffffffe0) },
126 { "lime", Color(0xff00ff00) },
127 { "limegreen", Color(0xff32cd32) },
128 { "linen", Color(0xfffaf0e6) },
129 { "magenta", Color(0xffff00ff) },
130 { "maroon", Color(0xff800000) },
131 { "mediumaquamarine", Color(0xff66cdaa) },
132 { "mediumblue", Color(0xff0000cd) },
133 { "mediumorchid", Color(0xffba55d3) },
134 { "mediumpurple", Color(0xff9370db) },
135 { "mediumseagreen", Color(0xff3cb371) },
136 { "mediumslateblue", Color(0xff7b68ee) },
137 { "mediumspringgreen", Color(0xff00fa9a) },
138 { "mediumturquoise", Color(0xff48d1cc) },
139 { "mediumvioletred", Color(0xffc71585) },
140 { "midnightblue", Color(0xff191970) },
141 { "mintcream", Color(0xfff5fffa) },
142 { "mistyrose", Color(0xffffe4e1) },
143 { "moccasin", Color(0xffffe4b5) },
144 { "navajowhite", Color(0xffffdead) },
145 { "navy", Color(0xff000080) },
146 { "oldlace", Color(0xfffdf5e6) },
147 { "olive", Color(0xff808000) },
148 { "olivedrab", Color(0xff6b8e23) },
149 { "orange", Color(0xffffa500) },
150 { "orangered", Color(0xffff4500) },
151 { "orchid", Color(0xffda70d6) },
152 { "palegoldenrod", Color(0xffeee8aa) },
153 { "palegreen", Color(0xff98fb98) },
154 { "paleturquoise", Color(0xffafeeee) },
155 { "palevioletred", Color(0xffdb7093) },
156 { "papayawhip", Color(0xffffefd5) },
157 { "peachpuff", Color(0xffffdab9) },
158 { "peru", Color(0xffcd853f) },
159 { "pink", Color(0xffffc0cb) },
160 { "plum", Color(0xffdda0dd) },
161 { "powderblue", Color(0xffb0e0e6) },
162 { "purple", Color(0xff800080) },
163 { "red", Color(0xffff0000) },
164 { "rosybrown", Color(0xffbc8f8f) },
165 { "royalblue", Color(0xff4169e1) },
166 { "rebeccapurple", Color(0xff663399) },
167 { "saddlebrown", Color(0xff8b4513) },
168 { "salmon", Color(0xfffa8072) },
169 { "sandybrown", Color(0xfff4a460) },
170 { "seagreen", Color(0xff2e8b57) },
171 { "seashell", Color(0xfffff5ee) },
172 { "sienna", Color(0xffa0522d) },
173 { "silver", Color(0xffc0c0c0) },
174 { "skyblue", Color(0xff87ceeb) },
175 { "slateblue", Color(0xff6a5acd) },
176 { "slategray", Color(0xff708090) },
177 { "slategrey", Color(0xff708090) },
178 { "snow", Color(0xfffffafa) },
179 { "springgreen", Color(0xff00ff7f) },
180 { "steelblue", Color(0xff4682b4) },
181 { "tan", Color(0xffd2b48c) },
182 { "teal", Color(0xff008080) },
183 { "thistle", Color(0xffd8bfd8) },
184 { "tomato", Color(0xffff6347) },
185 { "turquoise", Color(0xff40e0d0) },
186 { "violet", Color(0xffee82ee) },
187 { "wheat", Color(0xfff5deb3) },
188 { "white", Color(0xffffffff) },
189 { "whitesmoke", Color(0xfff5f5f5) },
190 { "yellow", Color(0xffffff00) },
191 { "yellowgreen", Color(0xff9acd32) },
192 };
193
194 } // namespace
195
196 using namespace Framework;
197
InitSpecialized()198 void SvgBaseDeclaration::InitSpecialized()
199 {
200 AddSpecializedAttribute(DeclarationConstants::DEFAULT_SVG_BASE_ATTR);
201 }
202
SetSpecializedAttr(const std::pair<std::string,std::string> & attr)203 bool SvgBaseDeclaration::SetSpecializedAttr(const std::pair<std::string, std::string>& attr)
204 {
205 return SetPresentationAttr(attr);
206 }
207
SetSpecializedStyle(const std::pair<std::string,std::string> & style)208 bool SvgBaseDeclaration::SetSpecializedStyle(const std::pair<std::string, std::string>& style)
209 {
210 return SetPresentationAttr(style);
211 }
212
SetPresentationAttr(const std::pair<std::string,std::string> & attr)213 bool SvgBaseDeclaration::SetPresentationAttr(const std::pair<std::string, std::string>& attr)
214 {
215 static const LinearMapNode<void (*)(const std::string&, SvgBaseDeclaration&)> svgBaseAttrs[] = {
216 { DOM_SVG_SRC_CLIP_PATH,
217 [](const std::string& val, SvgBaseDeclaration& declaration) {
218 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
219 auto value = StringUtils::TrimStr(val);
220 if (value.find("url(") == 0) {
221 auto src = std::regex_replace(value,
222 std::regex(R"(^url\(\s*['"]?\s*#([^()]+?)\s*['"]?\s*\)$)"), "$1");
223 attrs.clipState.SetHref(src);
224 }
225 } },
226 { DOM_SVG_SRC_CLIP_RULE,
227 [](const std::string& val, SvgBaseDeclaration& declaration) {
228 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
229 attrs.clipState.SetClipRule(val);
230 } },
231 { DOM_CLIP_PATH,
232 [](const std::string& val, SvgBaseDeclaration& declaration) {
233 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
234 auto value = StringUtils::TrimStr(val);
235 if (value.find("url(") == 0) {
236 auto src = std::regex_replace(value,
237 std::regex(R"(^url\(\s*['"]?\s*#([^()]+?)\s*['"]?\s*\)$)"), "$1");
238 attrs.clipState.SetHref(src);
239 }
240 } },
241 { DOM_SVG_CLIP_RULE,
242 [](const std::string& val, SvgBaseDeclaration& declaration) {
243 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
244 attrs.clipState.SetClipRule(val);
245 } },
246 { DOM_SVG_FILL,
247 [](const std::string& val, SvgBaseDeclaration& declaration) {
248 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
249 auto value = StringUtils::TrimStr(val);
250 if (value.find("url(") == 0) {
251 auto src = std::regex_replace(value,
252 std::regex(R"(^url\(\s*['"]?\s*#([^()]+?)\s*['"]?\s*\)$)"), "$1");
253 attrs.fillState.SetHref(src);
254 } else {
255 Color fill = (val == VALUE_NONE ? Color::TRANSPARENT : declaration.GetColor(val));
256 attrs.fillState.SetColor(fill);
257 }
258 } },
259 { DOM_SVG_SRC_FILL_OPACITY,
260 [](const std::string& val, SvgBaseDeclaration& declaration) {
261 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
262 attrs.fillState.SetOpacity(std::clamp(StringToDouble(val), 0.0, 1.0));
263 } },
264 { DOM_SVG_SRC_FILL_RULE,
265 [](const std::string& val, SvgBaseDeclaration& declaration) {
266 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
267 attrs.fillState.SetFillRule(val);
268 } },
269 { DOM_SVG_FILL_OPACITY,
270 [](const std::string& val, SvgBaseDeclaration& declaration) {
271 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
272 attrs.fillState.SetOpacity(std::clamp(StringToDouble(val), 0.0, 1.0));
273 } },
274 { DOM_SVG_FILL_RULE,
275 [](const std::string& val, SvgBaseDeclaration& declaration) {
276 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
277 attrs.fillState.SetFillRule(val);
278 } },
279 { DOM_SVG_FILTER,
280 [](const std::string& val, SvgBaseDeclaration& declaration) {
281 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
282 attrs.filterId = val;
283 } },
284 { DOM_SVG_FONT_SIZE,
285 [](const std::string& val, SvgBaseDeclaration& declaration) {
286 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
287 Dimension fontSize = StringToDimension(val);
288 if (GreatOrEqual(fontSize.Value(), 0.0)) {
289 attrs.textStyle.SetFontSize(fontSize);
290 }
291 } },
292 { DOM_SVG_HREF,
293 [](const std::string& val, SvgBaseDeclaration& declaration) {
294 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
295 auto value = StringUtils::TrimStr(val);
296 if (value.substr(0, 1) == "#") {
297 attrs.href = value.substr(1);
298 }
299 } },
300 { DOM_SVG_MASK,
301 [](const std::string& val, SvgBaseDeclaration& declaration) {
302 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
303 attrs.maskId = val;
304 } },
305 { DOM_SVG_OPACITY,
306 [](const std::string& val, SvgBaseDeclaration& declaration) {
307 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
308 attrs.hasOpacity = true;
309 attrs.opacity = std::clamp(StringToDouble(val), 0.0, 1.0);
310 } },
311 { DOM_SVG_STROKE,
312 [](const std::string& val, SvgBaseDeclaration& declaration) {
313 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
314 auto value = StringUtils::TrimStr(val);
315 if (value.find("url(") == 0) {
316 auto src = std::regex_replace(value,
317 std::regex(R"(^url\(\s*['"]?\s*#([^()]+?)\s*['"]?\s*\)$)"), "$1");
318 attrs.strokeState.SetHref(src);
319 } else {
320 Color stroke = (val == VALUE_NONE ? Color::TRANSPARENT : declaration.GetColor(val));
321 attrs.strokeState.SetColor(stroke);
322 }
323 } },
324 { DOM_SVG_SRC_STROKE_DASHARRAY,
325 [](const std::string& val, SvgBaseDeclaration& declaration) {
326 if (val.empty()) {
327 return;
328 }
329 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
330 std::vector<double> lineDashVector;
331 StringUtils::StringSplitter(val, ' ', lineDashVector);
332 attrs.strokeState.SetLineDash(lineDashVector);
333 } },
334 { DOM_SVG_SRC_STROKE_DASHOFFSET,
335 [](const std::string& val, SvgBaseDeclaration& declaration) {
336 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
337 attrs.strokeState.SetLineDashOffset(StringToDouble(val));
338 } },
339 { DOM_SVG_SRC_STROKE_LINECAP,
340 [](const std::string& val, SvgBaseDeclaration& declaration) {
341 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
342 attrs.strokeState.SetLineCap(declaration.GetLineCapStyle(val));
343 } },
344 { DOM_SVG_SRC_STROKE_LINEJOIN,
345 [](const std::string& val, SvgBaseDeclaration& declaration) {
346 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
347 attrs.strokeState.SetLineJoin(declaration.GetLineJoinStyle(val));
348 } },
349 { DOM_SVG_SRC_STROKE_MITERLIMIT,
350 [](const std::string& val, SvgBaseDeclaration& declaration) {
351 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
352 double miterLimit = StringToDouble(val);
353 if (GreatOrEqual(miterLimit, 1.0)) {
354 attrs.strokeState.SetMiterLimit(miterLimit);
355 }
356 } },
357 { DOM_SVG_SRC_STROKE_OPACITY,
358 [](const std::string& val, SvgBaseDeclaration& declaration) {
359 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
360 attrs.strokeState.SetOpacity(std::clamp(StringToDouble(val), 0.0, 1.0));
361 } },
362 { DOM_SVG_SRC_STROKE_WIDTH,
363 [](const std::string& val, SvgBaseDeclaration& declaration) {
364 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
365 Dimension lineWidth = StringToDimension(val);
366 if (GreatOrEqual(lineWidth.Value(), 0.0)) {
367 attrs.strokeState.SetLineWidth(lineWidth);
368 }
369 } },
370 { DOM_SVG_STROKE_DASHARRAY,
371 [](const std::string& val, SvgBaseDeclaration& declaration) {
372 if (val.empty()) {
373 return;
374 }
375 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
376 std::vector<double> lineDashVector;
377 StringUtils::StringSplitter(val, ' ', lineDashVector);
378 attrs.strokeState.SetLineDash(lineDashVector);
379 } },
380 { DOM_SVG_STROKE_DASHOFFSET,
381 [](const std::string& val, SvgBaseDeclaration& declaration) {
382 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
383 attrs.strokeState.SetLineDashOffset(StringToDouble(val));
384 } },
385 { DOM_SVG_STROKE_LINECAP,
386 [](const std::string& val, SvgBaseDeclaration& declaration) {
387 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
388 attrs.strokeState.SetLineCap(declaration.GetLineCapStyle(val));
389 } },
390 { DOM_SVG_STROKE_LINEJOIN,
391 [](const std::string& val, SvgBaseDeclaration& declaration) {
392 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
393 attrs.strokeState.SetLineJoin(declaration.GetLineJoinStyle(val));
394 } },
395 { DOM_SVG_STROKE_MITERLIMIT,
396 [](const std::string& val, SvgBaseDeclaration& declaration) {
397 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
398 double miterLimit = StringToDouble(val);
399 if (GreatOrEqual(miterLimit, 1.0)) {
400 attrs.strokeState.SetMiterLimit(miterLimit);
401 }
402 } },
403 { DOM_SVG_STROKE_OPACITY,
404 [](const std::string& val, SvgBaseDeclaration& declaration) {
405 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
406 attrs.strokeState.SetOpacity(std::clamp(StringToDouble(val), 0.0, 1.0));
407 } },
408 { DOM_SVG_STROKE_WIDTH,
409 [](const std::string& val, SvgBaseDeclaration& declaration) {
410 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
411 Dimension lineWidth = StringToDimension(val);
412 if (GreatOrEqual(lineWidth.Value(), 0.0)) {
413 attrs.strokeState.SetLineWidth(lineWidth);
414 }
415 } },
416 { DOM_TRANSFORM,
417 [](const std::string& val, SvgBaseDeclaration& declaration) {
418 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
419 attrs.transform = val;
420 } },
421 { DOM_SVG_SRC_TRANSFORM_ORIGIN,
422 [](const std::string& val, SvgBaseDeclaration& declaration) {
423 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
424 attrs.transformOrigin = val;
425 } },
426 { DOM_SVG_XLINK_HREF,
427 [](const std::string& val, SvgBaseDeclaration& declaration) {
428 auto& attrs = declaration.MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
429 auto value = StringUtils::TrimStr(val);
430 if (value.substr(0, 1) == "#") {
431 attrs.href = value.substr(1);
432 }
433 } }
434 };
435 auto attrIter = BinarySearchFindIndex(svgBaseAttrs, ArraySize(svgBaseAttrs), attr.first.c_str());
436 if (attrIter != -1) {
437 svgBaseAttrs[attrIter].value(attr.second, *this);
438 return true;
439 }
440 return false;
441 }
442
443 void SvgBaseDeclaration::Inherit(const RefPtr<Declaration>& parent)
444 {
445 auto svgDeclaration = AceType::DynamicCast<SvgBaseDeclaration>(parent);
446 if (!svgDeclaration) {
447 LOGD("parent declaration is null");
448 return;
449 }
450 auto& attrs = MaybeResetAttribute<SvgBaseAttribute>(AttributeTag::SPECIALIZED_ATTR);
451 if (!attrs.IsValid()) {
452 LOGE("attrs is invalid");
453 return;
454 }
455 if (!attrs.hasOpacity) {
456 if (svgDeclaration->HasOpacity()) {
457 attrs.opacity = svgDeclaration->GetOpacity();
458 } else {
459 attrs.opacity = 1.0; // default opacity is 1.0
460 }
461 }
462 attrs.fillState.Inherit(svgDeclaration->GetFillState());
463 attrs.strokeState.Inherit(svgDeclaration->GetStrokeState());
464 attrs.textStyle.Inherit(svgDeclaration->GetSvgTextStyle());
465 attrs.clipState.Inherit(svgDeclaration->GetClipState());
466 }
467
468 LineCapStyle SvgBaseDeclaration::GetLineCapStyle(const std::string& val) const
469 {
470 if (val == LINECAP_ROUND) {
471 return LineCapStyle::ROUND;
472 } else if (val == LINECAP_SQUARE) {
473 return LineCapStyle::SQUARE;
474 } else {
475 return LineCapStyle::BUTT;
476 }
477 }
478
479 LineJoinStyle SvgBaseDeclaration::GetLineJoinStyle(const std::string& val) const
480 {
481 if (val == LINEJOIN_BEVEL) {
482 return LineJoinStyle::BEVEL;
483 } else if (val == LINEJOIN_ROUND) {
484 return LineJoinStyle::ROUND;
485 } else {
486 return LineJoinStyle::MITER;
487 }
488 }
489
490 Color SvgBaseDeclaration::GetColor(const std::string& value) const
491 {
492 int64_t colorIndex = BinarySearchFindIndex(COLOR_TABLE, ArraySize(COLOR_TABLE), value.c_str());
493 if (colorIndex != -1) {
494 return COLOR_TABLE[colorIndex].value;
495 }
496 return Color::FromString(value);
497 }
498
499 } // namespace OHOS::Ace
500