1 /*
2 * Copyright (c) 2021-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 "frameworks/bridge/declarative_frontend/jsview/js_marquee.h"
17
18 #include "base/geometry/dimension.h"
19 #include "base/log/ace_scoring_log.h"
20 #include "bridge/declarative_frontend/engine/functions/js_function.h"
21 #include "bridge/declarative_frontend/jsview/js_view_common_def.h"
22 #include "bridge/declarative_frontend/jsview/models/marquee_model_impl.h"
23 #include "core/components/text/text_theme.h"
24 #include "core/components_ng/pattern/marquee/marquee_model.h"
25 #include "core/components_ng/pattern/marquee/marquee_model_ng.h"
26
27 namespace OHOS::Ace {
28
29 std::unique_ptr<MarqueeModel> MarqueeModel::instance_ = nullptr;
30
GetInstance()31 MarqueeModel* MarqueeModel::GetInstance()
32 {
33 if (!instance_) {
34 #ifdef NG_BUILD
35 instance_.reset(new NG::MarqueeModelNG());
36 #else
37 if (Container::IsCurrentUseNewPipeline()) {
38 instance_.reset(new NG::MarqueeModelNG());
39 } else {
40 instance_.reset(new Framework::MarqueeModelImpl());
41 }
42 #endif
43 }
44 return instance_.get();
45 }
46 } // namespace OHOS::Ace
47
48 namespace OHOS::Ace::Framework {
49
Create(const JSCallbackInfo & info)50 void JSMarquee::Create(const JSCallbackInfo& info)
51 {
52 if (info.Length() < 1 || !info[0]->IsObject()) {
53 LOGE("marquee create error, info is non-valid");
54 return;
55 }
56
57 MarqueeModel::GetInstance()->Create();
58 auto paramObject = JSRef<JSObject>::Cast(info[0]);
59 auto src = paramObject->GetProperty("src");
60 if (!src->IsString()) {
61 LOGE("marquee create error, src is non-valid");
62 return;
63 }
64 MarqueeModel::GetInstance()->SetValue(src->ToString());
65
66 auto getStart = paramObject->GetProperty("start");
67 bool start = getStart->IsBoolean() ? getStart->ToBoolean() : false;
68 MarqueeModel::GetInstance()->SetPlayerStatus(start);
69
70 auto getStep = paramObject->GetProperty("step");
71 if (getStep->IsNumber()) {
72 MarqueeModel::GetInstance()->SetScrollAmount(getStep->ToNumber<double>());
73 }
74
75 auto getLoop = paramObject->GetProperty("loop");
76 if (getLoop->IsNumber()) {
77 MarqueeModel::GetInstance()->SetLoop(getLoop->ToNumber<int32_t>());
78 }
79
80 auto getFromStart = paramObject->GetProperty("fromStart");
81 bool fromStart = getFromStart->IsBoolean() ? getFromStart->ToBoolean() : true;
82 if (fromStart) {
83 MarqueeModel::GetInstance()->SetDirection(MarqueeDirection::LEFT);
84 } else {
85 MarqueeModel::GetInstance()->SetDirection(MarqueeDirection::RIGHT);
86 }
87 }
88
JSBind(BindingTarget globalObj)89 void JSMarquee::JSBind(BindingTarget globalObj)
90 {
91 JSClass<JSMarquee>::Declare("Marquee");
92 MethodOptions opt = MethodOptions::NONE;
93 JSClass<JSMarquee>::StaticMethod("create", &JSMarquee::Create, opt);
94 JSClass<JSMarquee>::StaticMethod("allowScale", &JSMarquee::SetAllowScale);
95 JSClass<JSMarquee>::StaticMethod("fontColor", &JSMarquee::SetTextColor);
96 JSClass<JSMarquee>::StaticMethod("fontSize", &JSMarquee::SetFontSize);
97 JSClass<JSMarquee>::StaticMethod("fontWeight", &JSMarquee::SetFontWeight);
98 JSClass<JSMarquee>::StaticMethod("fontFamily", &JSMarquee::SetFontFamily);
99 JSClass<JSMarquee>::StaticMethod("onStart", &JSMarquee::OnStart);
100 JSClass<JSMarquee>::StaticMethod("onBounce", &JSMarquee::OnBounce);
101 JSClass<JSMarquee>::StaticMethod("onFinish", &JSMarquee::OnFinish);
102 JSClass<JSMarquee>::StaticMethod("onClick", &JSInteractableView::JsOnClick);
103 JSClass<JSMarquee>::StaticMethod("onTouch", &JSInteractableView::JsOnTouch);
104 JSClass<JSMarquee>::StaticMethod("onKeyEvent", &JSInteractableView::JsOnKey);
105 JSClass<JSMarquee>::StaticMethod("onDeleteEvent", &JSInteractableView::JsOnDelete);
106 JSClass<JSMarquee>::StaticMethod("onAppear", &JSInteractableView::JsOnAppear);
107 JSClass<JSMarquee>::StaticMethod("onDisAppear", &JSInteractableView::JsOnDisAppear);
108 JSClass<JSMarquee>::Inherit<JSViewAbstract>();
109 JSClass<JSMarquee>::Bind(globalObj);
110 }
111
SetTextColor(const JSCallbackInfo & info)112 void JSMarquee::SetTextColor(const JSCallbackInfo& info)
113 {
114 if (info.Length() < 1) {
115 LOGE("SetFontColor create error, info is non-valid");
116 return;
117 }
118
119 Color color;
120 if (!ParseJsColor(info[0], color)) {
121 LOGE("the info[0] is null");
122 return;
123 }
124 MarqueeModel::GetInstance()->SetTextColor(color);
125 }
126
SetFontSize(const JSCallbackInfo & info)127 void JSMarquee::SetFontSize(const JSCallbackInfo& info)
128 {
129 if (info.Length() < 1) {
130 LOGE("SetFrontSize create error, info is non-valid");
131 return;
132 }
133
134 Dimension fontSize;
135 if (!ParseJsDimensionFp(info[0], fontSize)) {
136 return;
137 }
138 if (fontSize.IsNegative() || fontSize.Unit() == DimensionUnit::PERCENT) {
139 auto pipelineContext = PipelineContext::GetCurrentContext();
140 CHECK_NULL_VOID_NOLOG(pipelineContext);
141 auto theme = pipelineContext->GetTheme<TextTheme>();
142 CHECK_NULL_VOID_NOLOG(theme);
143 MarqueeModel::GetInstance()->SetFontSize(theme->GetTextStyle().GetFontSize());
144 return;
145 }
146 MarqueeModel::GetInstance()->SetFontSize(fontSize);
147 }
148
SetAllowScale(const JSCallbackInfo & info)149 void JSMarquee::SetAllowScale(const JSCallbackInfo& info)
150 {
151 if (info.Length() < 1 || !info[0]->IsBoolean()) {
152 LOGE("SetAllowScale create error, info is non-valid");
153 return;
154 }
155 MarqueeModel::GetInstance()->SetAllowScale(info[0]->ToBoolean());
156 }
157
SetFontWeight(const std::string & value)158 void JSMarquee::SetFontWeight(const std::string& value)
159 {
160 MarqueeModel::GetInstance()->SetFontWeight(ConvertStrToFontWeight(value));
161 }
162
SetFontFamily(const JSCallbackInfo & info)163 void JSMarquee::SetFontFamily(const JSCallbackInfo& info)
164 {
165 if (info.Length() < 1) {
166 LOGE("SetFrontFamily create error, info is non-valid");
167 return;
168 }
169
170 std::vector<std::string> fontFamilies;
171 if (!ParseJsFontFamilies(info[0], fontFamilies)) {
172 LOGE("Parse FontFamilies failed");
173 return;
174 }
175 MarqueeModel::GetInstance()->SetFontFamily(fontFamilies);
176 }
177
OnStart(const JSCallbackInfo & info)178 void JSMarquee::OnStart(const JSCallbackInfo& info)
179 {
180 if (!info[0]->IsFunction()) {
181 return;
182 }
183
184 auto jsFunc = AceType::MakeRefPtr<JsFunction>(JSRef<JSObject>(), JSRef<JSFunc>::Cast(info[0]));
185 auto onChange = [execCtx = info.GetExecutionContext(), func = std::move(jsFunc)]() {
186 JAVASCRIPT_EXECUTION_SCOPE_WITH_CHECK(execCtx);
187 ACE_SCORING_EVENT("Marquee.onStart");
188 func->ExecuteJS();
189 };
190 MarqueeModel::GetInstance()->SetOnStart(std::move(onChange));
191 }
192
OnBounce(const JSCallbackInfo & info)193 void JSMarquee::OnBounce(const JSCallbackInfo& info)
194 {
195 if (!info[0]->IsFunction()) {
196 return;
197 }
198
199 auto jsFunc = AceType::MakeRefPtr<JsFunction>(JSRef<JSObject>(), JSRef<JSFunc>::Cast(info[0]));
200 auto onChange = [execCtx = info.GetExecutionContext(), func = std::move(jsFunc)]() {
201 JAVASCRIPT_EXECUTION_SCOPE_WITH_CHECK(execCtx);
202 ACE_SCORING_EVENT("Marquee.onBounce");
203 func->ExecuteJS();
204 };
205 MarqueeModel::GetInstance()->SetOnBounce(std::move(onChange));
206 }
207
OnFinish(const JSCallbackInfo & info)208 void JSMarquee::OnFinish(const JSCallbackInfo& info)
209 {
210 if (!info[0]->IsFunction()) {
211 return;
212 }
213
214 auto jsFunc = AceType::MakeRefPtr<JsFunction>(JSRef<JSObject>(), JSRef<JSFunc>::Cast(info[0]));
215 auto onChange = [execCtx = info.GetExecutionContext(), func = std::move(jsFunc)]() {
216 JAVASCRIPT_EXECUTION_SCOPE_WITH_CHECK(execCtx);
217 ACE_SCORING_EVENT("Marquee.onFinish");
218 func->ExecuteJS();
219 };
220 MarqueeModel::GetInstance()->SetOnFinish(std::move(onChange));
221 }
222
223 } // namespace OHOS::Ace::Framework
224