django - Django 使用 Pillow 以不同格式保存图像
问题描述
我有我正在为我的学校制作的这个网站,我需要优化它,就像很多一样。
因此,我决定以 jpeg-2000 和 webp 等下一代格式提供我所有的压缩图像。使用 Pillow,这是我目前所拥有的:
class Bulletin(models.Model):
banner = models.ImageField(upload_to='banner/', blank=True)
def save(self, *args, **kwargs):
super().save()
if self.banner:
thumbnail = Image.open(self.banner.path)
resized = thumbnail.resize((1280, 620))
resized.save(self.banner.path, quality=60)
所以我认为这会压缩图像(如果我在上面的代码中犯了错误,请告诉我)。
所以现在我希望能够以多种格式保存这张图片我希望上传的一张图片以这些格式保存:
- 网页
- JPEG2000
- JPEG
我正在考虑在我的模型横幅上创建更多字段,例如 field banner_webp
,然后我将其转换为 webp 并在保存期间将转换后的图像保存到该字段。
问题是我不知道如何使用 Pillow 转换图像,或者如何做我所要求的。感谢帮助。
解决方案
约翰已经找到了一个可行的解决方案。我建议对此进行以下更改:
- 假设公告有更多字段可能会在不更改横幅的情况下发生更改:您不需要在每个
save()
公告上重新编码图像。如果您将编码放入其自己的函数中,则可以在上传视图中专门调用该函数,如果这是您的代码中修改此值的唯一位置。有可能检测save()
该字段是否已更改,因此这也是一种选择。 - 如果您保留自定义
save()
方法:您应该在调用中传递参数super
:super().save(*args, **kwargs)
- 您无需删除旧扩展名:您可以将图像命名为“whatever.jpg.webp”。它不会混淆计算机,而且我认为这个名称非常清楚地表明它是对原始文件的重新编码。此外,这允许您保持原始文件原样,以防有一天您决定要使用其他参数对图像进行编码,例如使用不同的质量设置。
- 对重新编码的图像文件路径使用统一的访问器可以防止一些与拼写错误相关的错误。
class Bulletin(models.Model):
BANNER_REENCODE_FORMATS = ["jpg", "jp2", "webp"]
banner = models.ImageField(upload_to='banner/', blank=True)
def reencoded_banner_path(self, file_format="jpg"):
assert file_format in self.BANNER_REENCODE_FORMATS
return self.banner.path + "." + file_format
def reencode_banner(self):
image = Image.open(self.banner.path).convert("RGB").resize((1280, 620))
for extension in self.BANNER_REENCODE_FORMATS:
image.save(self.reencoded_banner_path(extension), quality=60)
使用以下模板标签:
@register.filter(name='reencoded_banner_path')
@stringfilter
def reencoded_banner_path(bulletin, format):
return bulletin.reencoded_banner_path(format)
你可以在你的模板中使用它:
{{ bulletin|reencoded_banner_path:"webp" }}
请注意,您可能希望对图像上传有一些重命名逻辑,以便在用户上传两个具有相同文件名的文件时不会中断。
推荐阅读
- reactjs - 命令不创建reactjs的项目
- shell - 从 Ubuntu 端通过 ssh 或串行端口登录到嵌入式 Linux 设备而无需密码
- rotation - 旋转帧缓冲区仅适用于 180° 和 0°
- python - 将 PyQt5 桌面应用程序转换为使用 python 开发的 IOS/MacOS 应用程序
- javascript - 在 Laravel 中使用 pusher 收听消息
- amazon-ec2 - EC2 安全组中的 Bitbucket IP 白名单
- java - 如何使用邮递员休息客户端发送对象以调用 REST 服务,以便它使用正确的方法参数访问下面给定的方法?
- javascript - 在 Liferay 7.2 中将 Web 内容自动保存为草稿
- google-tag-manager - 所有元素单击触发器未触发
- android - 安卓流光盒遥控器使用方法