Go-GTK 信號處理

信號處理

簡介

如今咱們已經把按鈕添加到窗口中了,可是有一個問題:點擊按鈕沒有反應。咱們既然添加的是按鈕,確定但願當咱們點擊一個按鈕時,可以作一些事情,這就用到了信號處理。git

學習圖形界面編程,咱們會常常接觸到「信號」這個名詞。GTK中的「信號」其實是一種軟件中斷。「中斷」在咱們生活中常常遇到,譬如,我正在房間裏打遊戲,忽然送快遞的來了,把正在玩遊戲的我給「中斷」了,我去簽收快遞( 處理中斷 ),處理完成後,再繼續玩個人遊戲。GTK中的「信號」就是屬於這麼一種「中斷」,當用戶按下按鈕的時候,就產生一個「中斷」,至關於產生一個信號,接着就會處理這麼一個「中斷任務」(程序裏體驗爲調用一個函數)。github

按鈕中經常使用的信號:編程

信號標識 觸發條件
"clicked" 按下按鈕且鬆開鼠標時觸發(鼠標必須在按鈕範圍中)
"pressed" 按下按鈕時(尚未鬆開鼠標)觸發
"released" 釋放按鈕時(不管在哪鬆開鼠標)觸發

信號註冊

對於程序而言,咱們按下按鈕,其實就是調用一個函數來對信號進行處理。假若有函數A, B, C,咱們如何肯定按下按鈕後只調用函數A,而不是函數 B 或 C。這時候,咱們須要一種規則規定,按下按鈕後就調用函數A。函數

咱們經過控件的Connect()方法來處理對應的信號。佈局

Connect() 方法說明:學習

func (v *Widget) Connect(s string, f interface{}, datas ...interface{}) int
功能:信號註冊
參數:
  - v:信號發出者。能夠認爲咱們操做的控件,如按下按鈕,這個就是按鈕指針
  - s:信號標誌,如:"clicked"
  - f:回調函數的名稱
  - datas:給回調函數傳的參數。儘管是可變參數,可是隻能傳遞一個參數,可變參數的目的是爲了讓用戶多個選擇(能夠傳參,或者不傳)
返回值:註冊函數的標誌

示例程序

下面經過代碼實現一個按鈕的 clicked 信號,其它兩個請自行測試效果。測試

package main

import (
	"fmt"
	"github.com/mattn/go-gtk/glib"
	"github.com/mattn/go-gtk/gtk"
	"os"
)

func main(){
	//GTK初始化操做
	gtk.Init(&os.Args)

	// 經過GTK建立窗口
	win := gtk.NewWindow(gtk.WINDOW_TOPLEVEL)

	// 設置窗體的大小
	win.SetSizeRequest(640, 480)

	// 設置窗體標題
	win.SetTitle("GTK窗口")

	// 建立按鈕
	b := gtk.NewButton()
	// 設置按鈕大小
	b.SetSizeRequest(80, 32)
	// 設置按鈕內容
	b.SetLabel("點擊")

	// 設置按鈕點擊事件
	b.Connect("clicked", BtnClick, "點我幹嗎~")

	// 建立佈局
	layout := gtk.NewFixed()
	// 將按鈕 b 添加到佈局中
	layout.Add(b)

	// 放在佈局的指定位置
	layout.Put(b, 0, 0)
	// 移動按鈕的位置,必須先Put(),再用Move()
	layout.Move(b, 280, 224)

	// 將佈局放在界面中顯示
	win.Add(layout)

	// 將界面顯示
	win.ShowAll()

	// 調用GTK下的main運行程序
	gtk.Main()
}

// 按鈕 b 信號處理的回調函數
func BtnClick(ctx *glib.CallbackContext){
	// 獲取用戶傳遞的參數,空接口類型
	arg := ctx.Data()
	// 對數據進行類型斷言
	data, ok := arg.(string)
	// 若是 ok == true,說明類型斷言正確
	if ok{
		fmt.Println(data)
	}
}

或者能夠經過匿名函數來實現:網站

package main

import (
	"fmt"
	"github.com/mattn/go-gtk/glib"
	"github.com/mattn/go-gtk/gtk"
	"os"
)

func main(){
	//GTK初始化操做
	gtk.Init(&os.Args)

	// 經過GTK建立窗口
	win := gtk.NewWindow(gtk.WINDOW_TOPLEVEL)

	// 設置窗體的大小
	win.SetSizeRequest(640, 480)

	// 設置窗體標題
	win.SetTitle("GTK窗口")

	// 建立按鈕
	b := gtk.NewButton()
	// 設置按鈕大小
	b.SetSizeRequest(80, 32)
	// 設置按鈕內容
	b.SetLabel("點擊")

	// 設置按鈕點擊事件
	// b.Connect("clicked", BtnClick, "點我幹嗎~")

	// 使用匿名函數實現按鈕點擊事件處理
	b.Connect("clicked", func(ctx *glib.CallbackContext){
		// 獲取用戶傳遞的參數,空接口類型
		arg := ctx.Data()
		// 對數據進行類型斷言
		data, ok := arg.(string)
		// 若是 ok == true,說明類型斷言正確
		if ok{
			fmt.Println(data)
		}
	}, "點我幹嗎~")

	// 建立佈局
	layout := gtk.NewFixed()
	// 將按鈕 b 添加到佈局中
	layout.Add(b)

	// 放在佈局的指定位置
	layout.Put(b, 0, 0)
	// 移動按鈕的位置,必須先Put(),再用Move()
	layout.Move(b, 280, 224)

	// 將佈局放在界面中顯示
	win.Add(layout)

	// 將界面顯示
	win.ShowAll()

	// 調用GTK下的main運行程序
	gtk.Main()
}

運行結果:指針

運行結果

李培冠博客

歡迎訪問個人我的網站:code

李培冠博客:lpgit.com

相關文章
相關標籤/搜索