1 /*
2 * Copyright (c) 2022-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/web/web_pattern.h"
17
18 #include <securec.h>
19 #include <algorithm>
20 #include <unordered_map>
21 #include <vector>
22
23 #include "file_uri.h"
24 #include "image_source.h"
25 #include "input_method_controller.h"
26 #include "parameters.h"
27
28 #if !defined(PREVIEW) && !defined(ACE_UNITTEST)
29 #include "interfaces/inner_api/ui_session/ui_session_manager.h"
30 #endif
31
32 #include "auto_fill_type.h"
33 #include "page_node_info.h"
34
35 #include "adapter/ohos/capability/html/span_to_html.h"
36 #include "base/geometry/ng/offset_t.h"
37 #include "base/geometry/rect.h"
38 #include "base/image/file_uri_helper.h"
39 #include "base/mousestyle/mouse_style.h"
40 #include "base/utils/date_util.h"
41 #include "base/utils/linear_map.h"
42 #include "base/utils/time_util.h"
43 #include "base/utils/utils.h"
44 #include "core/common/ace_engine_ext.h"
45 #include "core/common/ai/data_detector_mgr.h"
46 #include "core/common/ai/image_analyzer_manager.h"
47 #include "core/common/ime/input_method_manager.h"
48 #include "core/common/udmf/udmf_client.h"
49 #include "core/common/udmf/unified_data.h"
50 #include "core/common/vibrator/vibrator_utils.h"
51 #include "core/components/dialog/dialog_theme.h"
52 #include "core/components/picker/picker_data.h"
53 #include "core/components/text_overlay/text_overlay_theme.h"
54 #include "core/components/web/resource/web_delegate.h"
55 #include "core/components/web/web_property.h"
56 #include "core/components_ng/base/view_stack_processor.h"
57 #include "core/components_ng/pattern/dialog/dialog_pattern.h"
58 #include "core/components_ng/pattern/linear_layout/linear_layout_pattern.h"
59 #include "core/components_ng/pattern/list/list_pattern.h"
60 #include "core/components_ng/pattern/menu/menu_view.h"
61 #include "core/components_ng/pattern/menu/wrapper/menu_wrapper_pattern.h"
62 #include "core/components_ng/pattern/overlay/overlay_manager.h"
63 #include "core/components_ng/pattern/refresh/refresh_pattern.h"
64 #include "core/components_ng/pattern/select_overlay/select_overlay_pattern.h"
65 #include "core/components_ng/pattern/swiper/swiper_pattern.h"
66 #include "core/components_ng/pattern/text/text_pattern.h"
67 #include "core/components_ng/pattern/text_field/text_field_manager.h"
68 #include "core/components_ng/pattern/web/web_event_hub.h"
69 #include "core/event/key_event.h"
70 #include "core/event/touch_event.h"
71 #include "core/pipeline_ng/pipeline_context.h"
72 #include "frameworks/base/utils/system_properties.h"
73 #include "frameworks/core/components_ng/base/ui_node.h"
74 #include "display_manager.h"
75
76 namespace OHOS::Ace::NG {
77 namespace {
78 const std::string IMAGE_POINTER_CONTEXT_MENU_PATH = "etc/webview/ohos_nweb/context-menu.svg";
79 const std::string IMAGE_POINTER_ALIAS_PATH = "etc/webview/ohos_nweb/alias.svg";
80 const std::string WEB_INFO_PC = "8";
81 const std::string WEB_INFO_TABLET = "4";
82 const std::string WEB_INFO_PHONE = "2";
83 const std::string WEB_INFO_DEFAULT = "1";
84 const std::string AUTO_FILL_VIEW_DATA_PAGE_URL = "autofill_viewdata_origin_pageurl";
85 const std::string AUTO_FILL_VIEW_DATA_OTHER_ACCOUNT = "autofill_viewdata_other_account";
86 constexpr int32_t UPDATE_WEB_LAYOUT_DELAY_TIME = 20;
87 constexpr int32_t AUTOFILL_DELAY_TIME = 200;
88 constexpr int32_t TOUCH_EVENT_MAX_SIZE = 5;
89 constexpr int32_t IMAGE_POINTER_CUSTOM_CHANNEL = 4;
90 constexpr int32_t KEYEVENT_MAX_NUM = 1000;
91 constexpr int32_t RESERVED_DEVICEID = 0xAAAAAAFF;
92 const LinearEnumMapNode<OHOS::NWeb::CursorType, MouseFormat> g_cursorTypeMap[] = {
93 { OHOS::NWeb::CursorType::CT_CROSS, MouseFormat::CROSS },
94 { OHOS::NWeb::CursorType::CT_HAND, MouseFormat::HAND_POINTING },
95 { OHOS::NWeb::CursorType::CT_IBEAM, MouseFormat::TEXT_CURSOR },
96 { OHOS::NWeb::CursorType::CT_WAIT, MouseFormat::LOADING },
97 { OHOS::NWeb::CursorType::CT_HELP, MouseFormat::HELP },
98 { OHOS::NWeb::CursorType::CT_EASTRESIZE, MouseFormat::WEST_EAST },
99 { OHOS::NWeb::CursorType::CT_NORTHRESIZE, MouseFormat::NORTH_SOUTH },
100 { OHOS::NWeb::CursorType::CT_NORTHEASTRESIZE, MouseFormat::NORTH_EAST_SOUTH_WEST },
101 { OHOS::NWeb::CursorType::CT_NORTHWESTRESIZE, MouseFormat::NORTH_WEST_SOUTH_EAST },
102 { OHOS::NWeb::CursorType::CT_SOUTHRESIZE, MouseFormat::NORTH_SOUTH },
103 { OHOS::NWeb::CursorType::CT_SOUTHEASTRESIZE, MouseFormat::NORTH_WEST_SOUTH_EAST },
104 { OHOS::NWeb::CursorType::CT_SOUTHWESTRESIZE, MouseFormat::NORTH_EAST_SOUTH_WEST },
105 { OHOS::NWeb::CursorType::CT_WESTRESIZE, MouseFormat::WEST_EAST },
106 { OHOS::NWeb::CursorType::CT_NORTHSOUTHRESIZE, MouseFormat::NORTH_SOUTH },
107 { OHOS::NWeb::CursorType::CT_EASTWESTRESIZE, MouseFormat::WEST_EAST },
108 { OHOS::NWeb::CursorType::CT_NORTHEASTSOUTHWESTRESIZE, MouseFormat::NORTH_EAST_SOUTH_WEST },
109 { OHOS::NWeb::CursorType::CT_NORTHWESTSOUTHEASTRESIZE, MouseFormat::NORTH_WEST_SOUTH_EAST },
110 { OHOS::NWeb::CursorType::CT_COLUMNRESIZE, MouseFormat::RESIZE_LEFT_RIGHT },
111 { OHOS::NWeb::CursorType::CT_ROWRESIZE, MouseFormat::RESIZE_UP_DOWN },
112 { OHOS::NWeb::CursorType::CT_MIDDLEPANNING, MouseFormat::MIDDLE_BTN_NORTH_SOUTH_WEST_EAST },
113 { OHOS::NWeb::CursorType::CT_EASTPANNING, MouseFormat::MIDDLE_BTN_EAST },
114 { OHOS::NWeb::CursorType::CT_NORTHPANNING, MouseFormat::MIDDLE_BTN_NORTH },
115 { OHOS::NWeb::CursorType::CT_NORTHEASTPANNING, MouseFormat::MIDDLE_BTN_NORTH_EAST },
116 { OHOS::NWeb::CursorType::CT_NORTHWESTPANNING, MouseFormat::MIDDLE_BTN_NORTH_WEST },
117 { OHOS::NWeb::CursorType::CT_SOUTHPANNING, MouseFormat::MIDDLE_BTN_SOUTH },
118 { OHOS::NWeb::CursorType::CT_SOUTHEASTPANNING, MouseFormat::MIDDLE_BTN_SOUTH_EAST },
119 { OHOS::NWeb::CursorType::CT_SOUTHWESTPANNING, MouseFormat::MIDDLE_BTN_SOUTH_WEST },
120 { OHOS::NWeb::CursorType::CT_WESTPANNING, MouseFormat::MIDDLE_BTN_WEST },
121 { OHOS::NWeb::CursorType::CT_MOVE, MouseFormat::CURSOR_MOVE },
122 { OHOS::NWeb::CursorType::CT_VERTICALTEXT, MouseFormat::HORIZONTAL_TEXT_CURSOR },
123 { OHOS::NWeb::CursorType::CT_CELL, MouseFormat::CURSOR_CROSS },
124 { OHOS::NWeb::CursorType::CT_PROGRESS, MouseFormat::RUNNING },
125 { OHOS::NWeb::CursorType::CT_NODROP, MouseFormat::CURSOR_FORBID },
126 { OHOS::NWeb::CursorType::CT_COPY, MouseFormat::CURSOR_COPY },
127 { OHOS::NWeb::CursorType::CT_NONE, MouseFormat::CURSOR_NONE },
128 { OHOS::NWeb::CursorType::CT_NOTALLOWED, MouseFormat::CURSOR_FORBID },
129 { OHOS::NWeb::CursorType::CT_ZOOMIN, MouseFormat::ZOOM_IN },
130 { OHOS::NWeb::CursorType::CT_ZOOMOUT, MouseFormat::ZOOM_OUT },
131 { OHOS::NWeb::CursorType::CT_GRAB, MouseFormat::HAND_OPEN },
132 { OHOS::NWeb::CursorType::CT_GRABBING, MouseFormat::HAND_GRABBING },
133 { OHOS::NWeb::CursorType::CT_MIDDLE_PANNING_VERTICAL, MouseFormat::MIDDLE_BTN_NORTH_SOUTH },
134 { OHOS::NWeb::CursorType::CT_MIDDLE_PANNING_HORIZONTAL, MouseFormat::MIDDLE_BTN_NORTH_SOUTH_WEST_EAST },
135 };
136
137 std::unordered_map<KeyCode, KeyCode> g_numPadFunctionMap = {
138 { KeyCode::KEY_NUMPAD_0, KeyCode::KEY_INSERT },
139 { KeyCode::KEY_NUMPAD_1, KeyCode::KEY_MOVE_END },
140 { KeyCode::KEY_NUMPAD_2, KeyCode::KEY_DPAD_DOWN },
141 { KeyCode::KEY_NUMPAD_3, KeyCode::KEY_PAGE_DOWN },
142 { KeyCode::KEY_NUMPAD_4, KeyCode::KEY_DPAD_LEFT },
143 { KeyCode::KEY_NUMPAD_5, KeyCode::KEY_CLEAR },
144 { KeyCode::KEY_NUMPAD_6, KeyCode::KEY_DPAD_RIGHT },
145 { KeyCode::KEY_NUMPAD_7, KeyCode::KEY_MOVE_HOME },
146 { KeyCode::KEY_NUMPAD_8, KeyCode::KEY_DPAD_UP },
147 { KeyCode::KEY_NUMPAD_9, KeyCode::KEY_PAGE_UP },
148 { KeyCode::KEY_NUMPAD_DIVIDE, KeyCode::KEY_NUMPAD_DIVIDE },
149 { KeyCode::KEY_NUMPAD_MULTIPLY, KeyCode::KEY_NUMPAD_MULTIPLY },
150 { KeyCode::KEY_NUMPAD_SUBTRACT, KeyCode::KEY_NUMPAD_SUBTRACT },
151 { KeyCode::KEY_NUMPAD_ADD, KeyCode::KEY_NUMPAD_ADD },
152 { KeyCode::KEY_NUMPAD_DOT, KeyCode::KEY_NUMPAD_DOT },
153 { KeyCode::KEY_NUMPAD_ENTER, KeyCode::KEY_NUMPAD_ENTER }
154 };
155
156 constexpr Dimension OPTION_MARGIN = 8.0_vp;
157 constexpr Dimension CALIBERATE_X = 4.0_vp;
158 constexpr Color SELECTED_OPTION_FONT_COLOR = Color(0xff0a59f7);
159 constexpr Color SELECTED_OPTION_BACKGROUND_COLOR = Color(0x19254FF7);
160
161 constexpr int32_t HALF = 2;
162 constexpr int32_t AI_TIMEOUT_LIMIT = 200;
163
164 constexpr int32_t CHECK_PRE_SIZE = 5;
165 constexpr int32_t ADJUST_RATIO = 10;
166
ParseDateTimeJson(const std::string & timeJson,NWeb::DateTime & result)167 bool ParseDateTimeJson(const std::string& timeJson, NWeb::DateTime& result)
168 {
169 auto sourceJson = JsonUtil::ParseJsonString(timeJson);
170 if (!sourceJson || sourceJson->IsNull()) {
171 return false;
172 }
173
174 auto year = sourceJson->GetValue("year");
175 if (year && year->IsNumber()) {
176 result.year = year->GetInt();
177 }
178 auto month = sourceJson->GetValue("month");
179 if (month && month->IsNumber()) {
180 result.month = month->GetInt();
181 }
182 auto day = sourceJson->GetValue("day");
183 if (day && day->IsNumber()) {
184 result.day = day->GetInt();
185 }
186 auto hour = sourceJson->GetValue("hour");
187 if (hour && hour->IsNumber()) {
188 result.hour = hour->GetInt();
189 }
190 auto minute = sourceJson->GetValue("minute");
191 if (minute && minute->IsNumber()) {
192 result.minute = minute->GetInt();
193 }
194 return true;
195 }
196
ParseTextJsonValue(const std::string & textJson)197 std::string ParseTextJsonValue(const std::string& textJson)
198 {
199 auto sourceJson = JsonUtil::ParseJsonString(textJson);
200 if (!sourceJson || sourceJson->IsNull()) {
201 return "";
202 }
203 auto value = sourceJson->GetValue("value");
204 if (value && value->IsString()) {
205 return value->GetString();
206 }
207 return "";
208 }
209
210 const std::map<std::string, AceAutoFillType> NWEB_AUTOFILL_TYPE_TO_ACE = {
211 {OHOS::NWeb::NWEB_AUTOFILL_STREET_ADDRESS, AceAutoFillType::ACE_FULL_STREET_ADDRESS},
212 {OHOS::NWeb::NWEB_AUTOFILL_ADDRESS_LEVEL_3, AceAutoFillType::ACE_DISTRICT_ADDRESS},
213 {OHOS::NWeb::NWEB_AUTOFILL_ADDRESS_LEVEL_2, AceAutoFillType::ACE_CITY_ADDRESS},
214 {OHOS::NWeb::NWEB_AUTOFILL_ADDRESS_LEVEL_1, AceAutoFillType::ACE_PROVINCE_ADDRESS},
215 {OHOS::NWeb::NWEB_AUTOFILL_COUNTRY, AceAutoFillType::ACE_COUNTRY_ADDRESS},
216 {OHOS::NWeb::NWEB_AUTOFILL_NAME, AceAutoFillType::ACE_PERSON_FULL_NAME},
217 {OHOS::NWeb::NWEB_AUTOFILL_FAMILY_NAME, AceAutoFillType::ACE_PERSON_LAST_NAME},
218 {OHOS::NWeb::NWEB_AUTOFILL_GIVEN_NAME, AceAutoFillType::ACE_PERSON_FIRST_NAME},
219 {OHOS::NWeb::NWEB_AUTOFILL_TEL_NATIONAL, AceAutoFillType::ACE_PHONE_NUMBER},
220 {OHOS::NWeb::NWEB_AUTOFILL_TEL, AceAutoFillType::ACE_FULL_PHONE_NUMBER},
221 {OHOS::NWeb::NWEB_AUTOFILL_TEL_COUNTRY_CODE, AceAutoFillType::ACE_PHONE_COUNTRY_CODE},
222 {OHOS::NWeb::NWEB_AUTOFILL_EMAIL, AceAutoFillType::ACE_EMAIL_ADDRESS},
223 {OHOS::NWeb::NWEB_AUTOFILL_CC_NUMBER, AceAutoFillType::ACE_BANK_CARD_NUMBER},
224 {OHOS::NWeb::NWEB_AUTOFILL_ID_CARD_NUMBER, AceAutoFillType::ACE_ID_CARD_NUMBER},
225 {OHOS::NWeb::NWEB_AUTOFILL_DETAIL_INFO_WITHOUT_STREET, AceAutoFillType::ACE_DETAIL_INFO_WITHOUT_STREET},
226 {OHOS::NWeb::NWEB_AUTOFILL_FORMAT_ADDRESS, AceAutoFillType::ACE_FORMAT_ADDRESS},
227 {OHOS::NWeb::NWEB_AUTOFILL_NICKNAME, AceAutoFillType::ACE_NICKNAME},
228 {OHOS::NWeb::NWEB_AUTOFILL_USERNAME, AceAutoFillType::ACE_USER_NAME},
229 {OHOS::NWeb::NWEB_AUTOFILL_PASSWORD, AceAutoFillType::ACE_PASSWORD},
230 {OHOS::NWeb::NWEB_AUTOFILL_NEW_PASSWORD, AceAutoFillType::ACE_NEW_PASSWORD},
231 };
232
233 const std::map<AceAutoFillType, std::string> ACE_AUTOFILL_TYPE_TO_NWEB = {
234 {AceAutoFillType::ACE_FULL_STREET_ADDRESS, OHOS::NWeb::NWEB_AUTOFILL_STREET_ADDRESS},
235 {AceAutoFillType::ACE_DISTRICT_ADDRESS, OHOS::NWeb::NWEB_AUTOFILL_ADDRESS_LEVEL_3},
236 {AceAutoFillType::ACE_CITY_ADDRESS, OHOS::NWeb::NWEB_AUTOFILL_ADDRESS_LEVEL_2},
237 {AceAutoFillType::ACE_PROVINCE_ADDRESS, OHOS::NWeb::NWEB_AUTOFILL_ADDRESS_LEVEL_1},
238 {AceAutoFillType::ACE_COUNTRY_ADDRESS, OHOS::NWeb::NWEB_AUTOFILL_COUNTRY},
239 {AceAutoFillType::ACE_PERSON_FULL_NAME, OHOS::NWeb::NWEB_AUTOFILL_NAME},
240 {AceAutoFillType::ACE_PERSON_LAST_NAME, OHOS::NWeb::NWEB_AUTOFILL_FAMILY_NAME},
241 {AceAutoFillType::ACE_PERSON_FIRST_NAME, OHOS::NWeb::NWEB_AUTOFILL_GIVEN_NAME},
242 {AceAutoFillType::ACE_PHONE_NUMBER, OHOS::NWeb::NWEB_AUTOFILL_TEL_NATIONAL},
243 {AceAutoFillType::ACE_FULL_PHONE_NUMBER, OHOS::NWeb::NWEB_AUTOFILL_TEL},
244 {AceAutoFillType::ACE_PHONE_COUNTRY_CODE, OHOS::NWeb::NWEB_AUTOFILL_TEL_COUNTRY_CODE},
245 {AceAutoFillType::ACE_EMAIL_ADDRESS, OHOS::NWeb::NWEB_AUTOFILL_EMAIL},
246 {AceAutoFillType::ACE_BANK_CARD_NUMBER, OHOS::NWeb::NWEB_AUTOFILL_CC_NUMBER},
247 {AceAutoFillType::ACE_ID_CARD_NUMBER, OHOS::NWeb::NWEB_AUTOFILL_ID_CARD_NUMBER},
248 {AceAutoFillType::ACE_DETAIL_INFO_WITHOUT_STREET, OHOS::NWeb::NWEB_AUTOFILL_DETAIL_INFO_WITHOUT_STREET},
249 {AceAutoFillType::ACE_FORMAT_ADDRESS, OHOS::NWeb::NWEB_AUTOFILL_FORMAT_ADDRESS},
250 {AceAutoFillType::ACE_NICKNAME, OHOS::NWeb::NWEB_AUTOFILL_NICKNAME},
251 {AceAutoFillType::ACE_USER_NAME, OHOS::NWeb::NWEB_AUTOFILL_USERNAME},
252 {AceAutoFillType::ACE_PASSWORD, OHOS::NWeb::NWEB_AUTOFILL_PASSWORD},
253 {AceAutoFillType::ACE_NEW_PASSWORD, OHOS::NWeb::NWEB_AUTOFILL_NEW_PASSWORD},
254 };
255
256 const std::map<std::string, OHOS::NWeb::NWebAutofillEvent> NWEB_AUTOFILL_EVENTS = {
257 {OHOS::NWeb::NWEB_AUTOFILL_EVENT_SAVE, OHOS::NWeb::NWebAutofillEvent::SAVE},
258 {OHOS::NWeb::NWEB_AUTOFILL_EVENT_FILL, OHOS::NWeb::NWebAutofillEvent::FILL},
259 {OHOS::NWeb::NWEB_AUTOFILL_EVENT_UPDATE, OHOS::NWeb::NWebAutofillEvent::UPDATE},
260 {OHOS::NWeb::NWEB_AUTOFILL_EVENT_CLOSE, OHOS::NWeb::NWebAutofillEvent::CLOSE},
261 };
262 } // namespace
263
264 constexpr int32_t SINGLE_CLICK_NUM = 1;
265 constexpr int32_t DOUBLE_CLICK_NUM = 2;
266 constexpr double DEFAULT_DBCLICK_INTERVAL = 0.5;
267 constexpr double DEFAULT_DBCLICK_OFFSET = 2.0;
268 constexpr double DEFAULT_AXIS_RATIO = -12.5;
269 constexpr double DEFAULT_WEB_WIDTH = 100.0;
270 constexpr double DEFAULT_WEB_HEIGHT = 80.0;
271 constexpr Dimension TOOLTIP_BORDER_WIDTH = 1.0_vp;
272 constexpr Dimension TOOLTIP_FONT_SIZE = 14.0_vp;
273 constexpr Dimension TOOLTIP_PADDING = 8.0_vp;
274 constexpr float TOOLTIP_MAX_PORTION = 0.35f;
275 constexpr float TOOLTIP_MARGIN = 10.0f;
276 constexpr float TOOLTIP_DELAY_MS = 700;
277 constexpr uint32_t ADJUST_WEB_DRAW_LENGTH = 3000;
278 constexpr int32_t FIT_CONTENT_LIMIT_LENGTH = 8000;
279 const std::string PATTERN_TYPE_WEB = "WEBPATTERN";
280 const std::string DEFAULT_WEB_TEXT_ENCODING_FORMAT = "UTF-8";
281 constexpr int32_t SYNC_SURFACE_QUEUE_SIZE = 8;
282 constexpr int32_t ASYNC_SURFACE_QUEUE_SIZE_FOR_PHONE = 5;
283 constexpr int32_t ASYNC_SURFACE_QUEUE_SIZE_FOR_OTHERS = 4;
284 constexpr uint32_t DEBUG_DRAGMOVEID_TIMER = 30;
285 // web feature params
286 constexpr char VISIBLE_ACTIVE_ENABLE[] = "persist.web.visible_active_enable";
287 constexpr char MEMORY_LEVEL_ENABEL[] = "persist.web.memory_level_enable";
288 const std::vector<std::string> SYNC_RENDER_SLIDE {V2::LIST_ETS_TAG, V2::SCROLL_ETS_TAG};
289
290 constexpr int32_t DEFAULT_PINCH_FINGER = 2;
291 constexpr double DEFAULT_PINCH_DISTANCE = 5.0;
292 constexpr double DEFAULT_PINCH_SCALE = 1.0;
293 constexpr double DEFAULT_PINCH_SCALE_MAX = 5.0;
294 constexpr double DEFAULT_PINCH_SCALE_MIN = 0.32;
295 constexpr int32_t PINCH_INDEX_ONE = 1;
296 constexpr int32_t STATUS_ZOOMIN = 1;
297 constexpr int32_t STATUS_ZOOMOUT = 2;
298 constexpr int32_t ZOOM_ERROR_COUNT_MAX = 5;
299 constexpr double ZOOMIN_SMOOTH_SCALE = 0.99;
300 constexpr int32_t POPUP_CALCULATE_RATIO = 2;
301
302 constexpr int32_t PINCH_START_TYPE = 1;
303 constexpr int32_t PINCH_UPDATE_TYPE = 3;
304 constexpr int32_t PINCH_END_TYPE = 2;
305
306 constexpr char ACCESSIBILITY_GENERIC_CONTAINER[] = "genericContainer";
307 constexpr char ACCESSIBILITY_IMAGE[] = "image";
308 constexpr char ACCESSIBILITY_PARAGRAPH[] = "paragraph";
309 constexpr char WEB_NODE_URL[] = "url";
310
311 const std::string IS_HINT_TYPE = "{\"isHint2Type\": true}";
312 const std::string STRING_LF = "\n";
313 const std::string DRAG_DATA_TYPE_TEXT = "general.plain-text";
314 const std::string DRAG_DATA_TYPE_HTML = "general.html";
315 const std::set<std::string> FILE_TYPE_SET = {"general.file", "general.audio", "general.video", "general.image"};
316 const std::string DRAG_DATA_TYPE_LINK = "general.hyperlink";
317 const std::string FAKE_DRAG_DATA_VAL = " ";
318 const std::string FAKE_LINK_VAL = "https://xxx.xxx.xxx";
319
320 #define WEB_ACCESSIBILITY_DELAY_TIME 100
321
322 class WebAccessibilityChildTreeCallback : public AccessibilityChildTreeCallback {
323 public:
WebAccessibilityChildTreeCallback(const WeakPtr<WebPattern> & weakPattern,int64_t accessibilityId)324 WebAccessibilityChildTreeCallback(const WeakPtr<WebPattern> &weakPattern, int64_t accessibilityId)
325 : AccessibilityChildTreeCallback(accessibilityId), weakPattern_(weakPattern)
326 {}
327
328 ~WebAccessibilityChildTreeCallback() override = default;
329
OnRegister(uint32_t windowId,int32_t treeId)330 bool OnRegister(uint32_t windowId, int32_t treeId) override
331 {
332 auto pattern = weakPattern_.Upgrade();
333 if (pattern == nullptr) {
334 return false;
335 }
336 if (isReg_) {
337 return true;
338 }
339 if (!pattern->OnAccessibilityChildTreeRegister()) {
340 return false;
341 }
342 pattern->SetAccessibilityState(true, isDelayed_);
343 isDelayed_ = false;
344 isReg_ = true;
345 return true;
346 }
347
OnDeregister()348 bool OnDeregister() override
349 {
350 auto pattern = weakPattern_.Upgrade();
351 if (pattern == nullptr) {
352 return false;
353 }
354 if (!isReg_) {
355 return true;
356 }
357 if (!pattern->OnAccessibilityChildTreeDeregister()) {
358 return false;
359 }
360 pattern->SetAccessibilityState(false);
361 isReg_ = false;
362 return true;
363 }
364
OnSetChildTree(int32_t childWindowId,int32_t childTreeId)365 bool OnSetChildTree(int32_t childWindowId, int32_t childTreeId) override
366 {
367 auto pattern = weakPattern_.Upgrade();
368 if (pattern == nullptr) {
369 return false;
370 }
371 pattern->OnSetAccessibilityChildTree(childWindowId, childTreeId);
372 return true;
373 }
374
OnDumpChildInfo(const std::vector<std::string> & params,std::vector<std::string> & info)375 bool OnDumpChildInfo(const std::vector<std::string>& params, std::vector<std::string>& info) override
376 {
377 return false;
378 }
379
OnClearRegisterFlag()380 void OnClearRegisterFlag() override
381 {
382 auto pattern = weakPattern_.Upgrade();
383 if (pattern == nullptr) {
384 return;
385 }
386 isReg_ = false;
387 }
388
SetIsDelayed(bool isDelayed)389 void SetIsDelayed(bool isDelayed)
390 {
391 isDelayed_ = isDelayed;
392 }
393
394 private:
395 bool isReg_ = false;
396 bool isDelayed_ = false;
397 WeakPtr<WebPattern> weakPattern_;
398 };
399
WebPattern()400 WebPattern::WebPattern()
401 {
402 InitMagnifier();
403 renderMode_ = RenderMode::ASYNC_RENDER;
404 }
405
WebPattern(const std::string & webSrc,const RefPtr<WebController> & webController,RenderMode renderMode,bool incognitoMode,const std::string & sharedRenderProcessToken)406 WebPattern::WebPattern(const std::string& webSrc, const RefPtr<WebController>& webController, RenderMode renderMode,
407 bool incognitoMode, const std::string& sharedRenderProcessToken)
408 : webSrc_(std::move(webSrc)), webController_(webController), renderMode_(renderMode), incognitoMode_(incognitoMode),
409 sharedRenderProcessToken_(sharedRenderProcessToken)
410 {
411 InitMagnifier();
412 }
413
WebPattern(const std::string & webSrc,const SetWebIdCallback & setWebIdCallback,RenderMode renderMode,bool incognitoMode,const std::string & sharedRenderProcessToken)414 WebPattern::WebPattern(const std::string& webSrc, const SetWebIdCallback& setWebIdCallback, RenderMode renderMode,
415 bool incognitoMode, const std::string& sharedRenderProcessToken)
416 : webSrc_(std::move(webSrc)), setWebIdCallback_(setWebIdCallback), renderMode_(renderMode),
417 incognitoMode_(incognitoMode), sharedRenderProcessToken_(sharedRenderProcessToken)
418 {
419 InitMagnifier();
420 }
421
~WebPattern()422 WebPattern::~WebPattern()
423 {
424 TAG_LOGI(AceLogTag::ACE_WEB, "NWEB ~WebPattern start");
425 UninitTouchEventListener();
426 if (delegate_) {
427 TAG_LOGD(AceLogTag::ACE_WEB, "NWEB ~WebPattern delegate_ start SetAudioMuted");
428 delegate_->SetAudioMuted(true);
429 }
430
431 if (observer_) {
432 TAG_LOGD(AceLogTag::ACE_WEB, "NWEB ~WebPattern observer_ start NotifyDestory");
433 observer_->NotifyDestory();
434 }
435 if (isActive_) {
436 TAG_LOGD(AceLogTag::ACE_WEB, "NWEB ~WebPattern isActive_ start OnInActive");
437 OnInActive();
438 }
439 if (imageAnalyzerManager_) {
440 imageAnalyzerManager_->ReleaseImageAnalyzer();
441 }
442 UninitializeAccessibility();
443 auto pipeline = PipelineBase::GetCurrentContextSafely();
444 if (pipeline) {
445 pipeline->UnregisterDensityChangedCallback(densityCallbackId_);
446 }
447 HideMagnifier();
448 OnTooltip("");
449 }
450
ShowContextSelectOverlay(const RectF & firstHandle,const RectF & secondHandle,TextResponseType responseType,bool handleReverse)451 void WebPattern::ShowContextSelectOverlay(const RectF& firstHandle, const RectF& secondHandle,
452 TextResponseType responseType, bool handleReverse)
453 {
454 if (contextSelectOverlay_) {
455 contextSelectOverlay_->ProcessOverlay({ .animation = true });
456 }
457 }
458
CloseContextSelectionMenu()459 void WebPattern::CloseContextSelectionMenu()
460 {
461 if (contextSelectOverlay_ && contextSelectOverlay_->IsCurrentMenuVisibile()) {
462 contextSelectOverlay_->CloseOverlay(true, CloseReason::CLOSE_REASON_NORMAL);
463 }
464 }
465
RemovePreviewMenuNode()466 void WebPattern::RemovePreviewMenuNode()
467 {
468 if (!previewImageNodeId_.has_value()) {
469 return;
470 }
471 TAG_LOGI(AceLogTag::ACE_WEB, "RemovePreviewMenuNode");
472 curContextMenuResult_ = false;
473 auto previewNode =
474 FrameNode::GetFrameNode(V2::IMAGE_ETS_TAG, previewImageNodeId_.value());
475 CHECK_NULL_VOID(previewNode);
476 auto parent = previewNode->GetParent();
477 CHECK_NULL_VOID(parent);
478 parent->RemoveChild(previewNode);
479 previewImageNodeId_.reset();
480 parent->MarkDirtyNode(PROPERTY_UPDATE_MEASURE_SELF);
481 }
482
IsPreviewMenuNotNeedShowPreview()483 bool WebPattern::IsPreviewMenuNotNeedShowPreview()
484 {
485 if (!previewImageNodeId_.has_value()) {
486 return false;
487 }
488 auto previewNode =
489 FrameNode::GetFrameNode(V2::IMAGE_ETS_TAG, previewImageNodeId_.value());
490 CHECK_NULL_RETURN(previewNode, false);
491 auto previewRenderContext = previewNode->GetRenderContext();
492 CHECK_NULL_RETURN(previewRenderContext, false);
493 auto previewGesture = previewNode->GetOrCreateGestureEventHub();
494 CHECK_NULL_RETURN(previewGesture, false);
495 bool isNotNeedShowPreview = previewGesture->GetBindMenuStatus().IsNotNeedShowPreview();
496 TAG_LOGI(AceLogTag::ACE_DRAG, "IsPreviewMenuNotNeedShowPreview:%{public}d", isNotNeedShowPreview);
497 return isNotNeedShowPreview;
498 }
499
SetPreviewSelectionMenu(const std::shared_ptr<WebPreviewSelectionMenuParam> & param)500 void WebPattern::SetPreviewSelectionMenu(const std::shared_ptr<WebPreviewSelectionMenuParam>& param)
501 {
502 CHECK_NULL_VOID(param);
503 auto onPreviewMenuDisappear = [weak = AceType::WeakClaim(this),
504 onDisappear = std::move(param->menuParam.onDisappear)]() {
505 TAG_LOGD(AceLogTag::ACE_WEB, "onPreviewMenuDisappear");
506 if (onDisappear) {
507 onDisappear();
508 }
509 auto webPattern = weak.Upgrade();
510 CHECK_NULL_VOID(webPattern);
511 webPattern->RemovePreviewMenuNode();
512 CHECK_NULL_VOID(webPattern->contextMenuResult_);
513 webPattern->contextMenuResult_->Cancel();
514 };
515 param->menuParam.onDisappear = std::move(onPreviewMenuDisappear);
516 auto key = std::make_pair(param->type, param->responseType);
517 auto it = previewSelectionMenuMap_.find(key);
518 if (it != previewSelectionMenuMap_.end()) {
519 if (param->menuBuilder == nullptr) {
520 previewSelectionMenuMap_.erase(it);
521 return;
522 }
523 it->second = param;
524 return;
525 }
526 previewSelectionMenuMap_[key] = param;
527 }
528
GetPreviewSelectionMenuParams(const WebElementType & type,const ResponseType & responseType)529 std::shared_ptr<WebPreviewSelectionMenuParam> WebPattern::GetPreviewSelectionMenuParams(
530 const WebElementType& type, const ResponseType& responseType)
531 {
532 auto key = std::make_pair(type, responseType);
533 auto it = previewSelectionMenuMap_.find(key);
534 if (it != previewSelectionMenuMap_.end()) {
535 return it->second;
536 }
537
538 TAG_LOGD(AceLogTag::ACE_WEB, "The key not in previewSelectionMenuMap_");
539 return nullptr;
540 }
541
GetPreviewImageOffsetAndSize(bool isImage,Offset & previewOffset,SizeF & previewSize)542 void WebPattern::GetPreviewImageOffsetAndSize(bool isImage, Offset& previewOffset, SizeF& previewSize)
543 {
544 if (isImage) {
545 CHECK_NULL_VOID(contextMenuParam_);
546 int32_t x = 0;
547 int32_t y = 0;
548 int32_t width = 0;
549 int32_t height = 0;
550 contextMenuParam_->GetImageRect(x, y, width, height);
551 previewOffset.SetX((float)x);
552 previewOffset.SetY((float)y);
553 previewSize.SetWidth((float)width);
554 previewSize.SetHeight((float)height);
555 } else {
556 previewSize.SetWidth(drawSize_.Width());
557 previewSize.SetHeight(drawSize_.Height());
558 }
559 auto host = GetHost();
560 CHECK_NULL_VOID(host);
561 auto pipeline = host->GetContextRefPtr();
562 CHECK_NULL_VOID(pipeline);
563 previewSize.SetWidth(previewSize.Width() / pipeline->GetDipScale());
564 previewSize.SetHeight(previewSize.Height() / pipeline->GetDipScale());
565 }
566
CreatePreviewImageFrameNode(bool isImage)567 RefPtr<FrameNode> WebPattern::CreatePreviewImageFrameNode(bool isImage)
568 {
569 RemovePreviewMenuNode();
570 previewImageNodeId_ = ElementRegister::GetInstance()->MakeUniqueId();
571 auto previewNode = FrameNode::GetOrCreateFrameNode(
572 V2::IMAGE_ETS_TAG, previewImageNodeId_.value(), []() { return AceType::MakeRefPtr<ImagePattern>(); });
573 CHECK_NULL_RETURN(previewNode, nullptr);
574 auto previewRenderContext = previewNode->GetRenderContext();
575 CHECK_NULL_RETURN(previewRenderContext, nullptr);
576 auto previewGesture = previewNode->GetOrCreateGestureEventHub();
577 CHECK_NULL_RETURN(previewGesture, nullptr);
578
579 previewNode->SetDraggable(false);
580 previewGesture->SetDragEvent(nullptr, { PanDirection::DOWN }, 0, Dimension(0));
581
582 Offset previewOffset(0, 0);
583 SizeF previewSize;
584 GetPreviewImageOffsetAndSize(isImage, previewOffset, previewSize);
585 if (previewSize.Width() <= 0 || previewSize.Height() <= 0) {
586 TAG_LOGI(AceLogTag::ACE_WEB, "CreatePreviewImageFrameNode get preview size(%{public}f, %{public}f) error",
587 previewSize.Width(), previewSize.Height());
588 return nullptr;
589 }
590 previewRenderContext->UpdatePosition(
591 OffsetT<Dimension>(Dimension(previewOffset.GetX()), Dimension(previewOffset.GetY())));
592
593 auto previewProperty = previewNode->GetLayoutProperty<ImageLayoutProperty>();
594 previewProperty->UpdateAutoResize(false);
595 previewProperty->UpdateMarginSelfIdealSize(previewSize);
596 MeasureProperty layoutConstraint;
597 CalcSize idealSize = { CalcLength(Dimension(previewSize.Width(), DimensionUnit::VP).ConvertToPx()),
598 CalcLength(Dimension(previewSize.Height(), DimensionUnit::VP).ConvertToPx()) };
599 layoutConstraint.selfIdealSize = idealSize;
600 layoutConstraint.maxSize = idealSize;
601 previewNode->UpdateLayoutConstraint(layoutConstraint);
602 TAG_LOGI(AceLogTag::ACE_WEB,
603 "CreatePreviewImageFrameNode offset:%{public}f, %{public}f; size:%{public}f, %{public}f",
604 previewOffset.GetX(), previewOffset.GetY(), previewSize.Width(), previewSize.Height());
605 needUpdateImagePreviewParam_ = true;
606 curContextMenuResult_ = true;
607 return previewNode;
608 }
609
UpdateImagePreviewParam()610 void WebPattern::UpdateImagePreviewParam()
611 {
612 CHECK_NULL_VOID(needUpdateImagePreviewParam_);
613 needUpdateImagePreviewParam_ = false;
614 if (!previewImageNodeId_.has_value()) {
615 return;
616 }
617 TAG_LOGI(AceLogTag::ACE_WEB, "UpdateImagePreviewParam");
618 auto params = GetPreviewSelectionMenuParams(curElementType_, curResponseType_);
619 if (!params) {
620 RemovePreviewMenuNode();
621 return;
622 }
623 #ifndef ACE_UNITTEST
624 auto previewNode =
625 FrameNode::GetFrameNode(V2::IMAGE_ETS_TAG, previewImageNodeId_.value());
626 CHECK_NULL_VOID(previewNode);
627 ViewStackProcessor::GetInstance()->Push(previewNode);
628 ViewAbstractModel::GetInstance()->BindContextMenu(
629 curResponseType_, params->menuBuilder, params->menuParam, params->previewBuilder);
630 ViewAbstractModel::GetInstance()->BindDragWithContextMenuParams(params->menuParam);
631 ViewStackProcessor::GetInstance()->Finish();
632 #endif
633 }
634
OnContextMenuShow(const std::shared_ptr<BaseEventInfo> & info,bool isRichtext,bool result)635 void WebPattern::OnContextMenuShow(const std::shared_ptr<BaseEventInfo>& info, bool isRichtext, bool result)
636 {
637 TAG_LOGI(AceLogTag::ACE_WEB,
638 "OnContextMenuShow result:%{public}d, isNewDragStyle_:%{public}d", result, isNewDragStyle_);
639 curContextMenuResult_ = result;
640 auto *eventInfo = TypeInfoHelper::DynamicCast<ContextMenuEvent>(info.get());
641 CHECK_NULL_VOID(eventInfo);
642 contextMenuParam_ = eventInfo->GetParam();
643 CHECK_NULL_VOID(contextMenuParam_);
644 contextMenuResult_ = eventInfo->GetContextMenuResult();
645 CHECK_NULL_VOID(contextMenuResult_);
646 if (isRichtext) {
647 if (!contextSelectOverlay_) {
648 contextSelectOverlay_ = AceType::MakeRefPtr<WebContextSelectOverlay>(WeakClaim(this));
649 }
650 ShowContextSelectOverlay(RectF(), RectF());
651 return;
652 }
653 CHECK_NULL_VOID(isNewDragStyle_ && result);
654 bool isImage = (contextMenuParam_->GetLinkUrl().empty() &&
655 (contextMenuParam_->GetMediaType() == OHOS::NWeb::NWebContextMenuParams::ContextMenuMediaType::CM_MT_IMAGE));
656 if (isImage) {
657 auto sourceType = contextMenuParam_->GetSourceType();
658 if (sourceType == OHOS::NWeb::NWebContextMenuParams::ContextMenuSourceType::CM_ST_MOUSE) {
659 curResponseType_ = ResponseType::RIGHT_CLICK;
660 } else if (sourceType == OHOS::NWeb::NWebContextMenuParams::ContextMenuSourceType::CM_ST_LONG_PRESS) {
661 curResponseType_ = ResponseType::LONG_PRESS;
662 } else {
663 return;
664 }
665 curElementType_ = WebElementType::IMAGE;
666 CHECK_NULL_VOID(GetPreviewSelectionMenuParams(curElementType_, curResponseType_));
667 auto host = GetHost();
668 if (!host) {
669 TAG_LOGE(AceLogTag::ACE_WEB, "GetHost failed");
670 delegate_->OnContextMenuHide("");
671 return;
672 }
673 auto previewNode = CreatePreviewImageFrameNode(isImage);
674 if (!previewNode) {
675 TAG_LOGI(AceLogTag::ACE_WEB, "CreatePreviewImageFrameNode failed");
676 delegate_->OnContextMenuHide("");
677 return;
678 }
679
680 host->AddChild(previewNode);
681 previewNode->MarkDirtyNode(PROPERTY_UPDATE_MEASURE);
682 previewNode->MarkModifyDone();
683 host->MarkDirtyNode(PROPERTY_UPDATE_MEASURE);
684 host->MarkModifyDone();
685 }
686 }
687
OnContextMenuHide()688 void WebPattern::OnContextMenuHide()
689 {
690 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern OnContextMenuHide");
691 if (webData_) {
692 CloseContextSelectionMenu();
693 return;
694 }
695 RemovePreviewMenuNode();
696 CHECK_NULL_VOID(contextMenuResult_);
697 contextMenuResult_->Cancel();
698 curContextMenuResult_ = false;
699 }
700
NeedSoftKeyboard() const701 bool WebPattern::NeedSoftKeyboard() const
702 {
703 if (delegate_) {
704 return delegate_->NeedSoftKeyboard();
705 }
706 return false;
707 }
708
OnAttachToFrameNode()709 void WebPattern::OnAttachToFrameNode()
710 {
711 auto host = GetHost();
712 CHECK_NULL_VOID(host);
713 auto pipeline = PipelineContext::GetCurrentContext();
714 CHECK_NULL_VOID(pipeline);
715 SetRotation(pipeline->GetTransformHint());
716
717 host->GetRenderContext()->SetClipToFrame(true);
718 if (!renderContextForSurface_) {
719 renderContextForSurface_ = RenderContext::Create();
720 static RenderContext::ContextParam param = { RenderContext::ContextType::HARDWARE_SURFACE,
721 "RosenWeb" };
722 CHECK_NULL_VOID(renderContextForSurface_);
723 renderContextForSurface_->InitContext(false, param);
724 // Disable hardware composition when initializing to fix visual artifacts when switching to a new webview.
725 auto surfaceNode = OHOS::Rosen::RSBaseNode::ReinterpretCast<OHOS::Rosen::RSSurfaceNode>(GetSurfaceRSNode());
726 CHECK_NULL_VOID(surfaceNode);
727 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::OnAttachToFrameNode, web id = %{public}d", GetWebId());
728 ACE_SCOPED_TRACE("WebPattern::OnAttachToFrameNode, web id = %d", GetWebId());
729 surfaceNode->SetHardwareEnabled(true, Rosen::SelfDrawingNodeType::DEFAULT, false);
730 }
731 host->GetLayoutProperty()->UpdateMeasureType(MeasureType::MATCH_PARENT);
732 pipeline->AddNodesToNotifyMemoryLevel(host->GetId());
733
734 auto callbackId = pipeline->RegisterTransformHintChangeCallback([weak = WeakClaim(this)](uint32_t transform) {
735 auto pattern = weak.Upgrade();
736 if (pattern) {
737 TAG_LOGD(AceLogTag::ACE_WEB, "OnAttach to frame node, set transform:%{public}u", transform);
738 pattern->SetRotation(transform);
739 }
740 });
741 UpdateTransformHintChangedCallbackId(callbackId);
742 #if !defined(PREVIEW) && !defined(ACE_UNITTEST) && defined(OHOS_PLATFORM)
743 if (UiSessionManager::GetInstance().GetWebFocusRegistered()) {
744 auto callback = [](int64_t accessibilityId, const std::string data) {
745 UiSessionManager::GetInstance().ReportWebUnfocusEvent(accessibilityId, data);
746 };
747 RegisterTextBlurCallback(callback);
748 }
749 #endif
750 }
751
OnDetachFromFrameNode(FrameNode * frameNode)752 void WebPattern::OnDetachFromFrameNode(FrameNode* frameNode)
753 {
754 CHECK_NULL_VOID(delegate_);
755 isFocus_ = false;
756 delegate_->OnBlur();
757 OnQuickMenuDismissed();
758
759 auto id = frameNode->GetId();
760 auto pipeline = AceType::DynamicCast<PipelineContext>(PipelineBase::GetCurrentContext());
761 CHECK_NULL_VOID(pipeline);
762 pipeline->RemoveWindowStateChangedCallback(id);
763 pipeline->RemoveWindowSizeChangeCallback(id);
764 pipeline->RemoveNodesToNotifyMemoryLevel(id);
765
766 if (HasTransformHintChangedCallbackId()) {
767 pipeline->UnregisterTransformHintChangedCallback(transformHintChangedCallbackId_.value_or(-1));
768 }
769 #if !defined(PREVIEW) && !defined(ACE_UNITTEST) && defined(OHOS_PLATFORM)
770 if (UiSessionManager::GetInstance().GetWebFocusRegistered()) {
771 UnRegisterTextBlurCallback();
772 }
773 #endif
774 }
775
SetRotation(uint32_t rotation)776 void WebPattern::SetRotation(uint32_t rotation)
777 {
778 if (renderMode_ == RenderMode::SYNC_RENDER || rotation_ == rotation) {
779 return;
780 }
781 rotation_ = rotation;
782 CHECK_NULL_VOID(renderSurface_);
783 renderSurface_->SetTransformHint(rotation);
784 }
785
OnAttachToMainTree()786 void WebPattern::OnAttachToMainTree()
787 {
788 isAttachedToMainTree_ = true;
789 InitSlideUpdateListener();
790 TAG_LOGD(AceLogTag::ACE_WEB, "OnAttachToMainTree");
791 // report component is in foreground.
792 delegate_->OnRenderToForeground();
793 }
794
OnDetachFromMainTree()795 void WebPattern::OnDetachFromMainTree()
796 {
797 isAttachedToMainTree_ = false;
798 TAG_LOGD(AceLogTag::ACE_WEB, "OnDetachFromMainTree");
799 // report component is in background.
800 delegate_->OnRenderToBackground();
801 }
802
InitEvent()803 void WebPattern::InitEvent()
804 {
805 auto host = GetHost();
806 CHECK_NULL_VOID(host);
807 auto eventHub = host->GetEventHub<WebEventHub>();
808 CHECK_NULL_VOID(eventHub);
809
810 auto gestureHub = eventHub->GetOrCreateGestureEventHub();
811 CHECK_NULL_VOID(gestureHub);
812
813 InitTouchEvent(gestureHub);
814 InitDragEvent(gestureHub);
815 InitPanEvent(gestureHub);
816 InitPinchEvent(gestureHub);
817
818 auto inputHub = eventHub->GetOrCreateInputEventHub();
819 CHECK_NULL_VOID(inputHub);
820 InitMouseEvent(inputHub);
821 InitHoverEvent(inputHub);
822
823 auto focusHub = eventHub->GetOrCreateFocusHub();
824 CHECK_NULL_VOID(focusHub);
825 InitFocusEvent(focusHub);
826 }
827
InitConfigChangeCallback(const RefPtr<PipelineContext> & context)828 void WebPattern::InitConfigChangeCallback(const RefPtr<PipelineContext> &context)
829 {
830 auto langTask = [weak = AceType::WeakClaim(this)]() {
831 auto WebPattern = weak.Upgrade();
832 CHECK_NULL_VOID(WebPattern);
833 WebPattern->UpdateLocale();
834 };
835 context->SetConfigChangedCallback(GetHost()->GetId(), std::move(langTask));
836 }
837
InitFeatureParam()838 void WebPattern::InitFeatureParam()
839 {
840 isVisibleActiveEnable_ = system::GetBoolParameter(VISIBLE_ACTIVE_ENABLE, true);
841 isMemoryLevelEnable_ = system::GetBoolParameter(MEMORY_LEVEL_ENABEL, true);
842 }
843
InitPanEvent(const RefPtr<GestureEventHub> & gestureHub)844 void WebPattern::InitPanEvent(const RefPtr<GestureEventHub>& gestureHub)
845 {
846 if (panEvent_) {
847 return;
848 }
849 auto actionStartTask = [weak = WeakClaim(this)](const GestureEvent& event) {
850 auto pattern = weak.Upgrade();
851 CHECK_NULL_VOID(pattern);
852 // Determine if there is already a fixed nested scroll mode.
853 if (!pattern->GetIsFixedNestedScrollMode() || !pattern->GetNestedScrollParent()) {
854 pattern->SetParentScrollable();
855 }
856 pattern->GetParentAxis();
857 };
858 auto actionUpdateTask = [weak = WeakClaim(this)](const GestureEvent& event) {
859 auto pattern = weak.Upgrade();
860 CHECK_NULL_VOID(pattern);
861 pattern->HandleDragMove(event);
862 };
863 auto actionEndTask = [weak = WeakClaim(this)](const GestureEvent& info) {
864 auto pattern = weak.Upgrade();
865 CHECK_NULL_VOID(pattern);
866 pattern->HandleFlingMove(info);
867 };
868 auto actionCancelTask = [weak = WeakClaim(this)]() { return; };
869 PanDirection panDirection;
870 panDirection.type = PanDirection::ALL;
871 panEvent_ = MakeRefPtr<PanEvent>(
872 std::move(actionStartTask), std::move(actionUpdateTask), std::move(actionEndTask), std::move(actionCancelTask));
873 gestureHub->AddPanEvent(panEvent_, panDirection, DEFAULT_PAN_FINGER, DEFAULT_PAN_DISTANCE);
874 gestureHub->SetPanEventType(GestureTypeName::WEBSCROLL);
875 gestureHub->SetOnGestureJudgeNativeBegin([](const RefPtr<NG::GestureInfo>& gestureInfo,
876 const std::shared_ptr<BaseGestureEvent>& info) -> GestureJudgeResult {
877 if (!gestureInfo) {
878 // info is null, default case to continue
879 return GestureJudgeResult::CONTINUE;
880 }
881 if (gestureInfo->GetType() != GestureTypeName::WEBSCROLL) {
882 // not web pan event type, continue
883 return GestureJudgeResult::CONTINUE;
884 }
885
886 auto inputEventType = gestureInfo->GetInputEventType();
887 if (inputEventType == InputEventType::AXIS) {
888 // axis event type of web pan, dispatch to panEvent to process
889 return GestureJudgeResult::CONTINUE;
890 } else if (inputEventType == InputEventType::MOUSE_BUTTON) {
891 // mouse button event type of web pan, dispatch to DragEvent to process
892 return GestureJudgeResult::REJECT;
893 }
894 // In other cases, the panEvent is used by default
895 return GestureJudgeResult::CONTINUE;
896 });
897 }
898
HandleFlingMove(const GestureEvent & event)899 void WebPattern::HandleFlingMove(const GestureEvent& event)
900 {
901 if ((event.GetInputEventType() == InputEventType::AXIS) &&
902 (event.GetSourceTool() == SourceTool::TOUCHPAD)) {
903 CHECK_NULL_VOID(delegate_);
904 std::vector<int32_t> pressedCodes;
905 auto gesturePressedCodes = event.GetPressedKeyCodes();
906 for (auto pCode : gesturePressedCodes) {
907 pressedCodes.push_back(static_cast<int32_t>(pCode));
908 }
909 auto localLocation = event.GetLocalLocation();
910 TAG_LOGI(AceLogTag::ACE_WEB, "web touchpad fling event, vx: %{public}f, vy: %{public}f",
911 event.GetVelocity().GetVelocityX(), event.GetVelocity().GetVelocityY());
912 delegate_->WebHandleTouchpadFlingEvent(localLocation.GetX(), localLocation.GetY(),
913 event.GetVelocity().GetVelocityX(),
914 event.GetVelocity().GetVelocityY(),
915 pressedCodes);
916 }
917 }
918
HandleDragMove(const GestureEvent & event)919 void WebPattern::HandleDragMove(const GestureEvent& event)
920 {
921 if (event.GetInputEventType() == InputEventType::AXIS) {
922 CHECK_NULL_VOID(delegate_);
923 auto localLocation = event.GetLocalLocation();
924 std::vector<int32_t> pressedCodes;
925 auto gesturePressedCodes = event.GetPressedKeyCodes();
926 for (auto pCode : gesturePressedCodes) {
927 pressedCodes.push_back(static_cast<int32_t>(pCode));
928 }
929 TAG_LOGD(AceLogTag::ACE_WEB, "HandleDragMove Axis deltaX: %{public}f deltaY: %{public}f",
930 event.GetDelta().GetX(), event.GetDelta().GetY());
931 delegate_->WebHandleAxisEvent(localLocation.GetX(), localLocation.GetY(),
932 event.GetDelta().GetX() / DEFAULT_AXIS_RATIO, event.GetDelta().GetY() / DEFAULT_AXIS_RATIO,
933 pressedCodes, static_cast<int32_t>(event.GetSourceTool()));
934 }
935 }
936
InitPinchEvent(const RefPtr<GestureEventHub> & gestureHub)937 void WebPattern::InitPinchEvent(const RefPtr<GestureEventHub>& gestureHub)
938 {
939 if (pinchGesture_) {
940 if (gestureHub->WillRecreateGesture()) {
941 gestureHub->AddGesture(pinchGesture_);
942 }
943 return;
944 }
945 auto actionStartTask = [weak = WeakClaim(this)](const GestureEvent& event) {
946 if (event.GetSourceTool() == SourceTool::TOUCHPAD) {
947 auto pattern = weak.Upgrade();
948 CHECK_NULL_VOID(pattern);
949 pattern->startPinchScale_ = event.GetScale();
950 pattern->preScale_ = event.GetScale();
951 pattern->pinchIndex_ = 0;
952 pattern->zoomOutSwitch_ = false;
953 pattern->zoomStatus_ = 0;
954 pattern->zoomErrorCount_ = 0;
955 TAG_LOGI(AceLogTag::ACE_WEB, "InitPinchEvent StartScale: %{public}f", pattern->startPinchScale_);
956
957 pattern->HandleScaleGestureStart(event);
958
959 return;
960 }
961 };
962 auto actionUpdateTask = [weak = WeakClaim(this)](const GestureEvent& event) {
963 ACE_SCOPED_TRACE("WebPattern::InitPinchEvent actionUpdateTask");
964 auto pattern = weak.Upgrade();
965 CHECK_NULL_VOID(pattern);
966 if (event.GetSourceTool() == SourceTool::TOUCHPAD) {
967 pattern->HandleScaleGestureChange(event);
968 TAG_LOGD(AceLogTag::ACE_WEB, "InitPinchEvent actionUpdateTask event scale:%{public}f: ",
969 event.GetScale());
970 }
971 };
972 auto actionEndTask = [weak = WeakClaim(this)](const GestureEvent& event) {
973 auto pattern = weak.Upgrade();
974 CHECK_NULL_VOID(pattern);
975 pattern->HandleScaleGestureEnd(event);
976 };
977 auto actionCancelTask = [weak = WeakClaim(this)]() { return; };
978
979 pinchGesture_ = MakeRefPtr<PinchGesture>(DEFAULT_PINCH_FINGER, DEFAULT_PINCH_DISTANCE);
980 pinchGesture_->SetPriority(GesturePriority::Parallel);
981 pinchGesture_->SetOnActionStartId(actionStartTask);
982 pinchGesture_->SetOnActionUpdateId(actionUpdateTask);
983 pinchGesture_->SetOnActionEndId(actionEndTask);
984 pinchGesture_->SetOnActionCancelId(actionCancelTask);
985 gestureHub->AddGesture(pinchGesture_);
986 }
987
CheckZoomStatus(const double & curScale)988 bool WebPattern::CheckZoomStatus(const double& curScale)
989 {
990 int32_t curScaleNew = (int32_t) (curScale * 100);
991 int32_t preScaleNew = (int32_t) (preScale_ * 100);
992
993 TAG_LOGI(AceLogTag::ACE_WEB,
994 "HandleScaleGestureChange curScaleNew:%{public}d preScaleNew: %{public}d",
995 curScaleNew, preScaleNew);
996
997 // check zoom status
998 if ((zoomStatus_ == STATUS_ZOOMOUT && curScaleNew - preScaleNew < 0)
999 && zoomErrorCount_ < ZOOM_ERROR_COUNT_MAX) {
1000 zoomErrorCount_++;
1001 TAG_LOGI(AceLogTag::ACE_WEB, "HandleScaleGestureChange zoomStatus = zoomout && curScale < preScale,"
1002 "ignore date.");
1003 return false;
1004 } else if ((zoomStatus_ == STATUS_ZOOMIN && curScaleNew - preScaleNew > 0)
1005 && zoomErrorCount_ < ZOOM_ERROR_COUNT_MAX) {
1006 zoomErrorCount_++;
1007 TAG_LOGI(AceLogTag::ACE_WEB, "HandleScaleGestureChange zoomStatus = zoomin && curScale >= preScale,"
1008 "ignore date.");
1009 return false;
1010 } else {
1011 // nothing
1012 }
1013 return true;
1014 }
1015
ZoomOutAndIn(const double & curScale,double & scale)1016 bool WebPattern::ZoomOutAndIn(const double& curScale, double& scale)
1017 {
1018 int32_t curScaleNew = (int32_t)(curScale * 100);
1019 int32_t preScaleNew = (int32_t)(preScale_ * 100);
1020
1021 // zoom out
1022 if (curScale - preScale_ >= 0) {
1023 if (preScale_ >= DEFAULT_PINCH_SCALE) {
1024 if (startPinchScale_ >= DEFAULT_PINCH_SCALE) {
1025 scale = curScale;
1026 } else {
1027 scale = DEFAULT_PINCH_SCALE + (curScale - startPinchScale_);
1028 }
1029
1030 // Prevent shaking in index 1
1031 if (pinchIndex_ == PINCH_INDEX_ONE) {
1032 pageScale_ = scale;
1033 }
1034 } else {
1035 // The scale is from 0.4 to 0.5, the scale conversion should be from 1.0 to 1.1
1036 if (pageScale_ < DEFAULT_PINCH_SCALE) {
1037 TAG_LOGI(AceLogTag::ACE_WEB, "HandleScaleGestureChange Switch from zoomin to zoomout.");
1038 // must be page scale form 0.4 to 1
1039 scale = DEFAULT_PINCH_SCALE;
1040 // reset
1041 startPinchScale_ = preScale_;
1042 pageScale_ = scale;
1043 zoomOutSwitch_ = true;
1044 } else {
1045 scale = DEFAULT_PINCH_SCALE + (curScale - startPinchScale_);
1046 zoomOutSwitch_ = false;
1047 }
1048 }
1049 zoomStatus_ = STATUS_ZOOMOUT;
1050 // zoom in
1051 } else {
1052 // When zooming in from a scale less than 1,
1053 // the current scale must be greater than the previous scale value
1054 if (zoomOutSwitch_) {
1055 TAG_LOGI(AceLogTag::ACE_WEB, "HandleScaleGestureChange the current scale must be greater "
1056 "than the previous scale value, ignore data.");
1057 return false;
1058 }
1059
1060 if (curScaleNew == preScaleNew) {
1061 return false;
1062 }
1063
1064 scale = ZOOMIN_SMOOTH_SCALE;
1065
1066 zoomStatus_ = STATUS_ZOOMIN;
1067 }
1068 return true;
1069 }
1070
HandleScaleGestureChange(const GestureEvent & event)1071 void WebPattern::HandleScaleGestureChange(const GestureEvent& event)
1072 {
1073 CHECK_NULL_VOID(delegate_);
1074
1075 double curScale = event.GetScale();
1076 if (std::fabs(curScale - preScale_) <= std::numeric_limits<double>::epsilon()) {
1077 TAG_LOGI(AceLogTag::ACE_WEB, "HandleScaleGestureChange curScale == preScale");
1078 return;
1079 }
1080
1081 if (LessOrEqual(curScale, 0.0) || LessOrEqual(preScale_, 0.0)) {
1082 TAG_LOGE(AceLogTag::ACE_WEB, "HandleScaleGestureChange invalid scale");
1083 return;
1084 }
1085
1086 if (!CheckZoomStatus(curScale)) {
1087 return;
1088 }
1089 zoomErrorCount_ = 0;
1090
1091 pinchIndex_++;
1092
1093 double newScale = curScale / preScale_;
1094 double newOriginScale = GetNewOriginScale(event.GetScale());
1095
1096 double centerX = event.GetPinchCenter().GetX();
1097 double centerY = event.GetPinchCenter().GetY();
1098 auto frameNode = GetHost();
1099 CHECK_NULL_VOID(frameNode);
1100 auto offset = frameNode->GetOffsetRelativeToWindow();
1101 TAG_LOGD(AceLogTag::ACE_WEB,
1102 "HandleScaleGestureChangeV2 curScale:%{public}f newScale: %{public}f"
1103 " centerX: %{public}f centerY: %{public}f",
1104 curScale, newScale, centerX, centerY);
1105
1106 // Plan two
1107 delegate_->ScaleGestureChangeV2(
1108 PINCH_UPDATE_TYPE, newScale, newOriginScale, centerX - offset.GetX(), centerY - offset.GetY());
1109
1110 preScale_ = curScale;
1111 }
1112
GetNewScale(double & scale) const1113 double WebPattern::GetNewScale(double& scale) const
1114 {
1115 double newScale = 0.0;
1116 if (scale >= DEFAULT_PINCH_SCALE) {
1117 // In order to achieve a sequence similar to scale, eg. 1.1, 1.2, 1.3
1118 newScale = scale / pageScale_;
1119 // scale max
1120 if (newScale > DEFAULT_PINCH_SCALE_MAX) {
1121 newScale = DEFAULT_PINCH_SCALE_MAX;
1122 scale = DEFAULT_PINCH_SCALE_MAX;
1123 }
1124 } else {
1125 newScale = scale;
1126 // scale min
1127 if (newScale < DEFAULT_PINCH_SCALE_MIN) {
1128 newScale = DEFAULT_PINCH_SCALE_MIN;
1129 scale = DEFAULT_PINCH_SCALE_MIN;
1130 }
1131 }
1132
1133 return newScale;
1134 }
1135
GetNewOriginScale(double originScale) const1136 double WebPattern::GetNewOriginScale(double originScale) const
1137 {
1138 double newScale = 0.0;
1139 if (zoomStatus_ == STATUS_ZOOMOUT) {
1140 newScale = DEFAULT_PINCH_SCALE_MAX;
1141 } else if (zoomStatus_ == STATUS_ZOOMIN) {
1142 newScale = DEFAULT_PINCH_SCALE_MIN;
1143 }
1144
1145 return newScale;
1146 }
1147
HandleScaleGestureStart(const GestureEvent & event)1148 void WebPattern::HandleScaleGestureStart(const GestureEvent& event)
1149 {
1150 CHECK_NULL_VOID(delegate_);
1151
1152 double scale = event.GetScale();
1153
1154 double centerX = event.GetPinchCenter().GetX();
1155 double centerY = event.GetPinchCenter().GetY();
1156 auto frameNode = GetHost();
1157 CHECK_NULL_VOID(frameNode);
1158 auto offset = frameNode->GetOffsetRelativeToWindow();
1159
1160 delegate_->ScaleGestureChangeV2(
1161 PINCH_START_TYPE, scale, event.GetScale(), centerX - offset.GetX(), centerY - offset.GetY());
1162 }
1163
HandleScaleGestureEnd(const GestureEvent & event)1164 void WebPattern::HandleScaleGestureEnd(const GestureEvent& event)
1165 {
1166 CHECK_NULL_VOID(delegate_);
1167
1168 double scale = event.GetScale();
1169
1170 double centerX = event.GetPinchCenter().GetX();
1171 double centerY = event.GetPinchCenter().GetY();
1172 auto frameNode = GetHost();
1173 CHECK_NULL_VOID(frameNode);
1174 auto offset = frameNode->GetOffsetRelativeToWindow();
1175
1176 delegate_->ScaleGestureChangeV2(
1177 PINCH_END_TYPE, scale, event.GetScale(), centerX - offset.GetX(), centerY - offset.GetY());
1178 }
1179
InitTouchEvent(const RefPtr<GestureEventHub> & gestureHub)1180 void WebPattern::InitTouchEvent(const RefPtr<GestureEventHub>& gestureHub)
1181 {
1182 if (touchEvent_) {
1183 return;
1184 }
1185
1186 auto touchTask = [weak = WeakClaim(this)](const TouchEventInfo& info) {
1187 auto pattern = weak.Upgrade();
1188 CHECK_NULL_VOID(pattern);
1189 pattern->OnTooltip("");
1190 if (info.GetChangedTouches().empty()) {
1191 return;
1192 }
1193
1194 // only handle touch event
1195 if (info.GetSourceDevice() != SourceType::TOUCH) {
1196 return;
1197 }
1198 pattern->touchEventInfo_ = info;
1199 pattern->isMouseEvent_ = false;
1200 const auto& changedPoint = info.GetChangedTouches().front();
1201 if (changedPoint.GetTouchType() == TouchType::DOWN ||
1202 changedPoint.GetTouchType() == TouchType::UP) {
1203 if (pattern->touchEventQueue_.size() < TOUCH_EVENT_MAX_SIZE) {
1204 pattern->touchEventQueue_.push(info);
1205 }
1206 }
1207
1208 if (changedPoint.GetTouchType() == TouchType::DOWN) {
1209 pattern->HandleTouchDown(info, false);
1210 return;
1211 }
1212 if (changedPoint.GetTouchType() == TouchType::MOVE) {
1213 pattern->HandleTouchMove(info, false);
1214 return;
1215 }
1216 if (changedPoint.GetTouchType() == TouchType::UP) {
1217 pattern->HandleTouchUp(info, false);
1218 return;
1219 }
1220 if (changedPoint.GetTouchType() == TouchType::CANCEL) {
1221 pattern->HandleTouchCancel(info);
1222 return;
1223 }
1224 };
1225 touchEvent_ = MakeRefPtr<TouchEventImpl>(std::move(touchTask));
1226 gestureHub->AddTouchEvent(touchEvent_);
1227 }
1228
InitMouseEvent(const RefPtr<InputEventHub> & inputHub)1229 void WebPattern::InitMouseEvent(const RefPtr<InputEventHub>& inputHub)
1230 {
1231 if (mouseEvent_) {
1232 return;
1233 }
1234
1235 auto mouseTask = [weak = WeakClaim(this)](MouseInfo& info) {
1236 auto pattern = weak.Upgrade();
1237 CHECK_NULL_VOID(pattern);
1238 pattern->HandleMouseEvent(info);
1239 };
1240
1241 mouseEvent_ = MakeRefPtr<InputEvent>(std::move(mouseTask));
1242 inputHub->AddOnMouseEvent(mouseEvent_);
1243 }
1244
InitHoverEvent(const RefPtr<InputEventHub> & inputHub)1245 void WebPattern::InitHoverEvent(const RefPtr<InputEventHub>& inputHub)
1246 {
1247 if (hoverEvent_) {
1248 return;
1249 }
1250
1251 auto hoverTask = [weak = WeakClaim(this)](bool isHover) {
1252 auto pattern = weak.Upgrade();
1253 CHECK_NULL_VOID(pattern);
1254 MouseInfo info;
1255 info.SetAction(isHover ? MouseAction::HOVER : MouseAction::HOVER_EXIT);
1256 pattern->SetMouseHoverExit(!isHover);
1257 if (!isHover) {
1258 TAG_LOGI(AceLogTag::ACE_WEB,
1259 "Set cursor to pointer when mouse pointer is leave.");
1260 pattern->OnCursorChange(OHOS::NWeb::CursorType::CT_POINTER, nullptr);
1261 }
1262 pattern->WebOnMouseEvent(info);
1263 };
1264
1265 hoverEvent_ = MakeRefPtr<InputEvent>(std::move(hoverTask));
1266 inputHub->AddOnHoverEvent(hoverEvent_);
1267 }
1268
HandleMouseEvent(MouseInfo & info)1269 void WebPattern::HandleMouseEvent(MouseInfo& info)
1270 {
1271 isMouseEvent_ = true;
1272 WebOnMouseEvent(info);
1273
1274 auto host = GetHost();
1275 CHECK_NULL_VOID(host);
1276 auto eventHub = host->GetEventHub<WebEventHub>();
1277 CHECK_NULL_VOID(eventHub);
1278 auto mouseEventCallback = eventHub->GetOnMouseEvent();
1279 CHECK_NULL_VOID(mouseEventCallback);
1280 mouseEventCallback(info);
1281 }
1282
WebOnMouseEvent(const MouseInfo & info)1283 void WebPattern::WebOnMouseEvent(const MouseInfo& info)
1284 {
1285 if (mouseEventDeviceId_ != info.GetDeviceId()) {
1286 mouseEventDeviceId_ = info.GetDeviceId();
1287 }
1288 CHECK_NULL_VOID(delegate_);
1289 auto localLocation = info.GetLocalLocation();
1290 if ((info.GetAction() == MouseAction::PRESS) ||
1291 (info.GetButton() == MouseButton::LEFT_BUTTON) ||
1292 (info.GetButton() == MouseButton::RIGHT_BUTTON) ||
1293 (info.GetButton() == MouseButton::BACK_BUTTON) ||
1294 (info.GetButton() == MouseButton::FORWARD_BUTTON)) {
1295 OnTooltip("");
1296 }
1297 if (info.GetAction() == MouseAction::PRESS) {
1298 delegate_->OnContextMenuHide("");
1299 WebRequestFocus();
1300 }
1301
1302 // set touchup false when using mouse
1303 isTouchUpEvent_ = false;
1304 if (info.GetButton() == MouseButton::LEFT_BUTTON && info.GetAction() == MouseAction::RELEASE) {
1305 if (isReceivedArkDrag_) {
1306 TAG_LOGI(AceLogTag::ACE_WEB, "DragDrop Do not reset drag action when dragging,"
1307 "drop/cancel/end event will do this");
1308 return;
1309 }
1310 ResetDragAction();
1311 }
1312 isHoverExit_ = false;
1313 if (info.GetAction() == MouseAction::HOVER_EXIT) {
1314 TAG_LOGI(AceLogTag::ACE_WEB,
1315 "Set cursor to pointer when mouse pointer is hover exit.");
1316 isHoverExit_ = true;
1317 OnCursorChange(OHOS::NWeb::CursorType::CT_POINTER, nullptr);
1318 }
1319
1320 if (!HandleDoubleClickEvent(info)) {
1321 delegate_->OnMouseEvent(
1322 localLocation.GetX(), localLocation.GetY(), info.GetButton(), info.GetAction(), SINGLE_CLICK_NUM);
1323 }
1324
1325 if (info.GetAction() == MouseAction::MOVE) {
1326 mouseHoveredX_ = localLocation.GetX();
1327 mouseHoveredY_ = localLocation.GetY();
1328 }
1329 }
1330
ResetDragAction()1331 void WebPattern::ResetDragAction()
1332 {
1333 auto frameNode = GetHost();
1334 CHECK_NULL_VOID(frameNode);
1335 frameNode->SetDraggable(false);
1336 auto eventHub = frameNode->GetEventHub<WebEventHub>();
1337 CHECK_NULL_VOID(eventHub);
1338 auto gestureHub = eventHub->GetOrCreateGestureEventHub();
1339 CHECK_NULL_VOID(gestureHub);
1340 gestureHub->ResetDragActionForWeb();
1341
1342 if (!isDragging_) {
1343 return;
1344 }
1345
1346 isDragging_ = false;
1347 isReceivedArkDrag_ = false;
1348 isDragStartFromWeb_ = false;
1349 // cancel drag action to avoid web kernel can't process other input event
1350 CHECK_NULL_VOID(delegate_);
1351 delegate_->HandleDragEvent(0, 0, DragAction::DRAG_CANCEL);
1352 gestureHub->CancelDragForWeb();
1353 }
1354
GetDragOffset() const1355 Offset WebPattern::GetDragOffset() const
1356 {
1357 Offset webDragOffset;
1358 int x = 0;
1359 int y = 0;
1360 if (delegate_ && delegate_->dragData_) {
1361 delegate_->dragData_->GetDragStartPosition(x, y);
1362 }
1363
1364 webDragOffset.SetX(x);
1365 webDragOffset.SetY(y);
1366
1367 return webDragOffset;
1368 }
1369
GetDragPixelMapSize() const1370 SizeF WebPattern::GetDragPixelMapSize() const
1371 {
1372 SizeF pixelMapSize;
1373 int32_t width = 0;
1374 int32_t height = 0;
1375 RefPtr<PixelMap> pixelMap = nullptr;
1376 if (delegate_) {
1377 pixelMap = delegate_->GetDragPixelMap();
1378 }
1379 if (pixelMap) {
1380 width = pixelMap->GetWidth();
1381 height = pixelMap->GetHeight();
1382 }
1383 pixelMapSize = SizeF(width, height);
1384 return pixelMapSize;
1385 }
1386
HandleDoubleClickEvent(const MouseInfo & info)1387 bool WebPattern::HandleDoubleClickEvent(const MouseInfo& info)
1388 {
1389 if (info.GetButton() != MouseButton::LEFT_BUTTON || info.GetAction() != MouseAction::PRESS) {
1390 return false;
1391 }
1392 auto localLocation = info.GetLocalLocation();
1393 MouseClickInfo clickInfo;
1394 clickInfo.x = localLocation.GetX();
1395 clickInfo.y = localLocation.GetY();
1396 clickInfo.start = info.GetTimeStamp();
1397 if (doubleClickQueue_.empty()) {
1398 doubleClickQueue_.push(clickInfo);
1399 return false;
1400 }
1401 std::chrono::duration<float> timeout_ = clickInfo.start - doubleClickQueue_.back().start;
1402 double offsetX = clickInfo.x - doubleClickQueue_.back().x;
1403 double offsetY = clickInfo.y - doubleClickQueue_.back().y;
1404 double offset = sqrt(offsetX * offsetX + offsetY * offsetY);
1405 if (timeout_.count() < DEFAULT_DBCLICK_INTERVAL && offset < DEFAULT_DBCLICK_OFFSET) {
1406 SendDoubleClickEvent(clickInfo);
1407 std::queue<MouseClickInfo> empty;
1408 swap(empty, doubleClickQueue_);
1409 return true;
1410 }
1411 if (doubleClickQueue_.size() == 1) {
1412 doubleClickQueue_.push(clickInfo);
1413 return false;
1414 }
1415 doubleClickQueue_.pop();
1416 doubleClickQueue_.push(clickInfo);
1417 return false;
1418 }
1419
SendDoubleClickEvent(const MouseClickInfo & info)1420 void WebPattern::SendDoubleClickEvent(const MouseClickInfo& info)
1421 {
1422 CHECK_NULL_VOID(delegate_);
1423 delegate_->OnMouseEvent(info.x, info.y, MouseButton::LEFT_BUTTON, MouseAction::PRESS, DOUBLE_CLICK_NUM);
1424 }
1425
GenerateDragDropInfo(NG::DragDropInfo & dragDropInfo)1426 bool WebPattern::GenerateDragDropInfo(NG::DragDropInfo& dragDropInfo)
1427 {
1428 if (delegate_) {
1429 dragDropInfo.pixelMap = delegate_->GetDragPixelMap();
1430 }
1431
1432 if (dragDropInfo.pixelMap) {
1433 isW3cDragEvent_ = true;
1434 return true;
1435 }
1436
1437 return false;
1438 }
1439
HandleOnDragStart(const RefPtr<OHOS::Ace::DragEvent> & info)1440 NG::DragDropInfo WebPattern::HandleOnDragStart(const RefPtr<OHOS::Ace::DragEvent>& info)
1441 {
1442 isDragging_ = true;
1443 isReceivedArkDrag_ = true;
1444 isDragStartFromWeb_ = true;
1445 NG::DragDropInfo dragDropInfo;
1446 if (GenerateDragDropInfo(dragDropInfo)) {
1447 auto frameNode = GetHost();
1448 CHECK_NULL_RETURN(frameNode, dragDropInfo);
1449 CHECK_NULL_RETURN(delegate_, dragDropInfo);
1450 CHECK_NULL_RETURN(delegate_->dragData_, dragDropInfo);
1451 // get drag pixel map successfully, disable next drag util received web kernel drag callback
1452 frameNode->SetDraggable(false);
1453 RefPtr<UnifiedData> aceUnifiedData = UdmfClient::GetInstance()->CreateUnifiedData();
1454 std::string fileName = delegate_->dragData_->GetImageFileName();
1455 std::string plainContent = delegate_->dragData_->GetFragmentText();
1456 std::string htmlContent = delegate_->dragData_->GetFragmentHtml();
1457 std::string linkUrl = delegate_->dragData_->GetLinkURL();
1458 std::string linkTitle = delegate_->dragData_->GetLinkTitle();
1459 if (!fileName.empty()) {
1460 OnDragFileNameStart(aceUnifiedData, fileName);
1461 } else {
1462 TAG_LOGW(AceLogTag::ACE_WEB, "DragDrop event start, dragdata has no image file uri, just pass");
1463 }
1464 if (!plainContent.empty()) {
1465 isDragEndMenuShow_ = true;
1466 UdmfClient::GetInstance()->AddPlainTextRecord(aceUnifiedData, plainContent);
1467 }
1468 if (!htmlContent.empty()) {
1469 isDragEndMenuShow_ = true;
1470 UdmfClient::GetInstance()->AddHtmlRecord(aceUnifiedData, htmlContent, "");
1471 }
1472 if (!linkUrl.empty()) {
1473 isDragEndMenuShow_ = false;
1474 UdmfClient::GetInstance()->AddLinkRecord(aceUnifiedData, linkUrl, linkTitle);
1475 TAG_LOGI(AceLogTag::ACE_WEB, "web DragDrop event Start, linkUrl size:%{public}zu", linkUrl.size());
1476 }
1477 info->SetData(aceUnifiedData);
1478 HandleOnDragEnter(info);
1479 return dragDropInfo;
1480 }
1481 return dragDropInfo;
1482 }
1483
OnDragFileNameStart(const RefPtr<UnifiedData> & aceUnifiedData,const std::string & fileName)1484 void WebPattern::OnDragFileNameStart(const RefPtr<UnifiedData>& aceUnifiedData, const std::string& fileName)
1485 {
1486 isDragEndMenuShow_ = false;
1487 std::string fullName;
1488 if (delegate_->tempDir_.empty()) {
1489 fullName = "/data/storage/el2/base/haps/entry/temp/dragdrop/" + fileName;
1490 } else {
1491 fullName = delegate_->tempDir_ + "/dragdrop/" + fileName;
1492 }
1493 AppFileService::ModuleFileUri::FileUri fileUri(fullName);
1494 TAG_LOGI(AceLogTag::ACE_WEB, "web DragDrop event Start, FileUri:%{public}s, image path:%{public}s",
1495 fileUri.ToString().c_str(), fullName.c_str());
1496 std::vector<std::string> urlVec;
1497 std::string udmfUri = fileUri.ToString();
1498 urlVec.emplace_back(udmfUri);
1499 UdmfClient::GetInstance()->AddFileUriRecord(aceUnifiedData, urlVec);
1500 }
1501
HandleOnDropMove(const RefPtr<OHOS::Ace::DragEvent> & info)1502 void WebPattern::HandleOnDropMove(const RefPtr<OHOS::Ace::DragEvent>& info)
1503 {
1504 if (!isDragging_) {
1505 return;
1506 }
1507
1508 if (!isW3cDragEvent_) {
1509 return;
1510 }
1511
1512 CHECK_NULL_VOID(delegate_);
1513 auto host = GetHost();
1514 CHECK_NULL_VOID(host);
1515 auto pipelineContext = host->GetContextRefPtr();
1516 CHECK_NULL_VOID(pipelineContext);
1517 auto viewScale = pipelineContext->GetViewScale();
1518 int32_t globalX = static_cast<int32_t>(info->GetX()) * viewScale;
1519 int32_t globalY = static_cast<int32_t>(info->GetY()) * viewScale;
1520 auto offset = GetCoordinatePoint();
1521 globalX = static_cast<int32_t>(globalX - offset.value_or(OffsetF()).GetX());
1522 globalY = static_cast<int32_t>(globalY - offset.value_or(OffsetF()).GetY());
1523 delegate_->HandleDragEvent(globalX, globalY, DragAction::DRAG_OVER);
1524 }
1525
InitCommonDragDropEvent(const RefPtr<GestureEventHub> & gestureHub)1526 void WebPattern::InitCommonDragDropEvent(const RefPtr<GestureEventHub>& gestureHub)
1527 {
1528 auto frameNode = GetHost();
1529 CHECK_NULL_VOID(frameNode);
1530 auto eventHub = frameNode->GetEventHub<WebEventHub>();
1531 CHECK_NULL_VOID(eventHub);
1532
1533 isDisableDrag_ = false;
1534 // disable drag
1535 frameNode->SetDraggable(false);
1536 // init common drag drop event
1537 gestureHub->InitDragDropEvent();
1538 InitWebEventHubDragDropStart(eventHub);
1539 InitWebEventHubDragDropEnd(eventHub);
1540 InitWebEventHubDragMove(eventHub);
1541 TAG_LOGI(AceLogTag::ACE_WEB, "DragDrop WebEventHub init drag event ok");
1542 }
1543
InitWebEventHubDragDropStart(const RefPtr<WebEventHub> & eventHub)1544 void WebPattern::InitWebEventHubDragDropStart(const RefPtr<WebEventHub>& eventHub)
1545 {
1546 auto onDragStartId = [weak = WeakClaim(this)](const RefPtr<OHOS::Ace::DragEvent>& info,
1547 const std::string& extraParams) -> NG::DragDropInfo {
1548 TAG_LOGI(AceLogTag::ACE_WEB, "DragDrop WebEventHub drag start,"
1549 " x:%{public}lf, y:%{public}lf", info->GetX(), info->GetY());
1550 NG::DragDropInfo dragDropInfo;
1551 auto pattern = weak.Upgrade();
1552 if (pattern) {
1553 TAG_LOGI(AceLogTag::ACE_WEB,
1554 "DragDrop event WebEventHub onDragStartId, x:%{public}lf, y:%{public}lf, webId:%{public}d",
1555 info->GetX(), info->GetY(), pattern->GetWebId());
1556 pattern->dropX_ = 0;
1557 pattern->dropY_ = 0;
1558 return pattern->HandleOnDragStart(info);
1559 }
1560 return dragDropInfo;
1561 };
1562
1563 auto onDragEnterId = [weak = WeakClaim(this)](const RefPtr<OHOS::Ace::DragEvent>& info,
1564 const std::string& extraParams) {
1565 TAG_LOGI(AceLogTag::ACE_WEB, "DragDrop WebEventHub drag enter,"
1566 " x:%{public}lf, y:%{public}lf", info->GetX(), info->GetY());
1567 auto pattern = weak.Upgrade();
1568 CHECK_NULL_VOID(pattern);
1569 TAG_LOGI(AceLogTag::ACE_WEB,
1570 "DragDrop event WebEventHub onDragEnterId, x:%{public}lf, y:%{public}lf, webId:%{public}d",
1571 info->GetX(), info->GetY(), pattern->GetWebId());
1572 pattern->isW3cDragEvent_ = true;
1573 pattern->isDragging_ = true;
1574 pattern->isReceivedArkDrag_ = true;
1575 pattern->dropX_ = 0;
1576 pattern->dropY_ = 0;
1577 return pattern->HandleOnDragEnter(info);
1578 };
1579
1580 // set custom OnDragStart function
1581 eventHub->SetOnDragStart(std::move(onDragStartId));
1582 eventHub->SetOnDragEnter(std::move(onDragEnterId));
1583 }
1584
InitWebEventHubDragMove(const RefPtr<WebEventHub> & eventHub)1585 void WebPattern::InitWebEventHubDragMove(const RefPtr<WebEventHub>& eventHub)
1586 {
1587 auto onDragMoveId = [weak = WeakClaim(this)](const RefPtr<OHOS::Ace::DragEvent>& info,
1588 const std::string& extraParams) {
1589 static uint32_t dragMoveCnt = 0;
1590 if ((dragMoveCnt % DEBUG_DRAGMOVEID_TIMER) == 0) {
1591 TAG_LOGI(AceLogTag::ACE_WEB, "DragDrop WebEventHub drag move,"
1592 " x:%{public}lf, y:%{public}lf", info->GetX(), info->GetY());
1593 }
1594 auto pattern = weak.Upgrade();
1595 CHECK_NULL_VOID(pattern);
1596 if ((dragMoveCnt++ % DEBUG_DRAGMOVEID_TIMER) == 0) {
1597 TAG_LOGI(AceLogTag::ACE_WEB,
1598 "DragDrop event WebEventHub onDragMoveId, x:%{public}lf, y:%{public}lf, webId:%{public}d",
1599 info->GetX(), info->GetY(), pattern->GetWebId());
1600 }
1601 if (!pattern->isDragging_) {
1602 return;
1603 }
1604
1605 // update drag status
1606 info->SetResult(pattern->GetDragAcceptableStatus());
1607
1608 pattern->HandleOnDropMove(info);
1609 };
1610 // set custom OnDragStart function
1611 eventHub->SetOnDragMove(std::move(onDragMoveId));
1612 }
1613
InitWebEventHubDragDropEnd(const RefPtr<WebEventHub> & eventHub)1614 void WebPattern::InitWebEventHubDragDropEnd(const RefPtr<WebEventHub>& eventHub)
1615 {
1616 auto onDragDropId = [weak = WeakClaim(this)](const RefPtr<OHOS::Ace::DragEvent>& info,
1617 const std::string& extraParams) {
1618 TAG_LOGI(AceLogTag::ACE_WEB, "DragDrop WebEventHub drag drop,"
1619 " x:%{public}lf, y:%{public}lf", info->GetX(), info->GetY());
1620 auto pattern = weak.Upgrade();
1621 CHECK_NULL_VOID(pattern);
1622 TAG_LOGI(AceLogTag::ACE_WEB,
1623 "DragDrop event WebEventHub onDragDropId, x:%{public}lf, y:%{public}lf, webId:%{public}d",
1624 info->GetX(), info->GetY(), pattern->GetWebId());
1625 if (!pattern->isDragging_) {
1626 return;
1627 }
1628 pattern->dropX_ = info->GetX();
1629 pattern->dropY_ = info->GetY();
1630 pattern->HandleOnDragDrop(info);
1631 };
1632
1633 auto onDragLeaveId = [weak = WeakClaim(this)](const RefPtr<OHOS::Ace::DragEvent>& info,
1634 const std::string& extraParams) {
1635 TAG_LOGI(AceLogTag::ACE_WEB, "DragDrop WebEventHub drag leave,"
1636 " x:%{public}lf, y:%{public}lf", info->GetX(), info->GetY());
1637 auto pattern = weak.Upgrade();
1638 CHECK_NULL_VOID(pattern);
1639 TAG_LOGI(AceLogTag::ACE_WEB,
1640 "DragDrop event WebEventHub onDragLeaveId, x:%{public}lf, y:%{public}lf, webId:%{public}d",
1641 info->GetX(), info->GetY(), pattern->GetWebId());
1642 pattern->HandleOnDragLeave(info->GetX(), info->GetY());
1643 };
1644
1645 auto onDragEndId = [weak = WeakClaim(this)](const RefPtr<OHOS::Ace::DragEvent>& info) {
1646 TAG_LOGI(AceLogTag::ACE_WEB, "DragDrop WebEventHub drag end,"
1647 " x:%{public}lf, y:%{public}lf", info->GetX(), info->GetY());
1648 auto pattern = weak.Upgrade();
1649 CHECK_NULL_VOID(pattern);
1650 TAG_LOGI(AceLogTag::ACE_WEB,
1651 "DragDrop event WebEventHub onDragEndId, x:%{public}lf, y:%{public}lf, webId:%{public}d",
1652 info->GetX(), info->GetY(), pattern->GetWebId());
1653 pattern->HandleDragEnd(pattern->dropX_, pattern->dropY_);
1654 };
1655 // set custom OnDragStart function
1656 eventHub->SetOnDragEnd(std::move(onDragEndId));
1657 eventHub->SetOnDragLeave(std::move(onDragLeaveId));
1658 eventHub->SetOnDrop(std::move(onDragDropId));
1659 }
1660
IsImageDrag()1661 bool WebPattern::IsImageDrag()
1662 {
1663 if (delegate_) {
1664 return delegate_->IsImageDrag();
1665 }
1666 return false;
1667 }
1668
GetDragAcceptableStatus()1669 DragRet WebPattern::GetDragAcceptableStatus()
1670 {
1671 OHOS::NWeb::NWebDragData::DragOperation status = delegate_->GetDragAcceptableStatus();
1672 if (status == OHOS::NWeb::NWebDragData::DragOperation::DRAG_OPERATION_MOVE ||
1673 status == OHOS::NWeb::NWebDragData::DragOperation::DRAG_OPERATION_LINK) {
1674 return DragRet::DRAG_DEFAULT;
1675 } else if (status == OHOS::NWeb::NWebDragData::DragOperation::DRAG_OPERATION_COPY) {
1676 return DragRet::DRAG_DEFAULT;
1677 }
1678 return DragRet::DRAG_DEFAULT;
1679 }
1680
NotifyStartDragTask(bool isDelayed)1681 bool WebPattern::NotifyStartDragTask(bool isDelayed)
1682 {
1683 if (isDisableDrag_ || isTouchUpEvent_) {
1684 TAG_LOGW(AceLogTag::ACE_WEB, "DragDrop disable drag in web. isDisableDrag_:%{public}d,"
1685 "isTouchUpEvent_:%{public}d, isDelayed:%{public}d", isDisableDrag_, isTouchUpEvent_, isDelayed);
1686 if (isDelayed) {
1687 CHECK_NULL_RETURN(delegate_, false);
1688 delegate_->HandleDragEvent(0, 0, DragAction::DRAG_CANCEL);
1689 }
1690 return false;
1691 }
1692 isDragging_ = true;
1693 auto frameNode = GetHost();
1694 CHECK_NULL_RETURN(frameNode, false);
1695 auto eventHub = frameNode->GetEventHub<WebEventHub>();
1696 CHECK_NULL_RETURN(eventHub, false);
1697 auto gestureHub = eventHub->GetOrCreateGestureEventHub();
1698 CHECK_NULL_RETURN(gestureHub, false);
1699 CHECK_NULL_RETURN(delegate_, false);
1700 if (curContextMenuResult_ && (!isNewDragStyle_ || !previewImageNodeId_.has_value())) {
1701 TAG_LOGI(AceLogTag::ACE_WEB,
1702 "preview menu is not displayed, and the app is notified to close the long-press menu");
1703 delegate_->OnContextMenuHide("");
1704 }
1705 // received web kernel drag callback, enable drag
1706 frameNode->SetDraggable(true);
1707 gestureHub->SetPixelMap(delegate_->GetDragPixelMap());
1708 if (!isMouseEvent_) {
1709 // mouse drag does not need long press action
1710 bool isFloatImage = true;
1711 auto param = GetPreviewSelectionMenuParams(WebElementType::IMAGE, ResponseType::LONG_PRESS);
1712 if (isNewDragStyle_ && delegate_->IsImageDrag() && param && curContextMenuResult_) {
1713 isFloatImage = false;
1714 }
1715 gestureHub->StartLongPressActionForWeb(isFloatImage);
1716 }
1717 TAG_LOGI(AceLogTag::ACE_WEB, "DragDrop enable drag and start drag task for web,"
1718 "is mouse event: %{public}d", isMouseEvent_);
1719 gestureHub->StartDragTaskForWeb();
1720 return true;
1721 }
1722
InitDragEvent(const RefPtr<GestureEventHub> & gestureHub)1723 void WebPattern::InitDragEvent(const RefPtr<GestureEventHub>& gestureHub)
1724 {
1725 if (dragEvent_) {
1726 return;
1727 }
1728
1729 auto host = GetHost();
1730 CHECK_NULL_VOID(host);
1731 auto eventHub = host->GetEventHub<WebEventHub>();
1732 CHECK_NULL_VOID(eventHub);
1733
1734 auto userOnDragStartFunc = eventHub->GetOnDragStart();
1735 if (userOnDragStartFunc) {
1736 isDisableDrag_ = true;
1737 return;
1738 }
1739
1740 InitCommonDragDropEvent(gestureHub);
1741
1742 auto actionStartTask = [weak = WeakClaim(this)](const GestureEvent& info) {
1743 int32_t x = info.GetGlobalPoint().GetX();
1744 int32_t y = info.GetGlobalPoint().GetY();
1745 auto pattern = weak.Upgrade();
1746 CHECK_NULL_VOID(pattern);
1747 TAG_LOGI(AceLogTag::ACE_WEB,
1748 "DragDrop event gestureHub actionStartTask x:%{public}d, y:%{public}d, webId:%{public}d",
1749 x, y, pattern->GetWebId());
1750 pattern->HandleDragStart(x, y);
1751 };
1752
1753 auto actionUpdateTask = [weak = WeakClaim(this)](const GestureEvent& info) {
1754 return;
1755 };
1756
1757 auto actionEndTask = [weak = WeakClaim(this)](const GestureEvent& info) {
1758 int32_t x = info.GetGlobalPoint().GetX();
1759 int32_t y = info.GetGlobalPoint().GetY();
1760 auto pattern = weak.Upgrade();
1761 CHECK_NULL_VOID(pattern);
1762 TAG_LOGI(AceLogTag::ACE_WEB,
1763 "DragDrop event gestureHub actionEndTask x:%{public}d, y:%{public}d, webId:%{public}d",
1764 x, y, pattern->GetWebId());
1765 pattern->HandleDragEnd(x, y);
1766 };
1767
1768 auto actionCancelTask = [weak = WeakClaim(this)]() {
1769 };
1770
1771 dragEvent_ = MakeRefPtr<DragEvent>(
1772 std::move(actionStartTask), std::move(actionUpdateTask), std::move(actionEndTask), std::move(actionCancelTask));
1773 gestureHub->SetCustomDragEvent(dragEvent_, { PanDirection::ALL }, DEFAULT_PAN_FINGER, DEFAULT_PAN_DISTANCE);
1774 }
1775
HandleDragStart(int32_t x,int32_t y)1776 void WebPattern::HandleDragStart(int32_t x, int32_t y)
1777 {
1778 TAG_LOGI(AceLogTag::ACE_WEB,
1779 "HandleDragStart DragDrop event actionStart, isDragStartFromWeb_:%{public}d, isMouseEvent_:%{public}d",
1780 (int)isDragStartFromWeb_, (int)isMouseEvent_);
1781 if (!isDragStartFromWeb_ && !isMouseEvent_) {
1782 auto frameNode = GetHost();
1783 CHECK_NULL_VOID(frameNode);
1784 frameNode->SetDraggable(false);
1785 auto eventHub = frameNode->GetEventHub<WebEventHub>();
1786 CHECK_NULL_VOID(eventHub);
1787 auto gestureHub = eventHub->GetOrCreateGestureEventHub();
1788 CHECK_NULL_VOID(gestureHub);
1789 gestureHub->ResetDragActionForWeb();
1790 isDragging_ = false;
1791 isReceivedArkDrag_ = false;
1792 // cancel drag action to avoid web kernel can't process other input event
1793 CHECK_NULL_VOID(delegate_);
1794 delegate_->HandleDragEvent(0, 0, DragAction::DRAG_CANCEL);
1795 gestureHub->CancelDragForWeb();
1796 }
1797 if (!isDragStartFromWeb_ && isMouseEvent_) {
1798 auto frameNode = GetHost();
1799 CHECK_NULL_VOID(frameNode);
1800 auto eventHub = frameNode->GetEventHub<WebEventHub>();
1801 CHECK_NULL_VOID(eventHub);
1802 auto gestureHub = eventHub->GetOrCreateGestureEventHub();
1803 CHECK_NULL_VOID(gestureHub);
1804 gestureHub->SetMouseDragMonitorState(true);
1805 }
1806 }
1807
HandleOnDragEnter(const RefPtr<OHOS::Ace::DragEvent> & info)1808 void WebPattern::HandleOnDragEnter(const RefPtr<OHOS::Ace::DragEvent>& info)
1809 {
1810 if (!delegate_) {
1811 return;
1812 }
1813
1814 auto host = GetHost();
1815 CHECK_NULL_VOID(host);
1816 auto pipelineContext = host->GetContextRefPtr();
1817 CHECK_NULL_VOID(pipelineContext);
1818 int32_t globalX = static_cast<int32_t>(info->GetX());
1819 int32_t globalY = static_cast<int32_t>(info->GetY());
1820 auto viewScale = pipelineContext->GetViewScale();
1821 auto offset = GetCoordinatePoint();
1822 int32_t localX = static_cast<int32_t>(globalX - offset.value_or(OffsetF()).GetX()) * viewScale;
1823 int32_t localY = static_cast<int32_t>(globalY - offset.value_or(OffsetF()).GetY()) * viewScale;
1824
1825 // fake drag data when enter
1826 delegate_->GetOrCreateDragData();
1827 // use summary to set fake data
1828 if (!isDragStartFromWeb_) {
1829 ClearDragData();
1830 SetFakeDragData(info);
1831 }
1832 delegate_->HandleDragEvent(localX, localY, DragAction::DRAG_ENTER);
1833 // RequestFocus to show the carret frame_caret
1834 WebRequestFocus();
1835 }
1836
HandleOnDragDropLink(RefPtr<UnifiedData> aceData)1837 void WebPattern::HandleOnDragDropLink(RefPtr<UnifiedData> aceData)
1838 {
1839 CHECK_NULL_VOID(aceData);
1840 CHECK_NULL_VOID(delegate_);
1841 CHECK_NULL_VOID(delegate_->dragData_);
1842 // hyperlink
1843 std::string linkUrl;
1844 std::string linkTitle;
1845 UdmfClient::GetInstance()->GetLinkRecord(aceData, linkUrl, linkTitle);
1846 if (!linkUrl.empty()) {
1847 delegate_->dragData_->SetLinkURL(linkUrl);
1848 delegate_->dragData_->SetLinkTitle(linkTitle);
1849 TAG_LOGI(AceLogTag::ACE_WEB,
1850 "DragDrop event WebEventHub onDragDropId, linkUrl size:%{public}zu", linkUrl.size());
1851 } else {
1852 TAG_LOGW(AceLogTag::ACE_WEB,
1853 "DragDrop event WebEventHub onDragDropId, linkUrl is empty");
1854 }
1855 }
1856
HandleOnDragDropFile(RefPtr<UnifiedData> aceData)1857 void WebPattern::HandleOnDragDropFile(RefPtr<UnifiedData> aceData)
1858 {
1859 CHECK_NULL_VOID(aceData);
1860 CHECK_NULL_VOID(delegate_);
1861 CHECK_NULL_VOID(delegate_->dragData_);
1862 // file
1863 std::vector<std::string> urlVec;
1864 UdmfClient::GetInstance()->GetFileUriRecord(aceData, urlVec);
1865 TAG_LOGI(AceLogTag::ACE_WEB, "DragDrop event WebEventHub onDragDropId,"
1866 "url array size is:%{public}zu", urlVec.size());
1867 delegate_->dragData_->ClearImageFileNames();
1868 for (std::string url : urlVec) {
1869 TAG_LOGI(AceLogTag::ACE_WEB, "DragDrop event WebEventHub onDragDropId,"
1870 "url get from udmf:%{public}zu", url.length());
1871 AppFileService::ModuleFileUri::FileUri fileUri(url);
1872 TAG_LOGI(AceLogTag::ACE_WEB, "DragDrop event WebEventHub onDragDropId,"
1873 "fileUri ToString:%{public}zu", fileUri.ToString().length());
1874 std::string uriRealPath = FileUriHelper::GetRealPath(url);
1875 if (!uriRealPath.empty() && access(uriRealPath.c_str(), F_OK) == 0) { // file exist
1876 TAG_LOGI(AceLogTag::ACE_WEB, "DragDrop event WebEventHub onDragDropId,"
1877 "url real path:%{public}zu", uriRealPath.length());
1878 delegate_->dragData_->SetFileUri(uriRealPath);
1879 } else {
1880 TAG_LOGW(AceLogTag::ACE_WEB, "DragDrop event WebEventHub onDragDropId,"
1881 "url is empty or not exist, uriRealPath:%{public}zu", uriRealPath.length());
1882 }
1883 }
1884 }
1885
ResetDragStateValue()1886 void WebPattern::ResetDragStateValue()
1887 {
1888 isDragging_ = false;
1889 isReceivedArkDrag_ = false;
1890 isW3cDragEvent_ = false;
1891 isDragStartFromWeb_ = false;
1892 }
1893
HandleOnDragDrop(const RefPtr<OHOS::Ace::DragEvent> & info)1894 void WebPattern::HandleOnDragDrop(const RefPtr<OHOS::Ace::DragEvent>& info)
1895 {
1896 ResetDragStateValue();
1897 CHECK_NULL_VOID(delegate_);
1898 auto host = GetHost();
1899 CHECK_NULL_VOID(host);
1900 auto pipelineContext = host->GetContextRefPtr();
1901 CHECK_NULL_VOID(pipelineContext);
1902 auto viewScale = pipelineContext->GetViewScale();
1903 auto offset = GetCoordinatePoint();
1904 int32_t localX = static_cast<int32_t>(info->GetX() - offset.value_or(OffsetF()).GetX()) * viewScale;
1905 int32_t localY = static_cast<int32_t>(info->GetY() - offset.value_or(OffsetF()).GetY()) * viewScale;
1906
1907 RefPtr<UnifiedData> aceData = info->GetData();
1908 // get data from ace(from udmf), and send it to chromium
1909 if (aceData && aceData->GetSize() >= 1) {
1910 TAG_LOGI(AceLogTag::ACE_WEB,
1911 "DragDrop event WebEventHub onDragDropId, size:%{public}" PRId64 "", aceData->GetSize());
1912 CHECK_NULL_VOID(delegate_->dragData_);
1913 // plain text
1914 std::vector<std::string> plains = UdmfClient::GetInstance()->GetPlainTextRecords(aceData);
1915 if (!plains.empty() && !plains[0].empty()) {
1916 std::string plain = plains[0];
1917 delegate_->dragData_->SetFragmentText(plain);
1918 TAG_LOGI(AceLogTag::ACE_WEB,
1919 "DragDrop event WebEventHub onDragDropId, plain size:%{public}zu", plain.size());
1920 }
1921 // html
1922 std::string htmlContent;
1923 std::string plainContent;
1924 UdmfClient::GetInstance()->GetHtmlRecord(aceData, htmlContent, plainContent);
1925 if (!htmlContent.empty()) {
1926 delegate_->dragData_->SetFragmentHtml(htmlContent);
1927 TAG_LOGI(AceLogTag::ACE_WEB,
1928 "DragDrop event WebEventHub onDragDropId, htmlContent size:%{public}zu", htmlContent.size());
1929 }
1930 // spanstring
1931 std::vector<uint8_t> spanString = UdmfClient::GetInstance()->GetSpanStringRecord(aceData);
1932 if (!spanString.empty()) {
1933 std::string htmlStr = OHOS::Ace::SpanToHtml::ToHtml(spanString);
1934 delegate_->dragData_->SetFragmentHtml(htmlStr);
1935 TAG_LOGI(AceLogTag::ACE_WEB,
1936 "DragDrop event WebEventHub onDragDropId, spanstring to html success, html size:%{public}zu",
1937 htmlStr.size());
1938 }
1939 // link
1940 HandleOnDragDropLink(aceData);
1941 // file
1942 HandleOnDragDropFile(aceData);
1943 } else {
1944 TAG_LOGW(AceLogTag::ACE_WEB, "DragDrop event WebEventHub onDragDropId get data failed");
1945 }
1946
1947 delegate_->HandleDragEvent(localX, localY, DragAction::DRAG_DROP);
1948 delegate_->RegisterWebWindowFocusChangedListener();
1949 }
1950
HandleOnDragLeave(int32_t x,int32_t y)1951 void WebPattern::HandleOnDragLeave(int32_t x, int32_t y)
1952 {
1953 CHECK_NULL_VOID(delegate_);
1954 isDragging_ = false;
1955 isW3cDragEvent_ = false;
1956 isReceivedArkDrag_ = isDragStartFromWeb_ ? isReceivedArkDrag_ : false;
1957 auto host = GetHost();
1958 CHECK_NULL_VOID(host);
1959 auto pipelineContext = host->GetContextRefPtr();
1960 CHECK_NULL_VOID(pipelineContext);
1961 auto viewScale = pipelineContext->GetViewScale();
1962 auto offset = GetCoordinatePoint();
1963 int32_t localX = static_cast<int32_t>(x - offset.value_or(OffsetF()).GetX());
1964 int32_t localY = static_cast<int32_t>(y - offset.value_or(OffsetF()).GetY());
1965 delegate_->HandleDragEvent(localX * viewScale, localY * viewScale, DragAction::DRAG_LEAVE);
1966 }
1967
HandleDragEnd(int32_t x,int32_t y)1968 void WebPattern::HandleDragEnd(int32_t x, int32_t y)
1969 {
1970 CHECK_NULL_VOID(delegate_);
1971
1972 isDragging_ = false;
1973 isReceivedArkDrag_ = false;
1974 isW3cDragEvent_ = false;
1975 isDragStartFromWeb_ = false;
1976 ClearDragData();
1977
1978 auto host = GetHost();
1979 CHECK_NULL_VOID(host);
1980 auto pipelineContext = host->GetContextRefPtr();
1981 CHECK_NULL_VOID(pipelineContext);
1982 auto viewScale = pipelineContext->GetViewScale();
1983 auto offset = GetCoordinatePoint();
1984 int32_t localX = static_cast<int32_t>(x - offset.value_or(OffsetF()).GetX()) * viewScale;
1985 int32_t localY = static_cast<int32_t>(y - offset.value_or(OffsetF()).GetY()) * viewScale;
1986 if (x == 0 && y == 0) {
1987 delegate_->HandleDragEvent(0, 0, DragAction::DRAG_END);
1988 } else {
1989 delegate_->HandleDragEvent(localX, localY, DragAction::DRAG_END);
1990 }
1991 }
1992
HandleDragCancel()1993 void WebPattern::HandleDragCancel()
1994 {
1995 auto frameNode = GetHost();
1996 CHECK_NULL_VOID(frameNode);
1997 // disable drag
1998 frameNode->SetDraggable(false);
1999 CHECK_NULL_VOID(delegate_);
2000 isDragging_ = false;
2001 isReceivedArkDrag_ = false;
2002 isW3cDragEvent_ = false;
2003 isDragStartFromWeb_ = false;
2004 ClearDragData();
2005 delegate_->HandleDragEvent(0, 0, DragAction::DRAG_CANCEL);
2006 }
2007
ClearDragData()2008 void WebPattern::ClearDragData()
2009 {
2010 CHECK_NULL_VOID(delegate_);
2011 std::string plain = "";
2012 std::string htmlContent = "";
2013 std::string linkUrl = "";
2014 std::string linkTitle = "";
2015 if (delegate_->dragData_) {
2016 delegate_->dragData_->SetFragmentText(plain);
2017 delegate_->dragData_->SetFragmentHtml(htmlContent);
2018 delegate_->dragData_->SetLinkURL(linkUrl);
2019 delegate_->dragData_->SetLinkTitle(linkTitle);
2020 delegate_->dragData_->ClearImageFileNames();
2021 }
2022 }
2023
SetFakeDragData(const RefPtr<OHOS::Ace::DragEvent> & info)2024 void WebPattern::SetFakeDragData(const RefPtr<OHOS::Ace::DragEvent>& info)
2025 {
2026 CHECK_NULL_VOID(delegate_);
2027 CHECK_NULL_VOID(delegate_->dragData_);
2028 if (info && !info->GetSummary().empty()) {
2029 std::map<std::string, int64_t> dragDataSummary = info->GetSummary();
2030 TAG_LOGI(AceLogTag::ACE_WEB, "DragDrop, set fake drag data by summary, summary size is %{public}zu",
2031 dragDataSummary.size());
2032 std::map<std::string, int64_t>::iterator iter;
2033 for (iter = dragDataSummary.begin(); iter != dragDataSummary.end(); iter++) {
2034 if (FILE_TYPE_SET.find(iter->first) != FILE_TYPE_SET.end()) {
2035 delegate_->dragData_->SetFileUri(FAKE_DRAG_DATA_VAL);
2036 } else if (DRAG_DATA_TYPE_TEXT == iter->first) {
2037 delegate_->dragData_->SetFragmentText(FAKE_DRAG_DATA_VAL);
2038 } else if (DRAG_DATA_TYPE_HTML == iter->first) {
2039 delegate_->dragData_->SetFragmentHtml(FAKE_DRAG_DATA_VAL);
2040 } else if (DRAG_DATA_TYPE_LINK == iter->first) {
2041 delegate_->dragData_->SetLinkURL(FAKE_LINK_VAL);
2042 delegate_->dragData_->SetLinkTitle(FAKE_LINK_VAL);
2043 }
2044 }
2045 return;
2046 }
2047 delegate_->dragData_->SetFragmentText(FAKE_DRAG_DATA_VAL);
2048 delegate_->dragData_->SetFragmentHtml(FAKE_DRAG_DATA_VAL);
2049 }
2050
InitFocusEvent(const RefPtr<FocusHub> & focusHub)2051 void WebPattern::InitFocusEvent(const RefPtr<FocusHub>& focusHub)
2052 {
2053 auto focusTask = [weak = WeakClaim(this)]() {
2054 auto pattern = weak.Upgrade();
2055 CHECK_NULL_VOID(pattern);
2056 pattern->HandleFocusEvent();
2057 };
2058 focusHub->SetOnFocusInternal(focusTask);
2059
2060 auto blurTask = [weak = WeakClaim(this)](const BlurReason& blurReason) {
2061 auto pattern = weak.Upgrade();
2062 CHECK_NULL_VOID(pattern);
2063 pattern->HandleBlurEvent(blurReason);
2064 };
2065 focusHub->SetOnBlurReasonInternal(blurTask);
2066
2067 auto keyTask = [weak = WeakClaim(this)](const KeyEvent& keyEvent) -> bool {
2068 auto pattern = weak.Upgrade();
2069 CHECK_NULL_RETURN(pattern, false);
2070 return pattern->HandleKeyEvent(keyEvent);
2071 };
2072 focusHub->SetOnKeyEventInternal(keyTask);
2073 }
2074
HandleFocusEvent()2075 void WebPattern::HandleFocusEvent()
2076 {
2077 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::HandleFocusEvent webId:%{public}d, needOnFocus: %{public}d.", GetWebId(),
2078 needOnFocus_);
2079 CHECK_NULL_VOID(delegate_);
2080 isFocus_ = true;
2081 if (needOnFocus_) {
2082 delegate_->OnFocus();
2083 } else {
2084 delegate_->OnFocus(OHOS::NWeb::FocusReason::FOCUS_DEFAULT);
2085 needOnFocus_ = true;
2086 }
2087 }
2088
HandleBlurEvent(const BlurReason & blurReason)2089 void WebPattern::HandleBlurEvent(const BlurReason& blurReason)
2090 {
2091 TAG_LOGI(AceLogTag::ACE_WEB,
2092 "HandleBlurEvent webId:%{public}d, selectPopupMenuShowing: %{public}d, isDragStartFromWeb: %{public}d",
2093 GetWebId(), selectPopupMenuShowing_, isDragStartFromWeb_);
2094 CHECK_NULL_VOID(delegate_);
2095 isFocus_ = false;
2096
2097 if (isDragStartFromWeb_) {
2098 return;
2099 }
2100 if (!selectPopupMenuShowing_) {
2101 delegate_->SetBlurReason(static_cast<OHOS::NWeb::BlurReason>(blurReason));
2102 delegate_->OnBlur();
2103 }
2104 OnQuickMenuDismissed();
2105 CloseContextSelectionMenu();
2106 if (!isVisible_ && isActive_ && IsDialogNested()) {
2107 TAG_LOGI(AceLogTag::ACE_WEB, "HandleBlurEvent, dialog nested blur but invisible while active, set inactive.");
2108 OnInActive();
2109 }
2110 HideMagnifier();
2111 }
2112
HandleKeyEvent(const KeyEvent & keyEvent)2113 bool WebPattern::HandleKeyEvent(const KeyEvent& keyEvent)
2114 {
2115 bool ret = false;
2116
2117 auto host = GetHost();
2118 CHECK_NULL_RETURN(host, ret);
2119 auto eventHub = host->GetEventHub<WebEventHub>();
2120 CHECK_NULL_RETURN(eventHub, ret);
2121
2122 KeyEventInfo info(keyEvent);
2123 auto keyEventCallback = eventHub->GetOnKeyEvent();
2124 if (keyEventCallback) {
2125 keyEventCallback(info);
2126 }
2127
2128 auto preKeyEventCallback = eventHub->GetOnPreKeyEvent();
2129 if (preKeyEventCallback) {
2130 ret = preKeyEventCallback(info);
2131 if (ret) {
2132 return ret;
2133 }
2134 }
2135
2136 ret = WebOnKeyEvent(keyEvent);
2137 return ret;
2138 }
2139
ClearKeyEventByKeyCode(int32_t keyCode)2140 void WebPattern::ClearKeyEventByKeyCode(int32_t keyCode)
2141 {
2142 auto keyEvent = webKeyEvent_.begin();
2143 for (; keyEvent != webKeyEvent_.end();) {
2144 if (static_cast<int32_t>(keyEvent->code) == keyCode) {
2145 keyEvent = webKeyEvent_.erase(keyEvent);
2146 } else {
2147 ++keyEvent;
2148 }
2149 }
2150
2151 if (webKeyEvent_.size() >= KEYEVENT_MAX_NUM) {
2152 webKeyEvent_.clear();
2153 TAG_LOGW(AceLogTag::ACE_WEB,
2154 "WebPattern::ClearKeyEventByKeyCode clear all keyevent.");
2155 } else {
2156 TAG_LOGW(AceLogTag::ACE_WEB,
2157 "WebPattern::ClearKeyEventByKeyCode clear all tab keyevent.");
2158 }
2159 }
2160
WebOnKeyEvent(const KeyEvent & keyEvent)2161 bool WebPattern::WebOnKeyEvent(const KeyEvent& keyEvent)
2162 {
2163 CHECK_NULL_RETURN(delegate_, false);
2164 if (webKeyEvent_.size() >= KEYEVENT_MAX_NUM) {
2165 ClearKeyEventByKeyCode(static_cast<int32_t>(KeyCode::KEY_TAB));
2166 }
2167 TAG_LOGD(AceLogTag::ACE_WEB,
2168 "WebPattern::WebOnKeyEvent keyEvent:%{public}s", keyEvent.ToString().c_str());
2169 webKeyEvent_.push_back(keyEvent);
2170 std::vector<int32_t> pressedCodes;
2171 for (auto pCode : keyEvent.pressedCodes) {
2172 pressedCodes.push_back(static_cast<int32_t>(pCode));
2173 }
2174 KeyCode code = keyEvent.code;
2175 auto item = g_numPadFunctionMap.find(code);
2176 if (!keyEvent.numLock && item != g_numPadFunctionMap.end()) {
2177 code = item->second;
2178 }
2179 std::shared_ptr<NWebKeyboardEventImpl> keyboardEvent =
2180 std::make_shared<NWebKeyboardEventImpl>(static_cast<int32_t>(code),
2181 static_cast<int32_t>(keyEvent.action),
2182 keyEvent.unicode,
2183 keyEvent.enableCapsLock,
2184 pressedCodes);
2185 return delegate_->SendKeyboardEvent(keyboardEvent);
2186 }
2187
KeyboardReDispatch(const std::shared_ptr<OHOS::NWeb::NWebKeyEvent> & event,bool isUsed)2188 void WebPattern::KeyboardReDispatch(
2189 const std::shared_ptr<OHOS::NWeb::NWebKeyEvent>& event, bool isUsed)
2190 {
2191 CHECK_NULL_VOID(event);
2192 auto container = Container::Current();
2193 CHECK_NULL_VOID(container);
2194 auto host = GetHost();
2195 CHECK_NULL_VOID(host);
2196 auto pipelineContext = host->GetContext();
2197 CHECK_NULL_VOID(pipelineContext);
2198 auto taskExecutor = pipelineContext->GetTaskExecutor();
2199 CHECK_NULL_VOID(taskExecutor);
2200 auto keyEvent = webKeyEvent_.rbegin();
2201 for (; keyEvent != webKeyEvent_.rend(); ++keyEvent) {
2202 if (static_cast<int32_t>(keyEvent->code) == event->GetKeyCode() &&
2203 static_cast<int32_t>(keyEvent->action) == event->GetAction()) {
2204 break;
2205 }
2206 }
2207 if (keyEvent == webKeyEvent_.rend()) {
2208 TAG_LOGW(AceLogTag::ACE_WEB,
2209 "KeyEvent is not find keycode:%{public}d, action:%{public}d", event->GetKeyCode(), event->GetAction());
2210 return;
2211 }
2212 if (!isUsed) {
2213 taskExecutor->PostTask([context = AceType::WeakClaim(pipelineContext),
2214 event = *keyEvent] () {
2215 auto pipelineContext = context.Upgrade();
2216 CHECK_NULL_VOID(pipelineContext);
2217 TAG_LOGD(AceLogTag::ACE_WEB,
2218 "WebPattern::KeyboardReDispatch key:%{public}s", event.ToString().c_str());
2219 pipelineContext->ReDispatch(const_cast<KeyEvent&>(event));
2220 },
2221 TaskExecutor::TaskType::UI, "ArkUIWebKeyboardReDispatch");
2222 }
2223 TAG_LOGD(AceLogTag::ACE_WEB,
2224 "WebPattern::KeyboardReDispatch erase key:%{public}s", keyEvent->ToString().c_str());
2225 webKeyEvent_.erase((++keyEvent).base());
2226 }
2227
WebRequestFocus()2228 void WebPattern::WebRequestFocus()
2229 {
2230 auto host = GetHost();
2231 CHECK_NULL_VOID(host);
2232 auto eventHub = host->GetEventHub<WebEventHub>();
2233 CHECK_NULL_VOID(eventHub);
2234 auto focusHub = eventHub->GetOrCreateFocusHub();
2235 CHECK_NULL_VOID(focusHub);
2236
2237 focusHub->RequestFocusImmediately();
2238 }
2239
UpdateContentOffset(const RefPtr<LayoutWrapper> & dirty)2240 void WebPattern::UpdateContentOffset(const RefPtr<LayoutWrapper>& dirty)
2241 {
2242 CHECK_NULL_VOID(dirty);
2243 auto geometryNode = dirty->GetGeometryNode();
2244 CHECK_NULL_VOID(geometryNode);
2245 auto host = GetHost();
2246 CHECK_NULL_VOID(host);
2247 auto renderContext = host->GetRenderContext();
2248 CHECK_NULL_VOID(renderContext);
2249 auto paddingOffset = geometryNode->GetPaddingOffset();
2250 auto webContentSize = geometryNode->GetContentSize();
2251
2252 auto positionProperty = renderContext->GetPropertyOfPosition();
2253 renderContext->SetBounds(
2254 paddingOffset.GetX() + positionProperty.GetX(), paddingOffset.GetY() + positionProperty.GetY(),
2255 webContentSize.Width(), webContentSize.Height());
2256 }
2257
OnDirtyLayoutWrapperSwap(const RefPtr<LayoutWrapper> & dirty,const DirtySwapConfig & config)2258 bool WebPattern::OnDirtyLayoutWrapperSwap(const RefPtr<LayoutWrapper>& dirty, const DirtySwapConfig& config)
2259 {
2260 UpdateImagePreviewParam();
2261 if (!config.contentSizeChange || isInWindowDrag_) {
2262 if (isLayoutModeChanged_) {
2263 isLayoutModeChanged_ = false;
2264 } else {
2265 return false;
2266 }
2267 }
2268 CHECK_NULL_RETURN(delegate_, false);
2269 CHECK_NULL_RETURN(dirty, false);
2270
2271 Size drawSize = Size(1, 1);
2272 auto frameNode = GetHost();
2273 CHECK_NULL_RETURN(frameNode, false);
2274 auto renderContext = frameNode->GetRenderContext();
2275 CHECK_NULL_RETURN(renderContext, false);
2276 auto rect = renderContext->GetPaintRectWithoutTransform();
2277 drawSize = Size(rect.Width(), rect.Height());
2278 if (drawSize.IsInfinite() || drawSize.IsEmpty()) {
2279 return false;
2280 }
2281
2282 if (GreatOrEqual(drawSize.Width(), Infinity<double>())) {
2283 drawSize.SetWidth(DEFAULT_WEB_WIDTH);
2284 }
2285 if (GreatOrEqual(drawSize.Height(), Infinity<double>())) {
2286 drawSize.SetHeight(DEFAULT_WEB_HEIGHT);
2287 }
2288
2289 drawSize_ = drawSize;
2290 drawSizeCache_ = drawSize_;
2291 auto offset = Offset(GetCoordinatePoint()->GetX(), GetCoordinatePoint()->GetY());
2292
2293 if (!CheckSafeAreaIsExpand()) {
2294 TAG_LOGD(AceLogTag::ACE_WEB, "Not safe area, drawsize_ : %{public}s", drawSize_.ToString().c_str());
2295 delegate_->SetBoundsOrResize(drawSize_, offset, isKeyboardInSafeArea_);
2296 IsNeedResizeVisibleViewport();
2297 isKeyboardInSafeArea_ = false;
2298 } else {
2299 TAG_LOGD(AceLogTag::ACE_WEB, "OnDirtyLayoutWrapperSwap safeArea ins not set, no need setbouns");
2300 }
2301
2302 if (offlineWebInited_ && !offlineWebRendered_) {
2303 TAG_LOGI(AceLogTag::ACE_WEB,
2304 "OnDirtyLayoutWrapperSwap; WebPattern is Offline Mode, WebId:%{public}d", GetWebId());
2305 offlineWebRendered_ = true;
2306 delegate_->ShowWebView();
2307 }
2308 // first update size to load url.
2309 if (!isUrlLoaded_) {
2310 isUrlLoaded_ = true;
2311 if (webSrc_) {
2312 delegate_->LoadUrl();
2313 } else if (webData_) {
2314 delegate_->LoadDataWithRichText();
2315 }
2316 }
2317
2318 if (renderMode_ == RenderMode::SYNC_RENDER) {
2319 return true;
2320 }
2321 return false;
2322 }
2323
BeforeSyncGeometryProperties(const DirtySwapConfig & config)2324 void WebPattern::BeforeSyncGeometryProperties(const DirtySwapConfig& config)
2325 {
2326 if (!config.contentSizeChange || isInWindowDrag_) {
2327 return;
2328 }
2329 auto frameNode = GetHost();
2330 CHECK_NULL_VOID(frameNode);
2331 auto renderContext = frameNode->GetRenderContext();
2332 CHECK_NULL_VOID(renderContext);
2333 auto rect = renderContext->GetPaintRectWithoutTransform();
2334 auto drawSize = Size(rect.Width(), rect.Height());
2335 if (drawSize.IsInfinite() || drawSize.IsEmpty()) {
2336 return;
2337 }
2338
2339 if (GreatOrEqual(drawSize.Width(), Infinity<double>())) {
2340 drawSize.SetWidth(DEFAULT_WEB_WIDTH);
2341 }
2342 if (GreatOrEqual(drawSize.Height(), Infinity<double>())) {
2343 drawSize.SetHeight(DEFAULT_WEB_HEIGHT);
2344 }
2345
2346 if (layoutMode_ != WebLayoutMode::FIT_CONTENT) {
2347 drawSize_ = drawSize;
2348 drawSizeCache_ = drawSize_;
2349 }
2350
2351 TAG_LOGD(AceLogTag::ACE_WEB, "BeforeSync, drawsize_ : %{public}s", drawSize.ToString().c_str());
2352 }
2353
UpdateLayoutAfterKeyboardShow(int32_t width,int32_t height,double keyboard,double oldWebHeight)2354 void WebPattern::UpdateLayoutAfterKeyboardShow(int32_t width, int32_t height, double keyboard, double oldWebHeight)
2355 {
2356 lastKeyboardHeight_ = keyboard;
2357 if (isVirtualKeyBoardShow_ != VkState::VK_SHOW) {
2358 return;
2359 }
2360
2361 TAG_LOGI(AceLogTag::ACE_WEB,
2362 "KeyboardShow height:%{public}d, keyboard:%{public}f, offset:%{public}f, oldWebHeight:%{public}f",
2363 height, keyboard, GetCoordinatePoint()->GetY(), oldWebHeight);
2364 if (CheckSafeAreaKeyBoard()) {
2365 TAG_LOGI(AceLogTag::ACE_WEB, "CheckSafeAreaKeyBoard, no need resize");
2366 return;
2367 }
2368 if (GreatOrEqual(height, keyboard + GetCoordinatePoint()->GetY())) {
2369 double newHeight = height - keyboard - GetCoordinatePoint()->GetY();
2370 if (NearEqual(newHeight, oldWebHeight)) {
2371 return;
2372 }
2373 bool isUpdate = true;
2374 if (keyBoardAvoidMode_ == WebKeyboardAvoidMode::RESIZE_VISUAL) {
2375 visibleViewportSize_.SetWidth(drawSize_.Width());
2376 visibleViewportSize_.SetHeight(newHeight);
2377 isUpdate = false;
2378 } else if (keyBoardAvoidMode_ == WebKeyboardAvoidMode::OVERLAYS_CONTENT) {
2379 return;
2380 } else {
2381 TAG_LOGI(AceLogTag::ACE_WEB, "KeyboardShow newHeight: %{public}f", newHeight);
2382 drawSize_.SetHeight(newHeight);
2383 visibleViewportSize_.SetWidth(-1.0);
2384 visibleViewportSize_.SetHeight(-1.0);
2385 }
2386 UpdateWebLayoutSize(width, height, true, isUpdate);
2387 }
2388 }
2389
OnAreaChangedInner()2390 void WebPattern::OnAreaChangedInner()
2391 {
2392 auto offset = GetCoordinatePoint().value_or(OffsetF());
2393 auto resizeOffset = Offset(offset.GetX(), offset.GetY());
2394 auto frameNode = GetHost();
2395 CHECK_NULL_VOID(frameNode);
2396 auto renderContext = frameNode->GetRenderContext();
2397 CHECK_NULL_VOID(renderContext);
2398 auto geometryNode = frameNode->GetGeometryNode();
2399 CHECK_NULL_VOID(geometryNode);
2400 auto rect = renderContext->GetPaintRectWithoutTransform();
2401 auto size = Size(rect.Width(), rect.Height());
2402 delegate_->OnAreaChange({ resizeOffset.GetX(), resizeOffset.GetY(), size.Width(), size.Height() });
2403 if (CheckSafeAreaIsExpand() &&
2404 ((size.Width() != areaChangeSize_.Width()) || (size.Height() != areaChangeSize_.Height()))) {
2405 TAG_LOGD(AceLogTag::ACE_WEB, "OnAreaChangedInner setbounds: height:%{public}f, offsetY:%{public}f",
2406 size.Height(), resizeOffset.GetY());
2407 areaChangeSize_ = size;
2408 drawSize_ = size;
2409 if (renderMode_ != RenderMode::SYNC_RENDER) {
2410 drawSizeCache_ = drawSize_;
2411 }
2412 TAG_LOGD(AceLogTag::ACE_WEB, "Safe area, drawsize_ : %{public}s", drawSize_.ToString().c_str());
2413 delegate_->SetBoundsOrResize(drawSize_, resizeOffset, isKeyboardInSafeArea_);
2414 IsNeedResizeVisibleViewport();
2415 isKeyboardInSafeArea_ = false;
2416 }
2417 if (layoutMode_ == WebLayoutMode::NONE && renderMode_ == RenderMode::ASYNC_RENDER) {
2418 if (isVirtualKeyBoardShow_ != VkState::VK_SHOW) {
2419 drawSize_ = size;
2420 TAG_LOGD(AceLogTag::ACE_WEB, "ASYNC_RENDER, drawsize_ : %{public}s", drawSize_.ToString().c_str());
2421 }
2422 if (webOffset_ == offset) {
2423 return;
2424 }
2425 }
2426 if (offset != webOffset_) {
2427 webOffset_ = offset;
2428 if (webSelectOverlay_ && webSelectOverlay_->IsShowHandle())
2429 webSelectOverlay_->UpdateTouchHandleForOverlay();
2430 }
2431 if (isInWindowDrag_)
2432 return;
2433 TAG_LOGD(AceLogTag::ACE_WEB, "Normal state, drawsize_ : %{public}s", drawSize_.ToString().c_str());
2434 delegate_->SetBoundsOrResize(drawSize_, resizeOffset, isKeyboardInSafeArea_);
2435 IsNeedResizeVisibleViewport();
2436 isKeyboardInSafeArea_ = false;
2437 if (renderMode_ == RenderMode::SYNC_RENDER) {
2438 UpdateSlideOffset();
2439 }
2440 }
2441
OnWebSrcUpdate()2442 void WebPattern::OnWebSrcUpdate()
2443 {
2444 if (delegate_ && isUrlLoaded_) {
2445 delegate_->LoadUrl();
2446 }
2447 }
2448
OnWebDataUpdate()2449 void WebPattern::OnWebDataUpdate()
2450 {
2451 if (delegate_ && isUrlLoaded_) {
2452 delegate_->LoadDataWithRichText();
2453 }
2454 }
2455
OnJsEnabledUpdate(bool value)2456 void WebPattern::OnJsEnabledUpdate(bool value)
2457 {
2458 if (delegate_) {
2459 delegate_->UpdateJavaScriptEnabled(value);
2460 }
2461 }
2462
OnMediaPlayGestureAccessUpdate(bool value)2463 void WebPattern::OnMediaPlayGestureAccessUpdate(bool value)
2464 {
2465 if (delegate_) {
2466 delegate_->UpdateMediaPlayGestureAccess(value);
2467 }
2468 }
2469
OnFileAccessEnabledUpdate(bool value)2470 void WebPattern::OnFileAccessEnabledUpdate(bool value)
2471 {
2472 if (delegate_) {
2473 delegate_->UpdateAllowFileAccess(value);
2474 }
2475 }
2476
OnOnLineImageAccessEnabledUpdate(bool value)2477 void WebPattern::OnOnLineImageAccessEnabledUpdate(bool value)
2478 {
2479 if (delegate_) {
2480 delegate_->UpdateBlockNetworkImage(!value);
2481 }
2482 }
2483
OnDomStorageAccessEnabledUpdate(bool value)2484 void WebPattern::OnDomStorageAccessEnabledUpdate(bool value)
2485 {
2486 if (delegate_) {
2487 delegate_->UpdateDomStorageEnabled(value);
2488 }
2489 }
2490
OnImageAccessEnabledUpdate(bool value)2491 void WebPattern::OnImageAccessEnabledUpdate(bool value)
2492 {
2493 if (delegate_) {
2494 delegate_->UpdateLoadsImagesAutomatically(value);
2495 }
2496 }
2497
OnMixedModeUpdate(MixedModeContent value)2498 void WebPattern::OnMixedModeUpdate(MixedModeContent value)
2499 {
2500 if (delegate_) {
2501 delegate_->UpdateMixedContentMode(value);
2502 }
2503 }
2504
OnZoomAccessEnabledUpdate(bool value)2505 void WebPattern::OnZoomAccessEnabledUpdate(bool value)
2506 {
2507 if ((layoutMode_ == WebLayoutMode::FIT_CONTENT) || isEmbedModeEnabled_) {
2508 TAG_LOGI(AceLogTag::ACE_WEB, "When layoutMode is fit-content or EmbedMode is on, turn off zoom access.");
2509 value = false;
2510 }
2511 if (delegate_) {
2512 delegate_->UpdateSupportZoom(value);
2513 }
2514 }
2515
OnGeolocationAccessEnabledUpdate(bool value)2516 void WebPattern::OnGeolocationAccessEnabledUpdate(bool value)
2517 {
2518 if (delegate_) {
2519 delegate_->UpdateGeolocationEnabled(value);
2520 }
2521 }
2522
OnUserAgentUpdate(const std::string & value)2523 void WebPattern::OnUserAgentUpdate(const std::string& value)
2524 {
2525 if (delegate_) {
2526 delegate_->UpdateUserAgent(value);
2527 }
2528 }
2529
OnCacheModeUpdate(WebCacheMode value)2530 void WebPattern::OnCacheModeUpdate(WebCacheMode value)
2531 {
2532 if (delegate_) {
2533 delegate_->UpdateCacheMode(value);
2534 }
2535 }
2536
OnDarkModeUpdate(WebDarkMode mode)2537 void WebPattern::OnDarkModeUpdate(WebDarkMode mode)
2538 {
2539 if (delegate_) {
2540 delegate_->UpdateDarkMode(mode);
2541 }
2542 }
2543
OnOverScrollModeUpdate(int mode)2544 void WebPattern::OnOverScrollModeUpdate(int mode)
2545 {
2546 if (delegate_) {
2547 delegate_->UpdateOverScrollMode(mode);
2548 }
2549 }
2550
OnBlurOnKeyboardHideModeUpdate(int mode)2551 void WebPattern::OnBlurOnKeyboardHideModeUpdate(int mode)
2552 {
2553 if (delegate_) {
2554 delegate_->UpdateBlurOnKeyboardHideMode(mode);
2555 }
2556 }
2557
OnCopyOptionModeUpdate(int32_t mode)2558 void WebPattern::OnCopyOptionModeUpdate(int32_t mode)
2559 {
2560 if (delegate_) {
2561 delegate_->UpdateCopyOptionMode(mode);
2562 }
2563 }
2564
OnMetaViewportUpdate(bool value)2565 void WebPattern::OnMetaViewportUpdate(bool value)
2566 {
2567 if (delegate_) {
2568 delegate_->UpdateMetaViewport(value);
2569 }
2570 }
2571
OnForceDarkAccessUpdate(bool access)2572 void WebPattern::OnForceDarkAccessUpdate(bool access)
2573 {
2574 if (delegate_) {
2575 delegate_->UpdateForceDarkAccess(access);
2576 }
2577 }
2578
OnAudioResumeIntervalUpdate(int32_t resumeInterval)2579 void WebPattern::OnAudioResumeIntervalUpdate(int32_t resumeInterval)
2580 {
2581 if (delegate_) {
2582 delegate_->UpdateAudioResumeInterval(resumeInterval);
2583 }
2584 }
2585
OnAudioExclusiveUpdate(bool audioExclusive)2586 void WebPattern::OnAudioExclusiveUpdate(bool audioExclusive)
2587 {
2588 if (delegate_) {
2589 delegate_->UpdateAudioExclusive(audioExclusive);
2590 }
2591 }
2592
OnOverviewModeAccessEnabledUpdate(bool value)2593 void WebPattern::OnOverviewModeAccessEnabledUpdate(bool value)
2594 {
2595 if (delegate_) {
2596 delegate_->UpdateOverviewModeEnabled(value);
2597 }
2598 }
2599
OnFileFromUrlAccessEnabledUpdate(bool value)2600 void WebPattern::OnFileFromUrlAccessEnabledUpdate(bool value)
2601 {
2602 if (delegate_) {
2603 delegate_->UpdateFileFromUrlEnabled(value);
2604 }
2605 }
2606
OnDatabaseAccessEnabledUpdate(bool value)2607 void WebPattern::OnDatabaseAccessEnabledUpdate(bool value)
2608 {
2609 if (delegate_) {
2610 delegate_->UpdateDatabaseEnabled(value);
2611 }
2612 }
2613
OnTextZoomRatioUpdate(int32_t value)2614 void WebPattern::OnTextZoomRatioUpdate(int32_t value)
2615 {
2616 if (delegate_) {
2617 delegate_->UpdateTextZoomRatio(value);
2618 }
2619 }
2620
OnWebDebuggingAccessEnabledUpdate(bool value)2621 void WebPattern::OnWebDebuggingAccessEnabledUpdate(bool value)
2622 {
2623 if (delegate_) {
2624 delegate_->UpdateWebDebuggingAccess(value);
2625 }
2626 }
2627
OnPinchSmoothModeEnabledUpdate(bool value)2628 void WebPattern::OnPinchSmoothModeEnabledUpdate(bool value)
2629 {
2630 if (delegate_) {
2631 delegate_->UpdatePinchSmoothModeEnabled(value);
2632 }
2633 }
2634
OnBackgroundColorUpdate(int32_t value)2635 void WebPattern::OnBackgroundColorUpdate(int32_t value)
2636 {
2637 UpdateBackgroundColorRightNow(value);
2638 if (delegate_) {
2639 delegate_->UpdateBackgroundColor(value);
2640 }
2641 }
2642
OnInitialScaleUpdate(float value)2643 void WebPattern::OnInitialScaleUpdate(float value)
2644 {
2645 if ((layoutMode_ == WebLayoutMode::FIT_CONTENT) || isEmbedModeEnabled_) {
2646 TAG_LOGI(AceLogTag::ACE_WEB, "When layoutMode is fit-content or EmbedMode is on, Not allow to update scale.");
2647 return;
2648 }
2649 if (delegate_) {
2650 delegate_->UpdateInitialScale(value);
2651 }
2652 }
2653
OnMultiWindowAccessEnabledUpdate(bool value)2654 void WebPattern::OnMultiWindowAccessEnabledUpdate(bool value)
2655 {
2656 if (delegate_) {
2657 delegate_->UpdateMultiWindowAccess(value);
2658 }
2659 }
2660
OnAllowWindowOpenMethodUpdate(bool value)2661 void WebPattern::OnAllowWindowOpenMethodUpdate(bool value)
2662 {
2663 if (delegate_) {
2664 delegate_->UpdateAllowWindowOpenMethod(value);
2665 }
2666 }
2667
OnWebCursiveFontUpdate(const std::string & value)2668 void WebPattern::OnWebCursiveFontUpdate(const std::string& value)
2669 {
2670 if (delegate_) {
2671 delegate_->UpdateWebCursiveFont(value);
2672 }
2673 }
2674
OnWebFantasyFontUpdate(const std::string & value)2675 void WebPattern::OnWebFantasyFontUpdate(const std::string& value)
2676 {
2677 if (delegate_) {
2678 delegate_->UpdateWebFantasyFont(value);
2679 }
2680 }
2681
OnWebFixedFontUpdate(const std::string & value)2682 void WebPattern::OnWebFixedFontUpdate(const std::string& value)
2683 {
2684 if (delegate_) {
2685 delegate_->UpdateWebFixedFont(value);
2686 }
2687 }
2688
OnWebSansSerifFontUpdate(const std::string & value)2689 void WebPattern::OnWebSansSerifFontUpdate(const std::string& value)
2690 {
2691 if (delegate_) {
2692 delegate_->UpdateWebSansSerifFont(value);
2693 }
2694 }
2695
OnWebSerifFontUpdate(const std::string & value)2696 void WebPattern::OnWebSerifFontUpdate(const std::string& value)
2697 {
2698 if (delegate_) {
2699 delegate_->UpdateWebSerifFont(value);
2700 }
2701 }
2702
OnWebStandardFontUpdate(const std::string & value)2703 void WebPattern::OnWebStandardFontUpdate(const std::string& value)
2704 {
2705 if (delegate_) {
2706 delegate_->UpdateWebStandardFont(value);
2707 }
2708 }
2709
OnDefaultFixedFontSizeUpdate(int32_t value)2710 void WebPattern::OnDefaultFixedFontSizeUpdate(int32_t value)
2711 {
2712 if (delegate_) {
2713 delegate_->UpdateDefaultFixedFontSize(value);
2714 }
2715 }
2716
OnDefaultFontSizeUpdate(int32_t value)2717 void WebPattern::OnDefaultFontSizeUpdate(int32_t value)
2718 {
2719 if (delegate_) {
2720 delegate_->UpdateDefaultFontSize(value);
2721 }
2722 }
2723
OnMinFontSizeUpdate(int32_t value)2724 void WebPattern::OnMinFontSizeUpdate(int32_t value)
2725 {
2726 if (delegate_) {
2727 delegate_->UpdateMinFontSize(value);
2728 }
2729 }
2730
OnMinLogicalFontSizeUpdate(int32_t value)2731 void WebPattern::OnMinLogicalFontSizeUpdate(int32_t value)
2732 {
2733 if (delegate_) {
2734 delegate_->UpdateMinLogicalFontSize(value);
2735 }
2736 }
2737
OnBlockNetworkUpdate(bool value)2738 void WebPattern::OnBlockNetworkUpdate(bool value)
2739 {
2740 if (delegate_) {
2741 delegate_->UpdateBlockNetwork(value);
2742 }
2743 }
2744
OnHorizontalScrollBarAccessEnabledUpdate(bool value)2745 void WebPattern::OnHorizontalScrollBarAccessEnabledUpdate(bool value)
2746 {
2747 if (delegate_) {
2748 delegate_->UpdateHorizontalScrollBarAccess(value);
2749 }
2750 }
2751
OnVerticalScrollBarAccessEnabledUpdate(bool value)2752 void WebPattern::OnVerticalScrollBarAccessEnabledUpdate(bool value)
2753 {
2754 if (delegate_) {
2755 delegate_->UpdateVerticalScrollBarAccess(value);
2756 }
2757 }
2758
OnOverlayScrollbarEnabledUpdate(bool enable)2759 void WebPattern::OnOverlayScrollbarEnabledUpdate(bool enable)
2760 {
2761 if (delegate_) {
2762 delegate_->UpdateOverlayScrollbarEnabled(enable);
2763 }
2764 }
2765
OnNativeEmbedModeEnabledUpdate(bool value)2766 void WebPattern::OnNativeEmbedModeEnabledUpdate(bool value)
2767 {
2768 if (delegate_) {
2769 delegate_->UpdateNativeEmbedModeEnabled(value);
2770 }
2771 }
2772
OnNativeEmbedRuleTagUpdate(const std::string & tag)2773 void WebPattern::OnNativeEmbedRuleTagUpdate(const std::string& tag)
2774 {
2775 if (delegate_) {
2776 delegate_->UpdateNativeEmbedRuleTag(tag);
2777 }
2778 }
2779
OnNativeEmbedRuleTypeUpdate(const std::string & type)2780 void WebPattern::OnNativeEmbedRuleTypeUpdate(const std::string& type)
2781 {
2782 if (delegate_) {
2783 delegate_->UpdateNativeEmbedRuleType(type);
2784 }
2785 }
2786
OnTextAutosizingUpdate(bool isTextAutosizing)2787 void WebPattern::OnTextAutosizingUpdate(bool isTextAutosizing)
2788 {
2789 if (delegate_) {
2790 delegate_->UpdateTextAutosizing(isTextAutosizing);
2791 }
2792 }
2793
OnKeyboardAvoidModeUpdate(const WebKeyboardAvoidMode & mode)2794 void WebPattern::OnKeyboardAvoidModeUpdate(const WebKeyboardAvoidMode& mode)
2795 {
2796 keyBoardAvoidMode_ = mode;
2797 }
2798
OnEnabledHapticFeedbackUpdate(bool enable)2799 void WebPattern::OnEnabledHapticFeedbackUpdate(bool enable)
2800 {
2801 isEnabledHapticFeedback_ = enable;
2802 }
2803
IsRootNeedExportTexture()2804 bool WebPattern::IsRootNeedExportTexture()
2805 {
2806 auto host = GetHost();
2807 CHECK_NULL_RETURN(host, false);
2808 bool isNeedExportTexture = false;
2809 for (auto parent = host->GetParent(); parent != nullptr; parent = parent->GetParent()) {
2810 RefPtr<FrameNode> frameNode = AceType::DynamicCast<FrameNode>(parent);
2811 if (!frameNode) {
2812 continue;
2813 }
2814 isNeedExportTexture = frameNode->IsNeedExportTexture();
2815 if (isNeedExportTexture) {
2816 return isNeedExportTexture;
2817 }
2818 }
2819 return isNeedExportTexture;
2820 }
2821
OnAttachContext(PipelineContext * context)2822 void WebPattern::OnAttachContext(PipelineContext *context)
2823 {
2824 nodeAttach_ = true;
2825 auto pipelineContext = Claim(context);
2826 int32_t newId = pipelineContext->GetInstanceId();
2827 instanceId_ = newId;
2828 if (delegate_) {
2829 delegate_->OnAttachContext(pipelineContext);
2830 }
2831
2832 if (observer_) {
2833 observer_->OnAttachContext(pipelineContext);
2834 }
2835
2836 if (updateInstanceIdCallback_) {
2837 updateInstanceIdCallback_(newId);
2838 }
2839
2840 if (renderSurface_) {
2841 renderSurface_->SetInstanceId(newId);
2842 }
2843
2844 auto host = GetHost();
2845 CHECK_NULL_VOID(host);
2846 int32_t nodeId = host->GetId();
2847 auto dragDropManager = pipelineContext->GetDragDropManager();
2848 if (dragDropManager) {
2849 dragDropManager->AddDragFrameNode(host->GetId(), AceType::WeakClaim(AceType::RawPtr(host)));
2850 }
2851
2852 pipelineContext->AddWindowStateChangedCallback(nodeId);
2853 pipelineContext->AddWindowSizeChangeCallback(nodeId);
2854 pipelineContext->AddOnAreaChangeNode(nodeId);
2855 RegisterVisibleAreaChangeCallback(pipelineContext);
2856 needUpdateWeb_ = true;
2857 RegistVirtualKeyBoardListener(pipelineContext);
2858 InitConfigChangeCallback(pipelineContext);
2859 InitializeAccessibility();
2860 }
2861
OnDetachContext(PipelineContext * contextPtr)2862 void WebPattern::OnDetachContext(PipelineContext *contextPtr)
2863 {
2864 nodeAttach_ = false;
2865 auto context = AceType::Claim(contextPtr);
2866 CHECK_NULL_VOID(context);
2867
2868 auto host = GetHost();
2869 int32_t nodeId = host->GetId();
2870 UninitializeAccessibility();
2871 context->RemoveWindowStateChangedCallback(nodeId);
2872 context->RemoveWindowSizeChangeCallback(nodeId);
2873 context->RemoveOnAreaChangeNode(nodeId);
2874 context->RemoveVisibleAreaChangeNode(nodeId);
2875 context->RemoveVirtualKeyBoardCallback(nodeId);
2876 context->RemoveConfigChangedCallback(nodeId);
2877
2878 if (delegate_) {
2879 delegate_->OnDetachContext();
2880 }
2881
2882 if (observer_) {
2883 observer_->OnDetachContext();
2884 }
2885
2886 auto dragDropManager = context->GetDragDropManager();
2887 if (dragDropManager) {
2888 dragDropManager->RemoveDragFrameNode(nodeId);
2889 }
2890
2891 if (tooltipId_ != -1) {
2892 auto overlayManager = context->GetOverlayManager();
2893 if (overlayManager) {
2894 overlayManager->RemoveIndexerPopupById(tooltipId_);
2895 TAG_LOGI(AceLogTag::ACE_WEB,
2896 "OnDetachContext tooltipId_:%{public}d", tooltipId_);
2897 }
2898 tooltipId_ = -1;
2899 }
2900 }
2901
SetUpdateInstanceIdCallback(std::function<void (int32_t)> && callback)2902 void WebPattern::SetUpdateInstanceIdCallback(std::function<void(int32_t)>&& callback)
2903 {
2904 updateInstanceIdCallback_ = callback;
2905 }
2906
OnScrollBarColorUpdate(const std::string & value)2907 void WebPattern::OnScrollBarColorUpdate(const std::string& value)
2908 {
2909 if (delegate_) {
2910 delegate_->UpdateScrollBarColor(value);
2911 }
2912 }
2913
OnDefaultTextEncodingFormatUpdate(const std::string & value)2914 void WebPattern::OnDefaultTextEncodingFormatUpdate(const std::string& value)
2915 {
2916 if (delegate_) {
2917 delegate_->UpdateDefaultTextEncodingFormat(value);
2918 }
2919 }
2920
OnNativeVideoPlayerConfigUpdate(const std::tuple<bool,bool> & config)2921 void WebPattern::OnNativeVideoPlayerConfigUpdate(const std::tuple<bool, bool>& config)
2922 {
2923 if (delegate_) {
2924 delegate_->UpdateNativeVideoPlayerConfig(
2925 std::get<0>(config), std::get<1>(config));
2926 }
2927 }
2928
RegistVirtualKeyBoardListener(const RefPtr<PipelineContext> & pipelineContext)2929 void WebPattern::RegistVirtualKeyBoardListener(const RefPtr<PipelineContext> &pipelineContext)
2930 {
2931 if (!needUpdateWeb_) {
2932 return;
2933 }
2934 pipelineContext->SetVirtualKeyBoardCallback(GetHost()->GetId(),
2935 [weak = AceType::WeakClaim(this)](int32_t width, int32_t height, double keyboard) {
2936 auto webPattern = weak.Upgrade();
2937 CHECK_NULL_RETURN(webPattern, false);
2938 return webPattern->ProcessVirtualKeyBoard(width, height, keyboard);
2939 });
2940 needUpdateWeb_ = false;
2941 }
2942
InitEnhanceSurfaceFlag()2943 void WebPattern::InitEnhanceSurfaceFlag()
2944 {
2945 if (SystemProperties::GetExtSurfaceEnabled()) {
2946 isEnhanceSurface_ = true;
2947 } else {
2948 isEnhanceSurface_ = false;
2949 }
2950 }
2951
OnColorConfigurationUpdate()2952 void WebPattern::OnColorConfigurationUpdate()
2953 {
2954 auto host = GetHost();
2955 CHECK_NULL_VOID(host);
2956 if (magnifierController_) {
2957 magnifierController_->SetColorModeChange(true);
2958 host->MarkDirtyNode(PROPERTY_UPDATE_RENDER);
2959 }
2960 }
2961
OnModifyDone()2962 void WebPattern::OnModifyDone()
2963 {
2964 Pattern::OnModifyDone();
2965 // called in each update function.
2966 auto host = GetHost();
2967 CHECK_NULL_VOID(host);
2968 auto renderContext = host->GetRenderContext();
2969 CHECK_NULL_VOID(renderContext);
2970 renderContext->SetHandleChildBounds(true);
2971 if (!delegate_) {
2972 // first create case,
2973 delegate_ = AceType::MakeRefPtr<WebDelegate>(PipelineContext::GetCurrentContext(), nullptr, "",
2974 Container::CurrentId());
2975 instanceId_ = Container::CurrentId();
2976 CHECK_NULL_VOID(delegate_);
2977 observer_ = AceType::MakeRefPtr<WebDelegateObserver>(delegate_, PipelineContext::GetCurrentContext());
2978 CHECK_NULL_VOID(observer_);
2979 delegate_->SetObserver(observer_);
2980 delegate_->SetRenderMode(renderMode_);
2981 delegate_->SetFitContentMode(layoutMode_);
2982 InitEnhanceSurfaceFlag();
2983 delegate_->SetNGWebPattern(Claim(this));
2984 delegate_->SetEnhanceSurfaceFlag(isEnhanceSurface_);
2985 delegate_->SetPopup(isPopup_);
2986 delegate_->SetParentNWebId(parentNWebId_);
2987 delegate_->SetBackgroundColor(GetBackgroundColorValue(
2988 static_cast<int32_t>(renderContext->GetBackgroundColor().value_or(Color::WHITE).GetValue())));
2989 if (isEnhanceSurface_) {
2990 auto drawSize = Size(1, 1);
2991 delegate_->SetDrawSize(drawSize);
2992 delegate_->InitOHOSWeb(PipelineContext::GetCurrentContext());
2993 } else {
2994 auto drawSize = Size(1, 1);
2995 delegate_->SetDrawSize(drawSize);
2996 int32_t instanceId = Container::CurrentId();
2997 CHECK_NULL_VOID(renderSurface_);
2998 CHECK_NULL_VOID(renderContextForSurface_);
2999 renderSurface_->SetInstanceId(instanceId);
3000 renderSurface_->SetRenderContext(host->GetRenderContext());
3001 if (renderMode_ == RenderMode::SYNC_RENDER) {
3002 renderSurface_->SetIsTexture(true);
3003 renderSurface_->SetPatternType(PATTERN_TYPE_WEB);
3004 renderSurface_->SetSurfaceQueueSize(SYNC_SURFACE_QUEUE_SIZE);
3005 renderContextForSurface_->SetOpacity(0.0f);
3006 } else {
3007 renderSurface_->SetIsTexture(false);
3008 renderSurface_->SetSurfaceQueueSize(GetBufferSizeByDeviceType());
3009 renderSurface_->SetRenderContext(renderContextForSurface_);
3010 }
3011 renderContext->AddChild(renderContextForSurface_, 0);
3012 renderSurface_->InitSurface();
3013 renderSurface_->SetTransformHint(rotation_);
3014 TAG_LOGD(AceLogTag::ACE_WEB, "OnModify done, set rotation %{public}u", rotation_);
3015 renderSurface_->UpdateSurfaceConfig();
3016 delegate_->InitOHOSWeb(PipelineContext::GetCurrentContext(), renderSurface_);
3017 if (renderMode_ == RenderMode::ASYNC_RENDER) {
3018 std::string surfaceId = renderSurface_->GetUniqueId();
3019 delegate_->SetSurfaceId(surfaceId);
3020 TAG_LOGD(AceLogTag::ACE_WEB, "[getSurfaceId] set surfaceId is %{public}s", surfaceId.c_str());
3021 }
3022 }
3023
3024 UpdateJavaScriptOnDocumentStartByOrder();
3025 UpdateJavaScriptOnDocumentEndByOrder();
3026 UpdateJavaScriptOnDocumentStart();
3027 UpdateJavaScriptOnDocumentEnd();
3028 UpdateJavaScriptOnHeadReadyByOrder();
3029
3030 delegate_->UpdateBackgroundColor(GetBackgroundColorValue(
3031 static_cast<int32_t>(renderContext->GetBackgroundColor().value_or(Color::WHITE).GetValue())));
3032 delegate_->UpdateJavaScriptEnabled(GetJsEnabledValue(true));
3033 delegate_->UpdateBlockNetworkImage(!GetOnLineImageAccessEnabledValue(true));
3034 delegate_->UpdateLoadsImagesAutomatically(GetImageAccessEnabledValue(true));
3035 delegate_->UpdateMixedContentMode(GetMixedModeValue(MixedModeContent::MIXED_CONTENT_NEVER_ALLOW));
3036 isEmbedModeEnabled_ = GetNativeEmbedModeEnabledValue(false);
3037 if ((layoutMode_ == WebLayoutMode::FIT_CONTENT) || isEmbedModeEnabled_) {
3038 delegate_->UpdateSupportZoom(false);
3039 } else {
3040 delegate_->UpdateSupportZoom(GetZoomAccessEnabledValue(true));
3041 }
3042 delegate_->UpdateDomStorageEnabled(GetDomStorageAccessEnabledValue(false));
3043 delegate_->UpdateGeolocationEnabled(GetGeolocationAccessEnabledValue(true));
3044 delegate_->UpdateCacheMode(GetCacheModeValue(WebCacheMode::DEFAULT));
3045 if (webData_) {
3046 // Created a richtext component
3047 delegate_->SetRichtextIdentifier(webData_);
3048 delegate_->UpdateDarkMode(GetDarkModeValue(WebDarkMode::Auto));
3049 delegate_->UpdateForceDarkAccess(GetForceDarkAccessValue(true));
3050 delegate_->UpdateOverviewModeEnabled(GetOverviewModeAccessEnabledValue(false));
3051 } else {
3052 delegate_->UpdateDarkMode(GetDarkModeValue(WebDarkMode::Off));
3053 delegate_->UpdateForceDarkAccess(GetForceDarkAccessValue(false));
3054 delegate_->UpdateOverviewModeEnabled(GetOverviewModeAccessEnabledValue(true));
3055 }
3056 delegate_->UpdateAudioResumeInterval(GetAudioResumeIntervalValue(-1));
3057 delegate_->UpdateAudioExclusive(GetAudioExclusiveValue(true));
3058 delegate_->UpdateFileFromUrlEnabled(GetFileFromUrlAccessEnabledValue(false));
3059 delegate_->UpdateDatabaseEnabled(GetDatabaseAccessEnabledValue(false));
3060 delegate_->UpdateTextZoomRatio(GetTextZoomRatioValue(DEFAULT_TEXT_ZOOM_RATIO));
3061 delegate_->UpdateWebDebuggingAccess(GetWebDebuggingAccessEnabledValue(false));
3062 delegate_->UpdateMediaPlayGestureAccess(GetMediaPlayGestureAccessValue(true));
3063 delegate_->UpdatePinchSmoothModeEnabled(GetPinchSmoothModeEnabledValue(false));
3064 delegate_->UpdateMultiWindowAccess(GetMultiWindowAccessEnabledValue(false));
3065 delegate_->UpdateWebCursiveFont(GetWebCursiveFontValue(DEFAULT_CURSIVE_FONT_FAMILY));
3066 delegate_->UpdateWebFantasyFont(GetWebFantasyFontValue(DEFAULT_FANTASY_FONT_FAMILY));
3067 delegate_->UpdateWebFixedFont(GetWebFixedFontValue(DEFAULT_FIXED_fONT_FAMILY));
3068 delegate_->UpdateWebSansSerifFont(GetWebSansSerifFontValue(DEFAULT_SANS_SERIF_FONT_FAMILY));
3069 delegate_->UpdateWebSerifFont(GetWebSerifFontValue(DEFAULT_SERIF_FONT_FAMILY));
3070 delegate_->UpdateWebStandardFont(GetWebStandardFontValue(DEFAULT_STANDARD_FONT_FAMILY));
3071 delegate_->UpdateDefaultFixedFontSize(GetDefaultFixedFontSizeValue(DEFAULT_FIXED_FONT_SIZE));
3072 delegate_->UpdateDefaultFontSize(GetDefaultFontSizeValue(DEFAULT_FONT_SIZE));
3073 delegate_->UpdateDefaultTextEncodingFormat(GetDefaultTextEncodingFormatValue(DEFAULT_WEB_TEXT_ENCODING_FORMAT));
3074 delegate_->UpdateMinFontSize(GetMinFontSizeValue(DEFAULT_MINIMUM_FONT_SIZE));
3075 delegate_->UpdateMinLogicalFontSize(GetMinLogicalFontSizeValue(DEFAULT_MINIMUM_LOGICAL_FONT_SIZE));
3076 delegate_->UpdateHorizontalScrollBarAccess(GetHorizontalScrollBarAccessEnabledValue(true));
3077 delegate_->UpdateVerticalScrollBarAccess(GetVerticalScrollBarAccessEnabledValue(true));
3078 delegate_->UpdateScrollBarColor(GetScrollBarColorValue(DEFAULT_SCROLLBAR_COLOR));
3079 delegate_->UpdateOverlayScrollbarEnabled(GetOverlayScrollbarEnabledValue(false));
3080 bool isApiGteTwelve =
3081 AceApplicationInfo::GetInstance().GreatOrEqualTargetAPIVersion(PlatformVersion::VERSION_TWELVE);
3082 delegate_->UpdateOverScrollMode(GetOverScrollModeValue(OverScrollMode::NEVER));
3083 delegate_->UpdateBlurOnKeyboardHideMode(GetBlurOnKeyboardHideModeValue(BlurOnKeyboardHideMode::SILENT));
3084 delegate_->UpdateCopyOptionMode(GetCopyOptionModeValue(static_cast<int32_t>(CopyOptions::Distributed)));
3085 delegate_->UpdateAllowFileAccess(GetFileAccessEnabledValue(isApiGteTwelve ? false : true));
3086 delegate_->UpdateOptimizeParserBudgetEnabled(GetOptimizeParserBudgetEnabledValue(false));
3087 if (GetMetaViewport()) {
3088 delegate_->UpdateMetaViewport(GetMetaViewport().value());
3089 }
3090 delegate_->UpdateTextAutosizing(GetTextAutosizingValue(true));
3091 if (GetBlockNetwork()) {
3092 delegate_->UpdateBlockNetwork(GetBlockNetwork().value());
3093 }
3094 if (GetUserAgent()) {
3095 delegate_->UpdateUserAgent(GetUserAgent().value());
3096 }
3097 if (GetInitialScale()) {
3098 delegate_->UpdateInitialScale(GetInitialScale().value());
3099 }
3100 isAllowWindowOpenMethod_ = SystemProperties::GetAllowWindowOpenMethodEnabled();
3101 delegate_->UpdateAllowWindowOpenMethod(GetAllowWindowOpenMethodValue(isAllowWindowOpenMethod_));
3102 delegate_->UpdateNativeEmbedModeEnabled(GetNativeEmbedModeEnabledValue(false));
3103 delegate_->UpdateNativeEmbedRuleTag(GetNativeEmbedRuleTagValue(""));
3104 delegate_->UpdateNativeEmbedRuleType(GetNativeEmbedRuleTypeValue(""));
3105
3106 std::tuple<bool, bool> config = GetNativeVideoPlayerConfigValue({false, false});
3107 delegate_->UpdateNativeVideoPlayerConfig(std::get<0>(config), std::get<1>(config));
3108 }
3109
3110 if (!GetBackgroundColor()) {
3111 UpdateBackgroundColorRightNow(GetDefaultBackgroundColor().GetValue());
3112 }
3113
3114 // Initialize events such as keyboard, focus, etc.
3115 InitEvent();
3116 // Initialize web params.
3117 InitFeatureParam();
3118 InitializeAccessibility();
3119 // Initialize scrollupdate listener
3120 if (renderMode_ == RenderMode::SYNC_RENDER) {
3121 auto task = [weak = AceType::WeakClaim(this)]() {
3122 auto webPattern = weak.Upgrade();
3123 CHECK_NULL_VOID(webPattern);
3124 webPattern->InitSlideUpdateListener();
3125 };
3126 PostTaskToUI(std::move(task), "ArkUIWebInitSlideUpdateListener");
3127 }
3128
3129 auto embedEnabledTask = [weak = AceType::WeakClaim(this)]() {
3130 auto webPattern = weak.Upgrade();
3131 CHECK_NULL_VOID(webPattern);
3132 if (webPattern->IsRootNeedExportTexture() && webPattern->delegate_) {
3133 webPattern->delegate_->UpdateNativeEmbedModeEnabled(false);
3134 }
3135 };
3136 PostTaskToUI(std::move(embedEnabledTask), "ArkUIWebUpdateNativeEmbedModeEnabled");
3137
3138 auto pipelineContext = PipelineContext::GetCurrentContext();
3139 CHECK_NULL_VOID(pipelineContext);
3140 if (nodeAttach_) {
3141 pipelineContext->AddOnAreaChangeNode(host->GetId());
3142 }
3143 // offline mode
3144 if (host->GetNodeStatus() != NodeStatus::NORMAL_NODE) {
3145 InitInOfflineMode();
3146 }
3147
3148 auto pipeline = PipelineBase::GetCurrentContextSafely();
3149 if (pipeline) {
3150 densityCallbackId_ = pipeline->RegisterDensityChangedCallback([weak = WeakClaim(this)](double density) {
3151 auto webPattern = weak.Upgrade();
3152 CHECK_NULL_VOID(webPattern);
3153 webPattern->SetSurfaceDensity(density);
3154 });
3155 SetSurfaceDensity(pipeline->GetDensity());
3156 }
3157 }
3158
SetSurfaceDensity(double density)3159 void WebPattern::SetSurfaceDensity(double density)
3160 {
3161 if (delegate_) {
3162 delegate_->SetSurfaceDensity(density);
3163 }
3164 }
3165
InitInOfflineMode()3166 void WebPattern::InitInOfflineMode()
3167 {
3168 if (offlineWebInited_) {
3169 return;
3170 }
3171 TAG_LOGI(AceLogTag::ACE_WEB, "Web offline mode type, webId:%{public}d", GetWebId());
3172 delegate_->OnRenderToBackground();
3173 offlineWebInited_ = true;
3174 isActive_ = false;
3175 isVisible_ = false;
3176 auto host = GetHost();
3177 CHECK_NULL_VOID(host);
3178 int width = 0;
3179 int height = 0;
3180 auto layoutProperty = host->GetLayoutProperty();
3181 CHECK_NULL_VOID(layoutProperty);
3182 auto& calcLayout = layoutProperty->GetCalcLayoutConstraint();
3183 if (calcLayout) {
3184 width = calcLayout->selfIdealSize ?
3185 calcLayout->selfIdealSize->Width()->GetDimension().ConvertToPx() : 0;
3186 height = calcLayout->selfIdealSize ?
3187 calcLayout->selfIdealSize->Height()->GetDimension().ConvertToPx() : 0;
3188 }
3189 bool isUnSetSize = (width == 0) && (height == 0);
3190 auto defaultDisplay = OHOS::Rosen::DisplayManager::GetInstance().GetDefaultDisplay();
3191 if (isUnSetSize && defaultDisplay) {
3192 width = defaultDisplay->GetWidth();
3193 height = defaultDisplay->GetHeight();
3194 }
3195 Size drawSize = Size(width, height);
3196 Offset offset = Offset(0, 0);
3197 TAG_LOGD(AceLogTag::ACE_WEB, "InitInOfflineMode drawsize_ : %{public}s", drawSize_.ToString().c_str());
3198 delegate_->SetBoundsOrResize(drawSize, offset);
3199
3200 if (!isUrlLoaded_) {
3201 isUrlLoaded_ = true;
3202 if (webSrc_) {
3203 delegate_->LoadUrl();
3204 } else if (webData_) {
3205 delegate_->LoadDataWithRichText();
3206 }
3207 }
3208 delegate_->HideWebView();
3209 CloseContextSelectionMenu();
3210 }
3211
IsNeedResizeVisibleViewport()3212 bool WebPattern::IsNeedResizeVisibleViewport()
3213 {
3214 if (visibleViewportSize_.Width() < 0 || visibleViewportSize_.Height() < 0 ||
3215 isVirtualKeyBoardShow_ != VkState::VK_SHOW || NearZero(lastKeyboardHeight_)) {
3216 return false;
3217 }
3218 auto context = PipelineContext::GetCurrentContext();
3219 CHECK_NULL_RETURN(context, false);
3220 int32_t height = context->GetRootRect().Height();
3221 auto y = GetCoordinatePoint()->GetY();
3222 if (GreatOrEqual(height, lastKeyboardHeight_ + y)) {
3223 double newHeight = height - lastKeyboardHeight_ - y;
3224 if (GreatOrEqual(newHeight, drawSize_.Height()) ||
3225 NearEqual(newHeight, drawSize_.Height())) {
3226 visibleViewportSize_.SetWidth(-1.0);
3227 visibleViewportSize_.SetHeight(-1.0);
3228 } else {
3229 return false;
3230 }
3231 } else {
3232 visibleViewportSize_.SetWidth(-1.0);
3233 visibleViewportSize_.SetHeight(-1.0);
3234 }
3235 delegate_->ResizeVisibleViewport(visibleViewportSize_, false);
3236 return true;
3237 }
3238
ProcessVirtualKeyBoardHide(int32_t width,int32_t height,bool safeAreaEnabled)3239 bool WebPattern::ProcessVirtualKeyBoardHide(int32_t width, int32_t height, bool safeAreaEnabled)
3240 {
3241 isKeyboardInSafeArea_ = false;
3242 if (safeAreaEnabled) {
3243 isVirtualKeyBoardShow_ = VkState::VK_HIDE;
3244 return false;
3245 }
3246 if (isVirtualKeyBoardShow_ != VkState::VK_SHOW) {
3247 return false;
3248 }
3249 if (layoutMode_ == WebLayoutMode::FIT_CONTENT) {
3250 TAG_LOGI(AceLogTag::ACE_WEB, "ProcessVirtualKeyBoardHide layoutMode is FIT_CONTENT");
3251 isVirtualKeyBoardShow_ = VkState::VK_HIDE;
3252 return true;
3253 }
3254 drawSize_.SetSize(drawSizeCache_);
3255 visibleViewportSize_.SetWidth(-1.0);
3256 visibleViewportSize_.SetHeight(-1.0);
3257 UpdateWebLayoutSize(width, height, false);
3258 isVirtualKeyBoardShow_ = VkState::VK_HIDE;
3259 return true;
3260 }
3261
UpdateLayoutAfterKeyboard(int32_t width,int32_t height,double keyboard)3262 bool WebPattern::UpdateLayoutAfterKeyboard(int32_t width, int32_t height, double keyboard)
3263 {
3264 auto frameNode = GetHost();
3265 CHECK_NULL_RETURN(frameNode, false);
3266 frameNode->MarkDirtyNode(PROPERTY_UPDATE_MEASURE_SELF);
3267 auto context = PipelineContext::GetCurrentContext();
3268 CHECK_NULL_RETURN(context, false);
3269 auto taskExecutor = context->GetTaskExecutor();
3270 CHECK_NULL_RETURN(taskExecutor, false);
3271 lastKeyboardHeight_ = keyboard;
3272 taskExecutor->PostDelayedTask(
3273 [weak = WeakClaim(this), width, height]() {
3274 auto webPattern = weak.Upgrade();
3275 CHECK_NULL_VOID(webPattern);
3276 // In split-screen mode, the keyboard height is reported multiple times and is not the same.
3277 // Use the last height.
3278 webPattern->UpdateLayoutAfterKeyboardShow(width,
3279 height,
3280 webPattern->lastKeyboardHeight_,
3281 webPattern->GetDrawSize().Height());
3282 }, TaskExecutor::TaskType::UI, UPDATE_WEB_LAYOUT_DELAY_TIME, "ArkUIWebUpdateLayoutAfterKeyboardShow");
3283 return true;
3284 }
3285
ProcessVirtualKeyBoardShow(int32_t width,int32_t height,double keyboard,bool safeAreaEnabled)3286 bool WebPattern::ProcessVirtualKeyBoardShow(int32_t width, int32_t height, double keyboard, bool safeAreaEnabled)
3287 {
3288 if (IsDialogNested()) {
3289 TAG_LOGI(AceLogTag::ACE_WEB, "ProcessVirtualKeyBoardShow, dialog nested, web don't consume keyboard event.");
3290 isKeyboardInSafeArea_ = true;
3291 return false;
3292 }
3293 if (isVirtualKeyBoardShow_ != VkState::VK_SHOW) {
3294 drawSizeCache_.SetSize(drawSize_);
3295 }
3296 if (drawSizeCache_.Height() <= (height - keyboard - GetCoordinatePoint()->GetY())) {
3297 TAG_LOGI(AceLogTag::ACE_WEB, "ProcessVirtualKeyBoardShow not obstruct");
3298 isVirtualKeyBoardShow_ = VkState::VK_SHOW;
3299 lastKeyboardHeight_ = keyboard;
3300 return !safeAreaEnabled;
3301 }
3302 if (height - GetCoordinatePoint()->GetY() < keyboard) {
3303 TAG_LOGI(AceLogTag::ACE_WEB, "ProcessVirtualKeyBoardShow Complete occlusion");
3304 isVirtualKeyBoardShow_ = VkState::VK_SHOW;
3305 return true;
3306 }
3307 if (!delegate_->NeedSoftKeyboard()) {
3308 TAG_LOGI(AceLogTag::ACE_WEB, "ProcessVirtualKeyBoardShow not NeedSoftKeyboard");
3309 return false;
3310 }
3311 isVirtualKeyBoardShow_ = VkState::VK_SHOW;
3312 if (layoutMode_ == WebLayoutMode::FIT_CONTENT) {
3313 TAG_LOGI(AceLogTag::ACE_WEB, "ProcessVirtualKeyBoardShow layoutMode is FIT_CONTENT");
3314 lastKeyboardHeight_ = keyboard;
3315 return true;
3316 }
3317 if (safeAreaEnabled) {
3318 isKeyboardInSafeArea_ = true;
3319 lastKeyboardHeight_ = keyboard;
3320 return false;
3321 }
3322
3323 if (!UpdateLayoutAfterKeyboard(width, height, keyboard)) {
3324 return false;
3325 }
3326 return true;
3327 }
3328
ProcessVirtualKeyBoard(int32_t width,int32_t height,double keyboard)3329 bool WebPattern::ProcessVirtualKeyBoard(int32_t width, int32_t height, double keyboard)
3330 {
3331 CHECK_NULL_RETURN(delegate_, false);
3332 if (delegate_->ShouldVirtualKeyboardOverlay()) {
3333 if (!IsDialogNested()) {
3334 double webKeyboard = keyboard - (height - GetCoordinatePoint()->GetY() - drawSize_.Height());
3335 webKeyboard = (webKeyboard < 0) ? 0 : webKeyboard;
3336 TAG_LOGW(AceLogTag::ACE_WEB, "VirtualKeyboard Overlaycontent is true webKeyboard:%{public}f", webKeyboard);
3337 delegate_->SetVirtualKeyBoardArg(width, height, webKeyboard);
3338 } else {
3339 delegate_->SetVirtualKeyBoardArg(width, height, 0);
3340 }
3341 } else {
3342 delegate_->SetVirtualKeyBoardArg(width, height, keyboard);
3343 }
3344
3345 auto host = GetHost();
3346 CHECK_NULL_RETURN(host, false);
3347 auto pipelineContext = host->GetContextRefPtr();
3348 CHECK_NULL_RETURN(pipelineContext, false);
3349 auto safeAreaManager = pipelineContext->GetSafeAreaManager();
3350 CHECK_NULL_RETURN(safeAreaManager, false);
3351 bool keyboardSafeAreaEnabled = safeAreaManager->KeyboardSafeAreaEnabled();
3352 TAG_LOGI(AceLogTag::ACE_WEB,
3353 "ProcessVirtualKeyBoard width:%{public}d, height:%{public}d, keyboard:%{public}f, safeArea:%{public}d",
3354 width, height, keyboard, keyboardSafeAreaEnabled);
3355
3356 if (!isFocus_ || !isVisible_) {
3357 UpdateOnFocusTextField(false);
3358 ProcessVirtualKeyBoardHide(width, height, keyboardSafeAreaEnabled);
3359 return false;
3360 }
3361 UpdateOnFocusTextField(!NearZero(keyboard));
3362 if (NearZero(keyboard)) {
3363 return ProcessVirtualKeyBoardHide(width, height, keyboardSafeAreaEnabled);
3364 }
3365 return ProcessVirtualKeyBoardShow(width, height, keyboard, keyboardSafeAreaEnabled);
3366 }
3367
UpdateWebLayoutSize(int32_t width,int32_t height,bool isKeyboard,bool isUpdate)3368 void WebPattern::UpdateWebLayoutSize(int32_t width, int32_t height, bool isKeyboard, bool isUpdate)
3369 {
3370 CHECK_NULL_VOID(delegate_);
3371 if (delegate_->ShouldVirtualKeyboardOverlay()) {
3372 TAG_LOGW(AceLogTag::ACE_WEB, "VirtualKeyboard Overlaycontent is true and does not require resizing");
3373 return;
3374 }
3375 auto frameNode = GetHost();
3376 CHECK_NULL_VOID(frameNode);
3377 auto rect = frameNode->GetRenderContext()->GetPaintRectWithoutTransform();
3378 auto offset = Offset(GetCoordinatePoint()->GetX(), GetCoordinatePoint()->GetY());
3379
3380 // Scroll focused node into view when keyboard show.
3381 TAG_LOGD(AceLogTag::ACE_WEB, "UpdateWebLayoutSize drawsize_ : %{public}s", drawSize_.ToString().c_str());
3382 delegate_->SetBoundsOrResize(drawSize_, offset, isKeyboard);
3383 delegate_->ResizeVisibleViewport(visibleViewportSize_, isKeyboard);
3384
3385 if (isUpdate) {
3386 ACE_SCOPED_TRACE("WebPattern::UpdateWebLayoutSize rect: %s", rect.ToString().c_str());
3387 if (renderMode_ == RenderMode::SYNC_RENDER) {
3388 CHECK_NULL_VOID(renderSurface_);
3389 renderSurface_->SetIsNeedSyncGeometryProperties(true);
3390 renderSurface_->SetKeyBoardAvoidRect(rect);
3391 frameNode->MarkDirtyNode(PROPERTY_UPDATE_MEASURE_SELF | PROPERTY_UPDATE_RENDER);
3392 } else {
3393 rect.SetSize(SizeF(drawSize_.Width(), drawSize_.Height()));
3394 frameNode->GetRenderContext()->SyncGeometryProperties(rect);
3395 frameNode->MarkDirtyNode(PROPERTY_UPDATE_MEASURE_SELF);
3396 }
3397 }
3398 }
3399
HandleTouchDown(const TouchEventInfo & info,bool fromOverlay)3400 void WebPattern::HandleTouchDown(const TouchEventInfo& info, bool fromOverlay)
3401 {
3402 InitTouchEventListener();
3403 isTouchUpEvent_ = false;
3404 CHECK_NULL_VOID(delegate_);
3405 Offset touchOffset = Offset(0, 0);
3406 std::list<TouchInfo> touchInfos;
3407 if (!ParseTouchInfo(info, touchInfos)) {
3408 return;
3409 }
3410 for (auto& touchPoint : touchInfos) {
3411 if (fromOverlay) {
3412 touchPoint.x -= webOffset_.GetX();
3413 touchPoint.y -= webOffset_.GetY();
3414 TAG_LOGI(AceLogTag::ACE_WEB,
3415 "SelectOverlay touch down add id:%{public}d.", touchPoint.id);
3416 touchOverlayInfo_.push_back(touchPoint);
3417 }
3418 touchPointX = touchPoint.x;
3419 touchPointY = touchPoint.y;
3420 delegate_->HandleTouchDown(touchPoint.id, touchPoint.x, touchPoint.y, fromOverlay);
3421 if (overlayCreating_) {
3422 imageAnalyzerManager_->UpdateOverlayTouchInfo(touchPoint.x, touchPoint.y, TouchType::DOWN);
3423 }
3424 }
3425 if (!touchInfos.empty() && !GetNativeEmbedModeEnabledValue(false)) {
3426 WebRequestFocus();
3427 }
3428 }
3429
HandleTouchUp(const TouchEventInfo & info,bool fromOverlay)3430 void WebPattern::HandleTouchUp(const TouchEventInfo& info, bool fromOverlay)
3431 {
3432 UninitTouchEventListener();
3433 isTouchUpEvent_ = true;
3434 CHECK_NULL_VOID(delegate_);
3435 if (!isReceivedArkDrag_) {
3436 ResetDragAction();
3437 }
3438 HideMagnifier();
3439 std::list<TouchInfo> touchInfos;
3440 if (!ParseTouchInfo(info, touchInfos)) {
3441 return;
3442 }
3443 for (auto& touchPoint : touchInfos) {
3444 if (fromOverlay) {
3445 touchPoint.x -= webOffset_.GetX();
3446 touchPoint.y -= webOffset_.GetY();
3447 DelTouchOverlayInfoByTouchId(touchPoint.id);
3448 }
3449 if (!overlayCreating_) {
3450 delegate_->HandleTouchUp(touchPoint.id, touchPoint.x, touchPoint.y, fromOverlay);
3451 } else {
3452 if (imageAnalyzerManager_) {
3453 imageAnalyzerManager_->UpdateOverlayTouchInfo(touchPoint.x, touchPoint.y, TouchType::UP);
3454 overlayCreating_ = false;
3455 delegate_->HandleTouchCancel();
3456 }
3457 }
3458 }
3459 }
3460
OnMagnifierHandleMove(const RectF & handleRect,bool isFirst)3461 void WebPattern::OnMagnifierHandleMove(const RectF& handleRect, bool isFirst)
3462 {
3463 auto localX = handleRect.GetX() - webOffset_.GetX() + handleRect.Width() / HALF;
3464 auto localY = handleRect.GetY() - webOffset_.GetY() + handleRect.Height() / HALF;
3465 ShowMagnifier(localX, localY);
3466 }
3467
HandleTouchMove(const TouchEventInfo & info,bool fromOverlay)3468 void WebPattern::HandleTouchMove(const TouchEventInfo& info, bool fromOverlay)
3469 {
3470 if (isDragging_) {
3471 return;
3472 }
3473 auto pipeline = PipelineContext::GetCurrentContext();
3474 CHECK_NULL_VOID(pipeline);
3475 auto manager = pipeline->GetDragDropManager();
3476 CHECK_NULL_VOID(manager);
3477 if (manager->IsDragged()) {
3478 return;
3479 }
3480 CHECK_NULL_VOID(delegate_);
3481 std::list<TouchInfo> touchInfos;
3482
3483 touchEventInfoList_.emplace_back(info);
3484 for (const auto& touchEventInfo : touchEventInfoList_) {
3485 ParseTouchInfo(touchEventInfo, touchInfos);
3486 }
3487
3488 if (touchInfos.empty()) {
3489 return;
3490 }
3491 if (!info.GetTouchEventsEnd()) {
3492 return;
3493 }
3494 touchEventInfoList_.clear();
3495
3496 touchInfos.sort([](const TouchInfo &point1, const TouchInfo &point2) {
3497 return point1.id < point2.id;
3498 });
3499
3500 std::vector<std::shared_ptr<OHOS::NWeb::NWebTouchPointInfo>> touch_point_infos;
3501 for (auto& touchPoint : touchInfos) {
3502 if (fromOverlay) {
3503 touchPoint.x -= webOffset_.GetX();
3504 touchPoint.y -= webOffset_.GetY();
3505 }
3506 touchPointX = touchPoint.x;
3507 touchPointY = touchPoint.y;
3508 if (magnifierController_ && magnifierController_->GetMagnifierNodeExist()) {
3509 ShowMagnifier(touchPoint.x, touchPoint.y);
3510 }
3511 std::shared_ptr<OHOS::NWeb::NWebTouchPointInfo> touch_point_info =
3512 std::make_shared<NWebTouchPointInfoImpl>(touchPoint.id, touchPoint.x, touchPoint.y);
3513 touch_point_infos.emplace_back(touch_point_info);
3514 if (overlayCreating_) {
3515 imageAnalyzerManager_->UpdateOverlayTouchInfo(touchPoint.x, touchPoint.y, TouchType::MOVE);
3516 }
3517 }
3518
3519 if (!overlayCreating_) {
3520 delegate_->HandleTouchMove(touch_point_infos, fromOverlay);
3521 }
3522 }
3523
HandleTouchCancel(const TouchEventInfo & info)3524 void WebPattern::HandleTouchCancel(const TouchEventInfo& info)
3525 {
3526 UninitTouchEventListener();
3527 if (IsRootNeedExportTexture()) {
3528 HandleTouchUp(info, false);
3529 }
3530 CHECK_NULL_VOID(delegate_);
3531 delegate_->HandleTouchCancel();
3532 if (overlayCreating_) {
3533 imageAnalyzerManager_->UpdateOverlayTouchInfo(0, 0, TouchType::CANCEL);
3534 overlayCreating_ = false;
3535 }
3536 HideMagnifier();
3537 }
3538
ParseTouchInfo(const TouchEventInfo & info,std::list<TouchInfo> & touchInfos)3539 bool WebPattern::ParseTouchInfo(const TouchEventInfo& info, std::list<TouchInfo>& touchInfos)
3540 {
3541 auto context = PipelineContext::GetCurrentContext();
3542 CHECK_NULL_RETURN(context, false);
3543 auto viewScale = context->GetViewScale();
3544
3545 if (info.GetChangedTouches().empty()) {
3546 return false;
3547 }
3548 for (const auto& point : info.GetChangedTouches()) {
3549 TouchInfo touchInfo;
3550 touchInfo.id = point.GetFingerId();
3551 const Offset& location = point.GetLocalLocation();
3552 touchInfo.x = static_cast<float>(location.GetX() * viewScale);
3553 touchInfo.y = static_cast<float>(location.GetY() * viewScale);
3554 touchInfos.emplace_back(touchInfo);
3555 }
3556 return true;
3557 }
3558
RequestFullScreen()3559 void WebPattern::RequestFullScreen()
3560 {
3561 isFullScreen_ = true;
3562 }
3563
ExitFullScreen()3564 void WebPattern::ExitFullScreen()
3565 {
3566 isFullScreen_ = false;
3567 }
3568
GetCoordinatePoint()3569 std::optional<OffsetF> WebPattern::GetCoordinatePoint()
3570 {
3571 auto frameNode = GetHost();
3572 CHECK_NULL_RETURN(frameNode, std::nullopt);
3573 return frameNode->GetTransformRelativeOffset();
3574 }
3575
DelTouchOverlayInfoByTouchId(int32_t touchId)3576 void WebPattern::DelTouchOverlayInfoByTouchId(int32_t touchId)
3577 {
3578 std::list<TouchInfo>::iterator iter;
3579 for (iter = touchOverlayInfo_.begin(); iter != touchOverlayInfo_.end();) {
3580 if (iter->id == touchId) {
3581 TAG_LOGI(AceLogTag::ACE_WEB,
3582 "SelectOverlay del touch overlay info by id:%{public}d", iter->id);
3583 iter = touchOverlayInfo_.erase(iter);
3584 } else {
3585 ++iter;
3586 }
3587 }
3588 }
3589
CloseSelectOverlay()3590 void WebPattern::CloseSelectOverlay()
3591 {
3592 auto pipeline = PipelineContext::GetCurrentContext();
3593 CHECK_NULL_VOID(pipeline);
3594 if (webSelectOverlay_ && webSelectOverlay_->IsShowHandle()) {
3595 webSelectOverlay_->CloseOverlay(false, CloseReason::CLOSE_REASON_CLICK_OUTSIDE);
3596 for (auto& touchOverlayInfo : touchOverlayInfo_) {
3597 TAG_LOGI(AceLogTag::ACE_WEB, "SelectOverlay send touch up id:%{public}d", touchOverlayInfo.id);
3598 delegate_->HandleTouchUp(touchOverlayInfo.id, touchOverlayInfo.x, touchOverlayInfo.y, true);
3599 HideMagnifier();
3600 }
3601 touchOverlayInfo_.clear();
3602 }
3603 }
3604
ComputeMouseClippedSelectionBounds(int32_t x,int32_t y,int32_t w,int32_t h)3605 RectF WebPattern::ComputeMouseClippedSelectionBounds(int32_t x, int32_t y, int32_t w, int32_t h)
3606 {
3607 auto offset = GetCoordinatePoint().value_or(OffsetF());
3608 float selectX = offset.GetX() + x;
3609 float selectY = offset.GetY();
3610 float selectWidth = w;
3611 float selectHeight = h;
3612 if (LessOrEqual(GetHostFrameSize().value_or(SizeF()).Height(), y)) {
3613 selectY += GetHostFrameSize().value_or(SizeF()).Height();
3614 } else if (y + h <= 0) {
3615 selectY -= h;
3616 } else {
3617 selectY += y;
3618 }
3619 return RectF(selectX, selectY, selectWidth, selectHeight);
3620 }
3621
UpdateClippedSelectionBounds(int32_t x,int32_t y,int32_t w,int32_t h)3622 void WebPattern::UpdateClippedSelectionBounds(int32_t x, int32_t y, int32_t w, int32_t h)
3623 {
3624 selectArea_ = ComputeMouseClippedSelectionBounds(x, y, w, h);
3625 if (webSelectOverlay_) {
3626 webSelectOverlay_->UpdateClippedSelectionBounds(x, y, w, h);
3627 }
3628 }
3629
SelectCancel() const3630 void WebPattern::SelectCancel() const
3631 {
3632 if (webSelectOverlay_) {
3633 webSelectOverlay_->SelectCancel();
3634 }
3635 }
3636
IsSelectInfoValid()3637 bool WebPattern::IsSelectInfoValid()
3638 {
3639 auto info = GetSelectInfo();
3640 return !info.empty() && info != STRING_LF;
3641 }
3642
GetViewPort() const3643 std::optional<RectF> WebPattern::GetViewPort() const
3644 {
3645 CHECK_NULL_RETURN(GetHost(), std::nullopt);
3646 auto parentNode = GetHost()->GetAncestorNodeOfFrame(true);
3647 while (parentNode) {
3648 auto scrollablePattern = AceType::DynamicCast<NestableScrollContainer>(parentNode->GetPattern());
3649 auto geometryNode = parentNode->GetGeometryNode();
3650 if (scrollablePattern && geometryNode) {
3651 auto offsetRelativeToWindow = parentNode->GetOffsetRelativeToWindow();
3652 return RectF(offsetRelativeToWindow, geometryNode->GetFrameRect().GetSize());
3653 }
3654 parentNode = parentNode->GetAncestorNodeOfFrame(true);
3655 }
3656 return std::nullopt;
3657 }
3658
GetSelectInfo() const3659 std::string WebPattern::GetSelectInfo() const
3660 {
3661 CHECK_NULL_RETURN(delegate_, std::string());
3662 return delegate_->GetSelectInfo();
3663 }
3664
OnSelectionMenuOptionsUpdate(const WebMenuOptionsParam & webMenuOption)3665 void WebPattern::OnSelectionMenuOptionsUpdate(const WebMenuOptionsParam& webMenuOption)
3666 {
3667 menuOptionParam_ = std::move(webMenuOption.menuOption);
3668 for (auto& menuOption : menuOptionParam_) {
3669 std::function<void(const std::string&)> action = std::move(menuOption.action);
3670 menuOption.action = [weak = AceType::WeakClaim(this), action] (
3671 const std::string selectInfo) {
3672 auto webPattern = weak.Upgrade();
3673 CHECK_NULL_VOID(webPattern);
3674 webPattern->SelectCancel();
3675 std::string selectStr = webPattern->GetSelectInfo();
3676 if (action) {
3677 action(selectStr);
3678 }
3679 };
3680 }
3681 }
3682
UpdateEditMenuOptions(const NG::OnCreateMenuCallback && onCreateMenuCallback,const NG::OnMenuItemClickCallback && onMenuItemClick)3683 void WebPattern::UpdateEditMenuOptions(
3684 const NG::OnCreateMenuCallback&& onCreateMenuCallback,
3685 const NG::OnMenuItemClickCallback&& onMenuItemClick)
3686 {
3687 onCreateMenuCallback_ = std::move(onCreateMenuCallback);
3688 onMenuItemClick_ = [weak = AceType::WeakClaim(this), action = std::move(onMenuItemClick)] (
3689 const OHOS::Ace::NG::MenuItemParam& menuItem) -> bool {
3690 auto webPattern = weak.Upgrade();
3691 bool result = false;
3692 if (action) {
3693 result = action(menuItem);
3694 }
3695 CHECK_NULL_RETURN(webPattern, result);
3696 if (!result && webPattern->IsQuickMenuShow()) {
3697 webPattern->webSelectOverlay_->HideMenu(true);
3698 }
3699 return result;
3700 };
3701 }
3702
HideHandleAndQuickMenuIfNecessary(bool hide,bool isScroll)3703 void WebPattern::HideHandleAndQuickMenuIfNecessary(bool hide, bool isScroll)
3704 {
3705 if (webSelectOverlay_) {
3706 webSelectOverlay_->HideHandleAndQuickMenuIfNecessary(hide, isScroll);
3707 }
3708 }
3709
ChangeVisibilityOfQuickMenu()3710 void WebPattern::ChangeVisibilityOfQuickMenu()
3711 {
3712 CHECK_NULL_VOID(webSelectOverlay_);
3713 webSelectOverlay_->ChangeVisibilityOfQuickMenu();
3714 }
3715
IsQuickMenuShow()3716 bool WebPattern::IsQuickMenuShow()
3717 {
3718 CHECK_NULL_RETURN(webSelectOverlay_, false);
3719 return webSelectOverlay_->IsShowMenu();
3720 }
3721
RunQuickMenu(std::shared_ptr<OHOS::NWeb::NWebQuickMenuParams> params,std::shared_ptr<OHOS::NWeb::NWebQuickMenuCallback> callback)3722 bool WebPattern::RunQuickMenu(std::shared_ptr<OHOS::NWeb::NWebQuickMenuParams> params,
3723 std::shared_ptr<OHOS::NWeb::NWebQuickMenuCallback> callback)
3724 {
3725 if (!webSelectOverlay_) {
3726 webSelectOverlay_ = AceType::MakeRefPtr<WebSelectOverlay>(WeakClaim(this));
3727 }
3728 if (webSelectOverlay_->RunQuickMenu(params, callback)) {
3729 DestroyAnalyzerOverlay();
3730 return true;
3731 }
3732 return false;
3733 }
3734
ShowMagnifier(int centerOffsetX,int centerOffsetY)3735 void WebPattern::ShowMagnifier(int centerOffsetX, int centerOffsetY)
3736 {
3737 if (magnifierController_) {
3738 OffsetF localOffset = OffsetF(centerOffsetX, centerOffsetY);
3739 magnifierController_->SetLocalOffset(localOffset);
3740 }
3741 }
3742
HideMagnifier()3743 void WebPattern::HideMagnifier()
3744 {
3745 TAG_LOGI(AceLogTag::ACE_WEB, "HideMagnifier");
3746 if (magnifierController_) {
3747 magnifierController_->RemoveMagnifierFrameNode();
3748 }
3749 }
3750
GetTextPaintOffset() const3751 OffsetF WebPattern::GetTextPaintOffset() const
3752 {
3753 auto frameNode = GetHost();
3754 CHECK_NULL_RETURN(frameNode, OffsetF());
3755 return frameNode->GetTransformRelativeOffset();
3756 }
3757
OnQuickMenuDismissed()3758 void WebPattern::OnQuickMenuDismissed()
3759 {
3760 CloseSelectOverlay();
3761 }
3762
DumpViewDataPageNode(RefPtr<ViewDataWrap> viewDataWrap,bool needsRecordData)3763 void WebPattern::DumpViewDataPageNode(RefPtr<ViewDataWrap> viewDataWrap, bool needsRecordData)
3764 {
3765 TAG_LOGI(AceLogTag::ACE_WEB, "called");
3766 CHECK_NULL_VOID(viewDataWrap);
3767 for (const auto& nodeInfo : pageNodeInfo_) {
3768 if (nodeInfo) {
3769 viewDataWrap->AddPageNodeInfoWrap(nodeInfo);
3770 }
3771 }
3772 viewDataWrap->SetPageUrl(viewDataCommon_.pageUrl);
3773 viewDataWrap->SetUserSelected(viewDataCommon_.isUserSelected);
3774 viewDataWrap->SetOtherAccount(viewDataCommon_.isOtherAccount);
3775 }
3776
NotifyFillRequestSuccess(RefPtr<ViewDataWrap> viewDataWrap,RefPtr<PageNodeInfoWrap> nodeWrap,AceAutoFillType autoFillType)3777 void WebPattern::NotifyFillRequestSuccess(RefPtr<ViewDataWrap> viewDataWrap,
3778 RefPtr<PageNodeInfoWrap> nodeWrap, AceAutoFillType autoFillType)
3779 {
3780 TAG_LOGI(AceLogTag::ACE_WEB, "called");
3781 CHECK_NULL_VOID(viewDataWrap);
3782 auto nodeInfoWraps = viewDataWrap->GetPageNodeInfoWraps();
3783 auto jsonNode = JsonUtil::Create(true);
3784 AceAutoFillType focusType = AceAutoFillType::ACE_UNSPECIFIED;
3785 for (const auto& nodeInfoWrap : nodeInfoWraps) {
3786 if (nodeInfoWrap == nullptr) {
3787 continue;
3788 }
3789 auto type = nodeInfoWrap->GetAutoFillType();
3790 // white list check
3791 if (ACE_AUTOFILL_TYPE_TO_NWEB.count(type) != 0) {
3792 std::string key = ACE_AUTOFILL_TYPE_TO_NWEB.at(type);
3793 if (nodeInfoWrap->GetMetadata() != IS_HINT_TYPE) {
3794 jsonNode->Put(key.c_str(), nodeInfoWrap->GetValue().c_str());
3795 } else {
3796 auto json = JsonUtil::Create(true);
3797 json->Put(OHOS::NWeb::NWEB_VIEW_DATA_KEY_PLACEHOLDER.c_str(), nodeInfoWrap->GetId());
3798 json->Put(OHOS::NWeb::NWEB_VIEW_DATA_KEY_VALUE.c_str(), nodeInfoWrap->GetValue().c_str());
3799 jsonNode->Put(key.c_str(), std::move(json));
3800 }
3801 }
3802 if (nodeInfoWrap->GetIsFocus()) {
3803 focusType = type;
3804 }
3805 }
3806 auto pageUrl = viewDataWrap->GetPageUrl();
3807 jsonNode->Put(AUTO_FILL_VIEW_DATA_PAGE_URL.c_str(), pageUrl.c_str());
3808 auto otherAccount = viewDataWrap->GetOtherAccount();
3809 jsonNode->Put(AUTO_FILL_VIEW_DATA_OTHER_ACCOUNT.c_str(), otherAccount);
3810 delegate_->NotifyAutoFillViewData(jsonNode->ToString());
3811
3812 // shift focus after autofill
3813 if (focusType != AceAutoFillType::ACE_UNSPECIFIED && !isPasswordFill_) {
3814 for (const auto& nodeInfo : pageNodeInfo_) {
3815 if (nodeInfo && nodeInfo->GetAutoFillType() == focusType) {
3816 TouchEventInfo info("autofill");
3817 TouchLocationInfo location("autofill", 0);
3818 auto rectF = nodeInfo->GetPageNodeRect();
3819 location.SetLocalLocation(Offset(rectF.GetX() + (rectF.Width() / POPUP_CALCULATE_RATIO),
3820 rectF.GetY() + (rectF.Height() / POPUP_CALCULATE_RATIO)));
3821 info.AddChangedTouchLocationInfo(std::move(location));
3822 HandleTouchDown(info, false);
3823 HandleTouchUp(info, false);
3824 break;
3825 }
3826 }
3827 }
3828 }
3829
NotifyFillRequestFailed(int32_t errCode,const std::string & fillContent,bool isPopup)3830 void WebPattern::NotifyFillRequestFailed(int32_t errCode, const std::string& fillContent, bool isPopup)
3831 {
3832 TAG_LOGI(AceLogTag::ACE_WEB, "called, errCode:%{public}d", errCode);
3833 if (isPasswordFill_) {
3834 delegate_->AutofillCancel(fillContent);
3835 }
3836 }
3837
ParseViewDataNumber(const std::string & key,int32_t value,RefPtr<PageNodeInfoWrap> node,RectT<float> & rect,float viewScale)3838 void WebPattern::ParseViewDataNumber(const std::string& key, int32_t value,
3839 RefPtr<PageNodeInfoWrap> node, RectT<float>& rect, float viewScale)
3840 {
3841 CHECK_NULL_VOID(viewScale > FLT_EPSILON);
3842 CHECK_NULL_VOID(node);
3843 if (key == OHOS::NWeb::NWEB_VIEW_DATA_KEY_FOCUS) {
3844 node->SetIsFocus(static_cast<bool>(value));
3845 } else if (key == OHOS::NWeb::NWEB_VIEW_DATA_KEY_RECT_X) {
3846 rect.SetLeft(value / viewScale);
3847 } else if (key == OHOS::NWeb::NWEB_VIEW_DATA_KEY_RECT_Y) {
3848 rect.SetTop(value / viewScale);
3849 } else if (key == OHOS::NWeb::NWEB_VIEW_DATA_KEY_RECT_W) {
3850 rect.SetWidth(value / viewScale);
3851 } else if (key == OHOS::NWeb::NWEB_VIEW_DATA_KEY_RECT_H) {
3852 rect.SetHeight(value / viewScale);
3853 }
3854 }
3855
ParseViewDataString(const std::string & key,const std::string & value,RefPtr<PageNodeInfoWrap> node)3856 void ParseViewDataString(const std::string& key,
3857 const std::string& value, RefPtr<PageNodeInfoWrap> node)
3858 {
3859 CHECK_NULL_VOID(node);
3860 if (key == OHOS::NWeb::NWEB_VIEW_DATA_KEY_VALUE) {
3861 node->SetValue(value);
3862 } else if (key == OHOS::NWeb::NWEB_VIEW_DATA_KEY_PLACEHOLDER) {
3863 node->SetPlaceholder(value);
3864 }
3865 }
3866
GetHintTypeAndMetadata(const std::string & attribute,RefPtr<PageNodeInfoWrap> node)3867 HintToTypeWrap WebPattern::GetHintTypeAndMetadata(const std::string& attribute, RefPtr<PageNodeInfoWrap> node)
3868 {
3869 HintToTypeWrap hintToTypeWrap;
3870 auto placeholder = node->GetPlaceholder();
3871 if (NWEB_AUTOFILL_TYPE_TO_ACE.count(attribute) != 0) {
3872 AceAutoFillType type = NWEB_AUTOFILL_TYPE_TO_ACE.at(attribute);
3873 if (node->GetIsFocus()) {
3874 if (type == AceAutoFillType::ACE_USER_NAME || type == AceAutoFillType::ACE_PASSWORD ||
3875 type == AceAutoFillType::ACE_NEW_PASSWORD) {
3876 TAG_LOGI(AceLogTag::ACE_WEB, "The form is login fill form");
3877 isPasswordFill_ = true;
3878 }
3879 }
3880 hintToTypeWrap.autoFillType = type;
3881 } else if (!placeholder.empty()) {
3882 // try hint2Type
3883 auto host = GetHost();
3884 CHECK_NULL_RETURN(host, hintToTypeWrap);
3885 auto container = Container::Current();
3886 if (container == nullptr) {
3887 container = Container::GetActive();
3888 }
3889 CHECK_NULL_RETURN(container, hintToTypeWrap);
3890 hintToTypeWrap = container->PlaceHolderToType(placeholder);
3891 }
3892 return hintToTypeWrap;
3893 }
3894
ParseNWebViewDataNode(std::unique_ptr<JsonValue> child,std::vector<RefPtr<PageNodeInfoWrap>> & nodeInfos,int32_t nodeId)3895 void WebPattern::ParseNWebViewDataNode(std::unique_ptr<JsonValue> child,
3896 std::vector<RefPtr<PageNodeInfoWrap>>& nodeInfos, int32_t nodeId)
3897 {
3898 auto host = GetHost();
3899 CHECK_NULL_VOID(host);
3900 auto pipelineContext = host->GetContextRefPtr();
3901 CHECK_NULL_VOID(pipelineContext);
3902 float viewScale = pipelineContext->GetViewScale();
3903 CHECK_NULL_VOID(viewScale > FLT_EPSILON);
3904
3905 RefPtr<PageNodeInfoWrap> node = PageNodeInfoWrap::CreatePageNodeInfoWrap();
3906 std::string attribute = child->GetKey();
3907
3908 RectT<float> rect;
3909 int32_t len = child->GetArraySize();
3910 for (int32_t index = 0; index < len; index++) {
3911 auto object = child->GetArrayItem(index);
3912 if (object == nullptr || !object->IsObject()) {
3913 continue;
3914 }
3915 for (auto child = object->GetChild(); child && !child->IsNull(); child = child->GetNext()) {
3916 if (child->IsString()) {
3917 ParseViewDataString(child->GetKey(), child->GetString(), node);
3918 } else if (child->IsNumber()) {
3919 ParseViewDataNumber(child->GetKey(), child->GetInt(), node, rect, viewScale);
3920 }
3921 }
3922 }
3923
3924 HintToTypeWrap hintToTypeWrap = GetHintTypeAndMetadata(attribute, node);
3925 auto type = hintToTypeWrap.autoFillType;
3926 if (type != AceAutoFillType::ACE_UNSPECIFIED) {
3927 node->SetAutoFillType(type);
3928 node->SetMetadata(hintToTypeWrap.metadata);
3929 } else {
3930 return;
3931 }
3932
3933 NG::RectF rectF;
3934 rectF.SetRect(rect.GetX(), rect.GetY(), rect.Width(), rect.Height());
3935 node->SetPageNodeRect(rectF);
3936 node->SetId(nodeId);
3937 node->SetDepth(-1);
3938 nodeInfos.emplace_back(node);
3939 }
3940
ParseNWebViewDataCommonField(std::unique_ptr<JsonValue> child,ViewDataCommon & viewDataCommon)3941 void WebPattern::ParseNWebViewDataCommonField(std::unique_ptr<JsonValue> child, ViewDataCommon& viewDataCommon)
3942 {
3943 std::string key = child->GetKey();
3944 if (child->IsString() && key == OHOS::NWeb::NWEB_AUTOFILL_EVENT_TYPE) {
3945 std::string eventType = child->GetString();
3946 if (NWEB_AUTOFILL_EVENTS.count(eventType) != 0) {
3947 OHOS::NWeb::NWebAutofillEvent event = NWEB_AUTOFILL_EVENTS.at(eventType);
3948 viewDataCommon.eventType = event;
3949 }
3950 }
3951 if (child->IsString() && key == OHOS::NWeb::NWEB_AUTOFILL_PAGE_URL) {
3952 viewDataCommon.pageUrl = child->GetString();
3953 }
3954 if (child->IsBool() && key == OHOS::NWeb::NWEB_AUTOFILL_IS_USER_SELECTED) {
3955 viewDataCommon.isUserSelected = child->GetBool();
3956 }
3957 if (child->IsBool() && key == OHOS::NWeb::NWEB_AUTOFILL_IS_OTHER_ACCOUNT) {
3958 viewDataCommon.isOtherAccount = child->GetBool();
3959 }
3960 if (child->IsString() && key == OHOS::NWeb::NWEB_AUTOFILL_EVENT_SOURCE) {
3961 viewDataCommon.source = child->GetString();
3962 }
3963 }
3964
ParseNWebViewDataJson(const std::shared_ptr<OHOS::NWeb::NWebMessage> & viewDataJson,std::vector<RefPtr<PageNodeInfoWrap>> & nodeInfos,ViewDataCommon & viewDataCommon)3965 void WebPattern::ParseNWebViewDataJson(const std::shared_ptr<OHOS::NWeb::NWebMessage>& viewDataJson,
3966 std::vector<RefPtr<PageNodeInfoWrap>>& nodeInfos, ViewDataCommon& viewDataCommon)
3967 {
3968 nodeInfos.clear();
3969 auto sourceJson = JsonUtil::ParseJsonString(viewDataJson->GetString());
3970 if (sourceJson == nullptr || sourceJson->IsNull()) {
3971 return;
3972 }
3973
3974 int32_t nodeId = 1;
3975 int32_t len = sourceJson->GetArraySize();
3976 for (int32_t index = 0; index < len; index++) {
3977 auto object = sourceJson->GetArrayItem(index);
3978 if (object == nullptr || !object->IsObject()) {
3979 continue;
3980 }
3981 auto child = object->GetChild();
3982 if (child == nullptr || child->IsNull()) {
3983 continue;
3984 }
3985 if (child->IsArray()) {
3986 ParseNWebViewDataNode(std::move(child), nodeInfos, nodeId);
3987 nodeId++;
3988 } else {
3989 ParseNWebViewDataCommonField(std::move(child), viewDataCommon);
3990 }
3991 }
3992 }
3993
GetFocusedType()3994 AceAutoFillType WebPattern::GetFocusedType()
3995 {
3996 AceAutoFillType type = AceAutoFillType::ACE_UNSPECIFIED;
3997 for (const auto& nodeInfo : pageNodeInfo_) {
3998 if (nodeInfo && nodeInfo->GetIsFocus()) {
3999 type = static_cast<AceAutoFillType>(nodeInfo->GetAutoFillType());
4000 break;
4001 }
4002 }
4003 return type;
4004 }
4005
HandleAutoFillEvent(const std::shared_ptr<OHOS::NWeb::NWebMessage> & viewDataJson)4006 bool WebPattern::HandleAutoFillEvent(const std::shared_ptr<OHOS::NWeb::NWebMessage>& viewDataJson)
4007 {
4008 TAG_LOGI(AceLogTag::ACE_WEB, "AutoFillEvent");
4009 viewDataCommon_ = {};
4010 isPasswordFill_ = false;
4011 ParseNWebViewDataJson(viewDataJson, pageNodeInfo_, viewDataCommon_);
4012
4013 if (isPasswordFill_ && viewDataCommon_.source != OHOS::NWeb::NWEB_AUTOFILL_FOR_LOGIN) {
4014 TAG_LOGI(AceLogTag::ACE_WEB,
4015 "Handle autofill event failed! The form contains a login node, but the soruce is incorrect.");
4016 return false;
4017 }
4018
4019 auto eventType = viewDataCommon_.eventType;
4020
4021 if (eventType == OHOS::NWeb::NWebAutofillEvent::FILL) {
4022 auto host = GetHost();
4023 CHECK_NULL_RETURN(host, false);
4024 auto context = host->GetContext();
4025 CHECK_NULL_RETURN(context, false);
4026 auto taskExecutor = context->GetTaskExecutor();
4027 CHECK_NULL_RETURN(taskExecutor, false);
4028 bool fillRet = taskExecutor->PostDelayedTask(
4029 [weak = WeakClaim(this)] () {
4030 auto pattern = weak.Upgrade();
4031 CHECK_NULL_RETURN(pattern, false);
4032 return pattern->RequestAutoFill(pattern->GetFocusedType());
4033 },
4034 TaskExecutor::TaskType::UI, AUTOFILL_DELAY_TIME, "ArkUIWebHandleAutoFillEvent");
4035 return fillRet;
4036 }
4037
4038 if (eventType == OHOS::NWeb::NWebAutofillEvent::SAVE) {
4039 return RequestAutoSave();
4040 } else if (eventType == OHOS::NWeb::NWebAutofillEvent::UPDATE) {
4041 return UpdateAutoFillPopup();
4042 } else if (eventType == OHOS::NWeb::NWebAutofillEvent::CLOSE) {
4043 return CloseAutoFillPopup();
4044 }
4045
4046 return false;
4047 }
4048
RequestAutoFill(AceAutoFillType autoFillType)4049 bool WebPattern::RequestAutoFill(AceAutoFillType autoFillType)
4050 {
4051 TAG_LOGI(AceLogTag::ACE_WEB, "RequestAutoFill");
4052 auto host = GetHost();
4053 CHECK_NULL_RETURN(host, false);
4054 auto context = host->GetContext();
4055 CHECK_NULL_RETURN(context, false);
4056 auto instanceId = context->GetInstanceId();
4057 CHECK_NULL_RETURN(instanceId, false);
4058 ContainerScope scope(instanceId);
4059
4060 auto offset = GetCoordinatePoint().value_or(OffsetF());
4061 for (auto& nodeInfo : pageNodeInfo_) {
4062 auto rect = nodeInfo->GetPageNodeRect();
4063 NG::RectF rectF;
4064 rectF.SetRect(rect.GetX() + offset.GetX(), rect.GetY()+ offset.GetY(), rect.Width(), rect.Height());
4065 nodeInfo->SetPageNodeRect(rectF);
4066 }
4067
4068 auto container = Container::Current();
4069 if (container == nullptr) {
4070 container = Container::GetActive();
4071 }
4072 CHECK_NULL_RETURN(container, false);
4073 isAutoFillClosing_ = false;
4074 bool isPopup = false;
4075 return container->RequestAutoFill(host, autoFillType, false, isPopup, autoFillSessionId_, false);
4076 }
4077
RequestAutoSave()4078 bool WebPattern::RequestAutoSave()
4079 {
4080 TAG_LOGI(AceLogTag::ACE_WEB, "RequestAutoSave");
4081 auto host = GetHost();
4082 CHECK_NULL_RETURN(host, false);
4083 auto context = host->GetContext();
4084 CHECK_NULL_RETURN(context, false);
4085 auto instanceId = context->GetInstanceId();
4086 CHECK_NULL_RETURN(instanceId, false);
4087 ContainerScope scope(instanceId);
4088 auto container = Container::Current();
4089 if (container == nullptr) {
4090 container = Container::GetActive();
4091 }
4092 CHECK_NULL_RETURN(container, false);
4093 return container->RequestAutoSave(host, nullptr, nullptr, false);
4094 }
4095
UpdateAutoFillPopup()4096 bool WebPattern::UpdateAutoFillPopup()
4097 {
4098 TAG_LOGI(AceLogTag::ACE_WEB, "UpdateAutoFillPopup");
4099 if (isAutoFillClosing_) {
4100 return false;
4101 }
4102 auto host = GetHost();
4103 CHECK_NULL_RETURN(host, false);
4104 auto context = host->GetContext();
4105 CHECK_NULL_RETURN(context, false);
4106 auto instanceId = context->GetInstanceId();
4107 CHECK_NULL_RETURN(instanceId, false);
4108 ContainerScope scope(instanceId);
4109 auto container = Container::Current();
4110 if (container == nullptr) {
4111 container = Container::GetActive();
4112 }
4113 CHECK_NULL_RETURN(container, false);
4114 return container->UpdatePopupUIExtension(host, autoFillSessionId_, false);
4115 }
4116
CloseAutoFillPopup()4117 bool WebPattern::CloseAutoFillPopup()
4118 {
4119 TAG_LOGI(AceLogTag::ACE_WEB, "CloseAutoFillPopup");
4120 auto host = GetHost();
4121 CHECK_NULL_RETURN(host, false);
4122 auto context = host->GetContext();
4123 CHECK_NULL_RETURN(context, false);
4124 auto instanceId = context->GetInstanceId();
4125 CHECK_NULL_RETURN(instanceId, false);
4126 ContainerScope scope(instanceId);
4127 auto container = Container::Current();
4128 if (container == nullptr) {
4129 container = Container::GetActive();
4130 }
4131 CHECK_NULL_RETURN(container, false);
4132 isAutoFillClosing_ = true;
4133 return container->ClosePopupUIExtension(autoFillSessionId_);
4134 }
4135
OnTouchSelectionChanged(std::shared_ptr<OHOS::NWeb::NWebTouchHandleState> insertHandle,std::shared_ptr<OHOS::NWeb::NWebTouchHandleState> startSelectionHandle,std::shared_ptr<OHOS::NWeb::NWebTouchHandleState> endSelectionHandle)4136 void WebPattern::OnTouchSelectionChanged(std::shared_ptr<OHOS::NWeb::NWebTouchHandleState> insertHandle,
4137 std::shared_ptr<OHOS::NWeb::NWebTouchHandleState> startSelectionHandle,
4138 std::shared_ptr<OHOS::NWeb::NWebTouchHandleState> endSelectionHandle)
4139 {
4140 if (!webSelectOverlay_) {
4141 return;
4142 }
4143 webSelectOverlay_->OnTouchSelectionChanged(insertHandle, startSelectionHandle, endSelectionHandle);
4144 }
4145
OnCursorChange(const OHOS::NWeb::CursorType & type,std::shared_ptr<OHOS::NWeb::NWebCursorInfo> info)4146 bool WebPattern::OnCursorChange(const OHOS::NWeb::CursorType& type, std::shared_ptr<OHOS::NWeb::NWebCursorInfo> info)
4147 {
4148 TAG_LOGD(AceLogTag::ACE_WEB, "OnCursorChange type: %{public}d", type);
4149 if (mouseEventDeviceId_ == RESERVED_DEVICEID) {
4150 TAG_LOGD(AceLogTag::ACE_WEB, "OnCursorChange this device id is reserved.");
4151 return false;
4152 }
4153 if (isHoverExit_ && type == OHOS::NWeb::CursorType::CT_NONE) {
4154 TAG_LOGD(AceLogTag::ACE_WEB, "OnCursorChange reciving unexpected hide command");
4155 return false;
4156 }
4157 auto pipeline = PipelineContext::GetCurrentContext();
4158 CHECK_NULL_RETURN(pipeline, false);
4159 auto windowId = pipeline->GetWindowId();
4160 auto mouseStyle = MouseStyle::CreateMouseStyle();
4161 int32_t curPointerStyle = 0;
4162 if (mouseStyle->GetPointerStyle(windowId, curPointerStyle) == -1) {
4163 return false;
4164 }
4165
4166 if ((type == OHOS::NWeb::CursorType::CT_CONTEXTMENU) || (type == OHOS::NWeb::CursorType::CT_ALIAS)) {
4167 UpdateLocalCursorStyle(windowId, type);
4168 } else if (type == OHOS::NWeb::CursorType::CT_CUSTOM) {
4169 UpdateCustomCursor(windowId, info);
4170 } else {
4171 MouseFormat pointStyle = MouseFormat::DEFAULT;
4172 int64_t idx = BinarySearchFindIndex(g_cursorTypeMap, ArraySize(g_cursorTypeMap), type);
4173 if (idx >= 0) {
4174 pointStyle = g_cursorTypeMap[idx].value;
4175 }
4176 mouseStyle->SetPointerVisible(pointStyle);
4177 if (static_cast<int32_t>(pointStyle) != curPointerStyle) {
4178 mouseStyle->SetPointerStyle(windowId, pointStyle);
4179 }
4180 }
4181 return true;
4182 }
4183
UpdateLocalCursorStyle(int32_t windowId,const OHOS::NWeb::CursorType & type)4184 void WebPattern::UpdateLocalCursorStyle(int32_t windowId, const OHOS::NWeb::CursorType& type)
4185 {
4186 std::shared_ptr<Media::PixelMap> pixelMap;
4187 auto mouseStyle = MouseStyle::CreateMouseStyle();
4188 if (type == NWeb::CursorType::CT_CONTEXTMENU) {
4189 MouseFormat pointStyle = MouseFormat::CONTEXT_MENU;
4190 pixelMap = CreatePixelMapFromString(IMAGE_POINTER_CONTEXT_MENU_PATH);
4191 mouseStyle->SetMouseIcon(windowId, pointStyle, pixelMap);
4192 } else if (type == NWeb::CursorType::CT_ALIAS) {
4193 MouseFormat pointStyle = MouseFormat::ALIAS;
4194 pixelMap = CreatePixelMapFromString(IMAGE_POINTER_ALIAS_PATH);
4195 mouseStyle->SetMouseIcon(windowId, pointStyle, pixelMap);
4196 }
4197 }
4198
UpdateCustomCursor(int32_t windowId,std::shared_ptr<OHOS::NWeb::NWebCursorInfo> info)4199 void WebPattern::UpdateCustomCursor(int32_t windowId, std::shared_ptr<OHOS::NWeb::NWebCursorInfo> info)
4200 {
4201 int32_t x = 0;
4202 int32_t y = 0;
4203 int32_t width = 0;
4204 int32_t height = 0;
4205 uint8_t *buff = nullptr;
4206 if (info) {
4207 x = info->GetX();
4208 y = info->GetY();
4209 buff = info->GetBuff();
4210 width = info->GetWidth();
4211 height = info->GetHeight();
4212 }
4213 Media::InitializationOptions opt;
4214 opt.size.width = width;
4215 opt.size.height = height;
4216 opt.editable = true;
4217 auto pixelMap = Media::PixelMap::Create(opt);
4218 CHECK_NULL_VOID(pixelMap);
4219 uint64_t bufferSize = static_cast<uint64_t>(width * height * IMAGE_POINTER_CUSTOM_CHANNEL);
4220 uint32_t status = pixelMap->WritePixels(static_cast<const uint8_t*>(buff), bufferSize);
4221 if (status != 0) {
4222 TAG_LOGE(AceLogTag::ACE_WEB, "write pixel map failed %{public}u", status);
4223 return;
4224 }
4225 std::shared_ptr<Media::PixelMap> cursorPixelMap(pixelMap.release());
4226 CHECK_NULL_VOID(cursorPixelMap);
4227 auto mouseStyle = MouseStyle::CreateMouseStyle();
4228 CHECK_NULL_VOID(mouseStyle);
4229 mouseStyle->SetCustomCursor(windowId, x, y, cursorPixelMap);
4230 }
4231
CreatePixelMapFromString(const std::string & filePath)4232 std::shared_ptr<OHOS::Media::PixelMap> WebPattern::CreatePixelMapFromString(const std::string& filePath)
4233 {
4234 OHOS::Media::SourceOptions opts;
4235 opts.formatHint = "image/svg+xml";
4236 uint32_t errCode = 0;
4237 auto imageSource = OHOS::Media::ImageSource::CreateImageSource(filePath, opts, errCode);
4238 CHECK_NULL_RETURN(imageSource, nullptr);
4239 std::set<std::string> formats;
4240 errCode = imageSource->GetSupportedFormats(formats);
4241 Media::DecodeOptions decodeOpts;
4242 std::shared_ptr<OHOS::Media::PixelMap> pixelMap = imageSource->CreatePixelMap(decodeOpts, errCode);
4243 CHECK_NULL_RETURN(pixelMap, nullptr);
4244
4245 return pixelMap;
4246 }
4247
OnTooltip(const std::string & tooltip)4248 void WebPattern::OnTooltip(const std::string& tooltip)
4249 {
4250 auto pipeline = PipelineContext::GetCurrentContext();
4251 CHECK_NULL_VOID(pipeline);
4252 auto overlayManager = pipeline->GetOverlayManager();
4253 CHECK_NULL_VOID(overlayManager);
4254 tooltipTimestamp_ = GetSysTimestamp();
4255 auto tooltipTimestamp = tooltipTimestamp_;
4256
4257 if (tooltipId_ != -1) {
4258 TAG_LOGI(AceLogTag::ACE_WEB,
4259 "OnTooltip Remove text:%{public}s, tooltipId_:%{public}d", tooltip.c_str(), tooltipId_);
4260 overlayManager->RemoveIndexerPopupById(tooltipId_);
4261 tooltipId_ = -1;
4262 }
4263
4264 if (tooltip == "" || mouseHoveredX_ < 0 || mouseHoveredY_ < 0) {
4265 return;
4266 }
4267 ShowTooltip(tooltip, tooltipTimestamp);
4268 }
4269
GetVisibleRectToWeb(int & visibleX,int & visibleY,int & visibleWidth,int & visibleHeight)4270 void WebPattern::GetVisibleRectToWeb(int& visibleX, int& visibleY, int& visibleWidth, int& visibleHeight)
4271 {
4272 auto host = GetHost();
4273 CHECK_NULL_VOID(host);
4274 RectF visibleRect;
4275 RectF visibleInnerRect;
4276 RectF frameRect;
4277 host->GetVisibleRectWithClip(visibleRect, visibleInnerRect, frameRect);
4278 auto offset = GetCoordinatePoint().value_or(OffsetF());
4279 visibleX = visibleInnerRect.GetX() - offset.GetX();
4280 visibleY = visibleInnerRect.GetY() - offset.GetY();
4281 visibleWidth = visibleInnerRect.Width();
4282 visibleHeight = visibleInnerRect.Height();
4283 }
4284
RestoreRenderFit()4285 void WebPattern::RestoreRenderFit()
4286 {
4287 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::RestoreRenderFit, webId: %{public}d", GetWebId());
4288 if (renderContextForSurface_) {
4289 renderContextForSurface_->SetRenderFit(RenderFit::TOP_LEFT);
4290 }
4291 }
4292
AttachCustomKeyboard()4293 void WebPattern::AttachCustomKeyboard()
4294 {
4295 TAG_LOGI(AceLogTag::ACE_WEB, "WebCustomKeyboard AttachCustomKeyboard enter");
4296 CHECK_NULL_VOID(customKeyboardBuilder_);
4297 auto frameNode = GetHost();
4298 CHECK_NULL_VOID(frameNode);
4299 auto pipeline = PipelineContext::GetCurrentContextSafely();
4300 CHECK_NULL_VOID(pipeline);
4301 auto overlayManager = pipeline->GetOverlayManager();
4302 CHECK_NULL_VOID(overlayManager);
4303 overlayManager->SetCustomKeyboardOption(true);
4304 overlayManager->BindKeyboard(customKeyboardBuilder_, frameNode->GetId());
4305 keyboardOverlay_ = overlayManager;
4306 keyboardOverlay_->AvoidCustomKeyboard(frameNode->GetId(), 0);
4307 TAG_LOGI(AceLogTag::ACE_WEB, "WebCustomKeyboard AttachCustomKeyboard end");
4308 }
4309
CloseCustomKeyboard()4310 void WebPattern::CloseCustomKeyboard()
4311 {
4312 TAG_LOGI(AceLogTag::ACE_WEB, "WebCustomKeyboard CloseCustomKeyboard enter");
4313 auto frameNode = GetHost();
4314 CHECK_NULL_VOID(frameNode);
4315 CHECK_NULL_VOID(keyboardOverlay_);
4316 keyboardOverlay_->CloseKeyboard(frameNode->GetId());
4317 TAG_LOGI(AceLogTag::ACE_WEB, "WebCustomKeyboard CloseCustomKeyboard end");
4318 }
4319
HandleShowTooltip(const std::string & tooltip,int64_t tooltipTimestamp)4320 void WebPattern::HandleShowTooltip(const std::string& tooltip, int64_t tooltipTimestamp)
4321 {
4322 if ((tooltipTimestamp_ != tooltipTimestamp) || (tooltip == "")) {
4323 return;
4324 }
4325 auto pipeline = PipelineContext::GetCurrentContext();
4326 CHECK_NULL_VOID(pipeline);
4327 auto overlayManager = pipeline->GetOverlayManager();
4328 CHECK_NULL_VOID(overlayManager);
4329 if (tooltipId_ == -1) {
4330 tooltipId_ = ElementRegister::GetInstance()->MakeUniqueId();
4331 }
4332 SetTooltipTextLayoutPropertyInner(pipeline, tooltip, overlayManager);
4333 TAG_LOGI(AceLogTag::ACE_WEB, "HandleShowTooltip text:%{public}s, tooltipId_:%{public}d",
4334 tooltip.c_str(), tooltipId_);
4335 }
4336
SetTooltipTextLayoutPropertyInner(const RefPtr<PipelineContext> & pipeline,const std::string & tooltip,RefPtr<OverlayManager> & overlayManager)4337 void WebPattern::SetTooltipTextLayoutPropertyInner(const RefPtr<PipelineContext>& pipeline,
4338 const std::string& tooltip, RefPtr<OverlayManager>& overlayManager)
4339 {
4340 auto tooltipNode = FrameNode::GetOrCreateFrameNode(V2::TEXT_ETS_TAG, tooltipId_,
4341 []() { return AceType::MakeRefPtr<TextPattern>(); });
4342 CHECK_NULL_VOID(tooltipNode);
4343
4344 auto textRenderContext = tooltipNode->GetRenderContext();
4345 CHECK_NULL_VOID(textRenderContext);
4346 auto textLayoutProperty = tooltipNode->GetLayoutProperty<TextLayoutProperty>();
4347 CHECK_NULL_VOID(textLayoutProperty);
4348 textLayoutProperty->UpdateContent(tooltip);
4349
4350 BorderWidthProperty borderWidth;
4351 borderWidth.SetBorderWidth(TOOLTIP_BORDER_WIDTH);
4352 textLayoutProperty->UpdateBorderWidth(borderWidth);
4353 textLayoutProperty->UpdateFontSize(TOOLTIP_FONT_SIZE);
4354 textLayoutProperty->UpdatePadding({ CalcLength(TOOLTIP_PADDING),
4355 CalcLength(TOOLTIP_PADDING), CalcLength(TOOLTIP_PADDING), CalcLength(TOOLTIP_PADDING) });
4356 textLayoutProperty->UpdateCalcMaxSize(CalcSize(CalcLength(Dimension(
4357 pipeline->GetCurrentRootWidth() * TOOLTIP_MAX_PORTION)), std::nullopt));
4358 textRenderContext->UpdateBackgroundColor(Color::WHITE);
4359
4360 OffsetF tooltipOffset;
4361 CalculateTooltipOffset(tooltipNode, tooltipOffset);
4362 textRenderContext->UpdatePosition(OffsetT<Dimension>(Dimension(tooltipOffset.GetX()),
4363 Dimension(tooltipOffset.GetY())));
4364
4365 BorderColorProperty borderColor;
4366 borderColor.SetColor(Color::BLACK);
4367 textRenderContext->UpdateBorderColor(borderColor);
4368 overlayManager->ShowIndexerPopup(tooltipId_, tooltipNode);
4369 }
4370
ShowTooltip(const std::string & tooltip,int64_t tooltipTimestamp)4371 void WebPattern::ShowTooltip(const std::string& tooltip, int64_t tooltipTimestamp)
4372 {
4373 auto tooltipTask = [weak = WeakClaim(this), tooltip, tooltipTimestamp]() {
4374 auto pattern = weak.Upgrade();
4375 CHECK_NULL_VOID(pattern);
4376 pattern->HandleShowTooltip(tooltip, tooltipTimestamp);
4377 };
4378
4379 auto host = GetHost();
4380 CHECK_NULL_VOID(host);
4381 auto context = host->GetContext();
4382 CHECK_NULL_VOID(context);
4383
4384 auto taskExecutor = context->GetTaskExecutor();
4385 CHECK_NULL_VOID(taskExecutor);
4386
4387 taskExecutor->PostDelayedTask(tooltipTask, TaskExecutor::TaskType::UI, TOOLTIP_DELAY_MS, "ArkUIWebShowTooltip");
4388 }
4389
CalculateTooltipOffset(RefPtr<FrameNode> & tooltipNode,OffsetF & tooltipOffset)4390 void WebPattern::CalculateTooltipOffset(RefPtr<FrameNode>& tooltipNode, OffsetF& tooltipOffset)
4391 {
4392 auto textLayoutWrapper = tooltipNode->CreateLayoutWrapper(true);
4393 CHECK_NULL_VOID(textLayoutWrapper);
4394 textLayoutWrapper->Measure(std::nullopt);
4395 auto textGeometryNode = textLayoutWrapper->GetGeometryNode();
4396 CHECK_NULL_VOID(textGeometryNode);
4397 auto textWidth = textGeometryNode->GetMarginFrameSize().Width();
4398 auto textHeight = textGeometryNode->GetMarginFrameSize().Height();
4399
4400 auto offset = GetCoordinatePoint().value_or(OffsetF());
4401 auto pipeline = PipelineContext::GetCurrentContext();
4402 CHECK_NULL_VOID(pipeline);
4403 auto overlayManager = pipeline->GetOverlayManager();
4404 CHECK_NULL_VOID(overlayManager);
4405 auto rootNode = AceType::DynamicCast<FrameNode>(overlayManager->GetRootNode().Upgrade());
4406 CHECK_NULL_VOID(rootNode);
4407 auto root = rootNode->GetTransformRectRelativeToWindow();
4408
4409 auto offsetX = offset.GetX() - root.GetX() + mouseHoveredX_ + TOOLTIP_MARGIN;
4410 auto offsetY = offset.GetY() - root.GetY() + mouseHoveredY_ + TOOLTIP_MARGIN;
4411
4412 ScopedLayout scope(pipeline.GetRawPtr());
4413 if (GreatNotEqual(offsetX + textWidth, root.Width())) {
4414 offsetX = root.Width() - textWidth;
4415 }
4416 if (GreatNotEqual(offsetY + textHeight, root.Height())) {
4417 offsetY = root.Height() - textHeight;
4418 }
4419 tooltipOffset.SetX(offsetX);
4420 tooltipOffset.SetY(offsetY);
4421 TAG_LOGI(AceLogTag::ACE_WEB,
4422 "CalculateTooltipOffset [Tooltip] width: %{public}f height: %{public}f offset:(%{public}f, %{public}f)"
4423 " [Web] width: %{public}f height: %{public}f offset:(%{public}f, %{public}f)",
4424 textWidth, textHeight, offsetX, offsetY, drawSize_.Width(), drawSize_.Height(), offset.GetX(), offset.GetY());
4425 }
4426
OnSelectPopupMenu(std::shared_ptr<OHOS::NWeb::NWebSelectPopupMenuParam> params,std::shared_ptr<OHOS::NWeb::NWebSelectPopupMenuCallback> callback)4427 void WebPattern::OnSelectPopupMenu(std::shared_ptr<OHOS::NWeb::NWebSelectPopupMenuParam> params,
4428 std::shared_ptr<OHOS::NWeb::NWebSelectPopupMenuCallback> callback)
4429 {
4430 CHECK_NULL_VOID(params);
4431 CHECK_NULL_VOID(callback);
4432 auto host = GetHost();
4433 CHECK_NULL_VOID(host);
4434 auto eventHub = host->GetEventHub<WebEventHub>();
4435 CHECK_NULL_VOID(eventHub);
4436 auto context = PipelineContext::GetCurrentContext();
4437 CHECK_NULL_VOID(context);
4438 auto overlayManager = context->GetOverlayManager();
4439 CHECK_NULL_VOID(overlayManager);
4440
4441 auto id = host->GetId();
4442 std::vector<SelectParam> selectParam;
4443 for (auto& item : params->GetMenuItems()) {
4444 selectParam.push_back({
4445 item->GetLabel(), ""
4446 });
4447 }
4448 auto menu = MenuView::Create(selectParam, id, host->GetTag());
4449 CHECK_NULL_VOID(menu);
4450 auto menuWrapperPattern = menu->GetPattern<MenuWrapperPattern>();
4451 CHECK_NULL_VOID(menuWrapperPattern);
4452 auto destructor = [weak = WeakClaim(this), id]() {
4453 auto pattern = weak.Upgrade();
4454 CHECK_NULL_VOID(pattern);
4455 auto pipeline = NG::PipelineContext::GetCurrentContext();
4456 CHECK_NULL_VOID(pipeline);
4457 auto manager = pipeline->GetOverlayManager();
4458 CHECK_NULL_VOID(manager);
4459 pattern->SetSelectPopupMenuShowing(false);
4460 manager->DeleteMenu(id);
4461 };
4462 eventHub->SetOnDisappear(destructor);
4463
4464 WebPattern::InitSelectPopupMenuView(menu, callback, params, context->GetDipScale());
4465 menuWrapperPattern->RegisterMenuDisappearCallback([weak = WeakClaim(this), callback]() {
4466 auto pattern = weak.Upgrade();
4467 CHECK_NULL_VOID(pattern);
4468 callback->Cancel();
4469 pattern->SetSelectPopupMenuShowing(false);
4470 });
4471 auto offset = GetSelectPopupPostion(params->GetSelectMenuBound());
4472 TAG_LOGI(AceLogTag::ACE_WEB, "OnSelectPopupMenu offset:(%{public}f, %{public}f)", offset.GetX(), offset.GetY());
4473 selectPopupMenuShowing_ = true;
4474 overlayManager->ShowMenu(id, offset, menu);
4475 }
4476
NotifyForNextTouchEvent()4477 void WebPattern::NotifyForNextTouchEvent()
4478 {
4479 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::NotifyForNextTouchEvent");
4480 CHECK_NULL_VOID(delegate_);
4481 delegate_->NotifyForNextTouchEvent();
4482 }
4483
InitTouchEventListener()4484 void WebPattern::InitTouchEventListener()
4485 {
4486 TAG_LOGD(AceLogTag::ACE_WEB, "WebPattern::InitTouchEventListener");
4487 if (touchEventListener_) {
4488 return;
4489 }
4490 touchEventListener_ = std::make_shared<TouchEventListener>();
4491 touchEventListener_->SetPatternToListener(AceType::WeakClaim(this));
4492
4493 auto context = PipelineContext::GetCurrentContext();
4494 CHECK_NULL_VOID(context);
4495
4496 context->RegisterTouchEventListener(touchEventListener_);
4497 }
4498
UninitTouchEventListener()4499 void WebPattern::UninitTouchEventListener()
4500 {
4501 TAG_LOGD(AceLogTag::ACE_WEB, "WebPattern::UninitTouchEventListener");
4502 touchEventListener_ = nullptr;
4503
4504 auto context = PipelineContext::GetCurrentContext();
4505 CHECK_NULL_VOID(context);
4506 context->UnregisterTouchEventListener(AceType::WeakClaim(this));
4507 }
4508
OnDateTimeChooserPopup(std::shared_ptr<OHOS::NWeb::NWebDateTimeChooser> chooser,const std::vector<std::shared_ptr<OHOS::NWeb::NWebDateTimeSuggestion>> & suggestions,std::shared_ptr<NWeb::NWebDateTimeChooserCallback> callback)4509 void WebPattern::OnDateTimeChooserPopup(std::shared_ptr<OHOS::NWeb::NWebDateTimeChooser> chooser,
4510 const std::vector<std::shared_ptr<OHOS::NWeb::NWebDateTimeSuggestion>>& suggestions,
4511 std::shared_ptr<NWeb::NWebDateTimeChooserCallback> callback)
4512 {
4513 if (!chooser) {
4514 return;
4515 }
4516
4517 bool result = false;
4518 if (suggestions.size() != 0) {
4519 result = ShowDateTimeSuggestionDialog(chooser, suggestions, callback);
4520 } else if (chooser->GetType() == NWeb::DTC_TIME) {
4521 result = ShowTimeDialog(chooser, suggestions, callback);
4522 } else {
4523 result = ShowDateTimeDialog(chooser, suggestions, callback);
4524 }
4525 if (!result) {
4526 callback->Continue(false, OHOS::NWeb::DateTime());
4527 }
4528 }
4529
GetDialogProperties(const RefPtr<DialogTheme> & theme)4530 DialogProperties WebPattern::GetDialogProperties(const RefPtr<DialogTheme>& theme)
4531 {
4532 DialogProperties properties;
4533 if (GetWebInfoType() == WebInfoType::TYPE_MOBILE) {
4534 properties.alignment = DialogAlignment::BOTTOM;
4535 } else {
4536 properties.alignment = DialogAlignment::CENTER;
4537 }
4538 properties.customStyle = false;
4539 properties.offset = DimensionOffset(Offset(0, -theme->GetMarginBottom().ConvertToPx()));
4540 return properties;
4541 }
4542
ShowDateTimeDialog(std::shared_ptr<OHOS::NWeb::NWebDateTimeChooser> chooser,const std::vector<std::shared_ptr<OHOS::NWeb::NWebDateTimeSuggestion>> & suggestions,std::shared_ptr<NWeb::NWebDateTimeChooserCallback> callback)4543 bool WebPattern::ShowDateTimeDialog(std::shared_ptr<OHOS::NWeb::NWebDateTimeChooser> chooser,
4544 const std::vector<std::shared_ptr<OHOS::NWeb::NWebDateTimeSuggestion>>& suggestions,
4545 std::shared_ptr<NWeb::NWebDateTimeChooserCallback> callback)
4546 {
4547 auto container = Container::Current();
4548 CHECK_NULL_RETURN(container, false);
4549 auto pipelineContext = AccessibilityManager::DynamicCast<NG::PipelineContext>(container->GetPipelineContext());
4550 CHECK_NULL_RETURN(pipelineContext, false);
4551 auto executor = pipelineContext->GetTaskExecutor();
4552 CHECK_NULL_RETURN(executor, false);
4553 auto context = AccessibilityManager::DynamicCast<NG::PipelineContext>(pipelineContext);
4554 auto overlayManager = context ? context->GetOverlayManager() : nullptr;
4555 CHECK_NULL_RETURN(overlayManager, false);
4556 auto theme = pipelineContext->GetTheme<DialogTheme>();
4557 CHECK_NULL_RETURN(theme, false);
4558 NG::DatePickerSettingData settingData;
4559 settingData.isLunar = false;
4560 settingData.showTime = chooser->GetType() == NWeb::DTC_DATETIME_LOCAL;
4561 settingData.useMilitary = true;
4562 DialogProperties properties = GetDialogProperties(theme);
4563 std::map<std::string, PickerDate> datePickerProperty;
4564 std::map<std::string, PickerTime> timePickerProperty;
4565 OHOS::NWeb::DateTime minimum = chooser->GetMinimum();
4566 OHOS::NWeb::DateTime maximum = chooser->GetMaximum();
4567 OHOS::NWeb::DateTime dialogValue = chooser->GetDialogValue();
4568 settingData.datePickerProperty["start"] = PickerDate(
4569 minimum.year, minimum.month + 1, minimum.day);
4570 settingData.datePickerProperty["end"] = PickerDate(
4571 maximum.year, maximum.month + 1, maximum.day);
4572 if (chooser->GetHasSelected()) {
4573 int32_t day = (dialogValue.day == 0) ? 1 : dialogValue.day;
4574 settingData.datePickerProperty["selected"] =
4575 PickerDate(dialogValue.year, dialogValue.month + 1, day);
4576 }
4577 std::map<std::string, NG::DialogEvent> dialogEvent;
4578 std::map<std::string, NG::DialogGestureEvent> dialogCancelEvent;
4579 dialogEvent["acceptId"] = [callback](const std::string& info) {
4580 OHOS::NWeb::DateTime result;
4581 bool success = ParseDateTimeJson(info, result);
4582 callback->Continue(success, result);
4583 };
4584 dialogCancelEvent["cancelId"] =
4585 [callback](const GestureEvent&) { callback->Continue(false, OHOS::NWeb::DateTime()); };
4586 overlayManager->RegisterOnHideDialog([callback] { callback->Continue(false, OHOS::NWeb::DateTime()); });
4587 executor->PostTask(
4588 [properties, settingData, dialogEvent, dialogCancelEvent, weak = WeakPtr<NG::OverlayManager>(overlayManager)] {
4589 auto overlayManager = weak.Upgrade();
4590 CHECK_NULL_VOID(overlayManager);
4591 overlayManager->ShowDateDialog(properties, settingData, dialogEvent, dialogCancelEvent);
4592 },
4593 TaskExecutor::TaskType::UI, "ArkUIWebShowDateDialog");
4594 return true;
4595 }
4596
ShowTimeDialog(std::shared_ptr<OHOS::NWeb::NWebDateTimeChooser> chooser,const std::vector<std::shared_ptr<OHOS::NWeb::NWebDateTimeSuggestion>> & suggestions,std::shared_ptr<NWeb::NWebDateTimeChooserCallback> callback)4597 bool WebPattern::ShowTimeDialog(std::shared_ptr<OHOS::NWeb::NWebDateTimeChooser> chooser,
4598 const std::vector<std::shared_ptr<OHOS::NWeb::NWebDateTimeSuggestion>>& suggestions,
4599 std::shared_ptr<NWeb::NWebDateTimeChooserCallback> callback)
4600 {
4601 auto container = Container::Current();
4602 CHECK_NULL_RETURN(container, false);
4603 auto pipelineContext = AccessibilityManager::DynamicCast<NG::PipelineContext>(container->GetPipelineContext());
4604 CHECK_NULL_RETURN(pipelineContext, false);
4605 auto executor = pipelineContext->GetTaskExecutor();
4606 CHECK_NULL_RETURN(executor, false);
4607 auto theme = pipelineContext->GetTheme<DialogTheme>();
4608 CHECK_NULL_RETURN(theme, false);
4609 auto context = AccessibilityManager::DynamicCast<NG::PipelineContext>(pipelineContext);
4610 auto overlayManager = context ? context->GetOverlayManager() : nullptr;
4611 CHECK_NULL_RETURN(overlayManager, false);
4612 NG::TimePickerSettingData settingData;
4613 settingData.isUseMilitaryTime = true;
4614 DialogProperties properties = GetDialogProperties(theme);
4615 std::map<std::string, PickerTime> timePickerProperty;
4616 OHOS::NWeb::DateTime minimum = chooser->GetMinimum();
4617 OHOS::NWeb::DateTime maximum = chooser->GetMaximum();
4618 OHOS::NWeb::DateTime dialogValue = chooser->GetDialogValue();
4619 timePickerProperty["start"] = PickerTime(minimum.hour, minimum.minute, minimum.second);
4620 timePickerProperty["selected"] = PickerTime(maximum.hour, maximum.minute, maximum.second);
4621 if (chooser->GetHasSelected()) {
4622 timePickerProperty["selected"] =
4623 PickerTime(dialogValue.hour, dialogValue.minute, dialogValue.second);
4624 }
4625 std::map<std::string, NG::DialogEvent> dialogEvent;
4626 std::map<std::string, NG::DialogGestureEvent> dialogCancelEvent;
4627 dialogEvent["acceptId"] = [callback](const std::string& info) {
4628 OHOS::NWeb::DateTime result;
4629 bool success = ParseDateTimeJson(info, result);
4630 callback->Continue(success, result);
4631 };
4632 dialogCancelEvent["cancelId"] =
4633 [callback](const GestureEvent&) { callback->Continue(false, OHOS::NWeb::DateTime()); };
4634 overlayManager->RegisterOnHideDialog([callback] { callback->Continue(false, OHOS::NWeb::DateTime()); });
4635 executor->PostTask(
4636 [properties, settingData, timePickerProperty, dialogEvent, dialogCancelEvent,
4637 weak = WeakPtr<NG::OverlayManager>(overlayManager)] {
4638 auto overlayManager = weak.Upgrade();
4639 CHECK_NULL_VOID(overlayManager);
4640 overlayManager->ShowTimeDialog(properties, settingData, timePickerProperty, dialogEvent, dialogCancelEvent);
4641 },
4642 TaskExecutor::TaskType::UI, "ArkUIWebShowTimeDialog");
4643 return true;
4644 }
4645
ShowDateTimeSuggestionDialog(std::shared_ptr<OHOS::NWeb::NWebDateTimeChooser> chooser,const std::vector<std::shared_ptr<OHOS::NWeb::NWebDateTimeSuggestion>> & suggestions,std::shared_ptr<NWeb::NWebDateTimeChooserCallback> callback)4646 bool WebPattern::ShowDateTimeSuggestionDialog(std::shared_ptr<OHOS::NWeb::NWebDateTimeChooser> chooser,
4647 const std::vector<std::shared_ptr<OHOS::NWeb::NWebDateTimeSuggestion>>& suggestions,
4648 std::shared_ptr<NWeb::NWebDateTimeChooserCallback> callback)
4649 {
4650 auto container = Container::Current();
4651 CHECK_NULL_RETURN(container, false);
4652 auto pipelineContext = AccessibilityManager::DynamicCast<NG::PipelineContext>(container->GetPipelineContext());
4653 CHECK_NULL_RETURN(pipelineContext, false);
4654 auto executor = pipelineContext->GetTaskExecutor();
4655 CHECK_NULL_RETURN(executor, false);
4656 auto theme = pipelineContext->GetTheme<DialogTheme>();
4657 CHECK_NULL_RETURN(theme, false);
4658 auto context = AccessibilityManager::DynamicCast<NG::PipelineContext>(pipelineContext);
4659 auto overlayManager = context ? context->GetOverlayManager() : nullptr;
4660 CHECK_NULL_RETURN(overlayManager, false);
4661 NG::TextPickerSettingData settingData;
4662 if (memset_s(&settingData, sizeof(NG::TextPickerSettingData), 0, sizeof(NG::TextPickerSettingData)) != EOK) {
4663 return false;
4664 }
4665 std::map<std::string, OHOS::NWeb::DateTime> suggestionMap;
4666 for (size_t i = 0; i < suggestions.size(); i++) {
4667 settingData.rangeVector.push_back({ "", suggestions[i]->GetLocalizedValue() });
4668 settingData.values.push_back(suggestions[i]->GetLocalizedValue());
4669 suggestionMap.emplace(std::make_pair(suggestions[i]->GetLocalizedValue(), suggestions[i]->GetValue()));
4670 }
4671 settingData.columnKind = NG::TEXT;
4672 settingData.selected = chooser->GetSuggestionIndex();
4673 DialogProperties properties = GetDialogProperties(theme);
4674 std::map<std::string, NG::DialogTextEvent> dialogEvent;
4675 std::map<std::string, NG::DialogGestureEvent> dialogCancelEvent;
4676 dialogEvent["acceptId"] = [suggestionMap, callback](const std::string& info) {
4677 std::string value = ParseTextJsonValue(info);
4678 if (suggestionMap.find(value) != suggestionMap.end()) {
4679 callback->Continue(true, suggestionMap.at(value));
4680 } else {
4681 callback->Continue(false, OHOS::NWeb::DateTime());
4682 }
4683 };
4684 dialogCancelEvent["cancelId"] =
4685 [callback](const GestureEvent&) { callback->Continue(false, OHOS::NWeb::DateTime()); };
4686 overlayManager->RegisterOnHideDialog([callback] { callback->Continue(false, OHOS::NWeb::DateTime()); });
4687 executor->PostTask(
4688 [properties, settingData, dialogEvent, dialogCancelEvent,
4689 weak = WeakPtr<NG::OverlayManager>(overlayManager)] {
4690 auto overlayManager = weak.Upgrade();
4691 CHECK_NULL_VOID(overlayManager);
4692 overlayManager->ShowTextDialog(properties, settingData, dialogEvent, dialogCancelEvent);
4693 },
4694 TaskExecutor::TaskType::UI, "ArkUIWebShowTextDialog");
4695 return true;
4696 }
4697
OnDateTimeChooserClose()4698 void WebPattern::OnDateTimeChooserClose() {}
4699
InitSelectPopupMenuViewOption(const std::vector<RefPtr<FrameNode>> & options,const std::shared_ptr<OHOS::NWeb::NWebSelectPopupMenuCallback> & callback,const std::shared_ptr<OHOS::NWeb::NWebSelectPopupMenuParam> & params,const double & dipScale)4700 void WebPattern::InitSelectPopupMenuViewOption(const std::vector<RefPtr<FrameNode>>& options,
4701 const std::shared_ptr<OHOS::NWeb::NWebSelectPopupMenuCallback>& callback,
4702 const std::shared_ptr<OHOS::NWeb::NWebSelectPopupMenuParam>& params,
4703 const double& dipScale)
4704 {
4705 int32_t optionIndex = -1;
4706 int32_t width = params->GetSelectMenuBound() ? params->GetSelectMenuBound()->GetWidth() : 0;
4707 auto items = params->GetMenuItems();
4708 int32_t selectedIndex = params->GetSelectedItem();
4709 TAG_LOGD(AceLogTag::ACE_WEB, "InitSelectPopupMenuViewOption selectedIndex:%{public}d", selectedIndex);
4710
4711 for (auto &&option : options) {
4712 optionIndex++;
4713 CHECK_NULL_VOID(option);
4714 auto optionPattern = option->GetPattern<OptionPattern>();
4715 CHECK_NULL_VOID(optionPattern);
4716 auto optionPaintProperty = option->GetPaintProperty<OptionPaintProperty>();
4717 CHECK_NULL_VOID(optionPaintProperty);
4718 optionPaintProperty->SetIdealWidthForWeb(width - OPTION_MARGIN.ConvertToPx());
4719 optionPattern->SetFontSize(Dimension(params->GetItemFontSize() * dipScale));
4720 if (selectedIndex == optionIndex) {
4721 optionPattern->SetFontColor(SELECTED_OPTION_FONT_COLOR);
4722 optionPattern->SetBgColor(SELECTED_OPTION_BACKGROUND_COLOR);
4723 optionPattern->UpdateNextNodeDivider(false);
4724 optionPaintProperty->UpdateNeedDivider(false);
4725 }
4726 auto hub = option->GetEventHub<OptionEventHub>();
4727 CHECK_NULL_VOID(hub);
4728 if (optionIndex >= 0 && static_cast<uint32_t>(optionIndex) < items.size()) {
4729 hub->SetEnabled(items[optionIndex]->GetIsEnabled());
4730 auto focusHub = option->GetFocusHub();
4731 if (focusHub) {
4732 focusHub->SetEnabled(items[optionIndex]->GetIsEnabled());
4733 }
4734 }
4735 auto selectCallback = [callback](int32_t index) {
4736 std::vector<int32_t> indices { static_cast<int32_t>(index) };
4737 callback->Continue(indices);
4738 };
4739 hub->SetOnSelect(std::move(selectCallback));
4740 option->MarkModifyDone();
4741 }
4742 }
4743
InitSelectPopupMenuView(RefPtr<FrameNode> & menuWrapper,std::shared_ptr<OHOS::NWeb::NWebSelectPopupMenuCallback> callback,std::shared_ptr<OHOS::NWeb::NWebSelectPopupMenuParam> params,const double & dipScale)4744 void WebPattern::InitSelectPopupMenuView(RefPtr<FrameNode>& menuWrapper,
4745 std::shared_ptr<OHOS::NWeb::NWebSelectPopupMenuCallback> callback,
4746 std::shared_ptr<OHOS::NWeb::NWebSelectPopupMenuParam> params,
4747 const double& dipScale)
4748 {
4749 auto menu = AceType::DynamicCast<FrameNode>(menuWrapper->GetChildAtIndex(0));
4750 CHECK_NULL_VOID(menu);
4751 auto menuPattern = menu->GetPattern<MenuPattern>();
4752 CHECK_NULL_VOID(menuPattern);
4753
4754 InitSelectPopupMenuViewOption(menuPattern->GetOptions(), callback, params, dipScale);
4755 }
4756
GetSelectPopupPostion(std::shared_ptr<OHOS::NWeb::NWebSelectMenuBound> bound)4757 OffsetF WebPattern::GetSelectPopupPostion(std::shared_ptr<OHOS::NWeb::NWebSelectMenuBound> bound)
4758 {
4759 auto offset = GetCoordinatePoint().value_or(OffsetF());
4760 if (bound) {
4761 offset.AddX(bound->GetX());
4762 offset.AddY(bound->GetY() + bound->GetHeight());
4763 }
4764 if (Container::GreatOrEqualAPIVersion(PlatformVersion::VERSION_ELEVEN)) {
4765 offset.AddX(-CALIBERATE_X.ConvertToPx());
4766 }
4767 return offset;
4768 }
4769
UpdateLocale()4770 void WebPattern::UpdateLocale()
4771 {
4772 CHECK_NULL_VOID(delegate_);
4773 delegate_->UpdateLocale();
4774 }
4775
OnWindowShow()4776 void WebPattern::OnWindowShow()
4777 {
4778 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::OnWindowShow");
4779 CHECK_NULL_VOID(delegate_);
4780 delegate_->OnRenderToForeground();
4781 delegate_->OnOnlineRenderToForeground();
4782
4783 if (isWindowShow_ || !isVisible_) {
4784 return;
4785 }
4786
4787 delegate_->ShowWebView();
4788 isWindowShow_ = true;
4789 }
4790
OnWindowHide()4791 void WebPattern::OnWindowHide()
4792 {
4793 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::OnWindowHide");
4794 CHECK_NULL_VOID(delegate_);
4795 delegate_->OnRenderToBackground();
4796 if (!isWindowShow_ || !isActive_) {
4797 return;
4798 }
4799
4800 delegate_->HideWebView();
4801 CloseContextSelectionMenu();
4802 needOnFocus_ = false;
4803 isWindowShow_ = false;
4804 }
4805
OnWindowSizeChanged(int32_t width,int32_t height,WindowSizeChangeReason type)4806 void WebPattern::OnWindowSizeChanged(int32_t width, int32_t height, WindowSizeChangeReason type)
4807 {
4808 TAG_LOGD(AceLogTag::ACE_WEB, "WindowSizeChangeReason type: %{public}d ", type);
4809 if (type == WindowSizeChangeReason::MAXIMIZE) {
4810 WindowMaximize();
4811 return;
4812 }
4813 CHECK_NULL_VOID(delegate_);
4814 bool isSmoothDragResizeEnabled = delegate_->GetIsSmoothDragResizeEnabled();
4815 if (!isSmoothDragResizeEnabled) {
4816 return;
4817 }
4818 if (type == WindowSizeChangeReason::DRAG_START || type == WindowSizeChangeReason::DRAG) {
4819 dragWindowFlag_ = true;
4820 delegate_->SetDragResizeStartFlag(true);
4821 WindowDrag(width, height);
4822 }
4823 if (type == WindowSizeChangeReason::DRAG_END) {
4824 delegate_->SetDragResizeStartFlag(false);
4825 auto frameNode = GetHost();
4826 CHECK_NULL_VOID(frameNode);
4827 auto offset = Offset(GetCoordinatePoint()->GetX(), GetCoordinatePoint()->GetY());
4828 delegate_->SetBoundsOrResize(drawSize_, offset, false);
4829 delegate_->ResizeVisibleViewport(visibleViewportSize_, false);
4830 dragWindowFlag_ = false;
4831 lastHeight_ = 0;
4832 lastWidth_ = 0;
4833 }
4834 }
4835
WindowMaximize()4836 void WebPattern::WindowMaximize()
4837 {
4838 if (!SystemProperties::GetWebDebugMaximizeResizeOptimize()) {
4839 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::WindowMaximize not enabled");
4840 return;
4841 }
4842 WebInfoType webInfoType = GetWebInfoType();
4843 if (webInfoType != WebInfoType::TYPE_2IN1) {
4844 return;
4845 }
4846 if (layoutMode_ != WebLayoutMode::NONE || renderMode_ != RenderMode::ASYNC_RENDER) {
4847 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::WindowMaximize not support");
4848 return;
4849 }
4850 if (!isAttachedToMainTree_ || !isVisible_) {
4851 return;
4852 }
4853 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::WindowMaximize, webId: %{public}d", GetWebId());
4854 if (renderContextForSurface_) {
4855 renderContextForSurface_->SetRenderFit(RenderFit::RESIZE_FILL);
4856 }
4857 if (delegate_) {
4858 delegate_->MaximizeResize();
4859 }
4860 }
4861
WindowDrag(int32_t width,int32_t height)4862 void WebPattern::WindowDrag(int32_t width, int32_t height)
4863 {
4864 if (delegate_) {
4865 if (lastHeight_ == 0 && lastWidth_ == 0) {
4866 lastHeight_ = height;
4867 lastWidth_ = width;
4868 }
4869 if (!GetPendingSizeStatus() && dragWindowFlag_) {
4870 int64_t pre_height = height - lastHeight_;
4871 int64_t pre_width = width - lastWidth_;
4872 if (pre_height <= CHECK_PRE_SIZE && pre_height > 0) {
4873 pre_height = 0;
4874 }
4875 if (pre_width <= CHECK_PRE_SIZE && pre_width > 0) {
4876 pre_width = 0;
4877 }
4878 lastHeight_ = height;
4879 lastWidth_ = width;
4880 if (pre_width == 0 && pre_height == 0) {
4881 return;
4882 }
4883 delegate_->SetDragResizePreSize(pre_height * ADJUST_RATIO, pre_width * ADJUST_RATIO);
4884 }
4885 }
4886 }
4887
OnCompleteSwapWithNewSize()4888 void WebPattern::OnCompleteSwapWithNewSize()
4889 {
4890 if (!isInWindowDrag_ || !isWaiting_)
4891 return;
4892
4893 ACE_SCOPED_TRACE("WebPattern::OnCompleteSwapWithNewSize");
4894 isWaiting_ = false;
4895 }
4896
OnResizeNotWork()4897 void WebPattern::OnResizeNotWork()
4898 {
4899 if (!isInWindowDrag_ || !isWaiting_)
4900 return;
4901
4902 ACE_SCOPED_TRACE("WebPattern::OnResizeNotWork");
4903 isWaiting_ = false;
4904 }
4905
UpdateOnFocusTextField(bool isFocus)4906 void WebPattern::UpdateOnFocusTextField(bool isFocus)
4907 {
4908 auto host = GetHost();
4909 CHECK_NULL_VOID(host);
4910 auto context = PipelineContext::GetCurrentContext();
4911 CHECK_NULL_VOID(context);
4912 auto textFieldManager = DynamicCast<TextFieldManagerNG>(context->GetTextFieldManager());
4913 CHECK_NULL_VOID(textFieldManager);
4914 isFocus ? textFieldManager->SetOnFocusTextField(WeakClaim(this))
4915 : textFieldManager->ClearOnFocusTextField(host->GetId());
4916 }
4917
OnBackPressed()4918 bool WebPattern::OnBackPressed()
4919 {
4920 auto host = GetHost();
4921 CHECK_NULL_RETURN(host, false);
4922 TAG_LOGI(AceLogTag::ACE_WEB, "Web %{public}d receives back press event", host->GetId());
4923 if (IsVirtualKeyBoardShow()) {
4924 CloseSelectOverlay();
4925 SelectCancel();
4926 TAG_LOGI(AceLogTag::ACE_WEB, "Request close soft keyboard.");
4927 auto inputMethod = MiscServices::InputMethodController::GetInstance();
4928 CHECK_NULL_RETURN(inputMethod, false);
4929 inputMethod->HideTextInput();
4930 inputMethod->Close();
4931 CHECK_NULL_RETURN(delegate_, true);
4932 delegate_->CloseCustomKeyboard();
4933 delegate_->GestureBackBlur();
4934 return true;
4935 }
4936 return false;
4937 }
4938
OnBackPressedForFullScreen() const4939 bool WebPattern::OnBackPressedForFullScreen() const
4940 {
4941 if (!isFullScreen_) {
4942 return false;
4943 }
4944
4945 TAG_LOGI(AceLogTag::ACE_WEB, "FullScreenBackPressEvent Received");
4946 CHECK_NULL_RETURN(fullScreenExitHandler_, false);
4947 auto webFullScreenExitHandler = fullScreenExitHandler_->GetHandler();
4948 CHECK_NULL_RETURN(webFullScreenExitHandler, false);
4949 webFullScreenExitHandler->ExitFullScreen();
4950 return true;
4951 }
4952
SetFullScreenExitHandler(const std::shared_ptr<FullScreenEnterEvent> & fullScreenExitHandler)4953 void WebPattern::SetFullScreenExitHandler(const std::shared_ptr<FullScreenEnterEvent>& fullScreenExitHandler)
4954 {
4955 fullScreenExitHandler_ = fullScreenExitHandler;
4956 }
4957
OnInActive()4958 void WebPattern::OnInActive()
4959 {
4960 TAG_LOGI(AceLogTag::ACE_WEB,
4961 "WebPattern::OnInActive webId:%{public}d, isActive:%{public}d", GetWebId(), isActive_);
4962 if (!isActive_) {
4963 return;
4964 }
4965
4966 CHECK_NULL_VOID(delegate_);
4967 delegate_->OnInactive();
4968 isActive_ = false;
4969 }
4970
OnActive()4971 void WebPattern::OnActive()
4972 {
4973 TAG_LOGI(AceLogTag::ACE_WEB,
4974 "WebPattern::OnActive webId:%{public}d, isActive:%{public}d", GetWebId(), isActive_);
4975 if (isActive_) {
4976 return;
4977 }
4978
4979 CHECK_NULL_VOID(delegate_);
4980 delegate_->OnActive();
4981 isActive_ = true;
4982 }
4983
OnVisibleAreaChange(bool isVisible)4984 void WebPattern::OnVisibleAreaChange(bool isVisible)
4985 {
4986 bool isDialogNested = IsDialogNested();
4987 ACE_SCOPED_TRACE("WebPattern::OnVisibleAreaChange, webId: %d, isVisible: %d", GetWebId(), isVisible);
4988 TAG_LOGI(AceLogTag::ACE_WEB,
4989 "WebPattern::OnVisibleAreaChange webId:%{public}d, isVisible:%{public}d, old_isVisible:%{public}d, "
4990 "isVisibleActiveEnable:%{public}d, isDialogNested:%{public}d, isFocus:%{public}d",
4991 GetWebId(), isVisible, isVisible_, isVisibleActiveEnable_, isDialogNested, isFocus_);
4992 if (isVisible_ == isVisible) {
4993 return;
4994 }
4995
4996 isVisible_ = isVisible;
4997 if (!isVisible_) {
4998 CloseSelectOverlay();
4999 SelectCancel();
5000 DestroyAnalyzerOverlay();
5001 isDragEndMenuShow_ = false;
5002 if (isVisibleActiveEnable_ && (!isDialogNested || !isFocus_)) {
5003 OnInActive();
5004 }
5005 } else {
5006 if (isVisibleActiveEnable_) {
5007 OnActive();
5008 }
5009 }
5010 }
5011
GetDefaultBackgroundColor()5012 Color WebPattern::GetDefaultBackgroundColor()
5013 {
5014 auto darkMode = GetDarkModeValue(webData_ ? (WebDarkMode::Auto) : (WebDarkMode::Off));
5015 if (GetForceDarkAccessValue(false) &&
5016 (darkMode == WebDarkMode::On || ((darkMode == WebDarkMode::Auto) && (GetSystemColor() == Color::BLACK)))) {
5017 return Color::BLACK;
5018 } else {
5019 return Color::WHITE;
5020 }
5021 }
5022
UpdateBackgroundColorRightNow(int32_t color)5023 void WebPattern::UpdateBackgroundColorRightNow(int32_t color)
5024 {
5025 auto host = GetHost();
5026 CHECK_NULL_VOID(host);
5027 auto renderContext = host->GetRenderContext();
5028 CHECK_NULL_VOID(renderContext);
5029 renderContext->UpdateBackgroundColor(Color(static_cast<uint32_t>(color)));
5030 CHECK_NULL_VOID(renderContextForSurface_);
5031 renderContextForSurface_->UpdateBackgroundColor(Color(static_cast<uint32_t>(color)));
5032 }
5033
GetSystemColor() const5034 Color WebPattern::GetSystemColor() const
5035 {
5036 Color color = Color::WHITE;
5037 auto appMgrClient = std::make_shared<AppExecFwk::AppMgrClient>();
5038 CHECK_NULL_RETURN(appMgrClient, color);
5039 if (appMgrClient->ConnectAppMgrService()) {
5040 return color;
5041 }
5042 auto systemConfig = OHOS::AppExecFwk::Configuration();
5043 appMgrClient->GetConfiguration(systemConfig);
5044 auto colorMode = systemConfig.GetItem(OHOS::AAFwk::GlobalConfigurationKey::SYSTEM_COLORMODE);
5045 if (colorMode == OHOS::AppExecFwk::ConfigurationInner::COLOR_MODE_DARK) {
5046 return Color::BLACK;
5047 }
5048 if (colorMode == OHOS::AppExecFwk::ConfigurationInner::COLOR_MODE_LIGHT) {
5049 return Color::WHITE;
5050 }
5051 TAG_LOGW(AceLogTag::ACE_WEB, "no system color mode is found.");
5052 return color;
5053 }
5054
OnNotifyMemoryLevel(int32_t level)5055 void WebPattern::OnNotifyMemoryLevel(int32_t level)
5056 {
5057 if (!isMemoryLevelEnable_) {
5058 return;
5059 }
5060 CHECK_NULL_VOID(delegate_);
5061 delegate_->NotifyMemoryLevel(level);
5062 }
5063
GetWebId()5064 int WebPattern::GetWebId()
5065 {
5066 if (delegate_) {
5067 return delegate_->GetWebId();
5068 }
5069 return -1;
5070 }
5071
HandleScroll(float offset,int32_t source,NestedState state,float velocity)5072 ScrollResult WebPattern::HandleScroll(float offset, int32_t source, NestedState state, float velocity)
5073 {
5074 // If no parent object is specified, the nearest nested scrollable parent is used by default.
5075 return HandleScroll(GetNestedScrollParent(), offset, source, state);
5076 }
5077
HandleScroll(RefPtr<NestableScrollContainer> parent,float offset,int32_t source,NestedState state)5078 ScrollResult WebPattern::HandleScroll(RefPtr<NestableScrollContainer> parent, float offset,
5079 int32_t source, NestedState state)
5080 {
5081 TAG_LOGD(AceLogTag::ACE_WEB,
5082 "WebPattern::HandleScroll scroll direction: %{public}d, find parent component: %{public}d",
5083 expectedScrollAxis_,
5084 (parent != nullptr));
5085 if (parent) {
5086 source = isMouseEvent_ ? SCROLL_FROM_AXIS : source;
5087 return parent->HandleScroll(offset, source, state);
5088 }
5089 return { 0.0f, false };
5090 }
5091
HandleScrollVelocity(float velocity,const RefPtr<NestableScrollContainer> & child)5092 bool WebPattern::HandleScrollVelocity(float velocity, const RefPtr<NestableScrollContainer>& child)
5093 {
5094 // If no parent object is specified, the nearest nested scrollable parent is used by default.
5095 return HandleScrollVelocity(GetNestedScrollParent(), velocity);
5096 }
5097
HandleScrollVelocity(RefPtr<NestableScrollContainer> parent,float velocity)5098 bool WebPattern::HandleScrollVelocity(RefPtr<NestableScrollContainer> parent, float velocity)
5099 {
5100 CHECK_NULL_RETURN(parent, false);
5101 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::HandleScrollVelocity, to parent scroll velocity=%{public}f", velocity);
5102 if (parent->HandleScrollVelocity(velocity)) {
5103 OnParentScrollDragEndRecursive(parent);
5104 return true;
5105 }
5106 return false;
5107 }
5108
OnScrollStartRecursive(WeakPtr<NestableScrollContainer> child,float position,float velocity)5109 void WebPattern::OnScrollStartRecursive(WeakPtr<NestableScrollContainer> child, float position, float velocity)
5110 {
5111 // If only one position value is passed, it will be notified to the nearest nested scrollable parent.
5112 OnScrollStartRecursive(position);
5113 }
5114
OnScrollStartRecursive(float position)5115 void WebPattern::OnScrollStartRecursive(float position)
5116 {
5117 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::OnScrollStartRecursive");
5118 SetIsNestedInterrupt(false);
5119 isFirstFlingScrollVelocity_ = true;
5120 isScrollStarted_ = true;
5121 isDragEnd_ = false;
5122 auto it = parentsMap_.find(expectedScrollAxis_);
5123 CHECK_EQUAL_VOID(it, parentsMap_.end());
5124 auto parent = it->second.Upgrade();
5125 if (parent) {
5126 parent->OnScrollStartRecursive(WeakClaim(this), position);
5127 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::OnScrollStartRecursive parent OnScrollStartRecursive");
5128 }
5129 }
5130
OnAttachToBuilderNode(NodeStatus nodeStatus)5131 void WebPattern::OnAttachToBuilderNode(NodeStatus nodeStatus)
5132 {
5133 TAG_LOGD(AceLogTag::ACE_WEB, "WebPattern::OnAttachToBuilderNode");
5134 if (nodeStatus != NodeStatus::NORMAL_NODE) {
5135 InitInOfflineMode();
5136 }
5137 }
5138
OnScrollEndRecursive(const std::optional<float> & velocity)5139 void WebPattern::OnScrollEndRecursive(const std::optional<float>& velocity)
5140 {
5141 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::OnScrollEndRecursive");
5142 CHECK_EQUAL_VOID(isScrollStarted_, false);
5143 auto it = parentsMap_.find(expectedScrollAxis_);
5144 if (parentsMap_.find(expectedScrollAxis_) != parentsMap_.end()) {
5145 auto parent = it->second.Upgrade();
5146 if (parent) {
5147 OnParentScrollDragEndRecursive(parent);
5148 parent->OnScrollEndRecursive(std::nullopt);
5149 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::OnScrollEndRecursive parent OnScrollEndRecursive");
5150 }
5151 }
5152 isScrollStarted_ = false;
5153 SetIsNestedInterrupt(false);
5154 }
5155
OnOverScrollFlingVelocity(float xVelocity,float yVelocity,bool isFling)5156 void WebPattern::OnOverScrollFlingVelocity(float xVelocity, float yVelocity, bool isFling)
5157 {
5158 float velocity = (expectedScrollAxis_ == Axis::HORIZONTAL) ? xVelocity : yVelocity;
5159 OnOverScrollFlingVelocityHandler(velocity, isFling);
5160 }
5161
OnOverScrollFlingVelocityHandler(float velocity,bool isFling)5162 void WebPattern::OnOverScrollFlingVelocityHandler(float velocity, bool isFling)
5163 {
5164 auto it = parentsMap_.find(expectedScrollAxis_);
5165 CHECK_EQUAL_VOID(it, parentsMap_.end());
5166 auto parent = it->second;
5167 ScrollResult result = { 0.f, true };
5168 auto remain = 0.f;
5169 if (!isFling) {
5170 if (scrollState_) {
5171 if (CheckOverParentScroll(velocity, NestedScrollMode::SELF_FIRST)) {
5172 result = HandleScroll(parent.Upgrade(), -velocity, SCROLL_FROM_UPDATE, NestedState::CHILD_SCROLL);
5173 remain = result.remain;
5174 } else if (CheckOverParentScroll(velocity, NestedScrollMode::PARENT_FIRST)) {
5175 remain = -velocity;
5176 }
5177 if (!NearZero(remain)) {
5178 HandleScroll(parent.Upgrade(), remain, SCROLL_FROM_UPDATE, NestedState::CHILD_OVER_SCROLL);
5179 }
5180 }
5181 } else {
5182 if (CheckParentScroll(velocity, NestedScrollMode::SELF_FIRST)) {
5183 if (isFirstFlingScrollVelocity_) {
5184 HandleScrollVelocity(parent.Upgrade(), velocity);
5185 isFirstFlingScrollVelocity_ = false;
5186 }
5187 }
5188 }
5189 }
5190
OnScrollState(bool scrollState)5191 void WebPattern::OnScrollState(bool scrollState)
5192 {
5193 scrollState_ = scrollState;
5194 if (!scrollState) {
5195 OnScrollEndRecursive(std::nullopt);
5196 }
5197 }
5198
OnScrollStart(const float x,const float y)5199 void WebPattern::OnScrollStart(const float x, const float y)
5200 {
5201 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::OnScrollStart x=%{public}f, y=%{public}f", x, y);
5202 scrollState_ = true;
5203 GetParentAxis();
5204 expectedScrollAxis_ =(abs(x) > abs(y) ? Axis::HORIZONTAL : Axis::VERTICAL);
5205 OnScrollStartRecursive(0.0);
5206 if (imageAnalyzerManager_) {
5207 imageAnalyzerManager_->UpdateOverlayStatus(
5208 false,
5209 0,
5210 0,
5211 0,
5212 0);
5213 }
5214 }
5215
SetLayoutMode(WebLayoutMode mode)5216 void WebPattern::SetLayoutMode(WebLayoutMode mode)
5217 {
5218 if (layoutMode_ == mode) {
5219 return;
5220 }
5221 layoutMode_ = mode;
5222 TAG_LOGI(AceLogTag::ACE_WEB, "layoutMode is: %{public}d.", layoutMode_);
5223 OnZoomAccessEnabledUpdate(GetZoomAccessEnabledValue(true));
5224 if (delegate_) {
5225 delegate_->UpdateLayoutMode(mode);
5226 }
5227 isLayoutModeChanged_ = true;
5228 auto frameNode = GetHost();
5229 CHECK_NULL_VOID(frameNode);
5230 frameNode->MarkDirtyNode(PROPERTY_UPDATE_LAYOUT | PROPERTY_UPDATE_MEASURE | PROPERTY_UPDATE_RENDER);
5231 }
5232
SetRenderMode(RenderMode renderMode)5233 void WebPattern::SetRenderMode(RenderMode renderMode)
5234 {
5235 if (isRenderModeInit_) {
5236 TAG_LOGI(AceLogTag::ACE_WEB, "renderMode not allow to change.");
5237 return;
5238 }
5239 renderMode_ = renderMode;
5240 TAG_LOGI(AceLogTag::ACE_WEB, "renderMode is %{public}d", renderMode_);
5241 isRenderModeInit_ = true;
5242 }
5243
GetParentAxis()5244 void WebPattern::GetParentAxis()
5245 {
5246 auto parent = GetNestedScrollParent();
5247 if (parent) {
5248 axis_ = parent->GetAxis();
5249 parentsMap_ = { { axis_, parent } };
5250 auto oppositeParent = SearchParent(axis_ == Axis::HORIZONTAL ? Axis::VERTICAL : Axis::HORIZONTAL);
5251 if (oppositeParent) {
5252 parentsMap_.emplace(oppositeParent->GetAxis(), oppositeParent);
5253 }
5254 } else {
5255 auto verticalParent = SearchParent(Axis::VERTICAL);
5256 auto horizontalParent = SearchParent(Axis::HORIZONTAL);
5257 if (verticalParent) {
5258 parentsMap_.emplace(verticalParent->GetAxis(), verticalParent);
5259 }
5260 if (horizontalParent) {
5261 parentsMap_.emplace(horizontalParent->GetAxis(), horizontalParent);
5262 }
5263 }
5264 }
5265
SearchParent()5266 RefPtr<NestableScrollContainer> WebPattern::SearchParent()
5267 {
5268 return SearchParent(Axis::NONE);
5269 }
5270
SearchParent(Axis scrollAxis)5271 RefPtr<NestableScrollContainer> WebPattern::SearchParent(Axis scrollAxis)
5272 {
5273 auto host = GetHost();
5274 CHECK_NULL_RETURN(host, nullptr);
5275 for (auto parent = host->GetParent(); parent != nullptr; parent = parent->GetParent()) {
5276 RefPtr<FrameNode> frameNode = AceType::DynamicCast<FrameNode>(parent);
5277 if (!frameNode) {
5278 continue;
5279 }
5280 auto pattern = frameNode->GetPattern<NestableScrollContainer>();
5281 if (!pattern ||
5282 (!AceApplicationInfo::GetInstance().GreatOrEqualTargetAPIVersion(PlatformVersion::VERSION_TWELVE) &&
5283 InstanceOf<RefreshPattern>(pattern))) {
5284 continue;
5285 }
5286 if (scrollAxis == Axis::NONE || scrollAxis == pattern->GetAxis()) {
5287 return pattern;
5288 }
5289 }
5290 return nullptr;
5291 }
5292
SetNestedScrollExt(const NestedScrollOptionsExt & nestedScroll)5293 void WebPattern::SetNestedScrollExt(const NestedScrollOptionsExt &nestedScroll)
5294 {
5295 NestedScrollOptions nestedOpt = {
5296 .forward = NestedScrollMode::SELF_FIRST,
5297 .backward = NestedScrollMode::SELF_FIRST,
5298 };
5299 if (nestedScroll.scrollUp == nestedScroll.scrollLeft) {
5300 nestedOpt.backward = nestedScroll.scrollUp;
5301 }
5302 if (nestedScroll.scrollDown == nestedScroll.scrollRight) {
5303 nestedOpt.forward = nestedScroll.scrollDown;
5304 }
5305 auto pattern = ViewStackProcessor::GetInstance()->GetMainFrameNodePattern<NestableScrollContainer>();
5306 if (pattern) {
5307 pattern->SetNestedScroll(nestedOpt);
5308 }
5309 TAG_LOGI(
5310 AceLogTag::ACE_WEB, "SetNestedScrollExt nestedScroll: %{public}s", nestedScroll.ToString().c_str());
5311 nestedScroll_ = nestedScroll;
5312 }
5313
IsDialogNested()5314 bool WebPattern::IsDialogNested()
5315 {
5316 auto host = GetHost();
5317 CHECK_NULL_RETURN(host, false);
5318 for (auto parent = host->GetParent(); parent != nullptr; parent = parent->GetParent()) {
5319 RefPtr<FrameNode> frameNode = AceType::DynamicCast<FrameNode>(parent);
5320 if (!frameNode) {
5321 continue;
5322 }
5323 if (frameNode->GetPattern<DialogPattern>()) {
5324 return true;
5325 }
5326 }
5327 return false;
5328 }
5329
OnProgressChanged(int param)5330 void WebPattern::OnProgressChanged(int param)
5331 {
5332 progressParam_ = param;
5333 }
5334
OnRootLayerChanged(int width,int height)5335 void WebPattern::OnRootLayerChanged(int width, int height)
5336 {
5337 if ((rootLayerWidth_ == width) && (rootLayerHeight_ == height)) {
5338 return;
5339 }
5340 TAG_LOGI(AceLogTag::ACE_WEB, "OnRootLayerChanged width : %{public}d, height : %{public}d", width, height);
5341 rootLayerWidth_ = width;
5342 rootLayerHeight_ = height;
5343 if (layoutMode_ != WebLayoutMode::FIT_CONTENT) {
5344 return;
5345 }
5346 rootLayerChangeSize_ = Size(width, height);
5347 if (GetPendingSizeStatus()) {
5348 return;
5349 }
5350 ReleaseResizeHold();
5351 }
5352
ReleaseResizeHold()5353 void WebPattern::ReleaseResizeHold()
5354 {
5355 if (layoutMode_ != WebLayoutMode::FIT_CONTENT) {
5356 return;
5357 }
5358 drawSize_.SetSize(rootLayerChangeSize_);
5359 auto frameNode = GetHost();
5360 CHECK_NULL_VOID(frameNode);
5361 frameNode->MarkDirtyNode(PROPERTY_UPDATE_LAYOUT | PROPERTY_UPDATE_MEASURE | PROPERTY_UPDATE_RENDER);
5362 }
5363
FilterScrollEvent(const float x,const float y,const float xVelocity,const float yVelocity)5364 bool WebPattern::FilterScrollEvent(const float x, const float y, const float xVelocity, const float yVelocity)
5365 {
5366 float offset = expectedScrollAxis_ == Axis::HORIZONTAL ? x : y;
5367 float velocity = expectedScrollAxis_ == Axis::HORIZONTAL ? xVelocity : yVelocity;
5368 bool isConsumed = offset != 0 ? FilterScrollEventHandleOffset(offset) : FilterScrollEventHandlevVlocity(velocity);
5369 return isConsumed;
5370 }
5371
FilterScrollEventHandleOffset(float offset)5372 bool WebPattern::FilterScrollEventHandleOffset(float offset)
5373 {
5374 auto it = parentsMap_.find(expectedScrollAxis_);
5375 CHECK_EQUAL_RETURN(it, parentsMap_.end(), false);
5376 auto parent = it->second;
5377 if (parent.Upgrade() && !NearZero(offset)) {
5378 auto res = HandleScroll(parent.Upgrade(), offset, SCROLL_FROM_UPDATE, NestedState::CHILD_CHECK_OVER_SCROLL);
5379 if (NearZero(res.remain)) {
5380 return true;
5381 }
5382 offset = res.remain;
5383 }
5384 if (CheckParentScroll(offset, NestedScrollMode::PARENT_FIRST)) {
5385 auto result = HandleScroll(parent.Upgrade(), offset, SCROLL_FROM_UPDATE, NestedState::CHILD_SCROLL);
5386 CHECK_EQUAL_RETURN(isParentReachEdge_ && result.reachEdge, true, false);
5387 isParentReachEdge_ = result.reachEdge;
5388 CHECK_NULL_RETURN(delegate_, false);
5389 expectedScrollAxis_ == Axis::HORIZONTAL ? delegate_->ScrollByRefScreen(-result.remain, 0)
5390 : delegate_->ScrollByRefScreen(0, -result.remain);
5391 return true;
5392 } else if (CheckParentScroll(offset, NestedScrollMode::PARALLEL)) {
5393 HandleScroll(parent.Upgrade(), offset, SCROLL_FROM_UPDATE, NestedState::CHILD_SCROLL);
5394 } else if (CheckParentScroll(offset, NestedScrollMode::SELF_FIRST)) {
5395 if (parent.Upgrade() && parent.Upgrade()->NestedScrollOutOfBoundary()) {
5396 HandleScroll(parent.Upgrade(), offset, SCROLL_FROM_UPDATE, NestedState::CHILD_OVER_SCROLL);
5397 return true;
5398 }
5399 }
5400 return false;
5401 }
5402
CheckParentScroll(const float & directValue,const NestedScrollMode & scrollMode)5403 bool WebPattern::CheckParentScroll(const float &directValue, const NestedScrollMode &scrollMode)
5404 {
5405 auto nestedScroll = GetNestedScrollExt();
5406 return (directValue > 0 && nestedScroll.scrollUp == scrollMode &&
5407 expectedScrollAxis_ != Axis::HORIZONTAL) ||
5408 (directValue > 0 && nestedScroll.scrollLeft == scrollMode &&
5409 expectedScrollAxis_ == Axis::HORIZONTAL) ||
5410 (directValue < 0 && nestedScroll.scrollDown == scrollMode &&
5411 expectedScrollAxis_ != Axis::HORIZONTAL) ||
5412 (directValue < 0 && nestedScroll.scrollRight == scrollMode &&
5413 expectedScrollAxis_ == Axis::HORIZONTAL);
5414 }
5415
CheckOverParentScroll(const float & directValue,const NestedScrollMode & scrollMode)5416 bool WebPattern::CheckOverParentScroll(const float &directValue, const NestedScrollMode &scrollMode)
5417 {
5418 auto nestedScroll = GetNestedScrollExt();
5419 return (directValue < 0 && nestedScroll.scrollUp == scrollMode &&
5420 expectedScrollAxis_ != Axis::HORIZONTAL) ||
5421 (directValue < 0 && nestedScroll.scrollLeft == scrollMode &&
5422 expectedScrollAxis_ == Axis::HORIZONTAL) ||
5423 (directValue > 0 && nestedScroll.scrollDown == scrollMode &&
5424 expectedScrollAxis_ != Axis::HORIZONTAL) ||
5425 (directValue > 0 && nestedScroll.scrollRight == scrollMode &&
5426 expectedScrollAxis_ == Axis::HORIZONTAL);
5427 }
5428
FilterScrollEventHandlevVlocity(const float velocity)5429 bool WebPattern::FilterScrollEventHandlevVlocity(const float velocity)
5430 {
5431 auto it = parentsMap_.find(expectedScrollAxis_);
5432 CHECK_EQUAL_RETURN(it, parentsMap_.end(), false);
5433 auto parent = it->second;
5434 if (parent.Upgrade() && parent.Upgrade()->NestedScrollOutOfBoundary()) {
5435 return HandleScrollVelocity(parent.Upgrade(), velocity);
5436 }
5437 if (CheckParentScroll(velocity, NestedScrollMode::PARENT_FIRST)) {
5438 if (isParentReachEdge_) {
5439 return false;
5440 }
5441 return HandleScrollVelocity(parent.Upgrade(), velocity);
5442 } else if (CheckParentScroll(velocity, NestedScrollMode::PARALLEL)) {
5443 HandleScrollVelocity(parent.Upgrade(), velocity);
5444 }
5445 return false;
5446 }
5447
IsDefaultFocusNodeExist()5448 bool WebPattern::IsDefaultFocusNodeExist()
5449 {
5450 auto pipeline = PipelineContext::GetCurrentContext();
5451 CHECK_NULL_RETURN(pipeline, false);
5452 auto focusManager = pipeline->GetFocusManager();
5453 CHECK_NULL_RETURN(focusManager, false);
5454 auto focusView = focusManager->GetLastFocusView().Upgrade();
5455 CHECK_NULL_RETURN(focusView, false);
5456 auto focusHub = focusView->GetFocusHub();
5457 CHECK_NULL_RETURN(focusHub, false);
5458 bool result = focusHub->GetChildFocusNodeByType();
5459 return result;
5460 }
5461
InitSlideUpdateListener()5462 void WebPattern::InitSlideUpdateListener()
5463 {
5464 auto host = GetHost();
5465 CHECK_NULL_VOID(host);
5466 for (auto parent = host->GetParent(); parent != nullptr; parent = parent->GetParent()) {
5467 bool hasTargetParent =
5468 std::find(SYNC_RENDER_SLIDE.begin(), SYNC_RENDER_SLIDE.end(), parent->GetTag()) == SYNC_RENDER_SLIDE.end();
5469 if (hasTargetParent) {
5470 continue;
5471 }
5472 RefPtr<FrameNode> frameNode = AceType::DynamicCast<FrameNode>(parent);
5473 CHECK_NULL_VOID(frameNode);
5474 if (parent->GetTag() == V2::LIST_ETS_TAG) {
5475 auto pattern = frameNode->GetPattern<ListPattern>();
5476 CHECK_NULL_VOID(pattern);
5477 syncAxis_ = pattern->GetAxis();
5478 } else {
5479 auto pattern = frameNode->GetPattern<ScrollPattern>();
5480 CHECK_NULL_VOID(pattern);
5481 syncAxis_ = pattern->GetAxis();
5482 }
5483 CHECK_NULL_VOID(renderSurface_);
5484 renderSurface_->SetWebSlideAxis(syncAxis_);
5485 }
5486 }
5487
UpdateSlideOffset()5488 void WebPattern::UpdateSlideOffset()
5489 {
5490 switch (syncAxis_) {
5491 case Axis::HORIZONTAL:
5492 CalculateHorizontalDrawRect();
5493 break;
5494 case Axis::VERTICAL:
5495 CalculateVerticalDrawRect();
5496 break;
5497 default :
5498 break;
5499 }
5500 }
5501
CalculateHorizontalDrawRect()5502 void WebPattern::CalculateHorizontalDrawRect()
5503 {
5504 fitContentOffset_ = OffsetF(GetCoordinatePoint()->GetX(), GetCoordinatePoint()->GetY());
5505 CHECK_NULL_VOID(renderSurface_);
5506 renderSurface_->SetWebOffset(fitContentOffset_.GetX());
5507 if (fitContentOffset_.GetX() >= 0) {
5508 if (isNeedReDrawRect_) {
5509 SetDrawRect(0, 0, ADJUST_WEB_DRAW_LENGTH + ADJUST_WEB_DRAW_LENGTH, drawRectHeight_);
5510 }
5511 isNeedReDrawRect_ = false;
5512 return;
5513 }
5514
5515 int32_t stepGear = (-fitContentOffset_.GetX()) / ADJUST_WEB_DRAW_LENGTH;
5516 int32_t width = ADJUST_WEB_DRAW_LENGTH * 2 + stepGear;
5517 int32_t height = std::min(static_cast<int32_t>(drawSize_.Height()), FIT_CONTENT_LIMIT_LENGTH);
5518 int32_t x = ADJUST_WEB_DRAW_LENGTH * stepGear;
5519 int32_t y = 0;
5520 renderSurface_->SetWebMessage({ x, 0 });
5521 TAG_LOGD(AceLogTag::ACE_WEB, "SetDrawRect x : %{public}d, y : %{public}d, width : %{public}d, height : %{public}d",
5522 x, y, width, height);
5523 SetDrawRect(x, y, width, height);
5524 isNeedReDrawRect_ = true;
5525 }
5526
CalculateVerticalDrawRect()5527 void WebPattern::CalculateVerticalDrawRect()
5528 {
5529 fitContentOffset_ = OffsetF(GetCoordinatePoint()->GetX(), GetCoordinatePoint()->GetY());
5530 CHECK_NULL_VOID(renderSurface_);
5531 renderSurface_->SetWebOffset(fitContentOffset_.GetY());
5532 if (fitContentOffset_.GetY() >= 0) {
5533 if (isNeedReDrawRect_) {
5534 SetDrawRect(0, 0, drawRectWidth_, ADJUST_WEB_DRAW_LENGTH + ADJUST_WEB_DRAW_LENGTH);
5535 }
5536 isNeedReDrawRect_ = false;
5537 return;
5538 }
5539
5540 int32_t stepGear = (-fitContentOffset_.GetY()) / ADJUST_WEB_DRAW_LENGTH;
5541 int32_t width = std::min(static_cast<int32_t>(drawSize_.Width()), FIT_CONTENT_LIMIT_LENGTH);
5542 int32_t height = ADJUST_WEB_DRAW_LENGTH * 2 + stepGear;
5543 int32_t x = 0;
5544 int32_t y = ADJUST_WEB_DRAW_LENGTH * stepGear;
5545 renderSurface_->SetWebMessage({ 0, y });
5546 TAG_LOGD(AceLogTag::ACE_WEB, "SetDrawRect x : %{public}d, y : %{public}d, width : %{public}d, height : %{public}d",
5547 x, y, width, height);
5548 SetDrawRect(x, y, width, height);
5549 isNeedReDrawRect_ = true;
5550 }
5551
PostTaskToUI(const std::function<void ()> && task,const std::string & name) const5552 void WebPattern::PostTaskToUI(const std::function<void()>&& task, const std::string& name) const
5553 {
5554 CHECK_NULL_VOID(task);
5555 auto container = Container::Current();
5556 CHECK_NULL_VOID(container);
5557 auto pipelineContext = AccessibilityManager::DynamicCast<NG::PipelineContext>(container->GetPipelineContext());
5558 CHECK_NULL_VOID(pipelineContext);
5559 auto taskExecutor = pipelineContext->GetTaskExecutor();
5560 CHECK_NULL_VOID(taskExecutor);
5561 taskExecutor->PostTask(task, TaskExecutor::TaskType::UI, name);
5562 }
5563
SetDrawRect(int32_t x,int32_t y,int32_t width,int32_t height)5564 void WebPattern::SetDrawRect(int32_t x, int32_t y, int32_t width, int32_t height)
5565 {
5566 if ((drawRectWidth_ == width) && (drawRectHeight_ == height)) {
5567 return;
5568 }
5569 drawRectWidth_ = width;
5570 drawRectHeight_ = height;
5571 CHECK_NULL_VOID(delegate_);
5572 delegate_->SetDrawRect(x, y, width, height);
5573 }
5574
GetPendingSizeStatus()5575 bool WebPattern::GetPendingSizeStatus()
5576 {
5577 if (delegate_) {
5578 return delegate_->GetPendingSizeStatus();
5579 }
5580 return false;
5581 }
5582
CreateNodePaintMethod()5583 RefPtr<NodePaintMethod> WebPattern::CreateNodePaintMethod()
5584 {
5585 auto paint = MakeRefPtr<WebPaintMethod>(renderSurface_);
5586 return paint;
5587 }
5588
JavaScriptOnDocumentStart(const ScriptItems & scriptItems)5589 void WebPattern::JavaScriptOnDocumentStart(const ScriptItems& scriptItems)
5590 {
5591 onDocumentStartScriptItems_ = std::make_optional<ScriptItems>(scriptItems);
5592 onDocumentStartScriptItemsByOrder_ = std::nullopt;
5593 if (delegate_) {
5594 UpdateJavaScriptOnDocumentStart();
5595 delegate_->JavaScriptOnDocumentStart();
5596 }
5597 }
5598
JavaScriptOnDocumentStartByOrder(const ScriptItems & scriptItems,const ScriptItemsByOrder & scriptItemsByOrder)5599 void WebPattern::JavaScriptOnDocumentStartByOrder(const ScriptItems& scriptItems,
5600 const ScriptItemsByOrder& scriptItemsByOrder)
5601 {
5602 onDocumentStartScriptItems_ = std::make_optional<ScriptItems>(scriptItems);
5603 onDocumentStartScriptItemsByOrder_ = std::make_optional<ScriptItemsByOrder>(scriptItemsByOrder);
5604 if (delegate_) {
5605 delegate_->JavaScriptOnDocumentStartByOrder();
5606 }
5607 }
5608
JavaScriptOnDocumentEndByOrder(const ScriptItems & scriptItems,const ScriptItemsByOrder & scriptItemsByOrder)5609 void WebPattern::JavaScriptOnDocumentEndByOrder(const ScriptItems& scriptItems,
5610 const ScriptItemsByOrder& scriptItemsByOrder)
5611 {
5612 onDocumentEndScriptItems_ = std::make_optional<ScriptItems>(scriptItems);
5613 onDocumentEndScriptItemsByOrder_ = std::make_optional<ScriptItemsByOrder>(scriptItemsByOrder);
5614 if (delegate_) {
5615 UpdateJavaScriptOnDocumentEndByOrder();
5616 delegate_->JavaScriptOnDocumentEndByOrder();
5617 }
5618 }
5619
JavaScriptOnHeadReadyByOrder(const ScriptItems & scriptItems,const ScriptItemsByOrder & scriptItemsByOrder)5620 void WebPattern::JavaScriptOnHeadReadyByOrder(const ScriptItems& scriptItems,
5621 const ScriptItemsByOrder& scriptItemsByOrder)
5622 {
5623 onHeadReadyScriptItems_ = std::make_optional<ScriptItems>(scriptItems);
5624 onHeadReadyScriptItemsByOrder_ = std::make_optional<ScriptItemsByOrder>(scriptItemsByOrder);
5625 if (delegate_) {
5626 UpdateJavaScriptOnHeadReadyByOrder();
5627 delegate_->JavaScriptOnHeadReadyByOrder();
5628 }
5629 }
5630
JavaScriptOnDocumentEnd(const ScriptItems & scriptItems)5631 void WebPattern::JavaScriptOnDocumentEnd(const ScriptItems& scriptItems)
5632 {
5633 onDocumentEndScriptItems_ = std::make_optional<ScriptItems>(scriptItems);
5634 onDocumentEndScriptItemsByOrder_ = std::nullopt;
5635 if (delegate_) {
5636 UpdateJavaScriptOnDocumentEnd();
5637 delegate_->JavaScriptOnDocumentEnd();
5638 }
5639 }
5640
UpdateJavaScriptOnDocumentStart()5641 void WebPattern::UpdateJavaScriptOnDocumentStart()
5642 {
5643 if (delegate_ && onDocumentStartScriptItems_.has_value() && !onDocumentStartScriptItemsByOrder_.has_value()) {
5644 delegate_->SetJavaScriptItems(onDocumentStartScriptItems_.value(), ScriptItemType::DOCUMENT_START);
5645 onDocumentStartScriptItems_ = std::nullopt;
5646 }
5647 }
5648
UpdateJavaScriptOnDocumentStartByOrder()5649 void WebPattern::UpdateJavaScriptOnDocumentStartByOrder()
5650 {
5651 if (delegate_ && onDocumentStartScriptItems_.has_value() && onDocumentStartScriptItemsByOrder_.has_value()) {
5652 delegate_->SetJavaScriptItemsByOrder(onDocumentStartScriptItems_.value(), ScriptItemType::DOCUMENT_START,
5653 onDocumentStartScriptItemsByOrder_.value());
5654 onDocumentStartScriptItems_ = std::nullopt;
5655 onDocumentStartScriptItemsByOrder_ = std::nullopt;
5656 }
5657 }
5658
UpdateJavaScriptOnDocumentEndByOrder()5659 void WebPattern::UpdateJavaScriptOnDocumentEndByOrder()
5660 {
5661 if (delegate_ && onDocumentEndScriptItems_.has_value() && onDocumentEndScriptItemsByOrder_.has_value()) {
5662 delegate_->SetJavaScriptItemsByOrder(onDocumentEndScriptItems_.value(), ScriptItemType::DOCUMENT_END,
5663 onDocumentEndScriptItemsByOrder_.value());
5664 onDocumentEndScriptItems_ = std::nullopt;
5665 onDocumentEndScriptItemsByOrder_ = std::nullopt;
5666 }
5667 }
5668
UpdateJavaScriptOnHeadReadyByOrder()5669 void WebPattern::UpdateJavaScriptOnHeadReadyByOrder()
5670 {
5671 if (delegate_ && onHeadReadyScriptItems_.has_value() && onHeadReadyScriptItemsByOrder_.has_value()) {
5672 delegate_->SetJavaScriptItemsByOrder(onHeadReadyScriptItems_.value(), ScriptItemType::DOCUMENT_HEAD_READY,
5673 onHeadReadyScriptItemsByOrder_.value());
5674 onHeadReadyScriptItems_ = std::nullopt;
5675 onHeadReadyScriptItemsByOrder_ = std::nullopt;
5676 }
5677 }
5678
UpdateJavaScriptOnDocumentEnd()5679 void WebPattern::UpdateJavaScriptOnDocumentEnd()
5680 {
5681 CHECK_NULL_VOID(delegate_);
5682 if (onDocumentEndScriptItems_.has_value() && !onDocumentEndScriptItemsByOrder_.has_value()) {
5683 delegate_->SetJavaScriptItems(onDocumentEndScriptItems_.value(), ScriptItemType::DOCUMENT_END);
5684 onDocumentEndScriptItems_ = std::nullopt;
5685 }
5686 }
5687
GetAccessibilityNodeById(int64_t accessibilityId)5688 std::shared_ptr<NWeb::NWebAccessibilityNodeInfo> WebPattern::GetAccessibilityNodeById(int64_t accessibilityId)
5689 {
5690 if (!accessibilityState_) {
5691 return nullptr;
5692 }
5693 CHECK_NULL_RETURN(delegate_, nullptr);
5694 return delegate_->GetAccessibilityNodeInfoById(accessibilityId);
5695 }
5696
GetFocusedAccessibilityNode(int64_t accessibilityId,bool isAccessibilityFocus)5697 std::shared_ptr<NWeb::NWebAccessibilityNodeInfo> WebPattern::GetFocusedAccessibilityNode(
5698 int64_t accessibilityId, bool isAccessibilityFocus)
5699 {
5700 if (!accessibilityState_) {
5701 return nullptr;
5702 }
5703 CHECK_NULL_RETURN(delegate_, nullptr);
5704 return delegate_->GetFocusedAccessibilityNodeInfo(accessibilityId, isAccessibilityFocus);
5705 }
5706
5707
GetAccessibilityNodeByFocusMove(int64_t accessibilityId,int32_t direction)5708 std::shared_ptr<NWeb::NWebAccessibilityNodeInfo> WebPattern::GetAccessibilityNodeByFocusMove(int64_t accessibilityId,
5709 int32_t direction)
5710 {
5711 if (!accessibilityState_) {
5712 return nullptr;
5713 }
5714 CHECK_NULL_RETURN(delegate_, nullptr);
5715 return delegate_->GetAccessibilityNodeInfoByFocusMove(accessibilityId, direction);
5716 }
5717
ExecuteAction(int64_t accessibilityId,AceAction action,const std::map<std::string,std::string> & actionArguments) const5718 bool WebPattern::ExecuteAction(int64_t accessibilityId, AceAction action,
5719 const std::map<std::string, std::string>& actionArguments) const
5720 {
5721 CHECK_NULL_RETURN(delegate_, false);
5722 if (!accessibilityState_) {
5723 return false;
5724 }
5725 return delegate_->ExecuteAction(accessibilityId, action, actionArguments);
5726 }
5727
SetAccessibilityState(bool state,bool isDelayed)5728 void WebPattern::SetAccessibilityState(bool state, bool isDelayed)
5729 {
5730 CHECK_NULL_VOID(delegate_);
5731 focusedAccessibilityId_ = -1;
5732 if (!state) {
5733 if (!accessibilityState_ || inspectorAccessibilityEnable_ || textBlurAccessibilityEnable_) {
5734 return;
5735 }
5736 accessibilityState_ = state;
5737 delegate_->SetAccessibilityState(state, isDelayed);
5738 return;
5739 }
5740
5741 if (accessibilityState_ != state) {
5742 accessibilityState_ = state;
5743 delegate_->SetAccessibilityState(state, isDelayed);
5744 }
5745 }
5746
JsonNodePutDefaultValue(std::unique_ptr<OHOS::Ace::JsonValue> & jsonNode,WebAccessibilityType key,bool value)5747 void WebPattern::JsonNodePutDefaultValue(std::unique_ptr<OHOS::Ace::JsonValue>& jsonNode,
5748 WebAccessibilityType key, bool value)
5749 {
5750 if (!value) {
5751 return;
5752 }
5753 jsonNode->Put(EnumTypeToString(key).c_str(), 1);
5754 }
5755
JsonNodePutDefaultValue(std::unique_ptr<OHOS::Ace::JsonValue> & jsonNode,WebAccessibilityType key,std::string value)5756 void WebPattern::JsonNodePutDefaultValue(std::unique_ptr<OHOS::Ace::JsonValue>& jsonNode,
5757 WebAccessibilityType key, std::string value)
5758 {
5759 if (value.empty()) {
5760 return;
5761 }
5762 jsonNode->Put(EnumTypeToString(key).c_str(), value.c_str());
5763 }
5764
JsonNodePutDefaultValue(std::unique_ptr<OHOS::Ace::JsonValue> & jsonNode,WebAccessibilityType key,int32_t value,int32_t defaultValue)5765 void WebPattern::JsonNodePutDefaultValue(std::unique_ptr<OHOS::Ace::JsonValue>& jsonNode,
5766 WebAccessibilityType key, int32_t value, int32_t defaultValue)
5767 {
5768 if (value == defaultValue) {
5769 return;
5770 }
5771 jsonNode->Put(EnumTypeToString(key).c_str(), value);
5772 }
5773
EnumTypeToString(WebAccessibilityType type)5774 std::string WebPattern::EnumTypeToString(WebAccessibilityType type)
5775 {
5776 return std::to_string(static_cast<int>(type));
5777 }
5778
VectorIntToString(std::vector<int64_t> && vec)5779 std::string WebPattern::VectorIntToString(std::vector<int64_t>&& vec)
5780 {
5781 std::string vecStr;
5782 uint32_t vecLen = vec.size();
5783 if (vecLen < 1) {
5784 return vecStr;
5785 }
5786 for (uint32_t i = 0; i < vecLen - 1; ++i) {
5787 vecStr += std::to_string(vec[i]) + " ";
5788 }
5789 return vecStr + std::to_string(vec[vecLen - 1]);
5790 }
5791
WebNodeInfoToJsonValue(std::shared_ptr<OHOS::Ace::JsonValue> & jsonNodeArray,std::shared_ptr<OHOS::NWeb::NWebAccessibilityNodeInfo> webNodeInfo,std::string & nodeTag)5792 void WebPattern::WebNodeInfoToJsonValue(std::shared_ptr<OHOS::Ace::JsonValue>& jsonNodeArray,
5793 std::shared_ptr<OHOS::NWeb::NWebAccessibilityNodeInfo> webNodeInfo, std::string& nodeTag)
5794 {
5795 auto jsonNode = JsonUtil::Create(true);
5796 jsonNode->Put(WEB_NODE_URL, delegate_ ? delegate_->GetUrl().c_str() : "");
5797 jsonNode->Put(EnumTypeToString(WebAccessibilityType::ID).c_str(), webNodeInfo->GetAccessibilityId());
5798 if (webNodeInfo->GetSelectionEnd() != 0) {
5799 jsonNode->Put(EnumTypeToString(WebAccessibilityType::SEL_START).c_str(), webNodeInfo->GetSelectionStart());
5800 jsonNode->Put(EnumTypeToString(WebAccessibilityType::SEL_END).c_str(), webNodeInfo->GetSelectionEnd());
5801 }
5802 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::INPUT_TYPE, webNodeInfo->GetInputType(), -1);
5803 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::LIVE_REGION, webNodeInfo->GetLiveRegion(), -1);
5804 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::HINT, webNodeInfo->GetHint());
5805 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::CONTENT, webNodeInfo->GetContent());
5806 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::ERROR, webNodeInfo->GetError());
5807 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::CHILD_IDS, VectorIntToString(webNodeInfo->GetChildIds()));
5808 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::PARENT_ID, webNodeInfo->GetParentId(), -1);
5809 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::GRID_ROWS, webNodeInfo->GetGridRows(), -1);
5810 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::GRID_COLS, webNodeInfo->GetGridColumns(), -1);
5811 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::GRID_SEL_MODE, webNodeInfo->GetGridSelectedMode(), -1);
5812 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::GRID_ITEM_ROW, webNodeInfo->GetGridItemRow(), -1);
5813 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::GRID_ITEM_ROW_SPAN, webNodeInfo->GetGridItemRowSpan(), -1);
5814 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::GRID_ITEM_COL, webNodeInfo->GetGridItemColumn(), -1);
5815 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::GRID_ITEM_COL_SPAN,
5816 webNodeInfo->GetGridItemColumnSpan(), -1);
5817 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::PAGE_ID, webNodeInfo->GetPageId(), -1);
5818
5819 if (webNodeInfo->GetRectWidth() != 0 || webNodeInfo->GetRectHeight() != 0) {
5820 jsonNode->Put(EnumTypeToString(WebAccessibilityType::RECTX).c_str(), webNodeInfo->GetRectX());
5821 jsonNode->Put(EnumTypeToString(WebAccessibilityType::RECTY).c_str(), webNodeInfo->GetRectY());
5822 jsonNode->Put(EnumTypeToString(WebAccessibilityType::RECT_WIDTH).c_str(), webNodeInfo->GetRectWidth());
5823 jsonNode->Put(EnumTypeToString(WebAccessibilityType::RECT_HEIGHT).c_str(), webNodeInfo->GetRectHeight());
5824 }
5825
5826 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::HEADING, webNodeInfo->GetIsHeading());
5827 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::CHECKED, webNodeInfo->GetIsChecked());
5828 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::EDITABLE, webNodeInfo->GetIsEditable());
5829 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::ENABLED, webNodeInfo->GetIsEnabled());
5830 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::FOCUSED, webNodeInfo->GetIsFocused());
5831 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::SELECTED, webNodeInfo->GetIsSelected());
5832 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::CHECKABLE, webNodeInfo->GetIsCheckable());
5833 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::CLICKABLE, webNodeInfo->GetIsClickable());
5834 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::FOCUSABLE, webNodeInfo->GetIsFocusable());
5835 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::SCROLLABLE, webNodeInfo->GetIsScrollable());
5836 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::PASSWORD, webNodeInfo->GetIsPassword());
5837 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::VISIBLE, webNodeInfo->GetIsVisible());
5838 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::PLURAL_LINE, webNodeInfo->GetIsPluralLineSupported());
5839 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::POPUP, webNodeInfo->GetIsPopupSupported());
5840 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::DELETABLE, webNodeInfo->GetIsDeletable());
5841 JsonNodePutDefaultValue(jsonNode, WebAccessibilityType::FOCUS, webNodeInfo->GetIsAccessibilityFocus());
5842 jsonNodeArray->PutRef(nodeTag.c_str(), std::move(jsonNode));
5843 }
5844
GetWebAllInfosImpl(WebNodeInfoCallback cb,int32_t webId)5845 void WebPattern::GetWebAllInfosImpl(WebNodeInfoCallback cb, int32_t webId)
5846 {
5847 std::shared_ptr<OHOS::NWeb::NWebAccessibilityNodeInfo> rootWebNode;
5848 if (delegate_) {
5849 rootWebNode = delegate_->GetAccessibilityNodeInfoById(-1);
5850 }
5851 CHECK_NULL_VOID(rootWebNode);
5852
5853 auto jsonNodeArray = static_cast<std::shared_ptr<JsonValue> >(JsonUtil::Create(true));
5854 std::queue<uint64_t> que;
5855 for (auto id: rootWebNode->GetChildIds()) {
5856 que.push(id);
5857 }
5858 int nodeCount = 0;
5859 while (!que.empty()) {
5860 uint64_t tmp = que.front();
5861 que.pop();
5862 auto webNodeInfo = delegate_->GetAccessibilityNodeInfoById(tmp);
5863 CHECK_NULL_VOID(webNodeInfo);
5864 auto componentType = webNodeInfo->GetComponentType();
5865 if (componentType.compare(ACCESSIBILITY_GENERIC_CONTAINER) != 0
5866 && componentType.compare(ACCESSIBILITY_PARAGRAPH) != 0
5867 && componentType.compare(ACCESSIBILITY_IMAGE) != 0) {
5868 WebNodeInfoToJsonValue(jsonNodeArray, webNodeInfo, componentType);
5869 }
5870 for (auto id: webNodeInfo->GetChildIds()) {
5871 que.push(id);
5872 }
5873 nodeCount++;
5874 }
5875 TAG_LOGD(AceLogTag::ACE_WEB, "Current web info node count: %{public}d", nodeCount);
5876 cb(jsonNodeArray, webId);
5877 inspectorAccessibilityEnable_ = false;
5878 SetAccessibilityState(false);
5879 }
5880
GetAllWebAccessibilityNodeInfos(WebNodeInfoCallback cb,int32_t webId)5881 void WebPattern::GetAllWebAccessibilityNodeInfos(WebNodeInfoCallback cb, int32_t webId)
5882 {
5883 CHECK_NULL_VOID(cb);
5884 inspectorAccessibilityEnable_ = true;
5885 SetAccessibilityState(true);
5886 auto container = Container::Current();
5887 CHECK_NULL_VOID(container);
5888 auto host = GetHost();
5889 CHECK_NULL_VOID(host);
5890 auto pipelineContext = host->GetContext();
5891 CHECK_NULL_VOID(pipelineContext);
5892 auto taskExecutor = pipelineContext->GetTaskExecutor();
5893 taskExecutor->PostDelayedTask([weak = WeakClaim(this), cb, webId] () {
5894 auto pattern = weak.Upgrade();
5895 auto startTime = std::chrono::high_resolution_clock::now();
5896 pattern->GetWebAllInfosImpl(cb, webId);
5897 auto nowTime = std::chrono::high_resolution_clock::now();
5898 std::chrono::duration<double, std::milli> diff =
5899 std::chrono::duration_cast<std::chrono::milliseconds>(nowTime - startTime);
5900 TAG_LOGD(AceLogTag::ACE_WEB, "GetAllAccessibilityInfo time cost: %{public}f", diff.count());
5901 },
5902 TaskExecutor::TaskType::UI, WEB_ACCESSIBILITY_DELAY_TIME, "GetAllWebAccessibilityNodeInfos");
5903 }
5904
RegisterWebComponentClickCallback(WebComponentClickCallback && callback)5905 void WebPattern::RegisterWebComponentClickCallback(WebComponentClickCallback&& callback)
5906 {
5907 CHECK_NULL_VOID(callback);
5908 webComponentClickCallback_ = std::move(callback);
5909 textBlurAccessibilityEnable_ = true;
5910 SetAccessibilityState(true);
5911 }
5912
UnregisterWebComponentClickCallback()5913 void WebPattern::UnregisterWebComponentClickCallback()
5914 {
5915 webComponentClickCallback_ = nullptr;
5916 textBlurAccessibilityEnable_ = false;
5917 SetAccessibilityState(false);
5918 }
5919
UpdateFocusedAccessibilityId(int64_t accessibilityId)5920 void WebPattern::UpdateFocusedAccessibilityId(int64_t accessibilityId)
5921 {
5922 if (!accessibilityState_) {
5923 return;
5924 }
5925 auto host = GetHost();
5926 CHECK_NULL_VOID(host);
5927 auto renderContext = host->GetRenderContext();
5928 CHECK_NULL_VOID(renderContext);
5929
5930 if (accessibilityId > 0) {
5931 focusedAccessibilityId_ = accessibilityId;
5932 }
5933 RectT<int32_t> rect;
5934 if (focusedAccessibilityId_ <= 0) {
5935 focusedAccessibilityId_ = -1;
5936 renderContext->ResetAccessibilityFocusRect();
5937 renderContext->UpdateAccessibilityFocus(false);
5938 return;
5939 }
5940 if (GetAccessibilityFocusRect(rect, focusedAccessibilityId_)) {
5941 if (rect.Width() <= 1 || rect.Height() <= 1) {
5942 renderContext->ResetAccessibilityFocusRect();
5943 renderContext->UpdateAccessibilityFocus(false);
5944 } else {
5945 renderContext->UpdateAccessibilityFocusRect(rect);
5946 renderContext->UpdateAccessibilityFocus(true);
5947 }
5948 } else {
5949 renderContext->ResetAccessibilityFocusRect();
5950 renderContext->UpdateAccessibilityFocus(false);
5951 }
5952 }
5953
ClearFocusedAccessibilityId()5954 void WebPattern::ClearFocusedAccessibilityId()
5955 {
5956 if (!accessibilityState_) {
5957 return;
5958 }
5959
5960 focusedAccessibilityId_ = -1;
5961 auto host = GetHost();
5962 CHECK_NULL_VOID(host);
5963 auto renderContext = host->GetRenderContext();
5964 CHECK_NULL_VOID(renderContext);
5965 renderContext->ResetAccessibilityFocusRect();
5966 renderContext->UpdateAccessibilityFocus(false);
5967 }
5968
GetSurfaceRSNode() const5969 std::shared_ptr<Rosen::RSNode> WebPattern::GetSurfaceRSNode() const
5970 {
5971 CHECK_NULL_RETURN(renderContextForSurface_, nullptr);
5972 auto rosenRenderContext = AceType::DynamicCast<NG::RosenRenderContext>(renderContextForSurface_);
5973 CHECK_NULL_RETURN(rosenRenderContext, nullptr);
5974 return rosenRenderContext->GetRSNode();
5975 }
5976
GetAccessibilityFocusRect(RectT<int32_t> & paintRect,int64_t accessibilityId) const5977 bool WebPattern::GetAccessibilityFocusRect(RectT<int32_t>& paintRect, int64_t accessibilityId) const
5978 {
5979 if (!accessibilityState_) {
5980 return false;
5981 }
5982 CHECK_NULL_RETURN(delegate_, false);
5983 int32_t rectWidth = 0;
5984 int32_t rectHeight = 0;
5985 int32_t rectX = 0;
5986 int32_t rectY = 0;
5987 bool result = delegate_->GetAccessibilityNodeRectById(accessibilityId, &rectWidth, &rectHeight, &rectX, &rectY);
5988 if (!result) {
5989 return false;
5990 }
5991
5992 paintRect.SetRect(rectX, rectY, rectWidth, rectHeight);
5993 return true;
5994 }
5995
SetTouchEventInfo(const TouchEvent & touchEvent,TouchEventInfo & touchEventInfo,const std::string & embedId)5996 void WebPattern::SetTouchEventInfo(const TouchEvent& touchEvent,
5997 TouchEventInfo& touchEventInfo, const std::string& embedId)
5998 {
5999 CHECK_NULL_VOID(delegate_);
6000 auto host = GetHost();
6001 CHECK_NULL_VOID(host);
6002 auto offset = host->GetTransformRelativeOffset();
6003
6004 TouchEventInfo tempTouchInfo = touchEventInfo_;
6005 if (touchEvent.type == TouchType::DOWN || touchEvent.type == TouchType::UP) {
6006 while (!touchEventQueue_.empty()) {
6007 if (touchEventQueue_.front().GetChangedTouches().front().GetFingerId() == touchEvent.id) {
6008 tempTouchInfo = touchEventQueue_.front();
6009 touchEventQueue_.pop();
6010 break;
6011 } else {
6012 touchEventQueue_.pop();
6013 }
6014 }
6015 }
6016 auto pos = delegate_->GetPosition(embedId);
6017 touchEventInfo.SetSourceDevice(tempTouchInfo.GetSourceDevice());
6018 touchEventInfo.SetTarget(tempTouchInfo.GetTarget());
6019 touchEventInfo.SetForce(tempTouchInfo.GetForce());
6020 touchEventInfo.SetSourceTool(tempTouchInfo.GetSourceTool());
6021 touchEventInfo.SetTargetDisplayId(tempTouchInfo.GetTargetDisplayId());
6022 touchEventInfo.SetDeviceId(tempTouchInfo.GetDeviceId());
6023
6024 TouchLocationInfo changedInfo("onTouch", touchEvent.id);
6025 changedInfo.SetLocalLocation(Offset(touchEvent.x, touchEvent.y));
6026 changedInfo.SetGlobalLocation(Offset(touchEvent.x + offset.GetX() + pos.GetX(),
6027 touchEvent.y + offset.GetY() + pos.GetY()));
6028 changedInfo.SetScreenLocation(Offset(touchEvent.x + offset.GetX() + pos.GetX(),
6029 touchEvent.y + offset.GetY() + pos.GetY()));
6030 changedInfo.SetTouchType(touchEvent.type);
6031
6032 SetTouchLocationInfo(touchEvent, changedInfo, tempTouchInfo, touchEventInfo);
6033
6034 touchEventInfo.AddChangedTouchLocationInfo(std::move(changedInfo));
6035 }
6036
SetTouchLocationInfo(const TouchEvent & touchEvent,const TouchLocationInfo & changedInfo,const TouchEventInfo & tempTouchInfo,TouchEventInfo & touchEventInfo)6037 void WebPattern::SetTouchLocationInfo(const TouchEvent& touchEvent, const TouchLocationInfo& changedInfo,
6038 const TouchEventInfo& tempTouchInfo, TouchEventInfo& touchEventInfo)
6039 {
6040 float scaleX = 0.0f;
6041 float scaleY = 0.0f;
6042 const std::list<TouchLocationInfo>& touchList = tempTouchInfo.GetTouches();
6043 for (const TouchLocationInfo& location : touchList) {
6044 if (touchEvent.id == location.GetFingerId()) {
6045 const OHOS::Ace::Offset& localLocation = location.GetLocalLocation();
6046 scaleX = localLocation.GetX() - touchEvent.x;
6047 scaleY = localLocation.GetY() - touchEvent.y;
6048 }
6049 }
6050 for (const TouchLocationInfo& location : touchList) {
6051 TouchLocationInfo info("onTouch", location.GetFingerId());
6052 if (touchEvent.id == location.GetFingerId()) {
6053 info.SetGlobalLocation(changedInfo.GetGlobalLocation());
6054 info.SetLocalLocation(changedInfo.GetLocalLocation());
6055 info.SetScreenLocation(changedInfo.GetScreenLocation());
6056 info.SetTouchType(changedInfo.GetTouchType());
6057 } else {
6058 const OHOS::Ace::Offset& localLocation = location.GetLocalLocation();
6059 const OHOS::Ace::Offset& globalLocation = location.GetGlobalLocation();
6060 const OHOS::Ace::Offset& screenLocation = location.GetScreenLocation();
6061 info.SetGlobalLocation(Offset(globalLocation.GetX() - scaleX, globalLocation.GetY() - scaleY));
6062 info.SetLocalLocation(Offset(localLocation.GetX() - scaleX, localLocation.GetY() - scaleY));
6063 info.SetScreenLocation(Offset(screenLocation.GetX() - scaleX, screenLocation.GetY() - scaleY));
6064 info.SetTouchType(location.GetTouchType());
6065 }
6066 touchEventInfo.AddTouchLocationInfo(std::move(info));
6067 }
6068 }
6069
RegisterVisibleAreaChangeCallback(const RefPtr<PipelineContext> & pipeline)6070 void WebPattern::RegisterVisibleAreaChangeCallback(const RefPtr<PipelineContext> &pipeline)
6071 {
6072 auto host = GetHost();
6073 CHECK_NULL_VOID(host);
6074 auto callback = [weak = WeakClaim(this)](bool visible, double ratio) {
6075 auto webPattern = weak.Upgrade();
6076 CHECK_NULL_VOID(webPattern);
6077 if (!visible && !NearZero(ratio)) {
6078 TAG_LOGI(AceLogTag::ACE_WEB, "Fiterate not visible when ratio=%{public}f", ratio);
6079 return;
6080 }
6081 webPattern->OnVisibleAreaChange(visible);
6082 };
6083 std::vector<double> ratioList = {0.0, 1.0};
6084 pipeline->AddVisibleAreaChangeNode(host, ratioList, callback, false, true);
6085 }
6086
GetWordSelection(const std::string & text,int8_t offset)6087 std::vector<int8_t> WebPattern::GetWordSelection(const std::string& text, int8_t offset)
6088 {
6089 // start sync task
6090 std::future<std::vector<int8_t>> future = std::async(std::launch::async, [text, offset]() {
6091 return DataDetectorMgr::GetInstance().GetWordSelection(text, offset);
6092 });
6093 // set timeout
6094 auto status = future.wait_for(std::chrono::milliseconds(AI_TIMEOUT_LIMIT));
6095 if (status == std::future_status::ready) {
6096 return future.get();
6097 } else {
6098 TAG_LOGE(AceLogTag::ACE_WEB, "WebPattern::GetWordSelection timeout! return default");
6099 return std::vector<int8_t> { -1, -1 };
6100 }
6101 }
6102
CheckSafeAreaIsExpand()6103 bool WebPattern::CheckSafeAreaIsExpand()
6104 {
6105 auto host = GetHost();
6106 CHECK_NULL_RETURN(host, false);
6107 auto layoutProperty = host->GetLayoutProperty();
6108 CHECK_NULL_RETURN(layoutProperty, false);
6109 auto &&opts = layoutProperty->GetSafeAreaExpandOpts();
6110 CHECK_NULL_RETURN(opts, false);
6111 if ((opts->type & SAFE_AREA_TYPE_SYSTEM) || (opts->type & SAFE_AREA_TYPE_KEYBOARD)) {
6112 return true;
6113 }
6114 return false;
6115 }
6116
CheckSafeAreaKeyBoard()6117 bool WebPattern::CheckSafeAreaKeyBoard()
6118 {
6119 auto host = GetHost();
6120 CHECK_NULL_RETURN(host, false);
6121 auto layoutProperty = host->GetLayoutProperty();
6122 CHECK_NULL_RETURN(layoutProperty, false);
6123 auto &&opts = layoutProperty->GetSafeAreaExpandOpts();
6124 CHECK_NULL_RETURN(opts, false);
6125 if ((opts->type & SAFE_AREA_TYPE_KEYBOARD) && (opts->edges & SAFE_AREA_EDGE_BOTTOM)) {
6126 TAG_LOGI(AceLogTag::ACE_WEB, "SafeArea type is KEYBOARD.");
6127 return true;
6128 }
6129 return false;
6130 }
6131
Backward()6132 bool WebPattern::Backward()
6133 {
6134 if (!delegate_) {
6135 TAG_LOGE(AceLogTag::ACE_WEB, "delegate is null");
6136 return false;
6137 }
6138 if (delegate_->AccessBackward()) {
6139 delegate_->Backward();
6140 return true;
6141 }
6142 return false;
6143 }
6144
SuggestionSelected(int32_t index)6145 void WebPattern::SuggestionSelected(int32_t index)
6146 {
6147 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::SuggestionSelected index:%{public}d", index);
6148 CHECK_NULL_VOID(delegate_);
6149 delegate_->SuggestionSelected(index);
6150 }
6151
OnShowAutofillPopup(const float offsetX,const float offsetY,const std::vector<std::string> & menu_items)6152 void WebPattern::OnShowAutofillPopup(
6153 const float offsetX, const float offsetY, const std::vector<std::string>& menu_items)
6154 {
6155 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::OnShowAutofillPopup");
6156 isShowAutofillPopup_ = true;
6157 auto host = GetHost();
6158 CHECK_NULL_VOID(host);
6159 auto id = host->GetId();
6160 std::vector<SelectParam> selectParam;
6161 for (auto& item : menu_items) {
6162 selectParam.push_back({ item, "" });
6163 }
6164 auto menu = MenuView::Create(selectParam, id, host->GetTag());
6165 auto context = PipelineContext::GetCurrentContext();
6166 CHECK_NULL_VOID(context);
6167 auto menuContainer = AceType::DynamicCast<FrameNode>(menu->GetChildAtIndex(0));
6168 CHECK_NULL_VOID(menuContainer);
6169 auto menuPattern = menuContainer->GetPattern<MenuPattern>();
6170 CHECK_NULL_VOID(menuPattern);
6171 auto options = menuPattern->GetOptions();
6172 for (auto &&option : options) {
6173 auto selectCallback = [weak = WeakClaim(this)](int32_t index) {
6174 auto webPattern = weak.Upgrade();
6175 CHECK_NULL_VOID(webPattern);
6176 webPattern->SuggestionSelected(index);
6177 };
6178 auto optionNode = AceType::DynamicCast<FrameNode>(option);
6179 if (optionNode) {
6180 auto hub = optionNode->GetEventHub<OptionEventHub>();
6181 auto optionPattern = optionNode->GetPattern<OptionPattern>();
6182 if (!hub || !optionPattern) {
6183 continue;
6184 }
6185 hub->SetOnSelect(std::move(selectCallback));
6186 optionNode->MarkModifyDone();
6187 }
6188 }
6189 auto overlayManager = context->GetOverlayManager();
6190 CHECK_NULL_VOID(overlayManager);
6191 auto offset = GetCoordinatePoint().value_or(OffsetF());
6192 offset.AddX(offsetX);
6193 offset.AddY(offsetY);
6194 menu->GetOrCreateFocusHub()->SetFocusable(false);
6195 overlayManager->DeleteMenu(id);
6196 overlayManager->ShowMenu(id, offset, menu);
6197 }
6198
OnHideAutofillPopup()6199 void WebPattern::OnHideAutofillPopup()
6200 {
6201 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::OnHideAutofillPopup");
6202 if (!isShowAutofillPopup_) {
6203 return;
6204 }
6205 auto host = GetHost();
6206 CHECK_NULL_VOID(host);
6207 auto id = host->GetId();
6208 auto context = PipelineContext::GetCurrentContext();
6209 CHECK_NULL_VOID(context);
6210 auto eventHub = host->GetEventHub<WebEventHub>();
6211 auto destructor = [weak = WeakClaim(this), id]() {
6212 auto pattern = weak.Upgrade();
6213 CHECK_NULL_VOID(pattern);
6214 auto pipeline = NG::PipelineContext::GetCurrentContext();
6215 CHECK_NULL_VOID(pipeline);
6216 auto overlayManager = pipeline->GetOverlayManager();
6217 CHECK_NULL_VOID(overlayManager);
6218 overlayManager->DeleteMenu(id);
6219 };
6220 CHECK_NULL_VOID(eventHub);
6221 eventHub->SetOnDisappear(destructor);
6222 isShowAutofillPopup_ = false;
6223 }
6224
CloseKeyboard()6225 void WebPattern::CloseKeyboard()
6226 {
6227 InputMethodManager::GetInstance()->CloseKeyboard();
6228 }
6229
RequestFocus()6230 void WebPattern::RequestFocus()
6231 {
6232 WebRequestFocus();
6233 }
6234
OnRebuildFrame()6235 void WebPattern::OnRebuildFrame()
6236 {
6237 auto host = GetHost();
6238 CHECK_NULL_VOID(host);
6239 auto renderContext = host->GetRenderContext();
6240 CHECK_NULL_VOID(renderContext);
6241 CHECK_NULL_VOID(renderContextForSurface_);
6242 renderContext->AddChild(renderContextForSurface_, 0);
6243 }
6244
CreateOverlay(const RefPtr<OHOS::Ace::PixelMap> & pixelMap,int offsetX,int offsetY,int rectWidth,int rectHeight,int pointX,int pointY)6245 void WebPattern::CreateOverlay(const RefPtr<OHOS::Ace::PixelMap>& pixelMap, int offsetX, int offsetY, int rectWidth,
6246 int rectHeight, int pointX, int pointY)
6247 {
6248 if (!imageAnalyzerManager_) {
6249 imageAnalyzerManager_ = std::make_shared<ImageAnalyzerManager>(GetHost(), ImageAnalyzerHolder::WEB);
6250 }
6251 TAG_LOGI(AceLogTag::ACE_WEB,
6252 "CreateOverlay, offsetX=%{public}d, offsetY=%{public}d, width=%{public}d, height=%{public}d",
6253 offsetX,
6254 offsetY,
6255 rectWidth,
6256 rectHeight);
6257 auto task = [weak = AceType::WeakClaim(this)]() {
6258 auto webPattern = weak.Upgrade();
6259 CHECK_NULL_VOID(webPattern);
6260 webPattern->OnTextSelected();
6261 };
6262 imageAnalyzerManager_->DestroyAnalyzerOverlay();
6263 auto selectedTask = [weak = AceType::WeakClaim(this)](bool isSelected) {
6264 auto webPattern = weak.Upgrade();
6265 CHECK_NULL_VOID(webPattern);
6266 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::CreateOverlay selectedTask=%{public}d", isSelected);
6267 webPattern->SetImageOverlaySelectedStatus(isSelected);
6268 if (isSelected) {
6269 webPattern->CloseSelectOverlay();
6270 webPattern->SelectCancel();
6271 }
6272 };
6273 imageAnalyzerManager_->SetNotifySelectedCallback(std::move(selectedTask));
6274 imageAnalyzerManager_->UpdatePressOverlay(
6275 pixelMap, offsetX, offsetY, rectWidth, rectHeight, pointX, pointY, std::move(task));
6276 imageAnalyzerManager_->CreateAnalyzerOverlay(nullptr);
6277 }
6278
OnOverlayStateChanged(int offsetX,int offsetY,int rectWidth,int rectHeight)6279 void WebPattern::OnOverlayStateChanged(int offsetX, int offsetY, int rectWidth, int rectHeight)
6280 {
6281 if (imageAnalyzerManager_) {
6282 TAG_LOGI(AceLogTag::ACE_WEB,
6283 "OnOverlayStateChanged, offsetX=%{public}d, offsetY=%{public}d, width=%{public}d, height=%{public}d",
6284 offsetX,
6285 offsetY,
6286 rectWidth,
6287 rectHeight);
6288 imageAnalyzerManager_->UpdateOverlayStatus(true, offsetX, offsetY, rectWidth, rectHeight);
6289 }
6290 }
6291
OnTextSelected()6292 void WebPattern::OnTextSelected()
6293 {
6294 CHECK_NULL_VOID(delegate_);
6295 delegate_->OnTextSelected();
6296 overlayCreating_ = true;
6297 }
6298
DestroyAnalyzerOverlay()6299 void WebPattern::DestroyAnalyzerOverlay()
6300 {
6301 if (imageAnalyzerManager_ && imageAnalyzerManager_->IsOverlayCreated()) {
6302 imageAnalyzerManager_->DestroyAnalyzerOverlay();
6303 delegate_->OnDestroyImageAnalyzerOverlay();
6304 }
6305 overlayCreating_ = false;
6306 imageOverlayIsSelected_ = false;
6307 }
6308
GetWebInfoType()6309 WebInfoType WebPattern::GetWebInfoType()
6310 {
6311 std::string factoryLevel;
6312 if (delegate_) {
6313 factoryLevel = delegate_->GetWebInfoType();
6314 }
6315 if (factoryLevel == WEB_INFO_PHONE || factoryLevel == WEB_INFO_DEFAULT) {
6316 return WebInfoType::TYPE_MOBILE;
6317 } else if (factoryLevel == WEB_INFO_TABLET) {
6318 return WebInfoType::TYPE_TABLET;
6319 } else if (factoryLevel == WEB_INFO_PC) {
6320 return WebInfoType::TYPE_2IN1;
6321 }
6322 return WebInfoType::TYPE_UNKNOWN;
6323 }
6324
OnAccessibilityHoverEvent(const PointF & point)6325 bool WebPattern::OnAccessibilityHoverEvent(const PointF& point)
6326 {
6327 CHECK_NULL_RETURN(delegate_, false);
6328 auto host = GetHost();
6329 CHECK_NULL_RETURN(host, false);
6330 auto pipelineContext = host->GetContextRefPtr();
6331 CHECK_NULL_RETURN(pipelineContext, false);
6332 auto viewScale = pipelineContext->GetViewScale();
6333 int32_t globalX = static_cast<int32_t>(point.GetX()) * viewScale;
6334 int32_t globalY = static_cast<int32_t>(point.GetY()) * viewScale;
6335 auto offset = GetCoordinatePoint().value_or(OffsetF());
6336 globalX = static_cast<int32_t>(globalX - offset.GetX());
6337 globalY = static_cast<int32_t>(globalY - offset.GetY());
6338 delegate_->HandleAccessibilityHoverEvent(globalX, globalY);
6339 return true;
6340 }
6341
RegisterTextBlurCallback(TextBlurCallback && callback)6342 void WebPattern::RegisterTextBlurCallback(TextBlurCallback&& callback)
6343 {
6344 CHECK_NULL_VOID(callback);
6345 textBlurCallback_ = std::move(callback);
6346 textBlurAccessibilityEnable_ = true;
6347 SetAccessibilityState(true);
6348 }
6349
UnRegisterTextBlurCallback()6350 void WebPattern::UnRegisterTextBlurCallback()
6351 {
6352 textBlurCallback_ = nullptr;
6353 textBlurAccessibilityEnable_ = false;
6354 SetAccessibilityState(false);
6355 }
6356
InitMagnifier()6357 void WebPattern::InitMagnifier()
6358 {
6359 TAG_LOGI(AceLogTag::ACE_WEB, "InitMagnifier");
6360 if (!magnifierController_) {
6361 magnifierController_ = MakeRefPtr<MagnifierController>(WeakClaim(this));
6362 }
6363 }
6364
InitializeAccessibility()6365 void WebPattern::InitializeAccessibility()
6366 {
6367 ContainerScope scope(instanceId_);
6368 if (accessibilityChildTreeCallback_.find(instanceId_) != accessibilityChildTreeCallback_.end()) {
6369 return;
6370 }
6371 auto frameNode = frameNode_.Upgrade();
6372 CHECK_NULL_VOID(frameNode);
6373 int64_t accessibilityId = frameNode->GetAccessibilityId();
6374 auto pipeline = PipelineContext::GetCurrentContext();
6375 CHECK_NULL_VOID(pipeline);
6376 auto accessibilityManager = pipeline->GetAccessibilityManager();
6377 CHECK_NULL_VOID(accessibilityManager);
6378 accessibilityChildTreeCallback_[instanceId_] = std::make_shared<WebAccessibilityChildTreeCallback>(
6379 WeakClaim(this), frameNode->GetAccessibilityId());
6380 accessibilityManager->RegisterAccessibilityChildTreeCallback(accessibilityId,
6381 accessibilityChildTreeCallback_[instanceId_]);
6382 if (accessibilityManager->IsRegister()) {
6383 accessibilityChildTreeCallback_[instanceId_]->SetIsDelayed(true);
6384 accessibilityChildTreeCallback_[instanceId_]->OnRegister(pipeline->GetWindowId(),
6385 accessibilityManager->GetTreeId());
6386 }
6387 }
6388
UninitializeAccessibility()6389 void WebPattern::UninitializeAccessibility()
6390 {
6391 ContainerScope scope(instanceId_);
6392 auto frameNode = frameNode_.Upgrade();
6393 CHECK_NULL_VOID(frameNode);
6394 int64_t accessibilityId = frameNode->GetAccessibilityId();
6395 auto pipeline = PipelineContext::GetCurrentContext();
6396 CHECK_NULL_VOID(pipeline);
6397 auto accessibilityManager = pipeline->GetAccessibilityManager();
6398 CHECK_NULL_VOID(accessibilityManager);
6399 if (accessibilityManager->IsRegister()) {
6400 if (accessibilityChildTreeCallback_.find(instanceId_) == accessibilityChildTreeCallback_.end() ||
6401 accessibilityChildTreeCallback_[instanceId_] == nullptr) {
6402 return;
6403 }
6404 accessibilityChildTreeCallback_[instanceId_]->OnDeregister();
6405 }
6406 accessibilityManager->DeregisterAccessibilityChildTreeCallback(accessibilityId);
6407 accessibilityChildTreeCallback_.erase(instanceId_);
6408 }
6409
OnSetAccessibilityChildTree(int32_t childWindowId,int32_t childTreeId)6410 void WebPattern::OnSetAccessibilityChildTree(int32_t childWindowId, int32_t childTreeId)
6411 {
6412 treeId_ = childTreeId;
6413 auto frameNode = frameNode_.Upgrade();
6414 CHECK_NULL_VOID(frameNode);
6415 auto accessibilityProperty = frameNode->GetAccessibilityProperty<AccessibilityProperty>();
6416 if (accessibilityProperty != nullptr) {
6417 accessibilityProperty->SetChildWindowId(childWindowId);
6418 accessibilityProperty->SetChildTreeId(childTreeId);
6419 }
6420 }
6421
OnAccessibilityChildTreeRegister()6422 bool WebPattern::OnAccessibilityChildTreeRegister()
6423 {
6424 ContainerScope scope(instanceId_);
6425 auto pipeline = PipelineContext::GetCurrentContext();
6426 CHECK_NULL_RETURN(pipeline, false);
6427 auto accessibilityManager = pipeline->GetAccessibilityManager();
6428 CHECK_NULL_RETURN(accessibilityManager, false);
6429 auto frameNode = frameNode_.Upgrade();
6430 CHECK_NULL_RETURN(frameNode, false);
6431 int64_t accessibilityId = frameNode->GetAccessibilityId();
6432 return accessibilityManager->RegisterWebInteractionOperationAsChildTree(accessibilityId, WeakClaim(this));
6433 }
6434
OnAccessibilityChildTreeDeregister()6435 bool WebPattern::OnAccessibilityChildTreeDeregister()
6436 {
6437 ContainerScope scope(instanceId_);
6438 auto pipeline = PipelineContext::GetCurrentContext();
6439 CHECK_NULL_RETURN(pipeline, false);
6440 auto accessibilityManager = pipeline->GetAccessibilityManager();
6441 CHECK_NULL_RETURN(accessibilityManager, false);
6442 return accessibilityManager->DeregisterWebInteractionOperationAsChildTree(treeId_);
6443 }
6444
GetActiveStatus() const6445 bool WebPattern::GetActiveStatus() const
6446 {
6447 return isActive_;
6448 }
6449
GetBufferSizeByDeviceType()6450 int32_t WebPattern::GetBufferSizeByDeviceType()
6451 {
6452 return (SystemProperties::GetDeviceType() == DeviceType::PHONE) ? ASYNC_SURFACE_QUEUE_SIZE_FOR_PHONE :
6453 ASYNC_SURFACE_QUEUE_SIZE_FOR_OTHERS;
6454 }
6455
StartVibraFeedback(const std::string & vibratorType)6456 void WebPattern::StartVibraFeedback(const std::string& vibratorType)
6457 {
6458 if (isEnabledHapticFeedback_) {
6459 NG::VibratorUtils::StartVibraFeedback(vibratorType);
6460 }
6461 }
6462
CloseImageOverlaySelection()6463 bool WebPattern::CloseImageOverlaySelection()
6464 {
6465 if (imageOverlayIsSelected_) {
6466 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::CloseImageOverlaySelection");
6467 DestroyAnalyzerOverlay();
6468 return true;
6469 }
6470 return false;
6471 }
6472
OnParentScrollDragEndRecursive(RefPtr<NestableScrollContainer> parent)6473 void WebPattern::OnParentScrollDragEndRecursive(RefPtr<NestableScrollContainer> parent)
6474 {
6475 if (isDragEnd_) {
6476 return;
6477 }
6478 if (parent) {
6479 TAG_LOGI(AceLogTag::ACE_WEB, "WebPattern::OnParentScrollDragEndRecursive");
6480 parent->OnScrollDragEndRecursive();
6481 }
6482 isDragEnd_ = true;
6483 }
6484
GetAccessibilityVisible(int64_t accessibilityId)6485 bool WebPattern::GetAccessibilityVisible(int64_t accessibilityId)
6486 {
6487 if (delegate_) {
6488 return delegate_->GetAccessibilityVisible(accessibilityId);
6489 }
6490 return true;
6491 }
6492
OnOptimizeParserBudgetEnabledUpdate(bool value)6493 void WebPattern::OnOptimizeParserBudgetEnabledUpdate(bool value)
6494 {
6495 if (delegate_) {
6496 delegate_->UpdateOptimizeParserBudgetEnabled(value);
6497 }
6498 }
6499
PushOverlayInfo(float x,float y,int32_t id)6500 void WebPattern::PushOverlayInfo(float x, float y, int32_t id)
6501 {
6502 TouchInfo touchPoint;
6503 touchPoint.id = id;
6504 touchPoint.x = x;
6505 touchPoint.y = y;
6506 touchOverlayInfo_.push_back(touchPoint);
6507 }
6508
UpdateImageOverlayTouchInfo(int touchPointX,int touchPointY,TouchType touchType)6509 void WebPattern::UpdateImageOverlayTouchInfo(int touchPointX, int touchPointY, TouchType touchType)
6510 {
6511 if (overlayCreating_) {
6512 imageAnalyzerManager_->UpdateOverlayTouchInfo(touchPointX, touchPointY, TouchType::DOWN);
6513 }
6514 }
6515
WebOverlayRequestFocus()6516 void WebPattern::WebOverlayRequestFocus()
6517 {
6518 if (!GetNativeEmbedModeEnabledValue(false)) {
6519 WebRequestFocus();
6520 }
6521 }
6522
6523 } // namespace OHOS::Ace::NG
6524