Warning: Cannot use a scalar value as an array in /home/admin/public_html/forum/include/fm.class.php on line 757

Warning: Invalid argument supplied for foreach() in /home/admin/public_html/forum/include/fm.class.php on line 770

Warning: Invalid argument supplied for foreach() in /home/admin/public_html/forum/topic.php on line 737
Форумы портала PHP.SU :: Upload и сжатие изображений

 PHP.SU

Программирование на PHP, MySQL и другие веб-технологии
PHP.SU Портал     На главную страницу форума Главная     Помощь Помощь     Поиск Поиск     Поиск Яндекс Поиск Яндекс     Вакансии  Пользователи Пользователи


 Страниц (1): [1]   

> Без описания
Prizma
Отправлено: 07 Июля, 2016 - 03:00:39
Post Id



Посетитель


Покинул форум
Сообщений всего: 463
Дата рег-ции: Июнь 2012  
Откуда: Санкт-Петербург


Помог: 5 раз(а)




Тестирую модуль загрузки изображений на своем сайте и нащупал несколько неприятных звоночков:
1. При загрузке большого одноцветного PNG-изображения 2500х1700 на входе оно весит 20Кб, на выходе уменьшенная копия 150х100px весит 4Кб, а большая версия от оригинала отличается уже в 50-70 раз и переваливаем за 1МБ Хм и это с максимальной степенью сжатия, если не сжимать то переваливает за 13МБ... Пробывал использовать PNG_FILTER_ALL никак на размер не влияет.
2. При использовании степени сжатия 9 для png-изображений большие изображения грузятся секунд 15-20

PHP:
скопировать код в буфер обмена
  1. class ResizeImage
  2. {
  3.     const MAX_LARGE_WIDTH = 2600;
  4.     const MAX_LARGE_HEIGHT = 1600;
  5.     const MAX_ICON_WIDTH = 150;
  6.     const MAX_ICON_HEIGHT = 150;
  7.  
  8.     private $image;
  9.     private $imageType; // FALSE or jpg,gif,png
  10.     private $alpha;
  11.     private $originWidth;
  12.     private $originHeight;
  13.  
  14.     private $iconImage;
  15.     private $largeImage;
  16.  
  17.     public function __construct($imageName)
  18.     {
  19.         if (!$this->imageIdentification($imageName)) {
  20.             throw new \InvalidArgumentException('file can\'t be open as image[jpg,gif or png]');
  21.         }
  22.         $this->largeImage = $this->resizeImage(self::MAX_LARGE_WIDTH, self::MAX_LARGE_HEIGHT);
  23.         $this->iconImage = $this->resizeImage(self::MAX_ICON_WIDTH, self::MAX_ICON_HEIGHT);
  24.     }
  25.  
  26.     public function getLargeImage()
  27.     {
  28.         return $this->largeImage;
  29.     }
  30.  
  31.     public function getIconImage()
  32.     {
  33.         return $this->iconImage;
  34.     }
  35.  
  36.     public function getImageType()
  37.     {
  38.         return $this->imageType;
  39.     }
  40.  
  41.     public function getWidth()
  42.     {
  43.         return imagesx($this->largeImage);
  44.     }
  45.  
  46.     public function getHeight()
  47.     {
  48.         return imagesy($this->largeImage);
  49.     }
  50.  
  51.     public function saveImage($imageName, $icon = false) : bool
  52.     {
  53.         $image = $icon ? $this->getIconImage() : $this->getLargeImage();
  54.         $re = false;
  55.         switch ($this->imageType) {
  56.             case 'jpg':
  57.                 $re = imagejpeg($image, $imageName);
  58.                 break;
  59.             case 'png':
  60.                 $re = imagepng($image, $imageName, 9, PNG_ALL_FILTERS);
  61.                 break;
  62.             case 'gif':
  63.                 $re = imagegif($image, $imageName);
  64.                 break;
  65.         }
  66.         return $re;
  67.     }
  68.  
  69.     private function imageIdentification($imageName)
  70.     {
  71.         if ($image = @imagecreatefromjpeg($imageName)) {
  72.             $this->image = $image;
  73.             $this->imageType = 'jpg';
  74.             $this->alpha = false;
  75.         } elseif ($image = @imagecreatefrompng($imageName)) {
  76.             $this->image = $image;
  77.             $this->imageType = 'png';
  78.             $this->alpha = true;
  79.         } elseif ($image = @imagecreatefromgif($imageName)) {
  80.             $this->image = $image;
  81.             $this->imageType = 'gif';
  82.             $this->alpha = false;
  83.         } else {
  84.             return false;
  85.         }
  86.         $this->originWidth = imagesx($this->image);
  87.         $this->originHeight = imagesy($this->image);
  88.         return true;
  89.     }
  90.  
  91.     private function resizeImage($maxWidth, $maxHeight)
  92.     {
  93.         $k = max($this->originWidth / $maxWidth, $this->originHeight / $maxHeight);
  94.         if ($k <= 1) {
  95.             return $this->image;
  96.         }
  97.         $width = round($this->originWidth / $k);
  98.         $height = round($this->originHeight / $k);
  99.         $newImage = $this->createBaseImage($width, $height);
  100.         imagecopyresampled($newImage, $this->image,
  101.             0, 0, 0, 0,
  102.             $width,
  103.             $height,
  104.             $this->originWidth,
  105.             $this->originHeight);
  106.         return $newImage;
  107.     }
  108.  
  109.     private function createBaseImage(int $width, int $height)
  110.     {
  111.         $image = imagecreatetruecolor($width, $height);
  112.         imagesavealpha($image, $this->alpha);
  113.         $color = $this->alpha ? imagecolorallocatealpha($image, 0, 0, 0, 127) : imagecolorallocate($image, 255, 255, 255);
  114.         imagefill($image, 0, 0, $color);
  115.         return $image;
  116.     }
  117.  
  118. }

