視頻采集
AVFoundation 完成視頻采集,做個筆記吧.
初始化頁面布局
UILabel *titleLabel = [[UILabel alloc] init];
titleLabel.text = @"音視頻采集";
[self.view addSubview:titleLabel];
[titleLabel mas_makeConstraints:^(MASConstraintMaker *make) {
make.top.equalTo(self.view).offset(30);
make.centerX.equalTo(self.view);
}];
UIButton *beginInputVideo = [UIButton buttonWithType:UIButtonTypeCustom];
[beginInputVideo setTitle:@"開始視頻采集" forState:UIControlStateNormal];
[beginInputVideo setTitle:@"停止視頻采集" forState:UIControlStateSelected];
beginInputVideo.backgroundColor = [UIColor orangeColor];
[beginInputVideo addTarget:self action:@selector(beginInputVideoClcik:) forControlEvents:UIControlEventTouchUpInside];
[self.view addSubview:beginInputVideo];
[beginInputVideo mas_makeConstraints:^(MASConstraintMaker *make) {
make.top.equalTo(titleLabel.mas_bottom).offset(20);
make.centerX.equalTo(titleLabel);
make.width.equalTo(@150);
}];
self.captureVideoPreviewView = [[UIView alloc] init];
self.captureVideoPreviewView.backgroundColor = [UIColor whiteColor];
[self.view addSubview:self.captureVideoPreviewView];
[self.captureVideoPreviewView mas_makeConstraints:^(MASConstraintMaker *make) {
make.top.equalTo(beginInputVideo.mas_bottom).offset(20);
make.left.right.bottom.equalTo(self.view);
}];
懶加載需要用的對象
/** 圖像sesson */
@property (nonatomic, strong) AVCaptureSession *captureSession;
/** 采集數(shù)據(jù)用的相機設(shè)備 */
@property (nonatomic, strong) AVCaptureDevice *inputCamera;
/** 輸入 */
@property (nonatomic, strong) AVCaptureDeviceInput *captureDeviceInput;
/** 輸出 */
@property (nonatomic, strong) AVCaptureVideoDataOutput *captureVideoDataOutput;
/** 相機采集頁面的layer */
@property (nonatomic, strong) AVCaptureVideoPreviewLayer *captureVideoPreviewLayer;
/** 相機采集頁面View */
@property (nonatomic, strong) UIView *captureVideoPreviewView;
下面是懶加載的代碼
- (AVCaptureSession *)captureSession {
if (!_captureSession) {
_captureSession = [[AVCaptureSession alloc] init];
// 設(shè)置session顯示分辨率, 用于設(shè)置output輸出流的bitrate或者說畫面質(zhì)量
[_captureSession setSessionPreset:AVCaptureSessionPresetHigh];
/*
AVCaptureSessionPresetHigh 質(zhì)量最高
AVCaptureSessionPresetPhoto Photo模式不能輸出視頻
AVCaptureSessionPresetMedium 中等質(zhì)量
AVCaptureSessionPresetLow 最低質(zhì)量
AVCaptureSessionPreset320x240 320x240大刑泶伞(不支持IPhone)
AVCaptureSessionPreset352x288 (支持iPhone)
AVCaptureSessionPreset640x480(支持iPhone)等等...
*/
if ([_captureSession canAddInput:self.captureDeviceInput]) {
[_captureSession addInput:self.captureDeviceInput];
}
if ([_captureSession canAddOutput:self.captureVideoDataOutput]) {
[_captureSession addOutput:self.captureVideoDataOutput];
}
}
return _captureSession;
}
- (AVCaptureDevice *)inputCamera {
if (!_inputCamera) {
NSArray *devices = [AVCaptureDevice devicesWithMediaType:AVMediaTypeVideo];
for (AVCaptureDevice *device in devices) {
if ([device position] == AVCaptureDevicePositionBack) {
_inputCamera = device;
}
}
}
return _inputCamera;
}
- (AVCaptureDeviceInput *)captureDeviceInput {
if (!_captureDeviceInput) {
NSError *error;
_captureDeviceInput = [[AVCaptureDeviceInput alloc] initWithDevice:self.inputCamera error:&error];
NSLog(@"%@", error);
}
return _captureDeviceInput;
}
- (AVCaptureVideoDataOutput *)captureVideoDataOutput {
if (!_captureVideoDataOutput) {
_captureVideoDataOutput = [[AVCaptureVideoDataOutput alloc] init];
_captureVideoDataOutput.alwaysDiscardsLateVideoFrames = YES;
[_captureVideoDataOutput setAlwaysDiscardsLateVideoFrames:NO];
[_captureVideoDataOutput setVideoSettings:[NSDictionary dictionaryWithObject:[NSNumber numberWithInt:kCVPixelFormatType_420YpCbCr8BiPlanarFullRange] forKey:(id)kCVPixelBufferPixelFormatTypeKey]];
[_captureVideoDataOutput setSampleBufferDelegate:self queue:encodeQueue];
AVCaptureConnection *captureConnection = [_captureVideoDataOutput connectionWithMediaType:AVMediaTypeVideo];
[captureConnection setVideoOrientation:AVCaptureVideoOrientationPortrait | AVCaptureVideoOrientationLandscapeRight | AVCaptureVideoOrientationLandscapeLeft];
}
return _captureVideoDataOutput;
}
- (AVCaptureVideoPreviewLayer *)captureVideoPreviewLayer {
if (!_captureVideoPreviewLayer) {
_captureVideoPreviewLayer = [[AVCaptureVideoPreviewLayer alloc] initWithSession:self.captureSession];
/*
AVLayerVideoGravityResizeAspect // 適合層范圍內(nèi)(完全顯示,可能有黑邊)
AVLayerVideoGravityResizeAspectFill // 填充層邊界(平鋪,不拉伸,但是會被裁剪,內(nèi)容可能顯示不全)
AVLayerVideoGravityResize // 拉伸填充層邊界(拉伸填充視圖)
*/
[_captureVideoPreviewLayer setVideoGravity:AVLayerVideoGravityResizeAspect];
}
return _captureVideoPreviewLayer;
}
開始視頻采集
- (void)beginInputVideo {
self.captureVideoPreviewLayer.frame = self.captureVideoPreviewView.bounds;
self.captureVideoPreviewLayer.backgroundColor = [UIColor blackColor].CGColor;
[self.captureVideoPreviewView.layer addSublayer:self.captureVideoPreviewLayer];
[self.captureSession startRunning];
}
采集到視頻數(shù)據(jù)的回調(diào)
/**
采集到數(shù)據(jù)的回調(diào)
@param output outPut對象
@param sampleBuffer 數(shù)據(jù)
@param connection 鏈接
*/
- (void)captureOutput:(AVCaptureOutput *)output didOutputSampleBuffer:(CMSampleBufferRef)sampleBuffer fromConnection:(AVCaptureConnection *)connection {
NSLog(@"%@", sampleBuffer);
}
注: 如發(fā)現(xiàn)問題,請留言.謝謝.