Winforms 流程布局面板中控件的重新排序

Winforms 流程布局面板中控件的重新排序,winforms,controls,combobox,flowlayoutpanel,Winforms,Controls,Combobox,Flowlayoutpanel,在C#winform应用程序中使用flowlayoutPanel时遇到问题。我基本上有一个流程布局面板,它有3个部分 第1节是一组2个控件。。两个下拉控件,它们的顺序始终相同,在所有实例中始终可见 第2节是一组5种不同的控件。。。基于一系列因素,5个控件中的1个控件变为可见,所有其他控件的visible属性设置为false 第3节是一组3个控件。。与第1节一样,它们始终处于相同的顺序,并且始终可见 因此,这归结为第2部分是可变的,其他部分是静态的 问题来自第2节。。。当我更改任何控件的可见性时,

在C#winform应用程序中使用flowlayoutPanel时遇到问题。我基本上有一个流程布局面板,它有3个部分

第1节是一组2个控件。。两个下拉控件,它们的顺序始终相同,在所有实例中始终可见

第2节是一组5种不同的控件。。。基于一系列因素,5个控件中的1个控件变为可见,所有其他控件的visible属性设置为false

第3节是一组3个控件。。与第1节一样,它们始终处于相同的顺序,并且始终可见

因此,这归结为第2部分是可变的,其他部分是静态的

问题来自第2节。。。当我更改任何控件的可见性时,它们看起来都很好(即第1节、第2节和第3节)。。。除非我将combobox控件设置为可见。。。。在那种情况下,而且只有在那种情况下。。订单变为(第1节、第3节、第2节)。。。在这种情况下,我不知道是什么原因导致订单不同步

在我的方法开始时,我基本上是将所有控件设置为Visible=false。。。然后我设置第1节Visible=true。。。然后循环第2节的条件,并将相应的控件Visible设置为true,最后将第3节的控件Visible设置为true


是否有人有过流程布局面板控件订购的经验?我搞不清楚组合框发生了什么。

在第2节中放入另一个flowlayoutpanel,然后将第2节控件放入其中是否更容易?这样,顶部面板中的可见控件永远不会更改,您也不必担心排序问题。

FlowLayoutPanel内部。
控件是一个名为
SetChildIndex(Control c,int index)
的方法函数,它允许您将对象设置为特定索引

由于FlowLayoutPanel使用控件的索引来确定绘制它们的顺序,所以您可以将其设置为要交换的控件索引,它会将该控件索引向上增加一个,然后每增加一个

下面是我在FlowLayoutPanel中重新排序PictureBoxes的一段代码

在名为
flowLayoutPanel1
的WinForm上添加FlowLayoutPanel:

public partial class TestForm: Form
{
   public TestForm()
    {
        InitializeComponent();
        this.flowLayoutPanel1.AllowDrop = true
    }

    private void AddImageToBlog(System.Drawing.Image image)
    {
        PictureBox pbox = new PictureBox();
        pbox.SizeMode = PictureBoxSizeMode.Zoom;            
        pbox.Height = (_picturebox_height * _ScaleFactor);
        pbox.Width = (_picturebox_width * _ScaleFactor);
        pbox.Visible = true;
        pbox.Image = image;

        pbox.MouseDown += new MouseEventHandler(pbox_MouseDown);
        pbox.DragOver += new DragEventHandler(pbox_DragOver);            
        pbox.AllowDrop = true;
        flpNewBlog.Controls.Add(pbox);
    }

    void pbox_DragOver(object sender, DragEventArgs e)
    {
        base.OnDragOver(e);
        // is another dragable
        if (e.Data.GetData(typeof(PictureBox)) != null)
        {
            FlowLayoutPanel p = (FlowLayoutPanel)(sender as PictureBox).Parent;                 
            //Current Position             
            int myIndex = p.Controls.GetChildIndex((sender as PictureBox));

            //Dragged to control to location of next picturebox
            PictureBox q = (PictureBox) e.Data.GetData(typeof(PictureBox));                
            p.Controls.SetChildIndex(q, myIndex);
        }           
    }

    void pbox_MouseDown(object sender, MouseEventArgs e)
    {
        base.OnMouseDown(e);
        DoDragDrop(sender, DragDropEffects.All);
    }
}

SetChildIndex
不会重置flowlayout面板中控件的顺序。因此,当我们执行
FlowLayoutPanel.GetNextControl(q,true)
时,输出不正确。

您可以对flowpanel上的控件重新排序,更改控件的父属性并按需要的顺序重新指定父属性。

尝试此通用解决方案,您可以根据用户控件中的属性对控件进行排序

// When adding and removing controls, the order is not kept.
var runsOrderedByStartDate = this.nodesFlowLayoutPanel.Controls.Cast<RunNodeControl>().Select(_ => new { StartDate = _.StartDateTime, RunControl = _ }).OrderBy(_ => _.StartDate).ToList();

// Sets index of controls according to their index in the ordered collection
foreach (var anonKeyValue in runsOrderedByStartDate)
{
    this.nodesFlowLayoutPanel.Controls.SetChildIndex(anonKeyValue.RunControl, runsOrderedByStartDate.IndexOf(anonKeyValue));
}
//添加和删除控件时,不保留顺序。
var runsOrderedByStartDate=this.nodesFlowLayoutPanel.Controls.Cast().Select(=>new{StartDate=uu.StartDateTime,RunControl=}).OrderBy(=>.StartDate).ToList();
//根据控件在有序集合中的索引设置控件的索引
foreach(runsOrderedByStartDate中的var anonKeyValue)
{
this.nodesFlowLayoutPanel.Controls.SetChildIndex(anonKeyValue.RunControl,runsOrderedByStartDate.IndexOf(anonKeyValue));
}

对于基本控件顺序,控制flowlayoutPanel中控件顺序的最简单方法是将flowlayoutPanel TabStop属性设置为true。将控件tabstop属性设置为True,并将选项卡顺序设置为希望控件显示的顺序。

您还需要更改选项卡顺序。您也可以在索引更改时设置此选项。