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
16 #include "core/components_ng/pattern/text/span_model_ng.h"
17 #include "core/components_ng/render/drawing.h"
18
19 namespace OHOS::Ace::NG {
20
21 #ifdef USE_GRAPHIC_TEXT_GINE
22
23 #define UPDATE_SPAN_FONT_STYLE_ITEM(item, name, value) (item)->fontStyle->Update##name(value)
24
25 #define UPDATE_SPAN_TEXT_LINE_STYLE_ITEM(item, name, value) (item)->textLineStyle->Update##name(value)
26
CreateSpanItem(ArkUI_SpanItem * item)27 RefPtr<SpanItem> SpanModelNG::CreateSpanItem(ArkUI_SpanItem* item)
28 {
29 if (!item) {
30 return nullptr;
31 }
32 if (item->placeholder) {
33 auto* drawingPlaceholder = reinterpret_cast<Rosen::PlaceholderSpan*>(item->placeholder);
34 auto placeholder = AceType::MakeRefPtr<PlaceholderSpanItem>();
35 placeholder->run_.width = drawingPlaceholder->width;
36 placeholder->run_.height = drawingPlaceholder->height;
37 placeholder->run_.alignment = static_cast<PlaceholderAlignment>(drawingPlaceholder->alignment);
38 placeholder->run_.baseline = static_cast<TextBaseline>(drawingPlaceholder->baseline);
39 placeholder->run_.baseline_offset = drawingPlaceholder->baselineOffset;
40 return placeholder;
41 }
42 auto spanItem = AceType::MakeRefPtr<SpanItem>();
43 spanItem->content = item->content;
44 auto* textStyle = reinterpret_cast<RSTextStyle*>(item->textStyle);
45 if (!textStyle) {
46 return spanItem;
47 }
48 spanItem->fontStyle = std::make_unique<FontStyle>();
49 spanItem->textLineStyle = std::make_unique<TextLineStyle>();
50 UPDATE_SPAN_FONT_STYLE_ITEM(spanItem, FontSize, Dimension(textStyle->fontSize));
51 UPDATE_SPAN_FONT_STYLE_ITEM(spanItem, TextColor,
52 Color::FromARGB(textStyle->color.GetAlpha(), textStyle->color.GetRed(), textStyle->color.GetGreen(),
53 textStyle->color.GetBlue()));
54 UPDATE_SPAN_FONT_STYLE_ITEM(spanItem, ItalicFontStyle, static_cast<Ace::FontStyle>(textStyle->fontStyle));
55 UPDATE_SPAN_FONT_STYLE_ITEM(spanItem, FontWeight, static_cast<FontWeight>(textStyle->fontWeight));
56 UPDATE_SPAN_FONT_STYLE_ITEM(spanItem, FontFamily, textStyle->fontFamilies);
57 auto decoration = TextDecoration::INHERIT;
58 switch (textStyle->decoration) {
59 case Rosen::NONE:
60 decoration = TextDecoration::NONE;
61 break;
62 case Rosen::UNDERLINE:
63 decoration = TextDecoration::UNDERLINE;
64 break;
65 case Rosen::OVERLINE:
66 decoration = TextDecoration::OVERLINE;
67 break;
68 case Rosen::LINE_THROUGH:
69 decoration = TextDecoration::LINE_THROUGH;
70 break;
71 break;
72 }
73 UPDATE_SPAN_FONT_STYLE_ITEM(spanItem, TextDecoration, decoration);
74 UPDATE_SPAN_FONT_STYLE_ITEM(
75 spanItem, TextDecorationStyle, static_cast<TextDecorationStyle>(textStyle->decorationStyle));
76 UPDATE_SPAN_FONT_STYLE_ITEM(spanItem, TextDecorationColor,
77 Color::FromARGB(textStyle->decorationColor.GetAlpha(), textStyle->decorationColor.GetRed(),
78 textStyle->decorationColor.GetGreen(), textStyle->decorationColor.GetBlue()));
79 const auto& fontFeatures = textStyle->fontFeatures.GetFontFeatures();
80 FONT_FEATURES_LIST list;
81 for (const auto& item : fontFeatures) {
82 list.emplace_back(item.first, item.second);
83 }
84 UPDATE_SPAN_FONT_STYLE_ITEM(spanItem, FontFeature, list);
85 std::vector<Shadow> shadows;
86 shadows.reserve(textStyle->shadows.size());
87 for (const auto& shadow : textStyle->shadows) {
88 shadows.emplace_back(shadow.blurRadius, 0, Offset { shadow.offset.GetX(), shadow.offset.GetY() },
89 Color::FromARGB(
90 shadow.color.GetAlpha(), shadow.color.GetRed(), shadow.color.GetGreen(), shadow.color.GetBlue()));
91 }
92 UPDATE_SPAN_FONT_STYLE_ITEM(spanItem, TextShadow, shadows);
93 UPDATE_SPAN_FONT_STYLE_ITEM(spanItem, LetterSpacing, Dimension(textStyle->letterSpacing));
94 UPDATE_SPAN_TEXT_LINE_STYLE_ITEM(spanItem, TextBaseline, static_cast<TextBaseline>(textStyle->baseline));
95 UPDATE_SPAN_TEXT_LINE_STYLE_ITEM(spanItem, BaselineOffset, Dimension(textStyle->baseLineShift));
96 UPDATE_SPAN_TEXT_LINE_STYLE_ITEM(spanItem, EllipsisMode, static_cast<EllipsisMode>(textStyle->ellipsisModal));
97 return spanItem;
98 }
99
CreateParagraphStyle(ArkUI_StyledString * styledString)100 ParagraphStyle SpanModelNG::CreateParagraphStyle(ArkUI_StyledString* styledString)
101 {
102 auto typoStyle = reinterpret_cast<Rosen::TypographyStyle*>(styledString->paragraphStyle);
103 TextDirection textDirection;
104 switch (typoStyle->textDirection) {
105 case Rosen::TextDirection::RTL:
106 textDirection = TextDirection::RTL;
107 break;
108 case Rosen::TextDirection::LTR:
109 textDirection = TextDirection::LTR;
110 break;
111 default:
112 textDirection = TextDirection::LTR;
113 break;
114 }
115 TextAlign textAlign;
116 switch (typoStyle->textAlign) {
117 case Rosen::TextAlign::LEFT:
118 textAlign = TextAlign::LEFT;
119 break;
120 case Rosen::TextAlign::RIGHT:
121 textAlign = TextAlign::RIGHT;
122 break;
123 case Rosen::TextAlign::CENTER:
124 textAlign = TextAlign::CENTER;
125 break;
126 case Rosen::TextAlign::JUSTIFY:
127 textAlign = TextAlign::JUSTIFY;
128 break;
129 case Rosen::TextAlign::START:
130 textAlign = TextAlign::START;
131 break;
132 case Rosen::TextAlign::END:
133 textAlign = TextAlign::END;
134 break;
135 default:
136 textAlign = TextAlign::START;
137 break;
138 }
139 std::u16string ELLIPSIS = u"\u2026";
140 ParagraphStyle style = { .direction = textDirection,
141 .align = textAlign,
142 .maxLines = typoStyle->maxLines,
143 .fontLocale = typoStyle->locale,
144 .wordBreak = static_cast<WordBreak>(typoStyle->wordBreakType),
145 .ellipsisMode = static_cast<EllipsisMode>(typoStyle->ellipsisModal),
146 .lineBreakStrategy = static_cast<LineBreakStrategy>(typoStyle->breakStrategy),
147 .textOverflow = typoStyle->ellipsis == ELLIPSIS ? TextOverflow::ELLIPSIS : TextOverflow::CLIP };
148 return style;
149 }
150 #endif
151
152 } // namespace OHOS::Ace::NG