围绕AVCaptureSession的核心类的简介

AVCaptureSession是AVFoundation的核心类,用于捕捉视频和音频,协调视频和音频的输入和输出流.

对session的常见操作:

1. 创建AVCaptureSession

设置SessionPreset,用于设置output输出流的bitrate或者说画面质量

// 1 创建session
AVCaptureSession *session = [AVCaptureSession new];
//设置session显示分辨率
if ([[UIDevice currentDevice] userInterfaceIdiom] == UIUserInterfaceIdiomPhone)
    [session setSessionPreset:AVCaptureSessionPreset640x480];
    [session setSessionPreset:AVCaptureSessionPresetPhoto];

2. 给Session添加input输入

一般是Video或者Audio数据,也可以两者都添加,即AVCaptureSession的输入源AVCaptureDeviceInput.

// 2 获取摄像头device,并且默认使用的后置摄像头,并且将摄像头加入到captureSession中
AVCaptureDevice *device = [AVCaptureDevice defaultDeviceWithMediaType:AVMediaTypeVideo];
AVCaptureDeviceInput *deviceInput = [AVCaptureDeviceInput deviceInputWithDevice:device error:&error];
isUsingFrontFacingCamera = NO;
if ([session canAddInput:deviceInput]){
    [session addInput:deviceInput];
  

3. 给session添加output输出

添加AVCaptureOutput,即AVCaptureSession的输出源.一般输出源分成:音视频源,图片源,文件源等.

  • 音视频输出AVCaptureAudioDataOutput,AVCaptureVideoDataOutput.
  • 静态图片输出AVCaptureStillImageOutput(iOS10中被AVCapturePhotoOutput取代了)
  • AVCaptureMovieFileOutput表示文件源.

通常如果需要音视频帧,需要在将output加入到session之前,设置videoSetting或者audioSetting,主要是音视频的格式或者回调的delegate以及dispatch queue.

// 4 创建拍照使用的AVCaptureStillImageOutput,并且注册observer观察capturingStillImage,并将output加入到session. 使用observer的作用监控"capturingStillImage",如果为YES,那么表示开始截取视频帧.在回调方法中显示闪屏效果
stillImageOutput = [AVCaptureStillImageOutput new];
[stillImageOutput addObserver:self forKeyPath:@"capturingStillImage" options:NSKeyValueObservingOptionNew context:(__bridge void * _Nullable)(AVCaptureStillImageIsCapturingStillImageContext)];
if ([session canAddOutput:stillImageOutput]){
    [session addOutput:stillImageOutput];
// 5 创建预览output,设置预览videosetting,然后设置预览delegate使用的回调线程,将该预览output加入到session
videoDataOutput = [AVCaptureVideoDataOutput new];
// we want BGRA, both CoreGraphics and OpenGL work well with 'BGRA'
NSDictionary *rgbOutputSettings = [NSDictionary dictionaryWithObject:
                                   [NSNumber numberWithInt:kCMPixelFormat_32BGRA] forKey:(id)kCVPixelBufferPixelFormatTypeKey];
[videoDataOutput setVideoSettings:rgbOutputSettings];
[videoDataOutput setAlwaysDiscardsLateVideoFrames:YES]; // discard if the data output queue is blocked (as we process the still image)
// create a serial dispatch queue used for the sample buffer delegate as well as when a still image is captured
// a serial dispatch queue must be used to guarantee that video frames will be delivered in order
// see the header doc for setSampleBufferDelegate:queue: for more information
videoDataOutputQueue = dispatch_queue_create("VideoDataOutputQueue", DISPATCH_QUEUE_SERIAL);
[videoDataOutput setSampleBufferDelegate:self queue:videoDataOutputQueue];
if ([session canAddOutput:videoDataOutput]){
    [session addOutput:videoDataOutput];
  

4. AVCaptureConnection设置input,output连接的重要属性

在给AVCaptureSession添加input和output以后,就可以通过audio或者video的output生成AVCaptureConnection.通过connection设置output的视频或者音频的重要属性,比如ouput video的方向videoOrientation(这里注意videoOrientation并非DeviceOrientation,默认情况下录制的视频是90度转角的,这个是相机传感器导致的,请google)

[[videoDataOutput connectionWithMediaType:AVMediaTypeVideo] setEnabled:NO];
AVCaptureConnection *videoCon = [videoDataOutput connectionWithMediaType:AVMediaTypeVideo];
// 原来的刷脸没有这句话.因此录制出来的视频是有90度转角的, 这是默认情况
if ([videoCon isVideoOrientationSupported]) {
//        videoCon.videoOrientation = AVCaptureVideoOrientationPortrait;
    // 下面这句是默认系统video orientation情况!!!!,如果要outputsample图片输出的方向是正的那么需要将这里设置称为portrait
    //videoCon.videoOrientation = AVCaptureVideoOrientationLandscapeLeft;
  

5. 视频预览层AVCaptureVideoPreviewLayer

在input,output等重要信息都添加到session以后,可以用session创建AVCaptureVideoPreviewLayer,这是摄像头的视频预览层.

previewLayer = [[AVCaptureVideoPreviewLayer alloc] initWithSession:session];
[previewLayer setBackgroundColor:[[UIColor blackColor] CGColor]];
[previewLayer setVideoGravity:AVLayerVideoGravityResizeAspectFill];// 犹豫使用的aspectPerserve
CALayer *rootLayer = [previewView layer];
[rootLayer setMasksToBounds:YES];
[previewLayer setFrame:[rootLayer bounds]];
[rootLayer addSublayer:previewLayer];

6. 启动session

// 7 启动session,output开始接受samplebuffer回调
[session startRunning];

Apple Demo SquareCam的session的完整的初始化

具体解释见注释

* 相机初始化方法 - (void)setupAVCapture NSError *error = nil; // 1 创建session AVCaptureSession *session = [AVCaptureSession new]; // 2 设置session显示分辨率 if ([[UIDevice currentDevice] userInterfaceIdiom] == UIUserInterfaceIdiomPhone) [session setSessionPreset:AVCaptureSessionPreset640x480]; [session setSessionPreset:AVCaptureSessionPresetPhoto]; // 3 获取摄像头device,并且默认使用的后置摄像头,并且将摄像头加入到captureSession中 AVCaptureDevice *device = [AVCaptureDevice defaultDeviceWithMediaType:AVMediaTypeVideo]; AVCaptureDeviceInput *deviceInput = [AVCaptureDeviceInput deviceInputWithDevice:device error:&error]; isUsingFrontFacingCamera = NO; if ( [session canAddInput:deviceInput] ) [session addInput:deviceInput]; // 4 创建拍照使用的AVCaptureStillImageOutput,并且注册observer观察capturingStillImage,并将output加入到session. 使用observer的作用监控"capturingStillImage",如果为YES,那么表示开始截取视频帧.在回调方法中显示闪屏效果 stillImageOutput = [AVCaptureStillImageOutput new]; [stillImageOutput addObserver:self forKeyPath:@"capturingStillImage" options:NSKeyValueObservingOptionNew context:(__bridge void * _Nullable)(AVCaptureStillImageIsCapturingStillImageContext)]; if ( [session canAddOutput:stillImageOutput] ) [session addOutput:stillImageOutput]; // 5 创建预览output,设置预览videosetting,然后设置预览delegate使用的回调线程,将该预览output加入到session videoDataOutput = [AVCaptureVideoDataOutput new]; // we want BGRA, both CoreGraphics and OpenGL work well with 'BGRA' NSDictionary *rgbOutputSettings = [NSDictionary dictionaryWithObject: [NSNumber numberWithInt:kCMPixelFormat_32BGRA] forKey:(id)kCVPixelBufferPixelFormatTypeKey]; [videoDataOutput setVideoSettings:rgbOutputSettings]; [videoDataOutput setAlwaysDiscardsLateVideoFrames:YES]; // discard if the data output queue is blocked (as we process the still image) // create a serial dispatch queue used for the sample buffer delegate as well as when a still image is captured // a serial dispatch queue must be used to guarantee that video frames will be delivered in order // see the header doc for setSampleBufferDelegate:queue: for more information videoDataOutputQueue = dispatch_queue_create("VideoDataOutputQueue", DISPATCH_QUEUE_SERIAL); [videoDataOutput setSampleBufferDelegate:self queue:videoDataOutputQueue]; if ( [session canAddOutput:videoDataOutput] ) [session addOutput:videoDataOutput]; [[videoDataOutput connectionWithMediaType:AVMediaTypeVideo] setEnabled:NO]; AVCaptureConnection *videoCon = [videoDataOutput connectionWithMediaType:AVMediaTypeVideo]; // 原来的刷脸没有这句话.因此录制出来的视频是有90度转角的, 这是默认情况 if ([videoCon isVideoOrientationSupported]) { // videoCon.videoOrientation = AVCaptureVideoOrientationPortrait; // 下面这句是默认系统video orientation情况!!!!,如果要outputsample图片输出的方向是正的那么需要将这里设置称为portrait //videoCon.videoOrientation = AVCaptureVideoOrientationLandscapeLeft; effectiveScale = 1.0; // 6 获取相机的实时预览layer,并且设置layer的拉升属性AVLayerVideoGravityResizeAspect,设置previewLayer的bounds,并加入到view中 previewLayer = [[AVCaptureVideoPreviewLayer alloc] initWithSession:session]; [previewLayer setBackgroundColor:[[UIColor blackColor] CGColor]]; [previewLayer setVideoGravity:AVLayerVideoGravityResizeAspectFill];// 犹豫使用的aspectPerserve CALayer *rootLayer = [previewView layer]; [rootLayer setMasksToBounds:YES]; [previewLayer setFrame:[rootLayer bounds]]; [rootLayer addSublayer:previewLayer]; // 7 启动session,output开始接受samplebuffer回调 [session startRunning]; bail: if (error) { UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:[NSString stringWithFormat:@"Failed with error %d", (int)[error code]] message:[error localizedDescription] delegate:nil cancelButtonTitle:@"Dismiss" otherButtonTitles:nil]; [alertView show]; [self teardownAVCapture];

请参考apple 的官方demo: SquareCam


作者:brownfeng
链接:http://www.jianshu.com/p/b5618066dc2c
來源:简书
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。 转自:基本使用流程AVCaptureSession是AVFoundation的核心类,用于捕捉视频和音频,协调视频和音频的输入和输出流.下面是简书上找的围绕AVCaptureSession的图AVCapureSession.jpg围绕AVCaptureSession的核心类的简介AVCaptureSession是AVFoundation的核心类,用于
Live Networks LIVE555 streaming media RTSPServer lookForHeader code execution vulnerability OCTOBER 18, 2018 CVE NUMBER CVE-2018-4013 Summary An exploitable code execution vulnerability ex...
compile 'com.android.support:design:26.+' compile 'com.hjm:BottomTabBar:1.1.1' compile 'com.jakewharton:butterknife:7.0.1' compile 'io.reactivex:rxandroid:1.1.0' compile 'com.squareup.retrofit2:retrof
1. 简述 在音视频开发中,我们首先看到的就是视频的采集,在视频采集里,我们也要区分平台,例如android,iOS,PC。在本章的介绍中,我们集中介绍下iOS音视频开发相关能力。 从图里,我们可以看到,在整个直播架构体系里面,最开始的就是采集,之后就是编码,封装,推流,转发,拉流,解码,渲染。 我们今天先从第一个,采集开始,为你们系统介绍iOS视频采集相关流程。 2. 视频采集流程 iOS采集器的基本结构图如下: 从图里可以看到,我们可以通过AVCapture Device Input创建输入资源,通
华为VR眼镜终于来了笨丫头什么叫收租啊我一瞪眼你把黄金器给我我交易给你金币黄金器直接丢在我的小卖部里或许能顶出一个高价你明白吗华为VR眼镜终于来了笨丫头什么叫收租啊我一瞪眼你把黄金器给我我交易给你金币黄金器直接丢在我的小卖部里或许能顶出一个高价你明白吗华为VR眼镜终于来了笨丫头什么叫收租啊我一瞪眼你把黄金器给我我交易给你金币黄金器直接丢在我的小卖部里或许能顶出一个高价你明白吗华为VR眼镜终于来了
最近做了一个Android UI相关开源项目库汇总,里面集合了OpenDigg上的优质的Android开源项目库,方便移动开发人员便捷的找到自己需要的项目工具等,感兴趣的可以到GitHub上给个star。 MaterialDrawer★7337 - 安卓抽屉效果实现方案 Side-Menu.Android★3865 - 创意边侧菜单 FlowingDrawer★174...
Exception in thread "main" com.google.gson.JsonSyntaxException: com.google.gson.stream.MalformedJsonException: Unterminated object at line 1 column 29 path $.data at com.google.gson.internal.Streams.parse(Streams.java:60...
要使用AVCaptureSession这个类,首先需要对它有所了解,AVCaptureSession是AVFoundation库中的一个,如果我们需要使用的话,需要先了解其他几个类;分别是:AVCaptureDevice、AVCaptureDeviceInput、AVCaptureMetadataOutput、AVCaptureVideoPreviewLayer。下面我们就一一来介绍一下各个类
iOS中,摄像头采集到的图片有可能会被自动旋转。这是因为iOS设备的摄像头在捕捉照片时会考虑设备的方向并自动旋转照片方向。如果你使用AVCaptureSession拍摄照片,可以通过以下步骤解决: 1. 获取照片的方向信息 在`captureOutput`回调方法中,可以通过`AVCaptureConnection`的`videoOrientation`属性获取照片的方向信息。代码示例如下: - (void)captureOutput:(AVCaptureOutput *)output didOutputSampleBuffer:(CMSampleBufferRef)sampleBuffer fromConnection:(AVCaptureConnection *)connection { // 获取视频方向 AVCaptureVideoOrientation videoOrientation = connection.videoOrientation; // ... 2. 修正照片的方向 根据照片的方向信息,可以使用`UIImage`的`imageWithCGImage:scale:orientation:`方法修正照片的方向。代码示例如下: - (void)captureOutput:(AVCaptureOutput *)output didOutputSampleBuffer:(CMSampleBufferRef)sampleBuffer fromConnection:(AVCaptureConnection *)connection { // 获取视频方向 AVCaptureVideoOrientation videoOrientation = connection.videoOrientation; // 转换CMSampleBufferRef为UIImage UIImage *image = [self imageFromSampleBuffer:sampleBuffer]; // 修正照片方向 image = [UIImage imageWithCGImage:image.CGImage scale:image.scale orientation:[self imageOrientationFromVideoOrientation:videoOrientation]]; // ... - (UIImage *)imageFromSampleBuffer:(CMSampleBufferRef)sampleBuffer { // ... - (UIImageOrientation)imageOrientationFromVideoOrientation:(AVCaptureVideoOrientation)videoOrientation { // ... 其中,`imageFromSampleBuffer:`方法可以将`CMSampleBufferRef`转换为`UIImage`,`imageOrientationFromVideoOrientation:`方法可以将`AVCaptureVideoOrientation`转换为`UIImageOrientation`。这两个方法的具体实现可以参考相关文档或示例代码。 通过以上步骤,可以修正照片的方向,使其显示正常。