1 /* 2 * Copyright (c) 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_EVENT_AXIS_EVENT_H 17 #define FOUNDATION_ACE_FRAMEWORKS_CORE_EVENT_AXIS_EVENT_H 18 19 #include <list> 20 #include <utility> 21 22 #include "base/geometry/offset.h" 23 #include "base/memory/ace_type.h" 24 #include "core/components_ng/event/event_constants.h" 25 #include "core/event/ace_events.h" 26 27 namespace OHOS::MMI { 28 class PointerEvent; 29 } // namespace OHOS::MMI 30 31 namespace OHOS::Ace { 32 struct UIInputEvent { 33 virtual ~UIInputEvent() = default; 34 TimeStamp time; 35 ConvertInfo convertInfo = { UIInputEventType::NONE, UIInputEventType::NONE }; 36 UIInputEventType eventType = UIInputEventType::NONE; 37 }; 38 39 struct PointerEvent : public UIInputEvent { 40 virtual ~PointerEvent() = default; 41 explicit PointerEvent(float x = {}, float y = {}, float screenX = {}, float screenY = {}, 42 double globalDisplayX = {}, double globalDisplayY = {}, TimeStamp time = {}) globalDisplayXPointerEvent43 : globalDisplayX(globalDisplayX), globalDisplayY(globalDisplayY), x(x), y(y), screenX(screenX), screenY(screenY) 44 { 45 this->time = time; 46 } 47 double globalDisplayX = {}; 48 double globalDisplayY = {}; 49 float x = {}; 50 float y = {}; 51 float screenX = {}; 52 float screenY = {}; 53 // ID of the node to which this event is being explicitly posted (not necessarily the original target) 54 int32_t postEventNodeId = {}; 55 bool passThrough = {}; 56 }; 57 58 struct AxisEvent final : public PointerEvent { 59 ~AxisEvent() = default; 60 int32_t id = 0; 61 62 double verticalAxis = 0.0; 63 double horizontalAxis = 0.0; 64 double pinchAxisScale = 0.0; 65 double rotateAxisAngle = 0.0; 66 bool isRotationEvent = false; 67 AxisAction action = AxisAction::NONE; 68 int64_t deviceId = 0; 69 SourceType sourceType = SourceType::NONE; 70 SourceTool sourceTool = SourceTool::UNKNOWN; 71 std::shared_ptr<const MMI::PointerEvent> pointerEvent; 72 int32_t touchEventId = 0; 73 std::vector<KeyCode> pressedCodes; 74 75 // Coordinates relative to the upper-left corner of the current component 76 float localX = 0.0; 77 float localY = 0.0; 78 79 int32_t targetDisplayId = 0; 80 int32_t originalId = 0; 81 bool isInjected = false; 82 float targetPositionX = 0.0; 83 float targetPositionY = 0.0; 84 float targetGlobalPositionX = 0.0; 85 float targetGlobalPositionY = 0.0; 86 float width = 0.0; 87 float height = 0.0; 88 uint64_t modifierKeyState = 0; 89 90 int32_t scrollStep = 0; 91 AxisEventfinal92 AxisEvent() 93 { 94 eventType = UIInputEventType::AXIS; 95 } AxisEventfinal96 AxisEvent(int32_t id, float x, float y, float screenX, float screenY, double globalDisplayX, double globalDisplayY, 97 double verticalAxis, double horizontalAxis, double pinchAxisScale, double rotateAxisAngle, bool isRotationEvent, 98 AxisAction action, TimeStamp timestamp, int64_t deviceId, SourceType sourceType, SourceTool sourceTool, 99 std::shared_ptr<const MMI::PointerEvent> pointerEvent, std::vector<KeyCode> pressedCodes, 100 int32_t targetDisplayId, int32_t originalId, bool isInjected, int32_t scrollStep) 101 : PointerEvent(x, y, screenX, screenY, globalDisplayX, globalDisplayY, timestamp), id(id), 102 verticalAxis(verticalAxis), horizontalAxis(horizontalAxis), pinchAxisScale(pinchAxisScale), 103 rotateAxisAngle(rotateAxisAngle), isRotationEvent(isRotationEvent), action(action), deviceId(deviceId), 104 sourceType(sourceType), sourceTool(sourceTool), pointerEvent(std::move(pointerEvent)), 105 pressedCodes(pressedCodes), targetDisplayId(targetDisplayId), originalId(originalId), isInjected(isInjected), 106 scrollStep(scrollStep) 107 { 108 eventType = UIInputEventType::AXIS; 109 } 110 111 AxisEvent CreateScaleEvent(float scale) const; 112 Offset GetOffset() const; 113 Offset GetScreenOffset() const; 114 Offset GetGlobalDisplayOffset() const; 115 int32_t GetTargetDisplayId() const; 116 AxisDirection GetDirection() const; 117 static bool IsDirectionUp(AxisDirection direction); 118 static bool IsDirectionDown(AxisDirection direction); 119 static bool IsDirectionLeft(AxisDirection direction); 120 static bool IsDirectionRight(AxisDirection direction); 121 Offset ConvertToOffset(bool isShiftKeyPressed = false, bool hasDifferentDirectionGesture = false) const; 122 // MMI has the different direction, need to check truth direction. 123 std::pair<float, float> ConvertToSummationAxisValue(const AxisEvent& event) const; 124 bool HasKey(KeyCode expectCode) const; 125 }; 126 127 class AxisInfo : public BaseEventInfo { 128 DECLARE_RELATIONSHIP_OF_CLASSES(AxisInfo, BaseEventInfo); 129 130 public: AxisInfo()131 AxisInfo() : BaseEventInfo("onAxis") {} 132 AxisInfo(const AxisEvent& event, const Offset& localLocation, const EventTarget& target); 133 ~AxisInfo() override = default; 134 void SetAction(AxisAction action); 135 AxisAction GetAction() const; 136 int32_t GetScrollStep() const; 137 void SetPinchAxisScale(float scale); 138 float GetPinchAxisScale() const; 139 void SetRotateAxisAngle(float angle); 140 float GetRotateAxisAngle() const; 141 void SetIsRotationEvent(bool rotationFlag); 142 bool GetIsRotationEvent() const; 143 AxisInfo& SetGlobalLocation(const Offset& globalLocation); 144 AxisInfo& SetLocalLocation(const Offset& localLocation); 145 AxisInfo& SetScreenLocation(const Offset& screenLocation); 146 AxisInfo& SetGlobalDisplayLocation(const Offset& globalDisplayLocation); 147 const Offset& GetGlobalDisplayLocation() const; 148 const Offset& GetScreenLocation() const; 149 const Offset& GetLocalLocation() const; 150 const Offset& GetGlobalLocation() const; 151 AxisEvent ConvertToAxisEvent() const; 152 153 private: 154 AxisAction action_ = AxisAction::NONE; 155 int32_t scrollStep_ = 0; 156 float pinchAxisScale_ = 0.0; 157 float rotateAxisAngle_ = 0.0; 158 bool isRotationEvent_ = false; 159 // global position at which the touch point contacts the screen. 160 Offset globalLocation_; 161 // Different from global location, The local location refers to the location of the contact point relative to the 162 // current node which has the recognizer. 163 Offset localLocation_; 164 Offset screenLocation_; 165 // The location where the touch point touches the screen when there are multiple screens. 166 Offset globalDisplayLocation_; 167 }; 168 169 using OnAxisEventFunc = std::function<void(AxisInfo&)>; 170 using GetEventTargetImpl = std::function<std::optional<EventTarget>()>; 171 172 class AxisEventTarget : public virtual AceType { 173 DECLARE_ACE_TYPE(AxisEventTarget, AceType); 174 175 public: 176 AxisEventTarget() = default; AxisEventTarget(std::string frameName)177 AxisEventTarget(std::string frameName) : frameName_(std::move(frameName)) {} AxisEventTarget(std::string frameName,int32_t frameId)178 AxisEventTarget(std::string frameName, int32_t frameId) : frameName_(std::move(frameName)), frameId_(frameId) {} 179 ~AxisEventTarget() override = default; 180 void SetOnAxisCallback(const OnAxisEventFunc& onAxisCallback); 181 void SetCoordinateOffset(const NG::OffsetF& coordinateOffset); 182 void SetGetEventTargetImpl(const GetEventTargetImpl& getEventTargetImpl); 183 std::optional<EventTarget> GetEventTarget() const; 184 void SetFrameName(const std::string& frameName); 185 std::string GetFrameName() const; 186 bool HandleAxisEvent(const AxisEvent& event); HandleEvent(const AxisEvent & event)187 virtual void HandleEvent(const AxisEvent& event) {} GetFrameId()188 int32_t GetFrameId() const 189 { 190 return frameId_; 191 } 192 193 private: 194 OnAxisEventFunc onAxisCallback_; 195 NG::OffsetF coordinateOffset_; 196 GetEventTargetImpl getEventTargetImpl_; 197 std::string frameName_ = "Unknown"; 198 int32_t frameId_ = 0; 199 }; 200 201 class AxisEventChecker final { 202 public: 203 // check if we are receiving axis event in correct sequence 204 // for generic axis event, the correct sequence is begin/update.../end 205 // for other axis event, just update, so no need to check 206 // return true for no error, false for wrong sequence situation 207 bool IsAxisEventSequenceCorrect(const AxisEvent& event); 208 AxisAction GetPreAction() const; 209 private: 210 bool IsGenericAxisEventSequenceCorrect(const AxisEvent& event); 211 AxisAction preActionOld_ = AxisAction::NONE; 212 AxisAction preActionNew_ = AxisAction::NONE; 213 }; 214 215 using AxisTestResult = std::list<RefPtr<AxisEventTarget>>; 216 217 } // namespace OHOS::Ace 218 219 #endif // FOUNDATION_ACE_FRAMEWORKS_CORE_EVENT_AXIS_EVENT_H