Search code examples
perlpnggd

Perl GD module PNG image corrupt or cant open


I am running Windows 10 and I've installed Perl v5.26.1, built for MSWin32-x64-multithread. Binary build 2601 [404865] provided by ActiveState.

My problem is I want to use the GD::Graph.

Everything looked fine. I wrote a code and did a syntax check and everything was fine. When I run the script all I get is nonsense though. I tried outputting to *.png file instead, but the file is corrupt.

This is driving me bonkers. What am I doing wrong here? Any help would be much appreciated. The following is the code

#!usr/bin/perl -w
use strict;
use GD::Graph::area;
# File: prob1.pl

my @x = (0, 0, 0.00759, 0.018975, 0.036053, 0.216319, 0.449715, 0.648956, 
0.815939, 0.935484, 1);
my @y = (0, 0.053763, 0.16129, 0.308244, 0.577061, 0.792115, 0.874552, 
0.924731, 0.964158, 0.989247, 1);

my @data = (\@x, \@y);

my $graph = GD::Graph::area->new(500, 300);

$graph->set( x_label=>'False Positive Rate', y_label=>'True Positive 
Rate',title=>'ROC Curve') or warn $graph->error;

my $image = $graph->plot(\@data) or die $graph->error;

open IMG, ">prob1.png" or die "can't open prob1.png\n";
print IMG $image->png;
exit;

Solution

  • By default, the Windows version of Perl opens files in crlf mode (replacing each new line in an output stream with carriage return + new line). You don't want this to happen to your png stream, so you need to tell Perl to use raw mode (output raw bytes).

    open IMG, ">:raw", "prob1.png";
    

    is one way to do that.

    open IMG, ">", "prob1.png";
    binmode IMG;
    

    is another. Both the GD and GD::Graph documentation calls attention to the need for binmode several times.