shortcuts: Support direction-specific shortcuts
The prime example for direction-dependent shortcuts is using <Alt>Left or <Alt>Right to go back. Support this by adding a direction property to GtkShortcutsShortcut, and filtering by the current text direction. https://bugzilla.gnome.org/show_bug.cgi?id=757888
This commit is contained in:
@@ -114,9 +114,13 @@ gtk_shortcuts_group_get_height (GtkShortcutsGroup *group)
|
||||
children = gtk_container_get_children (GTK_CONTAINER (group));
|
||||
for (l = children; l; l = l->next)
|
||||
{
|
||||
if (GTK_IS_SHORTCUTS_SHORTCUT (l->data))
|
||||
GtkWidget *child = l->data;
|
||||
|
||||
if (!gtk_widget_get_visible (child))
|
||||
continue;
|
||||
else if (GTK_IS_SHORTCUTS_SHORTCUT (child))
|
||||
height += 1;
|
||||
else if (GTK_IS_SHORTCUTS_GESTURE (l->data))
|
||||
else if (GTK_IS_SHORTCUTS_GESTURE (child))
|
||||
height += 2;
|
||||
}
|
||||
g_list_free (children);
|
||||
@@ -164,6 +168,14 @@ gtk_shortcuts_group_get_property (GObject *object,
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_shortcuts_group_direction_changed (GtkWidget *widget,
|
||||
GtkTextDirection previous_dir)
|
||||
{
|
||||
GTK_WIDGET_CLASS (gtk_shortcuts_group_parent_class)->direction_changed (widget, previous_dir);
|
||||
g_object_notify (G_OBJECT (widget), "height");
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_shortcuts_group_set_property (GObject *object,
|
||||
guint prop_id,
|
||||
@@ -209,13 +221,15 @@ gtk_shortcuts_group_finalize (GObject *object)
|
||||
static void
|
||||
gtk_shortcuts_group_class_init (GtkShortcutsGroupClass *klass)
|
||||
{
|
||||
GtkContainerClass *container_class = GTK_CONTAINER_CLASS (klass);
|
||||
GObjectClass *object_class = G_OBJECT_CLASS (klass);
|
||||
GtkWidgetClass *widget_class = GTK_WIDGET_CLASS (klass);
|
||||
GtkContainerClass *container_class = GTK_CONTAINER_CLASS (klass);
|
||||
|
||||
object_class->finalize = gtk_shortcuts_group_finalize;
|
||||
object_class->get_property = gtk_shortcuts_group_get_property;
|
||||
object_class->set_property = gtk_shortcuts_group_set_property;
|
||||
|
||||
widget_class->direction_changed = gtk_shortcuts_group_direction_changed;
|
||||
container_class->add = gtk_shortcuts_group_add;
|
||||
|
||||
/**
|
||||
|
||||
@@ -557,12 +557,18 @@ gtk_shortcuts_section_reflow_groups (GtkShortcutsSection *self)
|
||||
if (n_rows == 0 || n_rows + height > self->max_height)
|
||||
{
|
||||
GtkWidget *column;
|
||||
GtkSizeGroup *group;
|
||||
|
||||
column = gtk_box_new (GTK_ORIENTATION_VERTICAL, 22);
|
||||
gtk_widget_show (column);
|
||||
|
||||
g_object_set_data_full (G_OBJECT (column), "accel-size-group", gtk_size_group_new (GTK_SIZE_GROUP_HORIZONTAL), g_object_unref);
|
||||
g_object_set_data_full (G_OBJECT (column), "title-size-group", gtk_size_group_new (GTK_SIZE_GROUP_HORIZONTAL), g_object_unref);
|
||||
group = gtk_size_group_new (GTK_SIZE_GROUP_HORIZONTAL);
|
||||
gtk_size_group_set_ignore_hidden (group, TRUE);
|
||||
g_object_set_data_full (G_OBJECT (column), "accel-size-group", group, g_object_unref);
|
||||
|
||||
group = gtk_size_group_new (GTK_SIZE_GROUP_HORIZONTAL);
|
||||
gtk_size_group_set_ignore_hidden (group, TRUE);
|
||||
g_object_set_data_full (G_OBJECT (column), "title-size-group", group, g_object_unref);
|
||||
|
||||
if (n_columns % 2 == 0)
|
||||
{
|
||||
@@ -598,14 +604,19 @@ gtk_shortcuts_section_reflow_groups (GtkShortcutsSection *self)
|
||||
if (n_columns % 2 == 1)
|
||||
{
|
||||
GtkWidget *column;
|
||||
GtkSizeGroup *group;
|
||||
GList *content;
|
||||
guint n;
|
||||
|
||||
column = gtk_box_new (GTK_ORIENTATION_VERTICAL, 22);
|
||||
gtk_widget_show (column);
|
||||
|
||||
g_object_set_data_full (G_OBJECT (column), "accel-size-group", gtk_size_group_new (GTK_SIZE_GROUP_HORIZONTAL), g_object_unref);
|
||||
g_object_set_data_full (G_OBJECT (column), "title-size-group", gtk_size_group_new (GTK_SIZE_GROUP_HORIZONTAL), g_object_unref);
|
||||
group = gtk_size_group_new (GTK_SIZE_GROUP_HORIZONTAL);
|
||||
gtk_size_group_set_ignore_hidden (group, TRUE);
|
||||
g_object_set_data_full (G_OBJECT (column), "accel-size-group", group, g_object_unref);
|
||||
group = gtk_size_group_new (GTK_SIZE_GROUP_HORIZONTAL);
|
||||
gtk_size_group_set_ignore_hidden (group, TRUE);
|
||||
g_object_set_data_full (G_OBJECT (column), "title-size-group", group, g_object_unref);
|
||||
|
||||
gtk_container_add (GTK_CONTAINER (current_page), column);
|
||||
|
||||
|
||||
@@ -43,6 +43,8 @@ struct _GtkShortcutsShortcut
|
||||
|
||||
GtkSizeGroup *accel_size_group;
|
||||
GtkSizeGroup *title_size_group;
|
||||
|
||||
GtkTextDirection direction;
|
||||
};
|
||||
|
||||
struct _GtkShortcutsShortcutClass
|
||||
@@ -58,6 +60,7 @@ enum {
|
||||
PROP_TITLE,
|
||||
PROP_ACCEL_SIZE_GROUP,
|
||||
PROP_TITLE_SIZE_GROUP,
|
||||
PROP_DIRECTION,
|
||||
LAST_PROP
|
||||
};
|
||||
|
||||
@@ -105,11 +108,46 @@ gtk_shortcuts_shortcut_get_property (GObject *object,
|
||||
g_value_set_string (value, gtk_shortcut_label_get_accelerator (self->accelerator));
|
||||
break;
|
||||
|
||||
case PROP_DIRECTION:
|
||||
g_value_set_enum (value, self->direction);
|
||||
break;
|
||||
|
||||
default:
|
||||
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
update_visible (GtkShortcutsShortcut *self)
|
||||
{
|
||||
if (self->direction == GTK_TEXT_DIR_NONE ||
|
||||
self->direction == gtk_widget_get_direction (GTK_WIDGET (self)))
|
||||
gtk_widget_set_visible (GTK_WIDGET (self), TRUE);
|
||||
else
|
||||
gtk_widget_set_visible (GTK_WIDGET (self), FALSE);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_shortcuts_shortcut_set_direction (GtkShortcutsShortcut *self,
|
||||
GtkTextDirection direction)
|
||||
{
|
||||
if (self->direction == direction)
|
||||
return;
|
||||
|
||||
self->direction = direction;
|
||||
|
||||
update_visible (self);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_shortcuts_shortcut_direction_changed (GtkWidget *widget,
|
||||
GtkTextDirection previous_dir)
|
||||
{
|
||||
update_visible (GTK_SHORTCUTS_SHORTCUT (widget));
|
||||
|
||||
GTK_WIDGET_CLASS (gtk_shortcuts_shortcut_parent_class)->direction_changed (widget, previous_dir);
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_shortcuts_shortcut_set_property (GObject *object,
|
||||
guint prop_id,
|
||||
@@ -136,6 +174,10 @@ gtk_shortcuts_shortcut_set_property (GObject *object,
|
||||
gtk_shortcuts_shortcut_set_title_size_group (self, GTK_SIZE_GROUP (g_value_get_object (value)));
|
||||
break;
|
||||
|
||||
case PROP_DIRECTION:
|
||||
gtk_shortcuts_shortcut_set_direction (self, g_value_get_enum (value));
|
||||
break;
|
||||
|
||||
default:
|
||||
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
|
||||
break;
|
||||
@@ -169,13 +211,16 @@ gtk_shortcuts_shortcut_child_type (GtkContainer *container)
|
||||
static void
|
||||
gtk_shortcuts_shortcut_class_init (GtkShortcutsShortcutClass *klass)
|
||||
{
|
||||
GtkContainerClass *container_class = GTK_CONTAINER_CLASS (klass);
|
||||
GObjectClass *object_class = G_OBJECT_CLASS (klass);
|
||||
GtkWidgetClass *widget_class = GTK_WIDGET_CLASS (klass);
|
||||
GtkContainerClass *container_class = GTK_CONTAINER_CLASS (klass);
|
||||
|
||||
object_class->finalize = gtk_shortcuts_shortcut_finalize;
|
||||
object_class->get_property = gtk_shortcuts_shortcut_get_property;
|
||||
object_class->set_property = gtk_shortcuts_shortcut_set_property;
|
||||
|
||||
widget_class->direction_changed = gtk_shortcuts_shortcut_direction_changed;
|
||||
|
||||
container_class->add = gtk_shortcuts_shortcut_add;
|
||||
container_class->child_type = gtk_shortcuts_shortcut_child_type;
|
||||
|
||||
@@ -248,6 +293,14 @@ gtk_shortcuts_shortcut_class_init (GtkShortcutsShortcutClass *klass)
|
||||
GTK_TYPE_SIZE_GROUP,
|
||||
(G_PARAM_WRITABLE | G_PARAM_STATIC_STRINGS));
|
||||
|
||||
properties[PROP_DIRECTION] =
|
||||
g_param_spec_enum ("direction",
|
||||
P_("Direction"),
|
||||
P_("Direction"),
|
||||
GTK_TYPE_TEXT_DIRECTION,
|
||||
GTK_TEXT_DIR_NONE,
|
||||
(G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
|
||||
|
||||
g_object_class_install_properties (object_class, LAST_PROP, properties);
|
||||
}
|
||||
|
||||
@@ -257,6 +310,8 @@ gtk_shortcuts_shortcut_init (GtkShortcutsShortcut *self)
|
||||
gtk_orientable_set_orientation (GTK_ORIENTABLE (self), GTK_ORIENTATION_HORIZONTAL);
|
||||
gtk_box_set_spacing (GTK_BOX (self), 12);
|
||||
|
||||
self->direction = GTK_TEXT_DIR_NONE;
|
||||
|
||||
self->accelerator = g_object_new (GTK_TYPE_SHORTCUT_LABEL,
|
||||
"visible", TRUE,
|
||||
NULL);
|
||||
|
||||
@@ -184,6 +184,7 @@ gtk_shortcuts_window_add_search_item (GtkWidget *child, gpointer data)
|
||||
gchar *title = NULL;
|
||||
gchar *hash_key = NULL;
|
||||
GIcon *icon = NULL;
|
||||
GtkTextDirection direction;
|
||||
gchar *str;
|
||||
gchar *keywords;
|
||||
|
||||
@@ -192,6 +193,7 @@ gtk_shortcuts_window_add_search_item (GtkWidget *child, gpointer data)
|
||||
g_object_get (child,
|
||||
"accelerator", &accelerator,
|
||||
"title", &title,
|
||||
"direction", &direction,
|
||||
NULL);
|
||||
|
||||
hash_key = g_strdup_printf ("%s-%s", title, accelerator);
|
||||
@@ -206,9 +208,9 @@ gtk_shortcuts_window_add_search_item (GtkWidget *child, gpointer data)
|
||||
g_hash_table_insert (priv->search_items_hash, hash_key, GINT_TO_POINTER (1));
|
||||
|
||||
item = g_object_new (GTK_TYPE_SHORTCUTS_SHORTCUT,
|
||||
"visible", TRUE,
|
||||
"accelerator", accelerator,
|
||||
"title", title,
|
||||
"direction", direction,
|
||||
"accel-size-group", priv->search_image_group,
|
||||
"title-size-group", priv->search_text_group,
|
||||
NULL);
|
||||
@@ -244,7 +246,6 @@ gtk_shortcuts_window_add_search_item (GtkWidget *child, gpointer data)
|
||||
g_hash_table_insert (priv->search_items_hash, hash_key, GINT_TO_POINTER (1));
|
||||
|
||||
item = g_object_new (GTK_TYPE_SHORTCUTS_GESTURE,
|
||||
"visible", TRUE,
|
||||
"title", title,
|
||||
"subtitle", subtitle,
|
||||
"icon", icon,
|
||||
@@ -379,6 +380,22 @@ gtk_shortcuts_window__list_box__row_activated (GtkShortcutsWindow *self,
|
||||
gtk_widget_hide (GTK_WIDGET (priv->popover));
|
||||
}
|
||||
|
||||
static gboolean
|
||||
hidden_by_direction (GtkWidget *widget)
|
||||
{
|
||||
if (GTK_IS_SHORTCUTS_SHORTCUT (widget))
|
||||
{
|
||||
GtkTextDirection dir;
|
||||
|
||||
g_object_get (widget, "direction", &dir, NULL);
|
||||
if (dir != GTK_TEXT_DIR_NONE &&
|
||||
dir != gtk_widget_get_direction (widget))
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_shortcuts_window__entry__changed (GtkShortcutsWindow *self,
|
||||
GtkSearchEntry *search_entry)
|
||||
@@ -400,6 +417,7 @@ gtk_shortcuts_window__entry__changed (GtkShortcutsWindow *self,
|
||||
{
|
||||
gtk_stack_set_visible_child_name (priv->stack, priv->last_section_name);
|
||||
return;
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@@ -423,7 +441,11 @@ gtk_shortcuts_window__entry__changed (GtkShortcutsWindow *self,
|
||||
const gchar *keywords = value;
|
||||
gboolean match;
|
||||
|
||||
match = strstr (keywords, downcase) != NULL;
|
||||
if (hidden_by_direction (widget))
|
||||
match = FALSE;
|
||||
else
|
||||
match = strstr (keywords, downcase) != NULL;
|
||||
|
||||
gtk_widget_set_visible (widget, match);
|
||||
has_result |= match;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user