- 1. Implementierung
- 1. fields.py
- 2. Modelle.py
WEBP ist ein Bildkomprimierungsformat, das 2010 von Google eingeführt wurde. Sein Hauptvorteil ist seine geringe Größe ohne sichtbaren Qualitätsverlust im Vergleich zu Formaten wie JPEG oder PNG. Daher ist es ziemlich logisch, dieses Format zum Speichern von Bildern auf der Website zu verwenden, insbesondere wenn Sie die Originalbilder nicht auf der Website speichern müssen.
Nach langer Suche habe ich immer noch keine fertige und einfache Lösung gefunden, die das Konvertieren von Bildern in das WEBP-Format im Handumdrehen unterstützen würde.
Deshalb beschloss ich, meine eigene Version zu schreiben, die schließlich aus ein paar Dutzend Zeilen besteht und so einfach wie ein Holzbrett ist.
Implementierung
Die gesamte Implementierung besteht aus zwei Teilen:
- WEBPFieldFile - eine von ImageFieldFile abgeleitete Klasse, die eine Datei mit automatischer Konvertierung in das WEBP-Format speichert.
- WEBPField - ImageField-Klasse, die WEBPFieldFile anstelle von ImageFieldFile verwendet
Und das alles befindet sich in einer Datei fields.py.
Um mit Bildern zu arbeiten, benötigen Sie die Pillow-Bibliothek. Also lass es uns installieren. Aber auch nur um ImageField-Felder zu verwenden, benötigen Sie diese Bibliothek.
pip install Pillow
fields.py
Erstellen Sie fields.py-Dateien in Ihrer Anwendung und fügen Sie den folgenden Code hinzu
# -*- coding: utf-8 -*- import io from PIL import Image from django.core.files.base import ContentFile from django.db import models from django.db.models.fields.files import ImageFieldFile class WEBPFieldFile(ImageFieldFile): def save(self, name, content, save=True): content.file.seek(0) image = Image.open(content.file) image_bytes = io.BytesIO() image.save(fp=image_bytes, format="WEBP") image_content_file = ContentFile(content=image_bytes.getvalue()) super().save(name, image_content_file, save) class WEBPField(models.ImageField): attr_class = WEBPFieldFile
Wie Sie sehen können, wird in diesem Code in der Klasse WEBPFieldFile die Methode save() überschrieben, die den Namen und Inhalt der zu speichernden Datei als Eingabeargument erhält und den Inhalt konvertiert der Datei in das WEBP-Format und speichert die Datei dann auf der Festplatte. Und die WEBPField -Klasse ist genau die gleiche wie ImageField , mit dem einzigen Unterschied, dass sie eine modifizierte Variante der Klasse für die Bildverarbeitung verwendet.
Modelle.py
Lassen Sie uns nun das neue Bildfeld in unserem Fotomodell verwenden.
# -*- coding: utf-8 -*- import os import uuid from django.conf import settings from django.db import models from django.utils.translation import gettext_lazy as _ from photo.fields import WEBPField def image_folder(instance, filename): return 'photos/{}.webp'.format(uuid.uuid4().hex) class Photo(models.Model): user = models.ForeignKey(to=settings.AUTH_USER_MODEL, on_delete=models.CASCADE) height = models.IntegerField(verbose_name=_('Height'), default=0, blank=True, null=True) width = models.IntegerField(verbose_name=_('Width'), default=0, blank=True, null=True) image = WEBPField( verbose_name=_('Image'), upload_to=image_folder, height_field='height', width_field='width' )
Wie Sie sehen, unterscheidet sich die Verwendung dieses WEBPField -Felds nicht von der Verwendung des standardmäßigen ImageField -Felds.
Und als Bonus habe ich in diesem Code in der Funktion image_folder die Generierung eines zufälligen eindeutigen Dateinamens mit uuid hinzugefügt.
Очень годно!