不显示UIVideoEditorController如何剪辑视频?

12

我目前正在开发一个与视频相关的应用程序。 在我的应用中,用户可以裁剪视频,我有一个自定义控件来选择开始时间和结束时间。我需要通过这两个值来裁剪视频。我尝试使用 UIVideoEditorController 如下。

    UIVideoEditorController* videoEditor = [[[UIVideoEditorController alloc] init] autorelease];
    videoEditor.delegate = self;
    NSString* videoPath = [[NSBundle mainBundle] pathForResource:@"test" ofType:@"MOV"];
    if ( [UIVideoEditorController canEditVideoAtPath:videoPath] )
    {
      videoEditor.videoPath = videoPath;
      [self presentModalViewController:videoEditor animated:YES];
    }
    else
    {
      NSLog( @"can't edit video at %@", videoPath );
    }

但问题在于上述代码会显示苹果的视频编辑控件,用户可以在该视图上执行一些操作。我不想显示这个视图,因为我已经在MPMoviePlayer上显示了视频,并在自定义控件上接收了用户输入(开始时间结束时间)以剪辑视频。

如何在不显示UIVideoEditorController的情况下剪辑视频?


1
请提供您裁剪视频的代码,让用户可以选择开始和结束时间。 - Mounika Vangala
2个回答

17

最终我找到了解决方案。

我们可以使用 AVAssetExportSession 对视频进行剪辑而不显示 UIVideoEditorController

我的代码如下:

- (void)splitVideo:(NSString *)outputURL
{

    @try
    {
        NSString *videoBundleURL = [[NSBundle mainBundle] pathForResource:@"Video_Album" ofType:@"mp4"];

        AVAsset *asset = [[AVURLAsset alloc] initWithURL:[NSURL fileURLWithPath:videoBundleURL] options:nil];

        NSArray *compatiblePresets = [AVAssetExportSession exportPresetsCompatibleWithAsset:asset];

        if ([compatiblePresets containsObject:AVAssetExportPresetLowQuality])
        {

            [self trimVideo:outputURL assetObject:asset];

        }
        videoBundleURL = nil;

        [asset release];
        asset = nil;

        compatiblePresets = nil;
    }
    @catch (NSException * e)
    {
        NSLog(@"Exception Name:%@ Reason:%@",[e name],[e reason]);
    }
}

该方法用于裁剪视频

- (void)trimVideo:(NSString *)outputURL assetObject:(AVAsset *)asset
  {

    @try
    {

        AVAssetExportSession *exportSession = [[AVAssetExportSession alloc]initWithAsset:asset presetName:AVAssetExportPresetLowQuality];

        exportSession.outputURL = [NSURL fileURLWithPath:outputURL];

        exportSession.outputFileType = AVFileTypeQuickTimeMovie;

        CMTime start = CMTimeMakeWithSeconds(splitedDetails.startTime, 1);

        CMTime duration = CMTimeMakeWithSeconds((splitedDetails.stopTime - splitedDetails.startTime), 1);

        CMTimeRange range = CMTimeRangeMake(start, duration);

        exportSession.timeRange = range;

        exportSession.outputFileType = AVFileTypeQuickTimeMovie;

        [self checkExportSessionStatus:exportSession];

        [exportSession release];
        exportSession = nil;

    }
    @catch (NSException * e)
    {
        NSLog(@"Exception Name:%@ Reason:%@",[e name],[e reason]);
    }
}

这个方法检查裁剪的状态:

- (void)checkExportSessionStatus:(AVAssetExportSession *)exportSession
  {

    [exportSession exportAsynchronouslyWithCompletionHandler:^(void)
    {

        switch ([exportSession status])
            {

            case AVAssetExportSessionStatusCompleted:

                NSLog(@"Export Completed");
                break;

            case AVAssetExportSessionStatusFailed:

                NSLog(@"Error in exporting");
                break;

            default:
                break;

        }
    }];
}
我从导出按钮的动作方法调用了splitVideo方法,并将输出URL作为参数传递。

