mirror of
https://gitlab.gnome.org/GNOME/gtk.git
synced 2025-01-02 17:00:19 +00:00
Merge branch 'widget-class-actions-2' into 'master'
Widget class action See merge request GNOME/gtk!948
This commit is contained in:
commit
cdee8270e2
@ -258,9 +258,11 @@
|
||||
</para>
|
||||
|
||||
<para>
|
||||
Actions are added to their relevant scope (application or
|
||||
window) either using the GActionMap interface, or by using
|
||||
gtk_widget_insert_action_group().
|
||||
Actions are added to their relevant scope (application,
|
||||
window or widget) either using the GActionMap interface,
|
||||
or by using gtk_widget_insert_action_group(). Actions that
|
||||
will be the same for all instances of a widget class can
|
||||
be added globally using gtk_widget_class_install_action().
|
||||
</para>
|
||||
|
||||
</refsect2>
|
||||
@ -317,8 +319,8 @@
|
||||
</para>
|
||||
|
||||
<para>
|
||||
Another of obtaining widgets that are connected to actions is
|
||||
to create a menu using a GMenu menu model. GMenu provides an
|
||||
Another way of obtaining widgets that are connected to actions
|
||||
is to create a menu using a GMenu menu model. GMenu provides an
|
||||
abstract way to describe typical menus: nested groups of items
|
||||
where each item can have a label, and icon, and an action.
|
||||
</para>
|
||||
@ -364,6 +366,25 @@
|
||||
(typically a GtkWindow, GtkDialog or GtkPopover)
|
||||
</para></listitem>
|
||||
</varlistentry>
|
||||
<varlistentry>
|
||||
<term>clipboard.cut, clipboard.copy, clipboard.paste</term>
|
||||
<listitem><para>Clipboard operations on entries, text view
|
||||
and labels, typically used in the context menu
|
||||
</para></listitem>
|
||||
</varlistentry>
|
||||
<varlistentry>
|
||||
<term>selection.delete, selection.select-all</term>
|
||||
<listitem><para>Selection operations on entries, text view
|
||||
and labels
|
||||
</para></listitem>
|
||||
</varlistentry>
|
||||
<varlistentry>
|
||||
<term>color.select, color.customize</term>
|
||||
<listitem><para>Operations on colors in GtkColorChooserWidget.
|
||||
These actions are unusual in that they have the non-trivial
|
||||
parameter type (dddd).
|
||||
</para></listitem>
|
||||
</varlistentry>
|
||||
</variablelist>
|
||||
</para>
|
||||
|
||||
|
@ -4549,10 +4549,6 @@ gtk_widget_get_opacity
|
||||
gtk_widget_set_opacity
|
||||
gtk_widget_get_overflow
|
||||
gtk_widget_set_overflow
|
||||
gtk_widget_insert_action_group
|
||||
gtk_widget_list_action_prefixes
|
||||
gtk_widget_activate_action
|
||||
gtk_widget_activate_default
|
||||
gtk_widget_measure
|
||||
gtk_widget_snapshot_child
|
||||
gtk_widget_get_next_sibling
|
||||
@ -4629,6 +4625,18 @@ gtk_widget_class_set_connect_func
|
||||
gtk_widget_observe_children
|
||||
gtk_widget_observe_controllers
|
||||
|
||||
<SUBSECTION Actions>
|
||||
gtk_widget_insert_action_group
|
||||
gtk_widget_activate_action
|
||||
gtk_widget_activate_default
|
||||
GtkWidgetActionActivateFunc
|
||||
GtkWidgetActionSetStateFunc
|
||||
GtkWidgetActionGetStateFunc
|
||||
gtk_widget_class_install_action
|
||||
gtk_widget_class_install_stateful_action
|
||||
gtk_widget_action_enabled_changed
|
||||
gtk_widget_action_state_changed
|
||||
|
||||
<SUBSECTION Standard>
|
||||
GTK_WIDGET
|
||||
GTK_IS_WIDGET
|
||||
|
@ -25,6 +25,7 @@
|
||||
#include "gtkactionobserverprivate.h"
|
||||
#include "gtkintl.h"
|
||||
#include "gtkmarshalers.h"
|
||||
#include "gtkwidget.h"
|
||||
|
||||
#include <string.h>
|
||||
|
||||
@ -69,6 +70,10 @@ struct _GtkActionMuxer
|
||||
GHashTable *groups;
|
||||
GHashTable *primary_accels;
|
||||
GtkActionMuxer *parent;
|
||||
|
||||
GtkWidget *widget;
|
||||
GPtrArray *widget_actions;
|
||||
gboolean *widget_actions_enabled;
|
||||
};
|
||||
|
||||
G_DEFINE_TYPE_WITH_CODE (GtkActionMuxer, gtk_action_muxer, G_TYPE_OBJECT,
|
||||
@ -79,6 +84,8 @@ enum
|
||||
{
|
||||
PROP_0,
|
||||
PROP_PARENT,
|
||||
PROP_WIDGET,
|
||||
PROP_WIDGET_ACTIONS,
|
||||
NUM_PROPERTIES
|
||||
};
|
||||
|
||||
@ -104,7 +111,7 @@ typedef struct
|
||||
static void
|
||||
gtk_action_muxer_append_group_actions (const char *prefix,
|
||||
Group *group,
|
||||
GArray *actions)
|
||||
GHashTable *actions)
|
||||
{
|
||||
gchar **group_actions;
|
||||
gchar **action;
|
||||
@ -112,10 +119,8 @@ gtk_action_muxer_append_group_actions (const char *prefix,
|
||||
group_actions = g_action_group_list_actions (group->group);
|
||||
for (action = group_actions; *action; action++)
|
||||
{
|
||||
gchar *fullname;
|
||||
|
||||
fullname = g_strconcat (prefix, ".", *action, NULL);
|
||||
g_array_append_val (actions, fullname);
|
||||
char *name = g_strconcat (prefix, ".", *action, NULL);
|
||||
g_hash_table_add (actions, name);
|
||||
}
|
||||
|
||||
g_strfreev (group_actions);
|
||||
@ -125,9 +130,11 @@ static gchar **
|
||||
gtk_action_muxer_list_actions (GActionGroup *action_group)
|
||||
{
|
||||
GtkActionMuxer *muxer = GTK_ACTION_MUXER (action_group);
|
||||
GArray *actions;
|
||||
GHashTable *actions;
|
||||
char **keys;
|
||||
|
||||
actions = g_array_new (TRUE, FALSE, sizeof (gchar *));
|
||||
actions = g_hash_table_new_full (g_str_hash, g_str_equal,
|
||||
g_free, NULL);
|
||||
|
||||
for ( ; muxer != NULL; muxer = muxer->parent)
|
||||
{
|
||||
@ -135,12 +142,28 @@ gtk_action_muxer_list_actions (GActionGroup *action_group)
|
||||
const char *prefix;
|
||||
Group *group;
|
||||
|
||||
if (muxer->widget_actions)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < muxer->widget_actions->len; i++)
|
||||
{
|
||||
GtkWidgetAction *action = g_ptr_array_index (muxer->widget_actions, i);
|
||||
g_hash_table_add (actions, g_strdup (action->name));
|
||||
}
|
||||
}
|
||||
|
||||
g_hash_table_iter_init (&iter, muxer->groups);
|
||||
while (g_hash_table_iter_next (&iter, (gpointer *)&prefix, (gpointer *)&group))
|
||||
gtk_action_muxer_append_group_actions (prefix, group, actions);
|
||||
}
|
||||
|
||||
return (gchar **)(void *) g_array_free (actions, FALSE);
|
||||
keys = (char **)g_hash_table_get_keys_as_array (actions, NULL);
|
||||
|
||||
g_hash_table_steal_all (actions);
|
||||
g_hash_table_unref (actions);
|
||||
|
||||
return (char **)keys;
|
||||
}
|
||||
|
||||
static Group *
|
||||
@ -179,7 +202,7 @@ gtk_action_muxer_find (GtkActionMuxer *muxer,
|
||||
return group->group;
|
||||
}
|
||||
|
||||
static void
|
||||
void
|
||||
gtk_action_muxer_action_enabled_changed (GtkActionMuxer *muxer,
|
||||
const gchar *action_name,
|
||||
gboolean enabled)
|
||||
@ -187,6 +210,19 @@ gtk_action_muxer_action_enabled_changed (GtkActionMuxer *muxer,
|
||||
Action *action;
|
||||
GSList *node;
|
||||
|
||||
if (muxer->widget_actions)
|
||||
{
|
||||
int i;
|
||||
for (i = 0; i < muxer->widget_actions->len; i++)
|
||||
{
|
||||
GtkWidgetAction *a = g_ptr_array_index (muxer->widget_actions, i);
|
||||
if (strcmp (a->name, action_name) == 0)
|
||||
{
|
||||
muxer->widget_actions_enabled[i] = enabled;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
action = g_hash_table_lookup (muxer->observed_actions, action_name);
|
||||
for (node = action ? action->watchers : NULL; node; node = node->next)
|
||||
gtk_action_observer_action_enabled_changed (node->data, GTK_ACTION_OBSERVABLE (muxer), action_name, enabled);
|
||||
@ -219,7 +255,7 @@ gtk_action_muxer_parent_action_enabled_changed (GActionGroup *action_group,
|
||||
gtk_action_muxer_action_enabled_changed (muxer, action_name, enabled);
|
||||
}
|
||||
|
||||
static void
|
||||
void
|
||||
gtk_action_muxer_action_state_changed (GtkActionMuxer *muxer,
|
||||
const gchar *action_name,
|
||||
GVariant *state)
|
||||
@ -397,6 +433,46 @@ gtk_action_muxer_query_action (GActionGroup *action_group,
|
||||
Group *group;
|
||||
const gchar *unprefixed_name;
|
||||
|
||||
if (muxer->widget_actions)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < muxer->widget_actions->len; i++)
|
||||
{
|
||||
GtkWidgetAction *action = g_ptr_array_index (muxer->widget_actions, i);
|
||||
if (strcmp (action->name, action_name) == 0)
|
||||
{
|
||||
if (enabled)
|
||||
*enabled = muxer->widget_actions_enabled[i];
|
||||
if (parameter_type)
|
||||
*parameter_type = action->parameter_type;
|
||||
|
||||
if (state_hint)
|
||||
*state_hint = NULL;
|
||||
if (state_type)
|
||||
*state_type = NULL;
|
||||
if (state)
|
||||
*state = NULL;
|
||||
|
||||
if (action->get_state)
|
||||
{
|
||||
GVariant *s;
|
||||
|
||||
s = g_variant_ref_sink (action->get_state (muxer->widget, action->name));
|
||||
|
||||
if (state_type)
|
||||
*state_type = g_variant_get_type (s);
|
||||
if (state)
|
||||
*state = g_variant_ref (s);
|
||||
|
||||
g_variant_unref (s);
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
group = gtk_action_muxer_find_group (muxer, action_name, &unprefixed_name);
|
||||
|
||||
if (group)
|
||||
@ -420,6 +496,22 @@ gtk_action_muxer_activate_action (GActionGroup *action_group,
|
||||
Group *group;
|
||||
const gchar *unprefixed_name;
|
||||
|
||||
if (muxer->widget_actions)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < muxer->widget_actions->len; i++)
|
||||
{
|
||||
GtkWidgetAction *action = g_ptr_array_index (muxer->widget_actions, i);
|
||||
if (strcmp (action->name, action_name) == 0)
|
||||
{
|
||||
action->activate (muxer->widget, action->name, parameter);
|
||||
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
group = gtk_action_muxer_find_group (muxer, action_name, &unprefixed_name);
|
||||
|
||||
if (group)
|
||||
@ -437,6 +529,23 @@ gtk_action_muxer_change_action_state (GActionGroup *action_group,
|
||||
Group *group;
|
||||
const gchar *unprefixed_name;
|
||||
|
||||
if (muxer->widget_actions)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < muxer->widget_actions->len; i++)
|
||||
{
|
||||
GtkWidgetAction *action = g_ptr_array_index (muxer->widget_actions, i);
|
||||
if (strcmp (action->name, action_name) == 0)
|
||||
{
|
||||
if (action->set_state)
|
||||
action->set_state (muxer->widget, action->name, state);
|
||||
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
group = gtk_action_muxer_find_group (muxer, action_name, &unprefixed_name);
|
||||
|
||||
if (group)
|
||||
@ -592,6 +701,14 @@ gtk_action_muxer_get_property (GObject *object,
|
||||
g_value_set_object (value, gtk_action_muxer_get_parent (muxer));
|
||||
break;
|
||||
|
||||
case PROP_WIDGET:
|
||||
g_value_set_object (value, muxer->widget);
|
||||
break;
|
||||
|
||||
case PROP_WIDGET_ACTIONS:
|
||||
g_value_set_boxed (value, muxer->widget_actions);
|
||||
break;
|
||||
|
||||
default:
|
||||
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
|
||||
}
|
||||
@ -611,6 +728,22 @@ gtk_action_muxer_set_property (GObject *object,
|
||||
gtk_action_muxer_set_parent (muxer, g_value_get_object (value));
|
||||
break;
|
||||
|
||||
case PROP_WIDGET:
|
||||
muxer->widget = g_value_get_object (value);
|
||||
break;
|
||||
|
||||
case PROP_WIDGET_ACTIONS:
|
||||
muxer->widget_actions = g_value_get_boxed (value);
|
||||
if (muxer->widget_actions)
|
||||
{
|
||||
int i;
|
||||
|
||||
muxer->widget_actions_enabled = g_new (gboolean, muxer->widget_actions->len);
|
||||
for (i = 0; i < muxer->widget_actions->len; i++)
|
||||
muxer->widget_actions_enabled[i] = TRUE;
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
|
||||
}
|
||||
@ -664,6 +797,20 @@ gtk_action_muxer_class_init (GObjectClass *class)
|
||||
G_PARAM_READWRITE |
|
||||
G_PARAM_STATIC_STRINGS);
|
||||
|
||||
properties[PROP_WIDGET] = g_param_spec_object ("widget", "Widget",
|
||||
"The widget that owns the muxer",
|
||||
GTK_TYPE_WIDGET,
|
||||
G_PARAM_READWRITE |
|
||||
G_PARAM_CONSTRUCT_ONLY |
|
||||
G_PARAM_STATIC_STRINGS);
|
||||
|
||||
properties[PROP_WIDGET_ACTIONS] = g_param_spec_boxed ("widget-actions", "Widget actions",
|
||||
"Widget actions",
|
||||
G_TYPE_PTR_ARRAY,
|
||||
G_PARAM_READWRITE |
|
||||
G_PARAM_CONSTRUCT_ONLY |
|
||||
G_PARAM_STATIC_STRINGS);
|
||||
|
||||
g_object_class_install_properties (class, NUM_PROPERTIES, properties);
|
||||
}
|
||||
|
||||
@ -771,13 +918,19 @@ gtk_action_muxer_lookup (GtkActionMuxer *muxer,
|
||||
|
||||
/*< private >
|
||||
* gtk_action_muxer_new:
|
||||
* @widget: the widget to which the muxer belongs
|
||||
* @actions: widget actions
|
||||
*
|
||||
* Creates a new #GtkActionMuxer.
|
||||
*/
|
||||
GtkActionMuxer *
|
||||
gtk_action_muxer_new (void)
|
||||
gtk_action_muxer_new (GtkWidget *widget,
|
||||
GPtrArray *actions)
|
||||
{
|
||||
return g_object_new (GTK_TYPE_ACTION_MUXER, NULL);
|
||||
return g_object_new (GTK_TYPE_ACTION_MUXER,
|
||||
"widget", widget,
|
||||
"widget-actions", actions,
|
||||
NULL);
|
||||
}
|
||||
|
||||
/*< private >
|
||||
|
@ -21,6 +21,7 @@
|
||||
#define __GTK_ACTION_MUXER_H__
|
||||
|
||||
#include <gio/gio.h>
|
||||
#include "gtkwidget.h"
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
@ -30,10 +31,21 @@ G_BEGIN_DECLS
|
||||
#define GTK_IS_ACTION_MUXER(inst) (G_TYPE_CHECK_INSTANCE_TYPE ((inst), \
|
||||
GTK_TYPE_ACTION_MUXER))
|
||||
|
||||
typedef struct {
|
||||
char *name;
|
||||
|
||||
GVariantType *parameter_type;
|
||||
|
||||
GtkWidgetActionActivateFunc activate;
|
||||
GtkWidgetActionSetStateFunc set_state;
|
||||
GtkWidgetActionGetStateFunc get_state;
|
||||
} GtkWidgetAction;
|
||||
|
||||
typedef struct _GtkActionMuxer GtkActionMuxer;
|
||||
|
||||
GType gtk_action_muxer_get_type (void);
|
||||
GtkActionMuxer * gtk_action_muxer_new (void);
|
||||
GtkActionMuxer * gtk_action_muxer_new (GtkWidget *widget,
|
||||
GPtrArray *actions);
|
||||
|
||||
void gtk_action_muxer_insert (GtkActionMuxer *muxer,
|
||||
const gchar *prefix,
|
||||
@ -58,6 +70,16 @@ void gtk_action_muxer_set_primary_accel (GtkActi
|
||||
const gchar * gtk_action_muxer_get_primary_accel (GtkActionMuxer *muxer,
|
||||
const gchar *action_and_target);
|
||||
|
||||
void
|
||||
gtk_action_muxer_action_enabled_changed (GtkActionMuxer *muxer,
|
||||
const char *action_name,
|
||||
gboolean enabled);
|
||||
void
|
||||
gtk_action_muxer_action_state_changed (GtkActionMuxer *muxer,
|
||||
const gchar *action_name,
|
||||
GVariant *state);
|
||||
|
||||
|
||||
/* No better place for these... */
|
||||
gchar * gtk_print_action_and_target (const gchar *action_namespace,
|
||||
const gchar *action_name,
|
||||
|
@ -394,7 +394,7 @@ gtk_application_init (GtkApplication *application)
|
||||
{
|
||||
GtkApplicationPrivate *priv = gtk_application_get_instance_private (application);
|
||||
|
||||
priv->muxer = gtk_action_muxer_new ();
|
||||
priv->muxer = gtk_action_muxer_new (NULL, NULL);
|
||||
|
||||
priv->accels = gtk_application_accels_new ();
|
||||
}
|
||||
|
@ -90,8 +90,6 @@ struct _GtkColorChooserWidgetPrivate
|
||||
gboolean has_default_palette;
|
||||
|
||||
GSettings *settings;
|
||||
|
||||
GActionMap *context_actions;
|
||||
};
|
||||
|
||||
enum
|
||||
@ -493,11 +491,11 @@ add_default_palette (GtkColorChooserWidget *cc)
|
||||
}
|
||||
|
||||
static void
|
||||
customize_color (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
gtk_color_chooser_widget_activate_color_customize (GtkWidget *widget,
|
||||
const char *name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
GtkColorChooserWidget *cc = user_data;
|
||||
GtkColorChooserWidget *cc = GTK_COLOR_CHOOSER_WIDGET (widget);
|
||||
GtkColorChooserWidgetPrivate *priv = gtk_color_chooser_widget_get_instance_private (cc);
|
||||
GdkRGBA color;
|
||||
|
||||
@ -511,11 +509,11 @@ customize_color (GSimpleAction *action,
|
||||
}
|
||||
|
||||
static void
|
||||
select_color (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
gtk_color_chooser_widget_activate_color_select (GtkWidget *widget,
|
||||
const char *name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
GtkColorChooserWidget *cc = user_data;
|
||||
GtkColorChooserWidget *cc = GTK_COLOR_CHOOSER_WIDGET (widget);
|
||||
GdkRGBA color;
|
||||
|
||||
g_variant_get (parameter, "(dddd)", &color.red, &color.green, &color.blue, &color.alpha);
|
||||
@ -523,26 +521,6 @@ select_color (GSimpleAction *action,
|
||||
_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)
|
||||
{
|
||||
@ -634,8 +612,6 @@ 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 */
|
||||
@ -736,6 +712,13 @@ gtk_color_chooser_widget_class_init (GtkColorChooserWidgetClass *class)
|
||||
FALSE, GTK_PARAM_READWRITE));
|
||||
|
||||
gtk_widget_class_set_css_name (GTK_WIDGET_CLASS (class), I_("colorchooser"));
|
||||
|
||||
gtk_widget_class_install_stateful_action (GTK_WIDGET_CLASS (class), "color.select",
|
||||
gtk_color_chooser_widget_activate_color_select,
|
||||
"(dddd)", NULL, NULL);
|
||||
gtk_widget_class_install_stateful_action (GTK_WIDGET_CLASS (class), "color.customize",
|
||||
gtk_color_chooser_widget_activate_color_customize,
|
||||
"(dddd)", NULL, NULL);
|
||||
}
|
||||
|
||||
/* GtkColorChooser implementation {{{1 */
|
||||
|
200
gtk/gtklabel.c
200
gtk/gtklabel.c
@ -285,7 +285,6 @@ struct _GtkLabelPrivate
|
||||
PangoAttrList *markup_attrs;
|
||||
PangoLayout *layout;
|
||||
|
||||
GActionMap *context_actions;
|
||||
GtkWidget *popup_menu;
|
||||
GMenuModel *extra_menu;
|
||||
|
||||
@ -575,8 +574,25 @@ static void gtk_label_drag_gesture_update (GtkGestureDrag *gesture,
|
||||
gdouble offset_y,
|
||||
GtkLabel *label);
|
||||
|
||||
static void gtk_label_add_context_actions (GtkLabel *label);
|
||||
static void gtk_label_update_clipboard_actions (GtkLabel *label);
|
||||
/* Actions */
|
||||
|
||||
static void gtk_label_activate_clipboard_copy (GtkWidget *label,
|
||||
const char *name,
|
||||
GVariant *parameter);
|
||||
static void gtk_label_activate_selection_select_all (GtkWidget *label,
|
||||
const char *name,
|
||||
GVariant *parameter);
|
||||
static void gtk_label_activate_link_open (GtkWidget *label,
|
||||
const char *name,
|
||||
GVariant *parameter);
|
||||
static void gtk_label_activate_link_copy (GtkWidget *label,
|
||||
const char *name,
|
||||
GVariant *parameter);
|
||||
static void gtk_label_nop (GtkWidget *label,
|
||||
const char *name,
|
||||
GVariant *parameter);
|
||||
|
||||
static void gtk_label_update_actions (GtkLabel *label);
|
||||
|
||||
static GtkSizeRequestMode gtk_label_get_request_mode (GtkWidget *widget);
|
||||
static void gtk_label_measure (GtkWidget *widget,
|
||||
@ -1143,6 +1159,21 @@ gtk_label_class_init (GtkLabelClass *class)
|
||||
quark_mnemonics_visible_connected = g_quark_from_static_string ("gtk-label-mnemonics-visible-connected");
|
||||
quark_gtk_signal = g_quark_from_static_string ("gtk-signal");
|
||||
quark_link = g_quark_from_static_string ("link");
|
||||
|
||||
gtk_widget_class_install_action (widget_class, "clipboard.cut",
|
||||
gtk_label_nop);
|
||||
gtk_widget_class_install_action (widget_class, "clipboard.copy",
|
||||
gtk_label_activate_clipboard_copy);
|
||||
gtk_widget_class_install_action (widget_class, "clipboard.paste",
|
||||
gtk_label_nop);
|
||||
gtk_widget_class_install_action (widget_class, "selection.delete",
|
||||
gtk_label_nop);
|
||||
gtk_widget_class_install_action (widget_class, "selection.select-all",
|
||||
gtk_label_activate_selection_select_all);
|
||||
gtk_widget_class_install_action (widget_class, "link.open",
|
||||
gtk_label_activate_link_open);
|
||||
gtk_widget_class_install_action (widget_class, "link.copy",
|
||||
gtk_label_activate_link_copy);
|
||||
}
|
||||
|
||||
static void
|
||||
@ -1330,8 +1361,6 @@ gtk_label_init (GtkLabel *label)
|
||||
priv->mnemonic_window = NULL;
|
||||
|
||||
priv->mnemonics_visible = TRUE;
|
||||
|
||||
gtk_label_add_context_actions (label);
|
||||
}
|
||||
|
||||
|
||||
@ -3205,7 +3234,6 @@ gtk_label_finalize (GObject *object)
|
||||
gtk_label_clear_links (label);
|
||||
g_free (priv->select_info);
|
||||
|
||||
g_clear_object (&priv->context_actions);
|
||||
g_clear_pointer (&priv->popup_menu, gtk_widget_unparent);
|
||||
g_clear_object (&priv->extra_menu);
|
||||
|
||||
@ -4854,6 +4882,8 @@ gtk_label_update_active_link (GtkWidget *widget,
|
||||
gtk_widget_queue_draw (widget);
|
||||
}
|
||||
}
|
||||
|
||||
gtk_label_update_actions (label);
|
||||
}
|
||||
}
|
||||
|
||||
@ -5295,6 +5325,8 @@ gtk_label_select_region_index (GtkLabel *label,
|
||||
}
|
||||
}
|
||||
|
||||
gtk_label_update_actions (label);
|
||||
|
||||
gtk_widget_queue_draw (GTK_WIDGET (label));
|
||||
|
||||
g_object_thaw_notify (G_OBJECT (label));
|
||||
@ -5968,24 +6000,24 @@ gtk_label_select_all (GtkLabel *label)
|
||||
}
|
||||
|
||||
static void
|
||||
open_link_activated (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
gtk_label_activate_link_open (GtkWidget *widget,
|
||||
const char *name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
GtkLabel *label = GTK_LABEL (user_data);
|
||||
GtkLabel *label = GTK_LABEL (widget);
|
||||
GtkLabelPrivate *priv = gtk_label_get_instance_private (label);
|
||||
GtkLabelLink *link = priv->select_info->context_link;
|
||||
GtkLabelLink *link = priv->select_info->context_link;
|
||||
|
||||
if (link)
|
||||
emit_activate_link (label, link);
|
||||
}
|
||||
|
||||
static void
|
||||
copy_link_activated (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
gtk_label_activate_link_copy (GtkWidget *widget,
|
||||
const char *name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
GtkLabel *label = GTK_LABEL (user_data);
|
||||
GtkLabel *label = GTK_LABEL (widget);
|
||||
GtkLabelPrivate *priv = gtk_label_get_instance_private (label);
|
||||
GtkLabelLink *link = priv->select_info->context_link;
|
||||
|
||||
@ -5993,101 +6025,59 @@ copy_link_activated (GSimpleAction *action,
|
||||
{
|
||||
GdkClipboard *clipboard;
|
||||
|
||||
clipboard = gtk_widget_get_clipboard (GTK_WIDGET (label));
|
||||
clipboard = gtk_widget_get_clipboard (widget);
|
||||
gdk_clipboard_set_text (clipboard, link->uri);
|
||||
}
|
||||
else
|
||||
g_print ("no link ?!\n");
|
||||
}
|
||||
|
||||
static void
|
||||
copy_clipboard_activated (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
gtk_label_activate_clipboard_copy (GtkWidget *widget,
|
||||
const char *name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
g_signal_emit_by_name (user_data, "copy-clipboard");
|
||||
g_signal_emit_by_name (widget, "copy-clipboard");
|
||||
}
|
||||
|
||||
static void
|
||||
select_all_activated (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
gtk_label_activate_selection_select_all (GtkWidget *widget,
|
||||
const char *name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
gtk_label_select_all (GTK_LABEL (user_data));
|
||||
gtk_label_select_all (GTK_LABEL (widget));
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_label_update_clipboard_actions (GtkLabel *label)
|
||||
gtk_label_nop (GtkWidget *widget,
|
||||
const char *name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_label_update_actions (GtkLabel *label)
|
||||
{
|
||||
GtkWidget *widget = GTK_WIDGET (label);
|
||||
GtkLabelPrivate *priv = gtk_label_get_instance_private (label);
|
||||
gboolean have_selection = FALSE;
|
||||
GAction *action;
|
||||
|
||||
if (priv->select_info)
|
||||
have_selection = priv->select_info->selection_anchor != priv->select_info->selection_end;
|
||||
|
||||
action = g_action_map_lookup_action (priv->context_actions, "copy-clipboard");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), have_selection);
|
||||
action = g_action_map_lookup_action (priv->context_actions, "select-all");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), gtk_label_get_selectable (label));
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_label_update_link_actions (GtkLabel *label)
|
||||
{
|
||||
GtkLabelPrivate *priv = gtk_label_get_instance_private (label);
|
||||
gboolean have_selection = FALSE;
|
||||
GAction *action;
|
||||
gboolean has_selection;
|
||||
GtkLabelLink *link;
|
||||
|
||||
have_selection = priv->select_info->selection_anchor != priv->select_info->selection_end;
|
||||
if (priv->select_info)
|
||||
has_selection = priv->select_info->selection_anchor != priv->select_info->selection_end;
|
||||
else
|
||||
has_selection = FALSE;
|
||||
|
||||
if (priv->select_info->link_clicked)
|
||||
link = priv->select_info->active_link;
|
||||
else
|
||||
link = gtk_label_get_focus_link (label);
|
||||
|
||||
action = g_action_map_lookup_action (priv->context_actions, "open-link");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), !have_selection && link);
|
||||
action = g_action_map_lookup_action (priv->context_actions, "copy-link");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), !have_selection && link);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_label_add_context_actions (GtkLabel *label)
|
||||
{
|
||||
GtkLabelPrivate *priv = gtk_label_get_instance_private (label);
|
||||
|
||||
GActionEntry entries[] = {
|
||||
{ "cut-clipboard", NULL, NULL, NULL, NULL },
|
||||
{ "copy-clipboard", copy_clipboard_activated, NULL, NULL, NULL },
|
||||
{ "paste-clipboard", NULL, NULL, NULL, NULL },
|
||||
{ "delete-selection", NULL, NULL, NULL, NULL },
|
||||
{ "select-all", select_all_activated, NULL, NULL, NULL },
|
||||
{ "open-link", open_link_activated, NULL, NULL, NULL },
|
||||
{ "copy-link", copy_link_activated, NULL, NULL, NULL },
|
||||
};
|
||||
|
||||
GSimpleActionGroup *actions = g_simple_action_group_new ();
|
||||
GAction *action;
|
||||
|
||||
priv->context_actions = G_ACTION_MAP (actions);
|
||||
|
||||
g_action_map_add_action_entries (G_ACTION_MAP (actions), entries, G_N_ELEMENTS (entries), label);
|
||||
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "cut-clipboard");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "copy-clipboard");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "paste-clipboard");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "delete-selection");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "select-all");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "open-link");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "copy-link");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
|
||||
gtk_widget_insert_action_group (GTK_WIDGET (label), "context", G_ACTION_GROUP (actions));
|
||||
gtk_widget_action_enabled_changed (widget, "clipboard.copy", has_selection);
|
||||
gtk_widget_action_enabled_changed (widget, "selection.select-all",
|
||||
gtk_label_get_selectable (label));
|
||||
gtk_widget_action_enabled_changed (widget, "link.open", !has_selection && link);
|
||||
gtk_widget_action_enabled_changed (widget, "link.copy", !has_selection && link);
|
||||
}
|
||||
|
||||
static GMenuModel *
|
||||
@ -6100,24 +6090,24 @@ gtk_label_get_menu_model (GtkLabel *label)
|
||||
menu = g_menu_new ();
|
||||
|
||||
section = g_menu_new ();
|
||||
g_menu_append (section, _("Cu_t"), "context.cut-clipboard");
|
||||
g_menu_append (section, _("_Copy"), "context.copy-clipboard");
|
||||
g_menu_append (section, _("_Paste"), "context.paste-clipboard");
|
||||
g_menu_append (section, _("_Delete"), "context.delete-selection");
|
||||
g_menu_append (section, _("Cu_t"), "clipboard.cut");
|
||||
g_menu_append (section, _("_Copy"), "clipboard.copy");
|
||||
g_menu_append (section, _("_Paste"), "clipboard.paste");
|
||||
g_menu_append (section, _("_Delete"), "selection.delete");
|
||||
g_menu_append_section (menu, NULL, G_MENU_MODEL (section));
|
||||
g_object_unref (section);
|
||||
|
||||
section = g_menu_new ();
|
||||
g_menu_append (section, _("Select _All"), "context.select-all");
|
||||
g_menu_append (section, _("Select _All"), "selection.select-all");
|
||||
g_menu_append_section (menu, NULL, G_MENU_MODEL (section));
|
||||
g_object_unref (section);
|
||||
|
||||
section = g_menu_new ();
|
||||
item = g_menu_item_new (_("_Open Link"), "context.open-link");
|
||||
item = g_menu_item_new (_("_Open Link"), "link.open");
|
||||
g_menu_item_set_attribute (item, "hidden-when", "s", "action-disabled");
|
||||
g_menu_append_item (section, item);
|
||||
g_object_unref (item);
|
||||
item = g_menu_item_new (_("Copy _Link Address"), "context.copy-link");
|
||||
item = g_menu_item_new (_("Copy _Link Address"), "link.copy");
|
||||
g_menu_item_set_attribute (item, "hidden-when", "s", "action-disabled");
|
||||
g_menu_append_item (section, item);
|
||||
g_object_unref (item);
|
||||
@ -6137,8 +6127,15 @@ gtk_label_do_popup (GtkLabel *label,
|
||||
{
|
||||
GtkLabelPrivate *priv = gtk_label_get_instance_private (label);
|
||||
|
||||
gtk_label_update_clipboard_actions (label);
|
||||
gtk_label_update_link_actions (label);
|
||||
if (!priv->select_info)
|
||||
return;
|
||||
|
||||
if (priv->select_info->link_clicked)
|
||||
priv->select_info->context_link = priv->select_info->active_link;
|
||||
else
|
||||
priv->select_info->context_link = gtk_label_get_focus_link (label);
|
||||
|
||||
gtk_label_update_actions (label);
|
||||
|
||||
if (!priv->popup_menu)
|
||||
{
|
||||
@ -6169,15 +6166,6 @@ static gboolean
|
||||
gtk_label_popup_menu (GtkWidget *widget)
|
||||
{
|
||||
GtkLabel *label = GTK_LABEL (widget);
|
||||
GtkLabelPrivate *priv = gtk_label_get_instance_private (label);
|
||||
|
||||
if (!priv->select_info)
|
||||
return FALSE;
|
||||
|
||||
if (priv->select_info->link_clicked)
|
||||
priv->select_info->context_link = priv->select_info->active_link;
|
||||
else
|
||||
priv->select_info->context_link = gtk_label_get_focus_link (label);
|
||||
|
||||
gtk_label_do_popup (label, -1, -1);
|
||||
return TRUE;
|
||||
|
@ -96,7 +96,6 @@ struct _GtkLinkButtonPrivate
|
||||
|
||||
gboolean visited;
|
||||
|
||||
GActionMap *context_actions;
|
||||
GtkWidget *popup_menu;
|
||||
};
|
||||
|
||||
@ -152,6 +151,17 @@ static guint link_signals[LAST_SIGNAL] = { 0, };
|
||||
|
||||
G_DEFINE_TYPE_WITH_PRIVATE (GtkLinkButton, gtk_link_button, GTK_TYPE_BUTTON)
|
||||
|
||||
static void
|
||||
gtk_link_button_activate_clipboard_copy (GtkWidget *widget,
|
||||
const char *name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
GtkLinkButton *link_button = GTK_LINK_BUTTON (widget);
|
||||
GtkLinkButtonPrivate *priv = gtk_link_button_get_instance_private (link_button);
|
||||
|
||||
gdk_clipboard_set_text (gtk_widget_get_clipboard (widget), priv->uri);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_link_button_class_init (GtkLinkButtonClass *klass)
|
||||
{
|
||||
@ -221,28 +231,9 @@ gtk_link_button_class_init (GtkLinkButtonClass *klass)
|
||||
|
||||
gtk_widget_class_set_accessible_type (widget_class, GTK_TYPE_LINK_BUTTON_ACCESSIBLE);
|
||||
gtk_widget_class_set_css_name (widget_class, I_("button"));
|
||||
}
|
||||
|
||||
static void copy_activate_cb (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data);
|
||||
|
||||
static void
|
||||
gtk_link_button_add_context_actions (GtkLinkButton *link_button)
|
||||
{
|
||||
GtkLinkButtonPrivate *priv = gtk_link_button_get_instance_private (link_button);
|
||||
|
||||
GActionEntry entries[] = {
|
||||
{ "copy-clipboard", copy_activate_cb, NULL, 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), link_button);
|
||||
|
||||
gtk_widget_insert_action_group (GTK_WIDGET (link_button), "context", G_ACTION_GROUP (actions));
|
||||
gtk_widget_class_install_action (widget_class, "clipboard.copy",
|
||||
gtk_link_button_activate_clipboard_copy);
|
||||
}
|
||||
|
||||
static GMenuModel *
|
||||
@ -298,7 +289,6 @@ gtk_link_button_init (GtkLinkButton *link_button)
|
||||
gtk_style_context_add_class (context, "link");
|
||||
|
||||
gtk_widget_set_cursor_from_name (GTK_WIDGET (link_button), "pointer");
|
||||
gtk_link_button_add_context_actions (link_button);
|
||||
}
|
||||
|
||||
static void
|
||||
@ -309,7 +299,6 @@ gtk_link_button_finalize (GObject *object)
|
||||
|
||||
g_free (priv->uri);
|
||||
|
||||
g_clear_object (&priv->context_actions);
|
||||
g_clear_pointer (&priv->popup_menu, gtk_widget_unparent);
|
||||
|
||||
G_OBJECT_CLASS (gtk_link_button_parent_class)->finalize (object);
|
||||
@ -360,18 +349,6 @@ gtk_link_button_set_property (GObject *object,
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
copy_activate_cb (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
{
|
||||
GtkLinkButton *link_button = user_data;
|
||||
GtkLinkButtonPrivate *priv = gtk_link_button_get_instance_private (link_button);
|
||||
|
||||
gdk_clipboard_set_text (gtk_widget_get_clipboard (GTK_WIDGET (link_button)),
|
||||
priv->uri);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_link_button_do_popup (GtkLinkButton *link_button,
|
||||
double x,
|
||||
|
@ -110,20 +110,30 @@ focus_changed (GtkWidget *widget)
|
||||
|
||||
static void
|
||||
gtk_password_entry_toggle_peek (GtkPasswordEntry *entry)
|
||||
{
|
||||
GtkPasswordEntryPrivate *priv = gtk_password_entry_get_instance_private (entry);
|
||||
gboolean visibility;
|
||||
|
||||
visibility = gtk_text_get_visibility (GTK_TEXT (priv->entry));
|
||||
gtk_text_set_visibility (GTK_TEXT (priv->entry), !visibility);
|
||||
}
|
||||
|
||||
static void
|
||||
visibility_toggled (GObject *object,
|
||||
GParamSpec *pspec,
|
||||
GtkPasswordEntry *entry)
|
||||
{
|
||||
GtkPasswordEntryPrivate *priv = gtk_password_entry_get_instance_private (entry);
|
||||
|
||||
if (gtk_text_get_visibility (GTK_TEXT (priv->entry)))
|
||||
{
|
||||
gtk_text_set_visibility (GTK_TEXT (priv->entry), FALSE);
|
||||
gtk_image_set_from_icon_name (GTK_IMAGE (priv->peek_icon), "eye-not-looking-symbolic");
|
||||
gtk_widget_set_tooltip_text (priv->peek_icon, _("Show text"));
|
||||
gtk_image_set_from_icon_name (GTK_IMAGE (priv->peek_icon), "eye-open-negative-filled-symbolic");
|
||||
gtk_widget_set_tooltip_text (priv->peek_icon, _("Hide text"));
|
||||
}
|
||||
else
|
||||
{
|
||||
gtk_text_set_visibility (GTK_TEXT (priv->entry), TRUE);
|
||||
gtk_image_set_from_icon_name (GTK_IMAGE (priv->peek_icon), "eye-open-negative-filled-symbolic");
|
||||
gtk_widget_set_tooltip_text (priv->peek_icon, _("Hide text"));
|
||||
gtk_image_set_from_icon_name (GTK_IMAGE (priv->peek_icon), "eye-not-looking-symbolic");
|
||||
gtk_widget_set_tooltip_text (priv->peek_icon, _("Show text"));
|
||||
}
|
||||
}
|
||||
|
||||
@ -482,11 +492,18 @@ gtk_password_entry_set_show_peek_icon (GtkPasswordEntry *entry,
|
||||
g_signal_connect_swapped (press, "released",
|
||||
G_CALLBACK (gtk_password_entry_toggle_peek), entry);
|
||||
gtk_widget_add_controller (priv->peek_icon, GTK_EVENT_CONTROLLER (press));
|
||||
|
||||
g_signal_connect (priv->entry, "notify::visibility",
|
||||
G_CALLBACK (visibility_toggled), entry);
|
||||
visibility_toggled (G_OBJECT (priv->entry), NULL, entry);
|
||||
}
|
||||
else
|
||||
{
|
||||
g_clear_pointer (&priv->peek_icon, gtk_widget_unparent);
|
||||
gtk_text_set_visibility (GTK_TEXT (priv->entry), FALSE);
|
||||
g_signal_handlers_disconnect_by_func (priv->entry,
|
||||
visibility_toggled,
|
||||
entry);
|
||||
}
|
||||
|
||||
keymap_state_changed (priv->keymap, GTK_WIDGET (entry));
|
||||
@ -532,13 +549,17 @@ gtk_password_entry_set_extra_menu (GtkPasswordEntry *entry,
|
||||
|
||||
g_return_if_fail (GTK_IS_PASSWORD_ENTRY (entry));
|
||||
|
||||
if (!g_set_object (&priv->extra_menu, model))
|
||||
return;
|
||||
/* bypass this check for the initial call from init */
|
||||
if (priv->extra_menu)
|
||||
{
|
||||
if (!g_set_object (&priv->extra_menu, model))
|
||||
return;
|
||||
}
|
||||
|
||||
menu = g_menu_new ();
|
||||
|
||||
section = g_menu_new ();
|
||||
item = g_menu_item_new (_("_Show Text"), "context.toggle-visibility");
|
||||
item = g_menu_item_new (_("_Show Text"), "misc.toggle-visibility");
|
||||
g_menu_item_set_attribute (item, "touch-icon", "s", "eye-not-looking-symbolic");
|
||||
g_menu_append_item (section, item);
|
||||
g_object_unref (item);
|
||||
|
268
gtk/gtktext.c
268
gtk/gtktext.c
@ -68,6 +68,7 @@
|
||||
#include "gtkwidgetprivate.h"
|
||||
#include "gtkwindow.h"
|
||||
#include "gtknative.h"
|
||||
#include "gtkactionmuxerprivate.h"
|
||||
|
||||
#include "a11y/gtktextaccessible.h"
|
||||
|
||||
@ -174,7 +175,6 @@ struct _GtkTextPrivate
|
||||
GtkCssNode *block_cursor_node;
|
||||
GtkCssNode *undershoot_node[2];
|
||||
|
||||
GActionMap *context_actions;
|
||||
GtkWidget *popup_menu;
|
||||
GMenuModel *extra_menu;
|
||||
|
||||
@ -542,10 +542,36 @@ static void begin_change (GtkText *self);
|
||||
static void end_change (GtkText *self);
|
||||
static void emit_changed (GtkText *self);
|
||||
|
||||
static void gtk_text_add_context_actions (GtkText *self);
|
||||
static void gtk_text_update_clipboard_actions (GtkText *self);
|
||||
static void gtk_text_update_emoji_action (GtkText *self);
|
||||
|
||||
static void gtk_text_activate_clipboard_cut (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter);
|
||||
static void gtk_text_activate_clipboard_copy (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter);
|
||||
static void gtk_text_activate_clipboard_paste (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter);
|
||||
static void gtk_text_activate_selection_delete (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter);
|
||||
static void gtk_text_activate_selection_select_all (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter);
|
||||
static void gtk_text_activate_misc_insert_emoji (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter);
|
||||
static void gtk_text_activate_misc_toggle_visibility (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter);
|
||||
|
||||
static void gtk_text_set_misc_toggle_visibility (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *state);
|
||||
static GVariant *gtk_text_get_misc_toggle_visibility (GtkWidget *widget,
|
||||
const char *action_name);
|
||||
|
||||
/* GtkTextContent implementation
|
||||
*/
|
||||
@ -706,7 +732,7 @@ gtk_text_class_init (GtkTextClass *class)
|
||||
class->toggle_overwrite = gtk_text_toggle_overwrite;
|
||||
class->insert_emoji = gtk_text_insert_emoji;
|
||||
class->activate = gtk_text_real_activate;
|
||||
|
||||
|
||||
quark_password_hint = g_quark_from_static_string ("gtk-entry-password-hint");
|
||||
quark_gtk_signal = g_quark_from_static_string ("gtk-signal");
|
||||
|
||||
@ -1336,6 +1362,24 @@ gtk_text_class_init (GtkTextClass *class)
|
||||
|
||||
gtk_widget_class_set_accessible_type (widget_class, GTK_TYPE_TEXT_ACCESSIBLE);
|
||||
gtk_widget_class_set_css_name (widget_class, I_("text"));
|
||||
|
||||
gtk_widget_class_install_action (widget_class, "clipboard.cut",
|
||||
gtk_text_activate_clipboard_cut);
|
||||
gtk_widget_class_install_action (widget_class, "clipboard.copy",
|
||||
gtk_text_activate_clipboard_copy);
|
||||
gtk_widget_class_install_action (widget_class, "clipboard.paste",
|
||||
gtk_text_activate_clipboard_paste);
|
||||
gtk_widget_class_install_action (widget_class, "selection.delete",
|
||||
gtk_text_activate_selection_delete);
|
||||
gtk_widget_class_install_action (widget_class, "selection.select-all",
|
||||
gtk_text_activate_selection_select_all);
|
||||
gtk_widget_class_install_action (widget_class, "misc.insert-emoji",
|
||||
gtk_text_activate_misc_insert_emoji);
|
||||
gtk_widget_class_install_stateful_action (widget_class, "misc.toggle-visibility",
|
||||
gtk_text_activate_misc_toggle_visibility,
|
||||
NULL,
|
||||
gtk_text_set_misc_toggle_visibility,
|
||||
gtk_text_get_misc_toggle_visibility);
|
||||
}
|
||||
|
||||
static void
|
||||
@ -1720,7 +1764,6 @@ gtk_text_init (GtkText *self)
|
||||
}
|
||||
|
||||
set_text_cursor (GTK_WIDGET (self));
|
||||
gtk_text_add_context_actions (self);
|
||||
}
|
||||
|
||||
static void
|
||||
@ -1766,7 +1809,7 @@ gtk_text_dispose (GObject *object)
|
||||
keymap = gdk_display_get_keymap (gtk_widget_get_display (GTK_WIDGET (object)));
|
||||
g_signal_handlers_disconnect_by_func (keymap, keymap_direction_changed, self);
|
||||
|
||||
g_clear_object (&priv->context_actions);
|
||||
g_clear_pointer (&priv->selection_bubble, gtk_widget_unparent);
|
||||
g_clear_pointer (&priv->popup_menu, gtk_widget_unparent);
|
||||
g_clear_object (&priv->extra_menu);
|
||||
|
||||
@ -1783,7 +1826,6 @@ gtk_text_finalize (GObject *object)
|
||||
|
||||
g_clear_object (&priv->cached_layout);
|
||||
g_clear_object (&priv->im_context);
|
||||
g_clear_pointer (&priv->selection_bubble, gtk_widget_unparent);
|
||||
g_clear_pointer (&priv->magnifier_popover, gtk_widget_destroy);
|
||||
g_clear_object (&priv->text_handle);
|
||||
g_free (priv->im_module);
|
||||
@ -2176,6 +2218,9 @@ gtk_text_size_allocate (GtkWidget *widget,
|
||||
|
||||
if (priv->popup_menu)
|
||||
gtk_native_check_resize (GTK_NATIVE (priv->popup_menu));
|
||||
|
||||
if (priv->selection_bubble)
|
||||
gtk_native_check_resize (GTK_NATIVE (priv->selection_bubble));
|
||||
}
|
||||
|
||||
static void
|
||||
@ -4047,6 +4092,7 @@ gtk_text_set_positions (GtkText *self,
|
||||
|
||||
if (changed)
|
||||
{
|
||||
gtk_text_update_clipboard_actions (self);
|
||||
gtk_text_recompute (self);
|
||||
}
|
||||
}
|
||||
@ -5261,15 +5307,14 @@ gtk_text_set_visibility (GtkText *self,
|
||||
|
||||
if (priv->visible != visible)
|
||||
{
|
||||
GAction *action;
|
||||
|
||||
priv->visible = visible;
|
||||
|
||||
g_object_notify (G_OBJECT (self), "visibility");
|
||||
gtk_text_recompute (self);
|
||||
|
||||
action = g_action_map_lookup_action (priv->context_actions, "toggle-visibility");
|
||||
g_simple_action_set_state (G_SIMPLE_ACTION (action), g_variant_new_boolean (visible));
|
||||
gtk_text_update_clipboard_actions (self);
|
||||
gtk_widget_action_state_changed (GTK_WIDGET (self), "misc.toggle-visibility",
|
||||
g_variant_new_boolean (visible));
|
||||
}
|
||||
}
|
||||
|
||||
@ -5615,152 +5660,129 @@ hide_selection_bubble (GtkText *self)
|
||||
}
|
||||
|
||||
static void
|
||||
cut_clipboard_activated (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
gtk_text_activate_clipboard_cut (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
g_signal_emit_by_name (user_data, "cut-clipboard");
|
||||
hide_selection_bubble (GTK_TEXT (user_data));
|
||||
GtkText *self = GTK_TEXT (widget);
|
||||
g_signal_emit_by_name (self, "cut-clipboard");
|
||||
hide_selection_bubble (self);
|
||||
}
|
||||
|
||||
static void
|
||||
copy_clipboard_activated (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
gtk_text_activate_clipboard_copy (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
g_signal_emit_by_name (user_data, "copy-clipboard");
|
||||
hide_selection_bubble (GTK_TEXT (user_data));
|
||||
GtkText *self = GTK_TEXT (widget);
|
||||
g_signal_emit_by_name (self, "copy-clipboard");
|
||||
hide_selection_bubble (self);
|
||||
}
|
||||
|
||||
static void
|
||||
paste_clipboard_activated (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
gtk_text_activate_clipboard_paste (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
g_signal_emit_by_name (user_data, "paste-clipboard");
|
||||
hide_selection_bubble (GTK_TEXT (user_data));
|
||||
GtkText *self = GTK_TEXT (widget);
|
||||
g_signal_emit_by_name (self, "paste-clipboard");
|
||||
hide_selection_bubble (self);
|
||||
}
|
||||
|
||||
static void
|
||||
delete_selection_activated (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
gtk_text_activate_selection_delete (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
gtk_text_delete_cb (GTK_TEXT (user_data));
|
||||
hide_selection_bubble (GTK_TEXT (user_data));
|
||||
GtkText *self = GTK_TEXT (widget);
|
||||
gtk_text_delete_cb (self);
|
||||
hide_selection_bubble (self);
|
||||
}
|
||||
|
||||
static void
|
||||
select_all_activated (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
gtk_text_activate_selection_select_all (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
gtk_text_select_all (GTK_TEXT (user_data));
|
||||
GtkText *self = GTK_TEXT (widget);
|
||||
gtk_text_select_all (self);
|
||||
}
|
||||
|
||||
static void
|
||||
insert_emoji_activated (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
gtk_text_activate_misc_insert_emoji (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
gtk_text_insert_emoji (GTK_TEXT (user_data));
|
||||
hide_selection_bubble (GTK_TEXT (user_data));
|
||||
GtkText *self = GTK_TEXT (widget);
|
||||
gtk_text_insert_emoji (self);
|
||||
hide_selection_bubble (self);
|
||||
}
|
||||
|
||||
static void
|
||||
toggle_visibility (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
gtk_text_activate_misc_toggle_visibility (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
GtkText *text = GTK_TEXT (user_data);
|
||||
gtk_text_set_visibility (text, !gtk_text_get_visibility (text));
|
||||
GtkText *self = GTK_TEXT (widget);
|
||||
gtk_text_set_visibility (self, !gtk_text_get_visibility (self));
|
||||
}
|
||||
|
||||
static GVariant *
|
||||
gtk_text_get_misc_toggle_visibility (GtkWidget *widget,
|
||||
const char *action_name)
|
||||
{
|
||||
GtkText *self = GTK_TEXT (widget);
|
||||
DisplayMode mode = gtk_text_get_display_mode (self);
|
||||
|
||||
return g_variant_new_boolean (mode == DISPLAY_NORMAL);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_text_add_context_actions (GtkText *self)
|
||||
gtk_text_set_misc_toggle_visibility (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *state)
|
||||
{
|
||||
GtkTextPrivate *priv = gtk_text_get_instance_private (self);
|
||||
|
||||
GActionEntry entries[] = {
|
||||
{ "cut-clipboard", cut_clipboard_activated, NULL, NULL, NULL },
|
||||
{ "copy-clipboard", copy_clipboard_activated, NULL, NULL, NULL },
|
||||
{ "paste-clipboard", paste_clipboard_activated, NULL, NULL, NULL },
|
||||
{ "delete-selection", delete_selection_activated, NULL, NULL, NULL },
|
||||
{ "select-all", select_all_activated, NULL, NULL, NULL },
|
||||
{ "insert-emoji", insert_emoji_activated, NULL, NULL, NULL },
|
||||
{ "toggle-visibility", toggle_visibility, NULL, "true", NULL },
|
||||
};
|
||||
|
||||
GSimpleActionGroup *actions = g_simple_action_group_new ();
|
||||
GAction *action;
|
||||
|
||||
priv->context_actions = G_ACTION_MAP (actions);
|
||||
|
||||
g_action_map_add_action_entries (G_ACTION_MAP (actions), entries, G_N_ELEMENTS (entries), self);
|
||||
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "cut-clipboard");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "copy-clipboard");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "paste-clipboard");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "delete-selection");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "select-all");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "insert-emoji");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
|
||||
gtk_widget_insert_action_group (GTK_WIDGET (self), "context", G_ACTION_GROUP (actions));
|
||||
GtkText *self = GTK_TEXT (widget);
|
||||
gboolean visible = g_variant_get_boolean (state);
|
||||
gtk_text_set_visibility (self, visible);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_text_update_clipboard_actions (GtkText *self)
|
||||
{
|
||||
{
|
||||
GtkTextPrivate *priv = gtk_text_get_instance_private (self);
|
||||
DisplayMode mode;
|
||||
GdkClipboard *clipboard;
|
||||
gboolean has_clipboard;
|
||||
GAction *action;
|
||||
|
||||
gboolean has_selection;
|
||||
gboolean has_content;
|
||||
gboolean visible;
|
||||
|
||||
clipboard = gtk_widget_get_clipboard (GTK_WIDGET (self));
|
||||
has_clipboard = gdk_content_formats_contain_gtype (gdk_clipboard_get_formats (clipboard), G_TYPE_STRING);
|
||||
mode = gtk_text_get_display_mode (self);
|
||||
has_clipboard = gdk_content_formats_contain_gtype (gdk_clipboard_get_formats (clipboard), G_TYPE_STRING);
|
||||
has_selection = priv->current_pos != priv->selection_bound;
|
||||
has_content = priv->buffer && (gtk_entry_buffer_get_length (priv->buffer) > 0);
|
||||
visible = mode == DISPLAY_NORMAL;
|
||||
|
||||
action = g_action_map_lookup_action (priv->context_actions, "cut-clipboard");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action),
|
||||
mode == DISPLAY_NORMAL &&
|
||||
priv->editable &&
|
||||
priv->current_pos != priv->selection_bound);
|
||||
gtk_widget_action_enabled_changed (GTK_WIDGET (self), "clipboard.cut",
|
||||
visible && priv->editable && has_selection);
|
||||
gtk_widget_action_enabled_changed (GTK_WIDGET (self), "clipboard.copy",
|
||||
visible && has_selection);
|
||||
gtk_widget_action_enabled_changed (GTK_WIDGET (self), "clipboard.paste",
|
||||
priv->editable && has_clipboard);
|
||||
|
||||
action = g_action_map_lookup_action (priv->context_actions, "copy-clipboard");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action),
|
||||
mode == DISPLAY_NORMAL &&
|
||||
priv->current_pos != priv->selection_bound);
|
||||
|
||||
action = g_action_map_lookup_action (priv->context_actions, "paste-clipboard");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action),
|
||||
priv->editable && has_clipboard);
|
||||
|
||||
action = g_action_map_lookup_action (priv->context_actions, "delete-selection");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action),
|
||||
priv->editable &&
|
||||
priv->current_pos != priv->selection_bound);
|
||||
|
||||
action = g_action_map_lookup_action (priv->context_actions, "select-all");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action),
|
||||
priv->buffer && (gtk_entry_buffer_get_length (priv->buffer) > 0));
|
||||
gtk_widget_action_enabled_changed (GTK_WIDGET (self), "selection.delete",
|
||||
priv->editable && has_selection);
|
||||
gtk_widget_action_enabled_changed (GTK_WIDGET (self), "selection.select-all",
|
||||
has_content);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_text_update_emoji_action (GtkText *self)
|
||||
{
|
||||
GtkTextPrivate *priv = gtk_text_get_instance_private (self);
|
||||
GAction *action;
|
||||
|
||||
action = g_action_map_lookup_action (priv->context_actions, "insert-emoji");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action),
|
||||
(gtk_text_get_input_hints (self) & GTK_INPUT_HINT_NO_EMOJI) == 0);
|
||||
gtk_widget_action_enabled_changed (GTK_WIDGET (self), "misc.insert-emoji",
|
||||
(gtk_text_get_input_hints (self) & GTK_INPUT_HINT_NO_EMOJI) == 0);
|
||||
}
|
||||
|
||||
static GMenuModel *
|
||||
@ -5773,19 +5795,19 @@ gtk_text_get_menu_model (GtkText *self)
|
||||
menu = g_menu_new ();
|
||||
|
||||
section = g_menu_new ();
|
||||
item = g_menu_item_new (_("Cu_t"), "context.cut-clipboard");
|
||||
item = g_menu_item_new (_("Cu_t"), "clipboard.cut");
|
||||
g_menu_item_set_attribute (item, "touch-icon", "s", "edit-cut-symbolic");
|
||||
g_menu_append_item (section, item);
|
||||
g_object_unref (item);
|
||||
item = g_menu_item_new (_("_Copy"), "context.copy-clipboard");
|
||||
item = g_menu_item_new (_("_Copy"), "clipboard.copy");
|
||||
g_menu_item_set_attribute (item, "touch-icon", "s", "edit-copy-symbolic");
|
||||
g_menu_append_item (section, item);
|
||||
g_object_unref (item);
|
||||
item = g_menu_item_new (_("_Paste"), "context.paste-clipboard");
|
||||
item = g_menu_item_new (_("_Paste"), "clipboard.paste");
|
||||
g_menu_item_set_attribute (item, "touch-icon", "s", "edit-paste-symbolic");
|
||||
g_menu_append_item (section, item);
|
||||
g_object_unref (item);
|
||||
item = g_menu_item_new (_("_Delete"), "context.delete-selection");
|
||||
item = g_menu_item_new (_("_Delete"), "selection.delete");
|
||||
g_menu_item_set_attribute (item, "touch-icon", "s", "edit-delete-symbolic");
|
||||
g_menu_append_item (section, item);
|
||||
g_object_unref (item);
|
||||
@ -5794,12 +5816,12 @@ gtk_text_get_menu_model (GtkText *self)
|
||||
|
||||
section = g_menu_new ();
|
||||
|
||||
item = g_menu_item_new (_("Select _All"), "context.select-all");
|
||||
item = g_menu_item_new (_("Select _All"), "selection.select-all");
|
||||
g_menu_item_set_attribute (item, "touch-icon", "s", "edit-select-all-symbolic");
|
||||
g_menu_append_item (section, item);
|
||||
g_object_unref (item);
|
||||
|
||||
item = g_menu_item_new ( _("Insert _Emoji"), "context.insert-emoji");
|
||||
item = g_menu_item_new ( _("Insert _Emoji"), "misc.insert-emoji");
|
||||
g_menu_item_set_attribute (item, "hidden-when", "s", "action-disabled");
|
||||
g_menu_item_set_attribute (item, "touch-icon", "s", "face-smile-symbolic");
|
||||
g_menu_append_item (section, item);
|
||||
@ -5860,12 +5882,11 @@ append_bubble_item (GtkText *self,
|
||||
GMenuModel *model,
|
||||
int index)
|
||||
{
|
||||
GtkTextPrivate *priv = gtk_text_get_instance_private (self);
|
||||
GtkActionMuxer *muxer;
|
||||
GtkWidget *item, *image;
|
||||
GVariant *att;
|
||||
const char *icon_name;
|
||||
const char *action_name;
|
||||
GAction *action;
|
||||
GMenuModel *link;
|
||||
|
||||
link = g_menu_model_get_item_link (model, index, "section");
|
||||
@ -5891,12 +5912,9 @@ append_bubble_item (GtkText *self,
|
||||
action_name = g_variant_get_string (att, NULL);
|
||||
g_variant_unref (att);
|
||||
|
||||
if (g_str_has_prefix (action_name, "context."))
|
||||
{
|
||||
action = g_action_map_lookup_action (priv->context_actions, action_name + strlen ("context."));
|
||||
if (action && !g_action_get_enabled (action))
|
||||
return;
|
||||
}
|
||||
muxer = _gtk_widget_get_action_muxer (GTK_WIDGET (self), FALSE);
|
||||
if (!g_action_group_get_action_enabled (G_ACTION_GROUP (muxer), action_name))
|
||||
return;
|
||||
|
||||
item = gtk_button_new ();
|
||||
gtk_widget_set_focus_on_click (item, FALSE);
|
||||
@ -5990,7 +6008,7 @@ gtk_text_selection_bubble_popup_show (gpointer user_data)
|
||||
rect.height += 10;
|
||||
|
||||
gtk_popover_set_pointing_to (GTK_POPOVER (priv->selection_bubble), &rect);
|
||||
gtk_widget_show (priv->selection_bubble);
|
||||
gtk_popover_popup (GTK_POPOVER (priv->selection_bubble));
|
||||
|
||||
priv->selection_bubble_timeout_id = 0;
|
||||
|
||||
|
@ -182,8 +182,6 @@ struct _GtkTextViewPrivate
|
||||
GtkAdjustment *hadjustment;
|
||||
GtkAdjustment *vadjustment;
|
||||
|
||||
GActionMap *context_actions;
|
||||
|
||||
/* X offset between widget coordinates and buffer coordinates
|
||||
* taking left_padding in account
|
||||
*/
|
||||
@ -595,10 +593,28 @@ static void extend_selection (GtkTextView *text_view,
|
||||
GtkTextIter *start,
|
||||
GtkTextIter *end);
|
||||
|
||||
static void gtk_text_view_add_context_actions (GtkTextView *text_view);
|
||||
|
||||
static void gtk_text_view_update_clipboard_actions (GtkTextView *text_view);
|
||||
static void gtk_text_view_update_emoji_action (GtkTextView *text_view);
|
||||
|
||||
static void gtk_text_view_activate_clipboard_cut (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter);
|
||||
static void gtk_text_view_activate_clipboard_copy (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter);
|
||||
static void gtk_text_view_activate_clipboard_paste (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter);
|
||||
static void gtk_text_view_activate_selection_delete (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter);
|
||||
static void gtk_text_view_activate_selection_select_all (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter);
|
||||
static void gtk_text_view_activate_misc_insert_emoji (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter);
|
||||
|
||||
|
||||
/* FIXME probably need the focus methods. */
|
||||
@ -1585,6 +1601,19 @@ gtk_text_view_class_init (GtkTextViewClass *klass)
|
||||
quark_text_selection_data = g_quark_from_static_string ("gtk-text-view-text-selection-data");
|
||||
quark_gtk_signal = g_quark_from_static_string ("gtk-signal");
|
||||
quark_text_view_child = g_quark_from_static_string ("gtk-text-view-child");
|
||||
|
||||
gtk_widget_class_install_action (widget_class, "clipboard.cut",
|
||||
gtk_text_view_activate_clipboard_cut);
|
||||
gtk_widget_class_install_action (widget_class, "clipboard.copy",
|
||||
gtk_text_view_activate_clipboard_copy);
|
||||
gtk_widget_class_install_action (widget_class, "clipboard.paste",
|
||||
gtk_text_view_activate_clipboard_paste);
|
||||
gtk_widget_class_install_action (widget_class, "selection.delete",
|
||||
gtk_text_view_activate_selection_delete);
|
||||
gtk_widget_class_install_action (widget_class, "selection.select-all",
|
||||
gtk_text_view_activate_selection_select_all);
|
||||
gtk_widget_class_install_action (widget_class, "misc.insert-emoji",
|
||||
gtk_text_view_activate_misc_insert_emoji);
|
||||
}
|
||||
|
||||
static void
|
||||
@ -1694,8 +1723,6 @@ gtk_text_view_init (GtkTextView *text_view)
|
||||
gtk_css_node_get_state (priv->text_window->css_node) & ~GTK_STATE_FLAG_DROP_ACTIVE);
|
||||
gtk_css_node_set_visible (priv->selection_node, FALSE);
|
||||
g_object_unref (priv->selection_node);
|
||||
|
||||
gtk_text_view_add_context_actions (text_view);
|
||||
}
|
||||
|
||||
GtkCssNode *
|
||||
@ -3617,7 +3644,6 @@ gtk_text_view_finalize (GObject *object)
|
||||
g_free (priv->im_module);
|
||||
|
||||
g_clear_pointer (&priv->popup_menu, gtk_widget_unparent);
|
||||
g_clear_object (&priv->context_actions);
|
||||
g_clear_object (&priv->extra_menu);
|
||||
|
||||
G_OBJECT_CLASS (gtk_text_view_parent_class)->finalize (object);
|
||||
@ -8438,33 +8464,6 @@ hide_selection_bubble (GtkTextView *text_view)
|
||||
gtk_widget_hide (priv->selection_bubble);
|
||||
}
|
||||
|
||||
static void
|
||||
cut_clipboard_activated (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
{
|
||||
g_signal_emit_by_name (user_data, "cut-clipboard");
|
||||
hide_selection_bubble (GTK_TEXT_VIEW (user_data));
|
||||
}
|
||||
|
||||
static void
|
||||
copy_clipboard_activated (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
{
|
||||
g_signal_emit_by_name (user_data, "copy-clipboard");
|
||||
hide_selection_bubble (GTK_TEXT_VIEW (user_data));
|
||||
}
|
||||
|
||||
static void
|
||||
paste_clipboard_activated (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
{
|
||||
g_signal_emit_by_name (user_data, "paste-clipboard");
|
||||
hide_selection_bubble (GTK_TEXT_VIEW (user_data));
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_text_view_select_all (GtkWidget *widget,
|
||||
gboolean select)
|
||||
@ -8487,34 +8486,6 @@ gtk_text_view_select_all (GtkWidget *widget,
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
select_all_activated (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
{
|
||||
GtkTextView *text_view = user_data;
|
||||
|
||||
gtk_text_view_select_all (GTK_WIDGET (text_view), TRUE);
|
||||
}
|
||||
|
||||
static void
|
||||
delete_selection_activated (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
{
|
||||
GtkTextView *text_view = user_data;
|
||||
|
||||
gtk_text_buffer_delete_selection (get_buffer (text_view), TRUE,
|
||||
text_view->priv->editable);
|
||||
}
|
||||
|
||||
static void
|
||||
insert_emoji_activated (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer user_data)
|
||||
{
|
||||
gtk_text_view_insert_emoji (GTK_TEXT_VIEW (user_data));
|
||||
}
|
||||
|
||||
static gboolean
|
||||
range_contains_editable_text (const GtkTextIter *start,
|
||||
@ -8535,40 +8506,60 @@ range_contains_editable_text (const GtkTextIter *start,
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_text_view_add_context_actions (GtkTextView *text_view)
|
||||
gtk_text_view_activate_clipboard_cut (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
GtkTextViewPrivate *priv = text_view->priv;
|
||||
GtkTextView *self = GTK_TEXT_VIEW (widget);
|
||||
g_signal_emit_by_name (self, "cut-clipboard");
|
||||
hide_selection_bubble (self);
|
||||
}
|
||||
|
||||
GActionEntry entries[] = {
|
||||
{ "cut-clipboard", cut_clipboard_activated, NULL, NULL, NULL },
|
||||
{ "copy-clipboard", copy_clipboard_activated, NULL, NULL, NULL },
|
||||
{ "paste-clipboard", paste_clipboard_activated, NULL, NULL, NULL },
|
||||
{ "delete-selection", delete_selection_activated, NULL, NULL, NULL },
|
||||
{ "select-all", select_all_activated, NULL, NULL, NULL },
|
||||
{ "insert-emoji", insert_emoji_activated, NULL, NULL, NULL },
|
||||
};
|
||||
static void
|
||||
gtk_text_view_activate_clipboard_copy (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
GtkTextView *self = GTK_TEXT_VIEW (widget);
|
||||
g_signal_emit_by_name (self, "copy-clipboard");
|
||||
hide_selection_bubble (self);
|
||||
}
|
||||
|
||||
GSimpleActionGroup *actions = g_simple_action_group_new ();
|
||||
GAction *action;
|
||||
static void
|
||||
gtk_text_view_activate_clipboard_paste (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
GtkTextView *self = GTK_TEXT_VIEW (widget);
|
||||
g_signal_emit_by_name (self, "paste-clipboard");
|
||||
hide_selection_bubble (self);
|
||||
}
|
||||
|
||||
priv->context_actions = G_ACTION_MAP (actions);
|
||||
static void
|
||||
gtk_text_view_activate_selection_select_all (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
gtk_text_view_select_all (widget, TRUE);
|
||||
}
|
||||
|
||||
g_action_map_add_action_entries (G_ACTION_MAP (actions), entries, G_N_ELEMENTS (entries), text_view);
|
||||
static void
|
||||
gtk_text_view_activate_selection_delete (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
GtkTextView *text_view = GTK_TEXT_VIEW (widget);
|
||||
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "cut-clipboard");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "copy-clipboard");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "paste-clipboard");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "delete-selection");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "select-all");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
action = g_action_map_lookup_action (G_ACTION_MAP (actions), "insert-emoji");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), FALSE);
|
||||
gtk_text_buffer_delete_selection (get_buffer (text_view), TRUE,
|
||||
text_view->priv->editable);
|
||||
}
|
||||
|
||||
gtk_widget_insert_action_group (GTK_WIDGET (text_view), "context", G_ACTION_GROUP (actions));
|
||||
static void
|
||||
gtk_text_view_activate_misc_insert_emoji (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
gtk_text_view_insert_emoji (GTK_TEXT_VIEW (widget));
|
||||
}
|
||||
|
||||
static void
|
||||
@ -8578,7 +8569,6 @@ gtk_text_view_update_clipboard_actions (GtkTextView *text_view)
|
||||
GdkClipboard *clipboard;
|
||||
gboolean have_selection;
|
||||
gboolean can_paste, can_insert;
|
||||
GAction *action;
|
||||
GtkTextIter iter, sel_start, sel_end;
|
||||
|
||||
clipboard = gtk_widget_get_clipboard (GTK_WIDGET (text_view));
|
||||
@ -8593,36 +8583,25 @@ gtk_text_view_update_clipboard_actions (GtkTextView *text_view)
|
||||
|
||||
can_insert = gtk_text_iter_can_insert (&iter, priv->editable);
|
||||
|
||||
action = g_action_map_lookup_action (priv->context_actions, "cut-clipboard");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action),
|
||||
have_selection &&
|
||||
range_contains_editable_text (&sel_start, &sel_end, priv->editable));
|
||||
|
||||
action = g_action_map_lookup_action (priv->context_actions, "copy-clipboard");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), have_selection);
|
||||
|
||||
action = g_action_map_lookup_action (priv->context_actions, "paste-clipboard");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action), can_insert && can_paste);
|
||||
|
||||
action = g_action_map_lookup_action (priv->context_actions, "delete-selection");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action),
|
||||
have_selection &&
|
||||
range_contains_editable_text (&sel_start, &sel_end, priv->editable));
|
||||
|
||||
action = g_action_map_lookup_action (priv->context_actions, "select-all");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action),
|
||||
gtk_text_buffer_get_char_count (priv->buffer) > 0);
|
||||
gtk_widget_action_enabled_changed (GTK_WIDGET (text_view), "clipboard.cut",
|
||||
have_selection &&
|
||||
range_contains_editable_text (&sel_start, &sel_end, priv->editable));
|
||||
gtk_widget_action_enabled_changed (GTK_WIDGET (text_view), "clipboard.copy",
|
||||
have_selection);
|
||||
gtk_widget_action_enabled_changed (GTK_WIDGET (text_view), "clipboard.paste",
|
||||
can_insert && can_paste);
|
||||
gtk_widget_action_enabled_changed (GTK_WIDGET (text_view), "selection.delete",
|
||||
have_selection &&
|
||||
range_contains_editable_text (&sel_start, &sel_end, priv->editable));
|
||||
gtk_widget_action_enabled_changed (GTK_WIDGET (text_view), "selection.select-all",
|
||||
gtk_text_buffer_get_char_count (priv->buffer) > 0);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_text_view_update_emoji_action (GtkTextView *text_view)
|
||||
{
|
||||
GtkTextViewPrivate *priv = text_view->priv;
|
||||
GAction *action;
|
||||
|
||||
action = g_action_map_lookup_action (priv->context_actions, "insert-emoji");
|
||||
g_simple_action_set_enabled (G_SIMPLE_ACTION (action),
|
||||
(gtk_text_view_get_input_hints (text_view) & GTK_INPUT_HINT_NO_EMOJI) == 0);
|
||||
gtk_widget_action_enabled_changed (GTK_WIDGET (text_view), "misc.insert-emoji",
|
||||
(gtk_text_view_get_input_hints (text_view) & GTK_INPUT_HINT_NO_EMOJI) == 0);
|
||||
}
|
||||
|
||||
static GMenuModel *
|
||||
@ -8635,19 +8614,19 @@ gtk_text_view_get_menu_model (GtkTextView *text_view)
|
||||
menu = g_menu_new ();
|
||||
|
||||
section = g_menu_new ();
|
||||
item = g_menu_item_new (_("Cu_t"), "context.cut-clipboard");
|
||||
item = g_menu_item_new (_("Cu_t"), "clipboard.cut");
|
||||
g_menu_item_set_attribute (item, "touch-icon", "s", "edit-cut-symbolic");
|
||||
g_menu_append_item (section, item);
|
||||
g_object_unref (item);
|
||||
item = g_menu_item_new (_("_Copy"), "context.copy-clipboard");
|
||||
item = g_menu_item_new (_("_Copy"), "clipboard.copy");
|
||||
g_menu_item_set_attribute (item, "touch-icon", "s", "edit-copy-symbolic");
|
||||
g_menu_append_item (section, item);
|
||||
g_object_unref (item);
|
||||
item = g_menu_item_new (_("_Paste"), "context.paste-clipboard");
|
||||
item = g_menu_item_new (_("_Paste"), "clipboard.paste");
|
||||
g_menu_item_set_attribute (item, "touch-icon", "s", "edit-paste-symbolic");
|
||||
g_menu_append_item (section, item);
|
||||
g_object_unref (item);
|
||||
item = g_menu_item_new (_("_Delete"), "context.delete-selection");
|
||||
item = g_menu_item_new (_("_Delete"), "selection.delete");
|
||||
g_menu_item_set_attribute (item, "touch-icon", "s", "edit-delete-symbolic");
|
||||
g_menu_append_item (section, item);
|
||||
g_object_unref (item);
|
||||
@ -8656,12 +8635,12 @@ gtk_text_view_get_menu_model (GtkTextView *text_view)
|
||||
|
||||
section = g_menu_new ();
|
||||
|
||||
item = g_menu_item_new (_("Select _All"), "context.select-all");
|
||||
item = g_menu_item_new (_("Select _All"), "selection.select-all");
|
||||
g_menu_item_set_attribute (item, "touch-icon", "s", "edit-select-all-symbolic");
|
||||
g_menu_append_item (section, item);
|
||||
g_object_unref (item);
|
||||
|
||||
item = g_menu_item_new ( _("Insert _Emoji"), "context.insert-emoji");
|
||||
item = g_menu_item_new ( _("Insert _Emoji"), "misc.insert-emoji");
|
||||
g_menu_item_set_attribute (item, "hidden-when", "s", "action-disabled");
|
||||
g_menu_item_set_attribute (item, "touch-icon", "s", "face-smile-symbolic");
|
||||
g_menu_append_item (section, item);
|
||||
|
137
gtk/gtkwidget.c
137
gtk/gtkwidget.c
@ -501,6 +501,7 @@ struct _GtkWidgetClassPrivate
|
||||
AtkRole accessible_role;
|
||||
const char *css_name;
|
||||
GType layout_manager_type;
|
||||
GPtrArray *actions;
|
||||
};
|
||||
|
||||
enum {
|
||||
@ -11897,14 +11898,16 @@ _gtk_widget_get_action_muxer (GtkWidget *widget,
|
||||
gboolean create)
|
||||
{
|
||||
GtkActionMuxer *muxer;
|
||||
GtkWidgetClass *widget_class = GTK_WIDGET_GET_CLASS (widget);
|
||||
GtkWidgetClassPrivate *priv = widget_class->priv;
|
||||
|
||||
muxer = (GtkActionMuxer*)g_object_get_qdata (G_OBJECT (widget), quark_action_muxer);
|
||||
if (muxer)
|
||||
return muxer;
|
||||
|
||||
if (create)
|
||||
if (create || priv->actions)
|
||||
{
|
||||
muxer = gtk_action_muxer_new ();
|
||||
muxer = gtk_action_muxer_new (widget, priv->actions);
|
||||
g_object_set_qdata_full (G_OBJECT (widget),
|
||||
quark_action_muxer,
|
||||
muxer,
|
||||
@ -13427,3 +13430,133 @@ gtk_widget_should_layout (GtkWidget *widget)
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/*
|
||||
* gtk_widget_class_install_action:
|
||||
* @widget_class: a #GtkWidgetClass
|
||||
* @action_name: a prefixed action name, such as "clipboard.paste"
|
||||
* @activate: callback to use when the action is activated
|
||||
*
|
||||
* This should be called at class initialization time to specify
|
||||
* actions to be added for all instances of this class.
|
||||
*
|
||||
* Actions installed by this function are stateless. The only state
|
||||
* they have is whether they are enabled or not. For more complicated
|
||||
* actions, see gtk_widget_class_install_stateful_action().
|
||||
*/
|
||||
void
|
||||
gtk_widget_class_install_action (GtkWidgetClass *widget_class,
|
||||
const char *action_name,
|
||||
GtkWidgetActionActivateFunc activate)
|
||||
{
|
||||
gtk_widget_class_install_stateful_action (widget_class, action_name, activate,
|
||||
NULL, NULL, NULL);
|
||||
}
|
||||
|
||||
/*
|
||||
* gtk_widget_class_install_stateful_action:
|
||||
* @widget_class: a #GtkWidgetClass
|
||||
* @action_name: a prefixed action name, such as "clipboard.paste"
|
||||
* @activate: callback to use when the action is activated
|
||||
* @parameter_type: (allow-none): the parameter type, or %NULL
|
||||
* @query: (allow-none): callback to use when the action properties
|
||||
are queried, or %NULL for always-enabled stateless actions
|
||||
* @query_state: (allow-none): callback to use when the action state
|
||||
is queried, or %NULL for stateless actions
|
||||
*
|
||||
* This should be called at class initialization time to specify
|
||||
* actions to be added for all instances of this class.
|
||||
*
|
||||
* Actions installed in this way can be simple or stateful.
|
||||
* See the #GAction documentation for more information.
|
||||
*/
|
||||
void
|
||||
gtk_widget_class_install_stateful_action (GtkWidgetClass *widget_class,
|
||||
const char *action_name,
|
||||
GtkWidgetActionActivateFunc activate,
|
||||
const char *parameter_type,
|
||||
GtkWidgetActionSetStateFunc set_state,
|
||||
GtkWidgetActionGetStateFunc get_state)
|
||||
{
|
||||
GtkWidgetClassPrivate *priv = widget_class->priv;
|
||||
GtkWidgetAction *action;
|
||||
|
||||
g_return_if_fail (GTK_IS_WIDGET_CLASS (widget_class));
|
||||
|
||||
if (priv->actions == NULL)
|
||||
priv->actions = g_ptr_array_new ();
|
||||
else if (GTK_IS_WIDGET_CLASS (&widget_class->parent_class))
|
||||
{
|
||||
GtkWidgetClass *parent_class = GTK_WIDGET_CLASS (&widget_class->parent_class);
|
||||
GtkWidgetClassPrivate *parent_priv = parent_class->priv;
|
||||
GPtrArray *parent_actions = parent_priv->actions;
|
||||
|
||||
if (priv->actions == parent_actions)
|
||||
{
|
||||
int i;
|
||||
|
||||
priv->actions = g_ptr_array_new ();
|
||||
for (i = 0; i < parent_actions->len; i++)
|
||||
g_ptr_array_add (priv->actions, g_ptr_array_index (parent_actions, i));
|
||||
}
|
||||
}
|
||||
|
||||
action = g_new0 (GtkWidgetAction, 1);
|
||||
action->name = g_strdup (action_name);
|
||||
action->activate = activate;
|
||||
action->parameter_type = parameter_type ? g_variant_type_new (parameter_type) : NULL;
|
||||
action->set_state = set_state;
|
||||
action->get_state = get_state;
|
||||
|
||||
GTK_NOTE(ACTIONS,
|
||||
g_message ("%sClass: Adding %s action\n",
|
||||
g_type_name (G_TYPE_FROM_CLASS (widget_class)),
|
||||
action_name));
|
||||
|
||||
g_ptr_array_add (priv->actions, action);
|
||||
}
|
||||
|
||||
/**
|
||||
* gtk_widget_action_enabled_changed:
|
||||
* @widget: a #GtkWidget
|
||||
* @action_name: action name, such as "clipboard.paste"
|
||||
* @enabled: whether the action is now enabled
|
||||
*
|
||||
* Notify when an action installed with
|
||||
* gtk_widget_class_install_action() changes its
|
||||
* enabled state.
|
||||
*/
|
||||
void
|
||||
gtk_widget_action_enabled_changed (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
gboolean enabled)
|
||||
{
|
||||
GtkActionMuxer *muxer;
|
||||
|
||||
g_return_if_fail (GTK_IS_WIDGET (widget));
|
||||
|
||||
muxer = _gtk_widget_get_action_muxer (widget, TRUE);
|
||||
gtk_action_muxer_action_enabled_changed (muxer, action_name, enabled);
|
||||
}
|
||||
|
||||
/**
|
||||
* gtk_widget_action_state_changed:
|
||||
* @widget: a #GtkWidget
|
||||
* @action_name: action name, such as "clipboard.paste"
|
||||
* @state: the new state
|
||||
*
|
||||
* Notify when an action installed with
|
||||
* gtk_widget_class_install_stateful_action() changes
|
||||
* its state.
|
||||
*/
|
||||
void
|
||||
gtk_widget_action_state_changed (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *state)
|
||||
{
|
||||
GtkActionMuxer *muxer;
|
||||
|
||||
g_return_if_fail (GTK_IS_WIDGET (widget));
|
||||
|
||||
muxer = _gtk_widget_get_action_muxer (widget, TRUE);
|
||||
gtk_action_muxer_action_state_changed (muxer, action_name, state);
|
||||
}
|
||||
|
@ -1023,6 +1023,76 @@ GDK_AVAILABLE_IN_ALL
|
||||
gboolean gtk_widget_should_layout (GtkWidget *widget);
|
||||
|
||||
|
||||
/**
|
||||
* GtkWidgetActionActivateFunc:
|
||||
* @widget: the widget to which the action belongs
|
||||
* @action_name: the action name
|
||||
* @parameter: parameter for activation
|
||||
*
|
||||
* The type of the callback functions used for activating
|
||||
* actions installed with gtk_widget_class_install_action().
|
||||
*
|
||||
* The @parameter must match the @parameter_type of the action.
|
||||
*/
|
||||
typedef void (* GtkWidgetActionActivateFunc) (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter);
|
||||
|
||||
/**
|
||||
* GtkWidgetActionGetStateFunc:
|
||||
* @widget: the widget to which the action belongs
|
||||
* @action_name: the action name
|
||||
*
|
||||
* The type of the callback functions used to query the state
|
||||
* of stateful actions installed with gtk_widget_class_install_action().
|
||||
*
|
||||
* See the #GAction documentation for more details about the
|
||||
* meaning of these properties.
|
||||
*/
|
||||
typedef GVariant * (* GtkWidgetActionGetStateFunc) (GtkWidget *widget,
|
||||
const char *action_name);
|
||||
|
||||
/**
|
||||
* GtkWidgetActionSetStateFunc:
|
||||
* @widget: the widget to which the action belongs
|
||||
* @action_name: the action name
|
||||
* @state: the new state
|
||||
*
|
||||
* The type of the callback functions used to change the
|
||||
* state of actions installed with gtk_widget_class_install_action().
|
||||
*
|
||||
* The @state must match the @state_type of the action.
|
||||
*
|
||||
* This callback is used when the action state is
|
||||
* changed via the #GActionGroup API.
|
||||
*/
|
||||
typedef void (*GtkWidgetActionSetStateFunc) (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *state);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_widget_class_install_action (GtkWidgetClass *widget_class,
|
||||
const char *action_name,
|
||||
GtkWidgetActionActivateFunc activate);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_widget_class_install_stateful_action (GtkWidgetClass *widget_class,
|
||||
const char *action_name,
|
||||
GtkWidgetActionActivateFunc activate,
|
||||
const char *parameter_type,
|
||||
GtkWidgetActionSetStateFunc set_state,
|
||||
GtkWidgetActionGetStateFunc get_state);
|
||||
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_widget_action_enabled_changed (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
gboolean enabled);
|
||||
GDK_AVAILABLE_IN_ALL
|
||||
void gtk_widget_action_state_changed (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *state);
|
||||
|
||||
|
||||
G_DEFINE_AUTOPTR_CLEANUP_FUNC(GtkWidget, g_object_unref)
|
||||
G_DEFINE_AUTOPTR_CLEANUP_FUNC(GtkRequisition, gtk_requisition_free)
|
||||
|
||||
|
@ -492,6 +492,10 @@ static void gtk_window_on_theme_variant_changed (GtkSettings *settings,
|
||||
#endif
|
||||
static void gtk_window_set_theme_variant (GtkWindow *window);
|
||||
|
||||
static void gtk_window_activate_default_activate (GtkWidget *widget,
|
||||
const char *action_name,
|
||||
GVariant *parameter);
|
||||
|
||||
static void gtk_window_do_popup (GtkWindow *window,
|
||||
GdkEventButton *event);
|
||||
static void gtk_window_style_updated (GtkWidget *widget);
|
||||
@ -1163,6 +1167,9 @@ gtk_window_class_init (GtkWindowClass *klass)
|
||||
* Key bindings
|
||||
*/
|
||||
|
||||
gtk_widget_class_install_action (widget_class, "default.activate",
|
||||
gtk_window_activate_default_activate);
|
||||
|
||||
binding_set = gtk_binding_set_by_class (klass);
|
||||
|
||||
gtk_binding_entry_add_signal (binding_set, GDK_KEY_space, 0,
|
||||
@ -1766,28 +1773,11 @@ gtk_window_capture_motion (GtkWidget *widget,
|
||||
}
|
||||
|
||||
static void
|
||||
activate_default_cb (GSimpleAction *action,
|
||||
GVariant *parameter,
|
||||
gpointer data)
|
||||
gtk_window_activate_default_activate (GtkWidget *widget,
|
||||
const char *name,
|
||||
GVariant *parameter)
|
||||
{
|
||||
gtk_window_real_activate_default (GTK_WINDOW (data));
|
||||
}
|
||||
|
||||
static void
|
||||
add_actions (GtkWindow *window)
|
||||
{
|
||||
GActionEntry entries[] = {
|
||||
{ "activate", activate_default_cb, NULL, NULL, NULL },
|
||||
};
|
||||
|
||||
GActionGroup *actions;
|
||||
|
||||
actions = G_ACTION_GROUP (g_simple_action_group_new ());
|
||||
g_action_map_add_action_entries (G_ACTION_MAP (actions),
|
||||
entries, G_N_ELEMENTS (entries),
|
||||
window);
|
||||
gtk_widget_insert_action_group (GTK_WIDGET (window), "default", actions);
|
||||
g_object_unref (actions);
|
||||
gtk_window_real_activate_default (GTK_WINDOW (widget));
|
||||
}
|
||||
|
||||
static void
|
||||
@ -1879,8 +1869,6 @@ gtk_window_init (GtkWindow *window)
|
||||
g_signal_connect_swapped (priv->key_controller, "focus-out",
|
||||
G_CALLBACK (gtk_window_focus_out), window);
|
||||
gtk_widget_add_controller (widget, priv->key_controller);
|
||||
|
||||
add_actions (window);
|
||||
}
|
||||
|
||||
static GtkGesture *
|
||||
|
Loading…
Reference in New Issue
Block a user