From 4a50579ef1c8b9bcfa52d2a5d488005fcc28a09e Mon Sep 17 00:00:00 2001 From: tenma Date: Thu, 13 Aug 2020 18:37:31 +0100 Subject: [PATCH] [MEDIA] Add WebP support WebP format is now the default image format for anything that is not an animated GIF. Image Intervention doesn't support animated WebPs so we don't convert animated GIFs. ImageFile: MediaFile: default: - Add WebP support --- DOCUMENTATION/DEVELOPERS/EVENTS.txt | 2 +- lib/media/imagefile.php | 32 +++++++++++++---------------- lib/media/mediafile.php | 4 ++-- lib/util/default.php | 1 + 4 files changed, 18 insertions(+), 21 deletions(-) diff --git a/DOCUMENTATION/DEVELOPERS/EVENTS.txt b/DOCUMENTATION/DEVELOPERS/EVENTS.txt index 7ab80afc94..e2a0ff4cd3 100644 --- a/DOCUMENTATION/DEVELOPERS/EVENTS.txt +++ b/DOCUMENTATION/DEVELOPERS/EVENTS.txt @@ -1447,7 +1447,7 @@ CreateFileImageThumbnailSource: Hook to create image thumbnail source from a Fil StartResizeImageFile: Hook to resize an image and output it to a file. No matching End event yet. - $imagefile: ImageFile object we're resizing. -- $outpath: string with output filepath +- $outpath: string with output filepath - $box: array with size ('width', 'height') and boundary box('x', 'y', 'w', 'h'). FillImageFileMetadata: Get more metadata about the ImageFile if it is perhaps not a real local file diff --git a/lib/media/imagefile.php b/lib/media/imagefile.php index cf425cbae8..b4bf006fd5 100644 --- a/lib/media/imagefile.php +++ b/lib/media/imagefile.php @@ -88,12 +88,13 @@ class ImageFile extends MediaFile } return false; }; - if (!(($cmp($this, IMAGETYPE_GIF) && function_exists('imagecreatefromgif')) || + if (!(($cmp($this, IMAGETYPE_GIF) && function_exists('imagecreatefromgif')) || ($cmp($this, IMAGETYPE_JPEG) && function_exists('imagecreatefromjpeg')) || - ($cmp($this, IMAGETYPE_BMP) && function_exists('imagecreatefrombmp')) || + ($cmp($this, IMAGETYPE_BMP) && function_exists('imagecreatefrombmp')) || ($cmp($this, IMAGETYPE_WBMP) && function_exists('imagecreatefromwbmp')) || - ($cmp($this, IMAGETYPE_XBM) && function_exists('imagecreatefromxbm')) || - ($cmp($this, IMAGETYPE_PNG) && function_exists('imagecreatefrompng')) + ($cmp($this, IMAGETYPE_XBM) && function_exists('imagecreatefromxbm')) || + ($cmp($this, IMAGETYPE_PNG) && function_exists('imagecreatefrompng')) || + ($cmp($this, IMAGETYPE_WEBP) && function_exists('imagecreatefromwebp')) ) ) { common_debug("Mimetype '{$this->mimetype}' was not recognized as a supported format"); @@ -169,6 +170,7 @@ class ImageFile extends MediaFile if ($media !== 'image') { throw new UnsupportedMediaException(_m('Unsupported media format.'), $file->getPath()); } + if (!empty($file->filename)) { $imgPath = $file->getPath(); } @@ -282,22 +284,19 @@ class ImageFile extends MediaFile } /** - * Several obscure file types should be normalized to PNG on resize. + * Several obscure file types should be normalized to WebP on resize. * - * Keeps only PNG, JPEG and GIF + * Keeps only GIF (if animated) and WebP formats * * @return int */ public function preferredType() { - // Keep only JPEG and GIF in their original format - if ($this->type === IMAGETYPE_JPEG || $this->type === IMAGETYPE_GIF) { + if ($this->type == IMAGETYPE_GIF && $this->animated) { return $this->type; } - // We don't want to save some formats as they are rare, inefficient and antiquated - // thus we can't guarantee clients will support - // So just save it as PNG - return IMAGETYPE_PNG; + + return IMAGETYPE_WEBP; } /** @@ -436,15 +435,12 @@ class ImageFile extends MediaFile // Ensure we save in the correct format and allow customization based on type $type = $this->preferredType(); switch ($type) { + case IMAGETYPE_WEBP: + $img->save($outpath, 100, 'webp'); + break; case IMAGETYPE_GIF: $img->save($outpath, 100, 'gif'); break; - case IMAGETYPE_PNG: - $img->save($outpath, 100, 'png'); - break; - case IMAGETYPE_JPEG: - $img->save($outpath, common_config('image', 'jpegquality'), 'jpg'); - break; default: // TRANS: Exception thrown when trying resize an unknown file type. throw new Exception(_m('Unknown file type')); diff --git a/lib/media/mediafile.php b/lib/media/mediafile.php index 31179db08f..3a26327fb4 100644 --- a/lib/media/mediafile.php +++ b/lib/media/mediafile.php @@ -408,8 +408,8 @@ class MediaFile if ($media == 'image') { // Use -1 for the id to avoid adding this temporary file to the DB $img = new ImageFile(-1, $_FILES[$param]['tmp_name']); - // Validate the image by re-encoding it. Additionally normalizes old formats to PNG, - // keeping JPEG and GIF untouched + // Validate the image by re-encoding it. Additionally normalizes old formats to WebP, + // keeping GIF untouched if animated $outpath = $img->resizeTo($img->filepath); $ext = image_type_to_extension($img->preferredType(), false); } diff --git a/lib/util/default.php b/lib/util/default.php index 58a46400b2..6ce1c733e6 100644 --- a/lib/util/default.php +++ b/lib/util/default.php @@ -256,6 +256,7 @@ $default = image_type_to_mime_type(IMAGETYPE_GIF) => image_type_to_extension(IMAGETYPE_GIF), 'image/svg+xml' => 'svg', // No built-in constant image_type_to_mime_type(IMAGETYPE_ICO) => image_type_to_extension(IMAGETYPE_ICO), + image_type_to_mime_type(IMAGETYPE_WEBP) => image_type_to_extension(IMAGETYPE_WEBP), 'audio/ogg' => 'ogg', 'audio/mpeg' => 'mpg', 'audio/x-speex' => 'spx',