Esempio n. 1
0
        private void ConfigureSession()
        {
            if (_setupResult != SessionSetupResult.Success)
            {
                return;
            }

            Console.WriteLine("capture session: configuring - adding video input");

            Session.BeginConfiguration();

            switch (PresetConfiguration)
            {
            case SessionPresetConfiguration.Photos:
            case SessionPresetConfiguration.LivePhotos:
                _setupResult = PhotoCaptureSession.ConfigureSession(Session, PresetConfiguration);
                break;

            case SessionPresetConfiguration.Videos:
                Session.SessionPreset = AVCaptureSession.PresetHigh;
                _setupResult          = VideoCaptureSession.ConfigureSession(Session);
                break;

            default:
                throw new ArgumentOutOfRangeException();
            }

            if (_setupResult != SessionSetupResult.Success)
            {
                Console.WriteLine("Cannot configure session");
                return;
            }

            Session.CommitConfiguration();
        }
Esempio n. 2
0
        public override void ViewDidLoad()
        {
            base.ViewDidLoad();


            // Disable UI. The UI is enabled if and only if the session starts running.

            // Add the open barcode gesture recognizer to the region of interest view.

            // Set up the video preview view.
            this.PreviewView.Session = session;

            // Check video authorization status. Video access is required and audio
            // access is optional. If audio access is denied, audio is not recorded
            // during movie recording.
            switch (AVCaptureDevice.GetAuthorizationStatus(AVMediaType.Video))
            {
            case AVAuthorizationStatus.Authorized:
                // The user has previously granted access to the camera.
                break;

            case AVAuthorizationStatus.NotDetermined:
                // The user has not yet been presented with the option to grant
                // video access. We suspend the session queue to delay session
                // setup until the access request has completed.
                this.sessionQueue.Suspend();
                AVCaptureDevice.RequestAccessForMediaType(AVMediaType.Video, (granted) =>
                {
                    if (!granted)
                    {
                        this.setupResult = SessionSetupResult.NotAuthorized;
                    }

                    this.sessionQueue.Resume();
                });
                break;

            default:
                // The user has previously denied access.
                this.setupResult = SessionSetupResult.NotAuthorized;
                break;
            }

            // Setup the capture session.
            // In general it is not safe to mutate an AVCaptureSession or any of its
            // inputs, outputs, or connections from multiple threads at the same time.
            //
            // Why not do all of this on the main queue?
            // Because AVCaptureSession.StartRunning() is a blocking call which can
            // take a long time. We dispatch session setup to the sessionQueue so
            // that the main queue isn't blocked, which keeps the UI responsive.
            this.sessionQueue.DispatchAsync(this.ConfigureSession);

            UISlider focusSlider = new UISlider(new CGRect(60, this.View.Frame.Location.Y - 60, 200, 20));

            // focusSlider.AddTarget(focusSlider, new ObjCRuntime.Selector(AdjustFocusAction), UIControlEvent.ValueChanged);
            focusSlider.MaxValue = 1;
            focusSlider.MinValue = 0;
            this.View.AddSubview(focusSlider);
        }
Esempio n. 3
0
        public void Prepare(AVCaptureVideoOrientation captureVideoOrientation)
        {
            var status = AVCaptureDevice.GetAuthorizationStatus(AVMediaType.Video);

            if (status == AVAuthorizationStatus.NotDetermined)
            {
                _sessionQueue.Suspend();
                AVCaptureDevice.RequestAccessForMediaType(AVAuthorizationMediaType.Video, granted =>
                {
                    if (granted)
                    {
                        DispatchQueue.MainQueue.DispatchAsync(() =>
                        {
                            _captureSessionDelegate.CaptureGrantedSession(AVAuthorizationStatus.Authorized);
                        });
                    }
                    else
                    {
                        _setupResult = SessionSetupResult.NotAuthorized;
                    }

                    _sessionQueue.Resume();
                });
            }
            else if (status != AVAuthorizationStatus.Authorized)
            {
                _setupResult = SessionSetupResult.NotAuthorized;
            }

            _sessionQueue.DispatchAsync(() =>
            {
                ConfigureSession();
                UpdateVideoOrientation(captureVideoOrientation);
            });
        }
