Merge "Migrate AuthContainerView to predictive back" into tm-qpr-dev
This commit is contained in:
@@ -54,6 +54,8 @@ import android.widget.FrameLayout;
|
|||||||
import android.widget.ImageView;
|
import android.widget.ImageView;
|
||||||
import android.widget.LinearLayout;
|
import android.widget.LinearLayout;
|
||||||
import android.widget.ScrollView;
|
import android.widget.ScrollView;
|
||||||
|
import android.window.OnBackInvokedCallback;
|
||||||
|
import android.window.OnBackInvokedDispatcher;
|
||||||
|
|
||||||
import com.android.internal.annotations.VisibleForTesting;
|
import com.android.internal.annotations.VisibleForTesting;
|
||||||
import com.android.internal.jank.InteractionJankMonitor;
|
import com.android.internal.jank.InteractionJankMonitor;
|
||||||
@@ -127,6 +129,7 @@ public class AuthContainerView extends LinearLayout
|
|||||||
private final float mTranslationY;
|
private final float mTranslationY;
|
||||||
@ContainerState private int mContainerState = STATE_UNKNOWN;
|
@ContainerState private int mContainerState = STATE_UNKNOWN;
|
||||||
private final Set<Integer> mFailedModalities = new HashSet<Integer>();
|
private final Set<Integer> mFailedModalities = new HashSet<Integer>();
|
||||||
|
private final OnBackInvokedCallback mBackCallback = this::onBackInvoked;
|
||||||
|
|
||||||
private final @Background DelayableExecutor mBackgroundExecutor;
|
private final @Background DelayableExecutor mBackgroundExecutor;
|
||||||
private int mOrientation;
|
private int mOrientation;
|
||||||
@@ -362,8 +365,7 @@ public class AuthContainerView extends LinearLayout
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if (event.getAction() == KeyEvent.ACTION_UP) {
|
if (event.getAction() == KeyEvent.ACTION_UP) {
|
||||||
sendEarlyUserCanceled();
|
onBackInvoked();
|
||||||
animateAway(AuthDialogCallback.DISMISSED_USER_CANCELED);
|
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
});
|
});
|
||||||
@@ -373,6 +375,11 @@ public class AuthContainerView extends LinearLayout
|
|||||||
requestFocus();
|
requestFocus();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void onBackInvoked() {
|
||||||
|
sendEarlyUserCanceled();
|
||||||
|
animateAway(AuthDialogCallback.DISMISSED_USER_CANCELED);
|
||||||
|
}
|
||||||
|
|
||||||
void sendEarlyUserCanceled() {
|
void sendEarlyUserCanceled() {
|
||||||
mConfig.mCallback.onSystemEvent(
|
mConfig.mCallback.onSystemEvent(
|
||||||
BiometricConstants.BIOMETRIC_SYSTEM_EVENT_EARLY_USER_CANCEL, getRequestId());
|
BiometricConstants.BIOMETRIC_SYSTEM_EVENT_EARLY_USER_CANCEL, getRequestId());
|
||||||
@@ -520,6 +527,11 @@ public class AuthContainerView extends LinearLayout
|
|||||||
.start();
|
.start();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
OnBackInvokedDispatcher dispatcher = findOnBackInvokedDispatcher();
|
||||||
|
if (dispatcher != null) {
|
||||||
|
dispatcher.registerOnBackInvokedCallback(
|
||||||
|
OnBackInvokedDispatcher.PRIORITY_DEFAULT, mBackCallback);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private Animator.AnimatorListener getJankListener(View v, String type, long timeout) {
|
private Animator.AnimatorListener getJankListener(View v, String type, long timeout) {
|
||||||
@@ -618,6 +630,10 @@ public class AuthContainerView extends LinearLayout
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onDetachedFromWindow() {
|
public void onDetachedFromWindow() {
|
||||||
|
OnBackInvokedDispatcher dispatcher = findOnBackInvokedDispatcher();
|
||||||
|
if (dispatcher != null) {
|
||||||
|
findOnBackInvokedDispatcher().unregisterOnBackInvokedCallback(mBackCallback);
|
||||||
|
}
|
||||||
super.onDetachedFromWindow();
|
super.onDetachedFromWindow();
|
||||||
mWakefulnessLifecycle.removeObserver(this);
|
mWakefulnessLifecycle.removeObserver(this);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -29,6 +29,7 @@ import android.testing.AndroidTestingRunner
|
|||||||
import android.testing.TestableLooper
|
import android.testing.TestableLooper
|
||||||
import android.testing.TestableLooper.RunWithLooper
|
import android.testing.TestableLooper.RunWithLooper
|
||||||
import android.testing.ViewUtils
|
import android.testing.ViewUtils
|
||||||
|
import android.view.KeyEvent
|
||||||
import android.view.View
|
import android.view.View
|
||||||
import android.view.WindowInsets
|
import android.view.WindowInsets
|
||||||
import android.view.WindowManager
|
import android.view.WindowManager
|
||||||
@@ -91,6 +92,21 @@ class AuthContainerViewTest : SysuiTestCase() {
|
|||||||
verify(callback).onDialogAnimatedIn(authContainer?.requestId ?: 0L)
|
verify(callback).onDialogAnimatedIn(authContainer?.requestId ?: 0L)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun testDismissesOnBack() {
|
||||||
|
val container = initializeFingerprintContainer(addToView = true)
|
||||||
|
assertThat(container.parent).isNotNull()
|
||||||
|
val root = container.rootView
|
||||||
|
|
||||||
|
// Simulate back invocation
|
||||||
|
container.dispatchKeyEvent(KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_BACK))
|
||||||
|
container.dispatchKeyEvent(KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_BACK))
|
||||||
|
waitForIdleSync()
|
||||||
|
|
||||||
|
assertThat(container.parent).isNull()
|
||||||
|
assertThat(root.isAttachedToWindow).isFalse()
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
fun testIgnoresAnimatedInWhenDismissed() {
|
fun testIgnoresAnimatedInWhenDismissed() {
|
||||||
val container = initializeFingerprintContainer(addToView = false)
|
val container = initializeFingerprintContainer(addToView = false)
|
||||||
|
|||||||
Reference in New Issue
Block a user