Jader Dias
Jader Dias

Reputation: 90465

There is any way to run processes in the background?

There is any command line or .NET method that runs a process in the background hiding any window it tries to open?

Already tried:

 var process = new Process()
 {
      StartInfo = new ProcessStartInfo()
      {
          CreateNoWindow = true,
          WindowStyle = ProcessWindowStyle.Hidden,
          FileName = TheRealExecutableFileNameHere
      }
 }
 process.Start();

With no success so far

Upvotes: 3

Views: 33597

Answers (14)

Kishor H Oswal
Kishor H Oswal

Reputation: 1

Below code worked for me: Earlier the process (notepad) used to flash the notepad on desktop screen for printing, but it distract the user , so below code hides the notepad process in background.

                System.Windows.Forms.PrintDialog printDialog = new PrintDialog();
                System.Diagnostics.ProcessStartInfo psi = new System.Diagnostics.ProcessStartInfo(Application.StartupPath + "/PrintingDocketFile/PrintCustomerOrder.txt");
                psi.Verb = "PRINT";

                //Process.Start(psi);
                //psi.CreateNoWindow = true;
                psi.UseShellExecute = false;
                //---------------------------------------------------

                psi.CreateNoWindow = false;
                psi.UseShellExecute = true;
                psi.FileName = Application.StartupPath + "/PrintingDocketFile/PrintCustomerOrder.txt";
                psi.WindowStyle = ProcessWindowStyle.Hidden;
                psi.Arguments =  @"%windir%\system32\notepad.exe"; 
                //Process.Start(psi);
                //------------------------------------------------------

                /////////////////////----------------------------------

                printProcess.StartInfo = psi;
                /////psi.CreateNoWindow = true;

                //psi.FileName = "Application.StartupPath" + "/PrintingDocketFile/PrintCustomerOrder.txt";
                //p.StartInfo.FileName = "Notepad.EXE";
                //p.StartInfo.Arguments = "/i /q \"" + installationPackages[i] + "\"";

                printProcess.Start();

                /////////////////////////-------------------------------
                while (!printProcess.HasExited) ;


                if (!printProcess.HasExited)
                {
                    printProcess.Close();
                }

Upvotes: 0

Rage
Rage

Reputation: 31

public Form1()
    {
        InitializeComponent();
        Form1 fm = new Form1();
        fm.ShowInTaskbar = false;
        fm.Visible = fm.ShowInTaskbar = false;
    }

Works great !

Upvotes: 1

NathanTempelman
NathanTempelman

Reputation: 1387

You could make a Windows' service. Any window a service tries to open just runs in session 0, which means no user can see it. That goes for all windows though, so perhaps that's not what you're looking for.

Upvotes: 0

Matt
Matt

Reputation: 224

I think what you might want to try is to create a new Windows Station. Check out this article that explains a bit about them on msdn.

http://msdn.microsoft.com/en-us/library/ms681928(VS.85).aspx

Upvotes: 0

Mark
Mark

Reputation: 108512

I realize this has been answered but you could force a window to hide with unmanaged calls to FindWindow and ShowWindow.

[DllImport("user32.dll")]
public static extern IntPtr FindWindow(string lpClassName, string lpWindowName);

[DllImport("user32.dll")]
static extern bool ShowWindow(IntPtr hWnd, int nCmdShow);

psi = new ProcessStartInfo(); // etc..
some_process = Process.Start(psi);
System.Threading.Thread.Sleep(50); // need give the window a chance to be created
IntPtr hWnd = FindWindow(null, "name of the window");
if (hWnd != IntPtr.Zero) ShowWindow(hWnd, 0); // 0 = SW_HIDE

Rather kludgy.

Upvotes: 2

Keith Adler
Keith Adler

Reputation: 21178

One very simply way to achieve this is to create a Service Account and run the executable under the context of the Service Account user via the Windows Task Scheduler.

You could use this CodeProject to setup the scheduled task:

http://www.codeproject.com/KB/cs/tsnewlib.aspx

You could create the service account programatically in the Domain or local machine very easily with C#.

http://www.codeproject.com/KB/system/OSUserMangement.aspx http://support.microsoft.com/kb/306273

Processes running as scheduled tasks in the context of another user do not appear interactively unless that user is logged in; hence the use of a service account.

Upvotes: 1

Abhijeet Patel
Abhijeet Patel

