I'm developing an application using PySide6. It uses both QtWidgets and QML (using QQuickWidget). I'm not able to catch the signal emitted from Qt in QML.
Here is a minimal reproducable example of the which I develop for demonstration purpose.
main.py
import sys
from PySide6.QtCore import QObject, Signal
from PySide6.QtWidgets import (
QApplication,
QMainWindow,
QGridLayout,
QHBoxLayout,
QVBoxLayout,
QSizePolicy,
QLabel,
QPushButton,
QLineEdit,
QSpacerItem,
QWidget
)
from PySide6.QtQuickWidgets import QQuickWidget
class Message(QObject):
updated = Signal(str, arguments=['msg'])
def __init__(self):
super().__init__()
def set_message(self, msg):
print(f'emitting signal with message: {msg}')
self.updated.emit(msg)
class MainWindow(QMainWindow):
def __init__(self):
super().__init__()
self.setWindowTitle('QQuickWidget Example')
# create QQuickWidget and set the source
self.qw = QQuickWidget()
self.qw.setSource('view.qml')
self.qw.setSizePolicy(QSizePolicy.Policy.Expanding, QSizePolicy.Policy.Expanding)
self.qw.setResizeMode(QQuickWidget.SizeRootObjectToView)
self.lineedit = QLineEdit()
self.button = QPushButton('Start')
self.button.clicked.connect(self.on_button_clicked)
grid = QGridLayout()
grid.addWidget(QLabel('Ener: '), 0, 0, 1, 1)
grid.addWidget(self.lineedit, 0, 1, 1, 1)
grid.addWidget(self.button, 1, 0, 1, 2)
vertical_layout = QVBoxLayout()
vertical_layout.addLayout(grid)
vertical_layout.addSpacerItem(QSpacerItem(1, 1, QSizePolicy.Minimum))
main_layout = QHBoxLayout()
main_layout.addLayout(vertical_layout)
main_layout.addWidget(self.qw)
main_layout.setStretch(0, 1)
widget = QWidget()
widget.setLayout(main_layout)
self.setCentralWidget(widget)
self.message = Message()
# THIS DOESN'T SEEMS TO SET THE PROPERTY IN QML
self.qw.engine().rootContext().setContextProperty('message', self.message)
def on_button_clicked(self):
msg = self.lineedit.text()
self.message.set_message(msg)
if __name__ == '__main__':
app = QApplication(sys.argv)
window = MainWindow()
window.show()
sys.exit(app.exec())
Here the the view.qml file:
import QtQuick
Rectangle {
property string newText: "Hello"
property QtObject message
id: root
width: 500
height: 500
color: "white"
Text {
id: text
anchors.fill: parent
text: newText
font.pixelSize: 24
color: "blue"
}
Connections {
target: message
function onUpdated(msg) {
newText = msg
console.log(msg)
}
}
}
Upon clicking the button, the text in the QLineEdit is emitted in the signal which I'm trying to catch in QML but the text in the QML is not getting updated.
Can someone please point me what is wrong with the code.
