return $result;
}
+sub rgb_difference {
+ my ($self, %opts) = @_;
+
+ $self->_valid_image("rgb_difference")
+ or return;
+
+ defined $opts{other}
+ or return $self->_set_error("No 'other' parameter supplied");
+ unless ($opts{other}->_valid_image("rgb_difference")) {
+ $self->_set_error($opts{other}->errstr . " (other image)");
+ return;
+ }
+
+ my $result = Imager->new;
+ $result->{IMG} = i_rgbdiff_image($self->{IMG}, $opts{other}{IMG})
+ or return $self->_set_error($self->_error_as_msg());
+
+ return $result;
+}
+
# destructive border - image is shrunk by one pixel all around
sub border {
register_writer() - L<Imager::Files/register_writer()>
+rgb_difference() - L<Imager::Filters/rgb_difference()> - produce a difference
+images from two input images.
+
rotate() - L<Imager::Transformations/rotate()>
rubthrough() - L<Imager::Transformations/rubthrough()> - draw an image
Imager::ImgRaw im2
im_double mindist
+Imager::ImgRaw
+i_rgbdiff_image(im, im2)
+ Imager::ImgRaw im
+ Imager::ImgRaw im2
+
undef_int
i_fountain(im, xa, ya, xb, yb, type, repeat, combine, super_sample, ssample_param, segs)
Imager::ImgRaw im
ysize = i_min(im1->ysize, im2->ysize);
out = i_sametype_chans(im1, xsize, ysize, outchans);
-
+
if (im1->bits == i_8_bits && im2->bits == i_8_bits) {
i_color *line1 = mymalloc(xsize * sizeof(*line1)); /* checked 17feb2005 tonyc */
i_color *line2 = mymalloc(xsize * sizeof(*line1)); /* checked 17feb2005 tonyc */
return out;
}
+/*
+=item i_rgbdiff_image(im1, im2)
+
+Creates a new image that is black, except where the pixel in im2 is
+different from im1, where it is the arithmetical difference to im2 per
+color.
+
+=cut
+*/
+
+i_img *
+i_rgbdiff_image(i_img *im1, i_img *im2) {
+ i_img *out;
+ int outchans, diffchans;
+ i_img_dim xsize, ysize;
+ dIMCTXim(im1);
+
+ i_clear_error();
+ if (im1->channels != im2->channels) {
+ i_push_error(0, "different number of channels");
+ return NULL;
+ }
+
+ outchans = diffchans = im1->channels;
+ if (outchans == 2 || outchans == 4)
+ --outchans;
+
+ xsize = i_min(im1->xsize, im2->xsize);
+ ysize = i_min(im1->ysize, im2->ysize);
+
+ out = i_sametype_chans(im1, xsize, ysize, outchans);
+
+#code im1->bits == i_8_bits && im2->bits == i_8_bits
+ IM_COLOR *line1 = mymalloc(xsize * sizeof(*line1));
+ IM_COLOR *line2 = mymalloc(xsize * sizeof(*line1));
+ i_img_dim x, y;
+ int ch;
+
+ for (y = 0; y < ysize; ++y) {
+ IM_GLIN(im1, 0, xsize, y, line1);
+ IM_GLIN(im2, 0, xsize, y, line2);
+ for (x = 0; x < xsize; ++x) {
+ for (ch = 0; ch < outchans; ++ch) {
+ line2[x].channel[ch] = IM_ABS(line1[x].channel[ch] - line2[x].channel[ch]);
+ }
+ }
+ IM_PLIN(out, 0, xsize, y, line2);
+ }
+ myfree(line1);
+ myfree(line2);
+#/code
+
+ return out;
+}
+
struct fount_state;
static double linear_fount_f(double x, double y, struct fount_state *state);
static double bilinear_fount_f(double x, double y, struct fount_state *state);
void i_gradgen(i_img *im, int num, i_img_dim *xo, i_img_dim *yo, i_color *ival, int dmeasure);
int i_nearest_color(i_img *im, int num, i_img_dim *xo, i_img_dim *yo, i_color *ival, int dmeasure);
i_img *i_diff_image(i_img *im, i_img *im2, double mindist);
+i_img *i_rgbdiff_image(i_img *im, i_img *im2);
int
i_fountain(i_img *im, double xa, double ya, double xb, double yb,
i_fountain_type type, i_fountain_repeat repeat,
=back
+=item rgb_difference()
+
+You can create a new image that is the difference between 2 other images.
+
+ my $diff = $img->rgb_difference(other=>$other_img);
+
+For each pixel in $img that is different to the pixel in $other_img,
+the arithmetic difference for the value of the pixel in $img from
+$other_img per color is given. Transparency is ignored.
+
+This can be used for measuring image differences ("How much are they
+different?").
+
+Note that $img and $other_img must have the same number of channels.
+The width and height of $diff will be the minimum of each of the width
+and height of $img and $other_img.
+
+Parameters:
+
+=over
+
+=item *
+
+C<other> - the other image object to compare against
+
+=back
+
+=back
+
=head1 AUTHOR
Arnar M. Hrafnkelsson, Tony Cook <tonyc@cpan.org>.
our @EXPORT = qw(preprocess);
our @ISA = qw(Exporter);
-our $VERSION = "1.002";
+our $VERSION = "1.003";
sub preprocess {
unshift @ARGV, grep /^-/, shellwords($ENV{IMAGER_PREPROCESS_OPTS})
s/\bIM_LIMIT\(/IM_LIMIT_8(/g;
s/\bIM_RENDER_LINE\(/i_render_line(/g;
s/\bIM_FILL_COMBINE_F\b/i_fill_combine_f/g;
+ s/\bIM_ABS\b/abs/g;
}
@lines;
s/\bIM_LIMIT\(/IM_LIMIT_double(/g;
s/\bIM_RENDER_LINE\(/i_render_linef(/g;
s/\bIM_FILL_COMBINE_F\b/i_fill_combinef_f/g;
+ s/\bIM_ABS\b/fabs/g;
}
@lines;
=item *
+IM_ABS(sample) - calculate the absolute value of an IM_WORK_T value.
+
+=item *
+
IM_SAMPLE_MAX - maximum value for a sample
=item *
#!perl -w
use strict;
use Imager qw(:handy);
-use Test::More tests => 136;
+use Test::More tests => 137;
-d "testout" or mkdir "testout";
my $cmp2 = Imager->new(xsize => 3, ysize => 2, channels => 4);
$cmp2->setpixel(x => 2, 'y' => 0, color => '#FF02FF');
is_image($diff2, $cmp2, "difference() - check image with mindist 1");
+
+ $im1 = Imager->new(xsize => 3, ysize => 2, channels => 4);
+ $im2 = $im1->copy;
+ $im1->setpixel(x => 1, 'y' => 0, color => 'FF00FF80');
+ $im2->setpixel(x => 1, 'y' => 0, color => 'FF01FF84');
+ $im1->setpixel(x => 2, 'y' => 0, color => 'FF00FF80');
+ $im2->setpixel(x => 2, 'y' => 0, color => 'FF02FF84');
+ my $diff3 = $im1->rgb_difference(other => $im2);
+ my $cmp3 = Imager->new(xsize => 3, ysize => 2, channels => 3);
+ $cmp3->box(filled => 1, color => '#000000');
+ $cmp3->setpixel(x => 1, 'y' => 0, color => '#000100');
+ $cmp3->setpixel(x => 2, 'y' => 0, color => '#000200');
+ is_image($diff3, $cmp3, "rgb_difference() - check image");
}
{