summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
author Adrian Roos <roosa@google.com> 2020-06-09 08:49:38 +0000
committer Automerger Merge Worker <android-build-automerger-merge-worker@system.gserviceaccount.com> 2020-06-09 08:49:38 +0000
commitd0c34aa55932d21808d8353a0e11e1e5537a3410 (patch)
tree2221d35f8ff1acb4ce5ad0e295f72bfde7357be4
parent03e02b09b7a933a54524cd00c3d6db183b32aaba (diff)
parent30e24e93fdf0a9b3b0b61f07a419083670ab47af (diff)
Merge "Insets: allow controlling insets as long as the window is covering in the relevant direction" into rvc-dev am: 5b12e07b9c am: 30e24e93fd
Original change: https://googleplex-android-review.googlesource.com/c/platform/frameworks/base/+/11632046 Change-Id: I4c568d30fee55d06bbb802a4cfde18c47a87f8aa
-rw-r--r--core/java/android/view/InsetsController.java14
-rw-r--r--core/java/android/view/InsetsState.java38
-rw-r--r--core/tests/coretests/src/android/view/InsetsStateTest.java22
3 files changed, 62 insertions, 12 deletions
diff --git a/core/java/android/view/InsetsController.java b/core/java/android/view/InsetsController.java
index ef9edc6c0741..e4d53c64a063 100644
--- a/core/java/android/view/InsetsController.java
+++ b/core/java/android/view/InsetsController.java
@@ -791,7 +791,7 @@ public class InsetsController implements WindowInsetsController, InsetsAnimation
WindowInsetsAnimationControlListener listener,
boolean fromIme, long durationMs, @Nullable Interpolator interpolator,
@AnimationType int animationType) {
- if (!checkDisplayFramesForControlling()) {
+ if ((mState.calculateUncontrollableInsetsFromFrame(mFrame) & types) != 0) {
listener.onCancelled(null);
return;
}
@@ -801,13 +801,6 @@ public class InsetsController implements WindowInsetsController, InsetsAnimation
false /* useInsetsAnimationThread */);
}
- private boolean checkDisplayFramesForControlling() {
-
- // If the frame of our window doesn't span the entire display, the control API makes very
- // little sense, as we don't deal with negative insets. So just cancel immediately.
- return mState.getDisplayFrame().equals(mFrame);
- }
-
private void controlAnimationUnchecked(@InsetsType int types,
@Nullable CancellationSignal cancellationSignal,
WindowInsetsAnimationControlListener listener, Rect frame, boolean fromIme,
@@ -1285,9 +1278,6 @@ public class InsetsController implements WindowInsetsController, InsetsAnimation
}
private @InsetsType int calculateControllableTypes() {
- if (!checkDisplayFramesForControlling()) {
- return 0;
- }
@InsetsType int result = 0;
for (int i = mSourceConsumers.size() - 1; i >= 0; i--) {
InsetsSourceConsumer consumer = mSourceConsumers.valueAt(i);
@@ -1295,7 +1285,7 @@ public class InsetsController implements WindowInsetsController, InsetsAnimation
result |= toPublicType(consumer.mType);
}
}
- return result;
+ return result & ~mState.calculateUncontrollableInsetsFromFrame(mFrame);
}
/**
diff --git a/core/java/android/view/InsetsState.java b/core/java/android/view/InsetsState.java
index 3822ee59b4aa..f0bca260be38 100644
--- a/core/java/android/view/InsetsState.java
+++ b/core/java/android/view/InsetsState.java
@@ -245,6 +245,44 @@ public class InsetsState implements Parcelable {
return insets.toRect();
}
+ /**
+ * Calculate which insets *cannot* be controlled, because the frame does not cover the
+ * respective side of the inset.
+ *
+ * If the frame of our window doesn't cover the entire inset, the control API makes very
+ * little sense, as we don't deal with negative insets.
+ */
+ @InsetsType
+ public int calculateUncontrollableInsetsFromFrame(Rect frame) {
+ int blocked = 0;
+ for (int type = FIRST_TYPE; type <= LAST_TYPE; type++) {
+ InsetsSource source = mSources.get(type);
+ if (source == null) {
+ continue;
+ }
+ if (!canControlSide(frame, getInsetSide(
+ source.calculateInsets(frame, true /* ignoreVisibility */)))) {
+ blocked |= toPublicType(type);
+ }
+ }
+ return blocked;
+ }
+
+ private boolean canControlSide(Rect frame, int side) {
+ switch (side) {
+ case ISIDE_LEFT:
+ case ISIDE_RIGHT:
+ return frame.left == mDisplayFrame.left && frame.right == mDisplayFrame.right;
+ case ISIDE_TOP:
+ case ISIDE_BOTTOM:
+ return frame.top == mDisplayFrame.top && frame.bottom == mDisplayFrame.bottom;
+ case ISIDE_FLOATING:
+ return true;
+ default:
+ return false;
+ }
+ }
+
private void processSource(InsetsSource source, Rect relativeFrame, boolean ignoreVisibility,
Insets[] typeInsetsMap, @Nullable @InternalInsetsSide SparseIntArray typeSideMap,
@Nullable boolean[] typeVisibilityMap) {
diff --git a/core/tests/coretests/src/android/view/InsetsStateTest.java b/core/tests/coretests/src/android/view/InsetsStateTest.java
index daaf31a6bb65..cd93eeb857f1 100644
--- a/core/tests/coretests/src/android/view/InsetsStateTest.java
+++ b/core/tests/coretests/src/android/view/InsetsStateTest.java
@@ -27,6 +27,8 @@ import static android.view.InsetsState.ITYPE_NAVIGATION_BAR;
import static android.view.InsetsState.ITYPE_STATUS_BAR;
import static android.view.View.SYSTEM_UI_FLAG_LAYOUT_STABLE;
import static android.view.WindowInsets.Type.ime;
+import static android.view.WindowInsets.Type.navigationBars;
+import static android.view.WindowInsets.Type.statusBars;
import static android.view.WindowManager.LayoutParams.SOFT_INPUT_ADJUST_NOTHING;
import static android.view.WindowManager.LayoutParams.SOFT_INPUT_ADJUST_PAN;
import static android.view.WindowManager.LayoutParams.SOFT_INPUT_ADJUST_RESIZE;
@@ -341,6 +343,26 @@ public class InsetsStateTest {
}
}
+ @Test
+ public void testCalculateUncontrollableInsets() throws Exception {
+ try (InsetsModeSession session = new InsetsModeSession(ViewRootImpl.NEW_INSETS_MODE_FULL)) {
+ mState.getSource(ITYPE_STATUS_BAR).setFrame(new Rect(0, 0, 200, 100));
+ mState.getSource(ITYPE_STATUS_BAR).setVisible(true);
+ mState.getSource(ITYPE_IME).setFrame(new Rect(0, 200, 200, 300));
+ mState.getSource(ITYPE_IME).setVisible(true);
+ mState.getSource(ITYPE_NAVIGATION_BAR).setFrame(new Rect(100, 0, 200, 300));
+ mState.getSource(ITYPE_NAVIGATION_BAR).setVisible(true);
+
+ mState.setDisplayFrame(new Rect(0, 0, 200, 300));
+ assertEquals(0,
+ mState.calculateUncontrollableInsetsFromFrame(new Rect(0, 0, 200, 300)));
+ assertEquals(statusBars() | ime(),
+ mState.calculateUncontrollableInsetsFromFrame(new Rect(0, 50, 200, 250)));
+ assertEquals(navigationBars(),
+ mState.calculateUncontrollableInsetsFromFrame(new Rect(50, 0, 150, 300)));
+ }
+ }
+
private void assertEqualsAndHashCode() {
assertEquals(mState, mState2);
assertEquals(mState.hashCode(), mState2.hashCode());