Esempio n. 4
0
        public override void ViewDidLoad()
        {
            base.ViewDidLoad();

            //systemSoundBeep = new SystemSound(NSUrl.FromFilename("Sounds/beep07.mp3"));
            //systemSoundCaution = new SystemSound(NSUrl.FromFilename("Sounds/beep06.mp3"));

            //audioPlayer = AVAudioPlayer.FromUrl(NSUrl.FromFilename("Sounds/beep07.mp3"));
            //audioCautionPlayer = AVAudioPlayer.FromUrl(NSUrl.FromFilename("Sounds/beep06.mp3"));

            // Perform any additional setup after loading the view, typically from a nib.
            this.PreviewView.AddGestureRecognizer(this.OpenBarcodeURLGestureRecognizer);

            // Set up the video preview view.
            this.PreviewView.Session = session;

            // Check video authorization status. Video access is required and audio
            // access is optional. If audio access is denied, audio is not recorded
            // during movie recording.
            switch (AVCaptureDevice.GetAuthorizationStatus(AVMediaType.Video))
            {
            case AVAuthorizationStatus.Authorized:
                // The user has previously granted access to the camera.
                break;

            case AVAuthorizationStatus.NotDetermined:
                // The user has not yet been presented with the option to grant
                // video access. We suspend the session queue to delay session
                // setup until the access request has completed.
                this.sessionQueue.Suspend();
                AVCaptureDevice.RequestAccessForMediaType(AVMediaType.Video, (granted) =>
                {
                    if (!granted)
                    {
                        this.setupResult = SessionSetupResult.NotAuthorized;
                    }

                    this.sessionQueue.Resume();
                });
                break;

            default:
                // The user has previously denied access.
                this.setupResult = SessionSetupResult.NotAuthorized;
                break;
            }

            // Setup the capture session.
            // In general it is not safe to mutate an AVCaptureSession or any of its
            // inputs, outputs, or connections from multiple threads at the same time.
            //
            // Why not do all of this on the main queue?
            // Because AVCaptureSession.StartRunning() is a blocking call which can
            // take a long time. We dispatch session setup to the sessionQueue so
            // that the main queue isn't blocked, which keeps the UI responsive.
            this.sessionQueue.DispatchAsync(this.ConfigureSession);
        }
Esempio n. 5
0
        public override void ViewDidLoad()
        {
            base.ViewDidLoad();

            // Disable UI. The UI is enabled if and only if the session starts running.
            this.MetadataObjectTypesButton.Enabled = false;
            this.SessionPresetsButton.Enabled      = false;
            this.CameraButton.Enabled = false;
            this.ZoomSlider.Enabled   = false;

            // Add the open barcode gesture recognizer to the region of interest view.
            this.PreviewView.AddGestureRecognizer(this.OpenBarcodeURLGestureRecognizer);

            // Set up the video preview view.
            this.PreviewView.Session = session;

            // Check video authorization status. Video access is required and audio
            // access is optional. If audio access is denied, audio is not recorded
            // during movie recording.
            switch (AVCaptureDevice.GetAuthorizationStatus(AVMediaType.Video))
            {
            case AVAuthorizationStatus.Authorized:
                // The user has previously granted access to the camera.
                break;

            case AVAuthorizationStatus.NotDetermined:
                // The user has not yet been presented with the option to grant
                // video access. We suspend the session queue to delay session
                // setup until the access request has completed.
                this.sessionQueue.Suspend();
                AVCaptureDevice.RequestAccessForMediaType(AVMediaType.Video, (granted) =>
                {
                    if (!granted)
                    {
                        this.setupResult = SessionSetupResult.NotAuthorized;
                    }

                    this.sessionQueue.Resume();
                });
                break;

            default:
                // The user has previously denied access.
                this.setupResult = SessionSetupResult.NotAuthorized;
                break;
            }

            // Setup the capture session.
            // In general it is not safe to mutate an AVCaptureSession or any of its
            // inputs, outputs, or connections from multiple threads at the same time.
            //
            // Why not do all of this on the main queue?
            // Because AVCaptureSession.StartRunning() is a blocking call which can
            // take a long time. We dispatch session setup to the sessionQueue so
            // that the main queue isn't blocked, which keeps the UI responsive.
            this.sessionQueue.DispatchAsync(this.ConfigureSession);
        }
