使用AVCptureSession获取静态图片,我们需要如下这几个类:
- AVCaptureDevice : 代表输入设备,如照相机或者麦克风.它被用于控制硬件特性,诸如镜头的位置、曝光、闪光灯等。
- AVCaptureInput : 提供来自设备的数据。
- AVCaptureOutput : 管理视频文件或者静态图像的输出.以下是三种关于静态图片捕捉的具体子类:
– AVCaptureStillImageOutput 用于捕捉静态图片
– AVCaptureMetadataOutput 启用检测人脸和二维码
– AVCaptureVideoOutput 为实时预览图提供原始帧
- AVCaptureSession: 协调输入和输出之间的数据流.
在很多情况下,这就是我们所需要的.但是,在一些情况下,我们需要选择哪个输入的端口需要和输出相连接.
一个AVCaptureConnection
对象代表了一个输入和输出在session中的连接.输入拥有一个或者多个接口,而输出可以接受一个或者多个来源的数据.
当往session中加入输入和输出,session会生成所有兼容的input和output之间的connection.所以我们需要选择我们需要的connection
设置并获取静态图片
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34
| self.session = AVCaptureSession() self.session?.sessionPreset = AVCaptureSessionPresetPhoto let DevicesArray = AVCaptureDevice.devices() for device in DevicesArray { if(device.position == AVCaptureDevicePosition.Front){ do{ try self.deviceInput = AVCaptureDeviceInput(device: device as! AVCaptureDevice) } catch{print("initialize device failed")} } } self.session?.addInput(self.deviceInput) self.stillImageOutput = AVCaptureStillImageOutput() let outputSetting = [AVVideoCodecKey : AVVideoCodecJPEG] self.stillImageOutput?.outputSettings = outputSetting self.session?.addOutput(self.stillImageOutput) for connection in (stillImageOutput?.connections)!{ for port in (connection as! AVCaptureConnection).inputPorts{ if (port.mediaType == AVMediaTypeVideo){ self.captureConnection = connection as! AVCaptureConnection self.captureConnection?.videoOrientation = AVCaptureVideoOrientation.Portrait break } } } self.session?.startRunning() self.stillImageOutput?.captureStillImageAsynchronouslyFromConnection(self.captureConnection, completionHandler: { (buffer, error) -> Void in if(buffer != nil){ let imageData = AVCaptureStillImageOutput.jpegStillImageNSDataRepresentation(buffer) var image = UIImage(data: imageData) }
|
录制视频,并写入文件
写入文件有两种方法.
AVCaptureMovieFileOutput
将视频写入文件,最简单的选择就是使用 AVCaptureMovieFileOutput 对象。把它作为输出添加到 capture session 中,就可以将视频和音频写入 QuickTime 文件,这只需很少的配置。
AVCaptureDataOutput 和 AVAssetWriter
重点说说第二种方法.
在session开始后,输出会捕获视频和音频的样本缓存,并且发送到代理.在这之前,需要先设置代理
1
| public func setSampleBufferDelegate(sampleBufferDelegate: AVCaptureVideoDataOutputSampleBufferDelegate!, queue sampleBufferCallbackQueue: dispatch_queue_t!)
|
其中的queue指定了所有采样缓存协议方法的被调用的线程.
这样,在session开始后,会调用代理的方法:
1 2 3
| optional func captureOutput(_ captureOutput: AVCaptureOutput!, didOutputSampleBuffer sampleBuffer: CMSampleBuffer!, fromConnection connection: AVCaptureConnection!)
|
在这个方法里我们可以对采样缓冲进行处理,或者保持原样传送.可以利用AVAssetWriterInput
写入文件.
1
| public func appendSampleBuffer(sampleBuffer: CMSampleBuffer) -> Bool
|
CVPixelBufferRef
对于CVPixelBufferRef
,我们需要用到AVAssetWriterInputPixelBufferAdaptor
来把buffer附加到AVAssetWriterInput
上.
1 2 3 4
| public init(assetWriterInput input: AVAssetWriterInput, sourcePixelBufferAttributes: [String : AnyObject]?)
public func appendPixelBuffer(pixelBuffer: CVPixelBuffer, withPresentationTime presentationTime: CMTime) -> Bool }
|