はじめに
Exif: Exchangeable image file format とは写真などの画像データのフォーマット情報に関する規約です。
Exif へレンズの情報を載せるようになったのは Exif 2.3 からです。Exif 2.3 では LensModel タグへレンズ名称を記載することとなっています。
しかし、それ以前から各ベンダーは固有領域の Makernote へ独自フォーマットでレンズ名称を記載していました。
LensModel タグは必須項目ではなく、オプショナル項目であることも相まって、レンズ名称を取得するのに苦労した・・・
というおはなしです。
準備
Exif 解析用のライブラリとしては Exifr がメジャーですが、mini_exiftool を使うこととしました。(固有領域情報を取得しやすいからだったか)
mini_exiftool は exiftool のラッパーですので、exiftool をインストール
brew install exiftool
そして、gem でインストール
gem install mini_exiftool
レンズ名称の取得
前提
-
- Exif バージョン 2.3 以降 LensModel タグへ記載されている可能性がある
-
- Exif バージョンに依存せず、固有領域の Makernote へ独自フォーマットで記載されている可能性がある
-
- レンズ名称の記載がない可能性がある
Exif データをサンプリング
上記を踏まえ、100件ほどの写真(それぞれカメラ・レンズが異なる)の Exif をサンプリングした結果、レンズ名称のタグは以下に書かれていることが多いようです。
- LensModel
- Lens
- LensID
サンプルを検証したデータの一部抜粋
余分な情報も入ってますが、スルーしてください
"ファイル名,Exifバージョン,モデル名,レンズ名,焦点距離,35mm換算レンズ焦点距離,Fナンバー,LensModel,Lens,LensID"
"1.jpg,0221,NIKON D90,28-300mm f/3.5-6.3,50.0 mm,-,4.2,-,28-300mm f/3.5-6.3,Tamron AF 28-300mm f/3.5-6.3 XR LD Aspherical (IF) (185D)"
"10.jpg,230,ILCE-7,FE 55mm F1.8 ZA,55.0 mm,-,4.0,FE 55mm F1.8 ZA,FE 55mm F1.8 ZA,-"
"2.jpg,220,DSC-N1,-,7.9 mm,-,2.8,-,-,-"
"3.jpg,0221,Canon PowerShot SX20 IS,5.0 - 100.0 mm,42.4 mm,-,5.0,-,5.0 - 100.0 mm,Unknown 5-100mm"
"4.jpg,0221,E-420,Olympus Zuiko Digital 25mm F2.8,25.0 mm,-,2.8,-,Olympus Zuiko Digital 25mm F2.8,-"
"5.jpg,230,X-E1,XF60mmF2.4 R Macro,60.0 mm,-,2.8,XF60mmF2.4 R Macro,XF60mmF2.4 R Macro,-"
"6.jpg,230,X-E1,XF18-55mmF2.8-4 R LM OIS,27.7 mm,-,11.0,-,XF18-55mmF2.8-4 R LM OIS,-"
"7.jpg,230,SLT-A57,DT 55-200mm F4-5.6 SAM,120.0 mm,-,22.0,DT 55-200mm F4-5.6 SAM,DT 55-200mm F4-5.6 SAM,-"
"8.jpg,230,ILCE-7,FE 28-70mm F3.5-5.6 OSS,47.0 mm,-,7.1,FE 28-70mm F3.5-5.6 OSS,FE 28-70mm F3.5-5.6 OSS,-"
"9.jpg,230,DSLR-A850,35mm F2,35.0 mm,-,2.2,35mm F2,35mm F2,Minolta AF 35mm F2 [New]"
"100.jpg,230,SLT-A55V,24-105mm F3.5-4.5,22.0 mm,-,7.1,24-105mm F3.5-4.5,24-105mm F3.5-4.5,Sigma 18-200mm F3.5-6.3 DC"
"91.jpg,230,DSLR-A580,DT 18-55mm F3.5-5.6 SAM,18.0 mm,-,3.5,DT 18-55mm F3.5-5.6 SAM,DT 18-55mm F3.5-5.6 SAM,Sony DT 18-55mm F3.5-5.6 SAM [II] (SAL1855)"
"92.jpg,230,DSLR-A580,50mm F1.7,50.0 mm,-,1.7,50mm F1.7,50mm F1.7,-"
"93.jpg,230,DSLR-A580,MACRO 100mm F2.8,100.0 mm,-,18.0,MACRO 100mm F2.8,MACRO 100mm F2.8,Minolta AF 100mm F2.8 Macro [New]"
"94.jpg,230,DSLR-A580,DT 18-55mm F3.5-5.6 SAM,55.0 mm,-,5.6,DT 18-55mm F3.5-5.6 SAM,DT 18-55mm F3.5-5.6 SAM,-"
"95.jpg,0221,NIKON D1H,24.0-70.0 mm f/2.8,24.0 mm,-,19.0,-,24.0-70.0 mm f/2.8,-"
"96.jpg,220,SIGMA SD14,-,500.0 mm,-,9.0,-,-,-"
"97.jpg,220,SIGMA SD14,-,50.0 mm,-,2.8,-,-,-"
レンズ名称取得ロジック
サンプルデータを解析した結果、以下の割り切りロジックとしました。
- Exif バージョンは意識しない
-
LensID
,LensModel
,Lens
の順にタグをチェックしていき、値が入っているものをレンズ名とする - レンズ名称が
unknown
であった場合、LensModel
,Lens
を再チェックする
レンズ名称とするタグの順番に関しては、個人的な所感で LensID
が一番詳細で正確な値が設定されていると判断したためです。
一部、特殊なケースとして、LendID
に unknown
と書かれ、LensModel
に正しい名称を記載しているデータがあったので対応を入れておくこととする。
ソースにすると以下のような形です。
exif = MiniExiftool.new path
lens = exif['LensID'] || exif['LensModel'] || exif['Lens']
lens = exif['LensModel'] || exif['Lens'] if lens =~ /unknown/i
最後に
完璧にレンズ名称を取得するのではなく、8割ほどの情報をカバーできればよいという前提で考えています。
独自調査による解析ロジックにてレンズ名称を取得していますので、ご利用は自己責任でお願いします。