I am trying to record a timelapse video via iphone. I have already got it working for slow motion (by capturing maximum frames possible), with 120 fps.
Now I am trying to reverse the logic to capture least frames possible, to achieve timelapse functionality.
Code flow is like this:
Query all the supported frame range from the available device formats of the AVCaptureDevice.
Check if the frame rate is below or equal to the desired 20 fps and dimensions are equal to or greater than 1920*1080.
All works fine except, when I press record, I get "AVCaptureMovieFileOutput - no active/enabled connections"
exception. I am only using one of the provided frame rate and range, why am I getting this exception?
All works well for 30 fps.
#define kTimelapseRequiredFPS = 20
#define kMinRequiredDimensions (1920*1080)
- (void)configureCameraForSlowMoRecording:(AVCaptureDevice *)currentCaptureDevice
{
[_captureSession beginConfiguration];
AVCaptureDeviceFormat *bestFormat = nil;
AVFrameRateRange *bestFrameRateRange = nil;
for ( AVCaptureDeviceFormat *format in [currentCaptureDevice formats] )
{
//NSLog(@"Format: %@", format);
CMFormatDescriptionRef videoInfo = [format formatDescription];
double videoWidth = CMVideoFormatDescriptionGetDimensions(videoInfo).width;
double videoHeight = CMVideoFormatDescriptionGetDimensions(videoInfo).height;
double dimensions = videoWidth * videoHeight;
for ( AVFrameRateRange *range in format.videoSupportedFrameRateRanges )
{
//NSLog(@"Range: %@", range);
if ((range.maxFrameRate <= kTimelapseRequiredFPS) && (dimensions >= kMinRequiredDimensions))
{
bestFormat = format;
bestFrameRateRange = range;
}
}
}
if ( bestFormat )
{
NSLog(@"Final format: %@, Final range %@", bestFormat, bestFrameRateRange);
if ( [currentCaptureDevice lockForConfiguration:NULL] == YES )
{
currentCaptureDevice.activeFormat = bestFormat;
currentCaptureDevice.activeVideoMinFrameDuration = bestFrameRateRange.minFrameDuration;
currentCaptureDevice.activeVideoMaxFrameDuration = bestFrameRateRange.minFrameDuration;
[currentCaptureDevice unlockForConfiguration];
}
}
[_captureSession commitConfiguration];
}
Here is the log of frame rate and range with 20 fps:
Format: <AVCaptureDeviceFormat: 0x1765f7a0 'vide'/'420v' 2592x1936, { 1- 20 fps}, fov:56.700, max zoom:153.00 (upscales @1.26), AF System:1, ISO:46.0-736.0, SS:0.000018-1.000000>
Range: <AVFrameRateRange: 0x176556d0 1 - 20>
Format: <AVCaptureDeviceFormat: 0x1765f750 'vide'/'420f' 2592x1936, { 1- 20 fps}, fov:56.700, max zoom:153.00 (upscales @1.26), AF System:1, ISO:46.0-736.0, SS:0.000018-1.000000>
Range: <AVFrameRateRange: 0x1750db10 1 - 20>
Format: <AVCaptureDeviceFormat: 0x1765f740 'vide'/'420v' 3264x2448, { 1- 20 fps}, fov:56.700, max zoom:153.00 (upscales @1.00), AF System:1, ISO:46.0-736.0, SS:0.000018-1.000000>
Range: <AVFrameRateRange: 0x1750dc80 1 - 20>
Format: <AVCaptureDeviceFormat: 0x1765f6f0 'vide'/'420f' 3264x2448, { 1- 20 fps}, fov:56.700, max zoom:153.00 (upscales @1.00), AF System:1, ISO:46.0-736.0, SS:0.000018-1.000000>
Range: <AVFrameRateRange: 0x1751a260 1 - 20>