上一篇我們從攝像頭捕捉到了畫面并加上了簡單的濾鏡并顯示出來了,接下來急待解決的就是保存捕獲的內(nèi)容到相冊。
翻開ViewController.m
-
首先把捕獲的內(nèi)容保存到沙盒的臨時目錄。一系列動作同樣是兩三行,我要封裝在一個方法里,為之后的一個功能做好準備。
- (void)initMovieWriter { [_filter removeTarget:_movieWriter]; [[NSFileManager defaultManager] removeItemAtURL:[self currentVideoURL] error:nil]; _movieWriter = [[GPUImageMovieWriter alloc] initWithMovieURL:[self videoURLByIndex:0] size:CGSizeMake(540.0, 960.0)]; _movieWriter.encodingLiveVideo = YES; [_filter addTarget:_movieWriter]; }
-
初始化movie writer的時候URL不用硬編碼,用這個方法。先在.h文件中加入一個成員變量
NSUInteger _currentVideoIndex;
(睿智的你一定猜到了我要做什么,不過現(xiàn)在還早):- (NSURL *)currentVideoURL { NSURL *url = [self videoURLByIndex:_currentVideoIndex]; return url; } - (NSURL *)videoURLByIndex:(NSInteger)index { NSString *pathToMovie = [NSHomeDirectory() stringByAppendingPathComponent:@"Documents/Movie"]; if (index != -1) { pathToMovie = [pathToMovie stringByAppendingString:[NSString stringWithFormat:@"%ld", index]]; } pathToMovie = [pathToMovie stringByAppendingString:@".mp4"]; NSURL *url = [NSURL fileURLWithPath:pathToMovie]; return url; }
在viewDidLoad中第二段代碼上方設置
_currentVideoIndex
初始值。
// 4. Setup movie writer
_currentVideoIndex = 0;-
在viewDidLoad中第二段代碼下方設置手勢操作
// 5. Setup gesture UILongPressGestureRecognizer *longPressGesture = [[UILongPressGestureRecognizer alloc] initWithTarget:self action:@selector(handleGesture:)]; [_captureButton addGestureRecognizer:longPressGesture];
-
實現(xiàn)一下
gestureHandler:
的基本框架- (void)handleGesture:(id)sender { if ([sender isKindOfClass:[UILongPressGestureRecognizer class]]) { UILongPressGestureRecognizer *longPressGesture = (UILongPressGestureRecognizer *)sender; switch ([longPressGesture state]) { case UIGestureRecognizerStateBegan: { } break; case UIGestureRecognizerStateEnded: { } break; default: break; } } }
-
保存到相冊好復雜哦。沒關系,官方demo自動錄像10秒保存,記得嗎?把相應代碼挖出來。在viewDidLoad中第一層dispatch里面獲取主線程進行錄像并寫入臨時文件,第二層dispatch預約了10秒后結束錄像并保存到相冊。
注意movie writer的初始化在每次錄像之前進行。因為一旦writer錄像過并停止,這個writer實例就不能再次使用了,要重新初始化一個,詳見我的另一篇文章
代碼挖出來以后在UIGestureRecognizerStateBegan
中添加如下代碼:[[NSFileManager defaultManager] removeItemAtURL:[self currentVideoURL] error:nil]; [self initMovieWriter]; _videoCamera.audioEncodingTarget = _movieWriter; [_movieWriter startRecording]; NSLog(@"Start recording");
在UIGestureRecognizerStateEnded
中添加如下代碼(記得添加頭文件引用#import <AssetsLibrary/AssetsLibrary.h>
):
_videoCamera.audioEncodingTarget = nil;
[_movieWriter finishRecording];
NSLog(@"Movie completed");
ALAssetsLibrary *library = [[ALAssetsLibrary alloc] init];
if ([library videoAtPathIsCompatibleWithSavedPhotosAlbum:[self currentVideoURL]]) {
[library writeVideoAtPathToSavedPhotosAlbum:[self currentVideoURL] completionBlock:^(NSURL *assetURL, NSError *error)
{
dispatch_async(dispatch_get_main_queue(), ^{
if (error) {
UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"Error" message:@"Video Saving Failed"
delegate:nil cancelButtonTitle:@"OK" otherButtonTitles:nil];
[alert show];
} else {
UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"Video Saved" message:@"Saved To Photo Album"
delegate:self cancelButtonTitle:@"OK" otherButtonTitles:nil];
[alert show];
}
});
}];
}
需要注意的是這個官方demo比較早了,現(xiàn)在AssetsLibrary已經(jīng)被棄用了,雖然我們這個demo現(xiàn)在還能用,但也請及時進行更換,使用`<Photos/Photos.h>`。日后我再找機會把這部分代碼更新一下。
至此我們這個demo可以任意錄像并保存到相冊了。這篇的代碼可能有漏貼的,如代碼有任何問題請及時留言指出。下一篇中我們將加入更加好玩的功能。