我正在尝试将程序(已知PID)设置为top / active / foreground(不确定哪个是最合适的)。
PID设置为Windows进程PID
handle = win32api.OpenProcess( win32con.PROCESS_ALL_ACCESS,
False, pid)
win32gui.SetForegroundWindow(handle)
win32gui.SetActiveWindow(handle)
我得到:
pywintypes.error: (1400, 'SetForegroundWindow', 'Invalid window Handle.')
pywintypes.error: (1400, 'SetActiveWindow', 'Invalid window handle.')
我意识到这是处理程序中的问题,但我不确定我应该如何正确地获得工作句柄。
答案 0 :(得分:3)
这项工作可以通过pywinauto完成:
from pywinauto import Application
app = Application().connect(process=<pid>)
app.top_window().set_focus()
但它可能不适用于最小化的应用程序。
答案 1 :(得分:2)
如果函数成功,则返回值是指定进程的打开句柄。它可以在任何需要处理句柄的函数中使用。
它的参数是窗口的句柄,应该被激活并带到前台。
所以你需要这样的翻译:
HWND h = ::GetTopWindow(0 );
while ( h )
{
DWORD pid;
DWORD dwTheardId = ::GetWindowThreadProcessId( h,&pid);
if ( pid == /*your process id*/ )
{
// here h is the handle to the window
break;
}
h = ::GetNextWindow( h , GW_HWNDNEXT);
}
python版本:
def find_window_for_pid(pid):
result = None
def callback(hwnd, _):
nonlocal result
ctid, cpid = win32process.GetWindowThreadProcessId(hwnd)
if cpid == pid:
result = hwnd
return False
return True
win32gui.EnumWindows(callback, None)
return result
一些注意事项:
但请注意,这很容易失败,因为当您第一次启动该过程时,它可能在几毫秒之后才会出现窗口。如果没有父母和孩子之间的某种同步手段,那么就没有办法解决这个问题。 (你可以通过,比如睡觉一秒钟来破解它,但这与任何试图睡觉而不是同步的问题相同 - 大部分时间,它会太长,降低了响应性/性能你的代码没有任何理由,偶尔,当计算机繁忙时,它会太短而且失败。)
真正解决这个问题的唯一方法是使用pywin32创建进程而不是使用标准Python代码。然后你就可以了解这个过程。这意味着您可以等待孩子开始其窗口循环,然后枚举该过程的窗口。