A Windows Form as a Dialog Box
This article was prompted by my desire to offer a Windows form in the manner of a File Dialog Box but populated with my own buttons and textboxes. I could display the "dialog" form and make it disappear, no problem. My problem was passing the results of the dialog operation back to the main program and passing configuration information to the dialog box prior to display.
This article presents the solution to my dilemma. Two forms are presented. The first is created by Main()
. The second is created then displayed by code in the first form's load event. Think of Form1
as the main program and Form2
as the dialog box. What is passed back and forth is an object of type DateTime
. If your data to and from the dialog box can be reduced to an object, this technique should work.
How to effectively Pass information from one Form to another
In each Form's class template, I thoughtfully provided private storage for the object that's to be passed: private DateTime form1_Time
, a method of getting the object (From_Form1_object_form1_GetTime()
) and a method to store the object (In_Form1_object_form1_Store_Time(DateTime timeType)
). Here're those three (one field and two methods) for class Form1
. Form2
contains very similar methods and private data.
private DateTime form1_Time;
public DateTime From_Form1_object_form1_GetTime()
{
return form1_Time;
}
public void In_Form1_object_form1_Store_Time(DateTime timeType)
{
form1_Time = timeType;
}
private Form2 form2;
Notice above that I have a private field variable that is a Form2
type, form2
. I allocate memory thus creating the actual object "form2
" when the Form1_Load
event occurs. Here's the code:
private void Form1_Load(object sender, System.EventArgs e)
{
form2 = new Form2();
form2.BringToFront();
form2.Show();
}
This is just about all we need. The newly created form2
object has access (scope) to the private
object (the form2
's DateTime
construction) through form2
's wordy Get
and Store
methods described above. If you think of form1
as your main program, we can send information to form2
(dialog box) by calling these methods. For example, your current configuration could be stuffed into an object and sent to the DialogBox
(here Form2
) for presentation to the user. Here in this demonstration program, I'm just sending the current time in response to a button click on Form1
.
private void button1_Click_Form1_SendTime(object sender, System.EventArgs e)
{
DateTime buttonClickTime = DateTime.Now;
form2.In_Form2_object_form2_Store_Time(buttonClickTime);
}
Now, consider that the user has completed filling out the dialog box and clicks the "accept" button (in this analogy, Form2
's Send Time button). How do you get the object full of information back in the main program. Just invoke Form2
's Get
method as shown below:
private void button2_Click_Form1_GetTime(object sender, System.EventArgs e)
{
DateTime timeStoredIn_form2 = form2.From_Form2_object_form2_GetTime();
textBox1.Text = String.Format( "{0:T}",timeStoredIn_form2);
}
A click on the Get Time button on Form1
invokes the object form2
causing execution on the method From_Form2_object_form2_GetTime()
. The method completes returning the DateTime
object from form2
's private memory space. Then the DateTime
object is formatted and presented in a textbox on Form1
.
So we've successfully passed access back and forth to a private object by invoking public methods!
Finally, notice that when you first start the program, the Get Time button returns 12:00:00 showing that the private object is indeed empty (null
).
Getting a Dialog Result from Form2
I didn't discover this until later but using a form as a dialog box is apparently a common technique. In fact, you can get a DialogResult
from a button press in the same manner as a MessageBox
. Here's a snip from the .NET Doc that shows this idea. A wonderful idea, but useless without knowing how to retrieve information from the DialogBox
.
public void ShowMyDialogBox()
{
Form2 testDialog = new Form2();
if (testDialog.ShowDialog(this) == DialogResult.OK)
{
this.txtResult.Text = testDialog.TextBox1.Text;
}
else
{
this.txtResult.Text = "Cancelled";
}
testDialog.Dispose();
}
I have no idea why something so incredibly easy now was so difficult then. I literally spend hours figuring out how to pass data between two .NET Forms. Good thing I'm retired and patient! Back in the old days of K + R C (pre C++ and pre C#), you could just put a fence around a heap of memory and then drive your bits and bytes in, out and around at will. The main program and dialog box both had access to the memory. One wrote and the other received. Incredibly convenient but then along came the virus writers. Anyway, I hope my explanation was informative and helpful.
History
- Version 1 - released January 2004.