in reply to Re^2: Testing image output
in thread Testing image output

It won't work as written. Neither coders nor decoders are stable.

Does your module (can't find it on CPAN) inherit from GD (judging by width/height/jpeg methods)? It doesn't matter in the end, I only hope you force it to treat jpegs as truecolor on open, because it doesn't despite whatever its doco says. If GD converts jpeg to palette, it will be even more mess to add to description below -- looks like GD tunes this algo (true to palette quantization) more frequently, then no need to go as far back as 5.010 to demonstrate.

Frog is frog

use strict; use warnings; use feature 'say'; use GD; use Digest::MD5 'md5_hex'; say $^V; say $GD::VERSION; my $f = 'frog.jpg'; GD::Image-> trueColor( 1 ); my $i = GD::Image-> new( $f ); say "Image is ", ( $i-> isTrueColor ? '' : 'not ' ), 'truecolor'; printf "RGB triplet for 0,0 pixel is: %3\$d, %2\$d, %1\$d\n", unpack 'C3', pack 'L', $i-> getPixel( 0, 0 ); __END__ v5.32.1 2.76 Image is truecolor RGB triplet for 0,0 pixel is: 0, 248, 231 v5.10.1 2.44 Image is truecolor RGB triplet for 0,0 pixel is: 0, 247, 231

Blame ancient GD version? But

>convert frog.jpg -format "%[pixel:u.p{0,0}]\n" info: srgb(0,247,231)

I'd say lossy codecs are murky waters and avoid them in tests:

>convert frog.jpg frog.png

use strict; use warnings; use feature 'say'; use GD; use Digest::MD5 'md5_hex'; say $^V; say $GD::VERSION; my $f = 'frog.png'; GD::Image-> trueColor( 1 ); my $i = GD::Image-> new( $f ); say "Image is ", ( $i-> isTrueColor ? '' : 'not ' ), 'truecolor'; say md5_hex( $i-> png() ); __END__ v5.32.1 2.76 Image is truecolor 1b6edecaa6d0b67f7bf960113f2136c7 v5.16.3 2.49 Image is truecolor 9edf3f9e11991f2dcfd77a7e1ffbafe8

Eh? What's the matter now? My first thought was zlib tunes its compression algo (despite same "level" 0..10), but it's not the reason for difference above -- though I strongly suspect it can influence the result for some input other than puny frog. But, above, it's just pHYs chunk that libpng decides to include from some version on.

Then, what it all amounts to -- try stable (read: "obsolete") lossless coder with uncompressed output (GD can't dump raw pixels, unfortunately), short of enumerating pixels one by one and adding RGB to string. Hopefully it's OK now:

use strict; use warnings; use feature 'say'; use GD; use Digest::MD5 'md5_hex'; say $^V; say $GD::VERSION; my $f = 'frog.png'; GD::Image-> trueColor( 1 ); my $i = GD::Image-> new( $f ); say "Image is ", ( $i-> isTrueColor ? '' : 'not ' ), 'truecolor'; say md5_hex( $i-> gd() ); __END__ v5.32.1 2.76 Image is truecolor e60c6afd7eefe80050d6af4488457281 v5.16.3 2.49 Image is truecolor e60c6afd7eefe80050d6af4488457281 v5.10.1 2.44 Image is truecolor e60c6afd7eefe80050d6af4488457281

Replies are listed 'Best First'.
Re^4: Testing image output
by Bod (Parson) on Sep 08, 2023 at 23:17 UTC
    Neither coders nor decoders are stable

    Do you mean the hashing coder/decoder or the image format?

    Does your module (can't find it on CPAN) inherit from GD (judging by width/height/jpeg methods)?

    Yes, it does use GD. It doesn't inherit from it.

    You can't find it on CPAN because it is still in development release. Although the module works under all visual testing, I wanted to get it working with a complete test suite before releasing it publicly.

    Yes, the module does use GD::Image-> trueColor( 1 ); and the tests specify $new->jpeg(50) rather than leaving GD to choose the best compression (whatever that means) as the docs say it does. I stayed away from PNG as I know that the exact behaviour of that depends on how GD was built, something that will vary on target machines.

    I hadn't thought of using a GD object to perform the comparison...obvious really...thanks...

      GD image file format[1] is not an "object", just dumb data stored externally, same as PNG, JPG, TIF, etc. I now see the module on CPAN. Not sure if it's worth re-iterating, what I suggested was no JPGs in t folder, because same image file can't be expected to decode to same data. Neither $new->jpeg(50) is reliable:

      v5.32.1 2.76 d0116830c00ed65dbebfd53afec1dcd0 v5.16.3 2.49 a26bc180a0f0067e00788dee47975324

      for CoventryCathedral.jpg source, because (1) comment segments are

      CREATOR: gd-jpeg v1.0 (using IJG JPEG v90), quality = 50 CREATOR: gd-jpeg v1.0 (using IJG JPEG v80), quality = 50

      respectively, and (2) APP0 segment stores aspect ratio for the former, vs. dots-per-inch resolution for the latter, for no obvious reason. +Of course I meant image coders/decoders.

      1: https://libgd.github.io/manuals/2.3.3/files/gd_gd-c.html