Qt第十六章:QWidget与QML混合开发

这篇具有很好参考价值的文章主要介绍了Qt第十六章:QWidget与QML混合开发。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

目录

一、Qml作为窗口引入

二、Qml作为控件引入(Qml根组件不能是window)

三、两个问题①Qml文件如何调用python函数②python代码如何控制Qml元素。


一、Qml作为窗口引入

例:QWidget窗口中用按钮打开和关闭Qml窗口
①QWidget窗口

import sys
from pathlib import Path

from PySide6.QtCore import QObject, Slot
from PySide6.QtQml import QQmlApplicationEngine
from PySide6.QtQuick import QQuickItem
from PySide6.QtWidgets import QApplication, QWidget, QPushButton

class TestWidget(QWidget):
    def __init__(self, parent=None):
        super(TestWidget, self).__init__(parent)
        self.button_open = QPushButton(self)
        self.button_open.setText("打开Qml窗口")
        self.button_open.setGeometry(0, 100, 100, 50)
        self.button_open.clicked.connect(self.handle_button_open_click)
        self.button_close = QPushButton(self)
        self.button_close.setText("关闭Qml窗口")
        self.button_close.setGeometry(100, 100, 100, 50)
        self.button_close.clicked.connect(self.handle_button_close_click)

    # 打开Qml窗口
    def handle_button_open_click(self):
        self.widget = LoginQuickWidget()

    # 关闭Qml窗口
    def handle_button_close_click(self):
        if hasattr(self, 'widget') and self.widget:
            del self.widget


if __name__ == '__main__':
    app = QApplication([])
    widget = TestWidget()
    widget.show()
    app.exec()

②Qml窗口

注意:此处是直接引入qml文件。如果是从qrc资源文件中引入qml,则直接QQmlApplicationEngine.load即可
qwidget和qml混合编程,Qt for Python,qt,ui,开发语言,qt designer,pyside6 ​​​​​​​qwidget和qml混合编程,Qt for Python,qt,ui,开发语言,qt designer,pyside6

# 槽函数类(一个承载槽函数的容器类)
class Slots(QObject):
    def __init__(self, objects):
        self.objects = objects
        super().__init__()

    @Slot(str, result=None)
    def set_text_msg(self, msg):
        # 获取qml中的Text对象
        child = self.objects[0].findChild(QQuickItem, "text1")
        # 获取对象属性
        p = child.property("text")
        # 设置对象属性
        child.setProperty("text", p + msg)

    @Slot(result=str)
    def get_text_msg(self):
        return "皎氯"


"""
这种方式是以Qml作为窗口来使用。所有的逻辑UI都由Qml来完成。python提供可以调用数据的API即可。
"""


class LoginQuickWidget:
    def __init__(self):
        # 初始化UI
        self.engine = QQmlApplicationEngine()
        qml_file = Path(__file__).resolve().parent / "login.qml"
        # 加载qml文件
        self.engine.load(qml_file)
        if not self.engine.rootObjects():
            sys.exit(-1)
        # qml对象集合
        objects = self.engine.rootObjects()
        # 实例化槽函数
        self.slots = Slots(objects)
        # 注入槽函数
        self.engine.rootContext().setContextProperty('slots', self.slots)

③Qml文件文章来源地址https://www.toymoban.com/news/detail-562437.html

/**************************QML文件**************************/

import QtQuick
import QtQuick.Window
import QtQuick.Controls 6.3
import QtQuick.Layouts 6.3
import QtQuick.Controls.Windows 6.0

//主窗口
Window {
    width: 800
    height: 400
    visible: true
    title: qsTr("测试窗口")
    Image {
        id:background_image
        anchors.fill: parent
        fillMode: Image.PreserveAspectCrop
        source: "http://cube.elemecdn.com/6/94/4d3ea53c084bad6931a56d5158a48jpeg.jpeg"
        antialiasing: true
    }
    //文本展示框
    Text {
        id: text1
        //用于python获取此对象
        objectName:"text1"
        x: 300
        y: 20
        width: 200
        height: 34
        text: qsTr("初始值")
        font.pixelSize: 12
    }

    //一:通过JavaScript控制UI逻辑
    Button {
        id: button
        x: 125
        y: 179
        width: 125
        height: 29
        text: qsTr("调用JavaScript方法")
        //点击事件
        onClicked: {
            change()
        }
        //JavaScript函数
        function change(){
            var date = new Date();
            text1.text=qsTr(date.getFullYear()+"年"+(date.getMonth() + 1)+"月"+date.getDate()+"日"+date.getHours()+"时"+date.getMinutes()+"分"+date.getSeconds()+"秒")
        }
    }

    //二:通过Python控制UI逻辑(不推荐,因为要做UI与业务逻辑分离;槽函数相当于于ajax请求来获取数据,而不是去控制UI本身)
    Button {
        id: button1
        x: 325
        y: 179
        width: 125
        height: 29
        text: qsTr("调用Python设置属性")
        //点击事件
        onClicked: {
            //调用注入的槽函数,使用槽函数改变视图
            slots.set_text_msg("小小改变")
        }
    }

    //三:通过Python获取数据,JavaScript渲染UI(推荐方式)
    Button {
        id: button2
        x: 525
        y: 179
        width: 125
        height: 29
        text: qsTr("调用Python获取数据")
        //点击事件
        onClicked: {
            //调用注入的槽函数,使用槽函数获取数据
            var msg=slots.get_text_msg()
            //利用JS进行渲染
            text1.text=qsTr(msg)
        }
    }

}

