0

I set the shutter speed, ISO and other camera parameters and capture an image using the code below. If I set the ISO to something like 119, it gets reported as 125 in the Exif info (it is always rounded to a standard value). How can I tell what the real ISO was? The maxISO gets reported as 734 but if I set it to 734 it is 800 in the Exif information. I had the same problem with the exposure time. If I set it to 800ms it shows up as 1s in the but the value calculated from the ShutterSpeedValue is correct.

- (void)setCameraSettings:(long)expTime1000thSec iso:(int)isoValue
{
    if ( currentCaptureDevice ) {

        [captureSession beginConfiguration];

        NSError *error = nil;
        if ([currentCaptureDevice lockForConfiguration:&error]) {

            if ([currentCaptureDevice isExposureModeSupported:AVCaptureExposureModeLocked]) {

                CMTime minTime, maxTime, exposureTime;

                if ( isoValue < minISO ) {
                    isoValue = minISO;
                } else if ( isoValue > maxISO ) {
                    isoValue = maxISO;
                }

                exposureTime = CMTimeMake(expTime1000thSec, EXP_TIME_UNIT); // in 1/EXP_TIME_UNIT of a second
                minTime = currentCaptureDevice.activeFormat.minExposureDuration;
                maxTime = currentCaptureDevice.activeFormat.maxExposureDuration;

                if ( CMTimeCompare(exposureTime, minTime) < 0 ) {
                    exposureTime = minTime;
                } else if ( CMTimeCompare(exposureTime, maxTime) > 0 ) {
                    exposureTime = maxTime;
                }

                NSLog(@"setting exp time to %lld/%d s (want %ld)   iso=%d", exposureTime.value, exposureTime.timescale, expTime1000thSec, isoValue);
                [currentCaptureDevice setExposureModeCustomWithDuration:exposureTime ISO:isoValue completionHandler:nil];
            }

            if (currentCaptureDevice.lowLightBoostSupported) {
                currentCaptureDevice.automaticallyEnablesLowLightBoostWhenAvailable = NO;
                NSLog(@"setting automaticallyEnablesLowLightBoostWhenAvailable = NO");
            }

            // lock the gains
            if ([currentCaptureDevice isWhiteBalanceModeSupported:AVCaptureWhiteBalanceModeLocked]) {
                currentCaptureDevice.whiteBalanceMode = AVCaptureWhiteBalanceModeLocked;
                NSLog(@"setting AVCaptureWhiteBalanceModeLocked");
            }

            // set the gains
            AVCaptureWhiteBalanceGains gains;
            gains.redGain = 1.0;
            gains.greenGain = 1.0;
            gains.blueGain = 1.0;

            AVCaptureWhiteBalanceGains normalizedGains = [self normalizedGains:gains];
            [currentCaptureDevice setWhiteBalanceModeLockedWithDeviceWhiteBalanceGains:normalizedGains completionHandler:nil];
            NSLog(@"setWhiteBalanceModeLockedWithDeviceWhiteBalanceGains g.red=%.2lf g.green=%.2lf g.blue=%.2lf",
                  normalizedGains.redGain, normalizedGains.greenGain, normalizedGains.blueGain);

            [currentCaptureDevice unlockForConfiguration];
        }
        [captureSession commitConfiguration];
    }
}



- (void)captureStillImage
{
    NSLog(@"about to request a capture from: %@", [self stillImageOutput]);

    if ( videoConnection ) {

        waitingForCapture = true;

        NSLog(@"requesting a capture from: %@", [self stillImageOutput]);
        [[self stillImageOutput] captureStillImageAsynchronouslyFromConnection:videoConnection
                                                         completionHandler:^(CMSampleBufferRef imageSampleBuffer, NSError *error) {

            if ( imageSampleBuffer ) {

                CFDictionaryRef exifAttachments = CMGetAttachment(imageSampleBuffer, kCGImagePropertyExifDictionary, NULL);
                if (exifAttachments) {
                    NSLog(@"attachements: %@", exifAttachments);
                } else {
                    NSLog(@"no attachments");
                }

                NSLog(@"name: %@", [currentCaptureDevice localizedName]);

                NSData *imageData = [AVCaptureStillImageOutput jpegStillImageNSDataRepresentation:imageSampleBuffer];
                UIImage *image = [[UIImage alloc] initWithData:imageData];
                [self setStillImage:image];


                NSDictionary *dict = (__bridge NSDictionary*)exifAttachments;
                NSString *value = [dict objectForKey:@"PixelXDimension"];
                [self setImageWidth:[NSNumber numberWithInt:[value intValue]]];

                value = [dict objectForKey:@"PixelYDimension"];
                [self setImageHeight:[NSNumber numberWithInt:[value intValue]]];

                value = [dict objectForKey:@"BrightnessValue"];
                [self setImageBrightnessValue:[NSNumber numberWithFloat:[value floatValue]]];

                value = [dict objectForKey:@"ShutterSpeedValue"];
                double val = [value doubleValue];
                val = 1.0 / pow(2.0, val);
                [self setImageExposureTime:[NSNumber numberWithDouble:val]];

                value = [dict objectForKey:@"ApertureValue"];
                [self setImageApertureValue:[NSNumber numberWithFloat:[value floatValue]]];

                NSArray *values = [dict objectForKey:@"ISOSpeedRatings"];
                [self setImageISOSpeedRatings:[NSNumber numberWithInt:[ [values objectAtIndex:0] intValue]]];


                NSLog(@"r/g/b gains = %.2lf/%.2lf/%.2lf",
                      currentCaptureDevice.deviceWhiteBalanceGains.redGain,
                      currentCaptureDevice.deviceWhiteBalanceGains.greenGain,
                      currentCaptureDevice.deviceWhiteBalanceGains.blueGain);


                [[NSNotificationCenter defaultCenter] postNotificationName:kImageCapturedSuccessfully object:nil];

            } else {
                NSLog(@"imageSampleBuffer = NULL");
            }

            waitingForCapture = false;

         }];
    } else {
        NSLog(@"can't capture from: videoConnection");
    }

}
rmaddy
  • 314,917
  • 42
  • 532
  • 579
user1390106
  • 23
  • 1
  • 8
  • it seems that the ISO reported in the Exif is not the one actually used. I kept the exposure time constant and recorded the same image at ISOs of 250 and 230. In the Exif hte ISO was reported to be 250 in both cases but the intensity changed by approximately a factor of 230/250. Does anyone how how to get teh ISO from the other parameters in the Exif? – user1390106 Jan 09 '15 at 03:46

2 Answers2

0

I answered your other question, same thing, you are not setting the CustomSettings mode:

[device lockForConfiguration:nil];

        if([device isExposureModeSupported:AVCaptureExposureModeCustom]){
            [device setExposureMode:AVCaptureExposureModeCustom];
            [device setExposureModeCustomWithDuration:exposureTime ISO:exposureISO completionHandler:^(CMTime syncTime) {}];
            [device setExposureTargetBias:exposureBIAS completionHandler:^(CMTime syncTime) {}];    
        }

Regards.

Eph Bee
  • 265
  • 1
  • 13
  • I downloaded the AVCamManualUsingtheManualCaptureAPI example and when I set the ISO to a non-standard value like 533 in the app with the "Exposure->Custom- – user1390106 Jan 22 '15 at 21:20
0

I added:

[device setExposureMode:AVCaptureExposureModeCustom];

and changed my completionHandler from nil to:

completionHandler:^(CMTime syncTime) {}

and I still see the same results. It seems that ISO can only be set to the "standard" values and not to any value between minISO and maxISO.

user1390106
  • 23
  • 1
  • 8