我像这样启动Windows On-Screen-Keyboard:
s_onScreenKeyboard = new Process();
s_onScreenKeyboard.StartInfo = new ProcessStartInfo("osk.exe");
s_onScreenKeyboard.EnableRaisingEvents = true;
s_onScreenKeyboard.Exited += new EventHandler(s_onScreenKeyboard_Exited);
s_onScreenKeyboard.Start();
这样可以正常工作,但是当我尝试使用以下代码停止它时,它不起作用,即OSK继续运行并且方法返回false
:
s_onScreenKeyboard.CloseMainWindow();
if (!s_onScreenKeyboard.HasExited)
{
if (!s_onScreenKeyboard.WaitForExit(1000))
{
s_onScreenKeyboard.Close();
//s_onScreenKeyboard.Kill();
}
}
取消注释s_onScreenKeyboard.Kill();
时,它已关闭,但问题是osk.exe显然使用另一个名为“msswchx.exe”的进程,如果我只是杀死OSK进程,它就不会关闭。这样,我最终会有数百个这样的过程,这不是我想要的。
另一个奇怪的事情是CloseMainWindow()
电话在某个时间有效,但之后它突然变得不起作用了,我不记得发生了什么变化。
有什么想法吗?
编辑:我自己找到了一个解决方案。有关详细信息,请see my answer。
背景
我正在为我的应用程序实现一个屏幕键盘,因为它应该与触摸屏一起使用。键盘布局与Windows中配置的布局相匹配非常重要,因为应用程序将运送到许多不同的国家/地区。因此,而不是实现大约自定义键盘控制。 537键盘布局(夸张一点......),我想利用Windows内置的屏幕键盘,它自动适应所选的键盘布局,为我节省了大量的工作。
答案 0 :(得分:2)
我自己找到了/ a解决方案:
在流程启动后成功检索MainWindowHandle
时,稍后对CloseMainWindow()
的调用也会成功。我不明白这个的原因,但重要的是:它有效!
BTW,对于遇到相同问题的其他人:启动此过程后,MainWindowHandle
无法立即使用。显然,在MainWindow启动之前需要几毫秒,这就是我使用以下代码来检索句柄的原因:
DateTime start = DateTime.Now;
IntPtr handle = IntPtr.Zero;
while (handle == IntPtr.Zero && DateTime.Now - start <= TimeSpan.FromSeconds(2))
{
try
{
// sleep a while to allow the MainWindow to open...
System.Threading.Thread.Sleep(50);
handle = s_onScreenKeyboard.MainWindowHandle;
}
catch (Exception) { }
}
在这段代码中,只要它仍然等于MainWindowHandle
,我每隔〜50ms就会持续IntPtr.Zero
。如果在2秒后无法检索到句柄,我会退出循环以避免出现错误时无限循环。
答案 1 :(得分:2)
您需要等到该过程完成初始化,然后运行 Process.WaitForInputIdle Method为了做到这一点。