二、Qml作为控件引入(Qml根组件不能是window)

from PySide6.QtCore import QUrl, Slot, QObject
from PySide6.QtQuick import QQuickItem
from PySide6.QtQuickWidgets import QQuickWidget
from PySide6.QtWidgets import QWidget, QApplication, QVBoxLayout, QPushButton


# 槽函数类(一个承载槽函数的容器类)
class Slots(QObject):
    def __init__(self, obj):
        super(Slots, self).__init__()
        self.obj = obj

    @Slot(str, result=None)
    def set_text_msg(self, msg):
        # 获取qml中的Text对象
        child = self.obj.findChild(QQuickItem, "text1")
        # 获取对象属性
        p = child.property("text")
        # 设置对象属性
        child.setProperty("text", p + msg)

    @Slot(result=str)
    def get_text_msg(self):
        return "皎氯"


class TestQWidget(QWidget):

    def __init__(self, parent=None):
        super(TestQWidget, self).__init__(parent)
        self.resize(800, 300)
        # 垂直布局
        self.layout = QVBoxLayout(self)
        # OK按钮
        self.button = QPushButton("OK")
        self.button.clicked.connect(lambda: print("OK"))
        self.layout.addWidget(self.button)

        # QML控件
        self.qml_widget = QQuickWidget()
        # 设置缩放模式
        self.qml_widget.setResizeMode(QQuickWidget.ResizeMode.SizeRootObjectToView)
        # 向QML中传入数据(必须在setSource之前传入)
        self.qml_widget.rootContext().setContextProperty("obj", '张良')
        self.qml_widget.setSource(QUrl("test2.qml"))
        # 获取QML中的对象(必须在setSource之后)
        self.root_object: QQuickItem = self.qml_widget.rootObject()
        # 实例化槽函数
        self.slots = Slots(self.root_object)
        # 注入槽函数
        self.qml_widget.rootContext().setContextProperty('slots', self.slots)

        # 获取对象
        child: QQuickItem = self.root_object.findChild(QQuickItem, "text1")
        # 获取对象属性
        print(child.property("text"))
        
        # 加入布局
        self.layout.addWidget(self.qml_widget)


if __name__ == '__main__':
    app = QApplication([])
    widget = TestQWidget()
    widget.show()
    app.exec()
import QtQuick
import QtQuick.Window
import QtQuick.Controls 6.3
import QtQuick.Layouts 6.3
import QtQuick.Controls.Windows 6.0


Rectangle {
    id:root
    color: "yellow"
    radius:10
    //背景图
    Image {
        id:background_image
        anchors.fill: parent
        fillMode: Image.PreserveAspectCrop
        source: "http://cube.elemecdn.com/6/94/4d3ea53c084bad6931a56d5158a48jpeg.jpeg"
        antialiasing: true
    }
    //文本展示框
    Text {
        id: text1
        //用于python获取此对象
        objectName:"text1"
        x: 300
        y: 20
        width: 200
        height: 34
        text: qsTr(obj)
        font.pixelSize: 12
    }

    //一:通过JavaScript控制UI逻辑
    Button {
        id: button
        x: 125
        y: 179
        width: 125
        height: 29
        text: qsTr("调用JavaScript方法")
        //点击事件
        onClicked: {
            change()
        }
        //JavaScript函数
        function change(){
            var date = new Date();
            text1.text=qsTr(date.getFullYear()+"年"+(date.getMonth() + 1)+"月"+date.getDate()+"日"+date.getHours()+"时"+date.getMinutes()+"分"+date.getSeconds()+"秒")
        }
    }

    //二:通过Python控制UI逻辑(不推荐,因为要做UI与业务逻辑分离;槽函数相当于于ajax请求来获取数据,而不是去控制UI本身)
    Button {
        id: button1
        x: 325
        y: 179
        width: 125
        height: 29
        text: qsTr("调用Python设置属性")
        //点击事件
        onClicked: {
            //调用注入的槽函数,使用槽函数改变视图
            slots.set_text_msg("小小改变")
        }
    }

    //三:通过Python获取数据,JavaScript渲染UI(推荐方式)
    Button {
        id: button2
        x: 525
        y: 179
        width: 125
        height: 29
        text: qsTr("调用Python获取数据")
        //点击事件
        onClicked: {
            //调用注入的槽函数,使用槽函数获取数据
            var msg=slots.get_text_msg()
            //利用JS进行渲染
            text1.text=qsTr(msg)
        }
    }

}

