0

2 つの画像解析機能を実行する画像処理アプリを作成しています。1 つは画像の RGB データを読み取る方法で、もう 1 つは EXIF データを読み取る方法です。フロントカメラで写真を撮り、ドキュメントフォルダーに保存しています。RGB 値を取得するには、次の方法で画像を読み込みます。

NSString *jpgPath = [NSHomeDirectory() stringByAppendingPathComponent:@"Documents/Test.jpg"];
UIImage *image = [UIImage imageWithContentsOfFile:jpgPath];
CFDataRef pixelData = CGDataProviderCopyData(CGImageGetDataProvider(image.CGImage));
const UInt8* data = CFDataGetBytePtr(pixelData);

これは期待どおりに機能し、ピクセル データを取得できます。私の問題は、EXIF データの収集です。RGB と同じ方法で画像の読み取りを実装していますが、すべての EXIF データが NULL として返されます。

NSString *EXIFPath = [NSHomeDirectory() stringByAppendingPathComponent:@"Documents/Test.jpg"];
NSURL *url = [NSURL fileURLWithPath:EXIFPath];

CGImageSourceRef sourceRef = CGImageSourceCreateWithURL((__bridge CFURLRef)url, NULL);

NSDictionary *immutableMetadata = (__bridge NSDictionary *) CGImageSourceCopyPropertiesAtIndex(sourceRef,0,NULL);
NSDictionary *exifDic = [immutableMetadata objectForKey:(NSString *)kCGImagePropertyExifDictionary];

NSNumber *ExifApertureValue  = [exifDic objectForKey:(NSString*)kCGImagePropertyExifApertureValue];
NSNumber *ExifShutterSpeed  = [exifDic objectForKey:(NSString*)kCGImagePropertyExifShutterSpeedValue];

NSLog(@"ExifApertureValue : %@ \n",ExifApertureValue);
NSLog(@"ExifShutterSpeed : %@ \n",ExifShutterSpeed);

次のように、コードの最初の行をアプリでプリロードされた画像を読み取るように変更すると:

NSString *aPath = [[NSBundle mainBundle] pathForResource:@"IMG_1406" ofType:@"JPG"];

できます。問題は、画像をプリロードできないことです。カメラからライブで撮影する必要があります。どんな提案でも大歓迎です。ありがとうございました。

4

1 に答える 1

1

そのファイルはどのようにしTest.jpgて Documents ディレクトリに書き込まれるのでしょうか? と書かれていUIImageJPEGRepresentationますか?その場合、EXIF データは失われます。メタデータが必要な画像の JPEG ソースを必ず保存してください。

何が起こっているかに関係なく、完全なオブジェクトimmutableMetadataexifDicオブジェクトを取得したらすぐにログに記録すると役立ちます。

NSDictionary *immutableMetadata = (__bridge NSDictionary *) CGImageSourceCopyPropertiesAtIndex(sourceRef,0,NULL);
NSLog(@"immutableMetadata = %@", immutableMetadata);
NSDictionary *exifDic = [immutableMetadata objectForKey:(NSString *)kCGImagePropertyExifDictionary];
NSLog(@"exifDic");

ログにこれら 3 つの値しか含まれていない場合exifDicは、EXIF ヘッダーの保存を考慮しない関数によって保存されています。

exifDic = {
    ColorSpace = 1;
    PixelXDimension = 1200;
    PixelYDimension = 1600;
}

動作する他の2つのことですが、より良い可能性があります。

(1) Documents ディレクトリが NSHomeDirectory() のサブディレクトリになるという保証はありません。このドキュメントの場所を取得する信頼できる方法は次のとおりです。

NSArray *documentDirectories = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentDirectory = [documentDirectories objectAtIndex:0];
NSString *imagePath = [documentDirectory stringByAppendingPathComponent:@"Test.jpg"];

(2) 現在、ストレージからイメージ バイトを 2 回読み込んでいます。1 回目はピクセルを取得するため、もう 1 回はメタデータを取得するためです。それらをオブジェクトにロードするNSDataと、ファイルを一度取得するだけで済みます。そのNSDataオブジェクトを保持しておけば、詳細を失うことなく後で画像を保存できます。(これはファイル サイズと同じメモリを消費するため、必要な場合にのみ保持してください。)

NSData *imageData = [NSData dataWithContentsOfFile:imagePath];
UIImage *image = [UIImage imageWithData:imageData];
// Do things involving image pixels...

CGImageSourceRef sourceRef = CGImageSourceCreateWithData((__bridge CFDataRef) imageData, NULL);
// Do things involving image metadata...
于 2012-04-11T09:28:01.443 に答える