C# SendKeys.SendWait 到另一个进程的对话框 (notepad.exe)
我正在尝试在 C# 中执行以下操作:
- 打开一个新进程 (notepad.exe)
- 输入一些文本(使用 SendKeys)
- 关闭记事本(处理任何确认对话框)
这是我得到的
Process p = new Process();
p.StartInfo.Filename = "notepad.exe";
p.Start();
// use the user32.dll SetForegroundWindow method
SetForegroundWindow( p.MainWindowHandle ); // make sure notepad has focus
SendKeys.SendWait( "some text" );
SendKeys.SendWait( "%f" ); // send ALT+f
SendKeys.SendWait( "x" ); // send x = exit
// a confirmation dialog appears
所有这些都按预期工作,但现在之后我已发送 ALT+f+x 我收到 “是否要保存更改为无标题”对话框,我想从内部关闭它 我的应用程序通过“按”“n”表示“不保存”。但是,
SendKeys.SendWait( "n" );
仅当我的应用程序没有失去焦点时(在 ALT+f+x 之后)才有效。如果确实如此,并且我尝试返回,则将
SetForegroundWindow( p.MainWindowHandle );
焦点设置到主记事本窗口而不是确认对话框。我使用了 user32.dll 中的 GetForegroundWindow 方法,发现对话框句柄与记事本句柄不同(这有点道理),但 SetForegroundWindow 甚至无法使用使用对话框窗口
句柄知道如何将焦点返回到对话框以便我可以成功使用 SendKeys
吗?
这是完整的代码
[DllImport("user32.dll")]
static extern bool SetForegroundWindow(IntPtr hWnd);
[DllImport("user32.dll")]
static extern IntPtr GetForegroundWindow();
[DllImport("User32.DLL")]
static extern bool ShowWindow(IntPtr hWnd, int nCmdShow);
public const int SW_RESTORE = 9;
...
Process p = new Process();
p.StartInfo.FileName = "notepad.exe";
p.Start();
Thread.Sleep( 1000 );
SendKeys.SendWait( "some text" );
SendKeys.SendWait( "%f" ); // send ALT+F
SendKeys.SendWait( "x" ); // send x = exit
IntPtr dialogHandle = GetForegroundWindow();
System.Diagnostics.Trace.WriteLine( "notepad handle: " + p.MainWindowHandle );
System.Diagnostics.Trace.WriteLine( "dialog handle: " + dialogHandle );
Thread.Sleep( 5000 ); // switch to a different application to lose focus
SetForegroundWindow( p.MainWindowHandle );
ShowWindow( dialogHandle, SW_RESTORE );
Thread.Sleep( 1000 );
SendKeys.SendWait( "n" );
谢谢
I'm trying to do the following in C#:
- Open a new process (notepad.exe)
- Enter some text (using SendKeys)
- Close Notepad (deal with any confirmation dialogs)
Here's what I got
Process p = new Process();
p.StartInfo.Filename = "notepad.exe";
p.Start();
// use the user32.dll SetForegroundWindow method
SetForegroundWindow( p.MainWindowHandle ); // make sure notepad has focus
SendKeys.SendWait( "some text" );
SendKeys.SendWait( "%f" ); // send ALT+f
SendKeys.SendWait( "x" ); // send x = exit
// a confirmation dialog appears
All this works just as expected, but now after I've sent ALT+f+x I get a
"Do you want to save changed to Untitled" dialog and I would like to close it from within
my applications by "pressing" 'n' for "Don't Save". However
SendKeys.SendWait( "n" );
works only if my application has not lost focus (after ALT+f+x). If it did and I try to go back using
SetForegroundWindow( p.MainWindowHandle );
this sets the focus to the main notepad window instead of the confirmation dialog. I used the GetForegroundWindow
method from user32.dll and found out that the dialog handle is different than the notepad handle (which kinda makes sence) but SetForegroundWindow
doesn't work with even with the dialog window handle
Any idea how I can give the focus back to the dialog so that I can successfully use SendKeys
?
here's the full code
[DllImport("user32.dll")]
static extern bool SetForegroundWindow(IntPtr hWnd);
[DllImport("user32.dll")]
static extern IntPtr GetForegroundWindow();
[DllImport("User32.DLL")]
static extern bool ShowWindow(IntPtr hWnd, int nCmdShow);
public const int SW_RESTORE = 9;
...
Process p = new Process();
p.StartInfo.FileName = "notepad.exe";
p.Start();
Thread.Sleep( 1000 );
SendKeys.SendWait( "some text" );
SendKeys.SendWait( "%f" ); // send ALT+F
SendKeys.SendWait( "x" ); // send x = exit
IntPtr dialogHandle = GetForegroundWindow();
System.Diagnostics.Trace.WriteLine( "notepad handle: " + p.MainWindowHandle );
System.Diagnostics.Trace.WriteLine( "dialog handle: " + dialogHandle );
Thread.Sleep( 5000 ); // switch to a different application to lose focus
SetForegroundWindow( p.MainWindowHandle );
ShowWindow( dialogHandle, SW_RESTORE );
Thread.Sleep( 1000 );
SendKeys.SendWait( "n" );
Thank you
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
您无法提供您没有的东西 -
SetForegroundWindow()
仅在您的应用程序当前获得焦点时才有效。现代 Windows 版本可防止应用程序窃取焦点,因为这在 Windows 9x 时代是一个主要烦恼。
另外,“Alt+F, x”仅指英语 Windows 版本上的退出,它不适用于大多数其他语言。避免使用
SendKeys()
,它不可能以可靠的方式使用。You can't give what you don't have -
SetForegroundWindow()
only works if your application currently has the focus.Modern Windows versions prevent applications from stealing focus, as that was a major annoyance back in the Windows 9x days.
Also, 'Alt+F, x' only refers to exit on English Windows versions, it won't work on most other languages. Avoid using
SendKeys()
, it's impossible to use in a reliable way.