User32 的 ShowWindow 未按预期运行
-
22-07-2019 - |
题
我正在使用 User32 的 ShowWindow 方法向用户隐藏窗口(cmd.exe)(主要是为了防止他们关闭它)。当用户打开表单时,进程启动并隐藏,然后当表单关闭时,进程被终止。但是,当再次打开表单时,它不会隐藏窗口(有时第一次也不会)有人可以帮助我吗?
[DllImport("User32")]
private static extern int ShowWindow(int hwnd, int nCmdShow); //this will allow me to hide a window
public ConsoleForm(Process p) {
this.p = p;
p.Start();
ShowWindow((int)p.MainWindowHandle, 0); //0 means to hide the window. See User32.ShowWindow documentation SW_HIDE
this.inStream = p.StandardInput;
this.outStream = p.StandardOutput;
this.errorStream = p.StandardError;
InitializeComponent();
wr = new watcherReader(watchProc);
wr.BeginInvoke(this.outStream, this.txtOut, null, null);
wr.BeginInvoke(this.errorStream, this.txtOut2, null, null);
}
private delegate void watcherReader(StreamReader sr, RichTextBox rtb);
private void watchProc(StreamReader sr, RichTextBox rtb) {
string line = sr.ReadLine();
while (line != null && !stop && !p.WaitForExit(0)) {
//Console.WriteLine(line);
line = stripColors(line);
rtb.Text += line + "\n";
line = sr.ReadLine();
}
}
public void start(string[] folders, string serverPath) {
this.inStream.WriteLine("chdir C:\\cygwin\\bin");
//this.inStream.WriteLine("bash --login -i");
this.inStream.WriteLine("");
}
private void ConsoleForm_FormClosed(object sender, FormClosedEventArgs e) {
this.stop = true;
try {
this.p.Kill();
this.p.CloseMainWindow();
} catch (InvalidOperationException) {
return;
}
}
解决方案
这将是更容易这样:
public ConsoleForm(Process p) {
this.p = p;
p.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;
p.StartInfo.CreateNoWindow = true;
p.Start();
this.inStream = p.StandardInput;
this.outStream = p.StandardOutput;
this.errorStream = p.StandardError;
InitializeComponent();
wr = new watcherReader(watchProc);
wr.BeginInvoke(this.outStream, this.txtOut, null, null);
wr.BeginInvoke(this.errorStream, this.txtOut2, null, null);
}
其他提示
你检查过是否 p.MainWindowHandle
是有效的句柄吗?至少它必须是非零的。尝试打电话 IsWindow
确认。
MSDN 建议 呼叫 WaitForInputIdle
检查之前 MainWindowHandle
;您可能会在新进程创建其窗口之前访问该属性。不过,无论如何,该属性本质上是不稳定的,因为进程实际上并不具有“主”窗口的概念。所有窗口都受到平等对待。.Net 框架只是将第一个窗口指定为主窗口,但进程本身不需要以这种方式考虑事情。
另外,您是否考虑过最初简单地隐藏该进程,而不是启动它然后在事后隐藏?设置进程的 StartInfo
特性 正如 Scotty2012 所展示的.
不隶属于 StackOverflow