Merge b75d8dcb81
into 61b9f81e39
This commit is contained in:
commit
f0a2aeae8e
6 changed files with 41 additions and 1 deletions
|
@ -7,7 +7,7 @@ scrubbing](https://sjp.pwn.pl/sjp/;2527372). It is pronounced as *shoorubooru*.
|
||||||
|
|
||||||
## Features
|
## Features
|
||||||
|
|
||||||
- Post content: images (JPG, PNG, GIF, animated GIF), videos (MP4, WEBM), Flash animations
|
- Post content: images (JPG, PNG, GIF, animated GIF, PSD), videos (MP4, WEBM), Flash animations
|
||||||
- Ability to retrieve web video content using [yt-dlp](https://github.com/yt-dlp/yt-dlp)
|
- Ability to retrieve web video content using [yt-dlp](https://github.com/yt-dlp/yt-dlp)
|
||||||
- Post comments
|
- Post comments
|
||||||
- Post notes / annotations, including arbitrary polygons
|
- Post notes / annotations, including arbitrary polygons
|
||||||
|
|
|
@ -41,3 +41,11 @@ def save(path: str, content: bytes) -> None:
|
||||||
os.makedirs(os.path.dirname(full_path), exist_ok=True)
|
os.makedirs(os.path.dirname(full_path), exist_ok=True)
|
||||||
with open(full_path, "wb") as handle:
|
with open(full_path, "wb") as handle:
|
||||||
handle.write(content)
|
handle.write(content)
|
||||||
|
if path.endswith(".psd"):
|
||||||
|
# Handle .psd files
|
||||||
|
handle_psd_file(full_path)
|
||||||
|
|
||||||
|
|
||||||
|
def handle_psd_file(path: str) -> None:
|
||||||
|
# Add specific handling for .psd files here
|
||||||
|
pass
|
||||||
|
|
|
@ -24,6 +24,13 @@ def convert_heif_to_png(content: bytes) -> bytes:
|
||||||
return img_byte_arr.getvalue()
|
return img_byte_arr.getvalue()
|
||||||
|
|
||||||
|
|
||||||
|
def convert_psd_to_png(content: bytes) -> bytes:
|
||||||
|
img = PILImage.open(BytesIO(content))
|
||||||
|
img_byte_arr = BytesIO()
|
||||||
|
img.save(img_byte_arr, format="PNG")
|
||||||
|
return img_byte_arr.getvalue()
|
||||||
|
|
||||||
|
|
||||||
class Image:
|
class Image:
|
||||||
def __init__(self, content: bytes) -> None:
|
def __init__(self, content: bytes) -> None:
|
||||||
self.content = content
|
self.content = content
|
||||||
|
@ -269,6 +276,8 @@ class Image:
|
||||||
# FFmpeg does not support HEIF.
|
# FFmpeg does not support HEIF.
|
||||||
# https://trac.ffmpeg.org/ticket/6521
|
# https://trac.ffmpeg.org/ticket/6521
|
||||||
self.content = convert_heif_to_png(self.content)
|
self.content = convert_heif_to_png(self.content)
|
||||||
|
elif mime_type == "image/vnd.adobe.photoshop":
|
||||||
|
self.content = convert_psd_to_png(self.content)
|
||||||
extension = mime.get_extension(mime_type)
|
extension = mime.get_extension(mime_type)
|
||||||
assert extension
|
assert extension
|
||||||
with util.create_temp_file(suffix="." + extension) as handle:
|
with util.create_temp_file(suffix="." + extension) as handle:
|
||||||
|
|
|
@ -33,6 +33,9 @@ def get_mime_type(content: bytes) -> str:
|
||||||
if content[4:12] in (b"ftypheic", b"ftypheix"):
|
if content[4:12] in (b"ftypheic", b"ftypheix"):
|
||||||
return "image/heic"
|
return "image/heic"
|
||||||
|
|
||||||
|
if content[0:4] == b"8BPS":
|
||||||
|
return "image/vnd.adobe.photoshop"
|
||||||
|
|
||||||
if content[0:4] == b"\x1A\x45\xDF\xA3":
|
if content[0:4] == b"\x1A\x45\xDF\xA3":
|
||||||
return "video/webm"
|
return "video/webm"
|
||||||
|
|
||||||
|
@ -56,6 +59,7 @@ def get_extension(mime_type: str) -> Optional[str]:
|
||||||
"image/avif": "avif",
|
"image/avif": "avif",
|
||||||
"image/heif": "heif",
|
"image/heif": "heif",
|
||||||
"image/heic": "heic",
|
"image/heic": "heic",
|
||||||
|
"image/vnd.adobe.photoshop": "psd",
|
||||||
"video/mp4": "mp4",
|
"video/mp4": "mp4",
|
||||||
"video/quicktime": "mov",
|
"video/quicktime": "mov",
|
||||||
"video/webm": "webm",
|
"video/webm": "webm",
|
||||||
|
@ -87,6 +91,7 @@ def is_image(mime_type: str) -> bool:
|
||||||
"image/avif",
|
"image/avif",
|
||||||
"image/heif",
|
"image/heif",
|
||||||
"image/heic",
|
"image/heic",
|
||||||
|
"image/vnd.adobe.photoshop",
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -617,6 +617,8 @@ def update_post_content(post: model.Post, content: Optional[bytes]) -> None:
|
||||||
update_signature = True
|
update_signature = True
|
||||||
if mime.is_animated_gif(content):
|
if mime.is_animated_gif(content):
|
||||||
post.type = model.Post.TYPE_ANIMATION
|
post.type = model.Post.TYPE_ANIMATION
|
||||||
|
elif post.mime_type == "image/vnd.adobe.photoshop":
|
||||||
|
post.type = model.Post.TYPE_IMAGE
|
||||||
else:
|
else:
|
||||||
post.type = model.Post.TYPE_IMAGE
|
post.type = model.Post.TYPE_IMAGE
|
||||||
elif mime.is_video(post.mime_type):
|
elif mime.is_video(post.mime_type):
|
||||||
|
|
16
server/szurubooru/func/psd_handler.py
Normal file
16
server/szurubooru/func/psd_handler.py
Normal file
|
@ -0,0 +1,16 @@
|
||||||
|
from PIL import Image
|
||||||
|
from io import BytesIO
|
||||||
|
|
||||||
|
def handle_psd_file(path: str) -> None:
|
||||||
|
with open(path, "rb") as f:
|
||||||
|
psd_content = f.read()
|
||||||
|
png_content = convert_psd_to_png(psd_content)
|
||||||
|
png_path = path.replace(".psd", ".png")
|
||||||
|
with open(png_path, "wb") as f:
|
||||||
|
f.write(png_content)
|
||||||
|
|
||||||
|
def convert_psd_to_png(content: bytes) -> bytes:
|
||||||
|
img = Image.open(BytesIO(content))
|
||||||
|
img_byte_arr = BytesIO()
|
||||||
|
img.save(img_byte_arr, format="PNG")
|
||||||
|
return img_byte_arr.getvalue()
|
Reference in a new issue