Programowanie w języku Delphi » Gotowce

Podwójne buforowanie

  • 2008-03-02 15:58
  • 5 komentarzy
  • 958 odsłon
  • Oceń ten tekst jako pierwszy
Załóżmy, że chcesz zaprogramować poruszający się prostokąt wzdłuż ekranu:

const
  Szerokosc = 20;
  Wysokosc = 20;
 
var
  Pozycja: Integer;
 
procedure TForm1.Timer1Timer(Sender: TObject);
begin
  Canvas.Pen.Color := clWhite;
  Canvas.Brush.Color := clWhite;
  Canvas.Rectangle(Pozycja, 100, Pozycja + Szerokosc, 100 + Wysokosc);
  Pozycja := Pozycja + 1;
end;


W rezultacie program będzie rysował grubą linię po środku ekranu
Dobrym sposobem będzie rysowanie linii w kolorze tla za kwadratem.

  Canvas.MoveTo(Pozycja - 1, 100);
  Canvas.LineTo(Pozycja - 1 , 100 + Wysokosc);


Ale co zrobić, gdy animacja będzie zawierała wiele rożnych figur, a tło nie będzie w postaci jednolitego koloru tylko bitmapy?

Własnie w takich momentach warto wykorzystać "Double Buffering"
Wystarczy zadeklarować dodatkową zmienną TCanvas

var
  Buf: TCanvas;


i tło jako bitmapę:
  Bitmap: TBitmap;


Inicjalizujemy Bufor:

  Buf := TBitmap.Create(Self);
  Buf.Width := Form1.Canvas.Width;
  Buf.Height := Form1.Canvas.Height;

a nastepnie wczytujemy tlo:
  Bitmap := TBitmap.Create;
  Bitmap.LoadFromFile('obrazek.bmp');


wtedy procedura wygląda tak:

procedure TForm1.Timer1Timer(Sender: TObject);
var
  l: Integer;
begin
  Buf.Draw(0, 0, Bitmap); {rysujemy tlo}
  Buf.Pen.Color := clWhite;
  Buf.Brush.Color := clWhite;
  Buf.Rectangle(Pozycja, 100, Pozycja + Szerokosc, 100 + Wysokosc);
  Pozycja := Pozycja + 1;
  {kopiujemy Buf na ekran}
  Form1.Canvas.CopyRect(Form1.Canvas.ClipRect, Buf, Buf.ClipRect);
end;


W efekcie prostokąt porusza się bez migotania i na tle które wczytaliśmy.

Zasada jest prosta. Pierw rysujemy całą animację w pamięci (zmienna Buf), a następnie kopiujemy ją na ekran (procedure CopyRect) , co daje efekt płynności i wrażenia, że całość rysuje się naraz.

5 komentarzy

TomRiddle 2011-02-01 18:33

A nie lepiej tak:
DoubleBuffered := True;

bahus 2009-06-30 17:40

bez jaj.... ale ten artykuł jest strasznie pokręcony ... i wyskakują błędy. Może jestem początkujący ale na necie znalazłem banalne rozwiązanie ... i piszę je dla tych co się załamali usiłując przepisać ten kod:
Problem: mruganie obrazka podczas przesuwania po formie
Rozwiązanie: Forma > OnCreate > wklepać   .....   DoubleBuffered := True  

Nie ma prawa migać ... Pozdrawiam

bordeux 2008-03-02 16:00

Pokolorowanie składni. Odrazu zachęca do przeczytania.

entek 2008-03-02 14:58

Juz mam ok.

//****************************************************
//    Tworzymy bufor dla obrazka
//****************************************************
  backgroundImage := TImage.Create( Self );
  backgroundCanvas := TCanvas.Create;

//zaladuj obrazek
backgroundImage.Picture.LoadFromFile('obrazek.bmp');

Warto spojrzeć, jak to jest zrobione w demie Delphi - Demos\EarthPng\

entek 2007-10-06 15:01

Tu mi sie wywala, ze argumenty złe:
Buf := TBitmap.Create(Self); <------- [Error] ClockZ.pas(185): Too many actual parameters

Co mam zrobić?