简体   繁体   English

PyQT5 ui 文件,无法从可执行文件正确加载

[英]PyQT5 ui file, does not load properly from the executable file

I am building a PyQt5 application by constructing the interfaces with the designer and the exporting to .ui files.我正在通过构建与设计器的接口并导出到.ui文件来构建一个 PyQt5 应用程序。 The latter are then loaded by my main class. Here is an example of my source code under the name main.py :后者随后由我的主 class 加载。这是我的源代码示例,名称为main.py

main.py主程序

import os.path
import PyQt5.QtWidgets as qtw
from PyQt5.uic import loadUi
import sys

class MainUI(qtw.QMainWindow):
    def __init__(self, parent=None):
        super(MainUI, self).__init__()
        self._ui_path = os.path.dirname(os.path.abspath(__file__))
        loadUi(os.path.join(self._ui_path, 'main.ui'), self)

if __name__ == "__main__":
    # Create the application
    app = qtw.QApplication(sys.argv)
    # Create and show the application's main window
    win = MainUI()
    win.show()
    sys.exit(app.exec())

main.ui主界面

<?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0">
 <class>MainWindow</class>
 <widget class="QMainWindow" name="MainWindow">
  <property name="geometry">
   <rect>
    <x>0</x>
    <y>0</y>
    <width>320</width>
    <height>240</height>
   </rect>
  </property>
  <property name="windowTitle">
   <string>MainWindow</string>
  </property>
  <widget class="QWidget" name="centralwidget">
   <widget class="QPushButton" name="pushButton">
    <property name="geometry">
     <rect>
      <x>110</x>
      <y>100</y>
      <width>88</width>
      <height>27</height>
     </rect>
    </property>
    <property name="text">
     <string>ok</string>
    </property>
   </widget>
  </widget>
  <widget class="QMenuBar" name="menubar">
   <property name="geometry">
    <rect>
     <x>0</x>
     <y>0</y>
     <width>320</width>
     <height>21</height>
    </rect>
   </property>
  </widget>
  <widget class="QStatusBar" name="statusbar"/>
 </widget>
 <resources/>
 <connections/>
</ui>

I generate an executable with pyinstaller by giving pyinstaller -F -w main.py .我通过给pyinstaller -F -w main.py生成一个带有pyinstaller的可执行文件。

In the beginning the executable should be in the same folder with the ui.一开始,可执行文件应该与 ui.xml 位于同一文件夹中。 I have changed loadUI following the answer here .我已经按照此处的答案更改了loadUI

When I run the executable now it gives me an error message with the following traceback:当我现在运行可执行文件时,它会给我一条带有以下回溯的错误消息:

Traceback (most recent call last):
  File "main.py", line 17, in <module>
    win = MainUI()
  File "main.py", line 11, in __init__
    loadUi(os.path.join(self._ui_path, 'main.ui'), self)
  File "PyQt5\uic\__init__.py", line 238, in loadUi
  File "PyQt5\uic\Loader\loader.py", line 66, in loadUi
  File "PyQt5\uic\uiparser.py", line 1020, in parse
  File "xml\etree\ElementTree.py", line 1202, in parse
  File "xml\etree\ElementTree.py", line 584, in parse
FileNotFoundError: [Errno 2] No such file or directory: 'C:\\Users\\username\\AppData\\Local\\Temp\\_MEI187162\\main.ui'

What has happened is that after running the.exe file, a temporary directory is created having some dll files, and the program tries to locate the.ui file there, without success.发生的事情是,在运行 .exe 文件后,会创建一个包含 dll 个文件的临时目录,程序会尝试在其中找到 .ui 文件,但没有成功。 What can be done to direct the executable to the place where the.ui file is?如何将可执行文件定向到 .ui 文件所在的位置?

Add this somewhere at the top of your program:将此添加到程序顶部的某处:

import sys
import os

if getattr(sys, 'frozen', False):
    RELATIVE_PATH = os.path.dirname(sys.executable)
else:
    RELATIVE_PATH = os.path.dirname(__file__)

Then when you go to call loadUi() :然后当您 go 调用loadUi()时:

self._ui_path = RELATIVE_PATH + "/ui_path"  # Update this as needed

loadUi(os.path.join(self._ui_path, 'main.ui'), self)

When programs are compiled and ran elsewhere the directories can get a little weird.当程序在别处编译和运行时,目录会变得有点奇怪。 See if this works for you, if not, let me know and I can help out further.看看这是否适合您,如果不适合,请告诉我,我可以进一步提供帮助。

I turn back from PyQt5 version 5.15.7 to version 5.15.1 by command " pip install PyQt5==5.15.1 ".我通过命令“ pip install PyQt5==5.15.1 ”从 PyQt5 版本 5.15.7 返回到版本 5.15.1 My problem resolved.我的问题解决了。

My Code Goes like this我的代码是这样的

from PyQt5.QtWidgets import QApplication
from PyQt5 import uic


class UI(QWidget):
    def __init__(self):
        super(UI,self).__init__()

    # loading the ui file with uic module
        uic.loadUi("*xxxxxx*.ui", self)


app = QApplication([])
window = UI()
window.show()
app.exec()

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM