Presenting camera permission dialog in iOS 8 Presenting camera permission dialog in iOS 8 ios ios

Presenting camera permission dialog in iOS 8


Here is the approach we ended up using:

if ([AVCaptureDevice respondsToSelector:@selector(requestAccessForMediaType: completionHandler:)]) {    [AVCaptureDevice requestAccessForMediaType:AVMediaTypeVideo completionHandler:^(BOOL granted) {        // Will get here on both iOS 7 & 8 even though camera permissions weren't required         // until iOS 8. So for iOS 7 permission will always be granted.        if (granted) {            // Permission has been granted. Use dispatch_async for any UI updating            // code because this block may be executed in a thread.            dispatch_async(dispatch_get_main_queue(), ^{                [self doStuff];            });                        } else {            // Permission has been denied.        }    }];} else {    // We are on iOS <= 6. Just do what we need to do.    [self doStuff];}


I'm running into a similar issue, if the user has denied camera access when they are first prompted, pressing the button to take snapshot results in a black screen in the camera mode.

However I want to detect that the user has declined access and prompt them it must be turned on but I can't find any functions to check the current user camera access, is there such a function?

EDIT: The following check will let you know in IOS 8 about camera access:

#import <AVFoundation/AVFoundation.h>AVAuthorizationStatus status = [AVCaptureDevice authorizationStatusForMediaType:AVMediaTypeVideo];        if(status == AVAuthorizationStatusAuthorized) { // authorized            }    else if(status == AVAuthorizationStatusDenied){ // denied            }    else if(status == AVAuthorizationStatusRestricted){ // restricted                    }    else if(status == AVAuthorizationStatusNotDetermined){ // not determined                [AVCaptureDevice requestAccessForMediaType:AVMediaTypeVideo completionHandler:^(BOOL granted) {            if(granted){ // Access has been granted ..do something                           } else { // Access denied ..do something                           }        }];    }

This information was found on the following question (How to know that application have camera access or not programmatically in iOS8):


Here is my Swift Solution (iOS 8), I needed the camera for QR scanning so really had to prompt its use.

This provides

  1. Encourage the user to select allow if prior to the default allow camera access question

  2. Easy way to access settings if the user denied the first request.

To get it running call check camera in ViewDidAppear / or ViewDidLoad etc. I needed to use viewDidAppear so my custom camera views constraints were set up.

func checkCamera() {    let authStatus = AVCaptureDevice.authorizationStatus(forMediaType: AVMediaTypeVideo)    switch authStatus {    case .authorized: break // Do your stuff here i.e. allowScanning()    case .denied: alertToEncourageCameraAccessInitially()    case .notDetermined: alertPromptToAllowCameraAccessViaSetting()    default: alertToEncourageCameraAccessInitially()    }}func alertToEncourageCameraAccessInitially() {    let alert = UIAlertController(        title: "IMPORTANT",        message: "Camera access required for QR Scanning",        preferredStyle: UIAlertControllerStyle.alert    )    alert.addAction(UIAlertAction(title: "Cancel", style: .default, handler: nil))    alert.addAction(UIAlertAction(title: "Allow Camera", style: .cancel, handler: { (alert) -> Void in        UIApplication.shared.openURL(URL(string: UIApplicationOpenSettingsURLString)!)    }))    present(alert, animated: true, completion: nil)}func alertPromptToAllowCameraAccessViaSetting() {    let alert = UIAlertController(        title: "IMPORTANT",        message: "Please allow camera access for QR Scanning",        preferredStyle: UIAlertControllerStyle.alert    )    alert.addAction(UIAlertAction(title: "Dismiss", style: .cancel) { alert in        if AVCaptureDevice.devices(withMediaType: AVMediaTypeVideo).count > 0 {            AVCaptureDevice.requestAccess(forMediaType: AVMediaTypeVideo) { granted in                DispatchQueue.main.async() {                    self.checkCamera() } }        }        }    )    present(alert, animated: true, completion: nil)}

Thanks to jamix above for the tip for using dispatch_async - makes the response to show the newly set camera function so much faster.

Sorry for a mix of trailing closures.. wanted to try them out.