Invoking Delegate in a Console Application - winforms

I need to migrate a WinForm Application to a Console Application.
In the WinForm Application, I have something like:
this.Invoke(new LogResponseCallback(this.LogResponse), new object[] { allAlarmsJson });
private delegate void LogResponseCallback(string text);
private void LogResponse(string response)
{
this._richTextResponse.Text = response + "\r\n";
}
Seems like Main Thread has been called after the processing of a certain operation.
My concern is how can the same Asynchronous delegate call can be achieved in the Console application.
Any help would be highly appreciated.
Thanks in advance

Here is a question I asked about how Invoke does what it does,
Curious about the implementation of Control.Invoke()

Normally in Windows Forms you'd use Control.Invoke to get back to the UI thread from a background thread, as you can't access UI controls within a non-UI thread.
The same restriction doesn't apply in a console application - you may still need to be careful to avoid threading issues, but they're unlikely to be the same issues. If all you're doing is logging to the console (e.g. with Console.WriteLine) you should be fine to just do the logging in the background thread.

First of all you are not using any asynchonous delegate in your code here, the this.Invoke is synchronous call.
Second if you are running Console application you don't have to marshal the call back to the main thread, You only should do so when you are executing code that relying on thread, such as winforms, wpf UI thread and some COM components, you only have to marshal call in these situations because these components are relying on the thread that created them

Related

How to handle Win32 Application termination

