我正在尝试在 iPhone 5s 上以最高分辨率 (AVCaptureSessionPresetPhoto) 拍摄多张照片。我尝试使用以下代码:
dispatch_semaphore_t sync = dispatch_semaphore_create(0);
while( [self isBurstModeEnabled] == YES )
{
[stillImageOutput captureStillImageAsynchronouslyFromConnection:videoConnection completionHandler: ^(CMSampleBufferRef imageSampleBuffer, NSError *error)
{
if (imageSampleBuffer != NULL)
{
NSData *imageData = [AVCaptureStillImageOutput jpegStillImageNSDataRepresentation:imageSampleBuffer];
NSString *videoThumbPath = [NSString
stringWithFormat:@"%@/img%d.png",
burstFolderPath,
index];
[imageData writeToFile:videoThumbPath atomically:YES];
if( 0 == index )
{
[self NSLogPrint:[NSString stringWithFormat:@"Created photo at %@",videoThumbPath]];
}
}
dispatch_semaphore_signal(sync);
}];
dispatch_semaphore_wait(sync, DISPATCH_TIME_FOREVER);
}
使用此代码,我每秒可以拍摄大约 2 张照片,远不及 native 相机应用程序连拍模式的性能。我究竟做错了什么?我也尝试在没有信号量的情况下使用上面的代码,但在那种情况下我有奇怪的行为,一些照片丢失了(img0.png img1.png img3.png 会存在但 img2.png 会丢失)。使用第二种方法性能会更好,但仍无法与 native 应用程序性能相提并论(在我的测试中,相机应用程序每秒可拍摄约 8.4 张照片)。
最佳答案
captureStillImageAsynchronouslyFromConnection:completionHandler:
我相信,Apple 在其突发模式中使用的不是它。
相反,Apple * 以全分辨率(5s 支持)抓取视频帧。方法如下:
AVCaptureDevice 将其 activeFormat
设置为全传感器分辨率,然后您每秒从 AVCaptureVideoDataOutputSampleBufferDelegate
的 captureOutput:didOutputSampleBuffer:fromConnection 抓取并处理 10 帧:
,每次抓取帧时都会发出快门声。
对于不支持全传感器尺寸分辨率视频的设备和/或如果您想支持任何东西,您需要有后备(较低分辨率的图像或较慢的连拍模式)早于 iOS 7.x。
请注意,您不能多次并发使用 captureStillImageAsynchronouslyFromConnection:completionHandler:
而不会产生一些极其意外的结果。这就是为什么您应该从前一个的 completionHandler
调用每个迭代(本质上,这就是您的信号量正在做的事情)。此外,您可能希望从 PNG 切换为连拍照片的文件格式——它保存速度非常慢并且需要大量系统资源——堆叠 15 或 20 个 PNG 可能会给你带来严重的痛苦!
*它可能正在这样做,因为它当然可能使用私有(private) API 来实现相同的最终结果。
关于ios/iphone 照片连拍模式 api,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22972402/