Esempio n. 6
0
        void ConfigureSession()
        {
            if (setupResult != SessionSetupResult.Success)
            {
                return;
            }

            session.BeginConfiguration();

            var     videoDevice = DeviceWithMediaType(AVMediaType.Video, AVCaptureDevicePosition.Back);
            NSError err;
            var     vDeviceInput = AVCaptureDeviceInput.FromDevice(videoDevice, out err);

            if (err != null)
            {
                Console.WriteLine($"Could not create video device input: ${err}");
                setupResult = SessionSetupResult.ConfigurationFailed;
                session.CommitConfiguration();
                return;
            }

            if (session.CanAddInput(vDeviceInput))
            {
                session.AddInput(vDeviceInput);
                videoDeviceInput = vDeviceInput;
            }
            else
            {
                Console.WriteLine("Could not add video device input to the session");
                setupResult = SessionSetupResult.ConfigurationFailed;
                session.CommitConfiguration();
                return;
            }

            // Add metadata output.
            if (session.CanAddOutput(metadataOutput))
            {
                session.AddOutput(metadataOutput);

                // Set this view controller as the delegate for metadata objects.
                metadataOutput.SetDelegate(this, metadataObjectsQueue);
                metadataOutput.MetadataObjectTypes = metadataOutput.AvailableMetadataObjectTypes;                 // Use all metadata object types by default.
                metadataOutput.RectOfInterest      = CGRect.Empty;
            }
            else
            {
                Console.WriteLine("Could not add metadata output to the session");
                setupResult = SessionSetupResult.ConfigurationFailed;
                session.CommitConfiguration();
                return;
            }

            session.CommitConfiguration();
        }
