View pressed state dispatching tweaks
Bugs 6075823, 6050563
Revise pressed state dispatch logic:
Only propagate pressed state to non-clickable views. This should
eliminate the "double glow" problem in some list items where a
clickable child button has a secondary glow along with a clickable
parent. This only applies to setPressed(true) calls; setPressed(false)
must propagate. Don't early-out in setPressed to support this use
case.
Change-Id: Ibbe2309f5030282fad8d23e4a9bc4616b3f5dc7c
diff --git a/core/java/android/view/View.java b/core/java/android/view/View.java
index 0675a74..e6b41da 100644
--- a/core/java/android/view/View.java
+++ b/core/java/android/view/View.java
@@ -5048,16 +5048,17 @@
* the View's internal state from a previously set "pressed" state.
*/
public void setPressed(boolean pressed) {
- if (pressed == ((mPrivateFlags & PRESSED) == PRESSED)) {
- return;
- }
+ final boolean needsRefresh = pressed != ((mPrivateFlags & PRESSED) == PRESSED);
if (pressed) {
mPrivateFlags |= PRESSED;
} else {
mPrivateFlags &= ~PRESSED;
}
- refreshDrawableState();
+
+ if (needsRefresh) {
+ refreshDrawableState();
+ }
dispatchSetPressed(pressed);
}
diff --git a/core/java/android/view/ViewGroup.java b/core/java/android/view/ViewGroup.java
index 2848e88..05c2b57 100644
--- a/core/java/android/view/ViewGroup.java
+++ b/core/java/android/view/ViewGroup.java
@@ -2770,7 +2770,13 @@
final View[] children = mChildren;
final int count = mChildrenCount;
for (int i = 0; i < count; i++) {
- children[i].setPressed(pressed);
+ final View child = children[i];
+ // Children that are clickable on their own should not
+ // show a pressed state when their parent view does.
+ // Clearing a pressed state always propagates.
+ if (!pressed || (!child.isClickable() && !child.isLongClickable())) {
+ child.setPressed(pressed);
+ }
}
}