18

我正在使用 AVAssetWriter,它在 iOS6 上完美运行。

问题是,当我调用 时finishWritingWithCompletionHandler,iOS7 GM 上没有调用完成处理程序。

我打电话了markAsFinished,甚至endSessionAtSourceTime在我打电话给finishWritingWithCompletionHandler之前。

它在 iOS6 上运行良好。

更重要的是,在 iOS7 上,它有时可以工作,然后又不能工作。

我不知道为什么,但如果我使用警报视图调用该方法,它就会起作用。所以我尝试了performSelectorOnMainThreadand inBackground,但它没有帮助。

有任何想法吗?

4

5 回答 5

38

显然你现在需要保留assetWriter。

您可以尝试使用强大的属性保留它并查看您的完成处理程序是否被调用。(确保在完成处理程序中将该属性设为 nil。)

于 2013-09-17T19:15:44.797 回答
8

雷修,你是对的。我们需要保留assetWriter。最简单的方法是在 finishWritingWithCompletionHandler 块中使用它:

        NSError *error = nil;

        AVAssetWriter *videoWriter = [[AVAssetWriter alloc] initWithURL:[NSURL fileURLWithPath:path]
                                                                   fileType:AVFileType3GPP
                                                                      error:&error];
        //startWriting, session etc.  

        [videoWriter finishWritingWithCompletionHandler:^{
                NSLog(@"%@",videoWriter);
                NSLog(@"Write Ended");
            }];
于 2013-11-07T09:17:34.303 回答
3

保留资产编写者非常重要,但我也遇到了一个非常奇怪的间歇性故障,即使我的资产编写者都被保留(并且从未重用)。问题也不是文件名冲突或缺少目录,因为我的文件名都基于 CACurrentMediaTime() 并且不更改目录。

似乎如果您不endSessionAtSourceTime:每次都为资产编写者设置,那么完成处理程序的完成处理程序finishWritingWithCompletionHandler:将永远不会被调用的可能性非常罕见(但可重现)。如果您等待几秒钟并检查资产写入器的状态,它将处于 AVAssetWriterStatusFailure 状态,并且错误将是非描述性的“发生未知错误(-12763)”。此外,更改资产编写器的文件格式不会对此问题产生影响。最后,这个问题可能只在您需要快速地一遍又一遍地录制电影时才会出现(因为失败的机会可能是 1/15 - 1/20)。

因此,只需确保存储您传递给资产编写器的最后一个样本的演示时间戳,并endSessionAtSourceTime:在您即将调用之前使用该样本时间进行调用finishWritingWithCompletionHandler:

于 2014-05-30T23:34:15.573 回答
3

这也发生在 ARC 上。

最简单的解决方案是定义 AVAssetWriter 的属性(和我假设的 AVAssetReader)

@property(nonatomic,strong) AVAssetWriter *assetWriter;
@property(nonatomic,strong) AVAssetReader *assetReader;

接着

self.assetWriter = [AVAssetWriter assetWriterWithURL:destURL
                                                       fileType:AVFileTypeWAVE
                                                          error:&assetError];

并在完成块中

              [assetWriterInput markAsFinished];
             [assetWriter finishWritingWithCompletionHandler:^{
                 [assetReader cancelReading];
                 completionBlock(self);

             }];
于 2014-10-08T16:09:21.403 回答
1

如果目标目录不存在,也会发生这种情况。在这种情况下,写入工作正常,但没有创建文件,也没有调用块。

于 2014-03-10T08:12:03.243 回答