Pywinauto не может найти / закрыть всплывающее окно - PullRequest
1 голос
/ 27 сентября 2019

Исходный код

def is_admin():
    try:
        return ctypes.windll.shell32.IsUserAnAdmin()
    except:
        return False

if is_admin():
    app = Application(backend='uia').start("C:\\Program Files (x86)\\Advantech\\AdamApax.NET Utility\\Program\\AdamNET.exe")
    win = app['Advantech Adam/Apax .NET Utility (Win32) Version 2.05.11 (B19)']
    win.wait('ready')
    win.menu_select("Setup->Refresh Serial and Ethernet")
    win.top_window().print_control_identifiers(filename="file.txt")
    # win.top_window().OKButton.click_input()  ---------This is what I hope to do

else
    ctypes.windll.shell32.ShellExecuteW(None, "runas", sys.executable, __file__, None, 1)

Постановка проблемы

Мне пришлось запустить это приложение с правами повышения прав.Выше мой код.Проблема в том, что я не могу определить окно (просмотр в output image), которое появляется после выбора из меню.Мне нужно закрыть окно.Прошу прощения за строку

win.top_window().print_control_identifiers(filename="file.txt")

Это означало запись идентификаторов в текстовый файл, потому что структура этого кода не отображает выходные данные для просмотра.Однако, поскольку ничего не добавлено, я думаю, что pywinauto не смог идентифицировать диалоговое окно.

Для более ясного понимания просмотрите изображение (вход), когда оно выбирает меню.

Вход

Теперь, это диалоговое окно появляется (вывод)

Выход

Я также использовал шпион, чтобы определитьзаголовок и он дает:

( дескриптор: 004E07D4, заголовок: информация, класс: # 32770 (диалог), стиль: 94C801C5)

Другие вещи, которые я пробовал:

Помимо использования win.topwindow() для идентификации диалога, я имеюused

win[Information].OKButton.click_input()
win[Information].OK.click_input()
win[Information].OK.close()
win[Information].OK.kill(soft=false)
win.Information.OKButton.click_input()
win.Information.OK.click_input()
win.Information.OK.close()
win.Information.OK.kill(soft=false)
app[Information] ...... curious if I could discover the new window from original application

Я также отправил ключи, такие как enter, space, esc и alt-f4, чтобы закрыть диалог с библиотеками, такими как клавиатура, pynput и ctypes.Это все еще не работает.

Ссылка для загрузки того же приложения: http://downloadt.advantech.com/download/downloadsr.aspx?File_Id=1-1NHAMZX

Любая помощь будет принята с благодарностью!

1 Ответ

1 голос
/ 30 сентября 2019

Я наконец нашел ветку, которая продемонстрировала, как многопотоковая работа решает эту проблему.Я попробовал это сам, и это работает.Это немного отличается, так как несколько частей кода устарели.Вот ссылка на решение: Как не дать диалоговому окну предупреждения остановить выполнение программы Python, которая его контролирует?

Вот изменения, которые я сделал для решения проблемы:

def is_admin():
    try:
        return ctypes.windll.shell32.IsUserAnAdmin()
    except:
        return False

if is_admin():

    def __init__(self, window_name, quit_event):
        threading.Thread.__init__(self)
        self.quit_event = quit_event
        self.window_name = window_name

    def run(self):
        while True:
            try:
                handles = windows.find_windows(title=self.window_name)
            except windows.WindowNotFoundError:
                pass 
            else: 
                for hwnd in handles:
                    app = Application()
                    app.connect(handle=hwnd)
                    popup = app[self.window_name]
                    popup.close()
            if self.quit_event.is_set():
                break
            time.sleep(1) 

    quit_event = threading.Event()
    mythread = ClearPopupThread('Information', quit_event)
    mythread.start()
    application = Application(backend="uia").start("C:\\Program Files (x86)\\Advantech\\AdamApax.NET Utility\\Program\\AdamNET.exe")
    time.sleep(2)
    win = application['Advantech Adam/Apax .NET Utility (Win32) Version 2.05.11 (B19)']
    win.menu_select("Setup->Refresh Serial and Ethernet")
    quit_event.set()

else:
    ctypes.windll.shell32.ShellExecuteW(None, "runas", sys.executable, __file__, None, 1)

Лучше всего то, что это решение работает для любого другого диалога, который останавливает работу основного скрипта, и я мог бы использовать их для выполнения различных действий, таких как нажатие кнопок, вставка значений, добавление нескольких многопотоков.

...