49

FlowLayoutPanelに挿入されたアイテムをFlowLayoutPanelの自動サイズにすることは可能ですか?次に例を示します。

1つのFlowLayoutPanelと3つのボタンが内部にあるフォーム:

ここに画像の説明を入力してください

フォームのサイズを変更すると、コントロールは次のようになります。「左から右」に配置されます

ここに画像の説明を入力してください

私が欲しいのはこれです:コントロールはFlowLayoutPanelの幅を持つ必要があります:

ここに画像の説明を入力してください

これを行う方法についてのアイデアはありますか?FlowDirectionを変更し、Anchorプロパティで遊んでいましたが、運がありませんでした。

もちろん、FlowLayoutPanel_Resizeイベントでコントロールのサイズを変更することもできますが、約500のユーザーコントロールを追加したいと思います。テストしたところ、速度が遅くなりました。

4

7 に答える 7

49

この場合、1つの列でTableLayoutPanelを使用することをお勧めします。TableLayoutPanelは、FlowLayoutPanelよりもはるかに予測可能で堅実であることがわかりました。

FlowLayoutPanelを引き続き使用する場合の別のオプションは、最初のコントロール幅を目的の幅に設定し、他のすべてのコントロールにはDock=Topを使用することです。

于 2011-03-22T20:40:22.970 に答える
20

これを行う簡単な方法です。flowLayoutPannelのSizeChangedevnentをバインドし、含まれているコントロールのサイズを変更するだけです。好き:

private void myFlowLayoutPannel_SizeChanged(object sender, EventArgs e)
{
    myFlowLayoutPannel.SuspendLayout();
    foreach (Control ctrl in pnSMS.Controls)
    {
        if (ctrl is Button) ctrl.Width = pnSMS.ClientSize.Width;
    }
    myFlowLayoutPannel.ResumeLayout();
}
于 2013-03-20T16:27:44.667 に答える
10

ここにStackPanelクラスがあります。

/// <summary>
/// A stackpanel similar to the Wpf stackpanel.
/// </summary>
public class StackPanel: FlowLayoutPanel
{
    public StackPanel(): base()
    {
        InitializeComponent();
        this.ForceAutoresizeOfControls = true;
    }

    private void InitializeComponent()
    {
        this.SuspendLayout();
        //
        // StackPanel
        //
        this.AutoSizeMode = System.Windows.Forms.AutoSizeMode.GrowAndShrink;
        this.WrapContents = false;
        this.ResumeLayout(false);
    }

    /// <summary>
    /// Override it just in order to hide it in design mode.
    /// </summary>
    [Browsable(false)]
    [DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
    public new bool WrapContents
    {
        get { return base.WrapContents; }
        set { base.WrapContents = value; }
    }

    /// <summary>
    /// Override it just in order to set its default value.
    /// </summary>
    [DefaultValue(typeof(AutoSizeMode), "GrowAndShrink")]
    public override AutoSizeMode AutoSizeMode
    {
        get { return base.AutoSizeMode; }
        set { base.AutoSizeMode = value; }
    }

    /// <summary>
    /// Get or set a value that when is true forces the resizing of each control.
    /// If this value is false then only control that have AutoSize == true will be resized to
    /// fit the client size of this container.
    /// </summary>
    [DefaultValue(true)]
    public bool ForceAutoresizeOfControls { get; set; }

    protected override void OnSizeChanged(EventArgs e)
    {
        base.OnSizeChanged(e);
        this.SuspendLayout();
        switch (FlowDirection)
        {
            case FlowDirection.BottomUp:
            case FlowDirection.TopDown:
                foreach (Control control in this.Controls)
                    if (ForceAutoresizeOfControls || control.AutoSize)
                        control.Width = this.ClientSize.Width - control.Margin.Left - control.Margin.Right;
                break;
            case FlowDirection.LeftToRight:
            case FlowDirection.RightToLeft:
                foreach (Control control in this.Controls)
                    if (ForceAutoresizeOfControls || control.AutoSize)
                        control.Height = this.ClientSize.Height - control.Margin.Top - control.Margin.Bottom;
                break;
            default:
                break;
        }
        this.ResumeLayout();
    }

    protected override void OnLayout(LayoutEventArgs levent)
    {
        base.OnLayout(levent);

        if (levent != null && levent.AffectedControl != null)
        {
            Control control = levent.AffectedControl;
            if (ForceAutoresizeOfControls || control.AutoSize)
            {
                switch (FlowDirection)
                {
                    case FlowDirection.BottomUp:
                    case FlowDirection.TopDown:
                        control.Width = this.ClientSize.Width - control.Margin.Left - control.Margin.Right;
                        break;
                    case FlowDirection.LeftToRight:
                    case FlowDirection.RightToLeft:
                        control.Height = this.ClientSize.Height - control.Margin.Top - control.Margin.Bottom;
                        break;
                    default:
                        break;
                }
            }
        }
    }
}
于 2017-04-12T08:16:56.590 に答える
5

ここは必要ありませんFlowLayoutPanel

Panel通常のコントロールでやりたいことができるはずです。フォームに合わせて伸びるように4つの側面すべてに固定し、ボタンを追加してすべてDock:Topに設定します。

編集-@UsamaAzizコメントへの応答。

パネルの下部を超えて非表示になっているコントロールにアクセスできるようにするには、パネルの「AutoScroll」プロパティをTrueに設定します。これにより、必要に応じてパネルに垂直スクロールバーが追加されます。

仕事は終わりました。

于 2018-08-13T14:28:40.947 に答える
3

MSDNFlowLayoutPanelによると、特定の方法でコントロールを配置します。

...垂直方向のフロー方向の場合、FlowLayoutPanelコントロールは、列内の最も幅の広い子コントロールから暗黙の列の幅を計算します。アンカーまたはドックプロパティを持つこの列の他のすべてのコントロールは、 この暗黙の列に合うように配置または拡大されます。この動作は、水平方向の流れ方向でも同様に機能します。

理想的ではありませんが、1つの子コントロールがコンテナと同じ幅に設定され、残りのコントロールがに設定されている限り、これをネイティブに実行できますDock

于 2015-09-29T02:22:10.240 に答える
2

私は提案します...ボタンのアンカーで遊んでみてください...それを次のように設定してみてください

Button1.Anchor = (AnchoreStyle.Left or AnchoreStyle.Right)

またはプロパティで設定します...

次に、FlowLayoutPanelではなくPanel内に配置します...;)

于 2012-02-23T03:55:05.947 に答える
1

他の回答が述べているように、パネル自体はボタンを処理するのに十分です。私のために働くコードのビット:

public class ButtonWindow : Panel
{
    public ButtonWindow()
    {
        Dock = DockStyle.Fill;
        AutoScroll = true;

        for (int i = 0; i < 500; i++) 
        {
           Button button = new Button() { Height = 100, Dock = DockStyle.Top };
           Controls.Add(button);
        }
    }
}

良い1日を。

于 2018-12-05T18:19:24.220 に答える