Methodenablauf verstehen, TControl.ChangeBounds()

Für Fragen zur Programmiersprache auf welcher Lazarus aufbaut
Antworten
thosch
Beiträge: 324
Registriert: Mo 10. Jul 2017, 20:32

Methodenablauf verstehen, TControl.ChangeBounds()

Beitrag von thosch »

Code: Alles auswählen

procedure TControl.ChangeBounds(ALeft, ATop, AWidth, AHeight: integer;
  KeepBase: boolean);
var
  SizeChanged, PosChanged : boolean;
  OldLeft, OldTop, OldWidth, OldHeight: Integer;

  function PosSizeChanged: boolean;
  begin
    SizeChanged:= (FWidth <> OldWidth) or (FHeight <> OldHeight);
    PosChanged:= (FLeft <> OldLeft) or (FTop <> OldTop);
    Result:= SizeChanged or PosChanged;
  end;
  {
  procedure DebugInvalidPos(N: integer);
  begin
    if (FLeft < Low(Smallint)) or (FLeft > High(Smallint))
    or (FTop  < Low(Smallint)) or (FTop  > High(Smallint)) then
      DebugLn(['TControl.ChangeBounds test(',N,')',DbgSName(Self),
        ' Old=',OldLeft,',',OldTop,',',OldWidth,',',OldHeight,
        ' New=',ALeft,',',ATop,',',AWidth,',',AHeight,
        ' Real=',FLeft,',',FTop,',',FWidth,',',FHeight]);
  end;
  }
begin
  {$IFDEF VerboseSizeMsg}
  DebugLn(['TControl.ChangeBounds A ',DbgSName(Self),
    ' Old=',Left,',',Top,',',Width,',',Height,
    ' New=',ALeft,',',ATop,',',AWidth,',',AHeight,
    ' KeepBase=',KeepBase]);
  //if (Parent=nil) and (Left>0) and (ALeft=0) then DumpStack; // This can happen if the interface has not yet moved the window and for some reason something applies the interface coords back to the LCL
  {$ENDIF}
  //------------------- Notwendigkeit prüfen
  //if Assigned(Parent) and not KeepBase then
  //  Parent.UpdateAlignIndex(Self);
  //----------------------------------

  //------------------ Notwendigkeit prüfen
  // constraint the size
  //DoConstrainedResize(ALeft, ATop, AWidth, AHeight);
  //----------------------------------

  // check if something would change
  SizeChanged := (FWidth <> AWidth) or (FHeight <> AHeight);
  PosChanged := (FLeft <> ALeft) or (FTop <> ATop);
  if not (SizeChanged or PosChanged) then Exit;
  SetDimensions(ALeft,ATop,AWidth,AHeight);
  // check for loop.
  {
  if (not KeepBase) and (cfKillChangeBounds in GetTopParent.FControlFlags) then
    raise Exception.Create('TControl.ChangeBounds loop detected '+DbgSName(Self)
      +' Left='+dbgs(Left)+',Top='+dbgs(Top)+',Width='+dbgs(Width)+',Height='+dbgs(Height)
      +' NewLeft='+dbgs(aLeft)+',NewTop='+dbgs(aTop)+',NewWidth='+dbgs(aWidth)+',NewHeight='+dbgs(aHeight)
      );
      }
  OldLeft := FLeft;
  OldTop := FTop;
  OldWidth := FWidth;
  OldHeight := FHeight;

  //DebugLn('TControl.ChangeBounds A ',DbgSName(Self),' Old=',dbgs(BoundsRect),' New=',dbgs(Bounds(ALeft,ATop,AWidth,AHeight)));
  //------------ Notwendigkeit prüfen
  //if not ((csLoading in ComponentState) or (Self is TWinControl)) then
  //  InvalidateControl(IsControlVisible, False, true);
  //DebugLn('TControl.ChangeBounds B ',Name,':',ClassName);
  //------------

  //DoSetBounds(ALeft, ATop, AWidth, AHeight);
  //DebugInvalidPos(1);

  // change base bounds
  // (base bounds are the base for the automatic resizing)
  if not KeepBase then
    ; //UpdateAnchorRules;
  //DebugInvalidPos(2);

  // lock size messages
  //inc(FSizeLock);
  try
    // notify before autosizing
    //BoundsChanged;
    if not PosSizeChanged then exit;
    if (Parent<>nil) or SizeChanged then
      //AdjustSize;
  finally
    //dec(FSizeLock);
  end;
  if not PosSizeChanged then exit;
  //DebugInvalidPos(3);

  // send messages, if this is the top level call
  //if FSizeLock > 0 then exit;

  // invalidate
  if (csDesigning in ComponentState) and (Parent <> nil) then
    //Parent.Invalidate
  else
  //if (not (csLoading in ComponentState)) and (not (Self is TWinControl)) then
    //Invalidate;
  //DebugInvalidPos(4);
  // notify user about resize
  if (not (csLoading in ComponentState)) then
  begin
    //Resize;
    //DebugInvalidPos(5);
    //CheckOnChangeBounds;
    //DebugInvalidPos(6);
    // for delphi compatibility send size/move messages
    if PosSizeChanged then
      {SendMoveSizeMessages(SizeChanged,PosChanged)};
  end;
end;                             
Ich habe einiges hier auskommentiert, da ich diese Methode per Copy und Paste nicht 1:1 in mein Projekt übernehmen kann. Ich muss sie anpassen.

Wer kann mir deshalb den genauen Ablauf dieser Methode erklären?


Wer kann mir den genauen Ablauf erklären?

wp_xyz
Beiträge: 4885
Registriert: Fr 8. Apr 2011, 09:01

Re: Methodenablauf verstehen, TControl.ChangeBounds()

Beitrag von wp_xyz »

Die Größeneinstellung von Controls mit AutoSize, Constraints, ChildSizing, Anchors usw. gehört mit zum Kompliziertesten, das die LCL zu bieten hat. Daher bin ich überzeugt, dass dich Änderungen an den internen Abläufen mit langer Fehlersuche "belohnen" werden.

Vielleicht gibt https://wiki.freepascal.org/Autosize_/_Layout ein paar Hinweise, was alles berücksichtigt ist.

thosch
Beiträge: 324
Registriert: Mo 10. Jul 2017, 20:32

Re: Methodenablauf verstehen, TControl.ChangeBounds()

Beitrag von thosch »

Dann halt so, da beschäftige ich mich halt mit der Doku.

Danke für den Link!

Antworten