I'm trying to learn vala at the moment. With my sample app i have a problem with the GLib.Menu actions.
I declared a new action quit_action which should quit the app. The compiler runs without any warnings or errors, but when i run the app i can open the menu, but the item "quit" is greyed-out.
/* main.vala */
using Gtk;
class mainWindow : Gtk.ApplicationWindow {
public mainWindow (Application app) {
// Window Properties
this.set_default_size (800, 600);
this.window_position = Gtk.WindowPosition.CENTER;
this.destroy.connect (Gtk.main_quit);
// HeaderBar
var headerBar = new Gtk.HeaderBar ();
headerBar.set_title ("Test Title");
headerBar.set_subtitle ("Test Subtitle");
headerBar.set_show_close_button (true);
// Menu
var menuButton = new Gtk.Button.from_icon_name ("open-menu-symbolic", Gtk.IconSize.SMALL_TOOLBAR);
headerBar.pack_end (menuButton);
var menu = new GLib.Menu ();
menu.append ("Quit", "app.quit");
var popover = new Gtk.Popover (menuButton);
popover.bind_model (menu, "app");
menuButton.clicked.connect (() => {
popover.popup ();
popover.show_all ();
});
this.set_titlebar (headerBar);
this.show_all ();
}
}
public class Application : Gtk.Application {
public Application () {
Object (application_id: "org.example.application", flags: 0);
}
protected override void activate () {
// Create a new window for this application.
mainWindow win = new mainWindow (this);
win.show_all ();
Gtk.main ();
}
protected override void startup () {
base.startup ();
var quit_action = new GLib.SimpleAction ("quit", null);
quit_action.activate.connect (this.quit);
this.add_action (quit_action);
}
}
int main (string[] args) {
Gtk.init (ref args);
return new Application ().run (args);
}
There are two things wrong here:
You have to assign the Application to the ApplicationWindow (this is normally done in the constructor, but since it's a GLib style constructor you can't call the inherited constructor):
this.application = app;
The action names have to match, if you want to use app.quit
it has to be called that way in both places.
The fully working code:
/* main.vala */
using Gtk;
class mainWindow : Gtk.ApplicationWindow {
public mainWindow (Application app) {
this.application = app;
// Window Properties
this.set_default_size (800, 600);
this.window_position = Gtk.WindowPosition.CENTER;
this.destroy.connect (Gtk.main_quit);
// HeaderBar
var headerBar = new Gtk.HeaderBar ();
headerBar.set_title ("Test Title");
headerBar.set_subtitle ("Test Subtitle");
headerBar.set_show_close_button (true);
// Menu
var menuButton = new Gtk.Button.from_icon_name ("open-menu-symbolic", Gtk.IconSize.SMALL_TOOLBAR);
headerBar.pack_end (menuButton);
var menu = new GLib.Menu ();
menu.append ("Quit", "app.quit");
var popover = new Gtk.Popover (menuButton);
popover.bind_model (menu, "app");
menuButton.clicked.connect (() => {
//popover.popdown ();
popover.show_all ();
});
this.set_titlebar (headerBar);
this.show_all ();
}
}
public class Application : Gtk.Application {
public Application () {
Object (application_id: "org.example.application", flags: 0);
}
protected override void activate () {
// Create a new window for this application.
mainWindow win = new mainWindow (this);
win.show_all ();
Gtk.main ();
}
protected override void startup () {
base.startup ();
var quit_action = new GLib.SimpleAction ("app.quit", null);
quit_action.activate.connect (this.quit);
this.add_action (quit_action);
}
}
int main (string[] args) {
Gtk.init (ref args);
return new Application ().run (args);
}