Como adicionar botão de fechar abas no GtkNoteBook

Explicação

Quando é desenvolvido um sistema com abas dinâmicas, precisamos fazer uma funcionalidade de fechamento das abas. Existem varias formas de se fazer isso, uma delas é utilizando um botão com um X no canto a aba. Alem de um belo aspecto, é bem intuitivo ao usuário. Sempre foco minhas aplicações na facilidade de intuição, assim o usuário se adapta facilmente à solução gerante menos suporte, por isso foco bastante isso em meus posts.

Imagem

notebook

Solução

Cria-se um GtkHBox(), e adiciona-se um GtkLabel e um GtkButton;
Na aba, colocamos este GtkHBox();
Conectamos o botão ao button-press-event, levando o widget container da aba;
No callback, recuperamos o index da aba a partir do widget container, e removemos a mesma.

Exemplo

widgets['ntbTeste'] = new GtkNoteBook();
			
			// Cria a primeira aba
			$this->__createTab(new GtkFixed(), "Aba 1");
			
			// Cria a segunda aba
			$this->__createTab(new GtkFixed(), "Aba 2");
			
			// Cria a terceira aba
			$this->__createTab(new GtkFixed(), "Aba 3");
			
			// Cria a janela
			$this->widgets['frmTeste'] = new GtkWindow();
			$this->widgets['frmTeste']->set_size_request(300, 200);
			$this->widgets['frmTeste']->set_resizable(FALSE);
			$this->widgets['frmTeste']->set_title("Teste");
			$this->widgets['frmTeste']->add($this->widgets['ntbTeste']);
			$this->widgets['frmTeste']->set_position(GTK::WIN_POS_CENTER);
			$this->widgets['frmTeste']->show_all();
			
			// Conecta o destroy
			$this->widgets['frmTeste']->connect_simple(
				"destroy", 
				array("Gtk", "main_quit")
			);
		}
		
		// Método que remove a aba
		public function ntbTeste_onTabClose($widget, $event, $child)
		{
			$index = $this->widgets['ntbTeste']->page_num($child);
			$this->widgets['ntbTeste']->remove_page($index);
		}
		
		// Método que cria a aba, para limpar o código
		private function __createTab($widget, $label)
		{
			// Cria o botão com a imagem
			$btn = new GtkButton();
			$img = GtkImage::new_from_stock(Gtk::STOCK_CLOSE, Gtk::ICON_SIZE_MENU);
			$hbox = new GtkHBox(0);
			$hbox->set_size_request(30, 20);
			$btn->set_size_request(30, 20);
			$hbox->pack_start($img, 0, 0);
			$btn->add($hbox);
			
			// Cria o label
			$lbl = new GtkLabel($label);
			
			// Cria o container da aba, e adiciona o label e o botão
			$hbox = new GtkHBox();
			$hbox->pack_start($lbl);
			$hbox->pack_start($btn);
			$hbox->show_all();
			
			// Cria a aba
			$tabIndex = $this->widgets['ntbTeste']->append_page($widget, $hbox);
			
			// Coneta o botão
			$btn->connect("button-press-event", array($this, "ntbTeste_onTabClose"), $widget);
		}
	}

	// Inicia a aplicação
	$teste = new Teste();
	gtk::main();

Referências

http://gtk.php.net/manual/en/gtk.gtkbutton.constructor.new_from_stock.php
http://gtk.php.net/manual/en/gtk.gtknotebook.method.remove_page.php
http://gtk.php.net/manual/en/gtk.gtkwidget.signal.button-release-event.php