Packaging Kivy apps written in Python 3, targeting Windows using Nuitka - darkopevec/kivy GitHub Wiki
Note
This guide was tested only with the provided sample app, you may need
to add, remove or uncomment modules in dependencies.py
for your own app,
if Nuitka does not detect them (usually when hidden imports are used).
Data files and some DLLs are not copied over, those should be manually added
to the resulting main.dist
folder.
Preparing the environment
SCons (used by Nuitka) is not compatible with Python 3, installing
Python 2.7
is necessary, preferably to C:\Python27
.
MinGW or Visual Studio can be used as a compiler, MinGW being included by default in the Kivy SDK. When using Visual Studio Community 2015, the C++ tools must be selected at installation time.
Download the Kivy SDK for Windows.
Updating Kivy to the development version is recommended, for a guide follow: Use development Kivy.
Launch kivy.bat
, which is located in the Kivy SDK, and install Nuitka:
pip install nuitka
Preparing the app
The compiled app with disabled console will only run if stdin
, stdout
and
stderr
are redirected. The KIVY_DATA_DIR
environment variable should be
also set, otherwise Kivy will not find some of its asssets.
The following sample app will be packaged in this guide, call the
prep_win_standalone
function the same way at the start of your main.py
:
import sys
from os import environ
from os.path import join, dirname, realpath
def prep_win_standalone():
class DummyStream():
def __init__(self):
pass
def write(self, data):
pass
def read(self, data):
pass
def flush(self):
pass
def close(self):
pass
sys.stdin = DummyStream()
sys.stdout = DummyStream()
sys.stderr = DummyStream()
sys.__stdin__ = DummyStream()
sys.__stdout__ = DummyStream()
sys.__stderr__ = DummyStream()
exec_dir = dirname(realpath(sys.argv[0]))
environ['KIVY_DATA_DIR'] = join(exec_dir, 'data')
prep_win_standalone()
from kivy.app import App
from kivy.lang import Builder
root = Builder.load_string('''
BoxLayout:
Button:
text: 'Nuitka!'
''')
class TestApp(App):
def build(self):
return root
if __name__ == '__main__':
TestApp().run()
Create dependencies.py
in the folder where main.py
is located, and add the
following imports to it:
# uncomment this if you need to package pygame
# import pygame
# import pygame.event
# import pygame.video
# import pygame.image
# import pygame.display
# import pygame
# external modules
import kivy.cache
import kivy.atlas
import kivy.network
import kivy.network.urlrequest
import kivy.lib.osc
import kivy.lib.osc.OSC
import kivy.lib.osc.oscAPI
import kivy.lib.mtdev
import kivy.lib.sdl2
import kivy.factory_registers
import kivy.input.recorder
import kivy.input.providers
import kivy.input.providers.tuio
import kivy.input.providers.mouse
import kivy.input.providers.wm_common
import kivy.input.providers.wm_touch
import kivy.input.providers.wm_pen
import kivy.input.providers.hidinput
import kivy.input.providers.linuxwacom
import kivy.input.providers.mactouch
import kivy.input.providers.mtdev
# compiled modules
import kivy.event
import kivy.graphics.buffer
import kivy.graphics.c_opengl_debug
import kivy.graphics.compiler
import kivy.graphics.context_instructions
import kivy.graphics.fbo
import kivy.graphics.instructions
import kivy.graphics.opengl
import kivy.graphics.opengl_utils
import kivy.graphics.shader
import kivy.graphics.stenctil_instructions
import kivy.graphics.texture
import kivy.graphics.transformation
import kivy.graphics.vbo
import kivy.graphics.vertex
import kivy.graphics.vertex_instructions
import kivy.graphics.tesselator
import kivy.graphics.svg
import kivy.properties
# core
# import kivy.core.audio.audio_gstplayer
# import kivy.core.audio.audio_pygst
import kivy.core.audio.audio_sdl2
# import kivy.core.audio.audio_pygame
# import kivy.core.camera.camera_avfoundation
# import kivy.core.camera.camera_pygst
# import kivy.core.camera.camera_opencv
# import kivy.core.camera.camera_videocapture
import kivy.core.clipboard.clipboard_sdl2
# import kivy.core.clipboard.clipboard_android
# import kivy.core.clipboard.clipboard_pygame
# import kivy.core.clipboard.clipboard_dummy
# import kivy.core.image.img_imageio
# import kivy.core.image.img_tex
# import kivy.core.image.img_dds
import kivy.core.image.img_sdl2
# import kivy.core.image.img_pygame
# import kivy.core.image.img_pil
# import kivy.core.image.img_gif
# import kivy.core.spelling.spelling_enchant
# import kivy.core.spelling.spelling_osxappkit
import kivy.core.text.text_sdl2
# import kivy.core.text.text_pygame
# import kivy.core.text.text_sdlttf
# import kivy.core.text.text_pil
# import kivy.core.video.video_gstplayer
# import kivy.core.video.video_pygst
# import kivy.core.video.video_ffmpeg
# import kivy.core.video.video_pyglet
# import kivy.core.video.video_null
import kivy.core.window.window_sdl2
# import kivy.core.window.window_egl_rpi
# import kivy.core.window.window_pygame
# import kivy.core.window.window_sdl
# import kivy.core.window.window_x11
Launch kivy.bat
and go to your application directory, assuming your app
(including main.py
) is in C:\test_app\
:
cd "C:\test_app\"
Packaging with Visual Studio
Set the Visual Studio paths (verify that the file path exists, it may differ, depending on the VS or Windows version):
"C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC\vcvarsall" x86
Start packaging (the --msvc
version may be changed):
nuitka --msvc=14.0 --python-version=3.4 --recurse-plugins=dependencies.py --standalone --windows-disable-console --remove-output main.py
Packaging with MinGW
nuitka --mingw --python-version=3.4 --recurse-plugins=dependencies.py --standalone --windows-disable-console --remove-output main.py
Copying assets and SDL2 dependencies
After the compilation is done (it may take several minutes), a folder named
main.dist
will be created in the app directory, holding your compiled Kivy
app, with its dependencies.
Grab Kivy's data
directory from <Kivy SDK path>\kivy\kivy\data
or from
Github, and copy it to the
main.dist
folder. Also copy all the DLLs located at
<Kivy SDK path>\SDL2\bin
into main.dist
.
That's it, your application can be distributed by sharing the main.dist
folder.