Introduction
This article describes how you can let arrange your Windows form its layout automatically by giving its handle to the layout persistence control.
Notice: Base idea comes from the article: Persistence of Window State and Appearance for .NET Applications (Alexander Fedorenko). I took his code that cared basically just about the top level controls to be found in the forms components collection. Now making heavy use of recursion, the control is able to re-arrange all controls in forms even if they are subcontrols of subcontrols...
How to use
Simply refer the assembly and use it in your main form as shown.
using Dau.UI.Forms;
Then, create a single instance of the control and pass your main form's handle and the registry key name where it shall (re-)store its settings!
private FormPersistence formPersistence;
public MainForm()
{
InitializeComponent();
formPersistence = new FormPersistence(this,"Dau\\Test\\Settings");
formPersistence.IsSavingOnMove = false;
}
The last line tells the control not to save the settings while the form is being resized. This will increase the drawing performance of your application drastically. You won't mention the difference for a small count of controls being located on your form.
How it works
Since I took the idea from another article, I won't describe its clues here, but I'll briefly explain how I improved it to layout all subcontrols.
protected void SaveControlsRecursively ( Control.ControlCollection p_controls,
string p_sParentControlConstantsPath)
{
string sCurrentPath;
foreach(Control control in p_controls)
{
sCurrentPath = p_sParentControlConstantsPath +"." + control.Name;
SaveControl(control,sCurrentPath );
if ( m_Recursive )
SaveControlsRecursively ( control.Controls , sCurrentPath );
}
}
As you can see in the snippet, I call the same function in itself if recursive is true
. All control containers do have the property Controls
which, if you call, makes it pretty easy to loop through a control and all of its subcontrols recursively. The abort criteria is kind of hidden here but your code won't loop endlessly because the recursive call happens at the end of the control's loop. And if a control has no more subcontrols then the function will exit.
In the function RestoreControl
, the most trickiest thing is done:
if ( control.Dock != DockStyle.None )
control.Bounds = profile.Read(p_sCurrentName + "." + Constants.Bounds );
The function applies the Bounds
values only if the control's DockStyle
was set to some dockstyle. This is very important because, you must not handle the layout of controls that are using anchors (self positioning anyway).
That's basically all about it. Don't forget to call the persistence object's dispose method because it keeps its registry key open as long as the object is alive in order to ensure best performance!