From cd3c5155d879782a6e6e1d7fa56043e03712b727 Mon Sep 17 00:00:00 2001 From: Jussi Kukkonen Date: Wed, 3 Feb 2010 17:04:38 +0000 Subject: [PATCH] text: implement del_word_next/del_word_prev() Bind ctrl-backspace and ctrl-del to functions that delete a word before or after the cursor, respectively. Selection does not affect the deletion, but current selection is preserved. This mimicks GTK+ functionality in GtkTextView and GtkEntry. http://bugzilla.openedhand.com/show_bug.cgi?id=1767 Signed-off-by: Emmanuele Bassi --- clutter/clutter-text.c | 95 ++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 95 insertions(+) diff --git a/clutter/clutter-text.c b/clutter/clutter-text.c index 7d77f1216..65aa44c70 100644 --- a/clutter/clutter-text.c +++ b/clutter/clutter-text.c @@ -2166,6 +2166,42 @@ clutter_text_real_del_next (ClutterText *self, return TRUE; } +static gboolean +clutter_text_real_del_word_next (ClutterText *self, + const gchar *action, + guint keyval, + ClutterModifierType modifiers) +{ + ClutterTextPrivate *priv = self->priv; + gint pos; + gint len; + + pos = priv->position; + len = priv->n_chars; + + if (len && pos != -1 && pos < len) + { + gint end; + + end = clutter_text_move_word_forward (self, pos); + clutter_text_delete_text (self, pos, end); + + if (priv->selection_bound >= end) + { + gint new_bound; + + new_bound = priv->selection_bound - (end - pos); + clutter_text_set_selection_bound (self, new_bound); + } + else if (priv->selection_bound > pos) + { + clutter_text_set_selection_bound (self, pos); + } + } + + return TRUE; +} + static gboolean clutter_text_real_del_prev (ClutterText *self, const gchar *action, @@ -2201,6 +2237,53 @@ clutter_text_real_del_prev (ClutterText *self, return TRUE; } +static gboolean +clutter_text_real_del_word_prev (ClutterText *self, + const gchar *action, + guint keyval, + ClutterModifierType modifiers) +{ + ClutterTextPrivate *priv = self->priv; + gint pos; + gint len; + + pos = priv->position; + len = priv->n_chars; + + if (pos != 0 && len != 0) + { + gint new_pos; + + if (pos == -1) + { + new_pos = clutter_text_move_word_backward (self, len); + clutter_text_delete_text (self, new_pos, len); + + clutter_text_set_positions (self, -1, -1); + } + else + { + new_pos = clutter_text_move_word_backward (self, pos); + clutter_text_delete_text (self, new_pos, pos); + + clutter_text_set_cursor_position (self, new_pos); + if (priv->selection_bound >= pos) + { + gint new_bound; + + new_bound = priv->selection_bound - (pos - new_pos); + clutter_text_set_selection_bound (self, new_bound); + } + else if (priv->selection_bound >= new_pos) + { + clutter_text_set_selection_bound (self, new_pos); + } + } + } + + return TRUE; +} + static gboolean clutter_text_real_activate (ClutterText *self, const gchar *action, @@ -2814,14 +2897,26 @@ clutter_text_class_init (ClutterTextClass *klass) CLUTTER_Delete, 0, G_CALLBACK (clutter_text_real_del_next), NULL, NULL); + clutter_binding_pool_install_action (binding_pool, "delete-next", + CLUTTER_Delete, CLUTTER_CONTROL_MASK, + G_CALLBACK (clutter_text_real_del_word_next), + NULL, NULL); clutter_binding_pool_install_action (binding_pool, "delete-next", CLUTTER_KP_Delete, 0, G_CALLBACK (clutter_text_real_del_next), NULL, NULL); + clutter_binding_pool_install_action (binding_pool, "delete-next", + CLUTTER_KP_Delete, CLUTTER_CONTROL_MASK, + G_CALLBACK (clutter_text_real_del_word_next), + NULL, NULL); clutter_binding_pool_install_action (binding_pool, "delete-prev", CLUTTER_BackSpace, 0, G_CALLBACK (clutter_text_real_del_prev), NULL, NULL); + clutter_binding_pool_install_action (binding_pool, "delete-prev", + CLUTTER_BackSpace, CLUTTER_CONTROL_MASK, + G_CALLBACK (clutter_text_real_del_word_prev), + NULL, NULL); clutter_binding_pool_install_action (binding_pool, "activate", CLUTTER_Return, 0,