GPUImage(六):GPUImageMovieWriter 保存滤镜处理过的视频

GPUImage保存滤镜视频.png

实现原理:

通过GPUImage滤镜处理、录制、保存的思路如图。
视频部分:经过filter的视频帧分两步,一步用于在屏幕预览GPUImageView上显示,另一步用于写入GPUImageMovieWriter。
音频部分:从GPUImageVideoCamera分离的音频直接写入GPUImageMovieWriter。另外,如果需要对音频进行混响、变声等处理,可以从这个节点分支处理写入。

实现流程:

摄像头

videoCamera = [[GPUImageVideoCamera alloc] initWithSessionPreset:AVCaptureSessionPreset640x480 cameraPosition:AVCaptureDevicePositionBack];
videoCamera.outputImageOrientation = UIInterfaceOrientationPortrait;
videoCamera.runBenchmark = YES;

滤镜和预览响应链

filter = [[GPUImageSaturationFilter alloc] init];
previewView = [[GPUImageView alloc] initWithFrame:self.view.frame];
previewView.fillMode = kGPUImageFillModePreserveAspectRatio;
self.view = previewView;

[videoCamera addTarget:filter];    
[filter addTarget:previewView];

[videoCamera startCameraCapture];

录入本地和保存

//开始
unlink([pathToMovie UTF8String]);
movieWriter = [[GPUImageMovieWriter alloc] initWithMovieURL:movieURL size:CGSizeMake(480, 640)];
movieWriter.encodingLiveVideo = YES;

[filter addTarget:movieWriter];
videoCamera.audioEncodingTarget = movieWriter;

[movieWriter startRecording];

//结束
 [filter removeTarget:movieWriter];
videoCamera.audioEncodingTarget = nil;
[movieWriter finishRecording];

[self saveVideoToLibrary:pathToMovie];//存入相册方法

核心类:GPUImageMovieWriter

GPUImageMovieWriter实现了GPUImageInput,一般作为响应链终点。

init方法

最终调用

- (id)initWithMovieURL:(NSURL *)newMovieURL size:(CGSize)newSize fileType:(NSString *)newFileType outputSettings:(NSMutableDictionary *)outputSettings;

方法里重写了void runSynchronouslyOnContextQueue(GPUImageContext *context, void (^block)(void))方法。

录制方法

GPUImage(六):GPUImageMovieWriter 保存滤镜处理过的视频_第1张图片
AVAssetWriter应用原理.png
//私有方法
1 - (void)initializeMovieWithOutputSettings:(NSDictionary *)outputSettings;
//公共方法
2 - (void)startRecording;
3 - (void)startRecordingInOrientation:(CGAffineTransform)orientationTransform;
4 - (void)finishRecording;
5 - (void)finishRecordingWithCompletionHandler:(void (^)(void))handler;
6 - (void)cancelRecording;
7 - (void)processAudioBuffer:(CMSampleBufferRef)audioBuffer;
8 - (void)enableSynchronizationCallbacks;

在私有方法中初始化了AVAssetWriter,传入一个本地存储地址和文件格式。
assetWriter = [[AVAssetWriter alloc] initWithURL:movieURL fileType:fileType error:&error];

2-6的方法无甚可说,基本就是调用AVAssetWriter的三个方法:

  • startWriting
  • cancelWriting
  • finishWriting
    还有finishRecording方法中对音频和视频AVAssetWriterInput调用的方法markAsFinished

第七个方法
- (void)processAudioBuffer:(CMSampleBufferRef)audioBuffer;比较重要,在整个GPUImage中,只在两种响应链起点GPUImageMovie和GPUImageVideoCamera中作为audioEncodingTarget属性调用过,这一部分也可以进行扩展,进行混音等操作。

帧渲染方法

//都是私有方法
- (void)createDataFBO;
- (void)destroyDataFBO;
- (void)setFilterFBO;
- (void)renderAtInternalSizeUsingFramebuffer:(GPUImageFramebuffer *)inputFramebufferToUse;

GPUImageInput协议方法

几个存取方法

追加

** AVAssetWriterInputPixelBufferAdaptor**:
AVAssetWriterInputPixelBufferAdaptor负责将图片转成的缓存数据CVPixelBufferRef追加到AVAssetWriterInput中,(把CVPixelBufferRef视频贞图像拼接到视频中)。

You use an AVAssetWriterInputPixelBufferAdaptor to append video samples packaged as CVPixelBuffer objects to a single AVAssetWriterInput object.//注意overview的部分

你可能感兴趣的:(GPUImage(六):GPUImageMovieWriter 保存滤镜处理过的视频)