我正在从具有嵌入式Ironpython shell的Windows应用程序执行Ironpython脚本。我可以启动应用程序,加载脚本并从(.bat)文件开始执行。我想在测试脚本完成后关闭应用程序。但是,应用程序供应商尚未提供以编程方式关闭应用程序的功能。
我的第一个想法是使用PIPE来监视将终止子进程的特定字符串。我的测试脚本打开了一个表单,其中填充了测试所需的数据。还有其他一些并发症,我不知道如何处理打印到PIPE。任何打印都直接进入应用程序的shell窗口。
我追求的方法是通过激活应用程序窗口来关闭应用程序。以下是我的代码,它基于
Python's pywin32 extension
import ctypes
import re
EnumWindows = ctypes.windll.user32.EnumWindows
EnumWindowsProc = ctypes.WINFUNCTYPE(ctypes.c_bool, ctypes.POINTER(ctypes.c_int), ctypes.POINTER(ctypes.c_int))
GetWindowText = ctypes.windll.user32.GetWindowTextW
GetWindowTextLength = ctypes.windll.user32.GetWindowTextLengthW
IsWindowVisible = ctypes.windll.user32.IsWindowVisible
class my_test():
def __init__ (self):
"""Constructor"""
self._handle = None
self.wildcard = "Program name"
self.titles = []
def foreach_window(self, hwnd, lParam):
'''Pass to EnumWindows() to check all the opened windows'''
if IsWindowVisible(hwnd):
length = GetWindowTextLength(hwnd)
#print 'length', length
buff = ctypes.create_unicode_buffer(1024)
#buff = ctypes.create_unicode_buffer(length + 1)
#print 'buff', buff
GetWindowText(hwnd, buff, length + 1)
self.titles.append(buff.value)
if re.match(self.wildcard, str(buff.value)) != None:
self._handle = hwnd
print 'self._handle', self._handle
print 'str(buff.value)', str(buff.value)
return True
def find_window(self):
EnumWindows(EnumWindowsProc(self.foreach_window), 0)
def set_foreground(self):
"""put the window in the foreground"""
ctypes.windll.user32.SetActiveWindow(self._handle)
ctypes.windll.user32.SetForegroundWindow(self._handle)
ctypes.windll.user32.PostMessage(self._handle, win32con.WM_CLOSE, 0, 0)
def main():
w = my_test()
w.find_window()
w.set_foreground()
我发现关于关闭应用程序的另一个讨论(我认为使用pywin32扩展)2。作者引用了win32process和win32gui。这些模块是否具有等效的类型?
我在代码中添加了以下行。
SendMessage = ctypes.windll.user32.SendMessageW
WM_SYSCOMMAND = ctypes.c_int(0x0112)
SC_CLOSE = ctypes.c_int(0xF060)
替换了行
ctypes.windll.user32.PostMessage(self._handle, win32con.WM_CLOSE, 0, 0)
与
SendMessage(my_window, WM_SYSCOMMAND, SC_CLOSE, 0)
只要我在单独的IronPython shell中执行此脚本,这就有效。
taskkill完成了这个伎俩,见