[20/n Dispatcher refactor] Allow access to all TouchedWindowHandles
In this CL we introduce following methods to allow iterating over all
touchedWindowHandles.
1. forAllTouchedWindows
2. forAllTouchedWindowsOnDisplay
Bug: 367661487
Bug: 245989146
Test: atest inputflinger_tests
Flag: EXEMPT refactor
Change-Id: I65b2b48d73e11c068d208339931b919e419e2893
diff --git a/services/inputflinger/dispatcher/InputDispatcher.cpp b/services/inputflinger/dispatcher/InputDispatcher.cpp
index 35558a7..ba8c814 100644
--- a/services/inputflinger/dispatcher/InputDispatcher.cpp
+++ b/services/inputflinger/dispatcher/InputDispatcher.cpp
@@ -4072,13 +4072,17 @@
// Generate cancellations for touched windows first. This is to avoid generating cancellations
// through a non-touched window if there are more than one window for an input channel.
if (cancelPointers) {
- for (const auto& [displayId, touchState] : mTouchStates.mTouchStatesByDisplay) {
- if (options.displayId.has_value() && options.displayId != displayId) {
- continue;
- }
- for (const auto& touchedWindow : touchState.windows) {
- synthesizeCancelationEventsForWindowLocked(touchedWindow.windowHandle, options);
- }
+ if (options.displayId.has_value()) {
+ mTouchStates.forAllTouchedWindowsOnDisplay(
+ options.displayId.value(), [&](const sp<gui::WindowInfoHandle>& windowHandle) {
+ base::ScopedLockAssertion assumeLocked(mLock);
+ synthesizeCancelationEventsForWindowLocked(windowHandle, options);
+ });
+ } else {
+ mTouchStates.forAllTouchedWindows([&](const sp<gui::WindowInfoHandle>& windowHandle) {
+ base::ScopedLockAssertion assumeLocked(mLock);
+ synthesizeCancelationEventsForWindowLocked(windowHandle, options);
+ });
}
}
// Follow up by generating cancellations for all windows, because we don't explicitly track
@@ -7475,6 +7479,27 @@
return std::nullopt;
}
+void InputDispatcher::DispatcherTouchState::forAllTouchedWindows(
+ std::function<void(const sp<gui::WindowInfoHandle>&)> f) const {
+ for (const auto& [_, state] : mTouchStatesByDisplay) {
+ for (const TouchedWindow& window : state.windows) {
+ f(window.windowHandle);
+ }
+ }
+}
+
+void InputDispatcher::DispatcherTouchState::forAllTouchedWindowsOnDisplay(
+ ui::LogicalDisplayId displayId,
+ std::function<void(const sp<gui::WindowInfoHandle>&)> f) const {
+ const auto touchStateIt = mTouchStatesByDisplay.find(displayId);
+ if (touchStateIt == mTouchStatesByDisplay.end()) {
+ return;
+ }
+ for (const TouchedWindow& window : touchStateIt->second.windows) {
+ f(window.windowHandle);
+ }
+}
+
std::string InputDispatcher::DispatcherTouchState::dump() const {
std::string dump;
if (!mTouchStatesByDisplay.empty()) {
diff --git a/services/inputflinger/dispatcher/InputDispatcher.h b/services/inputflinger/dispatcher/InputDispatcher.h
index 9b11c14..f468be8 100644
--- a/services/inputflinger/dispatcher/InputDispatcher.h
+++ b/services/inputflinger/dispatcher/InputDispatcher.h
@@ -396,6 +396,12 @@
std::optional<std::tuple<const sp<gui::WindowInfoHandle>&, ui::LogicalDisplayId>>
findTouchedWindowHandleAndDisplay(const sp<IBinder>& token) const;
+ void forAllTouchedWindows(std::function<void(const sp<gui::WindowInfoHandle>&)> f) const;
+
+ void forAllTouchedWindowsOnDisplay(
+ ui::LogicalDisplayId displayId,
+ std::function<void(const sp<gui::WindowInfoHandle>&)> f) const;
+
std::string dump() const;
// Updates the touchState for display from WindowInfo,