Einzelnen Beitrag anzeigen

BigAl

Registriert seit: 6. Sep 2008
Ort: Kehl
495 Beiträge
 
Delphi 12 Athens
 
#1

Flackern / Verzögerungen bei Update eigener Komponente

  Alt 24. Nov 2009, 18:47
Hallo zusammen,

habe hier ein paar Problemchen mit einer selbst erstellten Komponente.

Die Komponente ist auf Basis von TCustomControl erstellt. Die Initialisierung "Create" ist wie folgt:

Delphi-Quellcode:
constructor TPlanGrid.Create(AOwner: TComponent);
begin
  inherited;

  ControlStyle := [csCaptureMouse, csDoubleClicks, csOpaque, csFramed, csNeedsBorderPaint];
Die Darstellen findet in "Paint" statt. Der gekürzte Code sieht aus wie folgt:

Delphi-Quellcode:
begin
  Canvas.Font.Assign(Font);
  if FShowHeader then
    DrawHeader;
  DrawLines;
end;
Das "DrawHeader" zeichnet einen Kopfbereich, das "DrawLines" zeichnet unterhalb des Kopfbereich. Das Problem ist nun, dass die Komponente jedesmal bei einer Größenveränderung ihren kompletten Inhalt mit der Hintergrundfarbe überpinselt, ehe ich mit Paint zum Zug komme. Das flackert natürlich sehr unschön. Ok, mit "DoubleBuffer" lässt sich das zwar abschalten aber ist auch nicht die schöne Lösung. Hat jemand eine Idee, wie ich TCustomControl davon abbringen kann den Hintergrund bei "Resize" immer neu zu zeichnen? Das Ganze wird ja mit wachsender Funktionalität nicht besser.

Nun habe ich mich entschlossen dem Teil noch einen ScrollBar zu spendieren. Erstellt wird dieser in "Create" mit folgendem Code:

Delphi-Quellcode:
FVertScrollBar := TScrollBar.Create(Self);
with FVertScrollBar do
begin
  Kind := sbVertical;
  ParentDoubleBuffered := False;
  DoubleBuffered := False;
  Align := alRight;
  AlignWithMargins := True;
end;
InsertControl(FVertScrollBar);
Ob das so eine gute Lösung ist sei dahin gestellt. Wenn jemand eine elegantere Lösung hat, dann her damit. Auf jeden Fall wurde "Paint", zur Berücksichtigung des ScrollBars wie folgt angepasst:

Delphi-Quellcode:
var
  Region: HRGN;
begin
  Canvas.Font.Assign(Font);
  if FShowHeader then
  begin
    FVertScrollBar.Margins.SetBounds(0, FCellHeight * 4, 0, 0);
    DrawHeader;
  end
  else
    FVertScrollBar.Margins.SetBounds(0, 0, 0, 0);

  Region := CreateRectRgn(0, 0, ClientWidth - FVertScrollBar.Width, ClientHeight);
  SelectClipRgn(Canvas.Handle, Region);
  DrawLines;
  SelectClipRgn(Canvas.Handle, HRGN(nil));
  DeleteObject(Region);
end;
Der Code soll nur verhindern, dass die Bereiche, die ich zeichne nicht über den ScrollBar drüberpinseln. Richtig unschön wird es wieder bei "Resize". Da wandert der ScrollBar dem Rahmen hinterher. Schiebe ich das Fenster kleiner, dann verschwindet der ScrollBar währen der Größenveränderung teilweise unter dem Rahmen. Beim Größerziehen löst er sich davon ab. Sobald die Größe sich nicht mehr verändert stimmt wieder alles. Der Scrollbar selbst reagiert recht eigenartig auf "DoubleBufferd" oder manuelles Neuzeichnen vor meinen Aktionen (DrawHeader und DrawLines)...

Ich hoffe man kann ungefähr nachvollziehen wo meine Problematik ist.

Wäre für jede Hilfe, Tipps und Anregungen dankbar...

Alex
Man sollte nie so viel zu tun haben, dass man zum Nachdenken keine Zeit mehr hat. (G.C. Lichtenberg)
  Mit Zitat antworten Zitat