Cómo agregar Vista previa de Live Camera a UIView

Me encuentro con un problema, estoy tratando de resolver dentro del límite de UIView, ¿hay alguna forma de Agregar Vista previa de camera a UIView? Y agrega otro contenido en la parte superior de UIView (botones, label, etc.)?

Intento utilizar AVFoundation Framework, pero no hay suficiente documentation para Swift.

ACTUALIZADO PARA SWIFT 3

Puedes probar algo como esto:

import UIKit import AVFoundation class ViewController: UIViewController{ var previewView : UIView! var boxView:UIView! let myButton: UIButton = UIButton() //Camera Capture requienetworking properties var videoDataOutput: AVCaptureVideoDataOutput! var videoDataOutputQueue: DispatchQueue! var previewLayer:AVCaptureVideoPreviewLayer! var captureDevice : AVCaptureDevice! let session = AVCaptureSession() override func viewDidLoad() { super.viewDidLoad() previewView = UIView(frame: CGRect(x: 0, y: 0, width: UIScreen.main.bounds.size.width, height: UIScreen.main.bounds.size.height)) previewView.contentMode = UIViewContentMode.scaleAspectFit view.addSubview(previewView) //Add a view on top of the cameras' view boxView = UIView(frame: self.view.frame) myButton.frame = CGRect(x: 0, y: 0, width: 200, height: 40) myButton.backgroundColor = UIColor.networking myButton.layer.masksToBounds = true myButton.setTitle("press me", for: UIControlState.normal) myButton.setTitleColor(UIColor.white, for: UIControlState.normal) myButton.layer.cornerRadius = 20.0 myButton.layer.position = CGPoint(x: self.view.frame.width/2, y:200) myButton.addTarget(self, action: #selector(self.onClickMyButton(sender:)), for: UIControlEvents.touchUpInside) view.addSubview(boxView) view.addSubview(myButton) self.setupAVCapture() } override var shouldAutorotate: Bool { if (UIDevice.current.orientation == UIDeviceOrientation.landscapeLeft || UIDevice.current.orientation == UIDeviceOrientation.landscapeRight || UIDevice.current.orientation == UIDeviceOrientation.unknown) { return false } else { return true } } func onClickMyButton(sender: UIButton){ print("button pressed") } } // AVCaptureVideoDataOutputSampleBufferDelegate protocol and related methods extension ViewController: AVCaptureVideoDataOutputSampleBufferDelegate{ func setupAVCapture(){ session.sessionPreset = AVCaptureSessionPreset640x480 guard let device = AVCaptureDevice .defaultDevice(withDeviceType: .builtInWideAngleCamera, mediaType: AVMediaTypeVideo, position: .back) else{ return } captureDevice = device beginSession() } func beginSession(){ var err : NSError? = nil var deviceInput:AVCaptureDeviceInput? do { deviceInput = try AVCaptureDeviceInput(device: captureDevice) } catch let error as NSError { err = error deviceInput = nil } if err != nil { print("error: \(err?.localizedDescription)"); } if self.session.canAddInput(deviceInput){ self.session.addInput(deviceInput); } videoDataOutput = AVCaptureVideoDataOutput() videoDataOutput.alwaysDiscardsLateVideoFrames=true videoDataOutputQueue = DispatchQueue(label: "VideoDataOutputQueue") videoDataOutput.setSampleBufferDelegate(self, queue:self.videoDataOutputQueue) if session.canAddOutput(self.videoDataOutput){ session.addOutput(self.videoDataOutput) } videoDataOutput.connection(withMediaType: AVMediaTypeVideo).isEnabled = true self.previewLayer = AVCaptureVideoPreviewLayer(session: self.session) self.previewLayer.videoGravity = AVLayerVideoGravityResizeAspect let rootLayer :CALayer = self.previewView.layer rootLayer.masksToBounds = true self.previewLayer.frame = rootLayer.bounds rootLayer.addSublayer(self.previewLayer) session.startRunning() } func captureOutput(_ captureOutput: AVCaptureOutput!, didOutputSampleBuffer sampleBuffer: CMSampleBuffer!, from connection: AVCaptureConnection!) { // do stuff here } // clean up AVCapture func stopCamera(){ session.stopRunning() } } 

Aquí utilizo una UIview llamada previewView para iniciar la camera y luego agrego una nueva UIView llamada boxView que está por encima de previewView. Agrego un UIButton a boxView

IMPORTANTE

Recuerde que en iOS 10 primero debe pedir permiso al usuario para tener acceso a la camera. Para ello, agregue una key de uso a Info.plist su aplicación junto con una cadena de propósito, ya que si no declara el uso, su aplicación se bloqueará cuando realice el acceso por primera vez.

Aquí hay una captura de pantalla para mostrar la request de acceso a la camera. introduzca la descripción de la imagen aquí

Swift 3:

 @IBOutlet weak var cameraContainerView:UIView! var imagePickers:UIImagePickerController? 

En ViewDidLoad:

 override func viewDidLoad() { super.viewDidLoad() addImagePickerToContainerView() } 

Agregar vista previa de la camera a la vista del contenedor:

 func addImagePickerToContainerView(){ imagePickers = UIImagePickerController() if UIImagePickerController.isCameraDeviceAvailable( UIImagePickerControllerCameraDevice.front) { imagePickers?.delegate = self imagePickers?.sourceType = UIImagePickerControllerSourceType.camera //add as a childviewcontroller addChildViewController(imagePickers!) // Add the child's View as a subview self.cameraContainerView.addSubview((imagePickers?.view)!) imagePickers?.view.frame = cameraContainerView.bounds imagePickers?.allowsEditing = false imagePickers?.showsCameraControls = false imagePickers?.view.autoresizingMask = [.flexibleWidth, .flexibleHeight] } } 

En la acción personalizada del button:

 @IBAction func cameraButtonPressed(_ sender: Any) { if UIImagePickerController.isSourceTypeAvailable(.camera){ imagePickers?.takePicture() } else{ //Camera not available. } }