I would like to, depending on the device and the settings in my application, transcode a video to a specific video format. For an example, if the user has an iPhone 4S and chooses medium settings in my application I would like to convert the video to 540p before I start processing. If he chooses high then I would like to transcode to 720p.
I could read the video frame by frame, resize and save to disc but this does not seem very effective. What would be the easiest and fastest way to transcode a video that I can feed to my video processing libraries?
I have tried using the videoQuality settings on my UIImagePickerController but seems like it is not working as even when I set it to UIImagePickerControllerQualityTypeIFrame960x540 my video comes out as 720p (640x480 is working but I need to be more granular).
You might want to look at AVAssetExportSession, which makes it reasonably simple to re-encode videos. I think it's also hardware-supported when possible like the rest of AVFoundation:
https://developer.apple.com/library/ios/#DOCUMENTATION/AudioVideo/Conceptual/AVFoundationPG/Articles/01_UsingAssets.html
Note that it will never make the video larger than it already is, so you aren't guaranteed to get the output size you request. The following code might be a start for what you want, assuming you have an instance of ALAsset:
- (void)transcodeLibraryVideo:(ALAsset *)libraryAsset
toURL:(NSURL *)fileURL
withQuality:(NSString *quality) {
// get a video asset for the original video file
AVAsset *asset = [AVAsset assetWithURL:
[NSURL URLWithString:
[NSString stringWithFormat:@"%@",
[[libraryAsset defaultRepresentation] url]]]];
// see if it's possible to export at the requested quality
NSArray *compatiblePresets = [AVAssetExportSession
exportPresetsCompatibleWithAsset:asset];
if ([compatiblePresets containsObject:quality]) {
// set up the export
AVAssetExportSession *exportSession = [[AVAssetExportSession alloc]
initWithAsset:asset presetName:quality];
exportSession.outputURL = fileURL;
exportSession.outputFileType = AVFileTypeQuickTimeMovie;
// run the export
[exportSession exportAsynchronouslyWithCompletionHandler:^{
switch ([exportSession status]) {
case AVAssetExportSessionStatusFailed:
//TODO: warn of failure
break;
case AVAssetExportSessionStatusCancelled:
//TODO: warn of cancellation
break;
default:
//TODO: do whatever is next
break;
}
[exportSession release];
}];
}
else {
//TODO: warn that the requested quality is not available
}
}
You would want to pass a quality of AVAssetExportPreset960x540 for 540p and AVAssetExportPreset1280x720 for 720p, for example.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With