僕がiPhone6Plusに乗り換えて一番便利だなって思っている機能はTouchIDです。

他の主要アプリでも実装されているので、実装方法を紹介したいと思います。

ScreenShot86

ソースコード

いつも通り、ソースコードから紹介します。

ViewController.swift
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
import UIKit
import LocalAuthentication
class ViewController: UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a nib.
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
@IBAction func touchIDAuthentication(sender: AnyObject) {
if !self.canUseTouchID() {
let alertController = self.alertViewController("Error", message: "お使いの端末にTouchIDが設定されていません。")
self.presentViewController(alertController, animated: true, completion: nil)
return
}
let context = LAContext()
let localizedReason = "テストです。"
context.evaluatePolicy(LAPolicy.DeviceOwnerAuthenticationWithBiometrics, localizedReason: localizedReason) {(success: Bool, authenticationError: NSError!) in
if success {
let alertController = self.alertViewController("TouchID", message: "認証に成功しました!")
self.presentViewController(alertController, animated: true, completion: nil)
} else {
let message = "認証に失敗しました。\n\(authenticationError.localizedDescription)"
let alertController = self.alertViewController("TouchID", message: message)
self.presentViewController(alertController, animated: true, completion: nil)
}
}
}
// MARK: private
private func canUseTouchID() -> Bool {
let context: LAContext = LAContext()
var errorPointer: NSError? = nil
let result = context.canEvaluatePolicy(LAPolicy.DeviceOwnerAuthenticationWithBiometrics, error: &errorPointer)
if !result {
if let error = errorPointer {
println("error => \(error.localizedDescription)")
return false
}
}
return result
}
private func alertViewController(title: String, message: String) -> UIAlertController {
let alertController = UIAlertController(title: title, message: message, preferredStyle: UIAlertControllerStyle.Alert)
let okAction = UIAlertAction(title: "OK", style: UIAlertActionStyle.Default) { (action) in
}
alertController.addAction(okAction)
return alertController
}
}
  • 認証画面

    ScreenShot86

  • 認証成功

    ScreenShot87

  • 認証失敗

    ScreenShot88

  • TouchID未設定

    ScreenShot89

流れを紹介すると…

  1. ボタンを押して@IBAction func touchIDAuthentication(sender: AnyObject){}が呼ばれる
  2. private func canUseTouchID() -> BoolTouchIDが搭載、設定されているか確認
  3. context.evaluatePolicy()TouchIDによる認証画面を表示
  4. 引数のsuccessで認証が成功したかどうか判断

という感じです。

import LocalAuthentication

これがTouchIDによる認証機能を実現してくれるAPIになります。

Local Authentication Framework Reference | iOS Developer Library

とても簡単なサンプルが載っているので確認してみてください。

TouchIDが設定されているかどうか

最初にユーザーのデバイスにTouchIDが搭載されているか、設定されているかの確認をします。

以下のソースコードが例になります。

1
2
3
4
5
6
7
8
9
let context: LAContext = LAContext()
var errorPointer: NSError? = nil
let result = context.canEvaluatePolicy(LAPolicy.DeviceOwnerAuthenticationWithBiometrics, error: &errorPointer)
if !result {
if let error = errorPointer {
println("error => \(error.localizedDescription)")
return false
}
}

未だNSErrorPointerの使い方がわからないのでNSError?&で代用しました。

エラーコード

以下のように分類できます。

1
2
3
4
5
6
7
8
9
10
if let error = errorPointer {
switch error.code {
case LAError.TouchIDNotAvailable.rawValue:
println("デバイスがTouchIDを搭載していません。\n\(error.localizedDescription)")
case LAError.TouchIDNotEnrolled.rawValue:
println("TouchIDがまだ設定されていません。\n\(error.localizedDescription)")
default:
println("不明なエラーです。\n\(error.localizedDescription)")
}
}

エラーコードは以下のリンクを参照してください。

LAContext Class Reference | iOS Developer Library

認証処理

1
2
3
4
5
6
7
8
9
10
11
12
let context = LAContext()
let localizedReason = "テストです。"
context.evaluatePolicy(LAPolicy.DeviceOwnerAuthenticationWithBiometrics, localizedReason: localizedReason) {(success: Bool, authenticationError: NSError!) in
if success {
let alertController = self.alertViewController("TouchID", message: "認証に成功しました!")
self.presentViewController(alertController, animated: true, completion: nil)
} else {
let message = "認証に失敗しました。\n\(authenticationError.localizedDescription)"
let alertController = self.alertViewController("TouchID", message: message)
self.presentViewController(alertController, animated: true, completion: nil)
}
}

ここも特に疑問がないのかなーと思います。

LAContextevaluatePolicy(_policy: LAPolicy, localizedReason localizedReason: String!, reply reply: ((Bool, NSError!) -> Void)!)を呼ぶ事で認証画面を表示できます。

認証が成功した時はreplyの第一引数のBoolの値がtrueで返ってきます。

それ以外の場合はfalseになります。

認証時のエラーコード

以下のように分かれます。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
var message = ""
switch authenticationError.code {
case LAError.AuthenticationFailed.rawValue:
message = "認証に失敗しました。\n\(authenticationError.localizedDescription)"
case LAError.UserCancel.rawValue:
message = "キャンセルしました。\n\(authenticationError.localizedDescription)"
case LAError.UserFallback.rawValue:
message = "パスワードを入力したがってます。\n\(authenticationError.localizedDescription)"
case LAError.PasscodeNotSet.rawValue:
message = "パスコードがセットされていません。\n\(authenticationError.localizedDescription)"
case LAError.SystemCancel.rawValue:
message = "システムによってキャンセルされました。\n\(authenticationError.localizedDescription)"
default:
message = "不明なエラーです。\n\(authenticationError.localizedDescription)"
}

終わりに

GitHubにサンプル置いておきました。

NinjaAdMax / SampleTouchID

失礼します。

参考

Local Authentication Framework Reference | iOS Developer Library

LAContext Class Reference | iOS Developer Library

iOS

「iOS」のおすすめ記事