Я пытаюсь реализовать предоставленный пользователем пример кода в руководстве по PHP, но он не работает, как ожидалось - PullRequest
0 голосов
/ 01 июля 2019

Я пытаюсь реализовать код, предоставленный killing_wombles0000 (8 лет назад) на этой странице руководства по PHP: https://www.php.net/manual/en/function.imagecopymerge.php Проблема в том, что в коде есть ошибки / неожиданное поведение (например, $ aне определено) Это вроде работает, однако зеркальное изображение становится белым, и я хочу, чтобы оно стало черным.Когда я делаю то, что считаю необходимыми изменениями, я не могу заставить их делать то, что я хочу.В коде слишком много новых для меня функций изображения, и я не могу понять, как они работают вместе.

Я потратил целый день, читая каждую функцию, пытаясь работать логическичерез код, комментируя части, меняя цвета прозрачности и вообще цепляясь за соломинку.Я думал, что изменение 255,255,255, где бы оно ни происходило, на 0,0,0, затушевывает зеркальное изображение до черного.Как наивно с моей стороны;)

Это код, предоставленный пользователем на этой странице руководства по PHP:

$in = imagecreatefromjpeg('C:\test.jpg');
$reflection_strength = 120;        //    starting transparency (0-127, 0 being opaque)
$reflection_height = 40;        //     height of reflection in pixels
$gap = 10;                        //    gap between image and reflection

$orig_height = imagesy($in);                                //    store height of original image
$orig_width = imagesx($in);                                    //    store height of original image
$output_height = $orig_height + $reflection_height + $gap;    //    calculate height of output image

// create new image to use for output. fill with transparency. ALPHA BLENDING MUST BE FALSE
$out = imagecreatetruecolor($orig_width, $output_height);
imagealphablending($out, false);
$bg = imagecolortransparent($out, imagecolorallocatealpha($out, 255, 255, 255, 127));
imagefill($out, 0, 0, $bg);
imagefilledrectangle($out, 0, 0, imagesx($in), imagesy($in), $bg1);

// copy original image onto new one, leaving space underneath for reflection and 'gap'
imagecopyresampled ( $out , $in , 0, 0, 0, 0, imagesx($in), imagesy($in), imagesx($in), imagesy($in));

 // create new single-line image to act as buffer while applying transparency
$reflection_section = imagecreatetruecolor(imagesx($in), 1);
imagealphablending($reflection_section, false);
$bg1 = imagecolortransparent($reflection_section, imagecolorallocatealpha($reflection_section, 255, 255, 255, 127));
imagefill($reflection_section, 0, 0, $bg1);

// 1. copy each line individually, starting at the 'bottom' of the image, working upwards.
// 2. set transparency to vary between reflection_strength and 127
// 3. copy line back to mirrored position in original
for ($y = 0; $y<$reflection_height;$y++)
{   
    $t = ((127-$reflection_strength) + ($reflection_strength*($y/$reflection_height)));
    imagecopy($reflection_section, $out, 0, 0, 0, imagesy($in)  - $y, imagesx($in), 1);
    imagefilter($reflection_section, IMG_FILTER_COLORIZE, 0, 0, 0, $t);
    imagecopyresized($out, $reflection_section, $a, imagesy($in) + $y + $gap, 0, 0, imagesx($in) - (2*$a), 1, imagesx($in), 1);
}

// output image to view
header('Content-type: image/png');
imagesavealpha($out,true);
imagepng($out);

Установка $ a в 0 до входа в цикл устраняет ошибку.

1 Ответ

1 голос
/ 01 июля 2019

Кажется, в найденном вами коде есть несколько ошибок.

  1. $bg1 не определено для основного выходного изображения.Я изменил $bg1 на $bg в imagefilledrectangle.
  2. $a не определено.Я изменил ссылки на $a на ноль, так как он ссылается на координату "x", и нам нужна вся ширина изображения, от нуля до полной ширины.

Отражающая часть исчезаетпрозрачным.Так как цвет страницы белый, изображение выглядит как выцветшее до белого.Если вы хотите перейти в черный цвет вместо прозрачного, я предлагаю оставить режим смешивания по умолчанию, чтобы цвет фона просвечивал, и установить цвет фона на черный:

//imagealphablending($out, false);
//$bg = imagecolortransparent($out, imagecolorallocatealpha($out, 255, 255, 255, 127));
$bg = imagecolorallocatealpha($out, 0,0,0,0);

Для справки см. imagealphablending .

Вот пример:

$in = imagecreatefromjpeg('https://picsum.photos/id/1084/536/354?grayscale');
$reflection_strength = 127;        //    starting transparency (0-127, 0 being opaque)
$reflection_height = 40;        //     height of reflection in pixels
$gap = 0;                        //    gap between image and reflection

$orig_height = imagesy($in);                                //    store height of original image
$orig_width = imagesx($in);                                    //    store height of original image
$output_height = $orig_height + $reflection_height + $gap;    //    calculate height of output image

// create new image to use for output. fill with BLACK.
$out = imagecreatetruecolor($orig_width, $output_height);
//imagealphablending($out, false);
//$bg = imagecolortransparent($out, imagecolorallocatealpha($out, 255, 255, 255, 127));
$bg = imagecolorallocatealpha($out, 0,0,0,0);
imagefill($out, 0, 0, $bg);
imagefilledrectangle($out, 0, 0, imagesx($in), imagesy($in), $bg);

// copy original image onto new one, leaving space underneath for reflection and 'gap'
imagecopyresampled ( $out , $in , 0, 0, 0, 0, imagesx($in), imagesy($in), imagesx($in), imagesy($in));

 // create new single-line image to act as buffer while applying transparency
$reflection_section = imagecreatetruecolor(imagesx($in), 1);
imagealphablending($reflection_section, false);
$bg1 = imagecolortransparent($reflection_section, imagecolorallocatealpha($reflection_section, 255, 255, 255, 127));
imagefill($reflection_section, 0, 0, $bg1);

// 1. copy each line individually, starting at the 'bottom' of the image, working upwards.
// 2. set transparency to vary between reflection_strength and 127
// 3. copy line back to mirrored position in original
for ($y = 0; $y<$reflection_height;$y++)
{
    $t = ((127-$reflection_strength) + ($reflection_strength*($y/$reflection_height)));
    imagecopy($reflection_section, $out, 0, 0, 0, imagesy($in)  - $y, imagesx($in), 1);
    imagefilter($reflection_section, IMG_FILTER_COLORIZE, 0, 0, 0, $t);
    imagecopyresized($out, $reflection_section, 0, imagesy($in) + $y + $gap, 0, 0, imagesx($in) - 0, 1, imagesx($in), 1);
}

// output image to view
header('Content-type: image/png');
imagesavealpha($out,true);
imagepng($out);

Запуск на PHPFiddle

...