1 /* 2 * Copyright (c) 2021-2022 Huawei Device Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16 #ifndef FOUNDATION_ACE_FRAMEWORKS_CORE_FOCUS_FOCUS_NODE_H 17 #define FOUNDATION_ACE_FRAMEWORKS_CORE_FOCUS_FOCUS_NODE_H 18 19 #include <functional> 20 #include <list> 21 22 #include "base/geometry/rect.h" 23 #include "base/memory/ace_type.h" 24 #include "base/utils/macros.h" 25 #include "base/utils/noncopyable.h" 26 #include "core/event/key_event.h" 27 28 namespace OHOS::Ace { 29 30 class FocusNode; 31 class FocusGroup; 32 class ClickInfo; 33 34 using TabIndexNodeList = std::list<std::pair<int32_t, WeakPtr<FocusNode>>>; 35 constexpr int32_t DEFAULT_TAB_FOCUSED_INDEX = -2; 36 constexpr int32_t NONE_TAB_FOCUSED_INDEX = -1; 37 38 class ACE_FORCE_EXPORT FocusNode : public virtual AceType { 39 DECLARE_ACE_TYPE(FocusNode, AceType); 40 ACE_DISALLOW_COPY_AND_MOVE(FocusNode); 41 42 public: 43 explicit FocusNode(bool focusable = true) : focusable_(focusable) {} 44 ~FocusNode() override = default; 45 46 bool HandleKeyEvent(const KeyEvent& keyEvent); 47 void CollectTabIndexNodes(TabIndexNodeList& tabIndexNodes); 48 bool GoToFocusByTabNodeIdx(TabIndexNodeList& tabIndexNodes, int32_t tabNodeIdx); 49 bool HandleFocusByTabIndex(const KeyEvent& event, const RefPtr<FocusGroup>& mainNode); 50 bool RequestFocusImmediately(); 51 void UpdateAccessibilityFocusInfo(); 52 // Use pipeline to request focus. In this case that node gets focus when the layout needs to be completed. 53 void RequestFocus(); 54 void LostFocus(BlurReason reason = BlurReason::FOCUS_SWITCH); 55 void LostSelfFocus(); 56 IsFocusable()57 virtual bool IsFocusable() const 58 { 59 return enabled_ && show_ && focusable_ && parentFocusable_; 60 } 61 62 virtual bool IsFocusableByTab() const; 63 64 bool IsFocusableWholePath() const; 65 AcceptFocusByRectOfLastFocus(const Rect & rect)66 virtual bool AcceptFocusByRectOfLastFocus(const Rect& rect) 67 { 68 return IsFocusable(); 69 } 70 71 void SetFocusable(bool focusable); 72 IsParentFocusable()73 bool IsParentFocusable() const 74 { 75 return parentFocusable_; 76 } 77 SetParentFocusable(bool parentFocusable)78 void SetParentFocusable(bool parentFocusable) 79 { 80 parentFocusable_ = parentFocusable; 81 } 82 IsCurrentFocus()83 bool IsCurrentFocus() const 84 { 85 return currentFocus_; 86 } 87 SetOnKeyCallback(std::function<bool (const KeyEvent &)> && onKeyCallback)88 void SetOnKeyCallback(std::function<bool(const KeyEvent&)>&& onKeyCallback) 89 { 90 onKeyCallback_ = std::move(onKeyCallback); 91 } SetOnKeyCallback(std::function<void (const std::shared_ptr<KeyEventInfo> &)> && onKeyCallback)92 void SetOnKeyCallback(std::function<void(const std::shared_ptr<KeyEventInfo>&)>&& onKeyCallback) 93 { 94 onKeyEventCallback_ = std::move(onKeyCallback); 95 } SetOnClickCallback(std::function<void ()> && onClickCallback)96 void SetOnClickCallback(std::function<void()>&& onClickCallback) 97 { 98 onClickCallback_ = std::move(onClickCallback); 99 } SetOnClickCallback(std::function<void (const std::shared_ptr<ClickInfo> &)> && onClickCallback)100 void SetOnClickCallback(std::function<void(const std::shared_ptr<ClickInfo>&)>&& onClickCallback) 101 { 102 onClickEventCallback_ = std::move(onClickCallback); 103 } SetOnFocusCallback(std::function<void ()> && onFocusCallback)104 void SetOnFocusCallback(std::function<void()>&& onFocusCallback) 105 { 106 onFocusCallback_ = std::move(onFocusCallback); 107 } SetOnBlurCallback(std::function<void ()> && onBlurCallback)108 void SetOnBlurCallback(std::function<void()>&& onBlurCallback) 109 { 110 onBlurCallback_ = std::move(onBlurCallback); 111 } SetFocusMoveCallback(std::function<void ()> && focusMoveCallback)112 void SetFocusMoveCallback(std::function<void()>&& focusMoveCallback) 113 { 114 focusMoveCallback_ = std::move(focusMoveCallback); 115 } SetOnDeleteCallback(std::function<void ()> && onDeleteCallback)116 void SetOnDeleteCallback(std::function<void()>&& onDeleteCallback) 117 { 118 onDeleteCallback_ = std::move(onDeleteCallback); 119 } 120 SetFocusIndex(int32_t focusIndex)121 void SetFocusIndex(int32_t focusIndex) 122 { 123 focusIndex_ = focusIndex; 124 autoFocusIndex_ = false; 125 } 126 127 void RemoveSelf(); 128 GetParent()129 WeakPtr<FocusGroup> GetParent() const 130 { 131 return parent_; 132 } SetParent(WeakPtr<FocusGroup> && parent)133 void SetParent(WeakPtr<FocusGroup>&& parent) 134 { 135 parent_ = std::move(parent); 136 } 137 IsChild()138 virtual bool IsChild() const 139 { 140 return true; 141 } 142 SetRect(const Rect & rect)143 void SetRect(const Rect& rect) 144 { 145 rectFromOrigin_ = rect; 146 } GetRect()147 const Rect& GetRect() const 148 { 149 return rectFromOrigin_; 150 } 151 CanShow()152 bool CanShow() const 153 { 154 return show_; 155 } 156 virtual void SetShow(bool show); 157 IsEnabled()158 bool IsEnabled() const 159 { 160 return enabled_; 161 } 162 virtual void SetEnabled(bool enabled); 163 164 virtual void DumpFocusTree(int32_t depth); 165 166 virtual void DumpFocus(); 167 168 void RefreshFocus(); 169 170 virtual void RefreshParentFocusable(bool focusable); 171 OnClick()172 virtual void OnClick() 173 { 174 if (onClickCallback_) { 175 onClickCallback_(); 176 } 177 } 178 179 virtual bool OnClick(const KeyEvent& event); 180 GetTabIndex()181 int32_t GetTabIndex() const 182 { 183 return tabIndex_; 184 } 185 SetTabIndex(int32_t tabIndex)186 void SetTabIndex(int32_t tabIndex) 187 { 188 tabIndex_ = tabIndex; 189 } 190 GetInspectorKey()191 const std::string& GetInspectorKey() const 192 { 193 return inspectorKey_; 194 } 195 SetInspectorKey(std::string & inspectorKey)196 void SetInspectorKey(std::string& inspectorKey) 197 { 198 inspectorKey_ = inspectorKey; 199 } 200 201 RefPtr<FocusNode> GetChildDefaultFocusNode(bool isGetDefaultFocus = true); 202 203 RefPtr<FocusNode> GetChildFocusNodeById(const std::string& id); 204 205 bool RequestFocusImmediatelyById(const std::string& id); 206 IsDefaultFocus()207 bool IsDefaultFocus() const 208 { 209 return isDefaultFocus_; 210 } SetIsDefaultFocus(bool isDefaultFocus)211 void SetIsDefaultFocus(bool isDefaultFocus) 212 { 213 isDefaultFocus_ = isDefaultFocus; 214 } 215 IsDefaultGroupFocus()216 bool IsDefaultGroupFocus() const 217 { 218 return isDefaultGroupFocus_; 219 } SetIsDefaultGroupFocus(bool isDefaultGroupFocus)220 void SetIsDefaultGroupFocus(bool isDefaultGroupFocus) 221 { 222 isDefaultGroupFocus_ = isDefaultGroupFocus; 223 } 224 225 protected: 226 virtual bool OnKeyEvent(const KeyEvent& keyEvent); 227 OnFocus()228 virtual void OnFocus() 229 { 230 if (onFocusCallback_) { 231 onFocusCallback_(); 232 } 233 if (onFocus_) { 234 onFocus_(); 235 } 236 } OnBlur()237 virtual void OnBlur() 238 { 239 OnBlur(blurReason_); 240 if (onBlurCallback_) { 241 onBlurCallback_(); 242 } 243 if (onBlur_) { 244 onBlur_(); 245 } 246 } OnBlur(BlurReason reason)247 virtual void OnBlur(BlurReason reason) {} OnFocusMove(KeyCode keyCode)248 virtual void OnFocusMove(KeyCode keyCode) 249 { 250 bool flag = keyCode == KeyCode::TV_CONTROL_UP || keyCode == KeyCode::TV_CONTROL_DOWN || 251 keyCode == KeyCode::TV_CONTROL_LEFT || keyCode == KeyCode::TV_CONTROL_RIGHT || 252 keyCode == KeyCode::KEY_TAB; 253 if (onFocusMove_ && flag) { 254 onFocusMove_((int)keyCode); 255 } 256 } 257 HandleFocus()258 virtual void HandleFocus() 259 { 260 if ((!AceType::InstanceOf<FocusGroup>(this)) && focusMoveCallback_) { 261 focusMoveCallback_(); 262 } 263 OnFocus(); 264 } 265 OnDeleteEvent()266 virtual void OnDeleteEvent() 267 { 268 if (onDeleteCallback_) { 269 onDeleteCallback_(); 270 } 271 } 272 IsDeleteDisabled()273 virtual bool IsDeleteDisabled() 274 { 275 return false; 276 } 277 278 std::function<void(int)> onFocusMove_; 279 std::function<void()> onFocus_; 280 std::function<void()> onBlur_; 281 int32_t tabIndex_ = 0; 282 std::string inspectorKey_; 283 bool isFocusOnTouch_ = false; 284 bool isDefaultFocus_ = false; 285 bool isDefaultGroupFocus_ = false; 286 BlurReason blurReason_ = BlurReason::FOCUS_SWITCH; 287 288 private: 289 static int32_t GenerateFocusIndex(); 290 291 WeakPtr<FocusGroup> parent_; 292 293 std::function<void(std::shared_ptr<ClickInfo>&)> onClickEventCallback_; 294 std::function<bool(const KeyEvent&)> onKeyCallback_; 295 std::function<void(const std::shared_ptr<KeyEventInfo>&)> onKeyEventCallback_; 296 std::function<void()> onClickCallback_; 297 std::function<void()> onFocusCallback_; 298 std::function<void()> onBlurCallback_; 299 std::function<void()> focusMoveCallback_; 300 std::function<void()> onDeleteCallback_; 301 302 int32_t focusIndex_ { GenerateFocusIndex() }; 303 bool autoFocusIndex_ { true }; 304 305 bool focusable_ { true }; 306 bool parentFocusable_ { true }; 307 bool currentFocus_ { false }; 308 bool show_ { true }; 309 bool enabled_ { true }; 310 311 Rect rectFromOrigin_; 312 }; 313 314 class ACE_EXPORT FocusGroup : public FocusNode { 315 DECLARE_ACE_TYPE(FocusGroup, FocusNode); 316 317 public: FocusGroup()318 FocusGroup() : FocusNode(true) {} 319 ~FocusGroup() override = default; 320 321 bool IsFocusable() const override; 322 323 bool IsFocusableByTab() const override; 324 325 void AddChild(const RefPtr<FocusNode>& focusNode); 326 void AddChild(const RefPtr<FocusNode>& focusNode, const RefPtr<FocusNode>& nextFocusNode); 327 void RemoveChild(const RefPtr<FocusNode>& focusNode); 328 void RebuildChild(std::list<RefPtr<FocusNode>>&& rebuildFocusNodes); 329 330 void SwitchFocus(const RefPtr<FocusNode>& focusNode); 331 bool GoToNextFocus(bool reverse, const Rect& rect = Rect()); 332 333 int32_t GetFocusingTabNodeIdx(TabIndexNodeList& tabIndexNodes); 334 GetChildrenList()335 const std::list<RefPtr<FocusNode>>& GetChildrenList() const 336 { 337 return focusNodes_; 338 } 339 IsChild()340 bool IsChild() const override 341 { 342 return false; 343 } 344 345 void DumpFocusTree(int32_t depth) override; 346 347 void SetShow(bool show) override; 348 349 void SetEnabled(bool enabled) override; 350 351 void RefreshParentFocusable(bool focusable) override; 352 SetIsGroupDefaultFocused(bool isGroupDefaultFocused)353 void SetIsGroupDefaultFocused(bool isGroupDefaultFocused) 354 { 355 isGroupDefaultFocused_ = isGroupDefaultFocused; 356 } IsGroupDefaultFocused()357 bool IsGroupDefaultFocused() const 358 { 359 return isGroupDefaultFocused_; 360 } 361 SetIsDefaultHasFocused(bool isDefaultHasFocused)362 void SetIsDefaultHasFocused(bool isDefaultHasFocused) 363 { 364 isDefaultHasFocused_ = isDefaultHasFocused; 365 } IsDefaultHasFocused()366 bool IsDefaultHasFocused() const 367 { 368 return isDefaultHasFocused_; 369 } 370 371 protected: 372 bool OnKeyEvent(const KeyEvent& keyEvent) override; 373 void OnFocus() override; 374 void OnBlur() override; 375 376 bool TryRequestFocus(const RefPtr<FocusNode>& focusNode, const Rect& rect); 377 bool CalculateRect(const RefPtr<FocusNode>& node, Rect& rect); 378 bool AcceptFocusByRectOfLastFocus(const Rect& rect) override; 379 380 virtual bool RequestNextFocus(bool vertical, bool reverse, const Rect& rect) = 0; 381 382 std::list<RefPtr<FocusNode>> focusNodes_; 383 std::list<RefPtr<FocusNode>>::iterator itLastFocusNode_ { focusNodes_.end() }; 384 385 private: 386 bool CalculatePosition(); 387 bool isDefaultHasFocused_ { false }; 388 bool isGroupDefaultFocused_ { false }; 389 bool isFirstFocusInPage_ { true }; 390 }; 391 392 } // namespace OHOS::Ace 393 394 #endif // FOUNDATION_ACE_FRAMEWORKS_CORE_FOCUS_FOCUS_NODE_H 395