Python py2exe ventana que muestra (tkinter)

Estoy tratando de hacer un exe por py2exe. El progtwig está mostrando una ventana de tipo emergente usando Tkinter. El problema es que todo funciona bien cuando ejecuto la configuración de esta manera:

setup(windows = [{'script': "msg.py"}], zipfile = None) 

pero falla cuando bash hacer un exe de un archivo:

 setup(windows = [{'script': "msg.py"}], zipfile = None, options = {'py2exe': {'bundle_files': 1, 'compressed': True}}) 

En realidad, el exe final se ejecuta sin problemas, pero no muestra ninguna ventana. He leído que puede haber problemas con bundle_files = 1 en Windows 7, pero también probé bundle_files = 2 con el mismo efecto. Aquí está mi script msg.py:

 from win32gui import FindWindow, SetForegroundWindow from Image import open as iopen from ImageTk import PhotoImage from Tkinter import Tk, Label from threading import Timer from subprocess import Popen import os def Thread(t, fun, arg=None): if argNone: x = Timer(t, fun, arg) else: x = Timer(t, fun) x.daemon = True x.start() def NewMessage(): global root if not os.path.exists('dane/MSG'): open('dane/MSG', 'w').write('') root = Tk() img = PhotoImage(iopen("incl/nowa.png")) label = Label(root, image=img) label.image = img label.bind("", Click) label.pack() root.geometry('-0-40') root.wm_attributes("-topmost", 1) root.overrideredirect(1) root.mainloop() def Click(event): global root, exit root.destroy() os.remove('dane/MSG') OpenApp() exit = True def OpenApp(): hwnd = FindWindow(None, 'My program name') if hwnd: SetForegroundWindow(hwnd) else: Popen('app.exe') root, exit = None, False NewMessage() 

¿Algunas ideas? He leído que hay algunos problemas con Tkinter, pero hubo acerca de la comstackción. Mi script está comstackdo y no lanza ninguna excepción, pero no muestra la ventana …

Terminé encontrando este mismo problema, mi solución implicaba hacer lo siguiente:

Agregue "dll_excludes": ["tcl85.dll", "tk85.dll"],

en tus options = {...}

y luego copiar manualmente esos dos archivos DLL desde

PYTHON_PATH\DLLs\ (en mi caso C:\Python27\DLLs )

a la ubicación de tu exe e intenta ejecutarlo.

Una alternativa a dll_excludes y la copia manual es parchar py2exe para saber que estos archivos deben colocarse directamente en el directorio dist.

Dentro de build_exe.py, hay una clase llamada py2exe , que contiene una lista dlls_in_exedir para dll que tiene que ir allí. Esta lista se establece durante una función llamada plat_prepare , y puede agregar los archivos tclXX.dll y tkXX.dll para asegurarse de que se copien correctamente.

Por supuesto, a menos que usted sea el único que pueda construir esto, no necesariamente sabe qué versión de Tcl y Tk necesita empaquetar; alguien podría haber creado Python por sí mismo, o está utilizando un Python más antiguo con DLL más antiguos. Por lo tanto, deberá verificar qué versiones está utilizando realmente el sistema. En realidad, py2exe ya lo hace en un lugar diferente: al importar el módulo interno _tkinter (la interfaz Tk real, generalmente una DLL) y acceder a TK_VERSION y TCL_VERSION , que luego puede usar para generar y agregar los nombres de archivo correctos.

Si se supone que otros crean su aplicación, es probable que no quiera hacer que modifiquen su instalación de py2exe, así que aquí le explicamos cómo puede hacerlo desde su setup.py:

 import py2exe py2exe.build_exe.py2exe.old_prepare = py2exe.build_exe.py2exe.plat_prepare def new_prep(self): self.old_prepare() from _tkinter import TK_VERSION, TCL_VERSION self.dlls_in_exedir.append('tcl{0}.dll'.format(TCL_VERSION.replace('.',''))) self.dlls_in_exedir.append('tk{0}.dll'.format(TK_VERSION.replace('.',''))) py2exe.build_exe.py2exe.plat_prepare = new_prep 

Esto incluso funciona con bundle_files=1 en Windows 7.

Si solo tiene una versión, puede copiar archivos con el archivo de datos. A continuación un ejemplo completo:

  • WinXP
  • Python2.7.6
  • tk8.5
  • tcl8.5
  • tix8.4.3
  • py2exe 0.6.9

foo.py:

 # -*- coding: iso-8859-1 -*- import Tkinter """ sets TCL_LIBRARY, TIX_LIBRARY and TK_LIBRARY - see installation Lib\lib-tk\FixTk.py """ Tkinter._test() 

Setup.py:

 # -*- coding: iso-8859-1 -*- from distutils.core import setup import py2exe import sys import os import os.path sys.argv.append ('py2exe') setup ( options = {'py2exe': { "bundle_files" : 1 # 3 = don't bundle (default) # 2 = bundle everything but the Python interpreter # 1 = bundle everything, including the Python interpreter , "compressed" : False # (boolean) create a compressed zipfile , "unbuffered" : False # if true, use unbuffered binary stdout and stderr , "includes" : [ "Tkinter", "Tkconstants" ] , "excludes" : ["tcl", ] , "optimize" : 0 #-O , "packages" : [ ] , "dist_dir" : "foo" , "dll_excludes": ["tcl85.dll", "tk85.dll"] , } } , windows = ["foo.py" ] , zipfile = None # the syntax for data files is a list of tuples with (dest_dir, [sourcefiles]) # if only [sourcefiles] then they are copied to dist_dir , data_files = [ os.path.join (sys.prefix, "DLLs", f) for f in os.listdir (os.path.join (sys.prefix, "DLLs")) if ( f.lower ().startswith (("tcl", "tk")) and f.lower ().endswith ((".dll", )) ) ] , )