summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
author Yabin Huang <yabinh@google.com> 2023-06-06 14:53:53 -0700
committer Yabin Huang <yabinh@google.com> 2023-08-22 21:21:44 +0000
commitaafe0849b9ae77a2d802e26c380aa92bac4d2bda (patch)
tree775e565274d64850d7de2a6bf42d1c6e6ba2018b
parent6162ea96867142ee7ebffb6dd2655deded0c6f68 (diff)
Allow to customize BiometricsPromt for automative builds
- Allow to inflate different layouts for credential pin and password - Use the same layout for credential pin and password so that the layout stays the same for non-automative builds - Specify the layout of CredentialPasswordView in its layout file instead of programmatically so that it can be customized easily - Introduce IPinPad, which will used in automative variation of auth_credential_pin_view Bug: 276918288 Test: manual Change-Id: I3aec4081144b51014cdaf1cde70a04c8b2006240
-rw-r--r--packages/SystemUI/res/layout-land/auth_credential_password_pin_content_view.xml101
-rw-r--r--packages/SystemUI/res/layout-land/auth_credential_password_view.xml80
-rw-r--r--packages/SystemUI/res/layout-land/auth_credential_pin_view.xml28
-rw-r--r--packages/SystemUI/res/layout/auth_credential_password_pin_content_view.xml104
-rw-r--r--packages/SystemUI/res/layout/auth_credential_password_view.xml84
-rw-r--r--packages/SystemUI/res/layout/auth_credential_pin_view.xml28
-rw-r--r--packages/SystemUI/res/values/ids.xml3
-rw-r--r--packages/SystemUI/src/com/android/systemui/biometrics/AuthContainerView.java2
-rw-r--r--packages/SystemUI/src/com/android/systemui/biometrics/ui/CredentialPasswordView.kt109
-rw-r--r--packages/SystemUI/src/com/android/systemui/biometrics/ui/IPinPad.kt42
-rw-r--r--packages/SystemUI/src/com/android/systemui/biometrics/ui/binder/CredentialPasswordViewBinder.kt11
-rw-r--r--packages/SystemUI/src/com/android/systemui/biometrics/ui/binder/CredentialViewBinder.kt18
-rw-r--r--packages/SystemUI/src/com/android/systemui/biometrics/ui/binder/PinPadViewBinder.kt64
13 files changed, 419 insertions, 255 deletions
diff --git a/packages/SystemUI/res/layout-land/auth_credential_password_pin_content_view.xml b/packages/SystemUI/res/layout-land/auth_credential_password_pin_content_view.xml
new file mode 100644
index 000000000000..24222f7642be
--- /dev/null
+++ b/packages/SystemUI/res/layout-land/auth_credential_password_pin_content_view.xml
@@ -0,0 +1,101 @@
+<!--
+ ~ Copyright (C) 2019 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.
+ -->
+
+<merge xmlns:android="http://schemas.android.com/apk/res/android">
+
+ <RelativeLayout
+ android:id="@+id/auth_credential_header"
+ style="?headerStyle"
+ android:layout_width="0dp"
+ android:layout_height="wrap_content"
+ android:layout_weight="1">
+
+ <ImageView
+ android:id="@+id/icon"
+ style="?headerIconStyle"
+ android:layout_alignParentLeft="true"
+ android:layout_alignParentTop="true"
+ android:contentDescription="@null"/>
+
+ <TextView
+ android:id="@+id/title"
+ style="?titleTextAppearance"
+ android:layout_below="@id/icon"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content" />
+
+ <TextView
+ android:id="@+id/subtitle"
+ style="?subTitleTextAppearance"
+ android:layout_below="@id/title"
+ android:layout_alignParentLeft="true"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content" />
+
+ <TextView
+ android:id="@+id/description"
+ style="?descriptionTextAppearance"
+ android:layout_below="@id/subtitle"
+ android:layout_alignParentLeft="true"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content" />
+
+ </RelativeLayout>
+
+ <FrameLayout
+ android:id="@+id/auth_credential_input"
+ android:layout_width="0dp"
+ android:layout_height="match_parent"
+ android:layout_weight="1"
+ android:orientation="vertical">
+
+ <LinearLayout
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_gravity="center"
+ android:orientation="vertical">
+
+ <ImeAwareEditText
+ android:id="@+id/lockPassword"
+ style="?passwordTextAppearance"
+ android:layout_width="208dp"
+ android:layout_height="wrap_content"
+ android:layout_gravity="center_horizontal"
+ android:imeOptions="actionNext|flagNoFullscreen|flagForceAscii"
+ android:inputType="textPassword"
+ android:minHeight="48dp"/>
+
+ <TextView
+ android:id="@+id/error"
+ style="?errorTextAppearance"
+ android:layout_gravity="center_horizontal"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"/>
+ </LinearLayout>
+
+ <Button
+ android:id="@+id/emergencyCallButton"
+ style="@style/AuthCredentialEmergencyButtonStyle"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:visibility="gone"
+ android:layout_gravity="center_horizontal|bottom"
+ android:layout_marginTop="12dp"
+ android:layout_marginBottom="12dp"
+ android:text="@string/work_challenge_emergency_button_text"/>
+ </FrameLayout>
+
+</merge>
diff --git a/packages/SystemUI/res/layout-land/auth_credential_password_view.xml b/packages/SystemUI/res/layout-land/auth_credential_password_view.xml
index e439f775f8ea..8ac7583088f9 100644
--- a/packages/SystemUI/res/layout-land/auth_credential_password_view.xml
+++ b/packages/SystemUI/res/layout-land/auth_credential_password_view.xml
@@ -23,84 +23,6 @@
android:elevation="@dimen/biometric_dialog_elevation"
android:theme="?app:attr/lockPinPasswordStyle">
- <RelativeLayout
- android:id="@+id/auth_credential_header"
- style="?headerStyle"
- android:layout_width="wrap_content"
- android:layout_height="match_parent">
-
- <ImageView
- android:id="@+id/icon"
- style="?headerIconStyle"
- android:layout_alignParentLeft="true"
- android:layout_alignParentTop="true"
- android:contentDescription="@null"/>
-
- <TextView
- android:id="@+id/title"
- style="?titleTextAppearance"
- android:layout_below="@id/icon"
- android:layout_width="match_parent"
- android:layout_height="wrap_content" />
-
- <TextView
- android:id="@+id/subtitle"
- style="?subTitleTextAppearance"
- android:layout_below="@id/title"
- android:layout_alignParentLeft="true"
- android:layout_width="match_parent"
- android:layout_height="wrap_content" />
-
- <TextView
- android:id="@+id/description"
- style="?descriptionTextAppearance"
- android:layout_below="@id/subtitle"
- android:layout_alignParentLeft="true"
- android:layout_width="match_parent"
- android:layout_height="wrap_content" />
-
- </RelativeLayout>
-
- <FrameLayout
- android:id="@+id/auth_credential_input"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:orientation="vertical">
-
- <LinearLayout
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_gravity="center_horizontal|top"
- android:orientation="vertical">
-
- <ImeAwareEditText
- android:id="@+id/lockPassword"
- style="?passwordTextAppearance"
- android:layout_width="208dp"
- android:layout_height="wrap_content"
- android:layout_gravity="center_horizontal"
- android:imeOptions="actionNext|flagNoFullscreen|flagForceAscii"
- android:inputType="textPassword"
- android:minHeight="48dp"/>
-
- <TextView
- android:id="@+id/error"
- style="?errorTextAppearance"
- android:layout_gravity="center_horizontal"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"/>
- </LinearLayout>
-
- <Button
- android:id="@+id/emergencyCallButton"
- style="@style/AuthCredentialEmergencyButtonStyle"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:visibility="gone"
- android:layout_gravity="center_horizontal|bottom"
- android:layout_marginTop="12dp"
- android:layout_marginBottom="12dp"
- android:text="@string/work_challenge_emergency_button_text"/>
- </FrameLayout>
+ <include layout="@layout/auth_credential_password_pin_content_view" />
</com.android.systemui.biometrics.ui.CredentialPasswordView> \ No newline at end of file
diff --git a/packages/SystemUI/res/layout-land/auth_credential_pin_view.xml b/packages/SystemUI/res/layout-land/auth_credential_pin_view.xml
new file mode 100644
index 000000000000..8ac7583088f9
--- /dev/null
+++ b/packages/SystemUI/res/layout-land/auth_credential_pin_view.xml
@@ -0,0 +1,28 @@
+<!--
+ ~ 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.ui.CredentialPasswordView
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:app="http://schemas.android.com/apk/res-auto"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent"
+ android:orientation="horizontal"
+ android:elevation="@dimen/biometric_dialog_elevation"
+ android:theme="?app:attr/lockPinPasswordStyle">
+
+ <include layout="@layout/auth_credential_password_pin_content_view" />
+
+</com.android.systemui.biometrics.ui.CredentialPasswordView> \ No newline at end of file
diff --git a/packages/SystemUI/res/layout/auth_credential_password_pin_content_view.xml b/packages/SystemUI/res/layout/auth_credential_password_pin_content_view.xml
new file mode 100644
index 000000000000..11284fd2237b
--- /dev/null
+++ b/packages/SystemUI/res/layout/auth_credential_password_pin_content_view.xml
@@ -0,0 +1,104 @@
+<!--
+ ~ Copyright (C) 2019 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.
+ -->
+
+<merge xmlns:android="http://schemas.android.com/apk/res/android">
+
+ <ScrollView
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content">
+
+ <RelativeLayout
+ android:id="@+id/auth_credential_header"
+ style="?headerStyle"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:paddingBottom="0dp">
+
+ <ImageView
+ android:id="@+id/icon"
+ style="?headerIconStyle"
+ android:layout_alignParentLeft="true"
+ android:layout_alignParentTop="true"
+ android:contentDescription="@null" />
+
+ <TextView
+ android:id="@+id/title"
+ style="?titleTextAppearance"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:layout_below="@id/icon" />
+
+ <TextView
+ android:id="@+id/subtitle"
+ style="?subTitleTextAppearance"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:layout_below="@id/title" />
+
+ <TextView
+ android:id="@+id/description"
+ style="?descriptionTextAppearance"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:layout_below="@id/subtitle" />
+
+ </RelativeLayout>
+
+ </ScrollView>
+
+ <FrameLayout
+ android:id="@+id/auth_credential_input"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent"
+ android:orientation="vertical">
+
+ <LinearLayout
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:layout_gravity="center"
+ android:orientation="vertical">
+
+ <ImeAwareEditText
+ android:id="@+id/lockPassword"
+ style="?passwordTextAppearance"
+ android:layout_width="208dp"
+ android:layout_height="wrap_content"
+ android:layout_gravity="center_horizontal"
+ android:imeOptions="actionNext|flagNoFullscreen|flagForceAscii"
+ android:inputType="textPassword"
+ android:minHeight="48dp"/>
+
+ <TextView
+ android:id="@+id/error"
+ style="?errorTextAppearance"
+ android:layout_gravity="center_horizontal"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"/>
+ </LinearLayout>
+
+ <Button
+ android:id="@+id/emergencyCallButton"
+ style="@style/AuthCredentialEmergencyButtonStyle"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:visibility="gone"
+ android:layout_gravity="center_horizontal|bottom"
+ android:layout_marginTop="12dp"
+ android:layout_marginBottom="12dp"
+ android:text="@string/work_challenge_emergency_button_text"/>
+ </FrameLayout>
+
+</merge>
diff --git a/packages/SystemUI/res/layout/auth_credential_password_view.xml b/packages/SystemUI/res/layout/auth_credential_password_view.xml
index 9336845f20f7..f8d9a87d5e54 100644
--- a/packages/SystemUI/res/layout/auth_credential_password_view.xml
+++ b/packages/SystemUI/res/layout/auth_credential_password_view.xml
@@ -23,88 +23,6 @@
android:orientation="vertical"
android:theme="?app:attr/lockPinPasswordStyle">
- <ScrollView
- android:id="@+id/auth_credential_header"
- android:layout_width="match_parent"
- android:layout_height="wrap_content">
-
- <RelativeLayout
- style="?headerStyle"
- android:layout_width="match_parent"
- android:layout_height="wrap_content">
-
- <ImageView
- android:id="@+id/icon"
- style="?headerIconStyle"
- android:layout_alignParentLeft="true"
- android:layout_alignParentTop="true"
- android:contentDescription="@null" />
-
- <TextView
- android:id="@+id/title"
- style="?titleTextAppearance"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:layout_below="@id/icon" />
-
- <TextView
- android:id="@+id/subtitle"
- style="?subTitleTextAppearance"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:layout_below="@id/title" />
-
- <TextView
- android:id="@+id/description"
- style="?descriptionTextAppearance"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:layout_below="@id/subtitle" />
-
- </RelativeLayout>
-
- </ScrollView>
-
- <FrameLayout
- android:id="@+id/auth_credential_input"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:orientation="vertical">
-
- <LinearLayout
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:layout_gravity="center_horizontal|top"
- android:orientation="vertical">
-
- <ImeAwareEditText
- android:id="@+id/lockPassword"
- style="?passwordTextAppearance"
- android:layout_width="208dp"
- android:layout_height="wrap_content"
- android:layout_gravity="center_horizontal"
- android:imeOptions="actionNext|flagNoFullscreen|flagForceAscii"
- android:inputType="textPassword"
- android:minHeight="48dp"/>
-
- <TextView
- android:id="@+id/error"
- style="?errorTextAppearance"
- android:layout_gravity="center_horizontal"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"/>
- </LinearLayout>
-
- <Button
- android:id="@+id/emergencyCallButton"
- style="@style/AuthCredentialEmergencyButtonStyle"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:visibility="gone"
- android:layout_gravity="center_horizontal|bottom"
- android:layout_marginTop="12dp"
- android:layout_marginBottom="12dp"
- android:text="@string/work_challenge_emergency_button_text"/>
- </FrameLayout>
+ <include layout="@layout/auth_credential_password_pin_content_view" />
</com.android.systemui.biometrics.ui.CredentialPasswordView> \ No newline at end of file
diff --git a/packages/SystemUI/res/layout/auth_credential_pin_view.xml b/packages/SystemUI/res/layout/auth_credential_pin_view.xml
new file mode 100644
index 000000000000..a1cf807af088
--- /dev/null
+++ b/packages/SystemUI/res/layout/auth_credential_pin_view.xml
@@ -0,0 +1,28 @@
+<!--
+ ~ Copyright (C) 2019 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.ui.CredentialPasswordView
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:app="http://schemas.android.com/apk/res-auto"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent"
+ android:elevation="@dimen/biometric_dialog_elevation"
+ android:orientation="vertical"
+ android:theme="?app:attr/lockPinPasswordStyle">
+
+ <include layout="@layout/auth_credential_password_pin_content_view" />
+
+</com.android.systemui.biometrics.ui.CredentialPasswordView> \ No newline at end of file
diff --git a/packages/SystemUI/res/values/ids.xml b/packages/SystemUI/res/values/ids.xml
index fd1de25e8174..04eae64013b3 100644
--- a/packages/SystemUI/res/values/ids.xml
+++ b/packages/SystemUI/res/values/ids.xml
@@ -223,6 +223,9 @@
<!-- Communal mode -->
<item type="id" name="communal_widget_wrapper" />
+ <!-- Values assigned to the views in Biometrics Prompt -->
+ <item type="id" name="pin_pad"/>
+
<!--
Used to tag views programmatically added to the smartspace area so they can be more easily
removed later.
diff --git a/packages/SystemUI/src/com/android/systemui/biometrics/AuthContainerView.java b/packages/SystemUI/src/com/android/systemui/biometrics/AuthContainerView.java
index 802a550c4d29..7464c8803c99 100644
--- a/packages/SystemUI/src/com/android/systemui/biometrics/AuthContainerView.java
+++ b/packages/SystemUI/src/com/android/systemui/biometrics/AuthContainerView.java
@@ -499,6 +499,8 @@ public class AuthContainerView extends LinearLayout
R.layout.auth_credential_pattern_view, null, false);
break;
case Utils.CREDENTIAL_PIN:
+ mCredentialView = factory.inflate(R.layout.auth_credential_pin_view, null, false);
+ break;
case Utils.CREDENTIAL_PASSWORD:
mCredentialView = factory.inflate(
R.layout.auth_credential_password_view, null, false);
diff --git a/packages/SystemUI/src/com/android/systemui/biometrics/ui/CredentialPasswordView.kt b/packages/SystemUI/src/com/android/systemui/biometrics/ui/CredentialPasswordView.kt
index 709fe855fbfc..6c5cc4835787 100644
--- a/packages/SystemUI/src/com/android/systemui/biometrics/ui/CredentialPasswordView.kt
+++ b/packages/SystemUI/src/com/android/systemui/biometrics/ui/CredentialPasswordView.kt
@@ -8,11 +8,8 @@ import android.view.View
import android.view.WindowInsets
import android.view.WindowInsets.Type.ime
import android.view.accessibility.AccessibilityManager
-import android.widget.ImageView
-import android.widget.ImeAwareEditText
import android.widget.LinearLayout
import android.widget.TextView
-import androidx.core.view.isGone
import com.android.systemui.R
import com.android.systemui.biometrics.AuthPanelController
import com.android.systemui.biometrics.ui.binder.CredentialViewBinder
@@ -22,14 +19,6 @@ import com.android.systemui.biometrics.ui.viewmodel.CredentialViewModel
class CredentialPasswordView(context: Context, attrs: AttributeSet?) :
LinearLayout(context, attrs), CredentialView, View.OnApplyWindowInsetsListener {
- private lateinit var titleView: TextView
- private lateinit var subtitleView: TextView
- private lateinit var descriptionView: TextView
- private lateinit var iconView: ImageView
- private lateinit var passwordField: ImeAwareEditText
- private lateinit var credentialHeader: View
- private lateinit var credentialInput: View
-
private var bottomInset: Int = 0
private val accessibilityManager by lazy {
@@ -48,90 +37,32 @@ class CredentialPasswordView(context: Context, attrs: AttributeSet?) :
override fun onFinishInflate() {
super.onFinishInflate()
-
- titleView = requireViewById(R.id.title)
- subtitleView = requireViewById(R.id.subtitle)
- descriptionView = requireViewById(R.id.description)
- iconView = requireViewById(R.id.icon)
- passwordField = requireViewById(R.id.lockPassword)
- credentialHeader = requireViewById(R.id.auth_credential_header)
- credentialInput = requireViewById(R.id.auth_credential_input)
-
setOnApplyWindowInsetsListener(this)
}
- override fun onLayout(changed: Boolean, l: Int, t: Int, r: Int, b: Int) {
- super.onLayout(changed, left, top, right, bottom)
-
- val inputLeftBound: Int
- var inputTopBound: Int
- var headerRightBound = right
- var headerTopBounds = top
- var headerBottomBounds = bottom
- val subTitleBottom: Int = if (subtitleView.isGone) titleView.bottom else subtitleView.bottom
- val descBottom = if (descriptionView.isGone) subTitleBottom else descriptionView.bottom
- if (resources.configuration.orientation == ORIENTATION_LANDSCAPE) {
- inputTopBound = (bottom - credentialInput.height) / 2
- inputLeftBound = (right - left) / 2
- headerRightBound = inputLeftBound
- if (descriptionView.bottom > headerBottomBounds) {
- headerTopBounds -= iconView.bottom.coerceAtMost(bottomInset)
- credentialHeader.layout(left, headerTopBounds, headerRightBound, bottom)
- }
- } else {
- inputTopBound = descBottom + (bottom - descBottom - credentialInput.height) / 2
- inputLeftBound = (right - left - credentialInput.width) / 2
-
- if (bottom - inputTopBound < credentialInput.height) {
- inputTopBound = bottom - credentialInput.height
- }
-
- if (descriptionView.bottom > inputTopBound) {
- credentialHeader.layout(left, headerTopBounds, headerRightBound, inputTopBound)
- }
- }
-
- credentialInput.layout(inputLeftBound, inputTopBound, right, bottom)
- }
-
- override fun onMeasure(widthMeasureSpec: Int, heightMeasureSpec: Int) {
- super.onMeasure(widthMeasureSpec, heightMeasureSpec)
-
- val newWidth = MeasureSpec.getSize(widthMeasureSpec)
- val newHeight = MeasureSpec.getSize(heightMeasureSpec) - bottomInset
-
- setMeasuredDimension(newWidth, newHeight)
-
- val halfWidthSpec = MeasureSpec.makeMeasureSpec(width / 2, MeasureSpec.AT_MOST)
- val fullHeightSpec = MeasureSpec.makeMeasureSpec(newHeight, MeasureSpec.UNSPECIFIED)
- if (resources.configuration.orientation == ORIENTATION_LANDSCAPE) {
- measureChildren(halfWidthSpec, fullHeightSpec)
- } else {
- measureChildren(widthMeasureSpec, fullHeightSpec)
- }
- }
-
override fun onApplyWindowInsets(v: View, insets: WindowInsets): WindowInsets {
- val bottomInsets = insets.getInsets(ime())
- if (bottomInset != bottomInsets.bottom) {
- bottomInset = bottomInsets.bottom
-
- if (bottomInset > 0 && resources.configuration.orientation == ORIENTATION_LANDSCAPE) {
- titleView.isSingleLine = true
- titleView.ellipsize = TextUtils.TruncateAt.MARQUEE
- titleView.marqueeRepeatLimit = -1
- // select to enable marquee unless a screen reader is enabled
- titleView.isSelected = accessibilityManager?.shouldMarquee() ?: false
- } else {
- titleView.isSingleLine = false
- titleView.ellipsize = null
- // select to enable marquee unless a screen reader is enabled
- titleView.isSelected = false
+ val imeBottomInset = insets.getInsets(ime()).bottom
+ if (bottomInset != imeBottomInset) {
+ val titleView: TextView? = findViewById(R.id.title)
+ if (titleView != null) {
+ if (
+ bottomInset > 0 && resources.configuration.orientation == ORIENTATION_LANDSCAPE
+ ) {
+ titleView.isSingleLine = true
+ titleView.ellipsize = TextUtils.TruncateAt.MARQUEE
+ titleView.marqueeRepeatLimit = -1
+ // select to enable marquee unless a screen reader is enabled
+ titleView.isSelected = accessibilityManager.shouldMarquee()
+ } else {
+ titleView.isSingleLine = false
+ titleView.ellipsize = null
+ // select to enable marquee unless a screen reader is enabled
+ titleView.isSelected = false
+ }
}
-
- requestLayout()
}
- return insets
+ setPadding(paddingLeft, paddingTop, paddingRight, imeBottomInset)
+ return insets.inset(0, 0, 0, imeBottomInset)
}
}
diff --git a/packages/SystemUI/src/com/android/systemui/biometrics/ui/IPinPad.kt b/packages/SystemUI/src/com/android/systemui/biometrics/ui/IPinPad.kt
new file mode 100644
index 000000000000..cf6865c0fe8e
--- /dev/null
+++ b/packages/SystemUI/src/com/android/systemui/biometrics/ui/IPinPad.kt
@@ -0,0 +1,42 @@
+/*
+ * Copyright (C) 2023 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.systemui.biometrics.ui
+
+/**
+ * Interface for PinPad in auth_credential_pin_view. This is needed when a custom pin pad is
+ * preferred to the IME To use a PinPad, one needs to implement IPinPad interface and provide it in
+ * auth_credential_pin_view and specify the id as [pin_pad]
+ */
+interface IPinPad {
+ fun setPinPadClickListener(pinPadClickListener: PinPadClickListener)
+}
+
+/** The call back interface for onClick event in the view. */
+interface PinPadClickListener {
+ /**
+ * One of the digit key has been clicked.
+ *
+ * @param digit A String representing a digit between 0 and 9.
+ */
+ fun onDigitKeyClick(digit: String?)
+
+ /** The backspace key has been clicked. */
+ fun onBackspaceClick()
+
+ /** The enter key has been clicked. */
+ fun onEnterKeyClick()
+}
diff --git a/packages/SystemUI/src/com/android/systemui/biometrics/ui/binder/CredentialPasswordViewBinder.kt b/packages/SystemUI/src/com/android/systemui/biometrics/ui/binder/CredentialPasswordViewBinder.kt
index c27d71522c2f..996b62e084cb 100644
--- a/packages/SystemUI/src/com/android/systemui/biometrics/ui/binder/CredentialPasswordViewBinder.kt
+++ b/packages/SystemUI/src/com/android/systemui/biometrics/ui/binder/CredentialPasswordViewBinder.kt
@@ -15,6 +15,7 @@ import androidx.lifecycle.repeatOnLifecycle
import com.android.systemui.R
import com.android.systemui.biometrics.ui.CredentialPasswordView
import com.android.systemui.biometrics.ui.CredentialView
+import com.android.systemui.biometrics.ui.IPinPad
import com.android.systemui.biometrics.ui.viewmodel.CredentialViewModel
import com.android.systemui.lifecycle.repeatWhenAttached
import kotlinx.coroutines.awaitCancellation
@@ -53,13 +54,19 @@ object CredentialPasswordViewBinder {
}
)
passwordField.setOnKeyListener(OnBackButtonListener(onBackInvokedCallback))
-
+ val pinPadView = view.findViewById(R.id.pin_pad) as? IPinPad
+ if (pinPadView != null) {
+ PinPadViewBinder.bind(pinPadView, view)
+ }
repeatOnLifecycle(Lifecycle.State.STARTED) {
// dismiss on a valid credential check
launch {
viewModel.validatedAttestation.collect { attestation ->
if (attestation != null) {
- imeManager.hideSoftInputFromWindow(view.windowToken, 0 /* flags */)
+ imeManager.hideSoftInputFromWindow(
+ view.windowToken,
+ 0 // flag
+ )
host.onCredentialMatched(attestation)
} else {
passwordField.setText("")
diff --git a/packages/SystemUI/src/com/android/systemui/biometrics/ui/binder/CredentialViewBinder.kt b/packages/SystemUI/src/com/android/systemui/biometrics/ui/binder/CredentialViewBinder.kt
index 4ac9f967920f..25fe61916644 100644
--- a/packages/SystemUI/src/com/android/systemui/biometrics/ui/binder/CredentialViewBinder.kt
+++ b/packages/SystemUI/src/com/android/systemui/biometrics/ui/binder/CredentialViewBinder.kt
@@ -47,6 +47,7 @@ object CredentialViewBinder {
val descriptionView: TextView = view.requireViewById(R.id.description)
val iconView: ImageView? = view.findViewById(R.id.icon)
val errorView: TextView = view.requireViewById(R.id.error)
+ val cancelButton: Button? = view.findViewById(R.id.cancel_button)
val emergencyButtonView: Button = view.requireViewById(R.id.emergencyCallButton)
var errorTimer: Job? = null
@@ -60,7 +61,7 @@ object CredentialViewBinder {
updateForContentDimensions(
containerWidth,
containerHeight,
- 0 /* animateDurationMs */
+ 0 // animateDurationMs
)
}
}
@@ -103,7 +104,18 @@ object CredentialViewBinder {
}
}
}
- .collect { errorView.textOrHide = it }
+ .collect { it ->
+ val hasError = !it.isNullOrBlank()
+ errorView.visibility =
+ if (hasError) {
+ View.VISIBLE
+ } else if (cancelButton != null) {
+ View.INVISIBLE
+ } else {
+ View.GONE
+ }
+ errorView.text = if (hasError) it else ""
+ }
}
// show an extra dialog if the remaining attempts becomes low
@@ -117,6 +129,8 @@ object CredentialViewBinder {
}
}
+ cancelButton?.setOnClickListener { host.onCredentialAborted() }
+
// bind the auth widget
when (view) {
is CredentialPasswordView ->
diff --git a/packages/SystemUI/src/com/android/systemui/biometrics/ui/binder/PinPadViewBinder.kt b/packages/SystemUI/src/com/android/systemui/biometrics/ui/binder/PinPadViewBinder.kt
new file mode 100644
index 000000000000..906206c27455
--- /dev/null
+++ b/packages/SystemUI/src/com/android/systemui/biometrics/ui/binder/PinPadViewBinder.kt
@@ -0,0 +1,64 @@
+/*
+ * Copyright (C) 2023 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.systemui.biometrics.ui.binder
+
+import android.view.KeyEvent
+import android.widget.ImeAwareEditText
+import com.android.internal.widget.LockscreenCredential
+import com.android.systemui.R
+import com.android.systemui.biometrics.ui.CredentialPasswordView
+import com.android.systemui.biometrics.ui.IPinPad
+import com.android.systemui.biometrics.ui.PinPadClickListener
+
+/** Binder for IPinPad */
+object PinPadViewBinder {
+ /** Implements a PinPadClickListener inside a pin pad */
+ @JvmStatic
+ fun bind(view: IPinPad, credentialPasswordView: CredentialPasswordView) {
+ val passwordField: ImeAwareEditText =
+ credentialPasswordView.requireViewById(R.id.lockPassword)
+ view.setPinPadClickListener(
+ object : PinPadClickListener {
+
+ override fun onDigitKeyClick(digit: String?) {
+ passwordField.append(digit)
+ }
+
+ override fun onBackspaceClick() {
+ val pin = LockscreenCredential.createPinOrNone(passwordField.text)
+ if (pin.size() > 0) {
+ passwordField.text.delete(
+ passwordField.selectionEnd - 1,
+ passwordField.selectionEnd
+ )
+ }
+ pin.zeroize()
+ }
+
+ override fun onEnterKeyClick() {
+ passwordField.dispatchKeyEvent(
+ KeyEvent(0, 0, KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_ENTER, 0)
+ )
+ passwordField.dispatchKeyEvent(
+ KeyEvent(0, 0, KeyEvent.ACTION_UP, KeyEvent.KEYCODE_ENTER, 0)
+ )
+ }
+ }
+ )
+ }
+}