Интерпретация информации GPS данных exif с фотографии в python

Я пишу небольшую программу для получения информации GPS о фотографии iphone jpg.

Библиотека, которую я использую, - это PIL в python. Теперь я могу получить GPSInfo, что-то вроде:

{1: 'N', 
 2: ((1, 1), (20, 1), (5365, 100)), 
 3: 'E', 
 4: ((103, 1), (41, 1), (1052, 100)), 
 5: 0, 
 6: (43, 1), 
 7: ((15, 1), (32, 1), (7, 1)), 
 16: 'T', 
 17: (77473, 452), 
 29: '2013:10:25'}

Как я могу это интерпретировать? И я заметил, что тег не является непрерывным, так что есть ли какой-нибудь шпаргалку, к которой я могу обратиться, чтобы лучше понять все числовые теги и что они означают? Спасибо!

ОБНОВЛЕНИЯ

Извините, я разобрался. В библиотеке PIL есть функция GPSTAGS.get(), которая может помочь мне расшифровать ключ в информации GPS. Спасибо вам, ребята!

gpsinfo = {}
for key in exif['GPSInfo'].keys():
    decode = ExifTags.GPSTAGS.get(key,key)
    gpsinfo[decode] = exif['GPSInfo'][key]
print gpsinfo

и вот результат

{'GPSTimeStamp': ((15, 1), (32, 1), (7, 1)), 
 'GPSImgDirectionRef': 'T', 
 'GPSImgDirection': (77473, 452), 
 'GPSLongitude': ((103, 1), (41, 1), (1052, 100)), 
 'GPSLatitudeRef': 'N', 29: '2013:10:25', 
 'GPSAltitude': (43, 1), 
 'GPSLatitude': ((1, 1), (20, 1), (5365, 100)), 
 'GPSLongitudeRef': 'E', 
 'GPSAltitudeRef': 0}

person fyr91    schedule 06.11.2013    source источник
comment
Можете ли вы описать, какие кортежи находятся в значениях 'GPSLatitude' и 'GPSLongitude'?   -  person mnky9800n    schedule 09.06.2015
comment
@mnky9800n 103 градуса, 41 минута, 1052 сантисекунды, 103+41/60+1052/(3600*100)   -  person fujianjin6471    schedule 29.09.2019


Ответы (3)


Используйте модуль exifread.

Вот очень полезная суть

import exifread as ef


# barrowed from 
# https://gist.github.com/snakeye/fdc372dbf11370fe29eb 
def _convert_to_degress(value):
    """
    Helper function to convert the GPS coordinates stored in the EXIF to degress in float format
    :param value:
    :type value: exifread.utils.Ratio
    :rtype: float
    """
    d = float(value.values[0].num) / float(value.values[0].den)
    m = float(value.values[1].num) / float(value.values[1].den)
    s = float(value.values[2].num) / float(value.values[2].den)

    return d + (m / 60.0) + (s / 3600.0)


def getGPS(filepath):
    '''
    returns gps data if present other wise returns empty dictionary
    '''
    with open(filepath, 'r') as f:
        tags = ef.process_file(f)
        latitude = tags.get('GPS GPSLatitude')
        latitude_ref = tags.get('GPS GPSLatitudeRef')
        longitude = tags.get('GPS GPSLongitude')
        longitude_ref = tags.get('GPS GPSLongitudeRef')
        if latitude:
            lat_value = _convert_to_degress(latitude)
            if latitude_ref.values != 'N':
                lat_value = -lat_value
        else:
            return {}
        if longitude:
            lon_value = _convert_to_degress(longitude)
            if longitude_ref.values != 'E':
                lon_value = -lon_value
        else:
            return {}
        return {'latitude': lat_value, 'longitude': lon_value}
    return {}


file_path = 'file path of the file'    
gps = getGPS(file_path)
print gps
person Venkatesh Mondi    schedule 24.08.2017

Поздний ответ, но с 2021 вы можете использовать GPSPhoto, то есть:

from GPSPhoto import gpsphoto
# Get the data from image file and return a dictionary
data = gpsphoto.getGPSData('IMG_20181224_201933.jpg')
print(data['Latitude'], data['Longitude'])

Вывод:

38.71615498471598 -9.148730635643007


Установка:

pip3 install piexif
pip3 install gpsphoto
person Pedro Lobito    schedule 25.12.2018
comment
К вашему сведению, мне также пришлось pip install piexif заставить это работать. Спасибо! - person BruceWayne; 29.05.2019
comment
Привет, Педро, ты хоть представляешь, как это работает с URL-адресом? У меня возникла проблема, когда я пытаюсь использовать новый URL-адрес изображения, которое я сохранил из моего models.py -> TypeError: объект «NoneType» не подлежит подписке - person Louis; 17.10.2020
comment
@Louis, если под url вы подразумеваете URL-адрес фотографии, вам, вероятно, придется загрузить фотографию и обработать ее локально. - person Pedro Lobito; 24.10.2020
comment
Спасибо Педо за ответ. я уже нашел решение - person Louis; 24.10.2020

OP уже опубликовал решение с использованием PIL. Если вы хотите просто получить данные GPS из Python, вы можете получить их с помощью exifread.

Установить пакет с помощью pip

$ pip install exifread

и получить данные GPS

In [10]: import exifread

In [11]: tags = exifread.process_file(open('./tests/demo-project/content/test.jpg', 'rb'))                                              

In [12]: geo = {i:tags[i] for i in tags.keys() if i.startswith('GPS')}

In [13]: geo
Out[13]: 
{'GPS GPSAltitude': (0x0006) Ratio=186188/239 @ 898,
 'GPS GPSAltitudeRef': (0x0005) Byte=0 @ 722,
 'GPS GPSDate': (0x001D) ASCII=2015:12:06 @ 954,
 'GPS GPSDestBearing': (0x0018) Ratio=43771/526 @ 946,
 'GPS GPSDestBearingRef': (0x0017) ASCII=T @ 806,
 'GPS GPSImgDirection': (0x0011) Ratio=43771/526 @ 938,
 'GPS GPSImgDirectionRef': (0x0010) ASCII=T @ 782,
 'GPS GPSLatitude': (0x0002) Ratio=[46, 3803/100, 0] @ 850,
 'GPS GPSLatitudeRef': (0x0001) ASCII=N @ 674,
 'GPS GPSLongitude': (0x0004) Ratio=[13, 2429/100, 0] @ 874,
 'GPS GPSLongitudeRef': (0x0003) ASCII=E @ 698,
 'GPS GPSSpeed': (0x000D) Ratio=139/50 @ 930,
 'GPS GPSSpeedRef': (0x000C) ASCII=K @ 758,
 'GPS GPSTimeStamp': (0x0007) Ratio=[10, 37, 33] @ 906,
 'GPS Tag 0x001F': (0x001F) Ratio=30 @ 966}
person ChillarAnand    schedule 24.03.2016