Esempio n. 7
0
        private void ConfigureSession()
        {
            if (setupResult == SessionSetupResult.Success)
            {
                this.session.BeginConfiguration();

                // Add video input
                // Choose the back wide angle camera if available, otherwise default to the front wide angle camera
                AVCaptureDevice defaultVideoDevice = AVCaptureDevice.GetDefaultDevice(AVCaptureDeviceType.BuiltInWideAngleCamera, AVMediaType.Video, AVCaptureDevicePosition.Back) ??
                                                     AVCaptureDevice.GetDefaultDevice(AVCaptureDeviceType.BuiltInWideAngleCamera, AVMediaType.Video, AVCaptureDevicePosition.Front) ??
                                                     null;

                if (defaultVideoDevice == null)
                {
                    Console.WriteLine("Could not get video device");
                    this.setupResult = SessionSetupResult.ConfigurationFailed;
                    this.session.CommitConfiguration();
                    return;
                }

                //set the focus mode to AutoFocus
                if (defaultVideoDevice.IsFocusModeSupported(AVCaptureFocusMode.ContinuousAutoFocus))
                {
                    NSError errorConfig;
                    defaultVideoDevice.LockForConfiguration(out errorConfig);
                    defaultVideoDevice.FocusMode = AVCaptureFocusMode.ContinuousAutoFocus;
                    defaultVideoDevice.UnlockForConfiguration();
                }
                if (defaultVideoDevice.AutoFocusRangeRestrictionSupported)
                {
                    NSError errorConfig;
                    defaultVideoDevice.LockForConfiguration(out errorConfig);
                    defaultVideoDevice.AutoFocusRangeRestriction = AVCaptureAutoFocusRangeRestriction.Near;
                    defaultVideoDevice.UnlockForConfiguration();
                }
                //end focus mode setting

                NSError error;
                var     videoDeviceInput = AVCaptureDeviceInput.FromDevice(defaultVideoDevice, out error);

                if (this.session.CanAddInput(videoDeviceInput))
                {
                    this.videoDeviceInput = videoDeviceInput;
                    this.session.AddInput(videoDeviceInput);

                    DispatchQueue.MainQueue.DispatchAsync(() =>
                    {
                        // Why are we dispatching this to the main queue?
                        // Because AVCaptureVideoPreviewLayer is the backing layer for PreviewView and UIView
                        // can only be manipulated on the main thread
                        // Note: As an exception to the above rule, it's not necessary to serialize video orientation changed
                        // on the AVCaptureVideoPreviewLayer's connection with other session manipulation
                        //
                        // Use the status bar orientation as the internal video orientation. Subsequent orientation changes are
                        // handled by CameraViewController.ViewWillTransition(to:with:).

                        var initialVideoOrientation = AVCaptureVideoOrientation.Portrait;
                        var statusBarOrientation    = UIApplication.SharedApplication.StatusBarOrientation;
                        if (statusBarOrientation != UIInterfaceOrientation.Unknown)
                        {
                            AVCaptureVideoOrientation videoOrintation;
                            if (Enum.TryParse(statusBarOrientation.ToString(), out videoOrintation))
                            {
                                initialVideoOrientation = videoOrintation;
                            }
                        }

                        this.PreviewView.VideoPreviewLayer.Connection.VideoOrientation = initialVideoOrientation;
                    });
                }
                else if (error != null)
                {
                    Console.WriteLine($"Could not create video device input: {error}");
                    this.setupResult = SessionSetupResult.ConfigurationFailed;
                    this.session.CommitConfiguration();
                    return;
                }
                else
                {
                    Console.WriteLine("Could not add video device input to the session");
                    this.setupResult = SessionSetupResult.ConfigurationFailed;
                    this.session.CommitConfiguration();

                    return;
                }

                if (this.session.CanAddOutput(videoOutput))
                {
                    this.session.AddOutput(videoOutput);

                    frameExtractor.update = ResetResult;

                    videoOutput.SetSampleBufferDelegateQueue(frameExtractor, sampleBufferQueue);
                    videoOutput.WeakVideoSettings = new NSDictionary <NSString, NSObject>(CVPixelBuffer.PixelFormatTypeKey, NSNumber.FromInt32((int)CVPixelFormatType.CV32BGRA));

                    DispatchQueue.MainQueue.DispatchAsync(() =>
                    {
                        //var initialRegionOfInterest = this.PreviewView.VideoPreviewLayer.MapToLayerCoordinates(initialRectOfInterest);
                    });
                }
                else
                {
                    Console.WriteLine("Could not add metadata output to the session");
                    this.setupResult = SessionSetupResult.ConfigurationFailed;
                    this.session.CommitConfiguration();

                    return;
                }

                this.session.CommitConfiguration();
            }
        }