Может это дело как то можно оптимизировать? (для больших изображений сейчас буду переделывать сохранение оригинального изображения вместо полученного ресурса)
(Добавление)
Попровил сейв картинок png ... раз php с ними так работает думаю еще стоит добавить для png-картинок выходящих за допустимые размеры сообщение об ошибке
PHP:
скопировать код в буфер обмена
  1. public function saveImage($imageName, $icon = false) : bool
  2. {
  3.     $image = $icon ? $this->getIconImage() : $this->getLargeImage();
  4.     $re = false;
  5.     switch ($this->imageType) {
  6.         case 'jpg':
  7.             $re = imagejpeg($image, $imageName);
  8.             break;
  9.         case 'png':
  10.             if((imagesx($image) == $this->originWidth) && (imagesy($image) == $this->originHeight)) {
  11.                 if(copy($this->originImageName, $imageName)) {
  12.                     $re = true;
  13.                 }
  14.             }
  15.             if(!$re) {
  16.                 $re = imagepng($image, $imageName, 9);
  17.             }
  18.             break;
  19.         case 'gif':
  20.             $re = imagegif($image, $imageName);
  21.             break;
  22.     }
  23.     return $re;
  24. }
 
My status
 Top
Viper
Отправлено: 07 Июля, 2016 - 16:48:13
Post Id



Активный участник


Покинул форум
Сообщений всего: 4555
Дата рег-ции: Февр. 2007  
Откуда: Симферополь


Помог: 98 раз(а)




Imagick в помощь.


-----
Список фильмов с описанием, блекджеком и... для Joomla? -> https://киноархив[dot]com
Демо нового движка для сайта php.su -> php[dot]su, проект на гитхабе
 
 Top
Страниц (1): [1]
Сейчас эту тему просматривают: 0 (гостей: 0, зарегистрированных: 0)
« Вопросы новичков »


Все гости форума могут просматривать этот раздел.
Только зарегистрированные пользователи могут создавать новые темы в этом разделе.
Только зарегистрированные пользователи могут отвечать на сообщения в этом разделе.
 



Powered by PHP  Powered By MySQL  Powered by Nginx  Valid CSS  RSS

 
Powered by ExBB FM 1.0 RC1. InvisionExBB