I have an Win32 application with no window written in C.
My question is: is there any way to handle the termination of my application. Ex. closing it from the task manager or via the console.
It is unclear from the question, but if this is a console mode application then you can call SetConsoleCtrlHandler to install a callback that Windows will call just before it terminates your app. Beware that this callback runs on a separate thread and that you have to complete the callback function quickly.
If it is a native Windows program that just doesn't create a window then you really do need a window to get notifications like this. Which is not a problem, it doesn't have to be visible. Just don't call ShowWindow().
Note that atexit() as mentioned will not work, these are rude aborts you are talking about that don't let the program go through its normal shutdown sequence.
You might like to take a look at the atexit() function (http://msdn.microsoft.com/en-us/library/tze57ck3%28v=vs.100%29.aspx).
Using this function you can install handlers which are called when the program terminates.

does SoapClient run on UI thread just like WebClient?

I have this confusion that makes me uncertain about the origin of performance lag in my Windows Phone 7 application.
We all know WebClient runs on UI thread and is evil and should be avoided. But I have a webservice which is reference using visual studio so a class like XXXSoapClient : ClientBase is generated for that. Now the question is:
"Is this running on UI thread as well?"
-- Assuming the answer is yes, what is the workaround? Calling complex webservice methods using URL and HttpWebRequest is so labour-intensive!
Cheers.
P.S. Good news is that from "Mango" issue with WebClient will be resolved and it will run on "Originating thread".
WebClient will run on Originating Thread for Windows Phone 7.1/7.5

WPF application calls an API that needs a message pump; Dispather.Run() causes problems

I have a WPF app that uses a non-WPF vendor library. My app does not receive any events that the library fires. I've been told that this is because I need a message pump.
In another (very similar) question, the accepted answer suggested using System.Windows.Threading.Dispatcher.Run().
When I add in that call, however, my window won't pop up-- the app is effectively backgrounded and I have to shut it down with Task Manager.
I'm really stumped here, and I'm not even sure how to investigate it. Any help would be greatly appreciated.
You already have one if you use WPF, there's no other way that it can get any Windows notifications. Every WPF app starts life with a call to Application.Run() on the main thread. It is usually well hidden, auto-generated in the bin\debug\app.g.cs source code file. Application.Run() in turn calls Dispatcher.Run()
Your vendor is correct, without a message loop many COM components go catatonic. But since you have one you need to look for the problem elsewhere. Don't use the component on threads.

Winforms/ActiveX cross threaded calls

I have an application wherein I am hosting multiple types of content (images, PowerPoint presentations, videos etc) in a kiosk-type app. The user has to be able to page back and forth between these bits of content, preferably using gestures of the touchscreen on the kiosk, i.e. tap one side of the screen to go forward, the other side to go back.
Unfortunately, the controls that display the content could have further nesting, so I'm using a Win32 mouse hook to capture mouse clicks, checking if they are within a specified region. This works great. Unfortunately these click events are (indirectly) calling methods on the ActiveX control I'm using to host PP presentations (DSOFramer), and it's causing this nasty COM exception:
An outgoing call cannot be made since the application is dispatching an input-synchronous call. (Exception from HRESULT: 0x8001010D (RPC_E_CANTCALLOUT_ININPUTSYNCCALL))
My best guess is that the low level mouse hook is calling from a different thread, because if I make the call directly from the Winforms UI thread, there's no problem. I tried the standard Winforms Invoke/BeginInvoke with no success.
I was using the typical Winforms cross-thread pattern:
if(InvokeRequired)
{
Invoke(new Action(DoStuff));
}
else
{
DoStuff();
}
Of course the control I'm calling from has no idea of the AX control, so I need to explicitly invoke the action. It also needs to use BeginInvoke, so the above becomes:
BeginInvoke(new Action(DoStuff));
Works now. Oops!

'Cross-thread operation not valid' does not kill WinForms application (and it should)

Update: here is an MSDN article How to: Make Thread-Safe Calls to Windows Forms Controls. It states:
The .NET Framework helps you detect
when you are accessing your controls
in a manner that is not thread safe.
When you are running your application
in the debugger, and a thread other
than the one which created a control
tries to call that control, the
debugger raises an
InvalidOperationException with the
message, "Control control name
accessed from a thread other than the
thread it was created on."
This exception occurs reliably during
debugging and, under some
circumstances, at run time.
My previous experience was that the exception was thrown at run time, too.
Thanks to Spence for pointing me in the right direction.
I have a pretty common error in WinForms app: background thread accessing UI controls directly instead of using Control.BeginInvoke().
My problem is the following: I see the InvalidOperationException "Cross-thread operation not valid: Control 'uxCheckStatus' accessed from a thread other than the thread it was created on." in debugger on background thread, but then it is swallowed somewhere in WinForms internals.
I expect it to kill the background thread and entire application.
Moreover, the code that is triggering it uxCheckStatus.Text = "success"; sometimes gets executed during/after exception is thrown i.e. label text reads 'success'! I'm basically lost. Anyone else experiencing this behavior?
I reproduce it on completely new WinForms solution with 1 button, both using ThreadPool and Thread for evil background thread.
If I throw a new InvalidOperationException() on background thread, it does kill the application. So my only guess is that WinForms handles this specific exception somewhere, but I cannot find references to this behavior on the web.
I run .NET 3.5, VS 2008.
THis is by design. This is a coding error, not a runtime error. THe developers of Winforms decided that from .Net 2, they would implement code to check for the cross thread code and then fire an MDA. The MDA isn't an exception though, it's a check for badly designed code.
Additionally the MDA doesn't fire when your code is in release mode, it will just randomly fail every so often, the MDA is to help you at test, not during release.
I'm assuming that you are rewriting a badly written application to invoke onto the threads and you were hoping that the exceptions would catch for you, I have a suggestion:
Update your event handlers for GUI stuff to look like so:
public void button_clicked_handler(object sender, EventArgs e)
{
if(this.InvokeRequired)
{
this.Invoke(delegateToThisMethod)
}
else
{
//perform method
}
This pattern will catch all your methods and make it seamless for cross thread ops. If the threads are directly accessing code, this is a little tougher. You can get around this by renaming a control, then creating a property to the control, where you can then apply the invoke pattern to it. I've had to do this to troubleshoot some very funky cross thread stuff before.
EDIT:
Just wanted to clarify that checking the synchronisation context of the current thread and the Win Forms thread is a costly operation. Thus the reason they implemented the MDA is so that you find it in debug but that your release mode code isn't slowed down on EVERY access to EVERY property or method of a windows forms control.
I don't know of any specific documentation for how/why WinForms handles this exception. However, if you want to gracefully shut down your application when this happens, consider a global exception handler.

Resources