Click here to Skip to main content
15,885,910 members
Please Sign up or sign in to vote.
1.00/5 (1 vote)
See more:
When i run my WPF application, i want to do the points given below

> Execute 3 methods(MethodA,MethodB,MethodC) one after another.
> A label control in the Window which shows which method is executing now.(eg: Executing MethodA...)
> Show window without waiting.(UI thread must not wait for other 3 methods to finish).
How to do this?
Posted
Updated 4-Aug-15 2:29am
v3
Comments
[no name] 4-Aug-15 8:10am    
Okay... and? Did you have a question? Do you have some sort of a problem with the code you have written?
[no name] 4-Aug-15 8:26am    
How to update label in UI from MethodA?
[no name] 4-Aug-15 8:41am    
https://msdn.microsoft.com/en-us/library/system.windows.threading.dispatcher.invoke(v=vs.110).aspx
[no name] 4-Aug-15 8:27am    
How to execute 3 methods one by one without make UI wait?

You cannot call anything related to UI from non-UI thread. Instead, you need to use the method Invoke or BeginInvoke of System.Windows.Threading.Dispatcher (for both Forms or WPF) or System.Windows.Forms.Control (Forms only).

You will find detailed explanation of how it works and code samples in my past answers:
Control.Invoke() vs. Control.BeginInvoke(),
Problem with Treeview Scanner And MD5.

See also more references on threading:
.NET event on main thread[^],
.NET event on main thread,
How to get a keydown event to operate on a different thread in vb.net,
Control events not firing after enable disable + multithreading.

Prathap wrote:

…To display a text in label control, I had written code in ProgressChanged event of BackgroundWorker and it works fine.
When should I use Control.Invoke?
You need to call it each time you need to change something in UI. For example, to change the label text, you could use this method:
C#
static void SetLabelText(Label label, string newText) {
    label.Content = newText;
}
But this is something you could only call from the same UI thread. As I already explained before, you cannot call from a different thread. So, you need to call it from UI thread in all cases, but what to do in another thread? Delegate it to the UI thread. This is how?

```cs
using System.Windows;
using System.Windows.Controls;

// ...

public partial class MyWindow : Window {

public MainWindow() {
InitializeComponent();
} //MainWindow

void SetLabelText(Label label, string newText) {
Dispatcher.Invoke(
new System.Action<label, string="">((aLabel, aText) => {
aLabel.Content = aText;
}), label, newText);
} //SetLabelText

// ...

} //class MyWindow
```

—SA
 
Share this answer
 
v10
Comments
[no name] 5-Aug-15 1:44am    
Thanks, Sergey Alexandrovich Kryukov.
To display a text in label control, i had written code in ProgressChanged event of BackGroundWorker and it works fine.
When should i use 'Control.invoke'?
Sergey Alexandrovich Kryukov 5-Aug-15 1:46am    
You should delegate a simple method which assigns a text value to label.Text.
—SA
Sergey Alexandrovich Kryukov 5-Aug-15 2:29am    
Please see to my update to the answer, where I quote your question.
(Sorry, formatting is screwed up a bit; I'll report it as a regression bug.)
—SA
[no name] 5-Aug-15 5:34am    
I think i am updating UI control from the main thread itself (assuming ProgressChanged & RunWorkerCompleted events fire in main thread), using the result from worker thread(doWork event).So 'Dispatcher.Invoke' method not needed?
Sergey Alexandrovich Kryukov 5-Aug-15 10:38am    
You did not get it! It is needed. Read my words from my answer, not from your head.
—SA
1)
C#
private void MyFunction()
   {
   MethodA();
   MethodB();
   MethodC();
   }


2)
C#
private void MethodA()
   {
   myLabel.Text = "MethodA";
   }
private void MethodB()
   {
   myLabel.Text = "MethodB";
   }
private void MethodC()
   {
   myLabel.Text = "MethodC";
   }

3) Move MyFunction into a BackgroundWorker[^] and use Invoke[^] to set the label text.
 
Share this answer
 
Comments
OriginalGriff 5-Aug-15 2:02am    
You only (and always!) need Control.Invoke when your code is running on a thread other than that on which the control was created - the UI thread.

But BackgroundWorker is a very helpful class: the ProgressChanged event is always fired on the original thread, not the background thread, so you don't need to invoke controls in the event handler.
But you can always test Control.InvokeRequired in "general purpose" methods and invoke if necessary.
https://msdn.microsoft.com/en-us/library/system.windows.forms.control.invokerequired.aspx?PHPSESSID=6c7e47uec18v8n3121a6p001h4
It checks the thread, and returns false if it's safe to continue without invoking.
OriginalGriff 5-Aug-15 5:46am    
:thumbsup:

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900