rmm commited on
Commit
d90e4ef
·
2 Parent(s): 859e75b 6b164ea

Merge branch 'feat/exif-metadata' into test/tests

Browse files
Files changed (1) hide show
  1. src/input_handling.py +39 -3
src/input_handling.py CHANGED
@@ -1,3 +1,4 @@
 
1
  from PIL import Image
2
  from PIL import ExifTags
3
  import re
@@ -185,14 +186,49 @@ def get_image_datetime(image_file: UploadedFile) -> str | None:
185
  image = Image.open(image_file)
186
  exif_data = image._getexif()
187
  if exif_data is not None:
188
- for tag, value in exif_data.items():
189
- if ExifTags.TAGS.get(tag) == 'DateTimeOriginal':
190
- return value
191
  except Exception as e: # FIXME: what types of exception?
192
  st.warning(f"Could not extract date from image metadata. (file: {image_file.name})")
193
  # TODO: add to logger
194
  return None
195
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
196
 
197
  # an arbitrary set of defaults so testing is less painful...
198
  # ideally we add in some randomization to the defaults
 
1
+ from fractions import Fraction
2
  from PIL import Image
3
  from PIL import ExifTags
4
  import re
 
186
  image = Image.open(image_file)
187
  exif_data = image._getexif()
188
  if exif_data is not None:
189
+ if ExifTags.Base.DateTimeOriginal in exif_data:
190
+ return exif_data.get(ExifTags.Base.DateTimeOriginal)
 
191
  except Exception as e: # FIXME: what types of exception?
192
  st.warning(f"Could not extract date from image metadata. (file: {image_file.name})")
193
  # TODO: add to logger
194
  return None
195
 
196
+ def decimal_coords(coords:tuple, ref:str) -> Fraction:
197
+ # https://stackoverflow.com/a/73267185
198
+ decimal_degrees = coords[0] + coords[1] / 60 + coords[2] / 3600
199
+ if ref == "S" or ref =='W':
200
+ decimal_degrees = -decimal_degrees
201
+ return decimal_degrees
202
+
203
+
204
+ def get_image_latlon(image_file: UploadedFile) -> tuple[float, float] | None:
205
+ """
206
+ Extracts the latitude and longitude from the EXIF metadata of an uploaded image file.
207
+
208
+ Args:
209
+ image_file (UploadedFile): The uploaded image file from which to extract the latitude and longitude.
210
+
211
+ Returns:
212
+ tuple[float, float]: The latitude and longitude as a tuple if available, otherwise None.
213
+
214
+ Raises:
215
+ Warning: If the latitude and longitude could not be extracted from the image metadata.
216
+ """
217
+ try:
218
+ image = Image.open(image_file)
219
+ exif_data = image._getexif()
220
+ if exif_data is not None:
221
+ if ExifTags.Base.GPSInfo in exif_data:
222
+ gps_ifd = exif_data.get(ExifTags.Base.GPSInfo)
223
+
224
+ lat = float(decimal_coords(gps_ifd[ExifTags.GPS.GPSLatitude], gps_ifd[ExifTags.GPS.GPSLatitudeRef]))
225
+ lon = float(decimal_coords(gps_ifd[ExifTags.GPS.GPSLongitude], gps_ifd[ExifTags.GPS.GPSLongitudeRef]))
226
+
227
+ return lat, lon
228
+
229
+ except Exception as e: # FIXME: what types of exception?
230
+ st.warning(f"Could not extract latitude and longitude from image metadata. (file: {str(image_file)}")
231
+
232
 
233
  # an arbitrary set of defaults so testing is less painful...
234
  # ideally we add in some randomization to the defaults