Merge "UDFPS Enrollment refactor (3/N)" into main
This commit is contained in:
committed by
Android (Google) Code Review
commit
398b73a9fb
@@ -17,6 +17,7 @@
|
|||||||
package com.android.settings.biometrics.fingerprint2.ui.enrollment.modules.enrolling.udfps.ui.fragment
|
package com.android.settings.biometrics.fingerprint2.ui.enrollment.modules.enrolling.udfps.ui.fragment
|
||||||
|
|
||||||
import android.os.Bundle
|
import android.os.Bundle
|
||||||
|
import android.util.Log
|
||||||
import android.view.View
|
import android.view.View
|
||||||
import android.view.WindowManager
|
import android.view.WindowManager
|
||||||
import android.widget.TextView
|
import android.widget.TextView
|
||||||
@@ -117,7 +118,9 @@ class UdfpsEnrollFragment() : Fragment(R.layout.fingerprint_v2_udfps_enroll_enro
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
viewLifecycleOwner.lifecycleScope.launch {
|
viewLifecycleOwner.lifecycleScope.launch {
|
||||||
viewModel.udfpsEvent.collect { udfpsEnrollView.onUdfpsEvent(it) }
|
viewModel.udfpsEvent.collect {
|
||||||
|
Log.d(TAG, "EnrollEvent $it")
|
||||||
|
udfpsEnrollView.onUdfpsEvent(it) }
|
||||||
}
|
}
|
||||||
|
|
||||||
viewLifecycleOwner.lifecycleScope.launch {
|
viewLifecycleOwner.lifecycleScope.launch {
|
||||||
|
@@ -151,17 +151,27 @@ class UdfpsViewModel() : ViewModel() {
|
|||||||
private val enrollEvents: List<List<UdfpsEnrollEvent>> =
|
private val enrollEvents: List<List<UdfpsEnrollEvent>> =
|
||||||
listOf(
|
listOf(
|
||||||
listOf(OverlayShown),
|
listOf(OverlayShown),
|
||||||
CreateProgress(10, 10),
|
listOf(UdfpsHelp(1,"hi")),
|
||||||
CreateProgress(9, 10),
|
listOf(UdfpsHelp(1,"hi")),
|
||||||
CreateProgress(8, 10),
|
CreateProgress(15, 16),
|
||||||
CreateProgress(7, 10),
|
listOf(UdfpsHelp(1,"hi")),
|
||||||
CreateProgress(6, 10),
|
CreateProgress(14, 16),
|
||||||
CreateProgress(5, 10),
|
listOf(PointerDown, UdfpsHelp(1,"hi"), PointerUp),
|
||||||
CreateProgress(4, 10),
|
listOf(PointerDown, UdfpsHelp(1,"hi"), PointerUp),
|
||||||
CreateProgress(3, 10),
|
CreateProgress(13, 16),
|
||||||
CreateProgress(2, 10),
|
CreateProgress(12, 16),
|
||||||
CreateProgress(1, 10),
|
CreateProgress(11, 16),
|
||||||
CreateProgress(0, 10),
|
CreateProgress(10, 16),
|
||||||
|
CreateProgress(9, 16),
|
||||||
|
CreateProgress(8, 16),
|
||||||
|
CreateProgress(7, 16),
|
||||||
|
CreateProgress(6, 16),
|
||||||
|
CreateProgress(5, 16),
|
||||||
|
CreateProgress(4, 16),
|
||||||
|
CreateProgress(3, 16),
|
||||||
|
CreateProgress(2, 16),
|
||||||
|
CreateProgress(1, 16),
|
||||||
|
CreateProgress(0, 16),
|
||||||
)
|
)
|
||||||
|
|
||||||
/** This will be removed */
|
/** This will be removed */
|
||||||
|
@@ -169,15 +169,26 @@ class UdfpsEnrollIconV2 internal constructor(context: Context, attrs: AttributeS
|
|||||||
invalidateSelf()
|
invalidateSelf()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** Stop drawing the fingerprint icon. */
|
||||||
|
fun stopDrawing() {
|
||||||
|
alpha = 0
|
||||||
|
}
|
||||||
|
|
||||||
|
/** Resume drawing the fingerprint icon */
|
||||||
|
fun startDrawing() {
|
||||||
|
alpha = 255
|
||||||
|
}
|
||||||
|
|
||||||
override fun draw(canvas: Canvas) {
|
override fun draw(canvas: Canvas) {
|
||||||
|
movingTargetFpIcon.alpha = alpha
|
||||||
|
fingerprintDrawable.setAlpha(alpha)
|
||||||
|
sensorOutlinePaint.setAlpha(alpha)
|
||||||
val currLocation = getCurrLocation()
|
val currLocation = getCurrLocation()
|
||||||
canvas.scale(currentScale, currentScale, currLocation.centerX(), currLocation.centerY())
|
canvas.scale(currentScale, currentScale, currLocation.centerX(), currLocation.centerY())
|
||||||
|
|
||||||
sensorRectBounds?.let { canvas.drawOval(currLocation, sensorOutlinePaint) }
|
sensorRectBounds?.let { canvas.drawOval(currLocation, sensorOutlinePaint) }
|
||||||
fingerprintDrawable.bounds = currLocation.toRect()
|
fingerprintDrawable.bounds = currLocation.toRect()
|
||||||
fingerprintDrawable.draw(canvas)
|
fingerprintDrawable.draw(canvas)
|
||||||
fingerprintDrawable.setAlpha(alpha)
|
|
||||||
sensorOutlinePaint.setAlpha(alpha)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun getCurrLocation(): RectF =
|
private fun getCurrLocation(): RectF =
|
||||||
|
@@ -34,11 +34,11 @@ import android.util.DisplayMetrics
|
|||||||
import android.view.animation.DecelerateInterpolator
|
import android.view.animation.DecelerateInterpolator
|
||||||
import android.view.animation.Interpolator
|
import android.view.animation.Interpolator
|
||||||
import androidx.annotation.ColorInt
|
import androidx.annotation.ColorInt
|
||||||
|
import androidx.core.animation.doOnEnd
|
||||||
import androidx.core.graphics.toRectF
|
import androidx.core.graphics.toRectF
|
||||||
import com.android.internal.annotations.VisibleForTesting
|
import com.android.internal.annotations.VisibleForTesting
|
||||||
import com.android.settings.R
|
import com.android.settings.R
|
||||||
import kotlin.math.max
|
import kotlin.math.max
|
||||||
import kotlin.math.min
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* UDFPS enrollment progress bar. This view is responsible for drawing the progress ring and its
|
* UDFPS enrollment progress bar. This view is responsible for drawing the progress ring and its
|
||||||
@@ -136,18 +136,22 @@ class UdfpsEnrollProgressBarDrawableV2(private val mContext: Context, attrs: Att
|
|||||||
/** Indicates enrollment progress has occurred. */
|
/** Indicates enrollment progress has occurred. */
|
||||||
fun onEnrollmentProgress(remaining: Int, totalSteps: Int) {
|
fun onEnrollmentProgress(remaining: Int, totalSteps: Int) {
|
||||||
afterFirstTouch = true
|
afterFirstTouch = true
|
||||||
updateState(remaining, totalSteps, false /* showingHelp */)
|
updateProgress(remaining, totalSteps)
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Indicates enrollment help has occurred. */
|
/** Indicates enrollment help has occurred. */
|
||||||
fun onEnrollmentHelp(remaining: Int, totalSteps: Int) {
|
fun onEnrollmentHelp() {
|
||||||
updateState(remaining, totalSteps, true /* showingHelp */)
|
if (remainingSteps == totalSteps) {
|
||||||
|
// We haven't had any progress, animate the background arc fill
|
||||||
|
animateBackgroundColor()
|
||||||
|
} else {
|
||||||
|
// else we have had progress, animate the progress fill
|
||||||
|
flashHelpFillColor()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Indicates the last step was acquired. */
|
/** Indicates the last step was acquired. */
|
||||||
fun onLastStepAcquired() {
|
fun onLastStepAcquired() {}
|
||||||
updateState(0, totalSteps, false /* showingHelp */)
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun draw(canvas: Canvas) {
|
override fun draw(canvas: Canvas) {
|
||||||
|
|
||||||
@@ -224,15 +228,12 @@ class UdfpsEnrollProgressBarDrawableV2(private val mContext: Context, attrs: Att
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun updateState(remainingSteps: Int, totalSteps: Int, showingHelp: Boolean) {
|
private fun updateProgress(remainingSteps: Int, totalSteps: Int) {
|
||||||
updateProgress(remainingSteps, totalSteps, showingHelp)
|
|
||||||
updateFillColor(showingHelp)
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun updateProgress(remainingSteps: Int, totalSteps: Int, showingHelp: Boolean) {
|
|
||||||
if (this.remainingSteps == remainingSteps && this.totalSteps == totalSteps) {
|
if (this.remainingSteps == remainingSteps && this.totalSteps == totalSteps) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
this.remainingSteps = remainingSteps
|
||||||
|
this.totalSteps = totalSteps
|
||||||
if (this.showingHelp) {
|
if (this.showingHelp) {
|
||||||
if (vibrator != null && isAccessibilityEnabled) {
|
if (vibrator != null && isAccessibilityEnabled) {
|
||||||
vibrator.vibrate(
|
vibrator.vibrate(
|
||||||
@@ -270,13 +271,8 @@ class UdfpsEnrollProgressBarDrawableV2(private val mContext: Context, attrs: Att
|
|||||||
this.showingHelp = showingHelp
|
this.showingHelp = showingHelp
|
||||||
this.remainingSteps = remainingSteps
|
this.remainingSteps = remainingSteps
|
||||||
this.totalSteps = totalSteps
|
this.totalSteps = totalSteps
|
||||||
val progressSteps = max(0.0, (totalSteps - remainingSteps).toDouble()).toInt()
|
val targetProgress = (totalSteps - remainingSteps).toFloat().div(max(1, totalSteps))
|
||||||
|
|
||||||
// If needed, add 1 to progress and total steps to account for initial touch.
|
|
||||||
val adjustedSteps = if (afterFirstTouch) progressSteps + 1 else progressSteps
|
|
||||||
val adjustedTotal = if (afterFirstTouch) this.totalSteps + 1 else this.totalSteps
|
|
||||||
val targetProgress =
|
|
||||||
min(1.0, (adjustedSteps.toFloat() / adjustedTotal.toFloat()).toDouble()).toFloat()
|
|
||||||
if (progressAnimator != null && progressAnimator!!.isRunning) {
|
if (progressAnimator != null && progressAnimator!!.isRunning) {
|
||||||
progressAnimator!!.cancel()
|
progressAnimator!!.cancel()
|
||||||
}
|
}
|
||||||
@@ -286,13 +282,12 @@ class UdfpsEnrollProgressBarDrawableV2(private val mContext: Context, attrs: Att
|
|||||||
it.addUpdateListener(progressUpdateListener)
|
it.addUpdateListener(progressUpdateListener)
|
||||||
it.start()
|
it.start()
|
||||||
}
|
}
|
||||||
if (remainingSteps == 0) {
|
|
||||||
startCompletionAnimation()
|
|
||||||
} else if (remainingSteps > 0) {
|
|
||||||
rollBackCompletionAnimation()
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Flashes the background progress to a different color, followed by setting it back to the
|
||||||
|
* original progress color.
|
||||||
|
*/
|
||||||
private fun animateBackgroundColor() {
|
private fun animateBackgroundColor() {
|
||||||
if (backgroundColorAnimator != null && backgroundColorAnimator!!.isRunning) {
|
if (backgroundColorAnimator != null && backgroundColorAnimator!!.isRunning) {
|
||||||
backgroundColorAnimator!!.end()
|
backgroundColorAnimator!!.end()
|
||||||
@@ -304,21 +299,20 @@ class UdfpsEnrollProgressBarDrawableV2(private val mContext: Context, attrs: Att
|
|||||||
it.repeatMode = ValueAnimator.REVERSE
|
it.repeatMode = ValueAnimator.REVERSE
|
||||||
it.interpolator = DEACCEL
|
it.interpolator = DEACCEL
|
||||||
it.addUpdateListener(backgroundColorUpdateListener)
|
it.addUpdateListener(backgroundColorUpdateListener)
|
||||||
|
it.doOnEnd { backgroundPaint.color = movingTargetFill }
|
||||||
it.start()
|
it.start()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun updateFillColor(showingHelp: Boolean) {
|
/**
|
||||||
if (!afterFirstTouch && showingHelp) {
|
* Flashes the progress to a different color, followed by setting it back to the original progress
|
||||||
// If we are on the first touch, animate the background color
|
* color.
|
||||||
// instead of the progress color.
|
*/
|
||||||
animateBackgroundColor()
|
private fun flashHelpFillColor() {
|
||||||
return
|
|
||||||
}
|
|
||||||
if (fillColorAnimator != null && fillColorAnimator!!.isRunning) {
|
if (fillColorAnimator != null && fillColorAnimator!!.isRunning) {
|
||||||
fillColorAnimator!!.end()
|
fillColorAnimator!!.end()
|
||||||
}
|
}
|
||||||
@ColorInt val targetColor = if (showingHelp) helpColor else progressColor
|
@ColorInt val targetColor = helpColor
|
||||||
fillColorAnimator =
|
fillColorAnimator =
|
||||||
ValueAnimator.ofArgb(fillPaint.color, targetColor).also {
|
ValueAnimator.ofArgb(fillPaint.color, targetColor).also {
|
||||||
it.setDuration(FILL_COLOR_ANIMATION_DURATION_MS)
|
it.setDuration(FILL_COLOR_ANIMATION_DURATION_MS)
|
||||||
@@ -326,6 +320,7 @@ class UdfpsEnrollProgressBarDrawableV2(private val mContext: Context, attrs: Att
|
|||||||
it.repeatMode = ValueAnimator.REVERSE
|
it.repeatMode = ValueAnimator.REVERSE
|
||||||
it.interpolator = DEACCEL
|
it.interpolator = DEACCEL
|
||||||
it.addUpdateListener(fillColorUpdateListener)
|
it.addUpdateListener(fillColorUpdateListener)
|
||||||
|
it.doOnEnd { fillPaint.color = enrollProgressColor }
|
||||||
it.start()
|
it.start()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -54,23 +54,22 @@ class UdfpsEnrollViewV2(context: Context, attrs: AttributeSet?) : FrameLayout(co
|
|||||||
*/
|
*/
|
||||||
fun setSensorRect(rect: Rect) {
|
fun setSensorRect(rect: Rect) {
|
||||||
this.sensorRect = rect
|
this.sensorRect = rect
|
||||||
post {
|
|
||||||
findViewById<ImageView?>(R.id.udfps_enroll_animation_fp_progress_view)?.also {
|
|
||||||
it.setImageDrawable(fingerprintProgressDrawable)
|
|
||||||
}
|
|
||||||
findViewById<ImageView>(R.id.udfps_enroll_animation_fp_view)?.also {
|
|
||||||
it.setImageDrawable(fingerprintIcon)
|
|
||||||
}
|
|
||||||
val parentView = parent as ViewGroup
|
|
||||||
val coords = parentView.getLocationOnScreen()
|
|
||||||
val parentLeft = coords[0]
|
|
||||||
val parentTop = coords[1]
|
|
||||||
val sensorRectOffset = Rect(sensorRect)
|
|
||||||
sensorRectOffset.offset(-parentLeft, -parentTop)
|
|
||||||
|
|
||||||
fingerprintIcon.drawSensorRectAt(sensorRectOffset)
|
findViewById<ImageView?>(R.id.udfps_enroll_animation_fp_progress_view)?.also {
|
||||||
fingerprintProgressDrawable.drawProgressAt(sensorRectOffset)
|
it.setImageDrawable(fingerprintProgressDrawable)
|
||||||
}
|
}
|
||||||
|
findViewById<ImageView>(R.id.udfps_enroll_animation_fp_view)?.also {
|
||||||
|
it.setImageDrawable(fingerprintIcon)
|
||||||
|
}
|
||||||
|
val parentView = parent as ViewGroup
|
||||||
|
val coords = parentView.getLocationOnScreen()
|
||||||
|
val parentLeft = coords[0]
|
||||||
|
val parentTop = coords[1]
|
||||||
|
val sensorRectOffset = Rect(sensorRect)
|
||||||
|
sensorRectOffset.offset(-parentLeft, -parentTop)
|
||||||
|
|
||||||
|
fingerprintIcon.drawSensorRectAt(sensorRectOffset)
|
||||||
|
fingerprintProgressDrawable.drawProgressAt(sensorRectOffset)
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Updates the current enrollment stage. */
|
/** Updates the current enrollment stage. */
|
||||||
@@ -97,15 +96,7 @@ class UdfpsEnrollViewV2(context: Context, attrs: AttributeSet?) : FrameLayout(co
|
|||||||
fingerprintProgressDrawable.setAccessibilityEnabled(enabled)
|
fingerprintProgressDrawable.setAccessibilityEnabled(enabled)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onLayout(changed: Boolean, left: Int, top: Int, right: Int, bottom: Int) {
|
private fun udfpsError(errMsgId: Int, errString: String) {}
|
||||||
invalidate()
|
|
||||||
super.onLayout(changed, left, top, right, bottom)
|
|
||||||
invalidate()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun udfpsError(errMsgId: Int, errString: String) {
|
|
||||||
Log.e(TAG, "Implement udfpsError")
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun overlayShown() {
|
private fun overlayShown() {
|
||||||
Log.e(TAG, "Implement overlayShown")
|
Log.e(TAG, "Implement overlayShown")
|
||||||
@@ -113,28 +104,30 @@ class UdfpsEnrollViewV2(context: Context, attrs: AttributeSet?) : FrameLayout(co
|
|||||||
|
|
||||||
/** Receive enroll progress event */
|
/** Receive enroll progress event */
|
||||||
private fun onEnrollmentProgress(remaining: Int, totalSteps: Int) {
|
private fun onEnrollmentProgress(remaining: Int, totalSteps: Int) {
|
||||||
post {
|
fingerprintIcon.onEnrollmentProgress(remaining, totalSteps)
|
||||||
fingerprintIcon.onEnrollmentProgress(remaining, totalSteps)
|
fingerprintProgressDrawable.onEnrollmentProgress(remaining, totalSteps)
|
||||||
fingerprintProgressDrawable.onEnrollmentProgress(remaining, totalSteps)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Receive enroll help event */
|
/** Receive enroll help event */
|
||||||
private fun onEnrollmentHelp() {
|
private fun onEnrollmentHelp() {
|
||||||
post { fingerprintProgressDrawable.onEnrollmentHelp(mRemainingSteps, mTotalSteps) }
|
fingerprintProgressDrawable.onEnrollmentHelp()
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Receive onAcquired event */
|
/** Receive onAcquired event */
|
||||||
private fun onAcquired(isAcquiredGood: Boolean) {
|
private fun onAcquired(isAcquiredGood: Boolean) {
|
||||||
val animateIfLastStepGood = isAcquiredGood && mRemainingSteps <= 2 && mRemainingSteps >= 0
|
val animateIfLastStepGood = isAcquiredGood && mRemainingSteps <= 2 && mRemainingSteps >= 0
|
||||||
post { if (animateIfLastStepGood) fingerprintProgressDrawable.onLastStepAcquired() }
|
if (animateIfLastStepGood) fingerprintProgressDrawable.onLastStepAcquired()
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Receive onPointerDown event */
|
/** Receive onPointerDown event */
|
||||||
private fun onPointerDown() {}
|
private fun onPointerDown() {
|
||||||
|
fingerprintIcon.stopDrawing()
|
||||||
|
}
|
||||||
|
|
||||||
/** Receive onPointerUp event */
|
/** Receive onPointerUp event */
|
||||||
private fun onPointerUp() {}
|
private fun onPointerUp() {
|
||||||
|
fingerprintIcon.startDrawing()
|
||||||
|
}
|
||||||
|
|
||||||
companion object {
|
companion object {
|
||||||
private const val TAG = "UdfpsEnrollView"
|
private const val TAG = "UdfpsEnrollView"
|
||||||
|
Reference in New Issue
Block a user