// // YH_AlbumScanQRManager.m // YHScanQR // // Created by Foxconn on 2018/1/20. // Copyright © 2018年 Foxconn. All rights reserved. // #import "YHAlbumScanQRManager.h" #import <AVFoundation/AVFoundation.h> #import <Photos/Photos.h> #import "UIImage+YHImageSize.h" @interface YHAlbumScanQRManager () <UINavigationControllerDelegate, UIImagePickerControllerDelegate> @property (nonatomic, strong) UIViewController *currentVC; @property (nonatomic, strong) NSString *detectorString; @end @implementation YHAlbumScanQRManager + (instancetype)sharedManager { static YHAlbumScanQRManager *manager = nil; static dispatch_once_t onceToken; dispatch_once(&onceToken, ^{ manager = [[YHAlbumScanQRManager alloc] init]; }); return manager; } - (void)initialization { _isOpenAlret = YES; } - (void)readQRCodeFromAlbumWithCurrentController:(UIViewController *)currentController { [self initialization]; self.currentVC = currentController; if (currentController == nil) { NSException *excp = [NSException exceptionWithName:@"YHScanQR" reason:@"readQRCodeFromAlbumWithCurrentController: 方法中的 currentController 参数不能为空" userInfo:nil]; [excp raise]; } // 1、 获取摄像设备 AVCaptureDevice *device = [AVCaptureDevice defaultDeviceWithMediaType:AVMediaTypeVideo]; if (device) { // 判断授权状态 PHAuthorizationStatus status = [PHPhotoLibrary authorizationStatus]; if (status == PHAuthorizationStatusNotDetermined) { // 用户还没有做出选择 // 弹框请求用户授权 [PHPhotoLibrary requestAuthorization:^(PHAuthorizationStatus status) { if (status == PHAuthorizationStatusAuthorized) { // 用户第一次同意了访问相册权限 self.isAlbumAccessAuthorization = YES; dispatch_sync(dispatch_get_main_queue(), ^{ [self enterImagePickerController]; }); } else { // 用户第一次拒绝了访问相机权限 if (self.isOpenAlret) { [self createAlertViewWithMessage:@"您拒绝了访问相册权限"]; } } }]; } else if (status == PHAuthorizationStatusAuthorized) { // 用户允许当前应用访问相册 self.isAlbumAccessAuthorization = YES; [self enterImagePickerController]; } else if (status == PHAuthorizationStatusDenied) { // 用户拒绝当前应用访问相册 if (self.isOpenAlret) { NSString *message = @"请去-> [设置 - 隐私 - 照片 ] 打开访问开关"; UIAlertController *alertVC = [UIAlertController alertControllerWithTitle:@"温馨提示" message:message preferredStyle:(UIAlertControllerStyleAlert)]; UIAlertAction *alertsure = [UIAlertAction actionWithTitle:@"确定" style:(UIAlertActionStyleDefault) handler:^(UIAlertAction * _Nonnull action) { //跳转到系统类 NSURL * url = [NSURL URLWithString:UIApplicationOpenSettingsURLString]; if([[UIApplication sharedApplication] canOpenURL:url]) { NSURL*url =[NSURL URLWithString:UIApplicationOpenSettingsURLString]; [[UIApplication sharedApplication] openURL:url]; } }]; [alertVC addAction:alertsure]; [self.currentVC presentViewController:alertVC animated:YES completion:nil]; } } else if (status == PHAuthorizationStatusRestricted) { if (self.isOpenAlret) { [self createAlertViewWithMessage:@"由于系统原因, 无法访问相册"]; } } } } // 进入 UIImagePickerController - (void)enterImagePickerController { UIImagePickerController *imagePicker = [[UIImagePickerController alloc] init]; imagePicker.sourceType = UIImagePickerControllerSourceTypePhotoLibrary; imagePicker.delegate = self; [self.currentVC presentViewController:imagePicker animated:YES completion:nil]; } #pragma mark - - - UIImagePickerControllerDelegate - (void)imagePickerControllerDidCancel:(UIImagePickerController *)picker { [self.currentVC dismissViewControllerAnimated:YES completion:nil]; if (self.delegate && [self.delegate respondsToSelector:@selector(YHAlbumScanQRManagerDidCancelWithImagePickerController:)]) { [self.delegate YHAlbumScanQRManagerDidCancelWithImagePickerController:self]; } } - (void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary<NSString *,id> *)info { // 对选取照片的处理,如果选取的图片尺寸过大,则压缩选取图片,否则不作处理 UIImage *image = [UIImage imageSizeWithScreenImage:info[UIImagePickerControllerOriginalImage]]; // CIDetector(CIDetector可用于人脸识别)进行图片解析,从而使我们可以便捷的从相册中获取到二维码 // 声明一个 CIDetector,并设定识别类型 CIDetectorTypeQRCode CIDetector *detector = [CIDetector detectorOfType:CIDetectorTypeQRCode context:nil options:@{CIDetectorAccuracy: CIDetectorAccuracyHigh}]; // 取得识别结果 NSArray *features = [detector featuresInImage:[CIImage imageWithCGImage:image.CGImage]]; if (features.count == 0) { if (self.isOpenAlret) { [self createAlertViewWithMessage:@"暂未识别出扫描的二维码"]; } [self.currentVC dismissViewControllerAnimated:YES completion:nil]; return; } else { for (int index = 0; index < [features count]; index ++) { CIQRCodeFeature *feature = [features objectAtIndex:index]; NSString *resultStr = feature.messageString; self.detectorString = resultStr; } [self.currentVC dismissViewControllerAnimated:YES completion:^{ if (self.delegate && [self.delegate respondsToSelector:@selector(YHAlbumScanQRManager:didFinishPickingMediaWithResult:)]) { [self.delegate YHAlbumScanQRManager:self didFinishPickingMediaWithResult:self.detectorString]; } }]; } } #pragma mark - - - set - (void)setisOpenAlret:(BOOL)isOpenAlret { _isOpenAlret = isOpenAlret; } -(void) createAlertViewWithMessage:(NSString *)message{ UIAlertController *alertC = [UIAlertController alertControllerWithTitle:@"温馨提示" message:message preferredStyle:(UIAlertControllerStyleAlert)]; UIAlertAction *alertA = [UIAlertAction actionWithTitle:@"确定" style:(UIAlertActionStyleDefault) handler:^(UIAlertAction * _Nonnull action) { }]; [alertC addAction:alertA]; [self.currentVC presentViewController:alertC animated:YES completion:nil]; } @end