PasscodeLock
is the sample project of AppLocker. I took some hours and found how it worked.
Let The App Run
The original project used Carthage to manage the framework. It depended Valet
. However, the latest Valet
is 4.x but PasscodeLock
depends 3.x. So we need to specify the version.
pod 'Valet' , '< 4.0'
I switched Carthage to CocoaPods. So I also had to remove the Carthage part in building phase.
Core
// AppALConstants.swift
// MARK: - Keyboard
@IBAction func keyboardPressed(_ sender: UIButton) {
switch sender.tag {
case ALConstants.button.delete.rawValue:
drawing(isNeedClear: true)
case ALConstants.button.cancel.rawValue:
clearView()
dismiss(animated: true) {
self.onSuccessfulDismiss?(nil)
}
default:
drawing(isNeedClear: false, tag: sender.tag)
}
}
private func drawing(isNeedClear: Bool, tag: Int? = nil) { // Fill or cancel fill for indicators
let results = pinIndicators.filter { $0.isNeedClear == isNeedClear }
let pinView = isNeedClear ? results.last : results.first
pinView?.isNeedClear = !isNeedClear
UIView.animate(withDuration: ALConstants.duration, animations: {
pinView?.backgroundColor = isNeedClear ? .clear : .white
}) { _ in
isNeedClear ? self.pin = String(self.pin.dropLast()) : self.pincodeChecker(tag ?? 0)
}
}
private func pincodeChecker(_ pinNumber: Int) {
if pin.count < ALConstants.maxPinLength {
pin.append("\(pinNumber)")
if pin.count == ALConstants.maxPinLength {
switch mode {
case .create:
createModeAction()
case .change:
changeModeAction()
case .deactive:
deactiveModeAction()
case .validate:
validateModeAction()
}
}
}
}
When a user presses a key, private func drawing(isNeedClear: Bool, tag: Int? = nil)
is called.
pinView
is the current indicator. It is set to turn white.- then
func pincodeChecker(_ pinNumber: Int)
is called, the result is pin. - when pin.count is 4, the indicators are cleared.