第15.16節 PyQt(Python+Qt)入門學習:PyQt中的信號(signal)和槽(slot)機制以及Designer中的使用

1、引言

前面一些章節其實已經在使用信號和槽了,可是做爲Qt中最重要的機制也是Qt區別與其餘開發平臺的重要核心特性,仍是很是有必要單獨介紹。web

2、信號和槽的概念

2.一、概述

信號和槽是Qt特有的信息傳輸機制,是Qt設計程序的重要基礎,它可讓互不干擾的對象創建一種聯繫。svg

信號和槽用於對象間的通訊,在一個圖形界面程序中,當一個部件中發生變化時,一般須要通知其餘對象,在Qt中當採用特定事件發生時會發射(注意此處用的是發射(emit)而不是發送,老猿估計是由於這裏的信號不是一對一發送的,而是能夠一對多發射)一個信號來通知須要通知的對象,須要關注的對象就會調用信號鏈接的槽函數執行響應操做。函數

從QObject或其子類(如QWidget)繼承的全部類均可以包含信號和插槽。佈局

2.二、信號(signal)

當對象以其餘對象可能感興趣的方式改變其狀態時,它們會發出信號。學習

Qt中的信號本質上是一個公有函數(即方法),信號只需聲明,不能對其進行定義,聲明函數時不能有返回值。因爲信號是某個對象的公有方法,信號能夠從任何地方經過emit語句發出,與直接調用信號對應函數相似,只是在函數調用語句前多了個emit。.net

發射信號的語句:emit 信號函數(信號參數)設計

Qt建議只從定義信號的類及其子類的類發出信號,Qt中的部件(又稱爲控件、組件)都有一些預約義的信號,如按鈕的clicked()信號。信號發出方不知道也不關心是否有對象在接收它發出的信號指針

2.三、槽(slot)

槽能夠用來接收信號,但槽也是部件派生類的正常成員函數,槽本質上是某個類的方法(包括虛方法),用來調用以響應特定信號,非虛函數的槽函數也能夠正常調用,與普通成員方法的惟一的區別是信號能夠鏈接到它們。code

因爲槽是普通成員方法,因此當直接調用時,它們遵循正常的成員方法調用規則。可是,做爲槽,它們能夠由任何組件經過信號鏈接調用,無論槽函數的訪問級別是公開仍是私有,信號的發射者無需知道哪些對象會執行槽函數響應它發射的信號(老猿認爲因爲Python的封裝機制,這點在PyQt中意義不大)。xml

就像一個對象不知道是否有任何東西接收到它的信號同樣,槽也不知道是否有任何信號鏈接到它。

2.四、處理信號

處理信號一般的作法是對可視部件進行子類化並添加對應的槽,以便處理感興趣的信號。
當信號發
出時,一般與之相連的槽像正常的函數調用同樣會當即執行,全部槽都返回後,將執行信號發出的emit語句後面的代碼。但在信號和槽鏈接使用隊列鏈接(connect函數的type參數值爲Qt.QueuedConnection,使用Qt Designer定義的信號和槽鏈接經過PyUIC生成的代碼不會使用該值)時狀況略有不一樣,在這種狀況下,emit關鍵字後面的代碼將當即繼續,槽將在稍後執行。

若是多個槽鏈接到一個信號,則當信號發射時,槽函數將按照創建鏈接的順序依次執行。

與其餘平臺用於對象間通訊的回調函數機制相比,信號和槽的機制稍微慢一些,發射與某些槽相連的信號,比用槽函數直接調用響應慢約十倍(不考慮槽函數自己的執行時間,只是從信號發射到槽函數開始執行的時間),但這種機制提供的靈活性增長了。

注意:

槽函數可能與多個對象的多個信號鏈接,有時代碼須要判斷信號是哪一個對象發送的,此時可使用在槽函數中使用sender()函數獲取信號的發送對象來進行不一樣的處理。具體可參考:《PyQt學習隨筆:槽函數獲取信號發送對象的方法

2、信號和槽的特色

2.一、信號和槽的參數必須匹配

Qt的signal s和slots機制確保,若是將一個信號鏈接到一個slot,該slot將在正確的時間使用信號的參數調用。在Qt中,信號和插槽能夠接受任意數量的任何類型的參數,但老猿認爲在PyQt中可能存在一些限制。