1
@Khoool:提供了outputUrl用于写入已裁剪的视频,它是文档目录中的文件路径。 - Midhun MP
我正在使用相同的代码,但是收到错误:导出错误。NSString *path=[NSSearchPathForDirectoriesInDomains(NSDocumentationDirectory, NSUserDomainMask, YES) objectAtIndex:0]; path=[path stringByAppendingPathComponent:@"new.mov"]; NSLog(@"保存视频的路径为%@",path); [self splitVideo:path]; - Prince Kumar Sharma
你在传递开始和结束时间吗?我认为这将是剪辑视频的起始或结束时间。对吧?除了导出视频之外,一切都正常运作。 - Prince Kumar Sharma
@Khoool:是时候分割视频了,视频开始和结束时间。 - Midhun MP
我能否使用服务器上的视频相同代码?我只有视频的URL。请指导我。 - Shehbaz Khan
嗨,导出时出现错误:4,你能帮忙解决一下吗? - iPhone 7

2
我们可以导入AVFoundation/AVFoundation.h。
-(BOOL)trimVideofile
{

    float videoStartTime;//define start time of video
    float videoEndTime;//define end time of video
    NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
    [dateFormatter setDateFormat:@"yyyy-MM-dd_HH-mm-ss"];
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSLibraryDirectory, NSUserDomainMask, YES);
    NSString *libraryCachesDirectory = [paths objectAtIndex:0];
    libraryCachesDirectory = [libraryCachesDirectory stringByAppendingPathComponent:@"Caches"];
    NSString *OutputFilePath = [libraryCachesDirectory stringByAppendingFormat:@"/output_%@.mov", [dateFormatter stringFromDate:[NSDate date]]];
    NSURL *videoFileOutput = [NSURL fileURLWithPath:OutputFilePath];
    NSURL *videoFileInput;//<Path of orignal Video file>

    if (!videoFileInput || !videoFileOutput)
    {
        return NO;
    }

    [[NSFileManager defaultManager] removeItemAtURL:videoFileOutput error:NULL];
    AVAsset *asset = [AVAsset assetWithURL:videoFileInput];

    AVAssetExportSession *exportSession = [AVAssetExportSession exportSessionWithAsset:asset
                                                                            presetName:AVAssetExportPresetLowQuality];
    if (exportSession == nil)
    {
        return NO;
    }
    CMTime startTime = CMTimeMake((int)(floor(videoStartTime * 100)), 100);
    CMTime stopTime = CMTimeMake((int)(ceil(videoEndTime * 100)), 100);
    CMTimeRange exportTimeRange = CMTimeRangeFromTimeToTime(startTime, stopTime);

    exportSession.outputURL = videoFileOutput;
    exportSession.timeRange = exportTimeRange;
    exportSession.outputFileType = AVFileTypeQuickTimeMovie;

    [exportSession exportAsynchronouslyWithCompletionHandler:^
     {
         if (AVAssetExportSessionStatusCompleted == exportSession.status)
         {
            NSLog(@"Export OK");
         }
         else if (AVAssetExportSessionStatusFailed == exportSession.status)
         {
             NSLog(@"Export failed: %@", [[exportSession error] localizedDescription]);
         }
     }];
    return YES;
}

这个答案与上面的相同,复制答案有什么优点? - Midhun MP
这不是重复的答案。在这种情况下,我们使用另一种不同的解决方案。 - Vaibhav Sharma
在上面的答案中,也使用了 AVAssetExportSession。在这里也是同样的事情,那么有什么区别吗? - Midhun MP
2
所有函数都合并在一个带有“Cache”的方法中。将输出URL组合在“AVAssetExportSession”中。 这对您可能没有帮助,但对于其他新程序员来说很有用。 - Vaibhav Sharma

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接