Board index » delphi » Form Canvas vs Image Canvas

Form Canvas vs Image Canvas

Hi, i was just playing with drawing pixcels in a form's canvas, and then in
a Timage canvas, and i noticed that doing it in the form's canvas is WAY
MUCH faster than in the tImage.

Why could this be?

The code was:

 loop:=true;
  x:=0;
  y:=0;
  while loop do begin
  img.Canvas.Pixels[X,Y]:=CLRED;
    X:=X+1;
    if x>=img.Width then begin
     y:=y+1;
      x:=0;
    end;
    application.ProcessMessages;
  end;

--
Ral Andrs
5999...@entelpcs.cl

 

Re:Form Canvas vs Image Canvas


I haven't noticed a significant difference in speed between the TImage and
the TForm (when writing pixels)

But there is a massive difference if you use Scanline rather than Pixel[x,y]

Earl F. Glynn replied to an earlier message in this group. All is revealed
at his web site

See http://homepages.borland.com/efg2lab/ImageProcessing/Scanline.htm
for this particular topic and have hours of fun browsing other similar
topics :-)

--
Eddie

Mailto: eddie AT pcug DOT org DOT au
s...@above.for.real.address

"Ral Andrs No Spam del Canto" <RaulAnd...@NoSpamDelcanto.net> wrote in
message news:3c858cf1$1_1@dnews...

Quote
> Hi, i was just playing with drawing pixcels in a form's canvas, and then
in
> a Timage canvas, and i noticed that doing it in the form's canvas is WAY
> MUCH faster than in the tImage.

> Why could this be?

> The code was:

>  loop:=true;
>   x:=0;
>   y:=0;
>   while loop do begin
>   img.Canvas.Pixels[X,Y]:=CLRED;
>     X:=X+1;
>     if x>=img.Width then begin
>      y:=y+1;
>       x:=0;
>     end;
>     application.ProcessMessages;
>   end;

> --
> Ral Andrs
> 5999...@entelpcs.cl

Re:Form Canvas vs Image Canvas


"Ral Andrs No Spam del Canto" <RaulAnd...@NoSpamDelcanto.net> skrev i en
meddelelse news:3c858cf1$1_1@dnews...

Quote
> Hi, i was just playing with drawing pixcels in a form's canvas, and then
in
> a Timage canvas, and i noticed that doing it in the form's canvas is WAY
> MUCH faster than in the tImage.
> Why could this be?

Because there is a lot of overhead in TImage, mainly because TImage stores
the pixels, the form's canvas does not.
--
Finn Tolderlund

Re:Form Canvas vs Image Canvas


Quote
> Hi, i was just playing with drawing pixcels in a form's canvas, and then
in
> a Timage canvas, and i noticed that doing it in the form's canvas is WAY
> MUCH faster than in the tImage.

> Why could this be?

> The code was:

>  loop:=true;
>   x:=0;
>   y:=0;
>   while loop do begin
>   img.Canvas.Pixels[X,Y]:=CLRED;
>     X:=X+1;
>     if x>=img.Width then begin
>      y:=y+1;
>       x:=0;
>     end;
>     application.ProcessMessages;
>   end;

Finn mentioned overhead in his reply and I'll add that
the Application.ProcessMessages is a killer in a loop
like yours. You'd be better off either dropping it, or
looking into a separate drawing thread of some sort
that bitblt's the image to the form..

John McTaggart

Re:Form Canvas vs Image Canvas


In article <3c858cf1$1_1@dnews>, Ral Andrs No Spam del Canto wrote:

Quote
> The code was:

>  loop:=true;
>   x:=0;
>   y:=0;
>   while loop do begin
>   img.Canvas.Pixels[X,Y]:=CLRED;
>     X:=X+1;
>     if x>=img.Width then begin
>      y:=y+1;
>       x:=0;
>     end;
>     application.ProcessMessages;
>   end;

When you draw to the TImage canvas you're actually drawing to the
Picture.Bitmap.Canvas. Unless the bitmap is drawn to the controls
canvas you won't see any change, application.process messages is
allowing that to happen every time a pixel is drawn. Try leaving it
out and calling invalidate out of the loop and see what the
difference is. BTW John's right about it not being the way to do it
but if you're just experimenting...

Gordon

Re:Form Canvas vs Image Canvas


Mmm, yes. The tImage storing the pixels vs tForm don't may be the big
difference.
Any how the .proccessMessages is in both loopd (the image and the form) so i
guess it aadds the same pause for both. I found this method (of
.processMessages) a quick way to writh a loop that can be user-interrupted.

