#40158 [Opn]: Artifact left on transparent pngs using image filters
| From: | pajoye@php.net | Date: | Fri, 19 Jan 2007 12:02:41 +0000 |
| Subject: | #40158 [Opn]: Artifact left on transparent pngs using image filters | ||
| References: | 1 | Groups: | php.bugs |
| Request: | Send a blank email to php-bugs+get-107759@lists.php.net to get a copy of this message | ||
ID: 40158
Updated by: pajoye@php.net
Reported By: henus at mail dot ru
Status: Open
Bug Type: GD related
Operating System: Windows XP
PHP Version: 5.2.0
Assigned To: pajoye
New Comment:
Can you *PLEASE* confirm that it works when you disable alpha blending?
Answer should be Yes or No, I got the details already. I really do not
have the time to explain/ask again and again the same thing.
About imagefill, yes, that's a bug. Please open a new one if you like.
I will fix it as soon as possible.
Previous Comments:
------------------------------------------------------------------------
[2007-01-19 11:53:03] henus at mail dot ru
Yes, the is global problem with alphablending in libgd\gd.c
but about "imagealphablending($mask, false); //<<< Important!":
i absolutely should not care about ebabling\disabling
imagealphablending before imagefilter,
because of function shoud colorize image by new values of red,gree,blue
(!!!there is no alpha in parameters)
if IMG_FILTER_COLORIZE will have in parameters alpha,
if alphablending enable, value of alpha should allow for calculation of
new color values
(in gdImageColor it will before new_pxl =
gdImageColorAllocateAlpha(src, (int)r, (int)g, (int)b, a);)
and gdImageSetPixel shoul with disabled alphablending.
otherwise function work like merging of two images with alphablending.
where:
first image - source image from function parameters.
second image - correct colorized copy of source image.
it is not logically. it is incorrect.
another bug in imagefill:
this function not only fill image, it is also disable alphablending.
php example:
<?
/* first colorizing */
$im1=imagecreatetruecolor(1,1);
imagealphablending($im1, TRUE);
$c01=imagecolorallocatealpha($im1,255,0,0,63);
imagefill($im1,0,0,$c01);
$c01=imagecolorsforindex($im1,imagecolorat($im1,0,0));
imagefilter($im1, IMG_FILTER_COLORIZE, -255, 255, 0);
$c1=imagecolorsforindex($im1,imagecolorat($im1,0,0));
/* second colorizing */
$im2=imagecreatetruecolor(1,1);
imagealphablending($im2, TRUE);
$c02=imagecolorallocatealpha($im2,255,0,0,63);
imagefill($im2,0,0,$c02);
$c02=imagecolorsforindex($im1,imagecolorat($im1,0,0));
/* att!!! after imagefill another enabling alphablending */
imagealphablending($im2, TRUE);
imagefilter($im2, IMG_FILTER_COLORIZE, -255, 255, 0);
$c2=imagecolorsforindex($im2,imagecolorat($im2,0,0));
print"<br>before 1 - ";
print_r($c01);
print"<br>after 1 - ";
print_r($c1);
print"<br><br>before 2 - ";
print_r($c02);
print"<br>after 2 - ";
print_r($c2);
?>
results:
before 1- Array ( [red] => 255 [green] => 0 [blue] => 0 [alpha] => 63 )
after 1 - Array ( [red] => 0 [green] => 255 [blue] => 0 [alpha] => 63
)
before 2- Array ( [red] => 0 [green] => 255 [blue] => 0 [alpha] => 63 )
after 2 - Array ( [red] => 126 [green] => 128 [blue] => 0 [alpha] =>
31 )
where:
after 1 - correct result of IMG_FILTER_COLORIZE, because of imagefill
disable alphablending
after 2 - incorrect result of IMG_FILTER_COLORIZE, because of after
imagefill i manually enable alphablending
disabling alphablending in code it is good solutions for gdImageColor,
but after it is necessary to restore old value of alphaBlendingFlag.
------------------------------------------------------------------------
[2007-01-18 19:54:09] pajoye@php.net
"pixel from edge with coord (95,11) have wrong color.
red-98 green-98 blue-164 (why is red>0 and green>0 ????????? after
substracting 255???) (should be red-0 green-0 blue-102)"
It is blended over the destination pixel. You have to disable alpha
blending *before* the imagefilter call.
This image:
http://blog.thepimp.net/misc/bug40158_black_filtered_mask.png
shows exactly what you are trying to do (blue, black or purple, it
really does not matter), the script being:
$mask=imagecreatefrompng("40158.png");
imagealphablending($mask, false); //<<< Important!
imagefilter($mask, IMG_FILTER_COLORIZE, -255, -255, -255);
//<<< save alpha, so we see its value
imagesavealpha($mask, true);
imagepng($mask,"mask1.png");
Using your last example, the resulting image is like your
"result_correct3.png".
------------------------------------------------------------------------
[2007-01-18 19:37:49] henus at mail dot ru
it`s not solve my problem.... :(
first -
about blue color - look at my submission from
[18 Jan 11:03am UTC]
if use
imagefilter($mask, IMG_FILTER_COLORIZE, -255, -255, -255);
the result is
http://www.fort-ross.ru/henus/gd/result_incorrect.png
with legibly visible artefacts.
second -
image
http://blog.thepimp.net/misc/bug40158_result.png
also has artefacts at the adges...
pixel from edge with coord (95,11) have wrong color
red-98
green-98
blue-164
(why is red>0 and green>0 ????????? after substracting 255???)
(should be
red-0
green-0
blue-102)
third -
look at my submission from [18 Jan 5:56pm UTC]
why is 255-255=126????????????????
one more demo -
using
imagefilter($mask, IMG_FILTER_COLORIZE, -255, -255, 0);
mask - http://fort-ross.ru/henus/gd/mask3.png
incorrect image - http://fort-ross.ru/henus/gd/result_incorrect3.png
correct image - http://fort-ross.ru/henus/gd/result_correct3.png
------------------------------------------------------------------------
[2007-01-18 18:51:59] pajoye@php.net
(rgba(255,0,0,xxx)) should have been (rgba(0,0,255,xxx)) but you
noticed it :)
------------------------------------------------------------------------
[2007-01-18 18:51:04] pajoye@php.net
An absolute black image is not what you should expect.
imagefilter($mask, IMG_FILTER_COLORIZE, -255, -255, 0); will replace
the white color with blue (you remove all components but the blue):
http://blog.thepimp.net/misc/bug40158_filtered_mask.png
imagecopy($imagemain, $mask, 0, 0, 0, 0, $imagewidth, $imageheight);
will copy it over the $imagemain, the border of the quadrant will be
blended over black:
http://blog.thepimp.net/misc/bug40158_result.png
Each pixel in your circle are rgb(255,255,255) with some alpha value in
the edges (and only in the edges). You are substracting 255 to the R and
G component, the result is blue.
Now, take a look at this image:
http://blog.thepimp.net/misc/bug40158_correct_filtered_mask.png
It is what you are expecting (if I understand correctly your problem).
The edges of the circle have a blue color with various alpha values
(rgba(255,0,0,xxx)). You can reproduce it by disabling the alpha
blending mode in the mask image (imagealphablending($mask, false); ).
The alpha component will be kept and stored in the image instead of
being used as a blending value.
Let me know if that solves your problem.
By the way, COLORIZE uses gdImageColor. The lines you are referring to
are in the contrast function.
------------------------------------------------------------------------
The remainder of the comments for this report are too long. To view
the rest of the comments, please view the bug report online at
http://bugs.php.net/40158
--
Edit this bug report at http://bugs.php.net/?id=40158&edit=1