![]() |
|
|
#11 |
|
Guest
Posts: n/a
|
Re: Modifying Graphics object from separate threads
On Tue, 11 Dec 2007 10:09:05 +0100, Peter Duniho
<NpOeStPeAdM@nnowslpianmk.com> wrote: > And I apologize if the thread stuff is over your head. I'm writing the > detailed part here as much in hopes that someone who _does_ understand > the cross-thread stuff for the Control class better will pipe up and > elaborate. For the longest time I've just taken it as granted that > using Invoke() was required when calling any method other than those > documented as "thread safe" (see > <http://msdn2.microsoft.com/en-us/library/system.windows.forms.control.invokerequired(VS.90) .aspx> > for an example), but now I wonder if that's actually true. It does make > sense that Invalidate() might not be subject to the same limitation, > since it doesn't involve the message queue for the window (which is the > main thing that causes a window to be tied to a thread in the first > place). Hi Peter, I don't claim I understand the cross-thread stuff and i don't know if the following is really biting you but I once was, so ... In short (the important part is halfway down the description of InvokeRequired), if the Win32 handle is not yet created InvokeRequired can return false, indicating you're safe to modify the control and then there's also no exception fired if you do. *But* this causes the handle to be created on the calling thread if you access any other method/property that needs the win32 handle, ie on a thread without message pump ... not a good thing of course. So as they advise, you should also check IsHandleCreated if InvokeRequired returns false and if you're not sure the underlying handle is already created. I would be interested if this is really the cause of your problem because it would mean I'll have to look at my app a bit more closely too. :-/ -- Freddy |
|
|
|
#12 |
|
Guest
Posts: n/a
|
Re: Modifying Graphics object from separate threads
On Tue, 11 Dec 2007 02:36:49 -0800, Freddy Potargent
<freddy.potargent@amcnv.be> wrote: > [...] > So as they advise, you should also check IsHandleCreated if > InvokeRequired returns false and if you're not sure the underlying > handle is already created. > > I would be interested if this is really the cause of your problem > because it would mean I'll have to look at my app a bit more closely > too. :-/ No, it's not the issue I'm seeing, though thanks for the suggestion. I could have missed something, but I did read the documentation carefully and I was already aware of the issues with respect to a not-fully-initialized control. I try to never write code that accesses a control before it's been completely initialized. So far, I've been successful. ![]() You can see the code that the OP and I are talking about if you check back several posts in this thread; the sample code I posted is what I'm referring to. It will never fire the event that's the potential problem until the first time that the control in question (the form instance) is drawn, ensuring that the control is completely initialized by then. The more I think about it, the more I think that the requirement to call Invoke() is not precisely the same as a method or property being thread-safe, in spite of the documentation using the two ideas in an apparently synonymous manner. In the former, I suspect that the requirement to call Invoke() exists mainly (solely?) for situations that would wind up calling the window procedure for the control. In the latter, it would be more an issue of having multiple threads trying to call the same method or property at the same time. Since Invalidate() doesn't wind up calling the window procedure, I don't run into the first issue. There is in fact a potential issue with respect to it being called simultaneously from multiple threads, now that I think about it, but the docs don't say anything one way or the other that indicates whether this is a thread-safe operation. It probably comes down to whether the underlying native OS call InvalidateRect() is thread-safe, which I don't know off the top of my head. Pete |
|
|
|
#13 |
|
Guest
Posts: n/a
|
Re: Modifying Graphics object from separate threads
On Tue, 11 Dec 2007 02:36:49 -0800, Freddy Potargent
<freddy.potargent@amcnv.be> wrote: > [...] > So as they advise, you should also check IsHandleCreated if > InvokeRequired returns false and if you're not sure the underlying > handle is already created. > > I would be interested if this is really the cause of your problem > because it would mean I'll have to look at my app a bit more closely > too. :-/ No, it's not the issue I'm seeing, though thanks for the suggestion. I could have missed something, but I did read the documentation carefully and I was already aware of the issues with respect to a not-fully-initialized control. I try to never write code that accesses a control before it's been completely initialized. So far, I've been successful. ![]() You can see the code that the OP and I are talking about if you check back several posts in this thread; the sample code I posted is what I'm referring to. It will never fire the event that's the potential problem until the first time that the control in question (the form instance) is drawn, ensuring that the control is completely initialized by then. The more I think about it, the more I think that the requirement to call Invoke() is not precisely the same as a method or property being thread-safe, in spite of the documentation using the two ideas in an apparently synonymous manner. In the former, I suspect that the requirement to call Invoke() exists mainly (solely?) for situations that would wind up calling the window procedure for the control. In the latter, it would be more an issue of having multiple threads trying to call the same method or property at the same time. Since Invalidate() doesn't wind up calling the window procedure, I don't run into the first issue. There is in fact a potential issue with respect to it being called simultaneously from multiple threads, now that I think about it, but the docs don't say anything one way or the other that indicates whether this is a thread-safe operation. It probably comes down to whether the underlying native OS call InvalidateRect() is thread-safe, which I don't know off the top of my head. Pete |
|
|
|
#14 |
|
Guest
Posts: n/a
|
Re: Modifying Graphics object from separate threads
On Tue, 11 Dec 2007 02:36:49 -0800, Freddy Potargent
<freddy.potargent@amcnv.be> wrote: > [...] > So as they advise, you should also check IsHandleCreated if > InvokeRequired returns false and if you're not sure the underlying > handle is already created. > > I would be interested if this is really the cause of your problem > because it would mean I'll have to look at my app a bit more closely > too. :-/ No, it's not the issue I'm seeing, though thanks for the suggestion. I could have missed something, but I did read the documentation carefully and I was already aware of the issues with respect to a not-fully-initialized control. I try to never write code that accesses a control before it's been completely initialized. So far, I've been successful. ![]() You can see the code that the OP and I are talking about if you check back several posts in this thread; the sample code I posted is what I'm referring to. It will never fire the event that's the potential problem until the first time that the control in question (the form instance) is drawn, ensuring that the control is completely initialized by then. The more I think about it, the more I think that the requirement to call Invoke() is not precisely the same as a method or property being thread-safe, in spite of the documentation using the two ideas in an apparently synonymous manner. In the former, I suspect that the requirement to call Invoke() exists mainly (solely?) for situations that would wind up calling the window procedure for the control. In the latter, it would be more an issue of having multiple threads trying to call the same method or property at the same time. Since Invalidate() doesn't wind up calling the window procedure, I don't run into the first issue. There is in fact a potential issue with respect to it being called simultaneously from multiple threads, now that I think about it, but the docs don't say anything one way or the other that indicates whether this is a thread-safe operation. It probably comes down to whether the underlying native OS call InvalidateRect() is thread-safe, which I don't know off the top of my head. Pete |
|
|
|
#15 |
|
Guest
Posts: n/a
|
Re: Modifying Graphics object from separate threads
On Tue, 11 Dec 2007 02:36:49 -0800, Freddy Potargent
<freddy.potargent@amcnv.be> wrote: > [...] > So as they advise, you should also check IsHandleCreated if > InvokeRequired returns false and if you're not sure the underlying > handle is already created. > > I would be interested if this is really the cause of your problem > because it would mean I'll have to look at my app a bit more closely > too. :-/ No, it's not the issue I'm seeing, though thanks for the suggestion. I could have missed something, but I did read the documentation carefully and I was already aware of the issues with respect to a not-fully-initialized control. I try to never write code that accesses a control before it's been completely initialized. So far, I've been successful. ![]() You can see the code that the OP and I are talking about if you check back several posts in this thread; the sample code I posted is what I'm referring to. It will never fire the event that's the potential problem until the first time that the control in question (the form instance) is drawn, ensuring that the control is completely initialized by then. The more I think about it, the more I think that the requirement to call Invoke() is not precisely the same as a method or property being thread-safe, in spite of the documentation using the two ideas in an apparently synonymous manner. In the former, I suspect that the requirement to call Invoke() exists mainly (solely?) for situations that would wind up calling the window procedure for the control. In the latter, it would be more an issue of having multiple threads trying to call the same method or property at the same time. Since Invalidate() doesn't wind up calling the window procedure, I don't run into the first issue. There is in fact a potential issue with respect to it being called simultaneously from multiple threads, now that I think about it, but the docs don't say anything one way or the other that indicates whether this is a thread-safe operation. It probably comes down to whether the underlying native OS call InvalidateRect() is thread-safe, which I don't know off the top of my head. Pete |
|
|
|
#16 |
|
Guest
Posts: n/a
|
Re: Modifying Graphics object from separate threads
On Tue, 11 Dec 2007 02:36:49 -0800, Freddy Potargent
<freddy.potargent@amcnv.be> wrote: > [...] > So as they advise, you should also check IsHandleCreated if > InvokeRequired returns false and if you're not sure the underlying > handle is already created. > > I would be interested if this is really the cause of your problem > because it would mean I'll have to look at my app a bit more closely > too. :-/ No, it's not the issue I'm seeing, though thanks for the suggestion. I could have missed something, but I did read the documentation carefully and I was already aware of the issues with respect to a not-fully-initialized control. I try to never write code that accesses a control before it's been completely initialized. So far, I've been successful. ![]() You can see the code that the OP and I are talking about if you check back several posts in this thread; the sample code I posted is what I'm referring to. It will never fire the event that's the potential problem until the first time that the control in question (the form instance) is drawn, ensuring that the control is completely initialized by then. The more I think about it, the more I think that the requirement to call Invoke() is not precisely the same as a method or property being thread-safe, in spite of the documentation using the two ideas in an apparently synonymous manner. In the former, I suspect that the requirement to call Invoke() exists mainly (solely?) for situations that would wind up calling the window procedure for the control. In the latter, it would be more an issue of having multiple threads trying to call the same method or property at the same time. Since Invalidate() doesn't wind up calling the window procedure, I don't run into the first issue. There is in fact a potential issue with respect to it being called simultaneously from multiple threads, now that I think about it, but the docs don't say anything one way or the other that indicates whether this is a thread-safe operation. It probably comes down to whether the underlying native OS call InvalidateRect() is thread-safe, which I don't know off the top of my head. Pete |
|
|
|
#17 |
|
Guest
Posts: n/a
|
Re: Modifying Graphics object from separate threads
Well Pete,
I just wanted to thank you again for helping me out here - I did what you suggested and it worked right away. Without your help I wouldn't have known where to start, and I honestly didn't expect someone in a news group to spend so much time on this. The piece was performed last Wednesday and the program worked like a charm. If you'd like to hear a recording of it, please let me know. Happy Holidays to you & your family! -Mark |
|
|
|
#18 |
|
Guest
Posts: n/a
|
Re: Modifying Graphics object from separate threads
On Fri, 14 Dec 2007 15:08:14 -0800, <koschwitz@gmx.de> wrote:
> I just wanted to thank you again for helping me out here - I did what > you suggested and it worked right away. > Without your help I wouldn't have known where to start, and I honestly > didn't expect someone in a news group to spend so much time on this. I have found that I frequently learn something new trying to explain something I already know to someone. This was no exception (note the little tangent regarding Invalidate() and thread-safety). You're welcome for the help, but I hope you don't think I'm being entirely selfless. ![]() > The piece was performed last Wednesday and the program worked like a > charm. If you'd like to hear a recording of it, please let me know. Sure, if it's convenient I think it'd be fun to hear. Thanks, Pete |
|
![]() |
| Thread Tools | |
| Display Modes | |
|
|