[aisleriot/wip/redesign: 7/17] all: Move card theme to prefs dialogue
- From: Christian Persch <chpe src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [aisleriot/wip/redesign: 7/17] all: Move card theme to prefs dialogue
- Date: Wed, 3 Jul 2013 17:53:56 +0000 (UTC)
commit 60bf2fc8a3e35795c0d340c3f59bf7adf86be78d
Author: Christian Persch <chpe gnome org>
Date: Wed Jul 3 11:48:36 2013 +0200
all: Move card theme to prefs dialogue
src/ar-application.c | 23 +++++-
src/ar-application.h | 5 +
src/ar-prefs.c | 110 +++++++++++++++++++++++++
src/window.c | 218 ++++++--------------------------------------------
src/window.h | 1 -
5 files changed, 158 insertions(+), 199 deletions(-)
---
diff --git a/src/ar-application.c b/src/ar-application.c
index 15e8707..e930951 100644
--- a/src/ar-application.c
+++ b/src/ar-application.c
@@ -24,6 +24,7 @@
#include "ar-application.h"
#include "ar-defines.h"
#include "ar-runtime.h"
+#include "ar-card-themes.h"
#include <errno.h>
#include <stdlib.h>
@@ -67,14 +68,11 @@ struct _ArApplicationPrivate
gint seed; /* unused */
gboolean freecell; /* unused */
+ ArCardThemes *card_themes;
GSettingsBackend *state_keyfile_backend;
GSettingsBackend *scores_keyfile_backend;
};
-#if !GTK_CHECK_VERSION (3, 6, 0)
-#define gtk_application_get_active_window(w) NULL
-#endif
-
G_DEFINE_TYPE (ArApplication, ar_application, GTK_TYPE_APPLICATION)
static void
@@ -304,6 +302,7 @@ ar_application_dispose (GObject *object)
g_free (self->priv->variation);
self->priv->variation = NULL;
+ g_clear_object (&priv->card_themes);
g_clear_object (&priv->state_keyfile_backend);
g_clear_object (&priv->scores_keyfile_backend);
@@ -396,3 +395,19 @@ ar_application_options_settings_new (ArApplication *application,
return settings;
}
+
+ArCardThemes *
+ar_application_get_card_themes (ArApplication *application)
+{
+ ArApplicationPrivate *priv;
+
+ g_return_val_if_fail (AR_IS_APPLICATION (application), NULL);
+
+ priv = application->priv;
+
+ if (priv->card_themes == NULL)
+ priv->card_themes = ar_card_themes_new ();
+
+ return priv->card_themes;
+}
+
diff --git a/src/ar-application.h b/src/ar-application.h
index df5f381..f060126 100644
--- a/src/ar-application.h
+++ b/src/ar-application.h
@@ -19,6 +19,7 @@
#define AR_APPLICATION_H
#include <gtk/gtk.h>
+#include "ar-card-themes.h"
G_BEGIN_DECLS
@@ -47,6 +48,10 @@ GSettings *ar_application_scores_settings_new (ArApplication *application,
GSettings *ar_application_options_settings_new (ArApplication *application,
const char *game);
+ArCardThemes *ar_application_get_card_themes (ArApplication *application);
+
+#define AR_APP (AR_APPLICATION (g_application_get_default ()))
+
G_END_DECLS
#endif /* !AR_APPLICATION_H */
diff --git a/src/ar-prefs.c b/src/ar-prefs.c
index f2fdf5a..564c523 100644
--- a/src/ar-prefs.c
+++ b/src/ar-prefs.c
@@ -23,6 +23,7 @@
#include <glib/gi18n.h>
#include "ar-application.h"
+#include "ar-card-themes.h"
#include "ar-debug.h"
#include "ar-defines.h"
#include "util.h"
@@ -33,6 +34,8 @@ typedef struct {
GtkWidget *click_checkbutton;
GtkWidget *sound_checkbutton;
GtkWidget *animations_checkbutton;
+ GtkWidget *theme_combobox;
+ GtkListStore *theme_store;
} ArPrefsPrivate;
struct _ArPrefs
@@ -53,6 +56,11 @@ enum {
PROP_WINDOW
};
+enum {
+ COL_DISPLAY_NAME,
+ COL_THEME_INFO
+};
+
/* private functions */
static void
@@ -68,6 +76,72 @@ response_cb (GtkWidget *dialog,
gtk_widget_destroy (dialog);
}
+static void
+theme_combobox_changed_cb (GtkComboBox *combo,
+ ArPrefs *prefs);
+
+static void
+theme_changed_cb (GSettings *settings,
+ const char *key,
+ ArPrefs *prefs)
+{
+ ArPrefsPrivate *priv = prefs->priv;
+ GtkTreeModel *model = GTK_TREE_MODEL (priv->theme_store);
+ GtkTreeIter iter;
+ gboolean found = FALSE;
+ ArCardThemeInfo *info;
+ const char *theme;
+
+ g_settings_get (settings, key, "&s", &theme);
+
+ if (!gtk_tree_model_get_iter_first (model, &iter))
+ goto done;
+
+ do {
+ gtk_tree_model_get (model, &iter, COL_THEME_INFO, &info, -1);
+
+ found = g_str_equal (ar_card_theme_info_get_persistent_name (info), theme);
+
+ ar_card_theme_info_unref (info);
+ if (found)
+ break;
+ } while (gtk_tree_model_iter_next (model, &iter));
+
+ done:
+
+ g_signal_handlers_block_by_func (priv->theme_combobox, G_CALLBACK (theme_combobox_changed_cb), prefs);
+
+ if (found)
+ gtk_combo_box_set_active_iter (GTK_COMBO_BOX (priv->theme_combobox), &iter);
+ else
+ gtk_combo_box_set_active_iter (GTK_COMBO_BOX (priv->theme_combobox), NULL);
+
+ g_signal_handlers_unblock_by_func (priv->theme_combobox, G_CALLBACK (theme_combobox_changed_cb), prefs);
+}
+
+static void
+theme_combobox_changed_cb (GtkComboBox *combo,
+ ArPrefs *prefs)
+{
+ ArPrefsPrivate *priv = prefs->priv;
+ GtkTreeIter iter;
+ ArCardThemeInfo *info;
+
+ if (!gtk_combo_box_get_active_iter (combo, &iter))
+ return;
+
+ gtk_tree_model_get (GTK_TREE_MODEL (priv->theme_store), &iter,
+ COL_THEME_INFO, &info,
+ -1);
+
+ g_signal_handlers_block_by_func (priv->settings, G_CALLBACK (theme_changed_cb), prefs);
+ g_settings_set_string (priv->settings, AR_SETTINGS_CARD_THEME_KEY,
+ ar_card_theme_info_get_persistent_name (info));
+ g_signal_handlers_unblock_by_func (priv->settings, G_CALLBACK (theme_changed_cb), prefs);
+
+ ar_card_theme_info_unref (info);
+}
+
/* GType impl */
G_DEFINE_TYPE (ArPrefs, ar_prefs, GTK_TYPE_DIALOG)
@@ -77,7 +151,11 @@ G_DEFINE_TYPE (ArPrefs, ar_prefs, GTK_TYPE_DIALOG)
static void
ar_prefs_init (ArPrefs *prefs)
{
+ ArApplication *application = AR_APP;
ArPrefsPrivate *priv;
+ GList *list, *l;
+ GtkListStore *store;
+ ArCardThemes *card_themes;
priv = prefs->priv = G_TYPE_INSTANCE_GET_PRIVATE (prefs, AR_TYPE_PREFS, ArPrefsPrivate);
@@ -85,6 +163,29 @@ ar_prefs_init (ArPrefs *prefs)
gtk_widget_init_template (GTK_WIDGET (prefs));
+ /* Populate the card theme combo */
+ store = priv->theme_store = gtk_list_store_new (2, G_TYPE_STRING, AR_TYPE_CARD_THEME_INFO);
+
+ card_themes = ar_application_get_card_themes (application);
+ ar_card_themes_request_themes (card_themes);
+ list = ar_card_themes_get_themes (card_themes);
+ for (l = list; l != NULL; l = l->next) {
+ ArCardThemeInfo *info = (ArCardThemeInfo *) l->data;
+ GtkTreeIter iter;
+
+ gtk_list_store_insert_with_values (store, &iter, -1,
+ COL_DISPLAY_NAME,
+ ar_card_theme_info_get_display_name (info),
+ COL_THEME_INFO,
+ info,
+ -1);
+ }
+ g_list_free_full (list, (GDestroyNotify) ar_card_theme_info_unref);
+
+ gtk_combo_box_set_model (GTK_COMBO_BOX (priv->theme_combobox), GTK_TREE_MODEL (store));
+ g_object_unref (store);
+
+ /* Bind settings */
g_settings_bind (priv->settings, AR_SETTINGS_CLICK_TO_MOVE_KEY,
priv->click_checkbutton, "active",
G_SETTINGS_BIND_DEFAULT);
@@ -99,6 +200,12 @@ ar_prefs_init (ArPrefs *prefs)
gtk_widget_hide (priv->animations_checkbutton);
#endif
+ theme_changed_cb (priv->settings, AR_SETTINGS_CARD_THEME_KEY, prefs);
+ g_signal_connect (priv->settings, "changed::" AR_SETTINGS_CARD_THEME_KEY,
+ G_CALLBACK (theme_changed_cb), prefs);
+ g_signal_connect (priv->theme_combobox, "changed",
+ G_CALLBACK (theme_combobox_changed_cb), prefs);
+
g_signal_connect (prefs, "response", G_CALLBACK (response_cb), NULL);
}
@@ -108,6 +215,8 @@ ar_prefs_finalize (GObject *object)
ArPrefs *prefs = AR_PREFS (object);
ArPrefsPrivate *priv = prefs->priv;
+ g_signal_handlers_disconnect_by_func (priv->settings, G_CALLBACK (theme_changed_cb), prefs);
+
g_clear_object (&priv->settings);
G_OBJECT_CLASS (ar_prefs_parent_class)->finalize (object);
@@ -161,6 +270,7 @@ ar_prefs_class_init (ArPrefsClass *klass)
gtk_widget_class_bind_child (widget_class, ArPrefsPrivate, click_checkbutton);
gtk_widget_class_bind_child (widget_class, ArPrefsPrivate, sound_checkbutton);
gtk_widget_class_bind_child (widget_class, ArPrefsPrivate, animations_checkbutton);
+ gtk_widget_class_bind_child (widget_class, ArPrefsPrivate, theme_combobox);
}
/* public API */
diff --git a/src/window.c b/src/window.c
index fdbdb3d..e7fd4a2 100644
--- a/src/window.c
+++ b/src/window.c
@@ -1378,170 +1378,30 @@ aisleriot_window_take_card_theme (AisleriotWindow *window,
ar_style_set_card_theme (priv->board_style, theme);
}
-#if 0
static void
-card_theme_changed_cb (GtkToggleAction *action,
+card_theme_changed_cb (GSettings *settings,
+ const char *key,
AisleriotWindow *window)
{
AisleriotWindowPrivate *priv = window->priv;
- ArCardThemeInfo *current_theme_info = NULL, *new_theme_info;
- ArCardTheme *theme;
const char *theme_name;
+ ArCardTheme *theme;
- if (!gtk_toggle_action_get_active (action))
- return;
-
- new_theme_info = g_object_get_data (G_OBJECT (action), "theme-info");
- g_assert (new_theme_info != NULL);
-
- if (priv->theme) {
- current_theme_info = ar_card_theme_get_theme_info (priv->theme);
- }
-
- if (ar_card_theme_info_equal (new_theme_info, current_theme_info))
- return;
+ g_settings_get (settings, key, "&s", &theme_name);
- theme = ar_card_themes_get_theme (priv->theme_manager, new_theme_info);
+ theme = ar_card_themes_get_theme_by_name (priv->theme_manager, theme_name);
if (!theme) {
- GSList *group, *l;
-
- gtk_widget_error_bell (GTK_WIDGET (window));
-
- /* Set this action insensitive so we don't try again */
- gtk_action_set_sensitive (GTK_ACTION (action), FALSE);
-
- /* Re-set the radio action of the current theme to active */
- group = gtk_radio_action_get_group (GTK_RADIO_ACTION (action));
- for (l = group; l != NULL; l = l->next) {
- GtkToggleAction *theme_action = GTK_TOGGLE_ACTION (l->data);
- ArCardThemeInfo *info;
-
- if (theme_action == action)
- continue;
-
- info = g_object_get_data (G_OBJECT (theme_action), "theme-info");
- if (!ar_card_theme_info_equal (info, current_theme_info))
- continue;
-
- /* The check at the top will prevent an infinite loop */
- gtk_toggle_action_set_active (theme_action, TRUE);
- break;
- }
-
- return;
- }
-
- aisleriot_window_take_card_theme (window, theme);
-
- theme_name = ar_card_theme_info_get_persistent_name (new_theme_info);
- g_settings_set_string (priv->settings, AR_SETTINGS_CARD_THEME_KEY, theme_name);
-}
-#endif // 0
-
-static void
-install_card_theme_menu (ArCardThemes *theme_manager,
- AisleriotWindow *window)
-{
-#if 0
- AisleriotWindowPrivate *priv = window->priv;
- GList *list, *l;
- GSList *radio_group = NULL;
- ArCardThemeInfo *current_theme_info;
- guint i = 0;
-
- /* Clean out the old menu */
- if (priv->card_themes_merge_id != 0) {
- gtk_ui_manager_remove_ui (priv->ui_manager, priv->card_themes_merge_id);
- priv->card_themes_merge_id = 0;
- }
- if (priv->card_themes_group != NULL) {
- gtk_ui_manager_remove_action_group (priv->ui_manager, priv->card_themes_group);
- priv->card_themes_group = NULL;
- }
-
- /* See gtk bug #424448 */
- gtk_ui_manager_ensure_update (priv->ui_manager);
-
- list = ar_card_themes_get_themes (priv->theme_manager);
-
- /* No need to install the menu when there's only one theme available anyway */
- if (list == NULL || list->next == NULL) {
- g_list_foreach (list, (GFunc) ar_card_theme_info_unref, NULL);
- g_list_free (list);
- return;
+ /* Last-ditch fallback: try getting *any* theme */
+ theme = ar_card_themes_get_theme_any (priv->theme_manager);
}
-
- priv->card_themes_group = gtk_action_group_new ("Theme");
- gtk_ui_manager_insert_action_group (priv->ui_manager, priv->card_themes_group, -1);
- g_object_unref (priv->card_themes_group);
-
- priv->card_themes_merge_id = gtk_ui_manager_new_merge_id (priv->ui_manager);
-
- if (priv->theme) {
- current_theme_info = ar_card_theme_get_theme_info (priv->theme);
+ if (theme) {
+ aisleriot_window_take_card_theme (window, theme /* adopts */);
} else {
- current_theme_info = NULL;
- }
-
- for (l = list; l != NULL; l = l->next) {
- ArCardThemeInfo *info = (ArCardThemeInfo *) l->data;
- GtkRadioAction *action;
- char actionname[32];
- char *display_name, *tooltip;
-
- display_name = g_strdup (ar_card_theme_info_get_display_name (info));
-
- g_snprintf (actionname, sizeof (actionname), "Theme%d", i);
- tooltip = g_strdup_printf (_("Display cards with ā%sā card theme"), display_name);
- action = gtk_radio_action_new (actionname, display_name, tooltip, NULL, i);
- g_free (display_name);
- g_free (tooltip);
-
- gtk_radio_action_set_group (action, radio_group);
- radio_group = gtk_radio_action_get_group (action);
-
- /* Check if this is the current theme's action. Do this before connecting the callback */
- if (ar_card_theme_info_equal (info, current_theme_info)) {
- gtk_toggle_action_set_active (GTK_TOGGLE_ACTION (action), TRUE);
- }
-
- /* We steal the data from the list */
- g_object_set_data_full (G_OBJECT (action), "theme-info",
- l->data, (GDestroyNotify) ar_card_theme_info_unref);
- l->data = NULL;
-
- g_signal_connect (action, "toggled",
- G_CALLBACK (card_theme_changed_cb), window);
- gtk_action_group_add_action (priv->card_themes_group, GTK_ACTION (action));
- g_object_unref (action);
-
- gtk_ui_manager_add_ui (priv->ui_manager,
- priv->card_themes_merge_id,
- CARD_THEMES_MENU_PATH,
- actionname, actionname,
- GTK_UI_MANAGER_MENUITEM, FALSE);
-
- ++i;
+ /* FIXMEchpe: FUCK, what now? Panic! */
+ /* Put up some UI, and exit! */
+ g_assert_not_reached ();
}
-
- /* The list elements' data's refcount has been adopted above */
- g_list_free (list);
-#endif // 0
-}
-
-#if 0 //fixme
-static void
-view_menu_activate_cb (GtkAction *action,
- AisleriotWindow *window)
-{
- AisleriotWindowPrivate *priv = window->priv;
-
- /* Request the list of themes. If it wasn't updated yet, the "changed"
- * callback will build the card themes submenu.
- */
- ar_card_themes_request_themes (priv->theme_manager);
}
-#endif
/* Callbacks */
@@ -1967,26 +1827,24 @@ aisleriot_window_init (AisleriotWindow *window)
AisleriotWindowPrivate *priv;
GtkWidget *main_vbox;
GAction *action;
- const char *theme_name;
- ArCardTheme *theme;
GtkStatusbar *statusbar;
GtkWidget *statusbar_hbox, *label, *time_box;
#ifdef HAVE_CLUTTER
ClutterContainer *stage;
#endif
+ ArApplication *app = AR_APP;
priv = window->priv = AISLERIOT_WINDOW_GET_PRIVATE (window);
priv->settings = g_settings_new (AR_SETTINGS_SCHEMA);
- priv->state_settings = ar_application_state_settings_new (AR_APPLICATION (g_application_get_default ()),
- AR_STATE_SCHEMA);
+ priv->state_settings = ar_application_state_settings_new (app, AR_STATE_SCHEMA);
priv->fullscreen = FALSE;
priv->game = aisleriot_game_new ();
- priv->theme_manager = ar_card_themes_new ();
+ priv->theme_manager = ar_application_get_card_themes (app);
priv->board_style = ar_style_new ();
@@ -2019,20 +1877,6 @@ aisleriot_window_init (AisleriotWindow *window)
priv->board = AISLERIOT_BOARD (aisleriot_board_new (priv->board_style, priv->game));
#endif /* HAVE_CLUTTER */
- g_settings_get (priv->settings, AR_SETTINGS_CARD_THEME_KEY, "&s", &theme_name);
- theme = ar_card_themes_get_theme_by_name (priv->theme_manager, theme_name);
- if (!theme) {
- /* Last-ditch fallback: try getting *any* theme */
- theme = ar_card_themes_get_theme_any (priv->theme_manager);
- }
- if (theme) {
- aisleriot_window_take_card_theme (window, theme /* adopts */);
- } else {
- /* FIXMEchpe: FUCK, what now? Panic! */
- /* Put up some UI, and exit! */
- g_assert_not_reached ();
- }
-
/* GAction setup */
g_action_map_add_action_entries (G_ACTION_MAP (window),
gaction_entries, G_N_ELEMENTS (gaction_entries),
@@ -2102,24 +1946,6 @@ aisleriot_window_init (AisleriotWindow *window)
GTK_STYLE_CLASS_PRIMARY_TOOLBAR);
#endif
-#if 0 // fixme
- /* Defer building the card themes menu until its parent's menu is opened */
- action = gtk_action_group_get_action (priv->action_group, "ViewMenu");
- g_signal_connect (action, "activate",
- G_CALLBACK (view_menu_activate_cb), window);
-#endif
-
- /* It's possible that the themes list has already been loaded (e.g.
- * if the theme loading above involved the fallback); in that case
- * we need to update the menu right now.
- */
- if (ar_card_themes_get_themes_loaded (priv->theme_manager))
- install_card_theme_menu (priv->theme_manager, window);
-
- /* Rebuild the themes menu when the themes list changes */
- g_signal_connect (priv->theme_manager, "changed",
- G_CALLBACK (install_card_theme_menu), window);
-
/* The actions and menus are done. The
* recent games menu will be updated when the initial game loads.
*/
@@ -2195,6 +2021,10 @@ aisleriot_window_init (AisleriotWindow *window)
G_CALLBACK (enable_animations_changed_cb), window);
#endif
+ card_theme_changed_cb (priv->settings, AR_SETTINGS_CARD_THEME_KEY, window);
+ g_signal_connect (priv->settings, "changed::" AR_SETTINGS_CARD_THEME_KEY,
+ G_CALLBACK (card_theme_changed_cb), window);
+
/* Restore window state */
ar_gsettings_bind_window_state (AR_SETTINGS_WINDOW_STATE_PATH, GTK_WINDOW (window));
@@ -2247,7 +2077,6 @@ aisleriot_window_dispose (GObject *object)
priv->load_idle_id = 0;
}
- g_clear_object (&priv->settings);
g_clear_object (&priv->state_settings);
g_clear_object (&priv->game_options_settings);
@@ -2264,11 +2093,12 @@ aisleriot_window_finalize (GObject *object)
g_object_unref (priv->board_style);
#endif /* HAVE_CLUTTER */
- if (priv->theme) {
- g_object_unref (priv->theme);
- }
+ g_clear_object (&priv->theme);
- g_object_unref (priv->theme_manager);
+ g_signal_handlers_disconnect_matched (priv->settings,
+ G_SIGNAL_MATCH_DATA,
+ 0, 0, NULL, NULL, window);
+ g_clear_object (&priv->settings);
g_signal_handlers_disconnect_matched (priv->game,
G_SIGNAL_MATCH_DATA,
diff --git a/src/window.h b/src/window.h
index 0327f87..4b8c791 100644
--- a/src/window.h
+++ b/src/window.h
@@ -61,7 +61,6 @@ void aisleriot_window_change_game (AisleriotWindow * window);
void aisleriot_window_show_statistics_dialog (AisleriotWindow * window);
void aisleriot_window_show_about_dialog (AisleriotWindow * window);
-
G_END_DECLS
#endif /* !AISLERIOT_WINDOW_H */
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]