Python compilation with pyqt deploy

Introduction

When I try to distribute a Python program in binary, neither pyinstaller nor nuitka is a little unsatisfactory. Qt can build binaries on cross-platform, and pyqt deploy seems to be able to build binaries in Python as well. So I started it straightforwardly, but surprisingly there is no article in Japanese so I wrote it.

pyqtdeploy https://www.riverbankcomputing.com/software/pyqtdeploy/intro

Build the demo (sysroot build)

https://www.riverbankcomputing.com/static/Docs/pyqtdeploy/demo.html

Preparation (this configuration in Windows environment)

About 10GB of free disk Visual Studio Community Edition 2017 Perl (ActivePerl, Strawberry Perl, etc., put in PATH) Python2.7 (required to build Qt: installer version, not anaconda / miniconda) Python3.7 (for target: installer version, not anaconda / miniconda)

Put pyqt5 and pyqtdeploy with pip of Python3.

Since the number of PATH characters exceeds 255 in Qt build, make it compatible with long file names in advance by changing the registry. https://orebibou.com/2017/05/windows-10-insider-preview%E3%81%A7explorer%E3%81%A7260%E6%96%87%E5%AD%97%E4%BB%A5% See E4% B8% 8A% E3% 81% AEpath% E3% 82% 92% E5% 8F% 96% E3% 82% 8A% E6% 89% B1% E3% 81% 86 /

Pick up the sources such as Qt and Python and put them in the demo folder of the pyqt deploy source. The required source is in sysroot.json. (OpenSSL, Python, PyQt5, zlib, qt-everywhere, etc.)

Where I was addicted

--MSV 2015/2017 not found Execute the build command from the command prompt of Visual Studio. Build on 64bit: x64 Native Tools Command Prompt for VS20xx Build on 32bit: Use x86 Native Tools command prompt for VS20xx.

――The display is too small to understand the progress Display as python build-demo.py --verbose.

--File not found appears during decompression of Qt source Due to the above PATH character limit.

--Project ERROR: Building QtQml requires Python The setting for coexistence of Python2 and Python3 is not good. At the command prompt, set py --version to get Python3 and py -2 --version to get Python2. If PYTHONPATH and PYTHONHOME are in the environment variables, delete them. Only the Python3 path was set in the PATH, and the Python2 path was not set.

--If sysroot build fails, it will be cleaned when rebuilding, so you will have to start over. 6th generation i5 memory 8GB requires about 3 hours (Qt is huge).

Creating a project

https://www.riverbankcomputing.com/static/Docs/pyqtdeploy/pyqtdeploy.html Set as. Again, try compiling the homemade Python script I tried earlier with NUITKA-Utilities.

test.py



# -*- coding: utf-8 -*-

# Form implementation generated from reading ui file 'test.ui'
#
# Created by: PyQt5 UI code generator 5.13.1
#
# WARNING! All changes made in this file will be lost!


from PyQt5 import QtCore, QtGui, QtWidgets
import time

class Ui_MainWindow(object):
    def setupUi(self, MainWindow):
        MainWindow.setObjectName("MainWindow")
        MainWindow.resize(300, 200)
        MainWindow.setMaximumSize(QtCore.QSize(300, 200))
        self.centralwidget = QtWidgets.QWidget(MainWindow)
        self.centralwidget.setObjectName("centralwidget")
        self.pushButton = QtWidgets.QPushButton(self.centralwidget)
        self.pushButton.setGeometry(QtCore.QRect(100, 130, 75, 23))
        self.pushButton.setObjectName("pushButton")
        self.label = QtWidgets.QLabel(self.centralwidget)
        self.label.setGeometry(QtCore.QRect(100, 50, 50, 12))
        self.label.setObjectName("label")
        MainWindow.setCentralWidget(self.centralwidget)
        self.menubar = QtWidgets.QMenuBar(MainWindow)
        self.menubar.setGeometry(QtCore.QRect(0, 0, 300, 21))
        self.menubar.setObjectName("menubar")
        MainWindow.setMenuBar(self.menubar)
        self.statusbar = QtWidgets.QStatusBar(MainWindow)
        self.statusbar.setObjectName("statusbar")
        MainWindow.setStatusBar(self.statusbar)

        self.retranslateUi(MainWindow)
        QtCore.QMetaObject.connectSlotsByName(MainWindow)

    def retranslateUi(self, MainWindow):
        _translate = QtCore.QCoreApplication.translate
        MainWindow.setWindowTitle(_translate("MainWindow", "MainWindow"))
        self.pushButton.setText(_translate("MainWindow", "Start"))
        self.label.setText(_translate("MainWindow", "Time:"))

        self.pushButton.pressed.connect(calc)