--
Ral Andrs del Canto
5999...@entelpcs.cl
"Gordon Whittam" <gor...@mgcsoft.com> escribi en el mensaje
news:VA.00000049.0026882f@mgcsoft.com...

Quote
> In article <3c858cf1$1_1@dnews>, Ral Andrs No Spam del Canto wrote:
> > The code was:

> >  loop:=true;
> >   x:=0;
> >   y:=0;
> >   while loop do begin
> >   img.Canvas.Pixels[X,Y]:=CLRED;
> >     X:=X+1;
> >     if x>=img.Width then begin
> >      y:=y+1;
> >       x:=0;
> >     end;
> >     application.ProcessMessages;
> >   end;

> When you draw to the TImage canvas you're actually drawing to the
> Picture.Bitmap.Canvas. Unless the bitmap is drawn to the controls
> canvas you won't see any change, application.process messages is
> allowing that to happen every time a pixel is drawn. Try leaving it
> out and calling invalidate out of the loop and see what the
> difference is. BTW John's right about it not being the way to do it
> but if you're just experimenting...

> Gordon

Re:Form Canvas vs Image Canvas


Quote
In article <3c90c65f$1_2@dnews>, Ral Andrs wrote:
> Mmm, yes. The tImage storing the pixels vs tForm don't may be the big
> difference.
> Any how the .proccessMessages is in both loopd (the image and the form) so i
> guess it aadds the same pause for both. I found this method (of
> ..processMessages) a quick way to writh a loop that can be user-interrupted.

I don't think so. I /think/ that every time you draw a pixel onto the TImage
it repaints the whole image, that isn't happening when you draw a pixel on the
form.

What I do with operations that can be interrupted by the user is something
like this:

User does something which sets boolean var doInterrupt = true

for cnt:= ...
  begin
    if cnt mod n = 0 then
       Application.ProcessMessages;
    if doInterrupt then
      begin
        doInterrupt:= false;
        break;
      end;
    ...
    ...
  end;

'n' being dependent on the number of iterations and expected time of each
iteration.

Not suitable in every situation of course as the boolean evaluation takes
time. You'll just have to decide yourself whether you can use it.

Gordon

Re:Form Canvas vs Image Canvas


Good idea!, So in resume, if i get it, you say that instead of procesing the
medssageds every time, you process them every 'n' loops.. that makes a lot
of sense, since a loop probably takes a fraction of second.

I guess it's a llittle faster to make

if n=m then begin
    n:=0;
    Application.ProcessMessages;
end
.....

Because it's faster to compare 2 direct values than the result of an
aritmethic operation.

--
Ral Andrs del Canto
5999...@entelpcs.cl
"Gordon Whittam" <gor...@mgcsoft.com> escribi en el mensaje
news:VA.0000004a.0121818f@mgcsoft.com...

Quote
> In article <3c90c65f$1_2@dnews>, Ral Andrs wrote:
> > Mmm, yes. The tImage storing the pixels vs tForm don't may be the big
> > difference.
> > Any how the .proccessMessages is in both loopd (the image and the form)
so i
> > guess it aadds the same pause for both. I found this method (of
> > ..processMessages) a quick way to writh a loop that can be
user-interrupted.

> I don't think so. I /think/ that every time you draw a pixel onto the
TImage
> it repaints the whole image, that isn't happening when you draw a pixel on
the
> form.

> What I do with operations that can be interrupted by the user is something
> like this:

> User does something which sets boolean var doInterrupt = true

> for cnt:= ...
>   begin
>     if cnt mod n = 0 then
>        Application.ProcessMessages;
>     if doInterrupt then
>       begin
>         doInterrupt:= false;
>         break;
>       end;
>     ...
>     ...
>   end;

> 'n' being dependent on the number of iterations and expected time of each
> iteration.

> Not suitable in every situation of course as the boolean evaluation takes
> time. You'll just have to decide yourself whether you can use it.

> Gordon

Re:Form Canvas vs Image Canvas


Quote
In article <3c915e6c_2@dnews>, Ral Andrs wrote:
> Good idea!, So in resume, if i get it, you say that instead of procesing the
> medssageds every time, you process them every 'n' loops.. that makes a lot
> of sense, since a loop probably takes a fraction of second.

Yes, it works for me. Watch out for loops within loops, you need to do it
twice if 'exit' isn't an option or set another boolean and check that before
going into each loop. It isn't a method that can be blindly applied IMHO but
in the right place it's OK.

Quote
> I guess it's a llittle faster to make

> if n=m then begin
>     n:=0;
>     Application.ProcessMessages;
> end
> ......

> Because it's faster to compare 2 direct values than the result of an
> aritmethic operation.

Probably, yes.

Cheers

Gordon

Other Threads