Input devices configure on per-display basis (1/2)
A InputDevice may be associated with a specific display.
This would provide a function to check if an input device can dispatch
input events to the specific display.
If the device has no associated, the events can dispatch to any display.
Bug: 116767202
Test: atest -a libinput_tests inputflinger_tests
Change-Id: I05a1c8db191ef1e6c4182f902a7a3b51e420740d
diff --git a/services/inputflinger/InputReader.cpp b/services/inputflinger/InputReader.cpp
index 64070e3..f84aa34 100644
--- a/services/inputflinger/InputReader.cpp
+++ b/services/inputflinger/InputReader.cpp
@@ -805,6 +805,30 @@
return false;
}
+bool InputReader::canDispatchToDisplay(int32_t deviceId, int32_t displayId) {
+ AutoMutex _l(mLock);
+
+ ssize_t deviceIndex = mDevices.indexOfKey(deviceId);
+ if (deviceIndex < 0) {
+ ALOGW("Ignoring invalid device id %" PRId32 ".", deviceId);
+ return false;
+ }
+
+ InputDevice* device = mDevices.valueAt(deviceIndex);
+ std::optional<int32_t> associatedDisplayId = device->getAssociatedDisplay();
+ // No associated display. By default, can dispatch to all displays.
+ if (!associatedDisplayId) {
+ return true;
+ }
+
+ if (*associatedDisplayId == ADISPLAY_ID_NONE) {
+ ALOGW("Device has associated, but no associated display id.");
+ return true;
+ }
+
+ return *associatedDisplayId == displayId;
+}
+
void InputReader::dump(std::string& dump) {
AutoMutex _l(mLock);
@@ -1275,6 +1299,18 @@
mContext->getListener()->notifyDeviceReset(&args);
}
+std::optional<int32_t> InputDevice::getAssociatedDisplay() {
+ size_t numMappers = mMappers.size();
+ for (size_t i = 0; i < numMappers; i++) {
+ InputMapper* mapper = mMappers[i];
+ std::optional<int32_t> associatedDisplayId = mapper->getAssociatedDisplay();
+ if (associatedDisplayId) {
+ return associatedDisplayId;
+ }
+ }
+
+ return std::nullopt;
+}
// --- CursorButtonAccumulator ---
@@ -2647,7 +2683,7 @@
}
// Update the PointerController if viewports changed.
- if (mParameters.hasAssociatedDisplay) {
+ if (mParameters.mode == Parameters::MODE_POINTER) {
getPolicy()->obtainPointerController(getDeviceId());
}
bumpGeneration();
@@ -2919,6 +2955,19 @@
}
}
+std::optional<int32_t> CursorInputMapper::getAssociatedDisplay() {
+ if (mParameters.hasAssociatedDisplay) {
+ if (mParameters.mode == Parameters::MODE_POINTER) {
+ return std::make_optional(mPointerController->getDisplayId());
+ } else {
+ // If the device is orientationAware and not a mouse,
+ // it expects to dispatch events to any display
+ return std::make_optional(ADISPLAY_ID_NONE);
+ }
+ }
+ return std::nullopt;
+}
+
// --- RotaryEncoderInputMapper ---
RotaryEncoderInputMapper::RotaryEncoderInputMapper(InputDevice* device) :
@@ -6511,9 +6560,7 @@
ALOG_ASSERT(false);
}
}
- const int32_t displayId = mPointerController != nullptr ?
- mPointerController->getDisplayId() : mViewport.displayId;
-
+ const int32_t displayId = getAssociatedDisplay().value_or(ADISPLAY_ID_NONE);
const int32_t deviceId = getDeviceId();
std::vector<TouchVideoFrame> frames = mDevice->getEventHub()->getVideoFrames(deviceId);
NotifyMotionArgs args(mContext->getNextSequenceNum(), when, deviceId,
@@ -6830,6 +6877,16 @@
return true;
}
+std::optional<int32_t> TouchInputMapper::getAssociatedDisplay() {
+ if (mParameters.hasAssociatedDisplay) {
+ if (mDeviceMode == DEVICE_MODE_POINTER) {
+ return std::make_optional(mPointerController->getDisplayId());
+ } else {
+ return std::make_optional(mViewport.displayId);
+ }
+ }
+ return std::nullopt;
+}
// --- SingleTouchInputMapper ---