Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/312.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/apache-kafka/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 如何激活由另一进程启动的窗口_C#_.net_Winforms_Winapi - Fatal编程技术网

C# 如何激活由另一进程启动的窗口

C# 如何激活由另一进程启动的窗口,c#,.net,winforms,winapi,C#,.net,Winforms,Winapi,我认为这可能是不可能的。请证明我错了 以下设置: 带有GUI的My.NETC应用程序允许调用它GUI通过创建新进程打开另一个应用程序允许调用它服务器 其他人开发的服务器启动时使用一个参数来隐藏其GUI gui等待用户进行一些输入 然后,gui命令服务器执行一些任务 这些任务在我提供给服务器的assembly/DLL中定义 这些任务之一是打开一个表单/对话框,并向用户询问更多问题 现在,由于整个用户体验需要针对重复操作进行优化,因此打开的GUI元素窗口/窗体/对话框需要预先选择/聚焦/激活 第一个

我认为这可能是不可能的。请证明我错了

以下设置:

带有GUI的My.NETC应用程序允许调用它GUI通过创建新进程打开另一个应用程序允许调用它服务器 其他人开发的服务器启动时使用一个参数来隐藏其GUI gui等待用户进行一些输入 然后,gui命令服务器执行一些任务 这些任务在我提供给服务器的assembly/DLL中定义 这些任务之一是打开一个表单/对话框,并向用户询问更多问题 现在,由于整个用户体验需要针对重复操作进行优化,因此打开的GUI元素窗口/窗体/对话框需要预先选择/聚焦/激活

第一个问题出现了,因为我没有找到一个明确的解释,属性的重点是什么,活动的,选定的,最上面的

现在真正的问题是,我如何确保所有GUI元素都处于活动状态并处于选中状态,而不管它们是由我的GUI进程还是服务器进程启动的

使用WINAPI可以更强大,因此我定义了以下内容

// required to use WINAPI for RegainFocus();
[System.Runtime.InteropServices.DllImport("user32.dll")]
private static extern int SetForegroundWindow(IntPtr hwnd);
[System.Runtime.InteropServices.DllImport("user32.dll")]
private static extern IntPtr SetActiveWindow(IntPtr hwnd);
[System.Runtime.InteropServices.DllImport("user32.dll")]
private static extern bool ShowWindow(IntPtr hWnd, int nCmdShow);

static private void RegainFocus()
{
    // set focus back to and show application for faster input
    // SW_RESTORE = 9
    ShowWindow(Process.GetCurrentProcess().MainWindowHandle, 9);
    SetForegroundWindow(Process.GetCurrentProcess().MainWindowHandle);
    SetActiveWindow(Process.GetCurrentProcess().MainWindowHandle);
}
那么到目前为止我尝试的是:

这样设置服务器进程的StartInfo,这样新进程就不会窃取gui的焦点 启动服务器进程并按所述方式等待输入,以确保服务器真正就绪 还可以在gui应用程序中使用RegainFocus 在服务器的DLL中,我创建了一个新窗体,并尝试将窗口置于前端并将其选中 TopMost=true用于将对话框置于gui前面 对话框激活方法使用FocusControl在第一个输入控件上设置焦点。这很有效。 其结果是在我的gui上有一个窗口,该窗口的光标在第一个输入控件中闪烁,但被取消选择/未激活。当我点击时,我可以看到在后台的gui中选择了一个不同的控件

我也尝试过在表单中喷洒RegainFocus呼叫,但没有效果

我还有一些想法,但无法实现:

输入完成后,对gui进行散焦,但不聚焦 在我的表单类中重写,但是? 目标框架是.NET4.5,目标操作系统是Windows7和Windows10


感谢您的帮助和投入/TIPP

我找到了一个在Windows 10和Windows 7上运行的解决方案

失去焦点后,我使用RegainFocus功能重新获得焦点并激活窗口,请参见问题。注意:不要将进程句柄和MainWindowHandle混用。当一个对象被隐藏时,它的MainWindowHandle很可能是0

我搬走了

    myProcess.StartInfo.UseShellExecute = false;
    myProcess.StartInfo.CreateNoWindow = true;
    myProcess.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;
在启动服务器进程时,为了不影响可见性状态。不过我一直在等待[1]

在Windows7上,这仍然是不够的,而且在创建的过程中没有起作用。不过,感谢您的评论,不是将窗口放在前面,而是将窗口放在前面。这里的解决办法是

设置为0并重新启动计算机。然后,Windows 7和10的代码表现相同。如果有正确的权限,这甚至可以是

由于这个问题有这么多不同的答案和解决方案,我假设它取决于许多因素,如windows版本、注册表设置、可能的UAC和主题设置、框架和运行时,一些。。。这就是为什么我想提及我发现的其他方法

在展示之前先打开窗户 在Setforewindow之前 WM_显示窗口消息 带SW_RESTORE和SW_SHOW SetForegroundWindow的ShowWindow [SetWindowPos][10]、SetActiveWindow、SetFocus和finally AttachThreadInput的 允许使用[ASFW_ANY][11]设置SetForeGroundWindow 锁定 活跃 登顶
我找到了一个在Windows10和Windows7上运行的解决方案

失去焦点后,我使用RegainFocus功能重新获得焦点并激活窗口,请参见问题。注意:不要将进程句柄和MainWindowHandle混用。当一个对象被隐藏时,它的MainWindowHandle很可能是0

我搬走了

    myProcess.StartInfo.UseShellExecute = false;
    myProcess.StartInfo.CreateNoWindow = true;
    myProcess.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;
在启动服务器进程时,为了不影响可见性状态。不过我一直在等待[1]

在Windows7上,这仍然是不够的,而且在创建的过程中没有起作用。不过,感谢您的评论,不是将窗口放在前面,而是将窗口放在前面。这里的解决办法是

设置为0并重新启动计算机。然后,Windows 7和10的代码表现相同。如果有正确的权限,这甚至可以是

由于这个问题有这么多不同的答案和解决方案,我假设它取决于许多因素,如windows版本、注册表设置、可能的UAC和主题设置、框架和运行时,一些。。。这就是为什么我想提及我发现的其他方法

在展示之前先打开窗户 在Setforewindow之前 WM_显示窗口消息 带SW_RESTORE和SW_SHOW SetForegroundWindow的ShowWindow [SetWindowPos][10]的A,S etActiveWindow、SetFocus和最终AttachThreadInput 允许使用[ASFW_ANY][11]设置SetForeGroundWindow 锁定 活跃 登顶 看见同样相关:。请注意,表单尚未显示时,Form.BringToFront等无效。请参阅。同样相关:。请注意,表单尚未显示时,Form.BringToFront等无效。
    myProcess.StartInfo.UseShellExecute = false;
    myProcess.StartInfo.CreateNoWindow = true;
    myProcess.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;
\HKEY_CURRENT_USER\Control Panel\Desktop\ForegroundLockTimeout