Операции с прозрачными изображениями

  • Автор темы Андрей Усачёв
  • Дата начала

Андрей Усачёв

Guest
Операции с прозрачными изображениями

Не получается сделать следующее:
1) Создать True Color изображение с прозрачностью.
2) Наложить на него два промасштабированных GIF-а, у которых есть прозрачные области.
3) Наложить текст.
4) Сохранить с оптимальной палитрой в GIF, выделив цвет для сохранения прозрачности.

Не получается даже просто создать прозрачное True Color изображение, чтобы потом сохранить его в прозрачный GIF. Как я не заливал его после создания прозрачным цветом, всё равно сохраняется непрозрачный чёрный GIF.

PS: Сразу хочу предупредить, что на этапе создания, пока картинка ещё хранится в True Color, я не хочу выделять какое-либо сочетание RGB для прозрачного цвета, ведь для этого есть альфа-канал, судя по документации.

PHP:
<?
$img = ImageCreateTrueColor(123, 123);
// ...
// Что бы я тут ни делал...
$ovl = ImageCreateFromGIF('example.gif');
ImageCopyMerge($img, $ovl, 0, 0, 0, 0, 123, 123, 100);
header("Content-Type: image/gif");
ImageGIF($img);
// ...всё равно картинка example.gif накладывается на чёрный фон! :-(
?>
 

Андрей Усачёв

Guest
Это не о том.

Во-первых, у меня нету отдельного изображения с альфа-каналом картинки (допустим, прозрачные изображения в формате PNG-24 пользователь закачивает в базу данных).

Во-вторых, попиксельная обработка медленна. Мне почему-то кажется, что можно обойтись стандартными функциями.

Сейчас для меня задача-минимум:
1) Создать прозрачную True Type картинку, не выделяя для прозрачности отдельный цвет.
2) Сохранить её в GIF с 256-цветной палитрой, не теряя прозрачность.
 

Андрей Усачёв

Guest
Я всё уже решил с помощью стандартных функций и вывода в PNG.
 

Андрей Усачёв

Guest
Да пожалуйсто! :)

PHP:
<?
	$BACKGROUND_FILE_NAME = 'background.gif';
	$FOREGROUND_FILE_NAME = 'foreground.gif';
	$SMALL_WIDTH = 400;

	$k = 0.5; // Коэффициент расположения картинки относительно фона, меняется от 0.000 до 1.000
	$text = 'Sample text';

	// Считываем фон
	$bg = ImageCreateFromGIF($BACKGROUND_FILE_NAME);
	$bg_w = ImageSX($bg);
	$bg_h = ImageSY($bg);

	// Считываем картинку
	$fg = ImageCreateFromGIF($FOREGROUND_FILE_NAME);
	$fg_w = ImageSX($fg);
	$fg_h = ImageSY($fg);

	// Создаём прозрачный холст
	$big = ImageCreateTrueColor($bg_w, $bg_h);
	ImageAlphaBlending($big, false);
	$t = ImageColorAllocateAlpha($big, 255, 0, 255, 127);
	ImageFilledRectangle($big, 0, 0, $bg_w - 1, $bg_h - 1, $t);

	// Копируем фон на холст
	ImageCopy($big, $bg, 0, 0, 0, 0, $bg_w, $bg_h);

	// Копируем картинку на холст (расположение по горизонтали задаётся коэффициентом $k, по вертикали картинка центруется)
	ImageCopy($big, $fg, ($bg_w - $fg_w) * $k, ($bg_h -  $fg_h) / 2, 0, 0, $fg_w, $fg_h);

	// Вычисляем размер уменьшенной копии
	$w = $SMALL_WIDTH;
	$h = $w * $bg_h / $bg_w;

	// Создаём уменьшенный холст
	$small = ImageCreateTrueColor($w, $h);
	ImageAlphaBlending($small, false);
	$t = ImageColorAllocateAlpha($small, 255, 0, 255, 127);
	ImageFilledRectangle($small, 0, 0, $w - 1, $h - 1, $t);

	// Копируем с большого холста на уменьшенный
	ImageCopyResampled($small, $big, 0, 0, 0, 0, $w, $h, $bg_w, $bg_h);

	// Добавляем текст
	$font = ImageLoadFont ('myfont.phpfont');
	$black = ImageColorAllocate($small, 0, 0, 0);

	ImageString($small, $font,
		($w - ImageFontWidth($font) * strlen($text)) / 2,
		$h - ImageFontHeight($font),
		$text, $black);

	// Создаём уменьшенный холст с ограниченным количеством цветов
	$palette = ImageCreate($w, $h);

	// ImageColorMatch($small, $palette); // Эта функция создаёт недостаточно качественную палитру. :-(
	// Поэтому мне приходится копировать палитру из файла с приблизительно таким же содержанием, предварительно созданного в программе Adobe Photoshop
	$example = ImageCreateFromGIF('example.gif');
	ImagePaletteCopy($palette, $example);

	// Копируем полноцветное изображение на холст с ограниченным количеством цветов
	ImageCopyResampled($palette, $small, 0, 0, 0, 0, $w, $h, $w, $h);

	// Выдаём клиенту файл с палитрой
	header("Content-Type: image/png");
	ImagePNG($palette);
?>
ПРИМЕР.

Исходные картинки:



Файл с палитрой:


Результат:


К сожалению, этот форум не форматирует как картинки файлы с расширением "php". :)
 
Сверху