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/action_sheet/js_action_sheet.h"
17
18 #include <string>
19 #include <vector>
20
21 #include "base/log/ace_scoring_log.h"
22 #include "bridge/common/utils/engine_helper.h"
23 #include "bridge/declarative_frontend/engine/functions/js_function.h"
24 #include "bridge/declarative_frontend/engine/js_converter.h"
25 #include "bridge/declarative_frontend/jsview/models/action_sheet_model_impl.h"
26 #include "core/common/container.h"
27 #include "core/components_ng/base/view_stack_processor.h"
28 #include "core/components_ng/pattern/action_sheet/action_sheet_model_ng.h"
29 #include "core/components_ng/pattern/overlay/level_order.h"
30
31 namespace OHOS::Ace {
32 std::unique_ptr<ActionSheetModel> ActionSheetModel::instance_ = nullptr;
33 std::mutex ActionSheetModel::mutex_;
34
GetInstance()35 ActionSheetModel* ActionSheetModel::GetInstance()
36 {
37 if (!instance_) {
38 std::lock_guard<std::mutex> lock(mutex_);
39 if (!instance_) {
40 #ifdef NG_BUILD
41 instance_.reset(new NG::ActionSheetModelNG());
42 #else
43 if (Container::IsCurrentUseNewPipeline()) {
44 instance_.reset(new NG::ActionSheetModelNG());
45 } else {
46 instance_.reset(new Framework::ActionSheetModelImpl());
47 }
48 #endif
49 }
50 }
51 return instance_.get();
52 }
53 } // namespace OHOS::Ace
54
55 namespace OHOS::Ace::Framework {
56 namespace {
57 const DimensionOffset ACTION_SHEET_OFFSET_DEFAULT = DimensionOffset(0.0_vp, -40.0_vp);
58 const DimensionOffset ACTION_SHEET_OFFSET_DEFAULT_TOP = DimensionOffset(0.0_vp, 40.0_vp);
59 const std::vector<DialogAlignment> DIALOG_ALIGNMENT = { DialogAlignment::TOP, DialogAlignment::CENTER,
60 DialogAlignment::BOTTOM, DialogAlignment::DEFAULT, DialogAlignment::TOP_START, DialogAlignment::TOP_END,
61 DialogAlignment::CENTER_START, DialogAlignment::CENTER_END, DialogAlignment::BOTTOM_START,
62 DialogAlignment::BOTTOM_END };
63 const std::vector<LevelMode> DIALOG_LEVEL_MODE = { LevelMode::OVERLAY, LevelMode::EMBEDDED };
64 const std::vector<ImmersiveMode> DIALOG_IMMERSIVE_MODE = { ImmersiveMode::DEFAULT, ImmersiveMode::EXTEND};
65 } // namespace
66
SetParseStyle(ButtonInfo & buttonInfo,const int32_t styleValue)67 static void SetParseStyle(ButtonInfo& buttonInfo, const int32_t styleValue)
68 {
69 if (styleValue >= static_cast<int32_t>(DialogButtonStyle::DEFAULT) &&
70 styleValue <= static_cast<int32_t>(DialogButtonStyle::HIGHTLIGHT)) {
71 buttonInfo.dlgButtonStyle = static_cast<DialogButtonStyle>(styleValue);
72 }
73 }
74
ParseSheetInfo(const JsiExecutionContext & execContext,JSRef<JSVal> val)75 ActionSheetInfo ParseSheetInfo(const JsiExecutionContext& execContext, JSRef<JSVal> val)
76 {
77 ActionSheetInfo sheetInfo;
78 if (!val->IsObject()) {
79 LOGW("param is not an object.");
80 return sheetInfo;
81 }
82
83 auto obj = JSRef<JSObject>::Cast(val);
84 auto titleVal = obj->GetProperty("title");
85 std::string title;
86 if (JSActionSheet::ParseJsString(titleVal, title)) {
87 sheetInfo.title = title;
88 }
89
90 auto iconVal = obj->GetProperty("icon");
91 std::string icon;
92 if (JSActionSheet::ParseJsMedia(iconVal, icon)) {
93 sheetInfo.icon = icon;
94 }
95
96 auto actionValue = obj->GetProperty("action");
97 if (actionValue->IsFunction()) {
98 auto frameNode = AceType::WeakClaim(NG::ViewStackProcessor::GetInstance()->GetMainFrameNode());
99 auto actionFunc = AceType::MakeRefPtr<JsFunction>(JSRef<JSObject>(), JSRef<JSFunc>::Cast(actionValue));
100 auto eventFunc = [execContext, func = std::move(actionFunc), node = frameNode](const GestureEvent&) {
101 JAVASCRIPT_EXECUTION_SCOPE_WITH_CHECK(execContext);
102 ACE_SCORING_EVENT("SheetInfo.action");
103 auto pipelineContext = PipelineContext::GetCurrentContextSafely();
104 CHECK_NULL_VOID(pipelineContext);
105 pipelineContext->UpdateCurrentActiveNode(node);
106 func->ExecuteJS();
107 };
108 ActionSheetModel::GetInstance()->SetAction(eventFunc, sheetInfo);
109 }
110 return sheetInfo;
111 }
112
ParseTitleAndMessage(DialogProperties & properties,JSRef<JSObject> obj)113 void ParseTitleAndMessage(DialogProperties& properties, JSRef<JSObject> obj)
114 {
115 // Parse title.
116 auto titleValue = obj->GetProperty("title");
117 std::string title;
118 if (JSActionSheet::ParseJsString(titleValue, title)) {
119 properties.title = title;
120 }
121
122 // Parse subtitle.
123 auto subtitleValue = obj->GetProperty("subtitle");
124 std::string subtitle;
125 if (JSActionSheet::ParseJsString(subtitleValue, subtitle)) {
126 properties.subtitle = subtitle;
127 }
128
129 // Parses message.
130 auto messageValue = obj->GetProperty("message");
131 std::string message;
132 if (JSActionSheet::ParseJsString(messageValue, message)) {
133 properties.content = message;
134 }
135 }
136
ParseConfirmButton(const JsiExecutionContext & execContext,DialogProperties & properties,JSRef<JSObject> obj)137 void ParseConfirmButton(const JsiExecutionContext& execContext, DialogProperties& properties, JSRef<JSObject> obj)
138 {
139 auto confirmVal = obj->GetProperty("confirm");
140 if (!confirmVal->IsObject()) {
141 return;
142 }
143 JSRef<JSObject> confirmObj = JSRef<JSObject>::Cast(confirmVal);
144 std::string buttonValue;
145 if (JSActionSheet::ParseJsString(confirmObj->GetProperty("value"), buttonValue)) {
146 ButtonInfo buttonInfo = { .text = buttonValue };
147 JSRef<JSVal> actionValue = confirmObj->GetProperty("action");
148 if (actionValue->IsFunction()) {
149 auto frameNode = AceType::WeakClaim(NG::ViewStackProcessor::GetInstance()->GetMainFrameNode());
150 auto actionFunc = AceType::MakeRefPtr<JsFunction>(JSRef<JSObject>(), JSRef<JSFunc>::Cast(actionValue));
151 auto gestureEvent = [execContext, func = std::move(actionFunc), node = frameNode](GestureEvent&) {
152 JAVASCRIPT_EXECUTION_SCOPE_WITH_CHECK(execContext);
153 ACE_SCORING_EVENT("ActionSheet.confirm.action");
154 auto pipelineContext = PipelineContext::GetCurrentContextSafely();
155 CHECK_NULL_VOID(pipelineContext);
156 pipelineContext->UpdateCurrentActiveNode(node);
157 func->ExecuteJS();
158 };
159 actionFunc = AceType::MakeRefPtr<JsFunction>(JSRef<JSObject>(), JSRef<JSFunc>::Cast(actionValue));
160 auto eventFunc = [execContext, func = std::move(actionFunc), node = frameNode]() {
161 JAVASCRIPT_EXECUTION_SCOPE_WITH_CHECK(execContext);
162 ACE_SCORING_EVENT("ActionSheet.confirm.action");
163 auto pipelineContext = PipelineContext::GetCurrentContextSafely();
164 CHECK_NULL_VOID(pipelineContext);
165 pipelineContext->UpdateCurrentActiveNode(node);
166 func->Execute();
167 };
168 ActionSheetModel::GetInstance()->SetConfirm(gestureEvent, eventFunc, buttonInfo, properties);
169 }
170 auto enabledValue = confirmObj->GetProperty("enabled");
171 if (enabledValue->IsBoolean()) {
172 buttonInfo.enabled = enabledValue->ToBoolean();
173 }
174 auto defaultFocusValue = confirmObj->GetProperty("defaultFocus");
175 if (defaultFocusValue->IsBoolean()) {
176 buttonInfo.defaultFocus = defaultFocusValue->ToBoolean();
177 }
178 auto style = confirmObj->GetProperty("style");
179 if (style->IsNumber()) {
180 SetParseStyle(buttonInfo, style->ToNumber<int32_t>());
181 }
182 if (!buttonInfo.defaultFocus) {
183 buttonInfo.isPrimary = true;
184 }
185 if (buttonInfo.IsValid()) {
186 properties.buttons.clear();
187 properties.buttons.emplace_back(buttonInfo);
188 }
189 }
190 }
191
ParseShadow(DialogProperties & properties,JSRef<JSObject> obj)192 void ParseShadow(DialogProperties& properties, JSRef<JSObject> obj)
193 {
194 // Parse shadow.
195 auto shadowValue = obj->GetProperty("shadow");
196 Shadow shadow;
197 if ((shadowValue->IsObject() || shadowValue->IsNumber()) && JSActionSheet::ParseShadowProps(shadowValue, shadow)) {
198 properties.shadow = shadow;
199 }
200 }
201
ParseBorderWidthAndColor(DialogProperties & properties,JSRef<JSObject> obj)202 void ParseBorderWidthAndColor(DialogProperties& properties, JSRef<JSObject> obj)
203 {
204 auto borderWidthValue = obj->GetProperty("borderWidth");
205 NG::BorderWidthProperty borderWidth;
206 if (JSActionSheet::ParseBorderWidthProps(borderWidthValue, borderWidth)) {
207 properties.borderWidth = borderWidth;
208 auto colorValue = obj->GetProperty("borderColor");
209 NG::BorderColorProperty borderColor;
210 if (JSActionSheet::ParseBorderColorProps(colorValue, borderColor)) {
211 properties.borderColor = borderColor;
212 } else {
213 borderColor.SetColor(Color::BLACK);
214 properties.borderColor = borderColor;
215 }
216 }
217 }
218
ParseRadius(DialogProperties & properties,JSRef<JSObject> obj)219 void ParseRadius(DialogProperties& properties, JSRef<JSObject> obj)
220 {
221 auto cornerRadiusValue = obj->GetProperty("cornerRadius");
222 NG::BorderRadiusProperty radius;
223 if (JSActionSheet::ParseBorderRadius(cornerRadiusValue, radius)) {
224 properties.borderRadius = radius;
225 }
226 }
227
UpdateDialogAlignment(DialogAlignment & alignment)228 void UpdateDialogAlignment(DialogAlignment& alignment)
229 {
230 bool isRtl = AceApplicationInfo::GetInstance().IsRightToLeft();
231 if (alignment == DialogAlignment::TOP_START) {
232 if (isRtl) {
233 alignment = DialogAlignment::TOP_END;
234 }
235 } else if (alignment == DialogAlignment::TOP_END) {
236 if (isRtl) {
237 alignment = DialogAlignment::TOP_START;
238 }
239 } else if (alignment == DialogAlignment::CENTER_START) {
240 if (isRtl) {
241 alignment = DialogAlignment::CENTER_END;
242 }
243 } else if (alignment == DialogAlignment::CENTER_END) {
244 if (isRtl) {
245 alignment = DialogAlignment::CENTER_START;
246 }
247 } else if (alignment == DialogAlignment::BOTTOM_START) {
248 if (isRtl) {
249 alignment = DialogAlignment::BOTTOM_END;
250 }
251 } else if (alignment == DialogAlignment::BOTTOM_END) {
252 if (isRtl) {
253 alignment = DialogAlignment::BOTTOM_START;
254 }
255 }
256 }
257
ParseDialogAlignment(DialogProperties & properties,JSRef<JSObject> obj)258 void ParseDialogAlignment(DialogProperties& properties, JSRef<JSObject> obj)
259 {
260 // Parse alignment
261 auto alignmentValue = obj->GetProperty("alignment");
262 if (alignmentValue->IsNumber()) {
263 auto alignment = alignmentValue->ToNumber<int32_t>();
264 if (alignment >= 0 && alignment < static_cast<int32_t>(DIALOG_ALIGNMENT.size())) {
265 properties.alignment = DIALOG_ALIGNMENT[alignment];
266 UpdateDialogAlignment(properties.alignment);
267 }
268 if (alignment == static_cast<int32_t>(DialogAlignment::TOP) ||
269 alignment == static_cast<int32_t>(DialogAlignment::TOP_START) ||
270 alignment == static_cast<int32_t>(DialogAlignment::TOP_END)) {
271 properties.offset = ACTION_SHEET_OFFSET_DEFAULT_TOP;
272 }
273 }
274 }
275
ParseOffset(DialogProperties & properties,JSRef<JSObject> obj)276 void ParseOffset(DialogProperties& properties, JSRef<JSObject> obj)
277 {
278 // Parse offset
279 auto offsetValue = obj->GetProperty("offset");
280 if (offsetValue->IsObject()) {
281 auto offsetObj = JSRef<JSObject>::Cast(offsetValue);
282 CalcDimension dx;
283 auto dxValue = offsetObj->GetProperty("dx");
284 JSActionSheet::ParseJsDimensionVp(dxValue, dx);
285 CalcDimension dy;
286 auto dyValue = offsetObj->GetProperty("dy");
287 JSActionSheet::ParseJsDimensionVp(dyValue, dy);
288 properties.offset = DimensionOffset(dx, dy);
289 bool isRtl = AceApplicationInfo::GetInstance().IsRightToLeft();
290 Dimension offsetX = isRtl ? properties.offset.GetX() * (-1) : properties.offset.GetX();
291 properties.offset.SetX(offsetX);
292 }
293 }
294
ParseMaskRect(DialogProperties & properties,JSRef<JSObject> obj)295 void ParseMaskRect(DialogProperties& properties, JSRef<JSObject> obj)
296 {
297 // Parse maskRect.
298 auto maskRectValue = obj->GetProperty("maskRect");
299 DimensionRect maskRect;
300 if (JSViewAbstract::ParseJsDimensionRect(maskRectValue, maskRect)) {
301 properties.maskRect = maskRect;
302 bool isRtl = AceApplicationInfo::GetInstance().IsRightToLeft();
303 auto offset = maskRect.GetOffset();
304 Dimension offsetX = isRtl ? offset.GetX() * (-1) : offset.GetX();
305 offset.SetX(offsetX);
306 properties.maskRect->SetOffset(offset);
307 }
308 }
309
ParseDialogLevelMode(DialogProperties & properties,JSRef<JSObject> obj)310 void ParseDialogLevelMode(DialogProperties& properties, JSRef<JSObject> obj)
311 {
312 auto levelMode = obj->GetProperty("levelMode");
313 auto levelUniqueId = obj->GetProperty("levelUniqueId");
314 auto immersiveMode = obj->GetProperty("immersiveMode");
315 bool showInMainWindow = true;
316 if (obj->GetProperty("showInSubWindow")->IsBoolean() && obj->GetProperty("showInSubWindow")->ToBoolean()) {
317 showInMainWindow = false;
318 }
319 if (levelMode->IsNumber() && showInMainWindow) {
320 auto mode = levelMode->ToNumber<int32_t>();
321 if (mode >= 0 && mode < static_cast<int32_t>(DIALOG_LEVEL_MODE.size())) {
322 properties.dialogLevelMode = DIALOG_LEVEL_MODE[mode];
323 }
324 }
325 if (levelUniqueId->IsNumber()) {
326 properties.dialogLevelUniqueId = levelUniqueId->ToNumber<int32_t>();
327 }
328 if (immersiveMode->IsNumber()) {
329 auto immersiveVal = immersiveMode->ToNumber<int32_t>();
330 if (immersiveVal >= 0 && immersiveVal < static_cast<int32_t>(DIALOG_IMMERSIVE_MODE.size())) {
331 properties.dialogImmersiveMode = DIALOG_IMMERSIVE_MODE[immersiveVal];
332 }
333 }
334 }
335
ParseLevelOrder(DialogProperties & properties,JSRef<JSObject> obj)336 void ParseLevelOrder(DialogProperties& properties, JSRef<JSObject> obj)
337 {
338 if (properties.isShowInSubWindow) {
339 return;
340 }
341
342 properties.levelOrder = std::make_optional(NG::LevelOrder::ORDER_DEFAULT);
343 auto levelOrderValue = obj->GetProperty("levelOrder");
344 if (!levelOrderValue->IsObject()) {
345 return;
346 }
347 napi_value levelOrderApi = JsConverter::ConvertJsValToNapiValue(levelOrderValue);
348 CHECK_NULL_VOID(levelOrderApi);
349
350 auto engine = EngineHelper::GetCurrentEngine();
351 CHECK_NULL_VOID(engine);
352 NativeEngine* nativeEngine = engine->GetNativeEngine();
353 CHECK_NULL_VOID(nativeEngine);
354 auto env = reinterpret_cast<napi_env>(nativeEngine);
355 NG::LevelOrder* levelOrder = nullptr;
356 napi_status status = napi_unwrap(env, levelOrderApi, reinterpret_cast<void**>(&levelOrder));
357 if (status != napi_ok || !levelOrder) {
358 LOGE("Failed to unwrap LevelOrder.");
359 return;
360 }
361
362 double order = levelOrder->GetOrder();
363 properties.levelOrder = std::make_optional(order);
364 }
365
Show(const JSCallbackInfo & args)366 void JSActionSheet::Show(const JSCallbackInfo& args)
367 {
368 auto scopedDelegate = EngineHelper::GetCurrentDelegateSafely();
369 if (!scopedDelegate) {
370 // this case usually means there is no foreground container, need to figure out the reason.
371 LOGE("scopedDelegate is null, please check");
372 return;
373 }
374 if (!args[0]->IsObject()) {
375 LOGE("args is not an object, can't show ActionSheet.");
376 return;
377 }
378
379 DialogProperties properties {
380 .type = DialogType::ACTION_SHEET, .alignment = DialogAlignment::BOTTOM, .offset = ACTION_SHEET_OFFSET_DEFAULT
381 };
382 auto obj = JSRef<JSObject>::Cast(args[0]);
383 auto execContext = args.GetExecutionContext();
384 auto dialogNode = AceType::WeakClaim(NG::ViewStackProcessor::GetInstance()->GetMainFrameNode());
385
386 ParseTitleAndMessage(properties, obj);
387 ParseConfirmButton(execContext, properties, obj);
388 ParseShadow(properties, obj);
389 ParseBorderWidthAndColor(properties, obj);
390 ParseRadius(properties, obj);
391 ParseDialogAlignment(properties, obj);
392 ParseOffset(properties, obj);
393 ParseMaskRect(properties, obj);
394 ParseDialogLevelMode(properties, obj);
395
396 auto onLanguageChange = [execContext, obj, parseContent = ParseTitleAndMessage, parseButton = ParseConfirmButton,
397 parseShadow = ParseShadow, parseBorderProps = ParseBorderWidthAndColor,
398 parseRadius = ParseRadius, parseAlignment = ParseDialogAlignment,
399 parseOffset = ParseOffset, parseMaskRect = ParseMaskRect,
400 parseDialogLevelMode = ParseDialogLevelMode,
401 node = dialogNode](DialogProperties& dialogProps) {
402 JAVASCRIPT_EXECUTION_SCOPE_WITH_CHECK(execContext);
403 ACE_SCORING_EVENT("ActionSheet.property.onLanguageChange");
404 auto pipelineContext = PipelineContext::GetCurrentContextSafely();
405 CHECK_NULL_VOID(pipelineContext);
406 pipelineContext->UpdateCurrentActiveNode(node);
407 parseContent(dialogProps, obj);
408 parseButton(execContext, dialogProps, obj);
409 parseShadow(dialogProps, obj);
410 parseBorderProps(dialogProps, obj);
411 parseRadius(dialogProps, obj);
412 ParseDialogAlignment(dialogProps, obj);
413 parseOffset(dialogProps, obj);
414 parseMaskRect(dialogProps, obj);
415 parseDialogLevelMode(dialogProps, obj);
416 // Parse sheets
417 auto sheetsVal = obj->GetProperty("sheets");
418 if (sheetsVal->IsArray()) {
419 std::vector<ActionSheetInfo> sheetsInfo;
420 auto sheetsArr = JSRef<JSArray>::Cast(sheetsVal);
421 for (size_t index = 0; index < sheetsArr->Length(); ++index) {
422 sheetsInfo.emplace_back(ParseSheetInfo(execContext, sheetsArr->GetValueAt(index)));
423 }
424 dialogProps.sheetsInfo = std::move(sheetsInfo);
425 }
426 };
427 properties.onLanguageChange = std::move(onLanguageChange);
428
429 // Parse auto autoCancel.
430 auto autoCancelValue = obj->GetProperty("autoCancel");
431 if (autoCancelValue->IsBoolean()) {
432 properties.autoCancel = autoCancelValue->ToBoolean();
433 }
434
435 // Parse cancel.
436 auto cancelValue = obj->GetProperty("cancel");
437 if (cancelValue->IsFunction()) {
438 auto cancelFunc = AceType::MakeRefPtr<JsFunction>(JSRef<JSObject>(), JSRef<JSFunc>::Cast(cancelValue));
439 auto eventFunc = [execContext, func = std::move(cancelFunc), node = dialogNode]() {
440 JAVASCRIPT_EXECUTION_SCOPE_WITH_CHECK(execContext);
441 ACE_SCORING_EVENT("ActionSheet.cancel");
442 auto pipelineContext = PipelineContext::GetCurrentContextSafely();
443 CHECK_NULL_VOID(pipelineContext);
444 pipelineContext->UpdateCurrentActiveNode(node);
445 func->Execute();
446 };
447 ActionSheetModel::GetInstance()->SetCancel(eventFunc, properties);
448 }
449
450 std::function<void(const int32_t& info, const int32_t& instanceId)> onWillDismissFunc = nullptr;
451 ParseDialogCallback(obj, onWillDismissFunc);
452 ActionSheetModel::GetInstance()->SetOnWillDismiss(std::move(onWillDismissFunc), properties);
453
454 JSViewAbstract::ParseAppearDialogCallback(args, properties);
455
456 // Parse sheets
457 auto sheetsVal = obj->GetProperty("sheets");
458 if (sheetsVal->IsArray()) {
459 std::vector<ActionSheetInfo> sheetsInfo;
460 auto sheetsArr = JSRef<JSArray>::Cast(sheetsVal);
461 for (size_t index = 0; index < sheetsArr->Length(); ++index) {
462 sheetsInfo.emplace_back(ParseSheetInfo(execContext, sheetsArr->GetValueAt(index)));
463 }
464 properties.sheetsInfo = std::move(sheetsInfo);
465 }
466
467 // Parses gridCount.
468 auto gridCountValue = obj->GetProperty("gridCount");
469 if (gridCountValue->IsNumber()) {
470 properties.gridCount = gridCountValue->ToNumber<int32_t>();
471 }
472
473 // Parse showInSubWindowValue.
474 auto showInSubWindowValue = obj->GetProperty("showInSubWindow");
475 if (showInSubWindowValue->IsBoolean()) {
476 #if defined(PREVIEW)
477 LOGW("[Engine Log] Unable to use the SubWindow in the Previewer. Perform this operation on the "
478 "emulator or a real device instead.");
479 #else
480 properties.isShowInSubWindow = showInSubWindowValue->ToBoolean();
481 #endif
482 }
483
484 // Parse isModalValue.
485 auto isModalValue = obj->GetProperty("isModal");
486 if (isModalValue->IsBoolean()) {
487 LOGI("Parse isModalValue");
488 properties.isModal = isModalValue->ToBoolean();
489 }
490
491 auto backgroundColorValue = obj->GetProperty("backgroundColor");
492 Color backgroundColor;
493 if (JSViewAbstract::ParseJsColor(backgroundColorValue, backgroundColor)) {
494 properties.backgroundColor = backgroundColor;
495 }
496
497 auto backgroundBlurStyle = obj->GetProperty("backgroundBlurStyle");
498 if (backgroundBlurStyle->IsNumber()) {
499 auto blurStyle = backgroundBlurStyle->ToNumber<int32_t>();
500 if (blurStyle >= static_cast<int>(BlurStyle::NO_MATERIAL) &&
501 blurStyle <= static_cast<int>(BlurStyle::COMPONENT_ULTRA_THICK)) {
502 properties.backgroundBlurStyle = blurStyle;
503 }
504 }
505 // Parse transition.
506 properties.transitionEffect = ParseJsTransitionEffect(args);
507 ParseLevelOrder(properties, obj);
508 JSViewAbstract::SetDialogProperties(obj, properties);
509 JSViewAbstract::SetDialogHoverModeProperties(obj, properties);
510 JSViewAbstract::SetDialogBlurStyleOption(obj, properties);
511 JSViewAbstract::SetDialogEffectOption(obj, properties);
512 ActionSheetModel::GetInstance()->ShowActionSheet(properties);
513 args.SetReturnValue(args.This());
514 }
515
JSBind(BindingTarget globalObj)516 void JSActionSheet::JSBind(BindingTarget globalObj)
517 {
518 JSClass<JSActionSheet>::Declare("ActionSheet");
519 JSClass<JSActionSheet>::StaticMethod("show", &JSActionSheet::Show);
520 JSClass<JSActionSheet>::InheritAndBind<JSViewAbstract>(globalObj);
521 }
522 } // namespace OHOS::Ace::Framework
523