Esempio n. 8
0
        private void ConfigureSession()
        {
            if (setupResult == SessionSetupResult.Success)
            {
                this.session.BeginConfiguration();

                // Add video input
                // Choose the back wide angle camera if available, otherwise default to the front wide angle camera
                defaultVideoDevice = AVCaptureDevice.GetDefaultDevice(AVCaptureDeviceType.BuiltInWideAngleCamera, AVMediaType.Video, AVCaptureDevicePosition.Back) ??
                                     AVCaptureDevice.GetDefaultDevice(AVCaptureDeviceType.BuiltInWideAngleCamera, AVMediaType.Video, AVCaptureDevicePosition.Front) ??
                                     null;

                if (defaultVideoDevice == null)
                {
                    Console.WriteLine("Could not get video device");
                    this.setupResult = SessionSetupResult.ConfigurationFailed;
                    this.session.CommitConfiguration();
                    return;
                }

                NSError error;
                var     videoDeviceInput = AVCaptureDeviceInput.FromDevice(defaultVideoDevice, out error);
                if (this.session.CanAddInput(videoDeviceInput))
                {
                    this.session.AddInput(videoDeviceInput);
                    this.videoDeviceInput = videoDeviceInput;

                    if (this.videoDeviceInput.Device.LockForConfiguration(out error))
                    {
                        if (this.videoDeviceInput.Device.IsFocusModeSupported(AVCaptureFocusMode.ContinuousAutoFocus))
                        {
                            this.videoDeviceInput.Device.FocusMode = AVCaptureFocusMode.ContinuousAutoFocus;
                        }

                        if (this.videoDeviceInput.Device.AutoFocusRangeRestrictionSupported)
                        {
                            this.videoDeviceInput.Device.AutoFocusRangeRestriction = AVCaptureAutoFocusRangeRestriction.Near; //Near는 바코드 스캔용
                        }

                        if (this.videoDeviceInput.Device.IsExposureModeSupported(AVCaptureExposureMode.ContinuousAutoExposure))
                        {
                            this.videoDeviceInput.Device.ExposureMode = AVCaptureExposureMode.ContinuousAutoExposure;
                        }

                        //Console.WriteLine(this.videoDeviceInput.Device.ExposureMode.ToString());
                        this.videoDeviceInput.Device.UnlockForConfiguration();
                    }


                    this.session.SessionPreset = AVCaptureSession.Preset1920x1080;
                    //this.session.SessionPreset = AVCaptureSession.Preset1280x720;

                    DispatchQueue.MainQueue.DispatchAsync(() =>
                    {
                        // Why are we dispatching this to the main queue?
                        // Because AVCaptureVideoPreviewLayer is the backing layer for PreviewView and UIView
                        // can only be manipulated on the main thread
                        // Note: As an exception to the above rule, it's not necessary to serialize video orientation changed
                        // on the AVCaptureVideoPreviewLayer's connection with other session manipulation
                        //
                        // Use the status bar orientation as the internal video orientation. Subsequent orientation changes are
                        // handled by CameraViewController.ViewWillTransition(to:with:).

                        var initialVideoOrientation = AVCaptureVideoOrientation.Portrait;
                        var statusBarOrientation    = UIApplication.SharedApplication.StatusBarOrientation;
                        if (statusBarOrientation != UIInterfaceOrientation.Unknown)
                        {
                            AVCaptureVideoOrientation videoOrintation;
                            if (Enum.TryParse(statusBarOrientation.ToString(), out videoOrintation))
                            {
                                initialVideoOrientation = videoOrintation;
                            }
                        }

                        this.PreviewView.VideoPreviewLayer.Connection.VideoOrientation = initialVideoOrientation;
                    });
                }
                else if (error != null)
                {
                    Console.WriteLine($"Could not create video device input: {error}");
                    this.setupResult = SessionSetupResult.ConfigurationFailed;
                    this.session.CommitConfiguration();
                    return;
                }
                else
                {
                    Console.WriteLine("Could not add video device input to the session");
                    this.setupResult = SessionSetupResult.ConfigurationFailed;
                    this.session.CommitConfiguration();

                    return;
                }


                // Add metadata output
                if (this.session.CanAddOutput(metadataOutput))
                {
                    this.session.AddOutput(metadataOutput);

                    // Set this view controller as the delegate for metadata objects
                    this.metadataOutput.SetDelegate(this, this.metadataObjectsQueue);

                    AVMetadataObjectType supportBarcodeFormat = AVMetadataObjectType.None;

                    //hm.ji, 지원하는 바코드 지정, Defualt로 모든바코드
                    // this.metadataOutput.MetadataObjectTypes = this.metadataOutput.AvailableMetadataObjectTypes; // Use all metadata object types by default

                    string jsonList = Xamarin.Forms.Application.Current.Properties["SupportBarcodeFormat"].ToString();
                    List <Helpers.BarcodeFormat> tmpList = JsonConvert.DeserializeObject <List <Helpers.BarcodeFormat> >(jsonList);

                    supportBarcodeFormat = ConvertToIOS(tmpList);

                    this.metadataOutput.MetadataObjectTypes = supportBarcodeFormat;

                    //this.metadataOutput.MetadataObjectTypes = AVMetadataObjectType.AztecCode |
                    //                                          AVMetadataObjectType.Code128Code |
                    //                                          AVMetadataObjectType.Code39Code |
                    //                                          AVMetadataObjectType.Code39Mod43Code |
                    //                                          AVMetadataObjectType.Code93Code |
                    //                                          AVMetadataObjectType.EAN13Code |
                    //                                          AVMetadataObjectType.EAN8Code |
                    //                                          AVMetadataObjectType.PDF417Code |
                    //                                          AVMetadataObjectType.QRCode |
                    //                                          AVMetadataObjectType.UPCECode |
                    //                                          AVMetadataObjectType.Interleaved2of5Code |
                    //                                          AVMetadataObjectType.ITF14Code |
                    //                                          AVMetadataObjectType.DataMatrixCode;
                    // Set an initial rect of interest that is 80% of the views's shortest side
                    // and 25% of the longest side. This means that the region on interest will
                    // appear in the same spot regardless of whether the app starts in portrait
                    // or landscape

                    //var width = 0.7; //높이 기본값 : 0.25, 전체 사용하려면 1
                    //var height = 0.9; //넓이, 초기 값은 0.8
                    //var x = (1 - width) / 2;
                    //var y = (1 - height) / 2;
                    //var initialRectOfInterest = new CGRect(x + 0.01, y, width, height);

                    CGRect initialRectOfInterest;

                    if (Settings.ScanMode.Equals("FULL"))
                    {
                        var width  = 1.0; //높이 기본값 : 0.25, 전체 사용하려면 1
                        var height = 1.0; //넓이, 초기 값은 0.8
                        var x      = (1 - width) / 2;
                        var y      = (1 - height) / 2;
                        initialRectOfInterest = new CGRect(x, y, width, height);
                    }
                    else if (Settings.ScanMode.Equals("WIDE"))
                    {
                        var width  = 0.25; //높이 기본값 : 0.25, 전체 사용하려면 1
                        var height = 0.9;  //넓이, 초기 값은 0.8
                        var x      = (1 - width) / 2;
                        var y      = (1 - height) / 2;
                        initialRectOfInterest = new CGRect(x, y, width, height);
                    }
                    else if (Settings.ScanMode.Equals("SPLIT"))
                    {
                        var width  = 0.15;
                        var height = 1.0;
                        var x      = (1 - width) / 2;
                        var y      = (1 - height) / 2;
                        initialRectOfInterest = new CGRect(0.09, 0, width, height);
                    }
                    else
                    {
                        var width  = 0.15;
                        var height = 1.0;
                        var x      = (1 - width) / 2;
                        var y      = (1 - height) / 2;
                        initialRectOfInterest = new CGRect(0.09, 0, width, height);
                    }

                    this.metadataOutput.RectOfInterest = initialRectOfInterest;

                    DispatchQueue.MainQueue.DispatchAsync(() =>
                    {
                        var initialRegionOfInterest = this.PreviewView.VideoPreviewLayer.MapToLayerCoordinates(initialRectOfInterest);
                        this.PreviewView.SetRegionOfInterestWithProposedRegionOfInterest(initialRegionOfInterest);
                    });
                }
                else
                {
                    Console.WriteLine("Could not add metadata output to the session");
                    this.setupResult = SessionSetupResult.ConfigurationFailed;
                    this.session.CommitConfiguration();

                    return;
                }

                this.session.CommitConfiguration();
            }
        }
