iOS 截取和分割音视频
在 iOS 开发中,截取或分割音视频是常见需求,适用于短视频剪辑、语音消息裁剪、媒体内容编辑等场景。使用 AVFoundation 框架可以高效实现这一功能。下面将详细介绍如何在 iOS 中截取或分割音视频,并提供完整的代码示例和使用方法。
✅ 核心思路
截取或分割音视频的核心步骤如下:
-
加载原始音视频文件(
AVURLAsset
) -
设置时间范围(
CMTimeRange
)指定要截取的起始时间与持续时间 -
创建导出会话(
AVAssetExportSession
) -
导出目标文件(支持
.mp4
、.m4a
等格式) - 处理异步导出完成回调
🎬 视频截取示例(Objective-C)
- (void)trimVideoFromURL:(NSURL *)inputURL startTime:(NSTimeInterval)startTime duration:(NSTimeInterval)duration completion:(void (^)(NSURL *outputURL, NSError *error))completion {
AVURLAsset *asset = [AVURLAsset URLAssetWithURL:inputURL options:nil];
// 1. 创建导出会话
AVAssetExportSession *exportSession = [[AVAssetExportSession alloc] initWithAsset:asset presetName:AVAssetExportPresetHighestQuality];
// 2. 设置输出路径和文件格式
NSString *outputPath = [NSTemporaryDirectory() stringByAppendingPathComponent:@"trimmedVideo.mp4"];
exportSession.outputURL = [NSURL fileURLWithPath:outputPath];
exportSession.outputFileType = AVFileTypeMPEG4;
// 3. 设置时间范围(start ~ start + duration)
CMTime startCMTime = CMTimeMakeWithSeconds(startTime, 600);
CMTime durationCMTime = CMTimeMakeWithSeconds(duration, 600);
CMTimeRange timeRange = CMTimeRangeMake(startCMTime, durationCMTime);
exportSession.timeRange = timeRange;
// 4. 异步导出
[exportSession exportAsynchronouslyWithCompletionHandler:^{
if (exportSession.status == AVAssetExportSessionStatusCompleted) {
NSLog(@"视频截取成功: %@", outputPath);
if (completion) completion([NSURL fileURLWithPath:outputPath], nil);
} else {
NSError *error = exportSession.error;
NSLog(@"视频截取失败: %@", error.localizedDescription);
if (completion) completion(nil, error);
}
}];
}
✅ 使用方法
NSURL *videoURL = [NSURL fileURLWithPath:[[NSBundle mainBundle] pathForResource:@"myVideo" ofType:@"mp4"]];
[self trimVideoFromURL:videoURL startTime:5.0 duration:10.0 completion:^(NSURL *outputURL, NSError *error) {
if (outputURL) {
NSLog(@"截取后的视频路径: %@", outputURL.path);
}
}];
🎵 音频截取示例(Objective-C)
- (void)trimAudioFromURL:(NSURL *)inputURL startTime:(NSTimeInterval)startTime duration:(NSTimeInterval)duration completion:(void (^)(NSURL *outputURL, NSError *error))completion {
AVURLAsset *asset = [AVURLAsset URLAssetWithURL:inputURL options:nil];
AVAssetExportSession *exportSession = [[AVAssetExportSession alloc] initWithAsset:asset presetName:AVAssetExportPresetAppleM4A];
NSString *outputPath = [NSTemporaryDirectory() stringByAppendingPathComponent:@"trimmedAudio.m4a"];
exportSession.outputURL = [NSURL fileURLWithPath:outputPath];
exportSession.outputFileType = AVFileTypeAppleM4A;
CMTime startCMTime = CMTimeMakeWithSeconds(startTime, 600);
CMTime durationCMTime = CMTimeMakeWithSeconds(duration, 600);
CMTimeRange timeRange = CMTimeRangeMake(startCMTime, durationCMTime);
exportSession.timeRange = timeRange;
[exportSession exportAsynchronouslyWithCompletionHandler:^{
if (exportSession.status == AVAssetExportSessionStatusCompleted) {
NSLog(@"音频截取成功: %@", outputPath);
if (completion) completion([NSURL fileURLWithPath:outputPath], nil);
} else {
NSError *error = exportSession.error;
NSLog(@"音频截取失败: %@", error.localizedDescription);
if (completion) completion(nil, error);
}
}];
}
✅ 使用方法
NSURL *audioURL = [NSURL fileURLWithPath:[[NSBundle mainBundle] pathForResource:@"myAudio" ofType:@"mp3"]];
[self trimAudioFromURL:audioURL startTime:3.0 duration:5.0 completion:^(NSURL *outputURL, NSError *error) {
if (outputURL) {
NSLog(@"截取后的音频路径: %@", outputURL.path);
}
}];
📌 注意事项
项目 | 说明 |
---|---|
时间单位 | 使用 CMTimeMakeWithSeconds 将秒数转换为 CMTime
|
输出路径 | 使用 NSTemporaryDirectory() 可避免存储问题 |
输出格式 | 视频推荐 .mp4 ,音频推荐 .m4a 或 .caf
|
导出性能 | 使用 AVAssetExportPresetLowQuality 可提升处理速度 |
错误处理 | 检查 exportSession.status 和 exportSession.error
|
🚀 扩展建议
-
多片段拼接:可结合
AVMutableComposition
实现多段裁剪后的内容拼接。 - 后台导出:大文件建议在后台线程执行,避免阻塞主线程。
- 第三方库:如需更复杂剪辑功能,可使用 FFmpeg-iOS 或 GPUImage。
✅ 总结
通过 AVAssetExportSession
的 timeRange
属性,你可以轻松地从音视频文件中截取任意时间段的内容。这个方法既适用于音频也适用于视频,具有良好的兼容性和性能表现,是 iOS 音视频处理中的基础技能之一。