Add tap target for when udfps is unavailable
tapping on the target will bring up the bouncer since UDFPS is unavailable Test: manual Bug: 172050991 Change-Id: I8fafa2da174aec905ae0d9c4c19aff8907a4c67e
This commit is contained in:
19
packages/SystemUI/res-keyguard/drawable/circle_white.xml
Normal file
19
packages/SystemUI/res-keyguard/drawable/circle_white.xml
Normal file
@@ -0,0 +1,19 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<!-- Copyright (C) 2020 The Android Open Source Project
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
-->
|
||||
<shape xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:shape="oval">
|
||||
<solid android:color="#33FFFFFF" />
|
||||
</shape>
|
||||
24
packages/SystemUI/res/layout/disabled_udfps_view.xml
Normal file
24
packages/SystemUI/res/layout/disabled_udfps_view.xml
Normal file
@@ -0,0 +1,24 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<!--
|
||||
~ Copyright (C) 2020 The Android Open Source Project
|
||||
~
|
||||
~ Licensed under the Apache License, Version 2.0 (the "License");
|
||||
~ you may not use this file except in compliance with the License.
|
||||
~ You may obtain a copy of the License at
|
||||
~
|
||||
~ http://www.apache.org/licenses/LICENSE-2.0
|
||||
~
|
||||
~ Unless required by applicable law or agreed to in writing, software
|
||||
~ distributed under the License is distributed on an "AS IS" BASIS,
|
||||
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
~ See the License for the specific language governing permissions and
|
||||
~ limitations under the License.
|
||||
-->
|
||||
<com.android.keyguard.DisabledUdfpsView
|
||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:systemui="http://schemas.android.com/apk/res-auto"
|
||||
android:id="@+id/disabled_udfps_view"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:background="@drawable/circle_white"
|
||||
/>
|
||||
@@ -1,4 +1,19 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<!--
|
||||
~ Copyright (C) 2020 The Android Open Source Project
|
||||
~
|
||||
~ Licensed under the Apache License, Version 2.0 (the "License");
|
||||
~ you may not use this file except in compliance with the License.
|
||||
~ You may obtain a copy of the License at
|
||||
~
|
||||
~ http://www.apache.org/licenses/LICENSE-2.0
|
||||
~
|
||||
~ Unless required by applicable law or agreed to in writing, software
|
||||
~ distributed under the License is distributed on an "AS IS" BASIS,
|
||||
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
~ See the License for the specific language governing permissions and
|
||||
~ limitations under the License.
|
||||
-->
|
||||
<com.android.systemui.biometrics.UdfpsView
|
||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:systemui="http://schemas.android.com/apk/res-auto"
|
||||
|
||||
@@ -0,0 +1,155 @@
|
||||
/*
|
||||
* Copyright (C) 2020 The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package com.android.keyguard;
|
||||
|
||||
import static android.hardware.biometrics.BiometricSourceType.FINGERPRINT;
|
||||
|
||||
import android.hardware.biometrics.BiometricSourceType;
|
||||
import android.view.View;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
|
||||
import com.android.systemui.Dumpable;
|
||||
import com.android.systemui.biometrics.AuthController;
|
||||
import com.android.systemui.dagger.SysUISingleton;
|
||||
import com.android.systemui.plugins.statusbar.StatusBarStateController;
|
||||
import com.android.systemui.statusbar.StatusBarState;
|
||||
import com.android.systemui.util.ViewController;
|
||||
|
||||
import java.io.FileDescriptor;
|
||||
import java.io.PrintWriter;
|
||||
|
||||
/**
|
||||
* Controls when to show the DisabledUdfpsView to unlock the device on the lockscreen.
|
||||
* If the device is not authenticated, the bouncer will show.
|
||||
*
|
||||
* This tap target will only show when:
|
||||
* - User has UDFPS enrolled
|
||||
* - UDFPS is currently unavailable see {@link KeyguardUpdateMonitor#shouldListenForUdfps}
|
||||
*/
|
||||
@SysUISingleton
|
||||
public class DisabledUdfpsController extends ViewController<DisabledUdfpsView> implements Dumpable {
|
||||
@NonNull private final KeyguardUpdateMonitor mKeyguardUpdateMonitor;
|
||||
@NonNull private final KeyguardViewController mKeyguardViewController;
|
||||
@NonNull private final StatusBarStateController mStatusBarStateController;
|
||||
|
||||
private boolean mIsDozing;
|
||||
private boolean mIsBouncerShowing;
|
||||
private boolean mIsKeyguardShowing;
|
||||
private boolean mRunningFPS;
|
||||
private boolean mAuthenticated;
|
||||
|
||||
private boolean mShowButton;
|
||||
|
||||
public DisabledUdfpsController(
|
||||
@NonNull DisabledUdfpsView view,
|
||||
@NonNull StatusBarStateController statusBarStateController,
|
||||
@NonNull KeyguardUpdateMonitor keyguardUpdateMonitor,
|
||||
@NonNull AuthController authController,
|
||||
@NonNull KeyguardViewController keyguardViewController
|
||||
) {
|
||||
super(view);
|
||||
mView.setOnClickListener(mOnClickListener);
|
||||
mView.setSensorProperties(authController.getUdfpsProps().get(0));
|
||||
|
||||
mStatusBarStateController = statusBarStateController;
|
||||
mKeyguardUpdateMonitor = keyguardUpdateMonitor;
|
||||
mKeyguardViewController = keyguardViewController;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onViewAttached() {
|
||||
mKeyguardUpdateMonitor.registerCallback(mKeyguardUpdateMonitorCallback);
|
||||
mIsBouncerShowing = mKeyguardViewController.isBouncerShowing();
|
||||
|
||||
mStatusBarStateController.addCallback(mStatusBarStateListener);
|
||||
mIsKeyguardShowing = mStatusBarStateController.getState() == StatusBarState.KEYGUARD;
|
||||
mIsDozing = mStatusBarStateController.isDozing();
|
||||
mAuthenticated = false;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onViewDetached() {
|
||||
mKeyguardUpdateMonitor.removeCallback(mKeyguardUpdateMonitorCallback);
|
||||
mStatusBarStateController.removeCallback(mStatusBarStateListener);
|
||||
}
|
||||
|
||||
private void updateButtonVisibility() {
|
||||
mShowButton = !mAuthenticated && !mIsDozing && mIsKeyguardShowing
|
||||
&& !mIsBouncerShowing && !mRunningFPS;
|
||||
if (mShowButton) {
|
||||
mView.setVisibility(View.VISIBLE);
|
||||
} else {
|
||||
mView.setVisibility(View.INVISIBLE);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void dump(@NonNull FileDescriptor fd, @NonNull PrintWriter pw, @NonNull String[] args) {
|
||||
pw.println("DisabledUdfpsController state:");
|
||||
pw.println(" mShowBouncerButton: " + mShowButton);
|
||||
pw.println(" mIsDozing: " + mIsDozing);
|
||||
pw.println(" mIsKeyguardShowing: " + mIsKeyguardShowing);
|
||||
pw.println(" mIsBouncerShowing: " + mIsBouncerShowing);
|
||||
pw.println(" mRunningFPS: " + mRunningFPS);
|
||||
pw.println(" mAuthenticated: " + mAuthenticated);
|
||||
}
|
||||
|
||||
private final View.OnClickListener mOnClickListener = new View.OnClickListener() {
|
||||
@Override
|
||||
public void onClick(View v) {
|
||||
mKeyguardViewController.showBouncer(/* scrim */ true);
|
||||
}
|
||||
};
|
||||
|
||||
private StatusBarStateController.StateListener mStatusBarStateListener =
|
||||
new StatusBarStateController.StateListener() {
|
||||
@Override
|
||||
public void onStateChanged(int newState) {
|
||||
mIsKeyguardShowing = newState == StatusBarState.KEYGUARD;
|
||||
updateButtonVisibility();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDozingChanged(boolean isDozing) {
|
||||
mIsDozing = isDozing;
|
||||
updateButtonVisibility();
|
||||
}
|
||||
};
|
||||
|
||||
private final KeyguardUpdateMonitorCallback mKeyguardUpdateMonitorCallback =
|
||||
new KeyguardUpdateMonitorCallback() {
|
||||
@Override
|
||||
public void onKeyguardBouncerChanged(boolean bouncer) {
|
||||
mIsBouncerShowing = bouncer;
|
||||
updateButtonVisibility();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onBiometricRunningStateChanged(boolean running,
|
||||
BiometricSourceType biometricSourceType) {
|
||||
mRunningFPS = running && biometricSourceType == FINGERPRINT;
|
||||
updateButtonVisibility();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onUserUnlocked() {
|
||||
mAuthenticated = true;
|
||||
updateButtonVisibility();
|
||||
}
|
||||
};
|
||||
}
|
||||
@@ -0,0 +1,89 @@
|
||||
/*
|
||||
* Copyright (C) 2020 The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package com.android.keyguard;
|
||||
|
||||
import android.annotation.NonNull;
|
||||
import android.content.Context;
|
||||
import android.graphics.RectF;
|
||||
import android.hardware.fingerprint.FingerprintSensorPropertiesInternal;
|
||||
import android.util.AttributeSet;
|
||||
import android.view.Surface;
|
||||
import android.widget.Button;
|
||||
import android.widget.FrameLayout;
|
||||
|
||||
/**
|
||||
* A full screen view with an oval target where the UDFPS sensor is.
|
||||
* Controlled by {@link DisabledUdfpsController}.
|
||||
*/
|
||||
public class DisabledUdfpsView extends Button {
|
||||
@NonNull private final RectF mSensorRect;
|
||||
@NonNull private final Context mContext;
|
||||
|
||||
// Used to obtain the sensor location.
|
||||
@NonNull private FingerprintSensorPropertiesInternal mSensorProps;
|
||||
|
||||
public DisabledUdfpsView(Context context, AttributeSet attrs) {
|
||||
super(context, attrs);
|
||||
mContext = context;
|
||||
mSensorRect = new RectF();
|
||||
}
|
||||
|
||||
public void setSensorProperties(@NonNull FingerprintSensorPropertiesInternal properties) {
|
||||
mSensorProps = properties;
|
||||
}
|
||||
|
||||
// The "h" and "w" are the display's height and width relative to its current rotation.
|
||||
private void updateSensorRect(int h, int w) {
|
||||
// mSensorProps coordinates assume portrait mode.
|
||||
mSensorRect.set(mSensorProps.sensorLocationX - mSensorProps.sensorRadius,
|
||||
mSensorProps.sensorLocationY - mSensorProps.sensorRadius,
|
||||
mSensorProps.sensorLocationX + mSensorProps.sensorRadius,
|
||||
mSensorProps.sensorLocationY + mSensorProps.sensorRadius);
|
||||
|
||||
// Transform mSensorRect if the device is in landscape mode.
|
||||
switch (mContext.getDisplay().getRotation()) {
|
||||
case Surface.ROTATION_90:
|
||||
mSensorRect.set(mSensorRect.top, h - mSensorRect.right, mSensorRect.bottom,
|
||||
h - mSensorRect.left);
|
||||
break;
|
||||
case Surface.ROTATION_270:
|
||||
mSensorRect.set(w - mSensorRect.bottom, mSensorRect.left, w - mSensorRect.top,
|
||||
mSensorRect.right);
|
||||
break;
|
||||
default:
|
||||
// Do nothing to stay in portrait mode.
|
||||
}
|
||||
|
||||
setX(mSensorRect.left);
|
||||
setY(mSensorRect.top);
|
||||
setLayoutParams(new FrameLayout.LayoutParams(
|
||||
(int) (mSensorRect.right - mSensorRect.left),
|
||||
(int) (mSensorRect.bottom - mSensorRect.top)));
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
|
||||
super.onLayout(changed, left, top, right, bottom);
|
||||
// Always re-compute the layout regardless of whether "changed" is true. It is usually false
|
||||
// when the device goes from landscape to seascape and vice versa, but mSensorRect and
|
||||
// its dependencies need to be recalculated to stay at the same physical location on the
|
||||
// screen.
|
||||
final int w = getLayoutParams().width;
|
||||
final int h = getLayoutParams().height;
|
||||
updateSensorRect(h, w);
|
||||
}
|
||||
}
|
||||
@@ -1925,6 +1925,7 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab
|
||||
}
|
||||
|
||||
// TODO: Add support for multiple fingerprint sensors, b/173730729
|
||||
updateUdfpsEnrolled(getCurrentUser());
|
||||
boolean shouldListenForFingerprint =
|
||||
isUdfpsEnrolled() ? shouldListenForUdfps() : shouldListenForFingerprint();
|
||||
boolean runningOrRestarting = mFingerprintRunningState == BIOMETRIC_STATE_RUNNING
|
||||
@@ -2137,7 +2138,6 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab
|
||||
}
|
||||
if (DEBUG) Log.v(TAG, "startListeningForFingerprint()");
|
||||
int userId = getCurrentUser();
|
||||
updateUdfpsEnrolled(userId);
|
||||
if (isUnlockWithFingerprintPossible(userId)) {
|
||||
if (mFingerprintCancelSignal != null) {
|
||||
mFingerprintCancelSignal.cancel();
|
||||
@@ -2627,7 +2627,6 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab
|
||||
Assert.isMainThread();
|
||||
if (DEBUG) Log.d(TAG, "handleKeyguardBouncerChanged(" + bouncerVisible + ")");
|
||||
mBouncer = bouncerVisible == 1;
|
||||
|
||||
if (mBouncer) {
|
||||
// If the bouncer is shown, always clear this flag. This can happen in the following
|
||||
// situations: 1) Default camera with SHOW_WHEN_LOCKED is not chosen yet. 2) Secure
|
||||
|
||||
@@ -413,6 +413,11 @@ public class AuthController extends SystemUI implements CommandQueue.Callbacks,
|
||||
mCurrentDialog.onHelp(message);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public List<FingerprintSensorPropertiesInternal> getUdfpsProps() {
|
||||
return mUdfpsProps;
|
||||
}
|
||||
|
||||
private String getErrorString(int modality, int error, int vendorCode) {
|
||||
switch (modality) {
|
||||
case TYPE_FACE:
|
||||
|
||||
@@ -68,6 +68,7 @@ import com.android.internal.jank.InteractionJankMonitor;
|
||||
import com.android.internal.logging.MetricsLogger;
|
||||
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
|
||||
import com.android.internal.util.LatencyTracker;
|
||||
import com.android.keyguard.DisabledUdfpsController;
|
||||
import com.android.keyguard.KeyguardClockSwitchController;
|
||||
import com.android.keyguard.KeyguardStatusView;
|
||||
import com.android.keyguard.KeyguardStatusViewController;
|
||||
@@ -255,7 +256,25 @@ public class NotificationPanelViewController extends PanelViewController {
|
||||
mFirstBypassAttempt = mKeyguardBypassController.getBypassEnabled();
|
||||
mDelayShowingKeyguardStatusBar = false;
|
||||
}
|
||||
};
|
||||
|
||||
@Override
|
||||
public void onKeyguardVisibilityChanged(boolean showing) {
|
||||
if (mDisabledUdfpsController == null
|
||||
&& mAuthController.getUdfpsRegion() != null
|
||||
&& mAuthController.isUdfpsEnrolled(
|
||||
KeyguardUpdateMonitor.getCurrentUser())) {
|
||||
LayoutInflater.from(mView.getContext())
|
||||
.inflate(R.layout.disabled_udfps_view, mView);
|
||||
mDisabledUdfpsController = new DisabledUdfpsController(
|
||||
mView.findViewById(R.id.disabled_udfps_view),
|
||||
mStatusBarStateController,
|
||||
mUpdateMonitor,
|
||||
mAuthController,
|
||||
mStatusBarKeyguardViewManager);
|
||||
mDisabledUdfpsController.init();
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
private final InjectionInflationController mInjectionInflationController;
|
||||
private final PowerManager mPowerManager;
|
||||
@@ -283,6 +302,7 @@ public class NotificationPanelViewController extends PanelViewController {
|
||||
private QS mQs;
|
||||
private FrameLayout mQsFrame;
|
||||
private KeyguardStatusViewController mKeyguardStatusViewController;
|
||||
private DisabledUdfpsController mDisabledUdfpsController;
|
||||
private View mQsNavbarScrim;
|
||||
private NotificationsQuickSettingsContainer mNotificationContainerParent;
|
||||
private boolean mAnimateNextPositionUpdate;
|
||||
@@ -3041,6 +3061,9 @@ public class NotificationPanelViewController extends PanelViewController {
|
||||
if (mKeyguardStatusBar != null) {
|
||||
mKeyguardStatusBar.dump(fd, pw, args);
|
||||
}
|
||||
if (mDisabledUdfpsController != null) {
|
||||
mDisabledUdfpsController.dump(fd, pw, args);
|
||||
}
|
||||
}
|
||||
|
||||
public boolean hasActiveClearableNotifications() {
|
||||
|
||||
Reference in New Issue
Block a user