Added the option to lock the pattern security lock option when the user has entered it wrong too many times. Once the cooldown timer ends the pattern is re-enabled so the user can try again.
This commit is contained in:
parent
2ea32af377
commit
19ede70c69
2 changed files with 32 additions and 11 deletions
|
@ -5,6 +5,7 @@ import android.preference.PreferenceManager
|
||||||
import android.view.LayoutInflater
|
import android.view.LayoutInflater
|
||||||
import android.view.View
|
import android.view.View
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
|
import androidx.core.content.ContextCompat
|
||||||
import cy.agorise.bitsybitshareswallet.R
|
import cy.agorise.bitsybitshareswallet.R
|
||||||
import kotlinx.android.synthetic.main.dialog_pattern_security_lock.*
|
import kotlinx.android.synthetic.main.dialog_pattern_security_lock.*
|
||||||
import com.andrognito.patternlockview.PatternLockView
|
import com.andrognito.patternlockview.PatternLockView
|
||||||
|
@ -63,16 +64,21 @@ class PatternSecurityLockDialog : BaseSecurityLockDialog() {
|
||||||
|
|
||||||
override fun onComplete(pattern: List<PatternLockView.Dot>) {
|
override fun onComplete(pattern: List<PatternLockView.Dot>) {
|
||||||
if (currentStep == STEP_SECURITY_LOCK_VERIFY) {
|
if (currentStep == STEP_SECURITY_LOCK_VERIFY) {
|
||||||
context?.let {
|
|
||||||
val hashedPattern = CryptoUtils.createSHA256Hash(currentPINPatternSalt +
|
val hashedPattern = CryptoUtils.createSHA256Hash(currentPINPatternSalt +
|
||||||
getStringPattern(pattern))
|
getStringPattern(pattern))
|
||||||
if (hashedPattern == currentHashedPINPattern) {
|
if (hashedPattern == currentHashedPINPattern) {
|
||||||
// Pattern is correct, proceed
|
// Pattern is correct, proceed
|
||||||
|
resetIncorrectSecurityLockAttemptsAndTime()
|
||||||
dismiss()
|
dismiss()
|
||||||
mCallback?.onPINPatternEntered(actionIdentifier)
|
mCallback?.onPINPatternEntered(actionIdentifier)
|
||||||
} else {
|
} else {
|
||||||
|
increaseIncorrectSecurityLockAttemptsAndTime()
|
||||||
|
if (incorrectSecurityLockAttempts < Constants.MAX_INCORRECT_SECURITY_LOCK_ATTEMPTS) {
|
||||||
|
// Show the error only when the user has not reached the max attempts limit, because if that
|
||||||
|
// is the case another error is gonna be shown in the setupScreen() method
|
||||||
tvMessage.text = getString(R.string.error__wront_pattern)
|
tvMessage.text = getString(R.string.error__wront_pattern)
|
||||||
}
|
}
|
||||||
|
setupScreen()
|
||||||
}
|
}
|
||||||
} else if (currentStep == STEP_SECURITY_LOCK_CREATE) {
|
} else if (currentStep == STEP_SECURITY_LOCK_CREATE) {
|
||||||
btnClear.visibility = View.VISIBLE
|
btnClear.visibility = View.VISIBLE
|
||||||
|
@ -143,6 +149,21 @@ class PatternSecurityLockDialog : BaseSecurityLockDialog() {
|
||||||
tvSubTitle.text = getString(R.string.msg__enter_your_pattern)
|
tvSubTitle.text = getString(R.string.msg__enter_your_pattern)
|
||||||
btnClear.visibility = View.GONE
|
btnClear.visibility = View.GONE
|
||||||
btnNext.visibility = View.GONE
|
btnNext.visibility = View.GONE
|
||||||
|
tvMessage.text = ""
|
||||||
|
if (incorrectSecurityLockAttempts >= Constants.MAX_INCORRECT_SECURITY_LOCK_ATTEMPTS) {
|
||||||
|
// User has entered the Pattern incorrectly too many times
|
||||||
|
val now = System.currentTimeMillis()
|
||||||
|
if (now <= incorrectSecurityLockTime + Constants.INCORRECT_SECURITY_LOCK_COOLDOWN) {
|
||||||
|
patternLockView.isInputEnabled = false
|
||||||
|
startContDownTimer()
|
||||||
|
return
|
||||||
|
} else {
|
||||||
|
resetIncorrectSecurityLockAttemptsAndTime()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// This is not in an else statement because we also want to enable the EditText and remove the error
|
||||||
|
// when the cooldown time has been reached
|
||||||
|
patternLockView.isInputEnabled = true
|
||||||
patternLockView.isInStealthMode = true
|
patternLockView.isInStealthMode = true
|
||||||
}
|
}
|
||||||
STEP_SECURITY_LOCK_CREATE -> {
|
STEP_SECURITY_LOCK_CREATE -> {
|
||||||
|
@ -169,7 +190,7 @@ class PatternSecurityLockDialog : BaseSecurityLockDialog() {
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onTimerSecondPassed(errorMessage: String) {
|
override fun onTimerSecondPassed(errorMessage: String) {
|
||||||
tvMessage.error = errorMessage
|
tvMessage.text = errorMessage
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onTimerFinished() {
|
override fun onTimerFinished() {
|
||||||
|
|
|
@ -26,11 +26,11 @@ object Constants {
|
||||||
const val KEY_SECURITY_LOCK_SELECTED = "key_security_lock_selected"
|
const val KEY_SECURITY_LOCK_SELECTED = "key_security_lock_selected"
|
||||||
|
|
||||||
/** Maximum allowed number of incorrect attempts to input the current security lock */
|
/** Maximum allowed number of incorrect attempts to input the current security lock */
|
||||||
const val MAX_INCORRECT_SECURITY_LOCK_ATTEMPTS = 1 // TODO 5
|
const val MAX_INCORRECT_SECURITY_LOCK_ATTEMPTS = 5
|
||||||
|
|
||||||
/** Minimum time that the security lock options will be disabled when the user has incorrectly tried to enter
|
/** Minimum time that the security lock options will be disabled when the user has incorrectly tried to enter
|
||||||
* the current security lock option more than MAX_INCORRECT_SECURITY_LOCK_ATTEMPTS times */
|
* the current security lock option more than MAX_INCORRECT_SECURITY_LOCK_ATTEMPTS times */
|
||||||
const val INCORRECT_SECURITY_LOCK_COOLDOWN = 2 * 60L * 1000 // 5 seconds TODO 5L * 60 * 1000 // 5 minutes
|
const val INCORRECT_SECURITY_LOCK_COOLDOWN = 5L * 60 * 1000 // 5 minutes
|
||||||
|
|
||||||
/** Key used to store the consecutive number of times the user has incorrectly tried to enter the
|
/** Key used to store the consecutive number of times the user has incorrectly tried to enter the
|
||||||
* current security lock option */
|
* current security lock option */
|
||||||
|
|
Loading…
Reference in a new issue