信號和槽的參數必須匹配體如今如下方面:

  • 信號和槽的簽名(英文原文是signature,老猿理解簽名就是所帶的參數)必須匹配,槽的參數能夠少於信號的參數數量,由於槽函數能夠忽略額外的參數,槽的參數不能多餘信號的參數,由於若槽的參數更多,則多餘的參數不能接收到信號傳遞過來的值,若在槽中使用了這些多餘的無值的參數,就會產生錯誤;
  • 信號和槽的參數類型必須匹配,在Qt Designer中進行信號和槽編輯時定義槽函數時必須帶參數類型;
  • 因爲Qt是C++語言的平臺,信號的參數類型都是C++類型的,可能存在部分參數類型Python沒法使用的狀況,這種狀況老猿在學習中遇到過但沒記錄下來,也沒有專門研究,但絕大多數類型特別是標準的C++類型能夠支持;
  • Python沒有指針以及引用類型,這兩種信號帶的參數在信號和槽函數編輯時槽函數參數必須是指針以及引用類型,但在派生類實現槽函數時將其當成去掉指針或引用的類型。例如,QAbstractButton *類型在實現槽函數時應該做爲QAbstractButton 類型處理。

2.二、信號和槽是鬆耦合的

這種鬆耦合表如今發出信號的對象既不知道也不關心哪一個槽接收信號,槽也不知道有哪些信號鏈接到它。從某種程度上講,信號和槽是相似電視節目和觀衆之間的關係。電視節目播放相似於信號發射,觀衆觀看節目相似於槽,觀衆選擇本身感興趣的節目觀看就是創建信號與槽的鏈接。

2.三、信號和槽之間是多對多的關係

  • 可將多個信號鏈接到同一個槽
  • 可將同一個信號鏈接到多個槽
  • 能夠將一個信號直接鏈接到另外一個信號(這將在第一個信號發出時當即發出第二個信號)

下圖是官網文檔給出的信號和槽的對應關係示例:
在這裏插入圖片描述

2.四、信號和槽支持預約義和自定義匹配

因Qt在其類庫中預約義了不少信號和槽,所以在Qt中能夠僅使用Qt類庫中預約義的信號和槽,也能夠只使用Qt類庫中預約義的信號而使用自已的槽,也可使用Qt類庫中預約義的槽來響應自已定義的信號,固然,槽和信號也均可以使用自定義的( 關於自定義信號本節不進行進一步探討)。

2.五、能夠斷開信號和槽之間的鏈接

在信號和槽鏈接以後,connect方法會返回一個QMetaObjec.Connection類型的鏈接句柄,經過該句柄調用 disconnect()就能夠斷開信號和槽的鏈接。

3、Qt Designer中信號和槽操做

3.一、概述

在Qt Designer中能夠自定義信號,但本節只介紹使用已有信號的操做方法。

3.二、槽函數的定義

要定義一個新的槽方法,經過Edit->Edit Signals/Slots或F4快捷鍵進入信號和槽編輯界面,如圖:
在這裏插入圖片描述
進入編輯界面後雙擊要新增槽函數的部件或者從發射信號的部件開始使用鼠標畫鏈接線,線的終點爲槽函數所在部件(通常在窗口對象),釋放鼠標後調出配置界面,如圖爲從pushButton發出信號到窗口的槽函數創建鏈接的案例:
在這裏插入圖片描述
點擊上圖中藍色標記的Edit按鈕,如圖:
在這裏插入圖片描述
點擊上圖中的加號就能夠增長新的槽函數。

注意:

  • 在此定義槽函數須要輸入槽函數名和各參數類型,不能輸入參數名
  • 參數類型只能是C++的通用類型和Qt支持的類型,不能是Python獨有的類型
  • 對已有的自定義槽函數能夠經過鼠標雙擊進行編輯

3.三、信號和槽函數鏈接方法1

進入信號和槽的編輯界面後,能夠經過鼠標在編輯界面右側的信號列表中選擇對應信號,在槽函數列表中選擇對應槽函數,點擊OK保存退出,就完成了信號和槽函數的鏈接創建。如圖:
在這裏插入圖片描述
注意

3.四、信號和槽函數鏈接方法2

除了3.3部分介紹的信號和槽函數的鏈接方法以外,還能夠在Designer右側的信號和槽函數編輯界面進行信號和槽函數鏈接。如圖黃色熒光筆標記窗口:
在這裏插入圖片描述
點擊下面藍色標記的加號,新增一條能夠編輯記錄,選擇每一個字段鼠標雙擊進行編輯,如圖:
在這裏插入圖片描述
退出編輯狀態後相關鏈接自動保存。

這種方式與第一種方式相比,有以下不一樣:

  • 第一種方式直接使用鏈接線相似繪製線條同樣操做,相比第二種方式操做簡單、鏈接顯示直觀,但當界面線條過多雜亂時反而不如第二種方式操做方便
  • 第二種方式能夠將一些不可見的對象如Action對象在編輯界面進行操做,而第一種方式則不行

小結

本節詳細介紹了Qt中信號和槽的概念,同時詳細闡述了PyQt中與Qt中使用的一些差異,並詳細介紹了Qt Designer中的操做方法,有助於你們深刻理解信號和槽的概念,並熟練使用。

老猿Python,跟老猿學Python!

博文目錄

博客地址

相關文章
相關標籤/搜索