Водяные знаки на изображениях в OpenCart

Как добавить водяной знак к изображениям в OpenCart?

Возможно, этот вопрос беспокоит многих владельцев интернет магазинов. В особенности тех, кто тратит много времени и/или денег на съёмку и подготовку изображений своего товара.
И мне, как программисту, пришлось столкнуться с этой задачей. Итак, что нужно было сделать:
  • Добавить возможность наложения водяных знаков (watermark) для определённых изображений.

В данном случае — для больших изображений. Накладывать водяной знак «watermark» на изображения с маленькими размерами мы не видим смысла (маленькие изображения никто не будет воровать, а даже если и да, то он не читается на них всё равно).

Приступим к реализации! Хочу сразу заметить, что магазин в котором я это делал сильно отличается от стандартного OpenCart-овского и код я буду приводить небольшими примерами, чтоб показать общую идеологию.

Встроенная функциональность
В OpenCart есть уже функция для создания watermark, но она не работает (А потому немного изменим её)

Находим файл — /system/library/image.php, и вносим изменения в функцию
public function watermark($file, $position = 'bottomright')
строки инициализации $watermark.
Заменим
$watermark = $this->create($file);
на
//$watermark = $this->create($file);
$watermark = imagecreatefrompng($file);

Так же внизу функции нужно поменять
imagecopy($this->image, $watermark, $watermark_pos_x, $watermark_pos_y, 0, 0, 120, 40);
на
imagecopy($this->image, $watermark, $watermark_pos_x, $watermark_pos_y, 0, 0, $watermark_width, $watermark_height);

В результате получи такую функцию (можно просто заменить свою кодом ниже)
public function watermark($file, $position = 'bottomright') {
        //$watermark = $this->create($file);
        $watermark = imagecreatefrompng($file);

        $watermark_width = imagesx($watermark);
        $watermark_height = imagesy($watermark);

        switch ($position) {
            case 'topleft':
                $watermark_pos_x = 0;
                $watermark_pos_y = 0;
                break;
            case 'topright':
                $watermark_pos_x = $this->info['width'] - $watermark_width;
                $watermark_pos_y = 0;
                break;
            case 'bottomleft':
                $watermark_pos_x = 0;
                $watermark_pos_y = $this->info['height'] - $watermark_height;
                break;
            case 'bottomright':
                $watermark_pos_x = $this->info['width'] - $watermark_width;
                $watermark_pos_y = $this->info['height'] - $watermark_height;
                break;
        }

        imagecopy($this->image, $watermark, $watermark_pos_x, $watermark_pos_y, 0, 0, $watermark_width, $watermark_height);

        imagedestroy($watermark);
    }


Добавим водяной знак в функцию изменения размера изображения OpenCart
Находим файл модели — /catalog/model/tool/image.php
В файле находим функцию, которая отвечает за изменение размеров изображений
public function resize($filename, $width, $height)

И расширяем её возможности:
добавим в описание функции параметр определяющий накладывать водяной знак или нет $watermark = FALSE, получим
public function resize($filename, $width, $height, $watermark = FALSE)
а в фрагмент
if ($width_orig != $width || $height_orig != $height) {
      $image = new Image(DIR_IMAGE . $old_image);
      $image->resize($width, $height);
      $image->save(DIR_IMAGE . $new_image);
} else {
      copy(DIR_IMAGE . $old_image, DIR_IMAGE . $new_image);
}
после изменения размеров изображения ($image->resize($width, $height);), добавим код
if ($watermark) {
        $image->watermark(DIR_IMAGE . 'watermark.png', 'bottomleft');
}//if

Получаем такую функцию
public function resize($filename, $width, $height, $watermark = FALSE) {
        if (!file_exists(DIR_IMAGE . $filename) || !is_file(DIR_IMAGE . $filename)) {
            return;
        }

        $info = pathinfo($filename);
        $extension = $info['extension'];

        $old_image = $filename;
        $new_image = 'cache/' . utf8_substr($filename, 0, utf8_strrpos($filename, '.')) . '-' . $width . 'x' . $height . '.' . $extension;

        if (!file_exists(DIR_IMAGE . $new_image) || (filemtime(DIR_IMAGE . $old_image) > filemtime(DIR_IMAGE . $new_image))) {
            $path = '';

            $directories = explode('/', dirname(str_replace('../', '', $new_image)));

            foreach ($directories as $directory) {
                $path = $path . '/' . $directory;

                if (!file_exists(DIR_IMAGE . $path)) {
                    @mkdir(DIR_IMAGE . $path, 0777);
                }
            }

            list($width_orig, $height_orig) = getimagesize(DIR_IMAGE . $old_image);

            if ($width_orig != $width || $height_orig != $height) {
                $image = new Image(DIR_IMAGE . $old_image);
                $image->resize($width, $height);
                if ($watermark) {
                    $image->watermark(DIR_IMAGE . 'watermark.png', 'bottomleft');
                }//if
                $image->save(DIR_IMAGE . $new_image);
            } else {
                copy(DIR_IMAGE . $old_image, DIR_IMAGE . $new_image);
            }
        }

        if (isset($this->request->server['HTTPS']) && (($this->request->server['HTTPS'] == 'on') || ($this->request->server['HTTPS'] == '1'))) {
            return HTTPS_IMAGE . $new_image;
        } else {
            return HTTP_IMAGE . $new_image;
        }
    }


Теперь, вызывая функцию для изменения размеров изображений, нам достаточно последний параметр задать TRUE и водяной знак будет автоматически наложен.

Чуть не забыл!
Файл изображения водяного знака необходимо залить в папку /image/watermark.png (прозрачность сохраняется)
  • +2
  • 23 ноября 2012, 16:28
  • igorrius

Комментарии (10)

RSS свернуть / развернуть
То что нужно!!!
+1
Спасибо! Я старался)
0
комментарий был удален
комментарий был удален
комментарий был удален
Вот глупость спрошу)) Но я не вкурил что то
Где это?
«Теперь, вызывая функцию для изменения размеров изображений, нам достаточно последний параметр задать TRUE и водяной знак будет автоматически наложен.»
Ткните носом где эта функция вызываеся
0
Функция resize() (обычно в вызове так $this->model_tool_image->resize(...)) вызывается в контроллерах вывода. Например в контроллере вывода товара.
catalog/controller/product/product.php
0
Очень нужная модификация, но не совсем понятно как всё таки вывести водяной знак в карточке товара например, не могли бы вы показать код в контроллере или product.tpl где именно и как этот параметр объявить?
0
Ответ в комментария чуть выше…
Контроллер catalog/controller/product/product.php
Находите строчку вызова метода $this->model_tool_image->resize (прямо так скопируйте и ищите в файле).

Пример:
if ($product_info['image']) {
    $this->data['popup'] = $this->model_tool_image->resize($product_info['image'], $this->config->get('config_image_popup_width'), $this->config->get('config_image_popup_height'), true);
} else {
    $this->data['popup'] = '';
}
0
Спасибо огромное!
+1
Только зарегистрированные и авторизованные пользователи могут оставлять комментарии.
comments powered by Disqus