the source image is copied.
instead.
- some older FT1 don't define TT_MS_LANGID_ENGLISH_GENERAL,
which we use, define it if freetype doesn't.
-
+ - Added extra options to rubthrough() so only a subpart of
+ source image is used.
=================================================================
For latest versions check the Imager-devel pages:
sub rubthrough {
my $self=shift;
- my %opts=(tx=>0,ty=>0,@_);
+ my %opts=(tx => 0,ty => 0, @_);
unless ($self->{IMG}) { $self->{ERRSTR}='empty input image'; return undef; }
unless ($opts{src} && $opts{src}->{IMG}) { $self->{ERRSTR}='empty input image for source'; return undef; }
- unless (i_rubthru($self->{IMG}, $opts{src}->{IMG}, $opts{tx},$opts{ty})) {
+ %opts = (src_minx => 0,
+ src_miny => 0,
+ src_maxx => $opts{src}->getwidth(),
+ src_maxy => $opts{src}->getheight(),
+ %opts);
+
+ unless (i_rubthru($self->{IMG}, $opts{src}->{IMG}, $opts{tx}, $opts{ty},
+ $opts{src_minx}, $opts{src_miny}, $opts{src_maxx}, $opts{src_maxy})) {
$self->{ERRSTR} = $self->_error_as_msg();
return undef;
}
undef_int
-i_rubthru(im,src,tx,ty)
+i_rubthru(im,src,tx,ty,src_minx,src_miny,src_maxx,src_maxy)
Imager::ImgRaw im
Imager::ImgRaw src
int tx
int ty
+ int src_minx
+ int src_miny
+ int src_maxx
+ int src_maxy
+
undef_int
i_flipxy(im, direction)
lib/Imager/Font/FreeType2.pm
lib/Imager/Font/Win32.pm
lib/Imager/Font/Wrap.pm
+lib/Imager/Font/Image.pm
lib/Imager/Fountain.pm
lib/Imager/interface.pod
lib/Imager/Matrix2d.pm
/*
-=item i_rubthru(im, src, tx, ty)
+=item i_rubthru(im, src, tx, ty, src_minx, src_miny, src_maxx, src_maxy )
-Takes the image I<src> and applies it at an original (I<tx>,I<ty>) in I<im>.
+Takes the sub image I<src[src_minx, src_maxx)[src_miny, src_maxy)> and
+overlays it at (I<tx>,I<ty>) on the image object.
The alpha channel of each pixel in I<src> is used to control how much
the existing colour in I<im> is replaced, if it is 255 then the colour
*/
int
-i_rubthru(i_img *im,i_img *src,int tx,int ty) {
+i_rubthru(i_img *im, i_img *src, int tx, int ty, int src_minx, int src_miny,
+ int src_maxx, int src_maxy) {
int x, y, ttx, tty;
int chancount;
int chans[3];
int alphachan;
int ch;
- mm_log((1,"i_rubthru(im %p, src %p, tx %d, ty %d)\n", im, src, tx, ty));
+ mm_log((1,"i_rubthru(im %p, src %p, tx %d, ty %d, src_minx %d, "
+ "src_miny %d, src_maxx %d, src_maxy %d)\n",
+ im, src, tx, ty, src_minx, src_miny, src_maxx, src_maxy));
i_clear_error();
if (im->channels == 3 && src->channels == 4) {
changed in a similar fashion - TC */
int alpha;
i_color pv, orig, dest;
- ttx = tx;
- for(x=0; x<src->xsize; x++) {
- tty=ty;
- for(y=0;y<src->ysize;y++) {
- /* fprintf(stderr,"reading (%d,%d) writing (%d,%d).\n",x,y,ttx,tty); */
+ tty = ty;
+ for(y = src_miny; y < src_maxy; y++) {
+ ttx = tx;
+ for(x = src_minx; x < src_maxx; x++) {
i_gpix(src, x, y, &pv);
i_gpix(im, ttx, tty, &orig);
alpha = pv.channel[alphachan];
+ (255 - alpha) * orig.channel[ch])/255;
}
i_ppix(im, ttx, tty, &dest);
- tty++;
+ ttx++;
}
- ttx++;
+ tty++;
}
}
else {
double alpha;
i_fcolor pv, orig, dest;
- ttx = tx;
- for(x=0; x<src->xsize; x++) {
- tty=ty;
- for(y=0;y<src->ysize;y++) {
- /* fprintf(stderr,"reading (%d,%d) writing (%d,%d).\n",x,y,ttx,tty); */
+ tty = ty;
+ for(y = src_miny; y < src_maxy; y++) {
+ ttx = tx;
+ for(x = src_minx; x < src_maxx; x++) {
i_gpixf(src, x, y, &pv);
i_gpixf(im, ttx, tty, &orig);
alpha = pv.channel[alphachan];
for (ch = 0; ch < chancount; ++ch) {
dest.channel[ch] = alpha * pv.channel[chans[ch]]
- + (1 - alpha) * orig.channel[ch];
+ + (1 - alpha) * orig.channel[ch];
}
i_ppixf(im, ttx, tty, &dest);
- tty++;
+ ttx++;
}
- ttx++;
+ tty++;
}
}
void i_copyto (i_img *im,i_img *src,int x1,int y1,int x2,int y2,int tx,int ty);
void i_copyto_trans(i_img *im,i_img *src,int x1,int y1,int x2,int y2,int tx,int ty,i_color *trans);
void i_copy (i_img *im,i_img *src);
-int i_rubthru (i_img *im,i_img *src,int tx,int ty);
+int i_rubthru (i_img *im, i_img *src, int tx, int ty, int src_minx, int src_miny, int src_maxx, int src_maxy);
+
undef_int i_flipxy (i_img *im, int direction);
extern i_img *i_rotate90(i_img *im, int degrees);
$dest->paste(left=>40,top=>20,img=>$logo);
- $img->rubthrough(src=>$srcimage,tx=>30,ty=>50);
+ $img->rubthrough(src=>$srcimage,tx=>30, ty=>50);
+ $img->rubthrough(src=>$srcimage,tx=>30, ty=>50,
+ src_minx=>20, src_miny=>30,
+ src_maxx=>20, src_maxy=>30);
$img->flip(dir=>"h"); # horizontal flip
put 'over' the other with a certain amount of opaqueness. The
method that does this is rubthrough.
- $img->rubthrough(src=>$srcimage,tx=>30,ty=>50);
-
-That will take the image C<$srcimage> and overlay it with the upper
-left corner at (30,50). You can rub 2 or 4 channel images onto a 3
-channel image, or a 2 channel image onto a 1 channel image. The last
-channel is used as an alpha channel.
+ $img->rubthrough(src=>$overlay,
+ tx=>30, ty=>50,
+ src_minx=>20, src_miny=>30,
+ src_maxx=>20, src_maxy=>30);
+
+That will take the sub image defined by I<$overlay> and
+I<[src_minx,src_maxx)[src_miny,src_maxy)> and overlay it on top of
+I<$img> with the upper left corner at (30,50). You can rub 2 or 4
+channel images onto a 3 channel image, or a 2 channel image onto a 1
+channel image. The last channel is used as an alpha channel. To add
+an alpha channel to an image see I<convert()>.
=item flip
print "ok 1\n";
init_log("testout/t69rubthru.log", 1);
+my $src_height = 80;
+my $src_width = 80;
+
# raw interface
my $targ = Imager::ImgRaw::new(100, 100, 3);
-my $src = Imager::ImgRaw::new(80, 80, 4);
+my $src = Imager::ImgRaw::new($src_height, $src_width, 4);
my $halfred = NC(255, 0, 0, 128);
i_box_filled($src, 20, 20, 60, 60, $halfred);
-i_rubthru($targ, $src, 10, 10) or print "not ";
+i_rubthru($targ, $src, 10, 10, 0, 0, $src_width, $src_height) or print "not ";
print "ok 2\n";
my $c = Imager::i_get_pixel($targ, 10, 10) or print "not ";
print "ok 3\n";
my $black = NC(0, 0, 0);
# reset the target and try a grey+alpha source
i_box_filled($targ, 0, 0, 100, 100, $black);
-my $gsrc = Imager::ImgRaw::new(80, 80, 2);
+my $gsrc = Imager::ImgRaw::new($src_width, $src_height, 2);
my $halfwhite = NC(255, 128, 0);
i_box_filled($gsrc, 20, 20, 60, 60, $halfwhite);
-i_rubthru($targ, $gsrc, 10, 10) or print "not ";
+i_rubthru($targ, $gsrc, 10, 10, 0, 0, $src_width, $src_height) or print "not ";
print "ok 7\n";
$c = Imager::i_get_pixel($targ, 15, 15) or print "not ";
print "ok 8\n";
# try grey target and grey alpha source
my $gtarg = Imager::ImgRaw::new(100, 100, 1);
-i_rubthru($gtarg, $gsrc, 10, 10) or print "not ";
+i_rubthru($gtarg, $gsrc, 10, 10, 0, 0, $src_width, $src_height) or print "not ";
print "ok 12\n";
$c = Imager::i_get_pixel($gtarg, 10, 10) or print "not ";
print "ok 13\n";
print "ok 15\n";
# an attempt rub a 4 channel image over 1 channel should fail
-i_rubthru($gtarg, $src, 10, 10) and print "not ";
+i_rubthru($gtarg, $src, 10, 10, 0, 0, $src_width, $src_height) and print "not ";
print "ok 16\n";
# simple test for 16-bit/sample images
my $targ16 = Imager::i_img_16_new(100, 100, 3);
-i_rubthru($targ16, $src, 10, 10) or print "not ";
+i_rubthru($targ16, $src, 10, 10, 0, 0, $src_width, $src_height) or print "not ";
print "ok 17\n";
$c = Imager::i_get_pixel($targ16, 30, 30) or print "not ";
print "ok 18\n";
# check the OO interface
my $ootarg = Imager->new(xsize=>100, ysize=>100);
my $oosrc = Imager->new(xsize=>80, ysize=>80, channels=>4);
-$oosrc->box(color=>$halfred, xmin=>20, ymin=>20, xmax=>60, ymax=>60,
+$oosrc->box(color=>$halfred, xmin=>20, ymin=>20, xmax=>60, ymax=>60,
filled=>1);
$ootarg->rubthrough(src=>$oosrc, tx=>10, ty=>10) or print "not ";
print "ok 20\n";