Reputation: 6868

I noticed that if CreateNoWindow = false does absolutely nothing when the Filename is pointing to a Windows executable, if you have access to the source code of the winform app then you might be able to provide a command line argument which controls the default visibility of the form, and do something like this in the Winform App startup code:

static void Main(string[] args)
    {
        Application.EnableVisualStyles();
        Application.SetCompatibleTextRenderingDefault(false);
        Form1 form1 = new Form1();

        form1.Load += new EventHandler((s,o) =>
            {
              //check if the form should be shown based on command line arg
                if (args.Contains("dontShowWindow"))
                {
                    //hide it
                    form1.ShowInTaskbar = false;
                    form1.Visible = form1.ShowInTaskbar = false;
                }
            }
        );
        Application.Run(form1);
    }

In you calling code, you can now specify "dontShowWindow" as a process Argument:

 ProcessStartInfo info = new ProcessStartInfo
        {
            CreateNoWindow = false, 
            WindowStyle = ProcessWindowStyle.Hidden,
            UseShellExecute = false, 
            FileName = @"C:\temp\testWinForm.exe",
            Arguments = "dontShowWindow"
        };
        Process.Start(info);

Hope this helps

Upvotes: 1

Mark Good
Mark Good

Reputation: 4303

Have you tried using the Microsoft DOS start command with the /B switch?

Microsoft DOS start command

For example,

START /B cmd.exe

Upvotes: 5

CertifiedCrazy
CertifiedCrazy

Reputation: 935

You may want to try the BackgroundWorker Class in the .Net Framework if you haven't already. It's for executing long running processes on a separate thread to prevent them from impeding the UI. Give it a look.

Upvotes: 2

bohdan_trotsenko
bohdan_trotsenko

Reputation: 5357

There is no I do not know a pure .Net way to achieve this.

Then I thought about kernel Job Objects, but found no similar option in UI restrictions.

So, the next (yet unverified) idea is to create than process suspended, create a windows hook then, which will monitor CallWndProc and filter out WM_SHOW messages. (Then, surely, resume the process, wait in a separate thread till it terminates, remove the hook)

Upvotes: 3

Kenan E. K.
Kenan E. K.

Reputation: 14111

Check out the Matlab Engine.

There's even an interesting article on CodeProject, if this approach fits your needs.

Upvotes: 6

Ben Griswold
Ben Griswold

Reputation: 18321

I reviewed my code and it looks nearly identical to yours:

ProcessStartInfo psi = new ProcessStartInfo(fileName, arguments)
{
   CreateNoWindow = true,
   WindowStyle = ProcessWindowStyle.Hidden,
   UseShellExecute = false,
   RedirectStandardOutput = true                                               
};

Process process = Process.Start(psi);

The only notable difference (other than formatting and which PSI constructor we chose) is my use of UseShellExecute and RedirectStandardOutput as I needed to read the result of the ran process.

I have found the code above consistently runs a hidden process on XP and Vista. I have also found, however, and you may be experiencing the same, that a hidden process may kick off another process which by default isn't hidden. In other words, if you start hidden Process A and Process A, in turn, kicks off Process B, you have no control as to how Process B will be displayed. Windows which you have no control over may be displayed.

I hope this helps a little. Good luck.

Upvotes: 15

Chansik Im
Chansik Im

Reputation: 1493

I assume you want a process that is not visible to users while running.

You can try the following to see whether this is what you want.

  1. Create a simple console app that keeps running (and launch it to test).
  2. Right click on Project --> Properties --> Application tab --> Output type --> Change it from "Console Application" to Windows Application.
  3. Launch the same app one more time (to see whether this is what you want).
  4. Close the app via Windows Task Manager :)

It seems that the process appears in Task Manager, yet, is not visible in the task bar. Alt+TAB cannot bring this process up.

I just hope that you are not making any malicious app, though :)

Upvotes: 0

Bevan
Bevan

Reputation: 44307

It depends on whether you want to start the application minimized, but allow it to interact with the user if required, or if you want to prohibit all access with the user regardless of what happens.

If the latter, you could run the process under a different desktop context to the current user.

Different Desktop contexts are used, for example, by the Login dialog and by Vista UAC - anything that happens in one desktop context is independent of others.

Might be a sledgehammer approach to your problem though.

Upvotes: 1

Related Questions