gtk2/examples/bloatpad.c
Ryan Lortie eed307713b GtkBuilder: change format of menus
Change the format of GtkBuilder <menu> to be more in-line with the style
of the rest of GtkBuilder so that we can do translation in a consistent
way.

The format is now substantially more difficult to hand-write, but tools
should be along soon.

There is an xslt program attached to the bug to help you convert your
existing .ui files from the old format to the new one.

https://bugzilla.gnome.org/show_bug.cgi?id=668696
2012-01-25 19:42:19 -05:00

396 lines
13 KiB
C

#include <stdlib.h>
#include <gtk/gtk.h>
static void
activate_toggle (GSimpleAction *action,
GVariant *parameter,
gpointer user_data)
{
GVariant *state;
state = g_action_get_state (G_ACTION (action));
g_action_change_state (G_ACTION (action), g_variant_new_boolean (!g_variant_get_boolean (state)));
g_variant_unref (state);
}
static void
activate_radio (GSimpleAction *action,
GVariant *parameter,
gpointer user_data)
{
g_action_change_state (G_ACTION (action), parameter);
}
static void
change_fullscreen_state (GSimpleAction *action,
GVariant *state,
gpointer user_data)
{
if (g_variant_get_boolean (state))
gtk_window_fullscreen (user_data);
else
gtk_window_unfullscreen (user_data);
g_simple_action_set_state (action, state);
}
static void
change_justify_state (GSimpleAction *action,
GVariant *state,
gpointer user_data)
{
GtkTextView *text = g_object_get_data (user_data, "bloatpad-text");
const gchar *str;
str = g_variant_get_string (state, NULL);
if (g_str_equal (str, "left"))
gtk_text_view_set_justification (text, GTK_JUSTIFY_LEFT);
else if (g_str_equal (str, "center"))
gtk_text_view_set_justification (text, GTK_JUSTIFY_CENTER);
else if (g_str_equal (str, "right"))
gtk_text_view_set_justification (text, GTK_JUSTIFY_RIGHT);
else
/* ignore this attempted change */
return;
g_simple_action_set_state (action, state);
}
static GtkClipboard *
get_clipboard (GtkWidget *widget)
{
return gtk_widget_get_clipboard (widget, gdk_atom_intern_static_string ("CLIPBOARD"));
}
static void
window_copy (GSimpleAction *action,
GVariant *parameter,
gpointer user_data)
{
GtkWindow *window = GTK_WINDOW (user_data);
GtkTextView *text = g_object_get_data ((GObject*)window, "bloatpad-text");
gtk_text_buffer_copy_clipboard (gtk_text_view_get_buffer (text),
get_clipboard ((GtkWidget*) text));
}
static void
window_paste (GSimpleAction *action,
GVariant *parameter,
gpointer user_data)
{
GtkWindow *window = GTK_WINDOW (user_data);
GtkTextView *text = g_object_get_data ((GObject*)window, "bloatpad-text");
gtk_text_buffer_paste_clipboard (gtk_text_view_get_buffer (text),
get_clipboard ((GtkWidget*) text),
NULL,
TRUE);
}
static GActionEntry win_entries[] = {
{ "copy", window_copy, NULL, NULL, NULL },
{ "paste", window_paste, NULL, NULL, NULL },
{ "fullscreen", activate_toggle, NULL, "false", change_fullscreen_state },
{ "justify", activate_radio, "s", "'left'", change_justify_state }
};
static void
new_window (GApplication *app,
GFile *file)
{
GtkWidget *window, *grid, *scrolled, *view;
GtkWidget *toolbar;
GtkToolItem *button;
GtkWidget *sw, *box, *label;
window = gtk_application_window_new (GTK_APPLICATION (app));
gtk_window_set_default_size ((GtkWindow*)window, 640, 480);
g_action_map_add_action_entries (G_ACTION_MAP (window), win_entries, G_N_ELEMENTS (win_entries), window);
gtk_window_set_title (GTK_WINDOW (window), "Bloatpad");
grid = gtk_grid_new ();
gtk_container_add (GTK_CONTAINER (window), grid);
toolbar = gtk_toolbar_new ();
button = gtk_toggle_tool_button_new_from_stock (GTK_STOCK_JUSTIFY_LEFT);
gtk_actionable_set_detailed_action_name (GTK_ACTIONABLE (button), "win.justify::left");
gtk_container_add (GTK_CONTAINER (toolbar), GTK_WIDGET (button));
button = gtk_toggle_tool_button_new_from_stock (GTK_STOCK_JUSTIFY_CENTER);
gtk_actionable_set_detailed_action_name (GTK_ACTIONABLE (button), "win.justify::center");
gtk_container_add (GTK_CONTAINER (toolbar), GTK_WIDGET (button));
button = gtk_toggle_tool_button_new_from_stock (GTK_STOCK_JUSTIFY_RIGHT);
gtk_actionable_set_detailed_action_name (GTK_ACTIONABLE (button), "win.justify::right");
gtk_container_add (GTK_CONTAINER (toolbar), GTK_WIDGET (button));
button = gtk_separator_tool_item_new ();
gtk_separator_tool_item_set_draw (GTK_SEPARATOR_TOOL_ITEM (button), FALSE);
gtk_tool_item_set_expand (GTK_TOOL_ITEM (button), TRUE);
gtk_container_add (GTK_CONTAINER (toolbar), GTK_WIDGET (button));
button = gtk_tool_item_new ();
box = gtk_box_new (GTK_ORIENTATION_HORIZONTAL, 6);
gtk_container_add (GTK_CONTAINER (button), box);
label = gtk_label_new ("Fullscreen:");
gtk_container_add (GTK_CONTAINER (box), label);
sw = gtk_switch_new ();
gtk_actionable_set_action_name (GTK_ACTIONABLE (sw), "win.fullscreen");
gtk_container_add (GTK_CONTAINER (box), sw);
gtk_container_add (GTK_CONTAINER (toolbar), GTK_WIDGET (button));
gtk_grid_attach (GTK_GRID (grid), toolbar, 0, 0, 1, 1);
scrolled = gtk_scrolled_window_new (NULL, NULL);
gtk_widget_set_hexpand (scrolled, TRUE);
gtk_widget_set_vexpand (scrolled, TRUE);
view = gtk_text_view_new ();
g_object_set_data ((GObject*)window, "bloatpad-text", view);
gtk_container_add (GTK_CONTAINER (scrolled), view);
gtk_grid_attach (GTK_GRID (grid), scrolled, 0, 1, 1, 1);
if (file != NULL)
{
gchar *contents;
gsize length;
if (g_file_load_contents (file, NULL, &contents, &length, NULL, NULL))
{
GtkTextBuffer *buffer;
buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (view));
gtk_text_buffer_set_text (buffer, contents, length);
g_free (contents);
}
}
gtk_widget_show_all (GTK_WIDGET (window));
}
static void
bloat_pad_activate (GApplication *application)
{
new_window (application, NULL);
}
static void
bloat_pad_open (GApplication *application,
GFile **files,
gint n_files,
const gchar *hint)
{
gint i;
for (i = 0; i < n_files; i++)
new_window (application, files[i]);
}
typedef GtkApplication BloatPad;
typedef GtkApplicationClass BloatPadClass;
G_DEFINE_TYPE (BloatPad, bloat_pad, GTK_TYPE_APPLICATION)
static void
bloat_pad_finalize (GObject *object)
{
G_OBJECT_CLASS (bloat_pad_parent_class)->finalize (object);
}
static void
new_activated (GSimpleAction *action,
GVariant *parameter,
gpointer user_data)
{
GApplication *app = user_data;
g_application_activate (app);
}
static void
about_activated (GSimpleAction *action,
GVariant *parameter,
gpointer user_data)
{
gtk_show_about_dialog (NULL,
"program-name", "Bloatpad",
"title", "About Bloatpad",
"comments", "Not much to say, really.",
NULL);
}
static void
quit_app (GtkApplication *app)
{
GList *list, *next;
GtkWindow *win;
g_print ("Going down...\n");
list = gtk_application_get_windows (app);
while (list)
{
win = list->data;
next = list->next;
gtk_widget_destroy (GTK_WIDGET (win));
list = next;
}
}
static void
quit_activated (GSimpleAction *action,
GVariant *parameter,
gpointer user_data)
{
GtkApplication *app = user_data;
quit_app (app);
}
static GActionEntry app_entries[] = {
{ "new", new_activated, NULL, NULL, NULL },
{ "about", about_activated, NULL, NULL, NULL },
{ "quit", quit_activated, NULL, NULL, NULL },
};
static void
bloat_pad_startup (GApplication *application)
{
GtkBuilder *builder;
G_APPLICATION_CLASS (bloat_pad_parent_class)
->startup (application);
g_action_map_add_action_entries (G_ACTION_MAP (application), app_entries, G_N_ELEMENTS (app_entries), application);
builder = gtk_builder_new ();
gtk_builder_add_from_string (builder,
"<interface>"
" <menu id='app-menu'>"
" <section>"
" <item>"
" <attribute name='label'>_New Window</attribute>"
" <attribute name='action'>app.new</attribute>"
" <attribute name='accel'>&lt;Primary&gt;n</attribute>"
" </item>"
" </section>"
" <section>"
" <item>"
" <attribute name='label'>_About Bloatpad</attribute>"
" <attribute name='action'>app.about</attribute>"
" </item>"
" </section>"
" <section>"
" <item>"
" <attribute name='label'>_Quit</attribute>"
" <attribute name='action'>app.quit</attribute>"
" <attribute name='accel'>&lt;Primary&gt;q</attribute>"
" </item>"
" </section>"
" </menu>"
" <menu id='menubar'>"
" <submenu>"
" <attribute name='label'>_Edit</attribute>"
" <section>"
" <item>"
" <attribute name='label'>_Copy</attribute>"
" <attribute name='action'>win.copy</attribute>"
" <attribute name='accel'>&lt;Primary&gt;c</attribute>"
" </item>"
" <item>"
" <attribute name='label'>_Parse</attribute>"
" <attribute name='action'>win.parse</attribute>"
" <attribute name='accel'>&lt;Primary&gt;v</attribute>"
" </item>"
" </section>"
" </submenu>"
" <submenu>"
" <attribute name='label'>_View</attribute>"
" <section>"
" <item>"
" <attribute name='label'>_Fullscreen</attribute>"
" <attribute name='action'>win.fullscreen</attribute>"
" <attribute name='accel'>F11</attribute>"
" </item>"
" </section>"
" </submenu>"
" </menu>"
"</interface>", -1, NULL);
gtk_application_set_app_menu (GTK_APPLICATION (application), G_MENU_MODEL (gtk_builder_get_object (builder, "app-menu")));
gtk_application_set_menubar (GTK_APPLICATION (application), G_MENU_MODEL (gtk_builder_get_object (builder, "menubar")));
g_object_unref (builder);
}
static void
bloat_pad_init (BloatPad *app)
{
}
static void
bloat_pad_class_init (BloatPadClass *class)
{
GApplicationClass *application_class = G_APPLICATION_CLASS (class);
GObjectClass *object_class = G_OBJECT_CLASS (class);
application_class->startup = bloat_pad_startup;
application_class->activate = bloat_pad_activate;
application_class->open = bloat_pad_open;
object_class->finalize = bloat_pad_finalize;
}
static void
quit_cb (GtkApplication *app)
{
g_print ("Session manager to us to quit\n");
quit_app (app);
}
BloatPad *
bloat_pad_new (void)
{
GtkApplication *bloat_pad;
g_type_init ();
g_set_application_name ("Bloatpad");
bloat_pad = g_object_new (bloat_pad_get_type (),
"application-id", "org.gtk.Test.bloatpad",
"flags", G_APPLICATION_HANDLES_OPEN,
"inactivity-timeout", 30000,
"register-session", TRUE,
NULL);
g_signal_connect (bloat_pad, "quit", G_CALLBACK (quit_cb), NULL);
return bloat_pad;
}
int
main (int argc, char **argv)
{
BloatPad *bloat_pad;
int status;
bloat_pad = bloat_pad_new ();
gtk_application_add_accelerator (GTK_APPLICATION (bloat_pad),
"F11", "win.fullscreen", NULL);
status = g_application_run (G_APPLICATION (bloat_pad), argc, argv);
g_object_unref (bloat_pad);
return status;
}