Question

I have a WinForms application and from the main form I am opening a new form and because the new form opening reads details from .xml file, I am opening this form via different Thread in order to avoid my UI stuck (the details read could take 1-3 seconds). After I open this form in a different Thread my form appears in my other screen (I am working with dual screen) although the StartPosition property is CenterParent. When I disable this new Thread and open the form from within the same Thread the StartPosition is CenterParent.

This is how I am opening my new form:

       try
        {
            BackgroundWorker backgroundWorker = new BackgroundWorker();
            backgroundWorker.WorkerReportsProgress = true;
            backgroundWorker.DoWork += new DoWorkEventHandler(
            (s3, e3) =>
            {
                string xmlFile = Path.Combine(
                    Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location),
                    @"file.xml");
                XmlDocument doc = new XmlDocument();
                doc.Load(xmlFile);
                MyForm frm = new MyForm(doc);
                frm.ShowDialog();
                e3.Result = webmails;
            });

            backgroundWorker.RunWorkerCompleted += new RunWorkerCompletedEventHandler(
                (s3, e3) =>
                {
                    MyForm frm = (MyForm)e3.Result;                        
                    if (webmails.DialogResult == DialogResult.OK)
                    {
                        // bla bla
                    }
                }
                );

            backgroundWorker.RunWorkerAsync();

        }
        catch (Exception ex)
        {
            MessageBox.Show(ex.Message, "Error");
        }
Was it helpful?

Solution

To say it simply: Each stack of windows is related to single thread. So you might have 2 windows each running on different thread. When you open a new window or dialog, it looks at top of the stack of windows in current thread and uses the top as it's parent. In your case frm.ShowDialog(); opens the dialog in different thread than all other windows so it doesn't have a parent it can to relate to.

To fix this, either use manual invoke (like in How to update the GUI from another thread in C#?) or move opening of the dialog into RunWorkerCompleted event, that is automatically synchronized to run on main UI thread.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top