Reputation: 90465
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
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
Reputation: 31
public Form1()
{
InitializeComponent();
Form1 fm = new Form1();
fm.ShowInTaskbar = false;
fm.Visible = fm.ShowInTaskbar = false;
}
Works great !
Upvotes: 1
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
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
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
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
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
Reputation: 4303
Have you tried using the Microsoft DOS start command with the /B switch?
For example,
START /B cmd.exe
Upvotes: 5
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
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
Reputation: 14111
Check out the Matlab Engine.
There's even an interesting article on CodeProject, if this approach fits your needs.
Upvotes: 6
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
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.
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
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