Using Menus and MDI Forms
One of the worst interfaces ever created was the Menu Editor in Visual Basic 6 and earlier. It was a top complaint of developers; Microsoft heard their screams and provided an amazing, easy-to-use Menu Editor in Windows Forms. In addition to the editor being great, because items added to a menu are derived from a Menu class, you can easily create menu items dynamically at runtime, which was almost possible in Visual Basic 6. To test the new Menu Editor's features, you're going to create a Multiple Document Interface (MDI) application. The flexibility of MDI applications in .NET has also improved dramatically, as you'll see when you're done with the following exercise.
Note
The HelloNET application has been a SDI (single document interface) application until now. That means each form in the application is its own container. An MDI application has a parent form that contains children, and the child forms can't leave the screen boundary of the parent. MDI applications used to be the most popular type of UI, but in recent years SDI applications and Explorer-style applications have become more popular. Microsoft drives the UI trends with each new release of any product. Consider Microsoft Outlook: The Outlook Barstyle spread like wildfire when it was introduced, and it can be seen in hundreds of third-party applications today.To get started, add three new forms to the HelloNET application by right-clicking the HelloNET project name in the Solution Explorer and selecting Add, New Windows Form. Name the new forms as follows:- parentForm
- child1
- child2
You'll notice that there is no MDI form template. This is now just a property on a form. After the three new forms are added, your Solution Explorer should look something like Figure 3.11.
Figure 3.11. The HelloNET application after adding three new forms.

From the Solution Explorer, double-click the parentForm form so that it's in the Forms Designer. In the Properties window, change the IsMdiContainer property to True. You'll notice that the form now has a dark gray background color, which is the indication that it's a MDI parent form.Next, drag a MainMenu control from the Toolbox to the form. The MainMenu control is a nonvisual control, which means it doesn't appear as part of the form. When nonvisual controls are added to a form, the screen splits and the controls are added to the bottom portion of the Forms Designer. This makes it very easy to see what nonvisual controls have been added to a form. At this point, your application should look something like Figure 3.12.
Figure 3.12. The parentForm after adding a MainMenu control.

Adding menu items to the MainMenu is very intuitive: You simply type the name that you want the menu to display, and it shows up. Notice that you can go as many levels deep into a menu as you wantyou just keep typing where the arrow is in the editor, and that's where the menu item appears. Use the up-, down-, right-, and left-arrow keys on your keyboard to navigate the menu levels. Figure 3.13 demonstrates the addition of items to a MainMenu.
Figure 3.13. Adding items to a MainMenu.

Add the following five menu items to the MainMenu control:
- Top Level Menu
&File - Sub Level 1
&Show child1, Name = showChild1 - Sub Level 2
&Show child2, Name = showChild2 - Sub Level 3
&Forms Count, Name = formsCount - Sub Level 4
&Close All Forms, Name = exitApplication
While adding items to the menu, you can right-click on the menu itself to get the contextual menu with available options for the MainMenu control. One of the most useful items is the EditNames toggle. If you click EditNames, you can change the name of the menu item directly from the Menu Editor. You can also do this via the Properties window. From the Properties window, some of the individual properties that can be set are the Shortcut, RadioCheck, and Visible properties.
Note
In the code you just added to create the menu items, an ampersand was placed in front of each of the menu item captions. The ampersand will place an underscore underneath the character it prefixes in the menu, and will allow the end user to use the ALT key in combination with the underlined character as a shortcut to the menu item.After you've added the new menu items, you'll add some code that brings up the child1 and child2 forms, gets a count of open forms, and exits the application.To do this, add the code in Listing 3.5 to the click events for their corresponding controls.Listing 3.5 The Code-Behind for the MDI Application

Private Sub MenuItem2_Click(ByVal sender As System.Object, _
ByVal e As System.EventArgs) Handles showChild1.Click
Dim f As New child1()
f.MdiParent = Me
f.Show()
End Sub
Private Sub showChild2_Click(ByVal sender As System.Object, _
ByVal e As System.EventArgs) Handles showChild2.Click
Dim f As New child2()
f.MdiParent = Me
f.Show()
End Sub
Private Sub formsCount_Click(ByVal sender As System.Object, _
ByVal e As System.EventArgs) Handles formsCount.Click
' Get the number of children
MessageBox.Show(Me.MdiChildren.Length)
' Declare a Form object to get object properties
Dim f As Form
For Each f In Me.MdiChildren
MessageBox.Show(f.Name.ToString)
Next
End Sub
Private Sub closeAllForms_Click(ByVal sender As System.Object, _
ByVal e As System.EventArgs) Handles closeAllForms.Click
' Declare a Form object and call the Close event
Dim f As Form
For Each f In Me.MdiChildren
f.Close()
Next
End Sub
Private Sub exitApplication_Click(ByVal sender As System.Object, _
ByVal e As System.EventArgs) Handles exitApplication.Click
' Exit the Application
Application.Exit()
End Sub

private void showChild2_Click(object sender, System.EventArgs e)
{
Form f = new child1();
f.MdiParent = this;
f.Show();
}
private void showChild1_Click(object sender, System.EventArgs e)
{
Form f = new child2();
f.MdiParent = this;
f.Show();
}
private void formsCount_Click(object sender, System.EventArgs e)
{
MessageBox.Show(this.MdiChildren.Length.ToString());
foreach (Form f in this.MdiChildren)
{
MessageBox.Show(f.Name.ToString());
}
}
private void closeAllForms_Click(object sender, System.EventArgs e)
{
foreach (Form f in this.MdiChildren)
{
f.Close();
}
}
private void exitApplication_Click(object sender, System.EventArgs e)
{
Application.Exit();
}
}
Now press the F5 key to run the application. You should change the StartUp form in the parent form before starting. When the application is running, click the Show Child1 and Show Child2 menu items a few times each. You should see something like Figure 3.14.
Figure 3.14. Multiple MDIChildren open in an MDIParent form.

Each time you set the variable f to a new instance of a form, you're setting the MdiParent property to the current form. This makes it an MdiChild. The code for determining the number of MdiChildren open is simply the Length property of the MdiChildren class. Because the form is an object, you can use the For Each method to iterate through its collection to retrieve properties, methods, and events. So, by using the For Each method and calling the form's Close method, you're firing the Form_Closing method of each active form.To exit the application, you called the Application.Exit() method. The Application object is similar to the App object in Visual Basic 6; it contains information about the current running application. It's important to note that the Closing event won't fire when you call the Application.Exit() method. So, make sure that you gracefully close your windows, and then call Application.Exit(). The code in the closeAllForms click event demonstrates the correct way to accomplish that.Table 3.3 has some common properties of the Application object, and Table 3.4 has some common methods of the Application object that you'll find useful.