从 AVFoundation 保存录制的视频
Posted
技术标签:
【中文标题】从 AVFoundation 保存录制的视频【英文标题】:Save recorded video from AVFoundation 【发布时间】:2014-08-04 11:29:15 【问题描述】:我无法从 AVFoundation 保存录像机视频...在 didfinishcapture 中我检查文件是否存在于临时文件夹中,代码总是返回 NO。
此外,当我停止录制时会打印此警告: "无法保存到已保存的相册:Error Domain=NSOSStatusErrorDomain Code=2 "无法播放此电影。" UserInfo=0x1c5696c0 NSLocalizedDescription=无法播放此电影。"
#define OP_PATH [NSTemporaryDirectory() stringByAppendingPathComponent:[@"movie" stringByAppendingPathExtension:@"mov"]]
- (IBAction) startSession:(id)sender
if(! self.captureSession)
//Session
self.captureSession = [[AVCaptureSession alloc] init];
//self.captureSession.sessionPreset = AVCaptureSessionPresetMedium;
//Layer of own view
CALayer *viewLayer = self.captureView.layer;
//AVCaptureVideoPreviewLayer
AVCaptureVideoPreviewLayer *avCaptureLayer = [[AVCaptureVideoPreviewLayer alloc] initWithSession:self.captureSession];
avCaptureLayer.frame = self.captureView.bounds;
[self.captureView.layer addSublayer:avCaptureLayer];
//AVCaptureDevice
AVCaptureDevice *device = [AVCaptureDevice defaultDeviceWithMediaType:AVMediaTypeVideo];
NSError *err = nil;
//Output - Image
self.stillImgOutput = [[AVCaptureStillImageOutput alloc] init];
[self.stillImgOutput setOutputSettings:[NSDictionary dictionaryWithObjectsAndKeys:
AVVideoCodecJPEG, AVVideoCodecKey,
nil]];
[self.captureSession addOutput:self.stillImgOutput];
//Output - Video
self.movieOutput = [[AVCaptureMovieFileOutput alloc] init];
// NSString* key = (NSString*)kCVPixelBufferBytesPerRowAlignmentKey;
//
// NSNumber* value = [NSNumber numberWithUnsignedInt:kCVPixelFormatType_32BGRA];
//
// NSDictionary* videoSettings = [NSDictionary dictionaryWithObject:value forKey:key];
if([self.captureSession canAddOutput:self.movieOutput])
NSLog(@"Movie out put added");
[self.captureSession addOutput:self.movieOutput];
else
NSLog(@"Cannot add movie out put");
//Input
AVCaptureDeviceInput *input = [AVCaptureDeviceInput deviceInputWithDevice:device error:&err];
if(! input)
NSLog(@"Error no camera");
return;
if([self.captureSession canAddInput:input])
[self.captureSession addInput:input];
else
NSLog(@"Cannot add input. Check Output Settings");
if(! [self.captureSession isRunning])
[self.captureSession startRunning];
else
NSLog(@"Session already running");
- (void)captureOutput:(AVCaptureFileOutput *)captureOutput didFinishRecordingToOutputFileAtURL:(NSURL *)outputFileURL fromConnections:(NSArray *)connections error:(NSError *)error
NSLog(@"Did stop recording to - %@ \n Any error ? - %@", outputFileURL, [error description]);
if([[NSFileManager defaultManager] fileExistsAtPath:[outputFileURL absoluteString]])
NSLog(@"YES file exists");
else
NSLog(@"NO File does not exist");
if(UIVideoAtPathIsCompatibleWithSavedPhotosAlbum([outputFileURL absoluteString]))
NSLog(@"YES file is compatible to be saved in Album");
UISaveVideoAtPathToSavedPhotosAlbum([outputFileURL absoluteString], self, @selector(video:didFinishSavingWithError:contextInfo:), nil);
else
NSLog(@"NO File is not compatible");
- (void)video:(NSString *)videoPath didFinishSavingWithError:(NSError *)error contextInfo:(void *)contextInfo
if(! error)
NSLog(@"Video Saved to Album");
else
NSLog(@"Video not saved to Album - %@", [error description]);
NSError *er;
[[NSFileManager defaultManager] removeItemAtPath:OP_PATH error:&er];
if(! er)
NSLog(@"Temporary file deleted");
else
NSLog(@"Temporary file not deleted - %@", [er description]);
【问题讨论】:
但它仍然不会影响保存代码? 【参考方案1】:您缺少以下代码。见下文
//Use timestamp to get new movie name everytime you capture
NSString *timeStamp = [NSString stringWithFormat:@"%0.0f",[[NSDate date] timeIntervalSince1970] * 1000];
NSString *movieOutputUrl =[NSTemporaryDirectory() stringByAppendingPathComponent:[NSString stringWithFormat:@"%@.mov",timeStamp]];
NSURL *url = [NSURL URLWithString:movieOutputUrl];
[self.movieOutput startRecordingToOutputFileURL:url recordingDelegate:self];
希望对你有帮助。
干杯。
【讨论】:
naaaa。还是一样的错误!它让我发疯!【参考方案2】:- (void)captureOutput:(AVCaptureFileOutput *)captureOutputdidFinishRecordingToOutputFileAtURL:(NSURL *)outputFileURL fromConnections:(NSArray *)connections error:(NSError *)error
if (error)
NSLog(@"%@", error);
UIBackgroundTaskIdentifier backgroundRecordingID = [self backgroundRecordingID];
[self setBackgroundRecordingID:UIBackgroundTaskInvalid];
[[[ALAssetsLibrary alloc] init] writeVideoAtPathToSavedPhotosAlbum:outputFileURL completionBlock:^(NSURL *assetURL, NSError *error)
if (error)
NSLog(@"%@", error);
[[NSFileManager defaultManager] removeItemAtURL:outputFileURL error:nil];
if (backgroundRecordingID != UIBackgroundTaskInvalid)
[[UIApplication sharedApplication] endBackgroundTask:backgroundRecordingID];
];
希望能提供帮助。
【讨论】:
以上是关于从 AVFoundation 保存录制的视频的主要内容,如果未能解决你的问题,请参考以下文章
Swift IOS 使用 AVFoundation 录制视频和音频