diff --git a/gtk/gtkcolorchooserwidget.c b/gtk/gtkcolorchooserwidget.c index b2cfdac794..4172eb296b 100644 --- a/gtk/gtkcolorchooserwidget.c +++ b/gtk/gtkcolorchooserwidget.c @@ -90,6 +90,8 @@ struct _GtkColorChooserWidgetPrivate gboolean has_default_palette; GSettings *settings; + + GActionMap *context_actions; }; enum @@ -134,31 +136,6 @@ select_swatch (GtkColorChooserWidget *cc, g_object_notify (G_OBJECT (cc), "rgba"); } -static void -swatch_activate (GtkColorSwatch *swatch, - GtkColorChooserWidget *cc) -{ - GdkRGBA color; - - gtk_color_swatch_get_rgba (swatch, &color); - _gtk_color_chooser_color_activated (GTK_COLOR_CHOOSER (cc), &color); -} - -static void -swatch_customize (GtkColorSwatch *swatch, - GtkColorChooserWidget *cc) -{ - GtkColorChooserWidgetPrivate *priv = gtk_color_chooser_widget_get_instance_private (cc); - GdkRGBA color; - - gtk_color_swatch_get_rgba (swatch, &color); - gtk_color_chooser_set_rgba (GTK_COLOR_CHOOSER (priv->editor), &color); - - gtk_widget_hide (priv->palette); - gtk_widget_show (priv->editor); - g_object_notify (G_OBJECT (cc), "show-editor"); -} - static void swatch_selected (GtkColorSwatch *swatch, GtkStateFlags previous, @@ -176,31 +153,14 @@ static void connect_swatch_signals (GtkWidget *p, gpointer data) { - g_signal_connect (p, "activate", G_CALLBACK (swatch_activate), data); - g_signal_connect (p, "customize", G_CALLBACK (swatch_customize), data); g_signal_connect (p, "state-flags-changed", G_CALLBACK (swatch_selected), data); } -static void -button_activate (GtkColorSwatch *swatch, - GtkColorChooserWidget *cc) -{ - GtkColorChooserWidgetPrivate *priv = gtk_color_chooser_widget_get_instance_private (cc); - /* somewhat random, makes the hairline nicely visible */ - GdkRGBA color = { 0.75, 0.25, 0.25, 1.0 }; - - gtk_color_chooser_set_rgba (GTK_COLOR_CHOOSER (priv->editor), &color); - - gtk_widget_hide (priv->palette); - gtk_widget_show (priv->editor); - g_object_notify (G_OBJECT (cc), "show-editor"); -} - static void connect_button_signals (GtkWidget *p, gpointer data) { - g_signal_connect (p, "activate", G_CALLBACK (button_activate), data); +// g_signal_connect (p, "activate", G_CALLBACK (button_activate), data); } static void @@ -532,6 +492,57 @@ add_default_palette (GtkColorChooserWidget *cc) priv->has_default_palette = TRUE; } +static void +customize_color (GSimpleAction *action, + GVariant *parameter, + gpointer user_data) +{ + GtkColorChooserWidget *cc = user_data; + GtkColorChooserWidgetPrivate *priv = gtk_color_chooser_widget_get_instance_private (cc); + GdkRGBA color; + + g_variant_get (parameter, "(dddd)", &color.red, &color.green, &color.blue, &color.alpha); + + gtk_color_chooser_set_rgba (GTK_COLOR_CHOOSER (priv->editor), &color); + + gtk_widget_hide (priv->palette); + gtk_widget_show (priv->editor); + g_object_notify (G_OBJECT (cc), "show-editor"); +} + +static void +select_color (GSimpleAction *action, + GVariant *parameter, + gpointer user_data) +{ + GtkColorChooserWidget *cc = user_data; + GdkRGBA color; + + g_variant_get (parameter, "(dddd)", &color.red, &color.green, &color.blue, &color.alpha); + + _gtk_color_chooser_color_activated (GTK_COLOR_CHOOSER (cc), &color); +} + +static void +gtk_color_chooser_widget_add_context_actions (GtkColorChooserWidget *cc) +{ + GtkColorChooserWidgetPrivate *priv = gtk_color_chooser_widget_get_instance_private (cc); + + GActionEntry entries[] = { + { "select", select_color, "(dddd)", NULL, NULL }, + { "customize", customize_color, "(dddd)", NULL, NULL }, + }; + + GSimpleActionGroup *actions = g_simple_action_group_new (); + + priv->context_actions = G_ACTION_MAP (actions); + + g_action_map_add_action_entries (G_ACTION_MAP (actions), entries, G_N_ELEMENTS (entries), cc); + + gtk_widget_insert_action_group (GTK_WIDGET (cc), "color", G_ACTION_GROUP (actions)); +} + + static void gtk_color_chooser_widget_init (GtkColorChooserWidget *cc) { @@ -623,6 +634,8 @@ gtk_color_chooser_widget_init (GtkColorChooserWidget *cc) priv->size_group = gtk_size_group_new (GTK_SIZE_GROUP_HORIZONTAL); gtk_size_group_add_widget (priv->size_group, priv->palette); gtk_size_group_add_widget (priv->size_group, box); + + gtk_color_chooser_widget_add_context_actions (cc); } /* GObject implementation {{{1 */ diff --git a/gtk/gtkcolorswatch.c b/gtk/gtkcolorswatch.c index a5d3f52499..6932fa2413 100644 --- a/gtk/gtkcolorswatch.c +++ b/gtk/gtkcolorswatch.c @@ -33,7 +33,7 @@ #include "gtkintl.h" #include "gtkmain.h" #include "gtkmodelbutton.h" -#include "gtkpopover.h" +#include "gtkpopovermenu.h" #include "gtkprivate.h" #include "gtksnapshot.h" #include "gtkstylecontextprivate.h" @@ -76,16 +76,6 @@ enum PROP_HAS_MENU }; -enum -{ - ACTIVATE, - CUSTOMIZE, - LAST_SIGNAL -}; - -static guint signals[LAST_SIGNAL]; - - G_DEFINE_TYPE_WITH_PRIVATE (GtkColorSwatch, gtk_color_swatch, GTK_TYPE_WIDGET) #define INTENSITY(r, g, b) ((r) * 0.30 + (g) * 0.59 + (b) * 0.11) @@ -231,6 +221,32 @@ swatch_drag_data_received (GtkWidget *widget, gtk_color_swatch_set_rgba (GTK_COLOR_SWATCH (widget), &color); } +static void +activate_color (GtkColorSwatch *swatch) +{ + GtkColorSwatchPrivate *priv = gtk_color_swatch_get_instance_private (swatch); + gtk_widget_activate_action (GTK_WIDGET (swatch), + "color.select", + g_variant_new ("(dddd)", + priv->color.red, + priv->color.green, + priv->color.blue, + priv->color.alpha)); +} + +static void +customize_color (GtkColorSwatch *swatch) +{ + GtkColorSwatchPrivate *priv = gtk_color_swatch_get_instance_private (swatch); + gtk_widget_activate_action (GTK_WIDGET (swatch), + "color.customize", + g_variant_new ("(dddd)", + priv->color.red, + priv->color.green, + priv->color.blue, + priv->color.alpha)); +} + static gboolean key_controller_key_pressed (GtkEventControllerKey *controller, guint keyval, @@ -252,40 +268,51 @@ key_controller_key_pressed (GtkEventControllerKey *controller, (gtk_widget_get_state_flags (widget) & GTK_STATE_FLAG_SELECTED) == 0) gtk_widget_set_state_flags (widget, GTK_STATE_FLAG_SELECTED, FALSE); else - g_signal_emit (swatch, signals[ACTIVATE], 0); + customize_color (swatch); + return TRUE; } return FALSE; } -static void -emit_customize (GtkColorSwatch *swatch) +static GMenuModel * +gtk_color_swatch_get_menu_model (GtkColorSwatch *swatch) { - g_signal_emit (swatch, signals[CUSTOMIZE], 0); + GtkColorSwatchPrivate *priv = gtk_color_swatch_get_instance_private (swatch); + GMenu *menu, *section; + GMenuItem *item; + + menu = g_menu_new (); + + section = g_menu_new (); + item = g_menu_item_new (_("Customize"), NULL); + g_menu_item_set_action_and_target_value (item, "color.customize", + g_variant_new ("(dddd)", + priv->color.red, + priv->color.green, + priv->color.blue, + priv->color.alpha)); + + g_menu_append_item (section, item); + g_menu_append_section (menu, NULL, G_MENU_MODEL (section)); + g_object_unref (item); + g_object_unref (section); + + return G_MENU_MODEL (menu); } static void do_popup (GtkColorSwatch *swatch) { GtkColorSwatchPrivate *priv = gtk_color_swatch_get_instance_private (swatch); + GMenuModel *model; - if (priv->popover == NULL) - { - GtkWidget *box; - GtkWidget *item; + g_clear_pointer (&priv->popover, gtk_widget_unparent); - priv->popover = gtk_popover_new (GTK_WIDGET (swatch)); - box = gtk_box_new (GTK_ORIENTATION_VERTICAL, 0); - gtk_container_add (GTK_CONTAINER (priv->popover), box); - g_object_set (box, "margin", 10, NULL); - item = g_object_new (GTK_TYPE_MODEL_BUTTON, - "text", _("C_ustomize"), - NULL); - g_signal_connect_swapped (item, "clicked", - G_CALLBACK (emit_customize), swatch); - gtk_container_add (GTK_CONTAINER (box), item); - } + model = gtk_color_swatch_get_menu_model (swatch); + priv->popover = gtk_popover_menu_new_from_model (GTK_WIDGET (swatch), model); + g_object_unref (model); gtk_popover_popup (GTK_POPOVER (priv->popover)); } @@ -300,7 +327,7 @@ swatch_primary_action (GtkColorSwatch *swatch) flags = gtk_widget_get_state_flags (widget); if (!priv->has_color) { - g_signal_emit (swatch, signals[ACTIVATE], 0); + customize_color (swatch); return TRUE; } else if (priv->selectable && @@ -340,7 +367,7 @@ tap_action (GtkGestureClick *gesture, if (n_press == 1) swatch_primary_action (swatch); else if (n_press > 1) - g_signal_emit (swatch, signals[ACTIVATE], 0); + activate_color (swatch); } else if (button == GDK_BUTTON_SECONDARY) { @@ -505,7 +532,7 @@ swatch_dispose (GObject *object) GtkColorSwatch *swatch = GTK_COLOR_SWATCH (object); GtkColorSwatchPrivate *priv = gtk_color_swatch_get_instance_private (swatch); - g_clear_pointer (&priv->popover, gtk_widget_destroy); + g_clear_pointer (&priv->popover, gtk_widget_unparent); G_OBJECT_CLASS (gtk_color_swatch_parent_class)->dispose (object); } @@ -530,20 +557,6 @@ gtk_color_swatch_class_init (GtkColorSwatchClass *class) widget_class->size_allocate = swatch_size_allocate; widget_class->state_flags_changed = swatch_state_flags_changed; - signals[ACTIVATE] = - g_signal_new (I_("activate"), - GTK_TYPE_COLOR_SWATCH, - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (GtkColorSwatchClass, activate), - NULL, NULL, NULL, G_TYPE_NONE, 0); - - signals[CUSTOMIZE] = - g_signal_new (I_("customize"), - GTK_TYPE_COLOR_SWATCH, - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (GtkColorSwatchClass, customize), - NULL, NULL, NULL, G_TYPE_NONE, 0); - g_object_class_install_property (object_class, PROP_RGBA, g_param_spec_boxed ("rgba", P_("RGBA Color"), P_("Color as RGBA"), GDK_TYPE_RGBA, GTK_PARAM_READWRITE)); @@ -569,6 +582,10 @@ gtk_color_swatch_init (GtkColorSwatch *swatch) priv->use_alpha = TRUE; priv->selectable = TRUE; priv->has_menu = TRUE; + priv->color.red = 0.75; + priv->color.green = 0.25; + priv->color.blue = 0.25; + priv->color.alpha = 1.0; gtk_widget_set_can_focus (GTK_WIDGET (swatch), TRUE); gtk_widget_set_overflow (GTK_WIDGET (swatch), GTK_OVERFLOW_HIDDEN);