Einzelnen Beitrag anzeigen

Benutzerbild von Sir Rufo
Sir Rufo

Registriert seit: 5. Jan 2005
Ort: Stadthagen
9.454 Beiträge
 
Delphi 10 Seattle Enterprise
 
#9

AW: Anordnung von Align=Top Controls in Firemonkey

  Alt 30. Okt 2015, 13:51
Sieht zwar wild aus, aber das sollte die Controls zuverlässig in ihrem Container positionieren:
Delphi-Quellcode:
procedure TMainForm.RealignControls( const AParent: TFmxObject );
var
  LArea : TRectF;
  LContainer : IContainerObject;
  LControls : TArray<TControl>;
  LFmxObjectToControl : TFunction<TFmxObject, TControl>; // TFunc<T1,T2> mit const Argumenten
  LFmxObjectControlFilter: TFilter<TFmxObject>; // TPredicate<T> mit const Argument
  LArrangeControls : TAction<TControl>; // TProc<T> mit const Argument
  LAlignControlFilter : TFilter<TControl>; // TPredicate<T> mit const Argument
  LMostAlignControlFilter: TFilter<TControl>; // TPredicate<T> mit const Argument
begin
  if not Assigned( AParent )
  then
    raise EArgumentNilException.Create( 'AParent' );

  if not Supports( AParent, IContainerObject, LContainer )
  then
    Exit; // nicht für dieses Object

  LArea := TRectF.Create(
    TPointF.Zero,
    LContainer.ContainerWidth,
    LContainer.ContainerHeight );

  LArrangeControls :=
    procedure( const c: TControl )
    begin
      case c.Align of
        TAlignLayout.MostTop, TAlignLayout.Top:
          begin
            c.Position.Y := LArea.Top;
            LArea.Inflate( 0, -c.Height, 0, 0 );
          end;
        TAlignLayout.MostLeft, TAlignLayout.Left:
          begin
            c.Position.X := LArea.Left;
            LArea.Inflate( -c.Width, 0, 0, 0 );
          end;
        TAlignLayout.MostRight, TAlignLayout.Right:
          begin
            c.Position.X := LArea.Right - c.Width;
            LArea.Inflate( 0, 0, -c.Width, 0 );
          end;
        TAlignLayout.MostBottom, TAlignLayout.Bottom:
          begin
            c.Position.Y := LArea.Bottom - c.Height;
            LArea.Inflate( 0, 0, 0, -c.Height );
          end;
      end;
    end;

  LAlignControlFilter :=
    function( const c: TControl ): Boolean
    begin
      Result := c.Align in [ TAlignLayout.Top, TAlignLayout.Left, TAlignLayout.Right, TAlignLayout.Bottom ];
    end;

  LMostAlignControlFilter :=
    function( const c: TControl ): Boolean
    begin
      Result := c.Align in [ TAlignLayout.MostTop, TAlignLayout.MostLeft, TAlignLayout.MostRight, TAlignLayout.MostBottom ];
    end;

  LFmxObjectToControl :=
    function( const o: TFmxObject ): TControl
    begin
      Result := TControl( o );
    end;

  LFmxObjectControlFilter :=
    function( const o: TFmxObject ): Boolean
    begin
      Result := o is TControl;
    end;

  // Alle Controls von AParent holen
  LControls := TArray.Cast<TFmxObject, TControl>(
    { Values } AParent.Children.ToArray,
    { ResultSelector } LFmxObjectToControl,
    { Filter } LFmxObjectControlFilter );

  // erst die Controls, die Most... aligned sind
  TArray.ForEach<TControl>( // führt die Action auf jedem Eintrag in Values aus, wenn der Filter zutrifft
    { Values } LControls,
    { Action } LArrangeControls,
    { Filter } LMostAlignControlFilter );

  // dann den Rest
  TArray.ForEach<TControl>( // führt die Action auf jedem Eintrag in Values aus, wenn der Filter zutrifft
    { Values } LControls,
    { Action } LArrangeControls,
    { Filter } LAlignControlFilter );
end;
(BTW: Ich hasse Schleifchen schreiben, darum habe ich diese Wrapper im Einsatz)
Kaum macht man's richtig - schon funktioniert's
Zertifikat: Sir Rufo (Fingerprint: ‎ea 0a 4c 14 0d b6 3a a4 c1 c5 b9 dc 90 9d f0 e9 de 13 da 60)

Geändert von Sir Rufo (30. Okt 2015 um 14:01 Uhr)
  Mit Zitat antworten Zitat