Esempio n. 9
0
        private void ConfigureSession()
        {
            if (setupResult == SessionSetupResult.Success)
            {
                this.session.BeginConfiguration();

                // Add video input
                // Choose the back wide angle camera if available, otherwise default to the front wide angle camera
                AVCaptureDevice defaultVideoDevice = AVCaptureDevice.GetDefaultDevice(AVCaptureDeviceType.BuiltInWideAngleCamera, AVMediaType.Video, AVCaptureDevicePosition.Back) ??
                                                     AVCaptureDevice.GetDefaultDevice(AVCaptureDeviceType.BuiltInWideAngleCamera, AVMediaType.Video, AVCaptureDevicePosition.Front) ??
                                                     null;

                if (defaultVideoDevice == null)
                {
                    Console.WriteLine("Could not get video device");
                    this.setupResult = SessionSetupResult.ConfigurationFailed;
                    this.session.CommitConfiguration();
                    return;
                }

                NSError error;
                var     videoDeviceInput = AVCaptureDeviceInput.FromDevice(defaultVideoDevice, out error);
                if (this.session.CanAddInput(videoDeviceInput))
                {
                    this.session.AddInput(videoDeviceInput);
                    this.videoDeviceInput = videoDeviceInput;

                    DispatchQueue.MainQueue.DispatchAsync(() =>
                    {
                        // Why are we dispatching this to the main queue?
                        // Because AVCaptureVideoPreviewLayer is the backing layer for PreviewView and UIView
                        // can only be manipulated on the main thread
                        // Note: As an exception to the above rule, it's not necessary to serialize video orientation changed
                        // on the AVCaptureVideoPreviewLayer's connection with other session manipulation
                        //
                        // Use the status bar orientation as the internal video orientation. Subsequent orientation changes are
                        // handled by CameraViewController.ViewWillTransition(to:with:).

                        var initialVideoOrientation = AVCaptureVideoOrientation.Portrait;
                        var statusBarOrientation    = UIApplication.SharedApplication.StatusBarOrientation;
                        if (statusBarOrientation != UIInterfaceOrientation.Unknown)
                        {
                            AVCaptureVideoOrientation videoOrintation;
                            if (Enum.TryParse(statusBarOrientation.ToString(), out videoOrintation))
                            {
                                initialVideoOrientation = videoOrintation;
                            }
                        }

                        this.PreviewView.VideoPreviewLayer.Connection.VideoOrientation = initialVideoOrientation;
                    });
                }
                else if (error != null)
                {
                    Console.WriteLine($"Could not create video device input: {error}");
                    this.setupResult = SessionSetupResult.ConfigurationFailed;
                    this.session.CommitConfiguration();
                    return;
                }
                else
                {
                    Console.WriteLine("Could not add video device input to the session");
                    this.setupResult = SessionSetupResult.ConfigurationFailed;
                    this.session.CommitConfiguration();

                    return;
                }


                // Add metadata output
                if (this.session.CanAddOutput(metadataOutput))
                {
                    this.session.AddOutput(metadataOutput);

                    // Set this view controller as the delegate for metadata objects
                    this.metadataOutput.SetDelegate(this, this.metadataObjectsQueue);
                    this.metadataOutput.MetadataObjectTypes = this.metadataOutput.AvailableMetadataObjectTypes; // Use all metadata object types by default

                    // Set an initial rect of interest that is 80% of the views's shortest side
                    // and 25% of the longest side. This means that the region on interest will
                    // appear in the same spot regardless of whether the app starts in portrait
                    // or landscape

                    var width  = 0.25;
                    var height = 0.8;
                    var x      = (1 - width) / 2;
                    var y      = (1 - height) / 2;
                    var initialRectOfInterest = new CGRect(x, y, width, height);
                    this.metadataOutput.RectOfInterest = initialRectOfInterest;

                    DispatchQueue.MainQueue.DispatchAsync(() =>
                    {
                        var initialRegionOfInterest = this.PreviewView.VideoPreviewLayer.MapToLayerCoordinates(initialRectOfInterest);
                        this.PreviewView.SetRegionOfInterestWithProposedRegionOfInterest(initialRegionOfInterest);
                    });
                }
                else
                {
                    Console.WriteLine("Could not add metadata output to the session");
                    this.setupResult = SessionSetupResult.ConfigurationFailed;
                    this.session.CommitConfiguration();

                    return;
                }

                this.session.CommitConfiguration();
            }
        }
		public override void ViewDidLoad ()
		{
			base.ViewDidLoad ();

			// Disable UI. The UI is enabled if and only if the session starts running.
			MetadataObjectTypesButton.Enabled = false;
			SessionPresetsButton.Enabled = false;
			CameraButton.Enabled = false;
			ZoomSlider.Enabled = false;

			// Add the open barcode gesture recognizer to the region of interest view.
			PreviewView.AddGestureRecognizer (OpenBarcodeURLGestureRecognizer);

			// Set up the video preview view.
			PreviewView.Session = session;

			// Check video authorization status. Video access is required and audio
			// access is optional. If audio access is denied, audio is not recorded
			// during movie recording.
			switch (AVCaptureDevice.GetAuthorizationStatus (AVMediaType.Video)) {
			case AVAuthorizationStatus.Authorized:
				// The user has previously granted access to the camera.
				break;

			case AVAuthorizationStatus.NotDetermined:
				// The user has not yet been presented with the option to grant
				// video access. We suspend the session queue to delay session
				// setup until the access request has completed.
				sessionQueue.Suspend ();
				AVCaptureDevice.RequestAccessForMediaType (AVMediaType.Video, granted => {
					if (!granted)
						setupResult = SessionSetupResult.NotAuthorized;
					sessionQueue.Resume ();
				});
				break;

			default:
				// The user has previously denied access.
				setupResult = SessionSetupResult.NotAuthorized;
				break;
			}

			// Setup the capture session.
			// In general it is not safe to mutate an AVCaptureSession or any of its
			// inputs, outputs, or connections from multiple threads at the same time.
			// Why not do all of this on the main queue?
			// Because AVCaptureSession.StartRunning() is a blocking call which can
			// take a long time. We dispatch session setup to the sessionQueue so
			// that the main queue isn't blocked, which keeps the UI responsive.
			sessionQueue.DispatchAsync (ConfigureSession);
		}
		void ConfigureSession ()
		{
			if (setupResult != SessionSetupResult.Success)
				return;

			session.BeginConfiguration ();

			var videoDevice = DeviceWithMediaType (AVMediaType.Video, AVCaptureDevicePosition.Back);
			NSError err;
			var vDeviceInput = AVCaptureDeviceInput.FromDevice (videoDevice, out err);
			if (err != null) {
				Console.WriteLine ($"Could not create video device input: ${err}");
				setupResult = SessionSetupResult.ConfigurationFailed;
				session.CommitConfiguration ();
				return;
			}

			if (session.CanAddInput (vDeviceInput)) {
				session.AddInput (vDeviceInput);
				videoDeviceInput = vDeviceInput;
			} else {
				Console.WriteLine ("Could not add video device input to the session");
				setupResult = SessionSetupResult.ConfigurationFailed;
				session.CommitConfiguration ();
				return;
			}

			// Add metadata output.
			if (session.CanAddOutput (metadataOutput)) {
				session.AddOutput (metadataOutput);

				// Set this view controller as the delegate for metadata objects.
				metadataOutput.SetDelegate (this, metadataObjectsQueue);
				metadataOutput.MetadataObjectTypes = metadataOutput.AvailableMetadataObjectTypes; // Use all metadata object types by default.
				metadataOutput.RectOfInterest = CGRect.Empty;
			} else {
				Console.WriteLine ("Could not add metadata output to the session");
				setupResult = SessionSetupResult.ConfigurationFailed;
				session.CommitConfiguration ();
				return;
			}

			session.CommitConfiguration ();
		}