B
Bruce Schechter
An acquaintance just asked the following excellent question, which I need
help to answer for him...
"What I would like to know is the best way to switch from one form to
another in a multiform application which allows me to close forms which I no
longer need, thereby minimizing my use of memory.
Assume that I have an application with ten forms labeled Form 1 through Form
10. Assume that when my application begins Main creates an instance of Form
1. Now when a user wants to switch from Form 1 to Form 2 the simplest method
is to create an instance of Form 2 which belongs to Form 1. One of the
negative side effects of this approach is that it means that we can't close
Form 1 as long as Form 2 is open.
Now let's move from Form 2 to Form 3. Again, one option is to create a Form
3 instance which belongs to Form 2. Once again we can't close Form 2 until
we close Form 3. From this you should see a pattern: Each new object belongs
to the last object and eventually we will have a chain of objects streching
all the way back to Main.
Even more depressing is what will happen when we return to a form we
previously visited. For example, what will happen if after creating an
instance of Form 10 (which belongs to Form 9) the user chooses to return to
Form 3. In our current example our application already has an instance of
Form 3 which belongs to Form 2. However, while Form 2 already holds a
reference to Form 3, how can we access that reference? I don't see how we
can. So now we must create a new instance of Form 3 which is owned by Form
10. Now keep jumping back and forth between different forms and what do we
have? A real mess in my opinion.
My previous solution with which I am not especially happy is to place a
series of "form switching" functions in a separate class which then acts as
the designated owner of all of my forms. When a user wants to switch from
Form 1 to Form 2, he calls a method in the designated owner class which
creates an instance of Form 2. When this method which does nothing more than
to call the constructor for Form 2 (and then display it) completes, Form 1
can close.
Using this approach I ran into two problems. The first was that in my case I
usually had quite a few parameters that I wanted to pass along to the new
form. This probably reflects the complexity of my application and is likely
just unavoidable. Recently I have been thinking that I probably want to
explore the use of static variables as an alternative to passing parameters
to the form switching method. Under this new approach, before Form 1
switches to Form 2, I can set Form 2's static variables based on information
collected on Form 1. Moreover, if there is any state information for Form 1
which I want to persist in case there is a return to Form 1, I can save it
in Form 1 static variables.
A second even greater problem is that in order to make Form 2 visible to the
user, my designated owner method has to call Form2.ShowDialog().
Unfortunately, this method does not complete until after Form 2 closes.
Therefore, my approach results in exactly the same house of cards which I
described above. I gave some brief thought to the idea of using static
constructors but a static constructor only is useful to initialize static
data members.
Perhaps one solution is to spawn a separate thread for each new form and /
or make an asynchronous call to the designated owner method constructing
each new form. That seems like an awfully complex solution.
One thing that certainly surprises me is that one would think that this
issue would be pretty common. Isn't there some recognized way of dealing
with this issue in an efficient manner. So far my research hasn't disclosed
any."
Can anyone propose a solution or a link to related documentation?
Cheers, and Thanks,
-- Bruce
help to answer for him...
"What I would like to know is the best way to switch from one form to
another in a multiform application which allows me to close forms which I no
longer need, thereby minimizing my use of memory.
Assume that I have an application with ten forms labeled Form 1 through Form
10. Assume that when my application begins Main creates an instance of Form
1. Now when a user wants to switch from Form 1 to Form 2 the simplest method
is to create an instance of Form 2 which belongs to Form 1. One of the
negative side effects of this approach is that it means that we can't close
Form 1 as long as Form 2 is open.
Now let's move from Form 2 to Form 3. Again, one option is to create a Form
3 instance which belongs to Form 2. Once again we can't close Form 2 until
we close Form 3. From this you should see a pattern: Each new object belongs
to the last object and eventually we will have a chain of objects streching
all the way back to Main.
Even more depressing is what will happen when we return to a form we
previously visited. For example, what will happen if after creating an
instance of Form 10 (which belongs to Form 9) the user chooses to return to
Form 3. In our current example our application already has an instance of
Form 3 which belongs to Form 2. However, while Form 2 already holds a
reference to Form 3, how can we access that reference? I don't see how we
can. So now we must create a new instance of Form 3 which is owned by Form
10. Now keep jumping back and forth between different forms and what do we
have? A real mess in my opinion.
My previous solution with which I am not especially happy is to place a
series of "form switching" functions in a separate class which then acts as
the designated owner of all of my forms. When a user wants to switch from
Form 1 to Form 2, he calls a method in the designated owner class which
creates an instance of Form 2. When this method which does nothing more than
to call the constructor for Form 2 (and then display it) completes, Form 1
can close.
Using this approach I ran into two problems. The first was that in my case I
usually had quite a few parameters that I wanted to pass along to the new
form. This probably reflects the complexity of my application and is likely
just unavoidable. Recently I have been thinking that I probably want to
explore the use of static variables as an alternative to passing parameters
to the form switching method. Under this new approach, before Form 1
switches to Form 2, I can set Form 2's static variables based on information
collected on Form 1. Moreover, if there is any state information for Form 1
which I want to persist in case there is a return to Form 1, I can save it
in Form 1 static variables.
A second even greater problem is that in order to make Form 2 visible to the
user, my designated owner method has to call Form2.ShowDialog().
Unfortunately, this method does not complete until after Form 2 closes.
Therefore, my approach results in exactly the same house of cards which I
described above. I gave some brief thought to the idea of using static
constructors but a static constructor only is useful to initialize static
data members.
Perhaps one solution is to spawn a separate thread for each new form and /
or make an asynchronous call to the designated owner method constructing
each new form. That seems like an awfully complex solution.
One thing that certainly surprises me is that one would think that this
issue would be pretty common. Isn't there some recognized way of dealing
with this issue in an efficient manner. So far my research hasn't disclosed
any."
Can anyone propose a solution or a link to related documentation?
Cheers, and Thanks,
-- Bruce