Manage a ControlCollection - display a new element at the bottom

202 Views Asked by At

I need to add a simple at the bottom of an existing view. It is composed of nested panels in a code which I know is not proper. But what I want given my available time is (simple as it sounds) to add my link below what is existing.

In a few words, there is a ControlCollection object being displayed (this.Controls), and I can't locate an element (LinkLabel or TableLayoutPanel) below the other elements.

Here is the minimal existing code :

private void SetAppearance()
{
    pnlTitle = new Panel();
    pnlTitle.x = ...
    this.Controls.Add(pnlTitle);

    lblTitle = new Label();
    lblTitle.x = ...
    pnlTitle.Controls.Add(lblTitle);

    tlpnlCountryOfOrigin = new TableLayoutPanel();
    tlpnlCountryOfOrigin.x = ...
    pnlTitle.Controls.Add(tlpnlCountryOfOrigin);

    CountryOfOrigin = new Label();
    CountryOfOrigin.x = ...
    tlpnlCountryOfOrigin.Controls.Add(CountryOfOrigin, 0, 0);

    cbbCountryOrigin = new ComboBoxWithBorders();
    cbbCountryOrigin.x = ...
    tlpnlCountryOfOrigin.Controls.Add(cbbCountryOrigin, 1, 0);

    pnlSupportInfo = new TableLayoutPanel();
    pnlSupportInfo.x = ...
    this.Controls.Add(pnlSupportInfo);
}

And I am just basically wanting to add my LinkLabel at the bottom of that, with that :

lnkSendLogs = new LinkLabel
{
    Font = new Font(ArialBold12px, FontStyle.Regular | FontStyle.Underline),
    AutoSize = true,
    LinkColor = InfomaxConstants.Colors.Red,
    Margin = new Padding(0),
    Text = LabelManager.GetLabel("TEXTTOGETLABEL")
};
this.Controls.Add(lnkSendLogs);

Or even with a nested TableLayoutPanel (which I know is not a good practice) :

tlpnlSendLogs = new TableLayoutPanel();
tlpnlSendLogs.ColumnCount = 2;
tlpnlSendLogs.ColumnStyles.Clear();
tlpnlSendLogs.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 100));
tlpnlSendLogs.ColumnStyles.Add(new ColumnStyle(SizeType.AutoSize));
lnkSendLogs = new LinkLabel
{
    Font = new Font(ArialBold12px, FontStyle.Regular | FontStyle.Underline),
    AutoSize = true,
    LinkColor = InfomaxConstants.Colors.Red,
    Margin = new Padding(0),
    Text = LabelManager.GetLabel("TEXTTOGETLABEL")
};      
lnkSendLogs.Dock = DockStyle.Fill;
tlpnlSendLogs.Controls.Add(lnkSendLogs, 0, 0);
this.Controls.Add(tlpnlSendLogs);

But the link is always appearing behind other elements, instead of below them.

The rendered

The question is thus the very basic : How to add a simple LinkLabel appearing at the bottom of a view containing a few elements like Panels and TableLayoutPanels ?

1

There are 1 best solutions below

0
On BEST ANSWER

The first problem was that the controls had no location settings, which makes room for random and unwanted things.

Two things to have in mind for the ControlCollection elements:

  • Locate them
  • Order them

The thing to know is that the Controls of a ControlCollection are ordered based on their index, AND the one of bigger index will be the one the most at the border of the container (whatever the order in which the children elements anchor are being defined) (https://stackoverflow.com/a/7685041/6617804)

A solution is

1-To set the position of all the ControlCollection elements to the top of their container

pnlTitle.Dock = DockStyle.Top;
pnlSupportInfo.Dock = DockStyle.Top;
tlpnlSendLogs.Dock = DockStyle.Top;

Or the exact same :

pnlTitle.Anchor = (AnchorStyles.Left | AnchorStyles.Top);
pnlSupportInfo.Anchor = (AnchorStyles.Left | AnchorStyles.Top);
tlpnlSendLogs.Anchor = (AnchorStyles.Left | AnchorStyles.Top);

2.1-To arrange the child in the opposite order If we need to (in my case where we want to display them in the opposite order)

this.Controls.SetChildIndex(pnlTitle, 2);
this.Controls.SetChildIndex(pnlSupportInfo, 1);
this.Controls.SetChildIndex(tlpnlSendLogs, 0);

2.2-OR to add them directly in the order they need to be for the display :

this.Controls.Add(tlpnlSendLogs);
this.Controls.Add(pnlSupportInfo);
this.Controls.Add(pnlTitle);

Instead of :

this.Controls.Add(pnlTitle);
this.Controls.Add(pnlSupportInfo);
this.Controls.Add(tlpnlSendLogs);