forked from qt-creator/qt-creator
Improve Python generator
The Python generator generates the .qrc resources file, pyproject.toml, main.py and a settings.py files. This way, pyside6-project can run the code without doing any change in the QML code. Change-Id: Iddcc0c7f7a48c581f656f6d156b17460d4106691 Reviewed-by: Knud Dollereder <knud.dollereder@qt.io>
This commit is contained in:
committed by
Jaime Resano
parent
1278473e69
commit
4146d1bd01
@@ -11,5 +11,8 @@
|
|||||||
<file alias="import_qml_components_h">templates/import_qml_components_h.tpl</file>
|
<file alias="import_qml_components_h">templates/import_qml_components_h.tpl</file>
|
||||||
<file alias="qtquickcontrols_conf">templates/qtquickcontrols2_conf.tpl</file>
|
<file alias="qtquickcontrols_conf">templates/qtquickcontrols2_conf.tpl</file>
|
||||||
<file alias="cmake_shared">templates/cmakelists_txt_shared.tpl</file>
|
<file alias="cmake_shared">templates/cmakelists_txt_shared.tpl</file>
|
||||||
|
<file alias="python_generator_main">templates/python_generator_main.tpl</file>
|
||||||
|
<file alias="python_generator_settings">templates/python_generator_settings.tpl</file>
|
||||||
|
<file alias="python_pyproject_toml">templates/python_pyproject_toml.tpl</file>
|
||||||
</qresource>
|
</qresource>
|
||||||
</RCC>
|
</RCC>
|
||||||
|
@@ -30,6 +30,7 @@ void Exporter::updateProject(QmlProject *project)
|
|||||||
void Exporter::updateProjectItem(QmlProjectItem *item, bool updateEnabled)
|
void Exporter::updateProjectItem(QmlProjectItem *item, bool updateEnabled)
|
||||||
{
|
{
|
||||||
connect(item, &QmlProjectItem::filesChanged, m_cmakeGen, &CMakeGenerator::update);
|
connect(item, &QmlProjectItem::filesChanged, m_cmakeGen, &CMakeGenerator::update);
|
||||||
|
connect(item, &QmlProjectItem::filesChanged, m_pythonGen, &PythonGenerator::update);
|
||||||
connect(item, &QmlProjectItem::fileModified, m_cmakeGen, &CMakeGenerator::updateModifiedFile);
|
connect(item, &QmlProjectItem::fileModified, m_cmakeGen, &CMakeGenerator::updateModifiedFile);
|
||||||
|
|
||||||
if (updateEnabled) {
|
if (updateEnabled) {
|
||||||
|
@@ -3,41 +3,14 @@
|
|||||||
|
|
||||||
#include "pythongenerator.h"
|
#include "pythongenerator.h"
|
||||||
#include "cmakewriter.h"
|
#include "cmakewriter.h"
|
||||||
|
#include "resourcegenerator.h"
|
||||||
|
|
||||||
#include "projectexplorer/projectmanager.h"
|
#include "projectexplorer/projectmanager.h"
|
||||||
#include "qmlprojectmanager/qmlproject.h"
|
#include "qmlprojectmanager/qmlproject.h"
|
||||||
|
|
||||||
#include <QMenu>
|
#include <QMenu>
|
||||||
|
|
||||||
namespace QmlProjectManager {
|
namespace QmlProjectManager::QmlProjectExporter {
|
||||||
|
|
||||||
namespace QmlProjectExporter {
|
|
||||||
|
|
||||||
const char *PYTHON_MAIN_FILE_TEMPLATE = R"(
|
|
||||||
import os
|
|
||||||
import sys
|
|
||||||
from pathlib import Path
|
|
||||||
|
|
||||||
from PySide6.QtGui import QGuiApplication
|
|
||||||
from PySide6.QtQml import QQmlApplicationEngine
|
|
||||||
|
|
||||||
from autogen.settings import url, import_paths
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
|
||||||
app = QGuiApplication(sys.argv)
|
|
||||||
engine = QQmlApplicationEngine()
|
|
||||||
|
|
||||||
app_dir = Path(__file__).parent.parent
|
|
||||||
|
|
||||||
engine.addImportPath(os.fspath(app_dir))
|
|
||||||
for path in import_paths:
|
|
||||||
engine.addImportPath(os.fspath(app_dir / path))
|
|
||||||
|
|
||||||
engine.load(os.fspath(app_dir/url))
|
|
||||||
if not engine.rootObjects():
|
|
||||||
sys.exit(-1)
|
|
||||||
sys.exit(app.exec())
|
|
||||||
)";
|
|
||||||
|
|
||||||
void PythonGenerator::createMenuAction(QObject *parent)
|
void PythonGenerator::createMenuAction(QObject *parent)
|
||||||
{
|
{
|
||||||
@@ -66,8 +39,7 @@ PythonGenerator::PythonGenerator(QmlBuildSystem *bs)
|
|||||||
|
|
||||||
void PythonGenerator::updateMenuAction()
|
void PythonGenerator::updateMenuAction()
|
||||||
{
|
{
|
||||||
FileGenerator::updateMenuAction(
|
FileGenerator::updateMenuAction("QmlProject.EnablePythonGenerator",
|
||||||
"QmlProject.EnablePythonGenerator",
|
|
||||||
[this]() { return buildSystem()->enablePythonGeneration(); });
|
[this]() { return buildSystem()->enablePythonGeneration(); });
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -77,38 +49,47 @@ void PythonGenerator::updateProject(QmlProject *project)
|
|||||||
return;
|
return;
|
||||||
|
|
||||||
Utils::FilePath projectPath = project->rootProjectDirectory();
|
Utils::FilePath projectPath = project->rootProjectDirectory();
|
||||||
Utils::FilePath pythonPath = projectPath.pathAppended("Python");
|
Utils::FilePath pythonFolderPath = projectPath.pathAppended("Python");
|
||||||
if (!pythonPath.exists())
|
if (!pythonFolderPath.exists())
|
||||||
pythonPath.createDir();
|
pythonFolderPath.createDir();
|
||||||
|
|
||||||
Utils::FilePath mainFile = pythonPath.pathAppended("main.py");
|
Utils::FilePath mainFilePath = pythonFolderPath.pathAppended("main.py");
|
||||||
if (!mainFile.exists()) {
|
if (!mainFilePath.exists()) {
|
||||||
const QString mainContent = QString::fromUtf8(PYTHON_MAIN_FILE_TEMPLATE);
|
const QString mainFileTemplate = CMakeWriter::readTemplate(
|
||||||
CMakeWriter::writeFile(mainFile, mainContent);
|
":/templates/python_generator_main");
|
||||||
|
CMakeWriter::writeFile(mainFilePath, mainFileTemplate);
|
||||||
}
|
}
|
||||||
|
|
||||||
Utils::FilePath autogenPath = pythonPath.pathAppended("autogen");
|
Utils::FilePath pyprojectFilePath = pythonFolderPath.pathAppended("pyproject.toml");
|
||||||
if (!autogenPath.exists())
|
if (!pyprojectFilePath.exists()) {
|
||||||
autogenPath.createDir();
|
const QString pyprojectFileTemplate = CMakeWriter::readTemplate(
|
||||||
|
":/templates/python_pyproject_toml");
|
||||||
Utils::FilePath settingsPath = autogenPath.pathAppended("settings.py");
|
const QString pyprojectFileContent = pyprojectFileTemplate.arg(project->displayName());
|
||||||
CMakeWriter::writeFile(settingsPath, settingsFileContent());
|
CMakeWriter::writeFile(pyprojectFilePath, pyprojectFileContent);
|
||||||
}
|
}
|
||||||
|
|
||||||
QString PythonGenerator::settingsFileContent() const
|
Utils::FilePath autogenFolderPath = pythonFolderPath.pathAppended("autogen");
|
||||||
{
|
if (!autogenFolderPath.exists())
|
||||||
QTC_ASSERT(buildSystem(), return {});
|
autogenFolderPath.createDir();
|
||||||
|
|
||||||
QString content("\n");
|
Utils::FilePath settingsFilePath = autogenFolderPath.pathAppended("settings.py");
|
||||||
content.append("url = \"" + buildSystem()->mainFile() + "\"\n");
|
const QString settingsFileTemplate = CMakeWriter::readTemplate(
|
||||||
|
":/templates/python_generator_settings");
|
||||||
|
const QString settingsFileContent = settingsFileTemplate.arg(buildSystem()->mainFile());
|
||||||
|
CMakeWriter::writeFile(settingsFilePath, settingsFileContent);
|
||||||
|
|
||||||
content.append("import_paths = [\n");
|
// Python code uses the Qt resources collection file (.qrc)
|
||||||
for (const QString &path : buildSystem()->importPaths())
|
ResourceGenerator::createQrc(project);
|
||||||
content.append("\t\"" + path + "\",\n");
|
|
||||||
content.append("]\n");
|
|
||||||
|
|
||||||
return content;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace QmlProjectExporter.
|
/*!
|
||||||
} // namespace QmlProjectManager.
|
Regenerates the .qrc resources file
|
||||||
|
*/
|
||||||
|
void PythonGenerator::update(const QSet<QString> &added, const QSet<QString> &removed) {
|
||||||
|
Q_UNUSED(added);
|
||||||
|
Q_UNUSED(removed);
|
||||||
|
ResourceGenerator::createQrc(qmlProject());
|
||||||
|
// Generated Python code does not need to be updated
|
||||||
|
};
|
||||||
|
|
||||||
|
} // namespace QmlProjectExporter::QmlProjectManager.
|
||||||
|
@@ -21,11 +21,10 @@ public:
|
|||||||
static void createMenuAction(QObject *parent);
|
static void createMenuAction(QObject *parent);
|
||||||
|
|
||||||
PythonGenerator(QmlBuildSystem *bs);
|
PythonGenerator(QmlBuildSystem *bs);
|
||||||
|
|
||||||
|
void update(const QSet<QString> &added, const QSet<QString> &removed);
|
||||||
void updateMenuAction() override;
|
void updateMenuAction() override;
|
||||||
void updateProject(QmlProject *project) override;
|
void updateProject(QmlProject *project) override;
|
||||||
|
|
||||||
private:
|
|
||||||
QString settingsFileContent() const;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace QmlProjectExporter.
|
} // namespace QmlProjectExporter.
|
||||||
|
@@ -0,0 +1,26 @@
|
|||||||
|
import sys
|
||||||
|
|
||||||
|
from PySide6.QtGui import QGuiApplication
|
||||||
|
from PySide6.QtQml import QQmlApplicationEngine
|
||||||
|
|
||||||
|
from autogen.settings import setup_qt_environment
|
||||||
|
|
||||||
|
# Import here the Python files that define QML elements
|
||||||
|
|
||||||
|
|
||||||
|
def main():
|
||||||
|
app = QGuiApplication(sys.argv)
|
||||||
|
engine = QQmlApplicationEngine()
|
||||||
|
|
||||||
|
setup_qt_environment(engine)
|
||||||
|
|
||||||
|
if not engine.rootObjects():
|
||||||
|
sys.exit(-1)
|
||||||
|
|
||||||
|
ex = app.exec()
|
||||||
|
del engine
|
||||||
|
return ex
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == "__main__":
|
||||||
|
sys.exit(main())
|
@@ -0,0 +1,36 @@
|
|||||||
|
# This file is automatically generated by Qt Design Studio.
|
||||||
|
import os
|
||||||
|
import sys
|
||||||
|
from pathlib import Path
|
||||||
|
|
||||||
|
from PySide6.QtQml import QQmlApplicationEngine
|
||||||
|
|
||||||
|
project_root = Path(__file__).parent.parent.parent
|
||||||
|
|
||||||
|
|
||||||
|
def setup_qt_environment(qml_engine: QQmlApplicationEngine):
|
||||||
|
"""
|
||||||
|
Load the QML application. Import the compiled resources when the application is deployed.
|
||||||
|
"""
|
||||||
|
qml_app_url = "%1"
|
||||||
|
|
||||||
|
if "__compiled__" in globals():
|
||||||
|
# Application has been deployed using pyside6-deploy
|
||||||
|
try:
|
||||||
|
import autogen.resources # noqa: F401
|
||||||
|
except ImportError:
|
||||||
|
resource_file = Path(__file__).parent / "resources.py"
|
||||||
|
print(
|
||||||
|
f"Error: No compiled resources found in {resource_file.absolute()}\n"
|
||||||
|
f"Please compile the resources using pyside6-rcc or pyside6-project build",
|
||||||
|
file=sys.stderr,
|
||||||
|
)
|
||||||
|
sys.exit(1)
|
||||||
|
|
||||||
|
qml_engine.addImportPath(":/")
|
||||||
|
qml_engine.load(f":/{qml_app_url}")
|
||||||
|
return
|
||||||
|
|
||||||
|
qml_engine.addImportPath(str(project_root.absolute()))
|
||||||
|
os.environ["QT_QUICK_CONTROLS_CONF"] = str(project_root / "qtquickcontrols2.conf")
|
||||||
|
qml_engine.load(str(project_root / qml_app_url))
|
@@ -0,0 +1,5 @@
|
|||||||
|
[project]
|
||||||
|
name = "%1"
|
||||||
|
|
||||||
|
[tool.pyside6-project]
|
||||||
|
files = ["main.py", "autogen/settings.py"]
|
Reference in New Issue
Block a user