Skip to content

Commit

Permalink
add image loader tests
Browse files Browse the repository at this point in the history
  • Loading branch information
dk committed Nov 2, 2023
1 parent b563ca7 commit f61bc35
Show file tree
Hide file tree
Showing 4 changed files with 140 additions and 9 deletions.
1 change: 1 addition & 0 deletions MANIFEST
Original file line number Diff line number Diff line change
Expand Up @@ -415,6 +415,7 @@ t/Image/Conversion.t
t/Image/Extract.t
t/Image/FloodFill.t
t/Image/Import.t
t/Image/Loader.t
t/Image/Path.t
t/Image/ROP.t
t/Image/Stream.t
Expand Down
9 changes: 9 additions & 0 deletions Prima/Classes.pm
Original file line number Diff line number Diff line change
Expand Up @@ -983,6 +983,15 @@ sub save_stream
return $ok;
}

sub has_codec
{
my $what = $_[1];
for ( map { $_->{fileShortType} } @{ Prima::Image->codecs }) {
return 1 if m/$what/;
}
return 0;
}

package Prima::Icon;
use vars qw( @ISA);
@ISA = qw(Prima::Image);
Expand Down
21 changes: 12 additions & 9 deletions img/load.c
Original file line number Diff line number Diff line change
Expand Up @@ -335,7 +335,7 @@ apc_img_open_load( char * fileName, Bool is_utf8, PImgIORequest ioreq, HV * pro
char dummy_error_buf[256];
PImgCodec c;
PImgLoadFileInstance fi;
long pos = 0;
long pos1 = 0, pos2 = 0;

CHK;
if ( !( fi = malloc(sizeof(ImgLoadFileInstance)))) {
Expand All @@ -357,9 +357,6 @@ apc_img_open_load( char * fileName, Bool is_utf8, PImgIORequest ioreq, HV * pro
fi-> fileProperties = newHV();
fi-> frameCount = -1;

if ( ioreq != NULL)
pos = req_tell( ioreq );

if ( pexist( loadExtras) && pget_B( loadExtras))
fi-> loadExtras = true;

Expand Down Expand Up @@ -394,9 +391,13 @@ apc_img_open_load( char * fileName, Bool is_utf8, PImgIORequest ioreq, HV * pro
fi-> baseClassName = duplicate_string("Prima::Image");

/* find codec */
if ( ioreq != NULL)
pos1 = req_tell( ioreq );
if (( err = !img_find_codec( fi)))
goto EXIT_NOW;
c = fi->codec;
if ( ioreq != NULL)
pos2 = req_tell( ioreq );

/* use common profile */
fi-> cached_defaults = c-> vmt-> load_defaults( c);
Expand All @@ -408,10 +409,10 @@ apc_img_open_load( char * fileName, Bool is_utf8, PImgIORequest ioreq, HV * pro

if ( fi-> frameCount < 0 && fi-> wantFrames) {
if ( ioreq != NULL)
req_seek( ioreq, pos, SEEK_SET);
req_seek( ioreq, pos1, SEEK_SET);
fi-> frameCount = apc_img_frame_count( fileName, is_utf8, ioreq);
if ( ioreq != NULL)
req_seek( ioreq, pos, SEEK_SET);
req_seek( ioreq, pos2, SEEK_SET);
}

if ( fi-> loadExtras ) {
Expand Down Expand Up @@ -690,9 +691,7 @@ apc_img_load( Handle self, char * fileName, Bool is_utf8, PImgIORequest ioreq,
Bool eof_is_not_an_error = false;

if ( incrementalLoad ) {
if ( fi->frameCount < 0 )
fi->frame++;
else if ( i >= fi->frameCount)
if ( fi->frameCount >= 0 && i >= fi->frameCount)
break;
} else {
if ( fi->frameCount < 0 )
Expand All @@ -714,6 +713,9 @@ apc_img_load( Handle self, char * fileName, Bool is_utf8, PImgIORequest ioreq,

img = apc_img_load_next_frame( self, fi, frame_profile, error );

if ( incrementalLoad )
fi->frame++;

if ( img == NULL_HANDLE && incrementalLoad ) {
/* if it is EOF? report no error then */
if ( fi-> frameCount < 0) {
Expand Down Expand Up @@ -1086,6 +1088,7 @@ apc_img_save_next_frame( Handle source, PImgSaveFileInstance fi, HV * profile, c
/* saving image */
if ( !c-> vmt-> save( c, fi)) {
c-> vmt-> close_save( c, fi);
fi->instance = NULL;
err = true;
}

Expand Down
118 changes: 118 additions & 0 deletions t/Image/Loader.t
Original file line number Diff line number Diff line change
@@ -0,0 +1,118 @@
use strict;
use warnings;

use Prima::sys::Test qw(noX11);
use Test::More;
use Prima::Image::Loader;

my @codecs;
my @names;

for ( @{ Prima::Image->codecs }) {
next unless $_->{canLoad} && $_->{canSave} && $_->{canSaveMultiple} && $_->{canLoadMultiple} && $_->{canSaveStream} && $_->{canLoadStream};
push @codecs, $_->{codecID};
push @names, $_->{fileShortType};
}
plan skip_all => 'No multiframe-capable codecs' unless @codecs;

sub ix($) {
Prima::Image->new(
type => im::Byte,
size => [1,1],
data => $_[0],
)
}
my @ix = map { ix chr } 0..2;

sub test_codec
{
my ($codecID, $name) = @_;

my $buf1 = '';
open F, "+>", \ $buf1 or die $!;

my $ok = Prima::Image->save( \*F, images => \@ix, codecID => $codecID);
ok( $ok, "$name: traditional save".( $ok ? '' : ":$@"));

my $buf2 = '';
open G, "+>", \ $buf2 or die $!;

my ($s,$err) = Prima::Image::Saver->new( \*G, codecID => $codecID, frames => scalar(@ix) ) ;
ok( $s, "$name: open_save".($s ? '' : ":$err"));

for (0..2) {
($ok,$err) = $s->save($ix[$_]);
ok($ok, "$name: save frame $_".($ok ? '' : ":$err"));
}
undef $s;
close G;
ok( $buf1 eq $buf2, "$name: traditional and framed saves produce identical results");


seek(F,0,0);
my @nx = Prima::Image->load(\*F, loadAll => 1, loadExtras => 1 );
is( scalar(@nx), 3, "$name: traditional load returned 3 frames");
is( $nx[0] && $nx[0]->{extras} && $nx[0]->{extras}->{frames}, 3, "$name: extras.frames is okay");
for my $n ( 0..2 ) {
is($nx[$n]->pixel(0,0), $n, "$name/loadAll: image $n is loaded correctly") if $nx[$n];
}

for my $n (0..2) {
seek(F,0,0);
@nx = Prima::Image->load(\*F, index => $n);
is( scalar(@nx), 1, "$name/index: index $n loaded ok");
is($nx[0]->pixel(0,0), $n, "$name/index: image $n is loaded correctly") if $nx[0];

my $i = Prima::Image->new;
seek(F,0,0);
($ok,$err) = $i->load(\*F, index => $n);
ok( $ok, "$name/inplace: index $n loaded ok");
is($i->pixel(0,0), $n, "$name/inplace: image $n is loaded correctly");

seek(F,0,0);
@nx = Prima::Image->load(\*F, map => [$n]);
is( scalar(@nx), 1, "$name/map: index $n loaded ok");
is($nx[0]->pixel(0,0), $n, "$name/map: image $n is loaded correctly") if $nx[0];

my $m = ($n < 2) ? $n + 1 : 0;
seek(F,0,0);
@nx = Prima::Image->load(\*F, map => [$n, $m]);
is( scalar(@nx), 2, "$name/map($n,$m): images $n and $m loaded ok");
is($nx[0]->pixel(0,0), $n, "$name/map($n,$m): image $n is loaded correctly") if $nx[0];
is($nx[1]->pixel(0,0), $m, "$name/map($n,$m): image $m is loaded correctly") if $nx[1];
}

my ($lx,$i);
$i = Prima::Image->new;
seek(F,0,0);
@nx = $i->load(\*F, map => [], loadExtras => 1, wantFrames => 1);
is(scalar(@nx), 0, "$name: traditional null load request is ok");
is($i->{extras}->{frames}, 3, "$name: traditional null load request says 3 frames");

seek(F,0,0);
($lx,$err) = Prima::Image::Loader->new(\*F);
ok( $lx, "$name: loader created".($ok?'':":$err"));

is($lx->frames, 3, "$name/loader: null load request says 3 frames");

for my $n (0..2) {
ok(!$lx->eof, "$name/loader: lx($n) is not eof");
($i,$err) = $lx->next;
ok( $i, "$name/loader: image $n loaded".($i?'':":$err"));
is($i->pixel(0,0), $n, "$name/loader: image $n is loaded correctly")
if $i;
}
ok($lx->eof,"$name/loader: lx(3) is eof");
($i,$err) = $lx->next;
ok(!$i, "$name/loader: image(3) is null");

close F;
}

for ( my $i = 0; $i < @codecs; $i++) {
test_codec($codecs[$i], $names[$i]);
# last; # XXX
}


done_testing;

0 comments on commit f61bc35

Please sign in to comment.