Compare commits

..

No commits in common. 'main' and 'main' have entirely different histories.
main ... main

@ -166,16 +166,15 @@ async def photo_points():
"""Get points with the url of a photo and the rate""" """Get points with the url of a photo and the rate"""
# assume we always have at least some photos # assume we always have at least some photos
# fetch them all # fetch them all
# if frontend uses 1 and 0 to represent like and dislike
# we can just take the average and turn it into %
# 100 * AVG(marks.mark)
cur.execute( cur.execute(
"""SELECT images.imgid, resizedpath, GPSLatitude, GPSLongitude, """SELECT images.imgid, resizedpath, GPSLatitude, GPSLongitude,
100 * AVG(marks.mark) 100*SUM(marks.mark)/COUNT(marks.mark)/MAX(marks.mark)
FROM images FROM images
LEFT JOIN marks ON images.imgid = marks.imgid LEFT JOIN marks ON images.imgid = marks.imgid
GROUP BY images.imgid; GROUP BY images.imgid;
""", """, # 100 * SUM(marks.mark)/COUNT(marks.mark)/MAX(marks.mark)
# is an ad-hoc percentage of likes without know how front end defined like/dislike
# returns None with no marks (sqlite handles division by 0 gracefully)
) )
points = cur.fetchall() points = cur.fetchall()
return [ return [
@ -184,7 +183,7 @@ async def photo_points():
"url": point["resizedpath"], "url": point["resizedpath"],
"lon": point["GPSLongitude"], "lon": point["GPSLongitude"],
"lat": point["GPSLatitude"], "lat": point["GPSLatitude"],
"rate": point["100 * AVG(marks.mark)"], "rate": point["100*SUM(marks.mark)/COUNT(marks.mark)/MAX(marks.mark)"],
} }
for point in points for point in points
] ]

@ -6,50 +6,9 @@ import filetype
from os import path, walk from os import path, walk
from sys import argv, stderr from sys import argv, stderr
from shutil import move from shutil import move
from fractions import Fraction
import sqlite3 import sqlite3
def decimal_from_rational64u(dms: str, ref):
"""Convert coordinates from rational64u EXIF uses to represent
degrees, minutes, and seconds of a point to decimal format
Take into account reference cardinal direction and
turn [S]outh and [W]est coordinates negative
General formula is
dec_degree = degreesNumerator / degreesDenominator
+ minutesNumerator / minutesDenominator / 60
+ secondsNumerator / secondsDenominator / 3600
https://en.wikipedia.org/wiki/Geographic_coordinate_conversion
https://gis.stackexchange.com/questions/136925/how-to-parse-exif-gps-information-to-lat-lng-decimal-numbers
>>> decimal_from_rational64u(dms="42/1, 18/1, 2914/100", "S")
-42.30809
"""
# 1 split by comma
# 2 turn each into Fraction
# 3 zip fractions with their respective (degrees, minutes, seconds) denominator
# 4 divide the fraction
# 5 sum up the result
# 6 convert to decimal
# 7 round to 5th decimal point
dec_coordinates = round(
float(
sum(
a / b
for (a, b) in zip((Fraction(f) for f in dms.split(",")), (1, 60, 3600))
)
),
5,
)
if ref in ("S", "W"):
dec_coordinates = -dec_coordinates
return dec_coordinates
def process_pictures(source: str, dest_shrunk: str, dest_original: str): def process_pictures(source: str, dest_shrunk: str, dest_original: str):
"""Process images from the base directory in the first command line argument. """Process images from the base directory in the first command line argument.
Place the resized copies to dest_shrunk and Place the resized copies to dest_shrunk and
@ -73,14 +32,8 @@ def process_pictures(source: str, dest_shrunk: str, dest_original: str):
(k[5:], v) for k, v in image.metadata.items() if k.startswith("exif:") (k[5:], v) for k, v in image.metadata.items() if k.startswith("exif:")
) )
with image.clone() as cloned: with image.clone() as cloned:
# adjust an image so that its orientation is suitable for viewing
# (i.e. top-left orientation) by checking EXIF data
cloned.auto_orient()
# strip an image of all profiles and comments
cloned.strip() # Q: may damage icc, do we allow that or use smh else? cloned.strip() # Q: may damage icc, do we allow that or use smh else?
# resize the shorter side to be no more than 1000px cloned.transform(resize="50%") # Q: what do we want here?
# https://legacy.imagemagick.org/discourse-server/viewtopic.php?p=44329#p44329
cloned.transform(resize="1000^>") # Q: what do we want here?
# move them to the processed folder # move them to the processed folder
cloned.save(filename=path.join(dest_shrunk, filename)) cloned.save(filename=path.join(dest_shrunk, filename))
@ -94,12 +47,10 @@ def process_pictures(source: str, dest_shrunk: str, dest_original: str):
"ResizedImage": path.join(dest_shrunk, filename), "ResizedImage": path.join(dest_shrunk, filename),
"OriginalImage": path.join(dest_original, filename), "OriginalImage": path.join(dest_original, filename),
"DateTimeOriginal": exif["DateTimeOriginal"], # Q: normalize it? "DateTimeOriginal": exif["DateTimeOriginal"], # Q: normalize it?
"GPSLatitude": decimal_from_rational64u( "GPSLatitude": exif["GPSLatitude"],
exif["GPSLatitude"], exif["GPSLatitudeRef"] "GPSLatitudeRef": exif["GPSLatitudeRef"],
), "GPSLongitude": exif["GPSLongitude"],
"GPSLongitude": decimal_from_rational64u( "GPSLongitudeRef": exif["GPSLongitudeRef"],
exif["GPSLongitude"], exif["GPSLongitudeRef"]
),
} }
except KeyError as e: except KeyError as e:
print(f"Image '{filename}' has no valid exif") print(f"Image '{filename}' has no valid exif")
@ -122,13 +73,17 @@ def update_database(pic_info: dict, db_location: str):
origpath, origpath,
date, date,
GPSLatitude, GPSLatitude,
GPSLongitude) GPSLatitudeRef,
GPSLongitude,
GPSLongitudeRef)
VALUES (:ResizedImage, VALUES (:ResizedImage,
:OriginalImage, :OriginalImage,
:DateTimeOriginal, :DateTimeOriginal,
:GPSLatitude, :GPSLatitude,
:GPSLongitude) :GPSLatitudeRef,
:GPSLongitude,
:GPSLongitudeRef)
""", """,
pic_info, pic_info,
) )
@ -159,8 +114,10 @@ def check_database(database_path: str):
resizedpath TEXT NOT NULL, resizedpath TEXT NOT NULL,
origpath TEXT NOT NULL, origpath TEXT NOT NULL,
date TEXT, date TEXT,
GPSLatitude REAL, GPSLatitude TEXT,
GPSLongitude REAL GPSLatitudeRef TEXT,
GPSLongitude TEXT,
GPSLongitudeRef TEXT
)""" )"""
) )
con.commit() con.commit()

Loading…
Cancel
Save