淺談Qt信號與槽的各種連接方式
簡介
信號槽是 Qt 框架引以為豪的機制之一。當(dāng)用戶觸發(fā)某個事件時,就會發(fā)出一個信號(signal),這種發(fā)出是沒有目的的,類似廣播。如果有對象對這個信號感興趣,它就會連接(connect)綁定一個函數(shù)(稱為槽slot)來處理這個信號。也就是說當(dāng)信號發(fā)出時,被連接的槽函數(shù)會自動被回調(diào)。這有點類似與開發(fā)模式中的觀察者模式,即當(dāng)發(fā)生了感興趣的事件,某一個操作就會被自動觸發(fā)
信號和槽是Qt特有的信息傳輸機制,是Qt設(shè)計程序的重要基礎(chǔ),它可以讓互不干擾的對象建立一種聯(lián)系。槽的本質(zhì)是類的成員函數(shù),其參數(shù)可以是任意類型的。和普通C++成員函數(shù)幾乎沒有區(qū)別,它可以是虛函數(shù),也可以被重載??梢允枪械摹⒈Wo的、私有的、也可以被其他C++成員函數(shù)調(diào)用。唯一區(qū)別的是:槽可以與信號連接在一起,每當(dāng)和槽連接的信號被發(fā)射的時候,就會調(diào)用這個槽
連接信號槽 connect 函數(shù)的第五個參數(shù)
connect 函數(shù)原型如下:
[static] QMetaObject::Connection QObject::connect(const QObject *sender, const char *signal, const QObject *receiver, const char *method, Qt::ConnectionType type = Qt::AutoConnection)
ConnectionType 是一個定義在 Qt namespace 中的一個枚舉,具體內(nèi)容如下:
enum ConnectionType { AutoConnection, DirectConnection, QueuedConnection, BlockingQueuedConnection, UniqueConnection = 0x80 };
- Qt::AutoConnection:默認值。根據(jù) sender 和 receiver 所處線程在信號發(fā)出時作出判斷。如果在同一線程則使用 Qt::DirectConnection 連接,否則使用 Qt :: QueuedConnection 連接。需要注意的是,這個判斷和 sender 對象所處線程無關(guān),真正判斷的是發(fā)出信號這個動作所在的線程
- Qt::DirectConnection:槽函數(shù)會在信號發(fā)送的時候直接被調(diào)用,槽函數(shù)運行于信號發(fā)送者所在線程。效果看上去就像是直接在信號發(fā)送位置調(diào)用了槽函數(shù)。需要注意的是,在多線程環(huán)境下比較危險,可能會造成奔潰
- Qt::QueuedConnection:槽函數(shù)在控制回到接收者所在線程的事件循環(huán)時被調(diào)用,槽函數(shù)運行于信號接收者所在線程。發(fā)送信號之后,槽函數(shù)不會立刻被調(diào)用,等到接收者的當(dāng)前函數(shù)執(zhí)行完,進入事件循環(huán)之后,槽函數(shù)才會被調(diào)用。多線程環(huán)境下一般用這個
- Qt::BlockingQueuedConnection:槽函數(shù)的調(diào)用時機與 Qt::QueuedConnection 一致,不過發(fā)送完信號后發(fā)送者所在線程會阻塞,直到槽函數(shù)運行完,在多線程間需要同步的場合可能需要這個。需要注意的是,接收者和發(fā)送者絕對不能在一個線程,否則程序會死鎖
- Qt::UniqueConnection:這個 flag 可以通過按位或(|)與以上四個結(jié)合在一起使用。當(dāng)這個flag設(shè)置時,當(dāng)某個信號和槽已經(jīng)連接時,再進行重復(fù)的連接就會失敗,也就是避免了重復(fù)連接
信號與槽的連接方式
C++ 連接信號槽 - Qt4 語法
connect(ui->pushButton, SIGNAL(clicked()), this, SLOT(close()));
C++ 連接信號槽 - Qt5 語法
connect(ui->pushButton, &QPushButton::clicked, this, &MainWindow::close)
C++ 連接信號槽 - 函數(shù)指針
void(MainWindow:: *buttonClickSlot)() = &MainWindow::onButtonPushed; connect(ui->pushButton, &QPushButton::clicked, this, buttonClickSlot);
C++ 連接信號槽 - Lambda 表達式
connect(ui->pushButton, &QPushButton::clicked, this, [=](){ this->close(); });
C++ 信號連接 QML 的槽
class Test { signals: void sendData(QString str); }
1)如果注冊的是全局對象,則需要使用 Connections 連接:
Connections { target: test onSendData: { console.log(str) } }
2)如果注冊的是類,則需要先實例化對象,之后直接使用 on 接收:
Test { onSendData: { console.log(str) } }
QML 信號連接 C++ 的槽
#include <QQuickItem> QObject *quitButton = root->findChild<QObject*>("quitButton"); if (quitButton) { QObject::connect(quitButton, SIGNAL(clicked()), &app, SLOT(quit())); }
C++ 調(diào)用 QML 函數(shù)
QObject *changeBtn = root->findChild<QObject*>("objectName"); if (changeBtn) { QMetaObject::invokeMethod(changeBtn, "changeColor"); }
QML 調(diào)用 C++ 函數(shù)
onClicked: { className.test(); }
QML 信號連接 QML 的槽
// A.qml Rectangle { signal sendData(var data) } // B.qml Rectangle { onSendData: console.log(data) }
到此這篇關(guān)于淺談Qt信號與槽的各種連接方式的文章就介紹到這了,更多相關(guān)Qt信號與槽連接內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
C語言詳細分析結(jié)構(gòu)體的內(nèi)存對齊規(guī)則
C 數(shù)組允許定義可存儲相同類型數(shù)據(jù)項的變量,結(jié)構(gòu)是 C 編程中另一種用戶自定義的可用的數(shù)據(jù)類型,它允許你存儲不同類型的數(shù)據(jù)項,本篇讓我們來了解C 的結(jié)構(gòu)體內(nèi)存對齊2022-07-07C++用指針變量作為函數(shù)的參數(shù)接受數(shù)組的值的問題詳細總結(jié)
以下是對C++中用指針變量作為函數(shù)的參數(shù)接受數(shù)組的值的問題進行了詳細的總結(jié)介紹,需要的朋友可以過來參考下,希望對大家有所幫助2013-10-10