dragonchild has asked for the wisdom of the Perl Monks concerning the following question:

I'm trying to use GD to make some composite images. However, when I try to print the pictures out, the resultant image loses some sharpness that existed in the originals. I've isolated it down to the following test case:
use GD; my $x = GD::Image->new('start.png'); open OUT, '>end.png'; print OUT $x->png(0); # Use least compression # Or ... use GD; my $x = GD::Image->new('start.jpeg'); open OUT, '>end.jpeg'; print OUT $x->jpeg(100); # Use best quality

When I use a program to view the images on Windows and zoom in, the background is mottled. (Neighboring pixels are different shades of the same color.) This also causes previously sharp borders between a picture and the background to be ... well ... merged (in terms of colors).

It seems to be that GD (and libgd) seem to be changing the image. I've used GD's compare() method and it says the images are the same. But, zooming in shows they're different.

Does anyone have any suggestions for this?

------
We are the carpenters and bricklayers of the Information Age.

The idea is a little like C++ templates, except not quite so brain-meltingly complicated. -- TheDamian, Exegesis 6

... strings and arrays will suffice. As they are easily available as native data types in any sane language, ... - blokhead, speaking on evolutionary algorithms

Please remember that I'm crufty and crochety. All opinions are purely mine and all code is untested, unless otherwise specified.

Replies are listed 'Best First'.
Re: GD question
by BrowserUk (Patriarch) on Nov 09, 2003 at 21:47 UTC

    The problem is most likely in the application that you are using to do the zooming.


    Examine what is said, not who speaks.
    "Efficiency is intelligent laziness." -David Dunham
    "Think for yourself!" - Abigail
    Hooray!
    Wanted!

      I agree with BrowserUK that because the image viewing software is trying to reduce the blockiness/pixelation of the image after zoom, by interpolating the 'missing' pixels after zoom using some interpolation algorithm based on neibouring pixels. This technique is generally Ok if not best for reducing the pixelation for photographs but not good at preserving sharp edges.

      By the sound of it you probably don't want to enlarge an image physically. But if you do, you need a different image magnification algorithm all together to preserve the sharpness in the edges.

      PS. There is a commercial product on Windows called S-Spline from Shortcut, which uses the company's S-Spline algorithm. I have tested the program and I was impressed by the quality of the enlarged image.

Re: GD question
by hossman (Prior) on Nov 10, 2003 at 00:40 UTC

    You may want to check the details of your source PNG, and your version of GD. PNG files can either be truecolor, or have a 256 color palette. GD only started supporting the output of paletteless PNGs as of v2.0.

    Even if you have GD 2.0, you probably want to call GD::Image->trueColor(1) before constructing the object, either that or use GD::Image->newFromPng($file,1)

Re: GD question
by jonadab (Parson) on Nov 10, 2003 at 01:41 UTC

    Are you really losing quality on PNGs? Or did you notice the quality loss on JPGs and assume it was a problem with your script? It's normal to lose quality on each save with JPG, because the format uses lossy compression, but that shouldn't happen with PNG.


    $;=sub{$/};@;=map{my($a,$b)=($_,$;);$;=sub{$a.$b->()}} split//,".rekcah lreP rehtona tsuJ";$\=$ ;->();print$/
Re: GD question
by bradcathey (Prior) on Nov 10, 2003 at 03:58 UTC
    I have seen, and commented on here in the monastery, this same poor quality optimization in GD you describe. My images have all been JPGs, but no matter how I set the optimation, the result is as you described.

    I tested this by "Saving for Web" in Photoshop and then viewing the two images side by side in my browser. The difference is striking. The only thing I can attribute it to is the optimization algorithms used by GD.

    I would love to see the difference Image::Magick makes doing the same thing, but my web host does not support it.

    I'd hate to think that this is the best GD can do. I've got my fingers crossed hoping some monkish guru will have a solution.

    —Brad
    "A little yeast leavens the whole dough."
Re: GD question
by waswas-fng (Curate) on Nov 09, 2003 at 23:01 UTC
    best quality jpg and least compression png are still making a copy of a copy you lose quality every-time you re-compress the images. Try using a non-compreses starting image and see what happens.


    -Waswas
      best quality jpg and least compression png are still making a copy of a copy

      I was under the impression that PNGs use lossless compression?

        PNG is in fact lossless like gif, but you can turn down truecolor to 8Bit pallet. You could try using $image = GD::Image->newFromPng($file, [$truecolor]).
        The truecolor switch is new in GD 2.11, look here for more new things.