TDTouchID 免費的 FaceID、TouchID 驗證工具

在許多 App 的應用上,常常會使用到使用者登入的功能,尤其是金融交易的 App,用 FaceID 或 TouchID 更是一種不得不用上的趨勢,畢竟任何一個用戶都不希望自己在登入時還要再輸入一次密碼。而 TouchID 是一個第三方封裝好的 FaceID、TouchID 驗證工具,使用起來相當容易,程式碼也相當簡潔不囉嗦,個人是蠻推薦使用的喔!

◎◎軟體小檔案◎◎
軟體名稱:TDTouchID
軟體版本:20190712
軟體介面:英文
支援系統:iOS 開發
■ 軟體下載:【點我下載】

而在 TDTouch 的「.h」中,其實就有訂了以下的函式可以使用。

@interface TDTouchID : LAContext

typedef void (^StateBlock)(TDTouchIDState state,NSError *error);

+ (instancetype)sharedInstance;

/**
 启动生物验证
 @param desc Touch显示的描述
 @param block 回调状态的block
 */
- (void)td_showTouchIDWithDescribe:(NSString *)desc BlockState:(StateBlock)block;

/**
 启动生物验证
 @param desc Touch显示的描述
 @param faceDesc FaceID状态下显示的描述
 @param block 回调状态的block
 */
- (void)td_showTouchIDWithDescribe:(NSString *)desc FaceIDDescribe:(NSString *)faceDesc BlockState:(StateBlock)block;

// 判断设备支持哪种认证方式 TouchID & FaceID
- (TDTouchIDSupperType)td_canSupperBiometrics;


@end

也因此,我們如果要判斷 iOS 裝置是否有支援手機辨識,以官方的範例來說,我們只需要做以下的事情就好。

//判断是否支持生物验证(此处根据不同类型来显示不同的图标)
TDTouchIDSupperType type = [[TDTouchID sharedInstance] td_canSupperBiometrics];
switch (type) {
    case TDTouchIDSupperTypeFaceID:
       NSLog(@"????支持FaceID");
       break;
    case TDTouchIDSupperTypeTouchID:
       NSLog(@"????支持TouchID");
       break;
    case TDTouchIDSupperTypeNone:
       NSLog(@"????不支持生物验证");
       break;
    default:
       break;
}

在得知手機支援 Touch ID 或 Face ID 後,接下來就是驗證了,怎樣呼叫呢?其實也只要用以下的方式來呼叫就好了。

/**
 验证 TouchID
 */
- (void)touchVerification {
    
    [[TDTouchID sharedInstance] td_showTouchIDWithDescribe:@"通过Home键验证已有指纹" FaceIDDescribe:@"通过已有面容ID验证" BlockState:^(TDTouchIDState state, NSError *error) {
        if (state == TDTouchIDStateNotSupport) {    //不支持TouchID/FaceID
            
            UIAlertView *alertview = [[UIAlertView alloc] initWithTitle:@"当前设备不支持生物验证" message:@"请输入密码来验证" delegate:nil cancelButtonTitle:@"确定" otherButtonTitles:nil];
            alertview.alertViewStyle = UIAlertViewStyleSecureTextInput;
            [alertview show];
            
        } else if (state == TDTouchIDStateSuccess) {    //TouchID/FaceID验证成功
            
            NSLog(@"jump");
            TDHomeViewController *homeVc = [[TDHomeViewController alloc] init];
            [self.navigationController pushViewController:homeVc animated:YES];
            
        } else if (state == TDTouchIDStateInputPassword) { //用户选择手动输入密码
            
            UIAlertView *alertview = [[UIAlertView alloc] initWithTitle:nil message:@"请输入密码" delegate:nil cancelButtonTitle:@"确定" otherButtonTitles:nil];
            alertview.alertViewStyle = UIAlertViewStyleSecureTextInput;
            [alertview show];
            
        }
        
        // ps:以上的状态处理并没有写完全!
        // 在使用中你需要根据回调的状态进行处理,需要处理什么就处理什么
        
    }];
    
}

以金融交易的 App 來說,通常在「applicationWillResignActive」中都會訂立一個遮蔽的畫面,主要的目的是讓你的 App 縮到背景或在不同程式間切換時,使用者不會看到 App 正在執行的畫面,但使用「Touch ID」或「Face ID」會呼叫「applicationWillResignActive」,如果我們要在登入頁使用「Touch ID」或「Face ID」,但使用者看到的卻不是登入頁,而是遮蔽頁,那不是很怪的一件事嗎?所以,我們必須在 TDTouchID 動一點手腳。這時我們可以宣告一個變數 m_isUsingTouchID,來判斷是否正在使用 Touch ID 或是 Face ID。

@interface TDTouchID()

@property (assign, nonatomic) BOOL m_isUsingTouchID;

@end

接下來,改寫這隻程式的  sharedInstance。

+ (instancetype)sharedInstance {
    static TDTouchID *instance = nil;
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        instance = [[TDTouchID alloc] init];
        instance.m_isUsingTouchID = NO;
    });
    return instance;
}

新增一個函式來回傳是否正在使用「臉部辨識/指紋辨識」

/**
 是否正在使用「指紋辨識/臉部辨識」
 */
+ (BOOL) isUsingTouchID
{
    TDTouchID* touchID = [self sharedInstance];
    return touchID.m_isUsingTouchID;
}

最後,找到「LAPolicyDeviceOwnerAuthenticationWithBiometrics」,並在這行程式之前加入「self.m_isUsingTouchID」,而在 reply 的 Block 記得寫「self->_m_isUsingTouchID = NO;」

self.m_isUsingTouchID = YES; 
[context evaluatePolicy:LAPolicyDeviceOwnerAuthenticationWithBiometrics localizedReason:descStr reply:^(BOOL success, NSError * _Nullable error) {
            
            self->_m_isUsingTouchID = NO;

            if (success) {
                dispatch_async(dispatch_get_main_queue(), ^{
                    NSLog(@"TouchID 验证成功");
                    block(TDTouchIDStateSuccess,error);
                });
            }
            
        };

最後,別忘了在 Appdelegate 的 applicationWillResignActive 加上以下的程式碼:

- (void)applicationWillResignActive:(UIApplication *)application
{
    if ([TDTouchID isUsingTouchID]){
        return;
    }
    
    if (self.m_TopmaskView == nil) {
        self.m_TopmaskView = [[[NSBundle mainBundle] loadNibNamed: NSStringFromClass([MaskView class])
                                                            owner:self options:nil] objectAtIndex:0];
        self.m_TopmaskView.frame = self.window.frame;
        [self.window addSubview:self.m_TopmaskView];//加上遮蔽畫面
    }
}

Appdelegate 的 applicationDidEnterBackground 也別忘了喔

- (void)applicationDidEnterBackground:(UIApplication *)application
{
    if ([TDTouchID isUsingTouchID]){
        return;
    }
    
    if (self.m_TopmaskView == nil) {
        self.m_TopmaskView = [[[NSBundle mainBundle] loadNibNamed: NSStringFromClass([MaskView class])
                                                            owner:self options:nil] objectAtIndex:0];
        self.m_TopmaskView.frame = self.window.frame;
        [self.window addSubview:self.m_TopmaskView];//加上遮蔽畫面
    }
}

而以上的程式碼供參考,若有問題再請提出啦!

Subscribe
Notify of
guest

0 Comments
Inline Feedbacks
View all comments