Pause until complete?

D

David Veeneman

Is there a way that I can tell .NET to wait until a particular operation is
complete before passing control to the next statement?

Here's my problem: I'm working with the MonthCalendar control. When I set
its BoldedDates property, it fires the DateChanged event, which I don't want
to fire when I set that property. So I created a flag,
m_SuspendDateChangedEvent, which I set immediately before setting the
BoldedDates property, and clear immediately afterwards:

// Bold face dates with log entries
m_SuspendDateChangedEvent = true;
monthCalendar1.BoldedDates = datesWithEntries;
m_SuspendDateChangedEvent = false;

A statement at the top of the DateChanged event event handler causes an exit
if the flag is set. So far, so good.

But what is happening is that the flag is getting cleared before all of the
bold dates have been set. I'm guessing that the bolded dates are being set
asynchronously within the control. So I'm looking for a way to tell .NET to
wait until the setting of the BoldedDates property is finished before
clearing the flag.

Is that doable? Thanks in advance.

David Veeneman
Foresight Systems
 
P

Peter Duniho

David Veeneman said:
Is there a way that I can tell .NET to wait until a particular operation
is complete before passing control to the next statement?

It depends on the operation. But in the case you're asking about, I doubt
it, because I doubt that what's going on is what you think is going on.
[...]
But what is happening is that the flag is getting cleared before all of
the bold dates have been set. I'm guessing that the bolded dates are being
set asynchronously within the control.

I would be really surprised if the control uses a separate thread to set the
dates. I suspect that instead, you're running into the fact that the events
are processed in the message loop, which doesn't get to run until after your
code is all finished. The event gets posted when you change the bolded
dates, but isn't actually processed until after your code returns.

You should only get one DateChanged event when you set the BoldedDates
property, right? How about you set the flag, and then don't clear it there.
Instead, in your DateChanged handler, if the flag is set then just before
you exit the method without doing any real work, clear it there.

That way, the first DateChanged event that happens after you set the bolded
dates will be ignored, no matter how long it takes for the event to get
around to being processed.

Alternatively, you could force the messages to be pumped (I forget the call
to use, but I know it exists) right after you set the dates and before you
clear the flag. But personally, that seems more kludgy than just using the
flag in a way that works (and I admit, I find the whole "flag to disable the
method" approach kind of kludgy itself).

I admit, I don't have any firsthand experience with the MonthCalendar
control specifically. But based on your problem description and on what I
think I know about how .NET events are handled, I think the above is
correct.

One other thing: if you could explain why it is you don't want the
DateChanged property to be handled, that might help others come up with an
alternative solution that doesn't involve temporarily disabling the event
handler. After all, you haven't really prevented the event from
firing...you've just prevented the handler from doing any work when it does.
Depending on what the handler actually does, that may or may not be a
robust, maintainable solution.

If you could explain what it is exactly about the DateChanged event that you
don't want to happen, you might find you get an even better answer than the
one above. :)

Pete
 
D

David Veeneman

Yes, I find the supression flag to be a pretty ugly hack myself. But
occasionally, that's what it takes.

The DateChanged doesn't fire one time. Apparently, it fires once for each
month displayed in the control. I thought about counting the number of times
it fires, but that hack is way too ugly to consider seriously.

Why don't I want the event to fire? Something fairly subtle in my code is
causing the MonthCalendar to change the month displayed too many times when
I click the control's Forward or Back button, but only if dates get bolded.
I had hoped to avoid ferreting out the problem by simply supressing the
event when dates get bolded.

For the benefit of anyone reading this thread to research the MonthCalendar
control: The Month Calendar control is not one of Microsoft's finest
efforts. It lacks an event to inform the developer when the user changes the
month(s) displayed. Instead, it only provides a DateChanged event to inform
when any change is made to a calendar date (dates selected, or month(s)
displayed). Yes, it has a DateSelected event, but that fires only when a
date is selected with the mouse. It does not fire when a date is selected
with the keyboard. Why not use the Cick event? Because, for some reason,
Microsoft hides it on this control. Go figure.
 
M

Mythran

David Veeneman said:
Yes, I find the supression flag to be a pretty ugly hack myself. But
occasionally, that's what it takes.

The DateChanged doesn't fire one time. Apparently, it fires once for each
month displayed in the control. I thought about counting the number of
times it fires, but that hack is way too ugly to consider seriously.

Why don't I want the event to fire? Something fairly subtle in my code is
causing the MonthCalendar to change the month displayed too many times
when I click the control's Forward or Back button, but only if dates get
bolded. I had hoped to avoid ferreting out the problem by simply
supressing the event when dates get bolded.

For the benefit of anyone reading this thread to research the
MonthCalendar control: The Month Calendar control is not one of
Microsoft's finest efforts. It lacks an event to inform the developer when
the user changes the month(s) displayed. Instead, it only provides a
DateChanged event to inform when any change is made to a calendar date
(dates selected, or month(s) displayed). Yes, it has a DateSelected event,
but that fires only when a date is selected with the mouse. It does not
fire when a date is selected with the keyboard. Why not use the Cick
event? Because, for some reason, Microsoft hides it on this control. Go
figure.

Have you considered writing your own control for your application(s)? This
way, you can come up with exactly what you need...and it may not take too
much effort to accomplish...

By doing this, you wouldn't need any "kludgy"/"ugly" code.

:)

HTH,
Mythran
 
P

Peter Duniho

David Veeneman said:
Yes, I find the supression flag to be a pretty ugly hack myself. But
occasionally, that's what it takes.

The DateChanged doesn't fire one time. Apparently, it fires once for each
month displayed in the control. I thought about counting the number of
times it fires, but that hack is way too ugly to consider seriously.

Well, first of all, which is worse? A hack that doesn't do what you want?
Or an uglier hack that does? :)

Secondly, it sounds to me as though you're just using this for diagnostic
purposes. That is, you don't expect to release the project with the hack in
it. If I have that correct, then that would argue even more strongly for an
uglier hack that works than a simply ugly one that doesn't. Who cares how
ugly the hack is, if its only purpose is to get you the information you need
and it won't be in the final code? :)
Why don't I want the event to fire? Something fairly subtle in my code is
causing the MonthCalendar to change the month displayed too many times
when I click the control's Forward or Back button, but only if dates get
bolded. I had hoped to avoid ferreting out the problem by simply
supressing the event when dates get bolded.

I'm curious...are you bolding the dates *when* you click the Forward or Back
button? If not, it's not clear to me why the act of changing the bolded
dates is related to the act of changing the displayed month. If that's the
case, maybe you could explain in more detail why you believe they are
related.

If you *are* changing the dates that are bolded when you click the Forward
or Back button, then I could easily believe the control has a bug in it that
sets some sort of flag in response to the Forward or Back button, handling
the actual change in the DateChanged event handler. Running any code at the
same time that results in additional calls to the DateChanged event handler
could cause the behavior you see in that case. IMHO, the solution there
would be to not be doing other things (like changing the bolded dates) at
the same time that a Forward or Back click is being handled.

In this latter case, as you note, it's really the underlying design of
having a single event dealing with multiple kinds of changes that's the
problem. There wouldn't be an issue if there was one event for dealing with
the displayed month changing and another for dealing with the underlying
date data changing. But if it's a given that the control is the way it is,
the answer would be to not do more than one thing at a time that could cause
the DateChanged event to fire.

Of course, those last two paragraphs could be moot, depending on what you're
actually doing. I don't know how your code is written, so I can't say for
sure. It's just speculation.

Pete
 

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