• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2025 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_app_bar_view.h"
17 
18 #include <cstdint>
19 
20 #include "ui/base/utils/utils.h"
21 
22 #include "base/memory/ace_type.h"
23 #include "base/utils/utils.h"
24 #include "bridge/declarative_frontend/engine/jsi/nativeModule/arkts_native_common_bridge.h"
25 #include "core/common/ace_engine.h"
26 #include "core/components_ng/base/frame_node.h"
27 #include "core/components_ng/pattern/container_modal/enhance/container_modal_pattern_enhance.h"
28 #include "core/pipeline_ng/pipeline_context.h"
29 
30 namespace OHOS::Ace::Framework {
31 namespace {
32 const std::string EVENT_NAME_CUSTOM_APP_BAR_MENU_CLICK = "arkui_custom_app_bar_menu_click";
33 const std::string EVENT_NAME_CUSTOM_APP_BAR_CLOSE_CLICK = "arkui_custom_app_bar_close_click";
34 const std::string EVENT_NAME_CUSTOM_APP_BAR_DID_BUILD = "arkui_custom_app_bar_did_build";
35 const std::string EVENT_NAME_CUSTOM_APP_BAR_CREATE_SERVICE_PANEL = "arkui_custom_app_bar_create_service_panel";
36 
37 constexpr int32_t SERVICE_PANEL_PARAM_COUNT = 2;
38 constexpr int32_t PARAM_FIRST = 1;
39 
40 static std::map<std::string, std::function<void(const JSCallbackInfo& info)>> nativeFucMap_;
41 } // namespace
42 
OnMenuClick(const JSCallbackInfo & info)43 void JSAppBar::OnMenuClick(const JSCallbackInfo& info)
44 {
45     TAG_LOGI(AceLogTag::ACE_APPBAR, "JSAppBar OnMenuClick");
46     auto container = Container::Current();
47     CHECK_NULL_VOID(container);
48     auto appBar = container->GetAppBar();
49     CHECK_NULL_VOID(appBar);
50     appBar->OnMenuClick();
51 }
52 
OnCloseClick(const JSCallbackInfo & info)53 void JSAppBar::OnCloseClick(const JSCallbackInfo& info)
54 {
55     TAG_LOGI(AceLogTag::ACE_APPBAR, "JSAppBar OnCloseClick");
56     auto container = Container::Current();
57     CHECK_NULL_VOID(container);
58     auto appBar = container->GetAppBar();
59     CHECK_NULL_VOID(appBar);
60     appBar->OnCloseClick();
61 }
62 
OnDidBuild(const JSCallbackInfo & info)63 void JSAppBar::OnDidBuild(const JSCallbackInfo& info)
64 {
65     TAG_LOGI(AceLogTag::ACE_APPBAR, "JSAppBar OnDidBuild");
66     auto container = Container::Current();
67     CHECK_NULL_VOID(container);
68     auto appBar = container->GetAppBar();
69     CHECK_NULL_VOID(appBar);
70 }
71 
OnCreateServicePanel(const JSCallbackInfo & info)72 void JSAppBar::OnCreateServicePanel(const JSCallbackInfo& info)
73 {
74     TAG_LOGI(AceLogTag::ACE_APPBAR, "JSAppBar OnCreateServicePanel");
75 
76     if (info.Length() < SERVICE_PANEL_PARAM_COUNT) {
77         TAG_LOGI(AceLogTag::ACE_APPBAR, "appbar OnCreateServicePanel param erro");
78         return;
79     }
80     if (!info[PARAM_FIRST]->IsObject()) {
81         TAG_LOGI(AceLogTag::ACE_APPBAR, "appbar OnCreateServicePanel last param erro");
82         return;
83     }
84     JSRef<JSObject> jsObject = JSRef<JSObject>::Cast(info[PARAM_FIRST]);
85     auto bundleName = GetStringValueFromJSObject(jsObject, "bundleName");
86     if (bundleName.empty()) {
87         TAG_LOGI(AceLogTag::ACE_APPBAR, "appbar GetStringValueFromJSObject bundleName param is error");
88         return;
89     }
90 
91     auto abilityName = GetStringValueFromJSObject(jsObject, "abilityName");
92     if (abilityName.empty()) {
93         TAG_LOGI(AceLogTag::ACE_APPBAR, "appbar GetStringValueFromJSObject abilityName param is error");
94         return;
95     }
96 
97     auto jsParams = jsObject->GetProperty("params");
98     if (!jsParams->IsArray()) {
99         TAG_LOGI(AceLogTag::ACE_APPBAR, "appbar GetStringValueFromJSObject jsParams is error");
100         return;
101     }
102     JSRef<JSArray> jsParamsArray = JSRef<JSArray>::Cast(jsParams);
103     std::map<std::string, std::string> params;
104     GetParamsFromJSArray(jsParamsArray, params);
105     if (params.empty()) {
106         TAG_LOGI(AceLogTag::ACE_APPBAR, "appbar GetStringValueFromJSObject paramsMap param is error");
107         return;
108     }
109     auto container = Container::Current();
110     CHECK_NULL_VOID(container);
111     auto appBar = container->GetAppBar();
112     CHECK_NULL_VOID(appBar);
113     appBar->CreateServicePanel(bundleName, abilityName, params);
114 }
115 
GetStringValueFromJSObject(const JSRef<JSObject> & object,const char * prop)116 std::string JSAppBar::GetStringValueFromJSObject(const JSRef<JSObject>& object, const char* prop)
117 {
118     auto jsValue = object->GetProperty(prop);
119     if (!jsValue->IsString()) {
120         return "";
121     }
122     return jsValue->ToString();
123 }
124 
GetParamsFromJSArray(const JSRef<JSArray> & jsArray,std::map<std::string,std::string> & params)125 void JSAppBar::GetParamsFromJSArray(const JSRef<JSArray>& jsArray, std::map<std::string, std::string>& params)
126 {
127     int length = static_cast<int>(jsArray->Length());
128     for (int i = 0; i < length; i++) {
129         JSRef<JSVal> jsValue = jsArray->GetValueAt(i);
130         if (!jsValue->IsString()) {
131             continue;
132         }
133         auto pair = jsValue->ToString();
134         size_t colonPos = pair.find(':');
135         if (colonPos == std::string::npos) {
136             continue;
137         }
138         std::string key = pair.substr(0, colonPos);
139         std::string value = pair.substr(colonPos + 1);
140         if (key.empty() || value.empty()) {
141             continue;
142         }
143         params[key] = value;
144     }
145 }
146 
CallNative(const JSCallbackInfo & info)147 void JSAppBar::CallNative(const JSCallbackInfo& info)
148 {
149     nativeFucMap_ = {
150         { EVENT_NAME_CUSTOM_APP_BAR_MENU_CLICK, JSAppBar::OnMenuClick },
151         { EVENT_NAME_CUSTOM_APP_BAR_CLOSE_CLICK, JSAppBar::OnCloseClick },
152         { EVENT_NAME_CUSTOM_APP_BAR_DID_BUILD, JSAppBar::OnDidBuild },
153         { EVENT_NAME_CUSTOM_APP_BAR_CREATE_SERVICE_PANEL, JSAppBar::OnCreateServicePanel },
154     };
155 
156     if (info.Length() < 1) {
157         TAG_LOGI(AceLogTag::ACE_APPBAR, "appbar callNative param erro");
158         return;
159     }
160     if (!info[0]->IsString()) {
161         TAG_LOGI(AceLogTag::ACE_APPBAR, "appbar callNative first param erro");
162         return;
163     }
164     std::string eventName = info[0]->ToString();
165     TAG_LOGI(AceLogTag::ACE_APPBAR, "appbar callNative eventName = %{public}s", eventName.c_str());
166     auto it = nativeFucMap_.find(eventName);
167     if (it == nativeFucMap_.end()) {
168         TAG_LOGI(AceLogTag::ACE_APPBAR, "appbar Event not found: %{public}s", eventName.c_str());
169         return;
170     }
171     it->second(info);
172 }
173 
JSBind(BindingTarget globalObj)174 void JSAppBar::JSBind(BindingTarget globalObj)
175 {
176     JSClass<JSAppBar>::Declare("ContainerAppBar");
177     JSClass<JSAppBar>::StaticMethod("callNative", &JSAppBar::CallNative);
178     JSClass<JSAppBar>::InheritAndBind<JSContainerBase>(globalObj);
179 }
180 } // namespace OHOS::Ace::Framework
181