forked from GNUsocial/gnu-social
[MEDIA] Replaced internal image handling with intervention/image, which is capable of using both GD and ImageMagik
This commit is contained in:
parent
2db3825940
commit
955d5a136f
@ -30,6 +30,8 @@
|
|||||||
|
|
||||||
defined('GNUSOCIAL') || die();
|
defined('GNUSOCIAL') || die();
|
||||||
|
|
||||||
|
use Intervention\Image\ImageManagerStatic as Image;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A wrapper on uploaded images
|
* A wrapper on uploaded images
|
||||||
*
|
*
|
||||||
@ -53,27 +55,37 @@ class ImageFile extends MediaFile
|
|||||||
|
|
||||||
public function __construct($id, string $filepath)
|
public function __construct($id, string $filepath)
|
||||||
{
|
{
|
||||||
|
$old_limit = ini_set('memory_limit', common_config('attachments', 'memory_limit'));
|
||||||
|
|
||||||
// These do not have to be the same as fileRecord->filename for example,
|
// These do not have to be the same as fileRecord->filename for example,
|
||||||
// since we may have generated an image source file from something else!
|
// since we may have generated an image source file from something else!
|
||||||
$this->filepath = $filepath;
|
$this->filepath = $filepath;
|
||||||
$this->filename = basename($filepath);
|
$this->filename = basename($filepath);
|
||||||
|
|
||||||
$info = @getimagesize($this->filepath);
|
$img = Image::make($this->filepath);
|
||||||
|
$this->mimetype = $img->mime();
|
||||||
|
|
||||||
if (!(($info[2] == IMAGETYPE_GIF && function_exists('imagecreatefromgif')) ||
|
$cmp = function($obj, $type) {
|
||||||
($info[2] == IMAGETYPE_JPEG && function_exists('imagecreatefromjpeg')) ||
|
if ($obj->mimetype == image_type_to_mime_type($type)) {
|
||||||
($info[2] == IMAGETYPE_BMP && function_exists('imagecreatefrombmp')) ||
|
$obj->type = $type;
|
||||||
($info[2] == IMAGETYPE_WBMP && function_exists('imagecreatefromwbmp')) ||
|
return true;
|
||||||
($info[2] == IMAGETYPE_XBM && function_exists('imagecreatefromxbm')) ||
|
} else {
|
||||||
($info[2] == IMAGETYPE_PNG && function_exists('imagecreatefrompng')))) {
|
return false;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
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_WBMP) && function_exists('imagecreatefromwbmp')) ||
|
||||||
|
($cmp($this, IMAGETYPE_XBM) && function_exists('imagecreatefromxbm')) ||
|
||||||
|
($cmp($this, IMAGETYPE_PNG) && function_exists('imagecreatefrompng')))) {
|
||||||
|
common_debug("Mimetype '{$this->mimetype}' was not recognized as a supported format");
|
||||||
// TRANS: Exception thrown when trying to upload an unsupported image file format.
|
// TRANS: Exception thrown when trying to upload an unsupported image file format.
|
||||||
throw new UnsupportedMediaException(_m('Unsupported image format.'), $this->filepath);
|
throw new UnsupportedMediaException(_m('Unsupported image format.'), $this->filepath);
|
||||||
}
|
}
|
||||||
|
|
||||||
$this->width = $info[0];
|
$this->width = $img->width();
|
||||||
$this->height = $info[1];
|
$this->height = $img->height();
|
||||||
$this->type = $info[2];
|
|
||||||
$this->mimetype = $info['mime'];
|
|
||||||
|
|
||||||
parent::__construct(
|
parent::__construct(
|
||||||
$filepath,
|
$filepath,
|
||||||
@ -82,9 +94,9 @@ class ImageFile extends MediaFile
|
|||||||
$id
|
$id
|
||||||
);
|
);
|
||||||
|
|
||||||
if ($this->type === IMAGETYPE_JPEG && function_exists('exif_read_data')) {
|
if ($this->type === IMAGETYPE_JPEG) {
|
||||||
// Orientation value to rotate thumbnails properly
|
// Orientation value to rotate thumbnails properly
|
||||||
$exif = @exif_read_data($this->filepath);
|
$exif = @$img->exif();
|
||||||
if (is_array($exif) && isset($exif['Orientation'])) {
|
if (is_array($exif) && isset($exif['Orientation'])) {
|
||||||
switch (intval($exif['Orientation'])) {
|
switch (intval($exif['Orientation'])) {
|
||||||
case 1: // top is top
|
case 1: // top is top
|
||||||
@ -107,8 +119,16 @@ class ImageFile extends MediaFile
|
|||||||
}
|
}
|
||||||
|
|
||||||
Event::handle('FillImageFileMetadata', array($this));
|
Event::handle('FillImageFileMetadata', array($this));
|
||||||
|
|
||||||
|
$img->destroy();
|
||||||
|
ini_set('memory_limit', $old_limit); // Restore the old memory limit
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a thumbnail from a file object
|
||||||
|
*
|
||||||
|
* @return ImageFile
|
||||||
|
*/
|
||||||
public static function fromFileObject(File $file)
|
public static function fromFileObject(File $file)
|
||||||
{
|
{
|
||||||
$imgPath = null;
|
$imgPath = null;
|
||||||
@ -250,8 +270,9 @@ class ImageFile extends MediaFile
|
|||||||
$box['h'] = isset($box['h']) ? intval($box['h']) : $this->height;
|
$box['h'] = isset($box['h']) ? intval($box['h']) : $this->height;
|
||||||
|
|
||||||
if (!file_exists($this->filepath)) {
|
if (!file_exists($this->filepath)) {
|
||||||
// TRANS: Exception thrown during resize when image has been registered as present, but is no longer there.
|
// TRANS: Exception thrown during resize when image has been registered as present,
|
||||||
throw new Exception(_m('Lost our file.'));
|
// but is no longer there.
|
||||||
|
throw new FileNotFoundException($this->filepath);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Don't rotate/crop/scale if it isn't necessary
|
// Don't rotate/crop/scale if it isn't necessary
|
||||||
@ -307,94 +328,44 @@ class ImageFile extends MediaFile
|
|||||||
protected function resizeToFile(string $outpath, array $box) : string
|
protected function resizeToFile(string $outpath, array $box) : string
|
||||||
{
|
{
|
||||||
$old_limit = ini_set('memory_limit', common_config('attachments', 'memory_limit'));
|
$old_limit = ini_set('memory_limit', common_config('attachments', 'memory_limit'));
|
||||||
$image_src = null;
|
|
||||||
switch ($this->type) {
|
try {
|
||||||
case IMAGETYPE_GIF:
|
$img = Image::make($this->filepath);
|
||||||
$image_src = imagecreatefromgif($this->filepath);
|
} catch (Exception $e) {
|
||||||
break;
|
common_log(LOG_ERR, __METHOD__ . ' ecountered exception: ' . print_r($e, true));
|
||||||
case IMAGETYPE_JPEG:
|
|
||||||
$image_src = imagecreatefromjpeg($this->filepath);
|
|
||||||
break;
|
|
||||||
case IMAGETYPE_PNG:
|
|
||||||
$image_src = imagecreatefrompng($this->filepath);
|
|
||||||
break;
|
|
||||||
case IMAGETYPE_BMP:
|
|
||||||
$image_src = imagecreatefrombmp($this->filepath);
|
|
||||||
break;
|
|
||||||
case IMAGETYPE_WBMP:
|
|
||||||
$image_src = imagecreatefromwbmp($this->filepath);
|
|
||||||
break;
|
|
||||||
case IMAGETYPE_XBM:
|
|
||||||
$image_src = imagecreatefromxbm($this->filepath);
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
// TRANS: Exception thrown when trying to resize an unknown file type.
|
// TRANS: Exception thrown when trying to resize an unknown file type.
|
||||||
throw new Exception(_m('Unknown file type'));
|
throw new Exception(_m('Unknown file type'));
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($this->rotate != 0) {
|
|
||||||
$image_src = imagerotate($image_src, $this->rotate, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
$image_dest = imagecreatetruecolor($box['width'], $box['height']);
|
|
||||||
|
|
||||||
if ($this->type == IMAGETYPE_PNG || $this->type == IMAGETYPE_BMP) {
|
|
||||||
$transparent_idx = imagecolortransparent($image_src);
|
|
||||||
|
|
||||||
if ($transparent_idx >= 0 && $transparent_idx < 255) {
|
|
||||||
$transparent_color = imagecolorsforindex($image_src, $transparent_idx);
|
|
||||||
$transparent_idx = imagecolorallocate(
|
|
||||||
$image_dest,
|
|
||||||
$transparent_color['red'],
|
|
||||||
$transparent_color['green'],
|
|
||||||
$transparent_color['blue']
|
|
||||||
);
|
|
||||||
imagefill($image_dest, 0, 0, $transparent_idx);
|
|
||||||
imagecolortransparent($image_dest, $transparent_idx);
|
|
||||||
} elseif ($this->type == IMAGETYPE_PNG) {
|
|
||||||
imagealphablending($image_dest, false);
|
|
||||||
$transparent = imagecolorallocatealpha($image_dest, 0, 0, 0, 127);
|
|
||||||
imagefill($image_dest, 0, 0, $transparent);
|
|
||||||
imagesavealpha($image_dest, true);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
imagecopyresampled(
|
|
||||||
$image_dest,
|
|
||||||
$image_src,
|
|
||||||
0,
|
|
||||||
0,
|
|
||||||
$box['x'],
|
|
||||||
$box['y'],
|
|
||||||
$box['width'],
|
|
||||||
$box['height'],
|
|
||||||
$box['w'],
|
|
||||||
$box['h']
|
|
||||||
);
|
|
||||||
|
|
||||||
if ($this->filepath === $outpath) {
|
if ($this->filepath === $outpath) {
|
||||||
@unlink($outpath);
|
@unlink($outpath);
|
||||||
}
|
}
|
||||||
|
|
||||||
$type = $this->preferredType();
|
if ($this->rotate != 0) {
|
||||||
|
$img = $img->orientate();
|
||||||
|
}
|
||||||
|
|
||||||
|
$img->crop($box['width'], $box['height'], $box['x'], $box['y']);
|
||||||
|
|
||||||
|
// Ensure we save in the correct format and allow customization based on type
|
||||||
|
$type = $this->preferredType();
|
||||||
switch ($type) {
|
switch ($type) {
|
||||||
case IMAGETYPE_GIF:
|
case IMAGETYPE_GIF:
|
||||||
imagegif($image_dest, $outpath);
|
$img->save($outpath, 100, 'gif');
|
||||||
|
break;
|
||||||
|
case IMAGETYPE_PNG:
|
||||||
|
$img->save($outpath, 100, 'png');
|
||||||
break;
|
break;
|
||||||
case IMAGETYPE_JPEG:
|
case IMAGETYPE_JPEG:
|
||||||
imagejpeg($image_dest, $outpath, common_config('image', 'jpegquality'));
|
$img->save($outpath, common_config('image', 'jpegquality'), 'jpg');
|
||||||
break;
|
|
||||||
case IMAGETYPE_PNG:
|
|
||||||
imagepng($image_dest, $outpath);
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
// TRANS: Exception thrown when trying resize an unknown file type.
|
// TRANS: Exception thrown when trying resize an unknown file type.
|
||||||
throw new Exception(_m('Unknown file type'));
|
throw new Exception(_m('Unknown file type'));
|
||||||
}
|
}
|
||||||
|
|
||||||
imagedestroy($image_src);
|
$img->destroy();
|
||||||
imagedestroy($image_dest);
|
|
||||||
ini_set('memory_limit', $old_limit); // Restore the old memory limit
|
ini_set('memory_limit', $old_limit); // Restore the old memory limit
|
||||||
|
|
||||||
return $outpath;
|
return $outpath;
|
||||||
|
Loading…
Reference in New Issue
Block a user