qt - 如何在 Loader 的项目中正确连接信号?

标签 qt signals qml loader qt-quick

我想将 QObject 的一个信号连接到由“Loader”qml 元素加载的各个页面。我的问题类似 Dead QML elements receiving signals?但加载的项目在调用“onDestruction”方法之前被销毁。
例如下面,如果在控制台中从 page1 切换到 page2 写:

"QML: Loading status:  1  Item:  QDeclarativeRectangle(0x8dcd408, "page2")
QML Item: Loaded QDeclarativeRectangle(0x8dcd408, "page2") 1
qrc:/page1.qml:12: TypeError: Result of expression 'parent' [null] is not an object.
qrc:/page1.qml:15: ReferenceError: Can't find variable: page1text"

每一秒。所以不能断开信号,因为父对象被破坏了。

如何处理加载项中来自 QObject(根)的信号?或如何从卸载页面断开信号?

主文件
import QtQuick 1.1

Rectangle {
    id: root
    objectName: "root"
    width: 360
    height: 360
    state: "page1"
    color: "white"

    Item {
        width: parent.width
        height: parent.height/2
        anchors.top: parent.top
        Loader {
            id: pageLoader
            objectName: "pageLoader"
            anchors.fill: parent
            anchors.centerIn: parent
            signal textMsg(variant params)
            onStatusChanged: console.log("QML: Loading status: ", status, " Item: ", item)
            onLoaded: { console.log("QML Item: Loaded",item,status); }
        }
    }
    states: [
        State {
            name: "page1"
            PropertyChanges { target: pageLoader; source: "qrc:/page1.qml"}
        }
        ,State {
            name: "page2"
            PropertyChanges { target: pageLoader; source: "qrc:/page2.qml"}
        }
    ]
    Timer {
        // simulate signals from QObject
        interval: 1000; running: true; repeat: true
        onTriggered: pageLoader.textMsg({"msg2page1":"test","msg2page2":"test"})
    }
    Rectangle {
        anchors.left: parent.left
        anchors.bottom: parent.bottom
        width: parent.width/2
        height: parent.height/2
        border {
            color: "black"
            width: 1
        }
        color: "yellow"
        Text{
            anchors.fill: parent
            anchors.centerIn: parent
            text: "Set Page 1"
        }
        MouseArea {
            anchors.fill: parent
            onClicked: {
                root.state = "page1";
            }
        }
    }
    Rectangle {
        anchors.right: parent.right
        anchors.bottom: parent.bottom
        width: parent.width/2
        height: parent.height/2
        border {
            color: "black"
            width: 1
        }
        color: "red"
        Text{
            anchors.fill: parent
            anchors.centerIn: parent
            text: "Set Page 2"
        }
        MouseArea {
            anchors.fill: parent
            onClicked: {
                root.state = "page2";
            }
        }
    }
}

页面1.qml
import QtQuick 1.1

Rectangle {
    id: page1
    objectName: "page1"
    color: "yellow"

    Component.onCompleted: {
        parent.textMsg.connect(msgHandler);
    }
    Component.onDestruction: {
        parent.textMsg.disconnect(msgHandler);
    }
    function msgHandler(params) {
        page1text.text += " "+params.msg2page1;
    }
    Text {
        id: page1text
        anchors.fill: parent
        wrapMode: Text.WordWrap
        text: "page1"
    }
}

页面2.qml
import QtQuick 1.1

Rectangle {
    id: page2
    objectName: "page2"
    color: "red"
}

最佳答案

这在 Loader 中有很好的描述documenation .它写道:

Any signals emitted from the loaded item can be received using the Connections element.



还有一个例子,为了清楚起见,我复制在下面:
// Application.qml

import QtQuick 1.0

Item {
    width: 100; height: 100
    Loader {
        id: myLoader
        source: "MyItem.qml"
    }
    Connections {
        target: myLoader.item
        onMessage: console.log(msg)
    }
}

// MyItem.qml

import QtQuick 1.0

Rectangle {
    id: myItem
    signal message(string msg)
    width: 100; height: 100
    MouseArea {
        anchors.fill: parent
        onClicked: myItem.message("clicked!")
    }
}

显然,如果 item被销毁,任何信号处理程序都将被忽略,直到再次重新创建目标。

关于qt - 如何在 Loader 的项目中正确连接信号?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34207430/

相关文章:

python - PyQt 代码拆分——设计与功能

bash - shell脚本中的 `kill -0 $pid`有什么作用?

c - sigtimedwait() 在超时前返回 EAGAIN

qt - DropArea 不通知有关 onEntered、onExited、onDropped 的操作

c++ - 在 QQuickItem 引用上发出信号

qt - QML 文本元素超链接

qt - 将所有 QLineEdits 设置为只读

c++ - 无法将我的小部件添加到布局

c++ - 如何在各种显示器上使用 Qt/C++ 获取打印屏幕?

c - wait() 函数(在 LINUX 中)什么时候响应中断?