How Does a Procedure Know When To Shut Down?

T

TC

I'm confused about the proper way to shut down my application.

I have a form which instantiates a control, which instantiates another
control, which instantiates yet another control that runs a time-
consuming loop. I put Application.DoEvents() into the loop so the user
can continue to work on the form while the loop is running. Everything
works great until the user wants to exit the application. The
application will not close until the loop is done. That's bad. I need
to interrupt the loop and close immediately when the user wants to
exit.

I've figured out that I can respond to the FormClosing event on the
form, then call a procedure in the child control which calls a
procedure in the grandchild control which calls a procedure in the
great-grandchild control that sets a flag and stops the loop.

My question is this: Do I really have to write a set of cascading
procedures to shut down the application like this, or is there a more
elegant way? It seems to me that the application must "know" it is
waiting for my loop to finish. How can I use this awareness from
within my code? Is there some event I can respond to, or some
application variable I can check?

I used to think Finalize existed for this purpose -- I thought it's
job was to announce a pending shutdown to every instance of a class/
control. However, I've learned that Finalize doesn't get called until
after the loop is already done, so it obviously doesn't help in this
case.

By the way, I've browsed this newsgroup and I've seen the suggestions
that starting a new thread is preferable to DoEvents. I'm working on
that, but I have a lot of cross-threading problems to resolve first.
In any case, I believe that is a separate issue. Even if I run my loop
on a separate thread, instead of using DoEvents, I still need to
figure out how to shut it down, right?


-TC
 
A

Armin Zingler

TC said:
I'm confused about the proper way to shut down my application.

I have a form which instantiates a control, which instantiates
another control, which instantiates yet another control that runs a
time- consuming loop. I put Application.DoEvents() into the loop so
the user can continue to work on the form while the loop is running.
Everything works great until the user wants to exit the application.
The application will not close until the loop is done. That's bad. I
need to interrupt the loop and close immediately when the user wants
to exit.

I've figured out that I can respond to the FormClosing event on the
form, then call a procedure in the child control which calls a
procedure in the grandchild control which calls a procedure in the
great-grandchild control that sets a flag and stops the loop.

My question is this: Do I really have to write a set of cascading
procedures to shut down the application like this, or is there a
more elegant way? It seems to me that the application must "know" it
is waiting for my loop to finish. How can I use this awareness from
within my code? Is there some event I can respond to, or some
application variable I can check?

I used to pass a "CancelClass" from procedure to procedure. It just
contained a boolean flag. The flag was checked where it made sense - usually
in a loop - and the functions exited (in reverse order) if it was set to
True, for example if a Cancel button was pressed, or when closing the Form
like you mentioned. I don't use DoEvents anymore (other than for some small
quickly-written tools used by myself only).
I used to think Finalize existed for this purpose -- I thought it's
job was to announce a pending shutdown to every instance of a class/
control. However, I've learned that Finalize doesn't get called
until after the loop is already done, so it obviously doesn't help
in this case.

By the way, I've browsed this newsgroup and I've seen the
suggestions that starting a new thread is preferable to DoEvents.

If you hadn't mentioned it now, I would have suggested to use a separate
thread. :)
I'm working on that, but I have a lot of cross-threading problems to
resolve first. In any case, I believe that is a separate issue. Even
if I run my loop on a separate thread, instead of using DoEvents, I
still need to figure out how to shut it down, right?

Right. Synchronizationis most important in a multithreaded environment - and
making it bullet proof is nontrivial. (BTW, I happen to work on some
reusable base classes handling the thread management, currently.)


Armin
 
T

TC

I used to pass a "CancelClass" from procedure to procedure. It just
contained a boolean flag. The flag was checked where it made sense - usually
in a loop - and the functions exited (in reverse order) if it was set to
True, for example if a Cancel button was pressed, or when closing the Form
like you mentioned. I don't use DoEvents anymore (other than for some small
quickly-written tools used by myself only).



If you hadn't mentioned it now, I would have suggested to use a separate
thread. :)


Right. Synchronizationis most important in a multithreaded environment - and
making it bullet proof is nontrivial. (BTW, I happen to work on some
reusable base classes handling the thread management, currently.)

Armin- Hide quoted text -

- Show quoted text -

Armin,

Thank you for the reply. On your encouragement, I put extra effort
into creating a new thread, and now everything works great. The whole
application came together -- even the clean shut-down. I really like
this solution -- it works far better than expected. Now that I know
how to do multi-threading, I suspect I may never use DoEvents again.

-TC
 
A

Armin Zingler

TC said:
Armin,

Thank you for the reply. On your encouragement, I put extra effort
into creating a new thread, and now everything works great. The
whole application came together -- even the clean shut-down. I
really like this solution -- it works far better than expected. Now
that I know how to do multi-threading, I suspect I may never use
DoEvents again.

Congrats! :)


Armin
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top