def calc():
    start = time.time()
    i = 10000000
    while i >= 0:
        i = i - 1
    stop = time.time()
    ui.label.setText(str(stop - start))


if __name__ == "__main__":
    import sys
    app = QtWidgets.QApplication(sys.argv)
    MainWindow = QtWidgets.QMainWindow()
    ui = Ui_MainWindow()
    ui.setupUi(MainWindow)
    MainWindow.show()
    sys.exit(app.exec_())

Duplicate pyqt-demo.pdy into test.pdy and use it as a template. Duplicate test.py in \ pyqtdeploy-2.4 \ demo \ data Rename it to test.py.dat and keep it.

pyqtdeploy test.pdy To execute. Set the source file and rescan the data folder. Save the contents of other tabs from the File menu as they are.

pyqtdeploy1.png

Build source

https://www.riverbankcomputing.com/static/Docs/pyqtdeploy/building.html Do the following in order

Makefile is created by qmake, and Makefile is executed by nmake. You should have a single exe file test.exe in build-win-64 \ release.

The time required to compile test.exe was as short as 30 seconds excluding the sysroot creation time.

Comparison of single exe files

PyInstaller NUITKA(-Utilities) pyqtdeploy
Single exe size 34.8MB 17.1MB 36.2MB
Execution result 0.8277249s 0.7182800s 0.7182917s
Start-up Slightly slow slow early

The size is the smallest created by the single exe creation command of nuitka-utilities, but this is because it is compressed by the installer, and it will be executed after it is installed in the Temp folder at the time of execution, so startup will be slow. ..

The size of a single exe is almost the same between Pyinstaller and pyqtdeploy, but pyqtdeploy creates a compiled binary so it starts and runs faster.

By removing unnecessary libraries with pyqt deploy (checking pyqt modules only for QtWidget, QtGui, QtCore, sip), I was able to reduce the size of the binary to about 25MB. It seems that pyqt deploy is superior in terms of binary size, startup, and execution speed.

Also, pyqtdeploy says that you can develop cross-platform (Windows, MacOS, Linux, iOS, Android) with the same source, so I would like to actively use it.

Recommended Posts

Python compilation with pyqt deploy
Easy Python compilation with NUITKA-Utilities
[GUI with Python] PyQt5 -Preparation-
[GUI with Python] PyQt5 -Paint-
[GUI with Python] PyQt5 -Widget II-
Run python3 Django1.9 with mod_wsgi (deploy)
I played with PyQt5 and Python3
[GUI with Python] PyQt5 -Custom Widget-
FizzBuzz with Python3
Scraping with Python
Statistics with python
Scraping with Python
Python with Go
Twilio with Python
Play with 2016-Python
Tested with Python
python starts with ()
with syntax (Python)
Bingo with python
Zundokokiyoshi with python
Excel with Python
Microcomputer with Python
Cast with python
I made a GUI application with Python + PyQt5
Serial communication with Python
Zip, unzip with python
Django 1.11 started with Python3.6
Primality test with Python
Python with eclipse + PyDev.
Socket communication with Python
Data analysis with python 2
Scraping with Python (preparation)
Try scraping with Python.
Learning Python with ChemTHEATER 03
Sequential search with Python
"Object-oriented" learning with python
Run Python with VBA
Handling yaml with python
Solve AtCoder 167 with python
Serial communication with python
[Python] Use JSON with Python
Learning Python with ChemTHEATER 05-1
Learn Python with ChemTHEATER
1.1 Getting Started with Python
Binarization with OpenCV / Python
3. 3. AI programming with Python
Kernel Method with Python
Non-blocking with Python + uWSGI
Scraping with Python + PhantomJS
Posting tweets with python
Drive WebDriver with python
Use mecab with Python3
Voice analysis with python
Think yaml with python
Operate Kinesis with Python
Getting Started with Python
Use DynamoDB with Python
Zundko getter with python
Handle Excel with python
Ohm's Law with Python
Primality test with python