1 /* 2 * Copyright 2023 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #pragma once 18 19 #include <android/input.h> 20 #include <attestation/HmacKeyManager.h> 21 #include <gui/constants.h> 22 #include <input/Input.h> 23 #include <utils/Timers.h> // for nsecs_t, systemTime 24 25 #include <vector> 26 27 namespace android { 28 29 // An arbitrary device id. 30 static constexpr uint32_t DEFAULT_DEVICE_ID = 1; 31 32 // The default policy flags to use for event injection by tests. 33 static constexpr uint32_t DEFAULT_POLICY_FLAGS = POLICY_FLAG_FILTERED | POLICY_FLAG_PASS_TO_USER; 34 35 class PointerBuilder { 36 public: PointerBuilder(int32_t id,ToolType toolType)37 PointerBuilder(int32_t id, ToolType toolType) { 38 mProperties.clear(); 39 mProperties.id = id; 40 mProperties.toolType = toolType; 41 mCoords.clear(); 42 } 43 x(float x)44 PointerBuilder& x(float x) { return axis(AMOTION_EVENT_AXIS_X, x); } 45 y(float y)46 PointerBuilder& y(float y) { return axis(AMOTION_EVENT_AXIS_Y, y); } 47 axis(int32_t axis,float value)48 PointerBuilder& axis(int32_t axis, float value) { 49 mCoords.setAxisValue(axis, value); 50 return *this; 51 } 52 buildProperties()53 PointerProperties buildProperties() const { return mProperties; } 54 buildCoords()55 PointerCoords buildCoords() const { return mCoords; } 56 57 private: 58 PointerProperties mProperties; 59 PointerCoords mCoords; 60 }; 61 62 class MotionEventBuilder { 63 public: MotionEventBuilder(int32_t action,int32_t source)64 MotionEventBuilder(int32_t action, int32_t source) { 65 mAction = action; 66 mSource = source; 67 mEventTime = systemTime(SYSTEM_TIME_MONOTONIC); 68 mDownTime = mEventTime; 69 } 70 deviceId(int32_t deviceId)71 MotionEventBuilder& deviceId(int32_t deviceId) { 72 mDeviceId = deviceId; 73 return *this; 74 } 75 downTime(nsecs_t downTime)76 MotionEventBuilder& downTime(nsecs_t downTime) { 77 mDownTime = downTime; 78 return *this; 79 } 80 eventTime(nsecs_t eventTime)81 MotionEventBuilder& eventTime(nsecs_t eventTime) { 82 mEventTime = eventTime; 83 return *this; 84 } 85 displayId(int32_t displayId)86 MotionEventBuilder& displayId(int32_t displayId) { 87 mDisplayId = displayId; 88 return *this; 89 } 90 actionButton(int32_t actionButton)91 MotionEventBuilder& actionButton(int32_t actionButton) { 92 mActionButton = actionButton; 93 return *this; 94 } 95 buttonState(int32_t buttonState)96 MotionEventBuilder& buttonState(int32_t buttonState) { 97 mButtonState = buttonState; 98 return *this; 99 } 100 rawXCursorPosition(float rawXCursorPosition)101 MotionEventBuilder& rawXCursorPosition(float rawXCursorPosition) { 102 mRawXCursorPosition = rawXCursorPosition; 103 return *this; 104 } 105 rawYCursorPosition(float rawYCursorPosition)106 MotionEventBuilder& rawYCursorPosition(float rawYCursorPosition) { 107 mRawYCursorPosition = rawYCursorPosition; 108 return *this; 109 } 110 pointer(PointerBuilder pointer)111 MotionEventBuilder& pointer(PointerBuilder pointer) { 112 mPointers.push_back(pointer); 113 return *this; 114 } 115 addFlag(uint32_t flags)116 MotionEventBuilder& addFlag(uint32_t flags) { 117 mFlags |= flags; 118 return *this; 119 } 120 build()121 MotionEvent build() { 122 std::vector<PointerProperties> pointerProperties; 123 std::vector<PointerCoords> pointerCoords; 124 for (const PointerBuilder& pointer : mPointers) { 125 pointerProperties.push_back(pointer.buildProperties()); 126 pointerCoords.push_back(pointer.buildCoords()); 127 } 128 129 // Set mouse cursor position for the most common cases to avoid boilerplate. 130 if (mSource == AINPUT_SOURCE_MOUSE && 131 !MotionEvent::isValidCursorPosition(mRawXCursorPosition, mRawYCursorPosition)) { 132 mRawXCursorPosition = pointerCoords[0].getX(); 133 mRawYCursorPosition = pointerCoords[0].getY(); 134 } 135 136 MotionEvent event; 137 static const ui::Transform kIdentityTransform; 138 event.initialize(InputEvent::nextId(), mDeviceId, mSource, mDisplayId, INVALID_HMAC, 139 mAction, mActionButton, mFlags, /*edgeFlags=*/0, AMETA_NONE, mButtonState, 140 MotionClassification::NONE, kIdentityTransform, 141 /*xPrecision=*/0, /*yPrecision=*/0, mRawXCursorPosition, 142 mRawYCursorPosition, kIdentityTransform, mDownTime, mEventTime, 143 mPointers.size(), pointerProperties.data(), pointerCoords.data()); 144 return event; 145 } 146 147 private: 148 int32_t mAction; 149 int32_t mDeviceId{DEFAULT_DEVICE_ID}; 150 int32_t mSource; 151 nsecs_t mDownTime; 152 nsecs_t mEventTime; 153 int32_t mDisplayId{ADISPLAY_ID_DEFAULT}; 154 int32_t mActionButton{0}; 155 int32_t mButtonState{0}; 156 int32_t mFlags{0}; 157 float mRawXCursorPosition{AMOTION_EVENT_INVALID_CURSOR_POSITION}; 158 float mRawYCursorPosition{AMOTION_EVENT_INVALID_CURSOR_POSITION}; 159 160 std::vector<PointerBuilder> mPointers; 161 }; 162 163 } // namespace android 164