Click here to Skip to main content
15,892,697 members
Please Sign up or sign in to vote.
4.00/5 (1 vote)
See more:
Hi! First question, long time reader!

I'm trying to get to grips with threaded apps but can't seem to get passed the second hurdle. The first I've managed - to launch a second window in a separate thread. However, it is no use if the first window cannot prod the second into doing things! And visa-versa.

In future, the idea is that one window is the main control which has lists and buttons and a scheduler maybe; the other monitors things but has it's own user interaction. The first for example changes what the second monitors; the second later reports back what it has monitored to the first to display and corrolate...

I have a window with two buttons - "Open Window" and "Close Window".

private void ButtonOpen_Click(object sender, RoutedEventArgs e)
{
	Thread tbr = new Thread(() =>
		{
		Window2 br = new Window2();
		br.Closed += (sender2, e2) => br.Dispatcher.InvokeShutdown();
		br.Show();
		System.Windows.Threading.Dispatcher.Run();
		});
	tbr.SetApartmentState(ApartmentState.STA);	//required for WPF
	tbr.Start();
	((Button)sender).IsEnabled = false;
}

private void ButtonClose_Click(object sender, RoutedEventArgs e)
{
//need to figure out how this works	
}


ButtonOpen_Click creates a thread and launches a new instanace of Window2 with UI message pump and has a gracefull exit when closed.

But, how do I invoke "this.close" in the second window via the first's ButtonClose_Click? Since the first is on a different thread? I guess if I can crack this, then the same principle can be used for anything I want to call via a button click on the first window to invoke something to happen in the second?

Thanks in advance for your help.
Posted
Comments
Sergey Alexandrovich Kryukov 15-Jun-11 18:26pm    
Weird idea. Why doing so? You can perfectly do all multi-threading in WPF in one shared UI thread and multiple working thread using Dispatcher's Invoke/BeginInvoke....
My I know the idea?
--SA
Sergey Alexandrovich Kryukov 15-Jun-11 18:28pm    
You should understand that Windows and threads are not directly related. You can use the same window in several threads (of cause, multiple windows in one thread). Also, one-windows UI is the best (a few modal windows would not hurt, very few). Why all that? Just for research?
--SA

Hello Dear
Some times a go i was working on a chat program . because a lot of client connect to server , it was necessary that server work on multiple thread , i had a lot of problem like you , bu finally i could solve my problem . there is a standard way to communicate between thread and controls in each thread , and it is 'Invoke' method which is one of methods of 'Control' class.

I guild you by one example :
I create a project with two forms : Form1 , Form2
Form1 has two button : BtnOpenForm , BtnCloseForm
when user clicks BtnOpenForm a new thread creates and in that thread create a new instance of Form2 then this new insatnce is shown
when user clicks BtnCloseForm this new instance will close

this is an abstract Sample not a complete one . but you can Communicate between any controls in any thread

Form1 :
C#
public delegate void DelegetCloseForm();
public partial class Form1 : Form
{
    public Form1()
    {
        InitializeComponent();
    }
    private Form2 F;
    private void BtnOpenForm_Click(object sender, EventArgs e)
    {
        System.Threading.Thread T = new System.Threading.Thread(delegate()
            {
                F = new Form2();
                F.ShowDialog();
            });
        T.Start();
    }
    private void BtnCloseForm_Click(object sender, EventArgs e)
    {
        this.F.Invoke(F.Dlg);
    }
}

Form2 :
C#
public DelegetCloseForm Dlg;
private void CloseForm()
{
    this.Close();
}
public Form2()
{
    InitializeComponent();
    Dlg = new DelegetCloseForm(this.CloseForm);
}

this is very simple , just need a little practice
if had problem comment me
Good luck
 
Share this answer
 
Thanks Reza Mansoori615 for pointing the way! I'm extremely grateful. That's how I tried it originally, changed it, then tried random things getting more and more frustrated.

However, that's the Windows Forms way, not WPF... A bit more looking and I found a hint - in WPF, Invoke is called via the Dispatcher. So...

Window 1:
MSIL
public delegate void dWindow2Close(); //declare - outside window class
public partial class MainWindow : Window
{
    public MainWindow()
    {
        InitializeComponent();
    }

    private Window2 br;
    private void ButtonOpen_Click(object sender, RoutedEventArgs e)
    {
        Thread tbr = new Thread(() =>
                {
                    br = new Window2();
                    br.Closed += (sender2, e2) =>
                        br.Dispatcher.InvokeShutdown();
                    br.Show();
                    System.Windows.Threading.Dispatcher.Run();
                });
        tbr.SetApartmentState(ApartmentState.STA);  //required for WPF
        tbr.Start();
        ((Button)sender).IsEnabled = false;
    }

    private void ButtonClose_Click(object sender, RoutedEventArgs e)
    {
        br.Dispatcher.Invoke(br.Window2Close);
    }
}

Window 2
MSIL
public partial class Window2 : Window
{
    public dWindow2Close Window2Close;    //to instantiate

    public Window2()
    {
        InitializeComponent();
        Window2Close = new dWindow2Close(SecondWindowClose);
    }

    private void SecondWindowClose()
    {
        this.Close();
    }
}


For those who asked, I intend opening 5 to 10 browser windows to monitor live data in real time and collate to a central DB. Navigating the DOM is trivial so there is no actual work to offload to a background worker. However, when each browser starts running flash ads the workload is not trivial for one thread! And all my other CPU's stand idle while a single one is choking... Launching each browser in a seperately threaded window seems my only option.

Thanks again to those who read and replied!
 
Share this answer
 

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