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_form.h"
17
18 #include "base/geometry/dimension.h"
19 #include "base/log/log_wrapper.h"
20 #include "base/geometry/ng/size_t.h"
21 #include "base/log/ace_scoring_log.h"
22 #include "bridge/declarative_frontend/jsview/models/form_model_impl.h"
23 #include "core/components_ng/base/view_abstract.h"
24 #include "core/components_ng/pattern/form/form_model_ng.h"
25 #include "frameworks/bridge/declarative_frontend/jsview/js_utils.h"
26 #include "frameworks/bridge/declarative_frontend/view_stack_processor.h"
27
28 #if !defined(WEARABLE_PRODUCT)
29 #include "frameworks/core/components/form/form_component.h"
30 #endif
31
32 namespace OHOS::Ace {
33
34 std::unique_ptr<FormModel> FormModel::instance_ = nullptr;
35 std::mutex FormModel::mutex_;
36
GetInstance()37 FormModel* FormModel::GetInstance()
38 {
39 if (!instance_) {
40 std::lock_guard<std::mutex> lock(mutex_);
41 if (!instance_) {
42 #ifdef NG_BUILD
43 instance_.reset(new NG::FormModelNG());
44 #else
45 if (Container::IsCurrentUseNewPipeline()) {
46 instance_.reset(new NG::FormModelNG());
47 } else {
48 instance_.reset(new Framework::FormModelImpl());
49 }
50 #endif
51 }
52 }
53 return instance_.get();
54 }
55
56 } // namespace OHOS::Ace
57
58 namespace OHOS::Ace::Framework {
59
Create(const JSCallbackInfo & info)60 void JSForm::Create(const JSCallbackInfo& info)
61 {
62 if (info.Length() == 0 || !info[0]->IsObject()) {
63 return;
64 }
65 auto obj = JSRef<JSObject>::Cast(info[0]);
66 JSRef<JSVal> id = obj->GetProperty("id");
67 JSRef<JSVal> name = obj->GetProperty("name");
68 JSRef<JSVal> bundle = obj->GetProperty("bundle");
69 JSRef<JSVal> ability = obj->GetProperty("ability");
70 JSRef<JSVal> module = obj->GetProperty("module");
71 JSRef<JSVal> dimension = obj->GetProperty("dimension");
72 JSRef<JSVal> temporary = obj->GetProperty("temporary");
73 JSRef<JSVal> wantValue = obj->GetProperty("want");
74 JSRef<JSVal> renderingMode = obj->GetProperty("renderingMode");
75 RequestFormInfo fomInfo;
76 fomInfo.id = id->ToNumber<int32_t>();
77 fomInfo.cardName = name->ToString();
78 fomInfo.bundleName = bundle->ToString();
79 fomInfo.abilityName = ability->ToString();
80 fomInfo.moduleName = module->ToString();
81 if (!dimension->IsNull() && !dimension->IsEmpty()) {
82 fomInfo.dimension = dimension->ToNumber<int32_t>();
83 }
84 fomInfo.temporary = temporary->ToBoolean();
85 if (!wantValue->IsNull() && wantValue->IsObject()) {
86 fomInfo.wantWrap = CreateWantWrapFromNapiValue(wantValue);
87 }
88 if (!renderingMode->IsNull() && !renderingMode->IsEmpty()) {
89 fomInfo.renderingMode = renderingMode->ToNumber<int32_t>();
90 }
91 FormModel::GetInstance()->Create(fomInfo);
92 }
93
SetSize(const JSCallbackInfo & info)94 void JSForm::SetSize(const JSCallbackInfo& info)
95 {
96 JSViewAbstract::JsSize(info);
97
98 if (info.Length() == 0 || !info[0]->IsObject()) {
99 return;
100 }
101 Dimension width = 0.0_vp;
102 Dimension height = 0.0_vp;
103
104 JSRef<JSObject> sizeObj = JSRef<JSObject>::Cast(info[0]);
105 JSRef<JSVal> widthValue = sizeObj->GetProperty("width");
106 if (!widthValue->IsNull() && !widthValue->IsEmpty()) {
107 if (widthValue->IsNumber()) {
108 width = Dimension(widthValue->ToNumber<double>(), DimensionUnit::VP);
109 } else if (widthValue->IsString()) {
110 width = StringUtils::StringToDimension(widthValue->ToString(), true);
111 }
112 }
113
114 JSRef<JSVal> heightValue = sizeObj->GetProperty("height");
115 if (!heightValue->IsNull() && !heightValue->IsEmpty()) {
116 if (heightValue->IsNumber()) {
117 height = Dimension(heightValue->ToNumber<double>(), DimensionUnit::VP);
118 } else if (heightValue->IsString()) {
119 height = StringUtils::StringToDimension(heightValue->ToString(), true);
120 }
121 }
122 FormModel::GetInstance()->SetSize(width, height);
123 }
124
SetDimension(int32_t value)125 void JSForm::SetDimension(int32_t value)
126 {
127 FormModel::GetInstance()->SetDimension(value);
128 }
129
AllowUpdate(const JSCallbackInfo & info)130 void JSForm::AllowUpdate(const JSCallbackInfo& info)
131 {
132 if (info.Length() <= 0 || !info[0]->IsBoolean()) {
133 return;
134 }
135
136 auto allowUpdate = info[0]->ToBoolean();
137 FormModel::GetInstance()->AllowUpdate(allowUpdate);
138 }
139
SetVisibility(const JSCallbackInfo & info)140 void JSForm::SetVisibility(const JSCallbackInfo& info)
141 {
142 if (info.Length() <= 0 || !info[0]->IsNumber()) {
143 return;
144 }
145
146 auto type = info[0]->ToNumber<int32_t>();
147 FormModel::GetInstance()->SetVisibility(VisibleType(type));
148 }
149
SetModuleName(const JSCallbackInfo & info)150 void JSForm::SetModuleName(const JSCallbackInfo& info)
151 {
152 if (info.Length() <= 0 || !info[0]->IsString()) {
153 return;
154 }
155
156 auto moduleName = info[0]->ToString();
157 FormModel::GetInstance()->SetModuleName(moduleName);
158 }
159
JsOnAcquired(const JSCallbackInfo & info)160 void JSForm::JsOnAcquired(const JSCallbackInfo& info)
161 {
162 if (info[0]->IsFunction()) {
163 auto jsFunc = AceType::MakeRefPtr<JsFunction>(JSRef<JSObject>(), JSRef<JSFunc>::Cast(info[0]));
164 auto onAcquired = [execCtx = info.GetExecutionContext(), func = std::move(jsFunc)](const std::string& param) {
165 JAVASCRIPT_EXECUTION_SCOPE_WITH_CHECK(execCtx);
166 ACE_SCORING_EVENT("Form.onAcquired");
167 std::vector<std::string> keys = { "id" };
168 func->Execute(keys, param);
169 };
170 FormModel::GetInstance()->SetOnAcquired(std::move(onAcquired));
171 }
172 }
173
JsOnError(const JSCallbackInfo & info)174 void JSForm::JsOnError(const JSCallbackInfo& info)
175 {
176 if (info[0]->IsFunction()) {
177 auto jsFunc = AceType::MakeRefPtr<JsFunction>(JSRef<JSObject>(), JSRef<JSFunc>::Cast(info[0]));
178 auto onError = [execCtx = info.GetExecutionContext(), func = std::move(jsFunc)](const std::string& param) {
179 JAVASCRIPT_EXECUTION_SCOPE_WITH_CHECK(execCtx);
180 ACE_SCORING_EVENT("Form.onError");
181 std::vector<std::string> keys = { "errcode", "msg" };
182 func->Execute(keys, param);
183 };
184 FormModel::GetInstance()->SetOnError(std::move(onError));
185 }
186 }
187
JsOnUninstall(const JSCallbackInfo & info)188 void JSForm::JsOnUninstall(const JSCallbackInfo& info)
189 {
190 if (info[0]->IsFunction()) {
191 auto jsFunc = AceType::MakeRefPtr<JsFunction>(JSRef<JSObject>(), JSRef<JSFunc>::Cast(info[0]));
192 auto onUninstall = [execCtx = info.GetExecutionContext(), func = std::move(jsFunc)](const std::string& param) {
193 JAVASCRIPT_EXECUTION_SCOPE_WITH_CHECK(execCtx);
194 ACE_SCORING_EVENT("Form.onUninstall");
195 std::vector<std::string> keys = { "id" };
196 func->Execute(keys, param);
197 };
198 FormModel::GetInstance()->SetOnUninstall(std::move(onUninstall));
199 }
200 }
201
JsOnRouter(const JSCallbackInfo & info)202 void JSForm::JsOnRouter(const JSCallbackInfo& info)
203 {
204 if (info[0]->IsFunction()) {
205 auto jsFunc = AceType::MakeRefPtr<JsFunction>(JSRef<JSObject>(), JSRef<JSFunc>::Cast(info[0]));
206 auto onRouter = [execCtx = info.GetExecutionContext(), func = std::move(jsFunc)](const std::string& param) {
207 JAVASCRIPT_EXECUTION_SCOPE_WITH_CHECK(execCtx);
208 ACE_SCORING_EVENT("Form.onRouter");
209 std::vector<std::string> keys = { "action" };
210 func->Execute(keys, param);
211 };
212 FormModel::GetInstance()->SetOnRouter(std::move(onRouter));
213 }
214 }
215
JsOnLoad(const JSCallbackInfo & info)216 void JSForm::JsOnLoad(const JSCallbackInfo& info)
217 {
218 if (info[0]->IsFunction()) {
219 auto jsFunc = AceType::MakeRefPtr<JsFunction>(JSRef<JSObject>(), JSRef<JSFunc>::Cast(info[0]));
220 auto onLoad = [execCtx = info.GetExecutionContext(), func = std::move(jsFunc)](const std::string& param) {
221 JAVASCRIPT_EXECUTION_SCOPE_WITH_CHECK(execCtx);
222 ACE_SCORING_EVENT("Form.onLoad");
223 std::vector<std::string> keys;
224 func->Execute(keys, param);
225 };
226 FormModel::GetInstance()->SetOnLoad(std::move(onLoad));
227 }
228 }
229
JSBind(BindingTarget globalObj)230 void JSForm::JSBind(BindingTarget globalObj)
231 {
232 JSClass<JSForm>::Declare("FormComponent");
233 MethodOptions opt = MethodOptions::NONE;
234 JSClass<JSForm>::StaticMethod("create", &JSForm::Create, opt);
235 JSClass<JSForm>::StaticMethod("size", &JSForm::SetSize, opt);
236 JSClass<JSForm>::StaticMethod("dimension", &JSForm::SetDimension, opt);
237 JSClass<JSForm>::StaticMethod("allowUpdate", &JSForm::AllowUpdate, opt);
238 JSClass<JSForm>::StaticMethod("visibility", &JSForm::SetVisibility, opt);
239 JSClass<JSForm>::StaticMethod("moduleName", &JSForm::SetModuleName, opt);
240 JSClass<JSForm>::StaticMethod("clip", &JSViewAbstract::JsClip, opt);
241
242 JSClass<JSForm>::StaticMethod("onAcquired", &JSForm::JsOnAcquired);
243 JSClass<JSForm>::StaticMethod("onError", &JSForm::JsOnError);
244 JSClass<JSForm>::StaticMethod("onUninstall", &JSForm::JsOnUninstall);
245 JSClass<JSForm>::StaticMethod("onRouter", &JSForm::JsOnRouter);
246 JSClass<JSForm>::StaticMethod("onLoad", &JSForm::JsOnLoad);
247 JSClass<JSForm>::StaticMethod("onAppear", &JSInteractableView::JsOnAppear);
248 JSClass<JSForm>::StaticMethod("onDisAppear", &JSInteractableView::JsOnDisAppear);
249 JSClass<JSForm>::StaticMethod("onTouch", &JSInteractableView::JsOnTouch);
250 JSClass<JSForm>::StaticMethod("onKeyEvent", &JSInteractableView::JsOnKey);
251 JSClass<JSForm>::StaticMethod("onDeleteEvent", &JSInteractableView::JsOnDelete);
252 JSClass<JSForm>::StaticMethod("onClick", &JSInteractableView::JsOnClick);
253
254 JSClass<JSForm>::InheritAndBind<JSViewAbstract>(globalObj);
255 }
256
257 } // namespace OHOS::Ace::Framework
258