天天看點

Qt入門之信号與槽機制

一. 簡介

就我個人來了解,信号槽機制與Windows下消息機制類似,消息機制是基于回調函數,Qt中用信号與槽來代替函數指針,使程式更安全簡潔。

信号和槽機制是 Qt 的核心機制,可以讓程式設計人員将互不相關的對象綁定在一起,實作對象之間的通信。

  • 信号

    當對象改變其狀态時,信号就由該對象發射 (emit) 出去,而且對象隻負責發送信号,它不知道另一端是誰在接收這個信号。這樣就做到了真正的資訊封裝,能確定對象被當作一個真正的軟體元件來使用。

  • 用于接收信号,而且槽隻是普通的對象成員函數。一個槽并不知道是否有任何信号與自己相連接配接。而且對象并不了解具體的通信機制。

  • 信号與槽的連接配接

    所有從 QObject 或其子類 ( 例如 Qwidget ) 派生的類都能夠包含信号和槽。因為信号與槽的連接配接是通過 QObject 的 connect() 成員函數來實作的。

connect(sender, SIGNAL(signal), receiver, SLOT(slot));
           

其中 sender 與 receiver 是指向對象的指針,SIGNAL() 與 SLOT() 是轉換信号與槽的宏。

二. 特點

  • 一個信号可以連接配接多個槽

    當信号發射時,會以不确定的順序一個接一個的調用各個槽。

  • 多個信号可以連接配接同一個槽

    即無論是哪一個信号被發射,都會調用這個槽。

  • 信号直接可以互相連接配接

    發射第一個信号時,也會發射第二個信号。

  • 連接配接可以被移除

    這種情況用得比較少,因為在對象被删除時,Qt會自動移除與這個對象相關的所有連接配接。文法如下:

disconnect(sender, SIGNAL(signal), receiver, SLOT(slot));
           

三. 應注意的問題

  1. 信号與槽機制與普通函數的調用一樣,如果使用不當的話,在程式執行時也有可能産生死循環。是以,在定義槽函數時一定要注意避免間接形成無限循環,即在槽中再次發射所接收到的同樣信号。例如 , 在前面給出的例子中如果在 mySlot() 槽函數中加上語句 emit mySignal() 即可形成死循環。
  2. 如果一個信号與多個槽相聯系的話,那麼,當這個信号被發射時,與之相關的槽被激活的順序将是随機的。
  3. 宏定義不能用在 signal 和 slot 的參數中。
  4. 信号和槽的參數個數與類型必須一緻。

四. 程式舉例

這個demo程式由一個Label和PushButton組成,第一個例子中點選按鈕,可以讓label關閉,這是最簡單的信号與槽的連接配接;第二例子中點選按鈕,在label上擷取目前系統時間,這個涉及到的知識點有:信号與槽的參數類型不同時如何連接配接、自定義槽函數、自定義信号。

首先,建立一個Qt GUI程式,父視窗選為QDialog,類名為getTime,在頭檔案和CPP檔案分别加入如下代碼(小生愚鈍,還沒弄清楚部落格園MarkDown代碼塊怎麼高亮,是以隻好貼截圖了,見諒)

頭檔案

Qt入門之信号與槽機制

實作檔案

Qt入門之信号與槽機制

儲存、編譯、運作之後點選按鈕即可看到label消失了。

然後在頭檔案中加入自定義的槽函數和信号,并在CPP檔案中實作槽函數,具體如下:

Qt入門之信号與槽機制
Qt入門之信号與槽機制

然後儲存,編譯運作即可,點選按鈕後就能看到label上顯示目前時間了。