# Copyright (c) 2023 Riverbank Computing Limited <info@riverbankcomputing.com>
#
# This file is part of PyQt6.
#
# This file may be used under the terms of the GNU General Public License
# version 3.0 as published by the Free Software Foundation and appearing in
# the file LICENSE included in the packaging of this file. Please review the
# following information to ensure the GNU General Public License version 3.0
# requirements will be met: http://www.gnu.org/copyleft/gpl.html.
#
# If you do not wish to use this file under the terms of the GPL version 3.0
# then you may purchase a commercial license. For more information contact
# info@riverbankcomputing.com.
#
# This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
# WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
import sys
def main():
""" Convert a .ui file to a .py file. """
import argparse
from PyQt6.QtCore import PYQT_VERSION_STR
from .exceptions import (NoSuchClassError, NoSuchWidgetError,
UIFileException)
# The program name.
PROGRAM_NAME = 'pyuic6'
# Parse the command line.
parser = argparse.ArgumentParser(prog=PROGRAM_NAME,
description="Python User Interface Compiler")
parser.add_argument('-V', '--version', action='version',
version=PYQT_VERSION_STR)
parser.add_argument('-p', '--preview', dest='preview', action='store_true',
default=False,
help="show a preview of the UI instead of generating code")
parser.add_argument('-o', '--output', dest='output', default='-',
metavar="FILE",
help="write generated code to FILE instead of stdout")
parser.add_argument('-x', '--execute', dest='execute', action='store_true',
default=False,
help="generate extra code to test and display the class")
parser.add_argument('-d', '--debug', dest='debug', action='store_true',
default=False, help="show debug output")
parser.add_argument('-i', '--indent', dest='indent', action='store',
type=int, default=4, metavar="N",
help="set indent width to N spaces, tab if N is 0 [default: 4]")
parser.add_argument('ui', help="the .ui file created by Qt Designer")
args = parser.parse_args()
# Carry out the required action.
if args.debug:
configure_logging()
exit_status = 1
try:
if args.preview:
exit_status = preview(args.ui)
else:
generate(args.ui, args.output, args.indent, args.execute)
exit_status = 0
except IOError as e:
print("Error: {0}: '{1}'".format(e.strerror, e.filename),
file=sys.stderr)
except SyntaxError as e:
print("Error in input file: {0}".format(e), file=sys.stderr)
except (NoSuchClassError, NoSuchWidgetError, UIFileException) as e:
print(e, file=sys.stderr)
except Exception as e:
if args.debug:
import traceback
traceback.print_exception(*sys.exc_info())
else:
print("""An unexpected error occurred.
Check that you are using the latest version of {name} and send an error report
to the PyQt mailing list and include the following information:
- your version of {name} ({version})
- the .ui file that caused this error
- the debug output of {name} (use the --debug flag when calling {name})""".format(name=PROGRAM_NAME, version=PYQT_VERSION_STR), file=sys.stderr)
return exit_status
def configure_logging():
""" Configure logging when debug is enabled. """
import logging
handler = logging.StreamHandler()
handler.setFormatter(logging.Formatter("%(name)s: %(message)s"))
logger = logging.getLogger('PyQt6.uic')
logger.addHandler(handler)
logger.setLevel(logging.DEBUG)
def generate(ui_file, output, indent, execute):
""" Generate the Python code. """
from .compile_ui import compileUi
if output == '-':
import io
pyfile = io.TextIOWrapper(sys.stdout.buffer, encoding='utf8')
needs_close = False
else:
pyfile = open(output, 'wt', encoding='utf8')
needs_close = True
winfo = compileUi(ui_file, pyfile, execute, indent)
if needs_close:
pyfile.close()
# 生成派生类
generate_extend(output, winfo)
# by qifa
def generate_extend(output: str, winfo: dict) -> None:
import os
filename = output[:output.rfind('.')]
class_name = 'Ui_' + filename + 'extend'
output_file = filename + 'extend.py'
if os.path.exists(output_file):
return # 如果文件已经存在,不再生成
from PyQt6.uic.Compiler.indenter import createCodeIndenter, getIndenter, write_code
output_stream = open(output_file, 'wt', encoding='utf-8')
createCodeIndenter(output_stream)
indenter = getIndenter()
indenter.level = 0
# 生成代码
indenter.write("from %s import %s" % (filename, winfo['uiclass']))
indenter.write("")
indenter.write("")
indenter.write("class %s(%s):" %(class_name, winfo['uiclass']))
indenter.indent()
indenter.write("def __init__(self):")
indenter.indent()
indenter.write("super().__init__()")
indenter.write("pass")
output_stream.close()
def preview(ui_file):
""" Preview the .ui file. Return the exit status to be passed back to the
parent process.
"""
from PyQt6.QtWidgets import QApplication
from .load_ui import loadUi
app = QApplication([ui_file])
ui = loadUi(ui_file)
ui.show()
return app.exec()
if __name__ == '__main__':
sys.exit(main())