заморозка ткинтера с импортом pywinauto - PullRequest
0 голосов
/ 24 июня 2018

Проблема:
Мой Python GUI (tkinter) зависает, когда я нажимаю кнопку, которая работает:
filename = filedialog.askdirectory()
Это только происходит, когда у меня есть from pywinauto import application в другом скрипте. Если я закомментирую импорт pywinauto, директория ask работает нормально. Нет заморозки, окно всплывает, как и ожидалось. Я не вижу ошибок, когда это происходит.

Извините за длинный пост, кстати, я хотел предоставить как можно больше подробностей. Дайте мне знать, если нужно больше и что вы ищете. В идеале я хотел бы использовать askdirectory, но я подумал, что, возможно, я мог бы просто использовать askopenfilename и извлечь из этого каталог.

Версия Python:
Python 3.4.4

Версия для Windows:
Windows Server 2012 R2 (не могу изменить это)

Вещи, которые я пробовал:
1. Базовые потоки с помощью учебных пособий (по-прежнему каждый раз зависает, пример кода внизу)
2. Комментирование разделов кода для сужения проблемы.
3. Попытался пройти через отладчик PyCharms, но в случае ошибки я ее не вижу.
4. Разные IDE.

IDLE = ошибка Pycharm = fail (тот же интерпретатор, что и в простое, как я могу сказать, поэтому не удивительно) Pythonwin = отлично работает)

Кодовые блоки ниже:
Я поместил блоки кода ниже в порядке их взаимодействия, если хотите. Он начинается с первого, затем переходит ко второму (среднему), который, наконец, переходит к третьему.

Вопросы:
Есть ли способ для меня, чтобы проверить на ошибку? Я сделал что-то не так, что вызывает это? Почему бы askopenfilename нормально работать, а не askdirectory?

Файл, содержащий окно, которое зависает:

from InstallMenu import MainMenu
from tkinter import *
from tkinter import filedialog

"""
This is where it freezes.  If I change askdirectory to openaskfilename it 
works without any issues.  If I comment out the from pywinauto import 
application from opusite.py, askdirectory works without issue.
"""
def chooseInstallFolder(installFolderPath):
    filename = filedialog.askdirectory()
    installFolderPath.config(text=filename)

def submitFolder(installFolderApp, installFolderPath, setObj):
    installFolderApp.destroy()
    MainMenu(installFolderPath, setObj)

def chooseInstall(setObj):
    installFolderApp = Tk()
    installFolderApp.title("Find Install Folder")
    installFolderApp.geometry("300x200")

    #Gui items
    pickAFolder = Label(installFolderApp, text = "Select your Install Folder")
    pickInstallerButton = Button(installFolderApp, text="Browse", command = lambda : chooseInstallFolder(installFolderPath))
    installFolderPath = Label(installFolderApp, text = " ")
    submit = Button(installFolderApp, text="Submit", command = lambda : submitFolder(installFolderApp, installFolderPath, setObj))

    #Packing
    pickAFolder.pack()
    installFolderPath.pack()
    pickInstallerButton.pack()
    submit.pack()

    installFolderApp.mainloop()

Скрипт меню, в котором находится кнопка отправки, выглядит следующим образом:
Я закомментировал iParcPro, потому что он использует тот же импорт, который вызывает зависание.

import opusite
#from iParcPro import *
from Sql import *
from tkinter import *

def OPUSiteInstall(installFolderPath):
    opusite.OPUSiteInstall(installFolderPath, setObj)
    opusite.rs485Install(installFolderPath, setObj)

def MainMenu(installFolderPath, setObj):
    menuWindow = Tk()
    menuWindow.title("Auto Installer Menu")
    menuWindow.geometry("325x250")

    #Create variables
    ChooseAButton = Label(menuWindow, text = "Choose an option")

    OPUSiteButton = Button(menuWindow, text="OPUSite Install", height = 1, 
    width 
    = 15, command = lambda : OPUSiteInstall(installFolderPath, setObj))

    #Pack
    ChooseAButton.pack()
    OPUSiteButton.pack()

    menuWindow.mainloop()

Код, содержащий импорт, который, кажется, замораживает это:

import pyautogui as ag
"""
This import here freezes it.  If I comment out just the import, the 
askdirectory works fine.
"""
from pywinauto import application

def OPUSiteInstall(installFolderPath, setObj):
    path = installFolderPath + '\\OPUSite\\AMI.OPUSite.Setup.msi'
    app = application.Application().Start(r'msiexec.exe /i ' + path)
    Wizard = app['OPUSite Setup']
    Wizard.NextButton.Wait('enabled', 50000)
    Wizard.NextButton.Click()
    Wizard['I &accept the terms in the License 
    Agreement'].Wait('enabled').CheckByClick()
    Wizard.NextButton.Click()
    Wizard.NextButton.Click()
    ag.typewrite(setObj.databaseName)
    ag.press('tab')
    ag.press('space')
    ag.press('tab')
    ag.press('tab')
    ag.typewrite(setObj.password)
    ag.press('tab')
    ag.typewrite(setObj.password)
    ag.press('tab')
    ag.typewrite(setObj.password)
    Wizard.NextButton.Click()
    Wizard.Install.Click()

    Wizard.Finish.Wait('visible', 50000)
    Wizard.Finish.Click()

def rs485Install(installFolderPath, setObj):
    path = installFolderPath + '\\OPUSite\\AMI.RS485AdapterSvc.Setup.msi'
    app = application.Application().Start(r'msiexec.exe /i ' + path)
    Wizard = app['RS485Adapter Setup']
    Wizard.NextButton.Wait('enabled', 50000)
    Wizard.NextButton.Click()
    Wizard['I &accept the terms in the License 
    Agreement'].Wait('enabled').CheckByClick()
    Wizard.NextButton.Click()
    Wizard.NextButton.Click()
    Wizard.Install.Click()

    Wizard.Finish.Wait('visible', 50000)
    Wizard.Finish.Click()

Это нить, которую я пробовал. Это не сработало:

from InstallMenu import MainMenu
from tkinter import *
from tkinter import filedialog
import threading

def chooseInstallFolder(installFolderPath):
    def callback(installFolderPath):
        filename = filedialog.askdirectory()
        installFolderPath.config(text=filename)
    t = threading.Thread(target=callback, args=(installFolderPath,))
    t.start()

def submitFolder(installFolderApp, installFolderPath, setObj):
    installFolderApp.destroy()
    MainMenu(installFolderPath, setObj)

def chooseInstall(setObj):
    installFolderApp = Tk()
    installFolderApp.title("Find Install Folder")
    installFolderApp.geometry("300x200")

    #Gui items
    pickAFolder = Label(installFolderApp, text = "Select your Install 
    Folder")
    pickInstallerButton = Button(installFolderApp, text="Browse", command = 
    lambda : chooseInstallFolder(installFolderPath))
    installFolderPath = Label(installFolderApp, text = " ")
    submit = Button(installFolderApp, text="Submit", command = lambda : 
    submitFolder(installFolderApp, installFolderPath, setObj))

    #Packing
    pickAFolder.pack()
    installFolderPath.pack()
    pickInstallerButton.pack()
    submit.pack()

    installFolderApp.mainloop()

1 Ответ

0 голосов
/ 25 июня 2018

Мне удалось обойти эту проблему.Я хочу указать, что я все еще не уверен, почему это сработало.Все, что я сделал, это переместил импорт pywinauto в мои функции, и теперь директория ask работает нормально.

import pyautogui as ag

def OPUSiteInstall(installFolderPath, setObj):
    from pywinauto import application
    path = installFolderPath + '\\OPUSite\\AMI.OPUSite.Setup.msi'
    app = application.Application().Start(r'msiexec.exe /i ' + path)
    Wizard = app['OPUSite Setup']
    Wizard.NextButton.Wait('enabled', 50000)
    Wizard.NextButton.Click()
    Wizard['I &accept the terms in the License 
    Agreement'].Wait('enabled').CheckByClick()
    Wizard.NextButton.Click()
    Wizard.NextButton.Click()
    ag.typewrite(setObj.databaseName)
    ag.press('tab')
    ag.press('space')
    ag.press('tab')
    ag.press('tab')
    ag.typewrite(setObj.password)
    ag.press('tab')
    ag.typewrite(setObj.password)
    ag.press('tab')
    ag.typewrite(setObj.password)
    Wizard.NextButton.Click()
    Wizard.Install.Click()

    Wizard.Finish.Wait('visible', 50000)
    Wizard.Finish.Click()

def rs485Install(installFolderPath, setObj):
    from pywinauto import application
    path = installFolderPath + '\\OPUSite\\AMI.RS485AdapterSvc.Setup.msi'
    app = application.Application().Start(r'msiexec.exe /i ' + path)
    Wizard = app['RS485Adapter Setup']
    Wizard.NextButton.Wait('enabled', 50000)
    Wizard.NextButton.Click()
    Wizard['I &accept the terms in the License 
    Agreement'].Wait('enabled').CheckByClick()
    Wizard.NextButton.Click()
    Wizard.NextButton.Click()
    Wizard.Install.Click()

    Wizard.Finish.Wait('visible', 50000)
    Wizard.Finish.Click()
`
...