summaryrefslogtreecommitdiff
path: root/core/java/android/view/ViewGroup.java
diff options
context:
space:
mode:
authorTiger Huang <tigerhuang@google.com>2019-03-18 21:21:26 +0800
committerTiger Huang <tigerhuang@google.com>2019-03-28 16:53:20 +0800
commit2b210c234c32b1ea3d760f018274576d05b24ad6 (patch)
tree0707025cd3583c20c2ce0170849ffb9b29b0a9f6 /core/java/android/view/ViewGroup.java
parenta50d69cccce55a9de0bdb8e10400e760b3fd1edc (diff)
Reduce the window tap exclude region for child above it
For letting touches directly go to the embedded display, we've opened a tap exclude region for the ActivityView. However, if there is a view on top of the region, the view cannot be touched within the region. In this CL, we reduce the tap exclude region if there is a can-receive- pointer-event view on top of the region. Bug: 128517544 Test: atest CtsActivityManagerDeviceTestCases:ActivityViewTest Test: atest FrameworksCoreTests:ViewGroupTest Test: Menual test with ActivityViewTest and Bubbles Change-Id: I68e2a9fe9d0891801b533ab8d25074f64bef5a79
Diffstat (limited to 'core/java/android/view/ViewGroup.java')
-rw-r--r--core/java/android/view/ViewGroup.java59
1 files changed, 45 insertions, 14 deletions
diff --git a/core/java/android/view/ViewGroup.java b/core/java/android/view/ViewGroup.java
index 4851476e3d70..937bd1b34e61 100644
--- a/core/java/android/view/ViewGroup.java
+++ b/core/java/android/view/ViewGroup.java
@@ -2011,7 +2011,7 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager
for (int i = childrenCount - 1; i >= 0; i--) {
final int childIndex = getAndVerifyPreorderedIndex(childrenCount, i, customOrder);
final View child = getAndVerifyPreorderedView(preorderedList, children, childIndex);
- if (!canViewReceivePointerEvents(child)
+ if (!child.canReceivePointerEvents()
|| !isTransformedTouchPointInView(x, y, child, null)) {
continue;
}
@@ -2094,7 +2094,7 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager
childrenCount, i, customOrder);
final View child = getAndVerifyPreorderedView(
preorderedList, children, childIndex);
- if (!canViewReceivePointerEvents(child)
+ if (!child.canReceivePointerEvents()
|| !isTransformedTouchPointInView(x, y, child, null)) {
continue;
}
@@ -2314,7 +2314,7 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager
getAndVerifyPreorderedIndex(childrenCount, i, customOrder);
final View child =
getAndVerifyPreorderedView(preorderedList, children, childIndex);
- if (!canViewReceivePointerEvents(child)
+ if (!child.canReceivePointerEvents()
|| !isTransformedTouchPointInView(x, y, child, null)) {
continue;
}
@@ -2500,7 +2500,7 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager
for (int i = childrenCount - 1; i >= 0; i--) {
final int childIndex = getAndVerifyPreorderedIndex(childrenCount, i, customOrder);
final View child = getAndVerifyPreorderedView(preorderedList, children, childIndex);
- if (!canViewReceivePointerEvents(child)
+ if (!child.canReceivePointerEvents()
|| !isTransformedTouchPointInView(x, y, child, null)) {
continue;
}
@@ -2680,7 +2680,7 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager
i = childrenCount - 1;
}
- if (!canViewReceivePointerEvents(child)
+ if (!child.canReceivePointerEvents()
|| !isTransformedTouchPointInView(x, y, child, null)) {
ev.setTargetAccessibilityFocus(false);
continue;
@@ -2970,15 +2970,6 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager
}
}
- /**
- * Returns true if a child view can receive pointer events.
- * @hide
- */
- private static boolean canViewReceivePointerEvents(@NonNull View child) {
- return (child.mViewFlags & VISIBILITY_MASK) == VISIBLE
- || child.getAnimation() != null;
- }
-
private float[] getTempPoint() {
if (mTempPoint == null) {
mTempPoint = new float[2];
@@ -7199,6 +7190,46 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager
}
}
+ /**
+ * @hide
+ */
+ @Override
+ public void subtractObscuredTouchableRegion(Region touchableRegion, View view) {
+ final int childrenCount = mChildrenCount;
+ final ArrayList<View> preorderedList = buildTouchDispatchChildList();
+ final boolean customOrder = preorderedList == null && isChildrenDrawingOrderEnabled();
+ final View[] children = mChildren;
+ for (int i = childrenCount - 1; i >= 0; i--) {
+ final int childIndex = getAndVerifyPreorderedIndex(childrenCount, i, customOrder);
+ final View child = getAndVerifyPreorderedView(preorderedList, children, childIndex);
+ if (child == view) {
+ // We've reached the target view.
+ break;
+ }
+ if (!child.canReceivePointerEvents()) {
+ // This child cannot be touched. Skip it.
+ continue;
+ }
+ applyOpToRegionByBounds(touchableRegion, child, Region.Op.DIFFERENCE);
+ }
+
+ // The touchable region should not exceed the bounds of its container.
+ applyOpToRegionByBounds(touchableRegion, this, Region.Op.INTERSECT);
+
+ final ViewParent parent = getParent();
+ if (parent != null) {
+ parent.subtractObscuredTouchableRegion(touchableRegion, this);
+ }
+ }
+
+ private static void applyOpToRegionByBounds(Region region, View view, Region.Op op) {
+ final int[] locationInWindow = new int[2];
+ view.getLocationInWindow(locationInWindow);
+ final int x = locationInWindow[0];
+ final int y = locationInWindow[1];
+ region.op(x, y, x + view.getWidth(), y + view.getHeight(), op);
+ }
+
@Override
public WindowInsets dispatchApplyWindowInsets(WindowInsets insets) {
insets = super.dispatchApplyWindowInsets(insets);