Click here to Skip to main content
15,881,882 members
Please Sign up or sign in to vote.
0.00/5 (No votes)
See more:
Having trawled t'internet for the answer to the following question, it seems that a lot of people have asked this over the years; here's the issue:-

I have my library working away just fine. I would now like to launch a UI so that someone can simulate some function or other, introduce errors, change variables etc...

So, I have my form
C#
Form1 simUi;

and iv'e tried creating this in a method which is
C#
[STAThread]
(seems to be t'internets favourite answer)
C#
simUi = new Form1();


Now, here's the problem: If I use
C#
simUi.ShowDialog();

The method never returns; at least until I close the form. Whereas, if I use
C#
simUi.Show();

It returns but doesn't finish rendering the form and so is equally useless.
I want to be able to start the "ShowDialogue" in it's own thread but the compiler complains that the return type is incorrect.
So, how is best to do this ? Note that I have a number of controls on my form and so I don't just want to update a dialoge box. The plan is to use the properties in my form1.cs to access the responces on my UI and update any value's; I have a timer event to refresh.

Hopefully I am overlooking something that is obvious to all of you gurus'


Thanks Richard,
When I call the Show() method, the window appears but with no controls or buttons; just a blank grey box.

@Lukeer
C#
guiThread = new System.Threading.Thread(new System.Threading.ThreadStart(simUi.ShowDialog));

guiThread.Start();



UPDATE:
Perhaps I need to elaborate a bit more:- My project is essentially an instrument class driver ; depending on which instrument is connected, it picks the correct driver to use and begins it’s work in it’s own thread. There wouldn’t ordinarily be any need for a UI but this dll is now being used by other people and teams. I had included a “simulation” feature to enable my development whilst not attached to any hardware but this was/is relatively simplistic. My internal “customers” are developing in the same way using my simulator but would like to invoke every error condition / state possible; this requires me to add a human interface. I know this is possible because I have seen similar done before.
So, if I could just find a way of running the ShowDialogue() in it’s won thread or getting the Show() to draw the controls, I’d have it licked…
Posted
Updated 7-Jun-13 4:25am
v4
Comments
lukeer 7-Jun-13 8:05am    
Show the code you used to create the UI on a separate thread.
Mark where the return type error occured.
lukeer 7-Jun-13 9:20am    
I can explain why you're getting an error: You try to create a new instance of System.Threading.ThreadStart. As parameter you use simUi.ShowDialog. This method has the signature public DialogResult MethodName(). But the constructor you use expects a signature of public void MethodName(). That's why the compiler complains about the return type. It's void vs DialogResult.

I have no immediate solution except for saying that in a "normal" Windows Forms application, the UI thread is the main thread and starts the main form like this:
Application.Run(YourMainFormInstance);
That's a blocking call. So you usually put everything else in a separate thread instead of putting the UI in a separate thread.

Hope that helps somehow.

PS: If you want me to get automatically informed of something you wrote, reply to something that I wrote. Or add the important information to your question, like you did, and then leave me a small comment saying that you did so (You can Reply to this comment).
Member 9862872 7-Jun-13 9:43am    
Thanks Lukeer, Yes, this would be a non-issue if it was a Windows Forms Application but unfortunately this isn't possible in this instance.

This one works for me:
C#
using System;
using System.Collections.Generic;
using System.Text;

namespace KillmeConsole
{
    class Program
    {
        static void Main(string[] args)
        {
            Console.WriteLine("And now, starting a window...");


            System.Threading.ThreadStart ts = new System.Threading.ThreadStart(ShowForm);
            System.Threading.Thread uiThread = new System.Threading.Thread(ts);
            uiThread.Start();
            


            Console.WriteLine("Did it happen?");
        }


        private static void ShowForm()
        {
            System.Windows.Forms.Application.Run(new MainForm());
        }
    }

    public class MainForm : System.Windows.Forms.Form
    {
        System.Windows.Forms.Button btNix = new System.Windows.Forms.Button();

        public MainForm()
        {
            btNix.Location = new System.Drawing.Point(20, 20);
            btNix.Name = "btNix";
            btNix.Text = "Nix";
            this.Controls.Add(btNix);
        }
    }
}
There's just ShowForm(), a void-returning method without parameters. As such it matches what ThreadStart's constructor expects. It then runs the application window. It is still a blocking call, but since the method itself runs on a separate thread (uiThread), the main program can continue.

The application doesn't exit before the UI thread exits (just close the window).

This one needs references added to System.Windows.Forms.dll and System.Drawing.
 
Share this answer
 
Comments
Member 9862872 10-Jun-13 8:59am    
Excellent work; thanks lukeer, this works great. I'm surprised there isn't a more direct method available but I guess this only adds a couple of extra lines of code. Many thanks..
The ShowDialog() method never returns, because it is a dialog. It's purpose is to allow the user to enter information in the various controls, and then signify completion by pressing the "OK" button (or similar). By contrast the Show() method offers a fully interactive window that does not require a "completion" indicator, it usually closes when the application is terminated.

However, I cannot see any obvious problem from your description; I think you need to edit your question and provide a bit more detail.
 
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