From 792b9c875f1aefc83eda48b2d9fa9b66bf748b85 Mon Sep 17 00:00:00 2001 From: Sheldon Lee Date: Mon, 13 Nov 2023 02:03:04 +0800 Subject: [PATCH] Implement thumbnail generation --- php/get.php | 93 +++++++++++++++++++++++++++++++++++----------- scripts/resize-img | 62 +++++++++++++++++++++++++++++++ 2 files changed, 133 insertions(+), 22 deletions(-) create mode 100755 scripts/resize-img diff --git a/php/get.php b/php/get.php index 0cc73d8..91d046c 100644 --- a/php/get.php +++ b/php/get.php @@ -4,7 +4,25 @@ include_once __DIR__ . "/logging.php"; define("ROOT_URL", "http://localhost/"); define("ROOT_DIR", "/var/www/localhost/"); define("IMG_DIR", "img/"); -define("THUMBNAIL_DIR", __DIR__ . "../thumbnails"); +define("THUMBNAIL_DIR", "thumbnails/"); +define("THUMBNAIL_SCRIPT", __DIR__ . "/../scripts/resize-img"); + +define("IMAGE_EXTENSIONS", [ + 'jpg', + 'jpeg', + 'png', + 'gif', + 'tiff', + 'bmp', + 'webp', + 'svg', +]); + +define("VIDEO_EXTENSIONS", [ + 'mp4', +]); + +define("FILE_EXTENSIONS", array_merge(IMAGE_EXTENSIONS, VIDEO_EXTENSIONS)); main(); @@ -20,14 +38,19 @@ function main(): void { if ($file === ".") continue; if ($category === "" && $file === "..") continue; - if ($category != "") $file = $category.'/'.$file; - $is_dir = is_dir(ROOT_DIR.IMG_DIR.$file); + $path = add_seperator_ab("/", $category, $file); + $is_dir = is_dir(ROOT_DIR.IMG_DIR.$path); if (!$is_dir && !is_valid_file_type($file)) continue; $file_item = []; $file_item["is_dir"] = $is_dir; - $file_item["url"] = ROOT_URL.IMG_DIR.$file; - $file_item["thumbnail_url"] = create_thumbnail($file); + if ($is_dir) { + $file_item["url"] = ROOT_URL.IMG_DIR.$path; + $file_item["thumbnail_url"] = null; + } else { + $file_item["url"] = ROOT_URL.IMG_DIR.$path; + $file_item["thumbnail_url"] = create_thumbnail($category, $file); + } array_push($array, $file_item); } @@ -35,29 +58,55 @@ function main(): void { echo json_encode($array); } -function create_thumbnail(string $file): string { - return ROOT_URL.IMG_DIR.$file; +function create_thumbnail(string $category, string $file): string | null { + if (!is_image_file_type($file)) return null; + + $path = add_seperator_ab("/", $category, $file); + $original_file = ROOT_DIR.IMG_DIR.$path; + $thumbnail_directory = ROOT_DIR.THUMBNAIL_DIR.IMG_DIR.add_seperator_ab("/", $category, ""); + $thumbnail_file = $thumbnail_directory.$file; + + if (file_exists($thumbnail_file)) { + log_print("$thumbnail_file exists, skipping gneeration"); + goto return_thumbnail; + } + + try { + if (!is_dir($thumbnail_directory)) mkdir($thumbnail_directory, 0777, true); + } + catch(Exception $e) { + log_error($e->getMessage()); + } + + log_print(THUMBNAIL_SCRIPT." '$original_file' '$thumbnail_file'"); + $output = shell_exec(THUMBNAIL_SCRIPT." '$original_file' '$thumbnail_file' 2>&1"); + log_print($output); + if ($output === false) { + log_error("Thumbnail failed"); + return ROOT_URL.IMG_DIR.$path; + } + + return_thumbnail: + return ROOT_URL.THUMBNAIL_DIR.IMG_DIR.$path; +} + +function add_seperator_ab(string $separator, string $a, string $b): string { + if ($a === "") return $b; + return $a.$separator.$b; } function is_valid_file_type(string $filename): bool { - $file_extensions = [ - // Image extensions - 'jpg', - 'jpeg', - 'png', - 'gif', - 'tiff', - 'bmp', - 'webp', - 'svg', - // Video extensions - 'mp4', - ]; - - foreach ($file_extensions as $file_extension) { + foreach (FILE_EXTENSIONS as $file_extension) { if (str_ends_with($filename, $file_extension)) return true; } return false; } + +function is_image_file_type(string $filename): bool { + foreach(IMAGE_EXTENSIONS as $file_extension) { + if(str_ends_with($filename, $file_extension)) return true; + } + return false; +} ?> diff --git a/scripts/resize-img b/scripts/resize-img new file mode 100755 index 0000000..0c1bcb4 --- /dev/null +++ b/scripts/resize-img @@ -0,0 +1,62 @@ +#!/usr/bin/python +from PIL import Image +import sys + + +def main(): + target_width = 2048 + + argn = len(sys.argv) + + if argn == 1: + print("You must specify an input file") + exit(1) + elif argn == 2: + print("You must specify an output file") + exit(1) + + input_image_path = sys.argv[1] + output_image_path = sys.argv[2] + + try: + image = Image.open(input_image_path) + except IOError: + print(f"Cannot open image file {input_image_path}") + exit(1) + + width, height = image.size + new_height = int(target_width * height / width) + + image = image.resize((target_width, new_height), Image.Resampling.BICUBIC) + image = rotate_image(image) + + kwargs = {"quality": 50} + if "exif" in image.info.keys(): + kwargs["exif"] = image.info["exif"] + + try: + image.save(output_image_path, **kwargs) + except IOError: + print(f"Cannot save file {output_image_path}") + exit(1) + + +def rotate_image(image): + exif = image.getexif() + if exif is None: + return image + + orientation = exif.get(0x0012, 1) # 0x0112 is the EXIF code for orientation + if orientation == 1: + return image + elif orientation == 3: + image = image.rotate(180, expand=True) + elif orientation == 6: + image = image.rotate(270, expand=True) + elif orientation == 8: + image = image.rotate(90, expand=True) + return image + + +if __name__ == "__main__": + main()