Custom panel with layout engine

I am trying to create my own Panel control using my own layout engine. I need every control that is added to my panel, which will be added below, and to get the full width (-padding), as shown below: enter image description here

Below is my code:

using System.Drawing; using System.Windows.Forms; using System.Windows.Forms.Layout; namespace VContainer { internal class VerticalFillList : Panel { public VerticalFillList() { AutoScroll = true; MinimumSize = new Size(200, 200); Size = new Size(200, 300); Padding = new Padding(10); } private readonly VerticalFillLayout _layoutEngine = new VerticalFillLayout(); public override LayoutEngine LayoutEngine { get { return _layoutEngine; } } private int _space = 10; public int Space { get { return _space; } set { _space = value; Invalidate(); } } } internal class VerticalFillLayout : LayoutEngine { public override bool Layout(object container, LayoutEventArgs layoutEventArgs) { var parent = container as VerticalFillList; Rectangle parentDisplayRectangle = parent.DisplayRectangle; Point nextControlLocation = parentDisplayRectangle.Location; foreach (Control c in parent.Controls) { if (!c.Visible) { continue; } c.Location = nextControlLocation; c.Width = parentDisplayRectangle.Width; nextControlLocation.Offset(0, c.Height + parent.Space); } return false; } } } 

The code works fine, except for one: when I add controls to my container, they are added correctly (the new one is below the parent, 100% of the width), but when the height of the controls is greater than my container height, I get horizontal scrollbars, but after adding control pairs removes the scroll bar. adding components

The same thing happens when I want to resize a container: resizing container

How can this be fixed? I just need to remove this horizontal scrollbar.

Of course, all improvements are welcome :)

I do not want to use a table layout or layout, as this gives me exactly what I need.

I need a simple container that arranges all the child controls from top to bottom and stretches them horizontally so that they occupy the same width as the horizontal scroll bar of the container is not needed.

+6
source share
2 answers

Here is a working example that, unfortunately, does not use the Layout Engine class. It simply relies on the OnControlAdded and OnControlRemoved methods, and also binds and sets the AutoScrollMinSize property to make sure that the horizontal scrollbar never appears:

 internal class VerticalPanel : Panel { private int space = 10; public int Space { get { return space; } set { space = value; LayoutControls(); } } protected override void OnControlAdded(ControlEventArgs e) { base.OnControlAdded(e); LayoutControls(); } protected override void OnControlRemoved(ControlEventArgs e) { base.OnControlRemoved(e); LayoutControls(); } private void LayoutControls() { int height = space; foreach (Control c in base.Controls) { height += c.Height + space; } base.AutoScrollMinSize = new Size(0, height); int top = base.AutoScrollPosition.Y + space; int width = base.ClientSize.Width - (space * 2); foreach (Control c in base.Controls) { c.SetBounds(space, top, width, c.Height); c.Anchor = AnchorStyles.Left | AnchorStyles.Top | AnchorStyles.Right; top += c.Height + space; } } } 
+3
source

You can install AnchorProperty on you. Buttons like:

 button1.Anchor = AnchorStyles.Left | AnchorStyles.Right | AnchorStyles.Top; 

Therefore they will be changed horizontally

-1
source

All Articles