三、3个问题①Qml文件如何调用python函数②python代码如何控制Qml元素。③python如何执行Qml中的函数。

到了这里,关于Qt第十六章:QWidget与QML混合开发的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • Qt 之 QWidget QLabel

    Qt Creator 以工程项目 的方式对源码进行管理一个Qt Creator工程包含不同类型的文件 。 .pro 项目描述文件 .pro.user用户配置描述文件- .h头文件 .cpp源文件 .ui界面描述文件 资源文件(图片,音频,等) pro 项目描述文件的基本组成 #一注释起始符 : 以“#”开始,到这一行结束。快捷

    2024年02月13日
    浏览(62)
  • 【QT】QWidget实现柱状图

    在名为 w_bar20auto1 的 QWidget 实现柱状图

    2024年02月02日
    浏览(62)
  • Qt:QWidget设置半透明背景

    设置窗体QWidget半透明背景 首先前提条件是设置: setAttribute(Qt::WA_TranslucentBackground); 方法一:重写QPaintEvent 方法二:自定义qss样式 方法三:使用QGraphicsOpacityEffect ,不过这种方法会影响子控件的透明度 效果参考如下:

    2024年02月15日
    浏览(86)
  • Qt QWidget、QDialog、QMainWindow的区别

    QWidget QWidget 是Qt框架中最基础的窗口类,可以理解为用户界面的最基本单元。QWidget类提供了一个空白窗口,可以通过继承该类来创建自定义的窗口类。QWidget类提供了基本的窗口属性和方法,如大小、位置、标题、图标等。 QDialog QDialog 是QWidget类的子类,用于创建对话框窗口

    2024年02月08日
    浏览(38)
  • QWidget:Qt中的基本用户界面类

    QString类是Qt中非常重要的一个类,用于表示基本用户界面构件。它是其他用户界面( Widget )类的基类,例如QMainWindow、QDialog和QPushButton等。在本文中,我们将详细介绍QWidget类的功能和应用场景。 为了创建QWidget对象,我们可以使用QWidget的默认构造函数或指定其父对象、名称和其

    2024年02月09日
    浏览(44)
  • 在ARM板上实现qt虚拟键盘 Qwidget实现 官方虚拟键盘、第三方虚拟键盘qtvirtualkeyboard //Qwidget最简单但效果不是最好

    在使用qt的虚拟键盘以前,我的开发板qt环境中并没有安装虚拟键盘库,所以这里还会顺便介绍如何在开发板上已安装qt环境的前提下,继续更新qt的组件。 开发板qt版本:5.15.2 在这里,我默认你已经有自己动手交叉编译过qt源码了,否则你将缺少部分细节和前置知识。首先在

    2024年04月09日
    浏览(350)
  • 【Qt】用QWidget显示opencv采集的摄像头图像

    本案例用QWidget容器重写paintEvent函数来显示OpenCv采集的摄像头画面,图像还可以自适应QWidget的大小,还可以检测相机断开失联的情况(可能是掉电、线被拔了等待)。在改变窗口大小时暂停显示图像,防止莫名其妙的卡顿奔溃错误!(显示图像的方式有很多种,可以用QLabel显

    2024年02月13日
    浏览(57)
  • Qt QWidget 抗锯齿圆角窗口的一个实现方案(支持子控件)

    由于 QWidget::setMask 接口设置圆角不支持抗锯齿,所以通常会使用透明窗口加圆角背景,但圆角背景不能满足对子控件的裁剪,子控件与圆角区域重叠的部分还是能显示出来。当然对于大多数窗口,留出足够的边距也是可以接受。 对一些特殊场景,比如QComboBox的列表框,UI设计

    2023年04月24日
    浏览(60)
  • Qt QWidget 设置样式表不生效的两种解决方案

    在进行Qt开发的时候,我们往往会遇到这样的场景:         使用Qt Designer 设计界面,但在Qt Designer里设置好样式表,使用快捷键 shift + alt + r 进行预览,样式都是正常的,但程序运行起来,样式就不生效了。 例如设计一个列表,我们将一条数据(一行)设计设计成一个类

    2023年04月10日
    浏览(44)
  • 【Qt 学习笔记】QWidget的windowTitle属性 | windowIcon属性 | qrc文件机制

    博客主页:Duck Bro 博客主页 系列专栏:Qt 专栏 关注博主,后期持续更新系列文章 如果有错误感谢请大家批评指出,及时修改 感谢大家点赞👍收藏⭐评论✍ 文章编号:Qt 学习笔记 / 17 1. 简介 windowTitle属性是一种在用户界面中显示窗口的标题的属性。它可以用来设置窗口的标

    2024年04月15日
    浏览(37)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包