[gtksourceview/wip/chergert/vim: 56/73] implement f and F
- From: Christian Hergert <chergert src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gtksourceview/wip/chergert/vim: 56/73] implement f and F
- Date: Tue, 26 Oct 2021 23:20:37 +0000 (UTC)
commit cb3a7bae8fe927f4c0e8210ff27b48ed8eeff1e5
Author: Christian Hergert <chergert redhat com>
Date: Sat Oct 23 15:09:25 2021 -0700
implement f and F
gtksourceview/vim/gtk-source-vim-motion.c | 191 ++++++++++++++++++++----------
1 file changed, 129 insertions(+), 62 deletions(-)
---
diff --git a/gtksourceview/vim/gtk-source-vim-motion.c b/gtksourceview/vim/gtk-source-vim-motion.c
index b4aa7dcd..abcc6fd7 100644
--- a/gtksourceview/vim/gtk-source-vim-motion.c
+++ b/gtksourceview/vim/gtk-source-vim-motion.c
@@ -25,8 +25,8 @@
#include "gtk-source-vim-motion.h"
-typedef gboolean (*Motion) (GtkTextIter *iter,
- GtkSourceView *view);
+typedef gboolean (*Motion) (GtkTextIter *iter,
+ GtkSourceVimMotion *state);
struct _GtkSourceVimMotion
{
@@ -38,6 +38,9 @@ struct _GtkSourceVimMotion
/* A number for the motion like `3e`. */
int number;
+ /* character for f or F */
+ gunichar f_char;
+
/* Apply the motion when leaving the state. This is useful
* so that you can either capture a motion for future use
* or simply apply it immediately.
@@ -49,6 +52,9 @@ struct _GtkSourceVimMotion
/* If we called gtk_source_vim_motion_bail(). */
guint failed : 1;
+
+ /* If we just did f/F and need another char */
+ guint waiting_for_f_char : 1;
};
G_DEFINE_TYPE (GtkSourceVimMotion, gtk_source_vim_motion, GTK_SOURCE_TYPE_VIM_STATE)
@@ -334,8 +340,8 @@ get_iter_at_visual_column (GtkSourceView *view,
}
static gboolean
-motion_line_start (GtkTextIter *iter,
- GtkSourceView *view)
+motion_line_start (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
if (!gtk_text_iter_starts_line (iter))
{
@@ -347,8 +353,8 @@ motion_line_start (GtkTextIter *iter,
}
static gboolean
-motion_line_first_char (GtkTextIter *iter,
- GtkSourceView *view)
+motion_line_first_char (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
if (!gtk_text_iter_starts_line (iter))
{
@@ -368,8 +374,8 @@ motion_line_first_char (GtkTextIter *iter,
}
static gboolean
-motion_forward_char (GtkTextIter *iter,
- GtkSourceView *view)
+motion_forward_char (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
GtkTextIter begin = *iter;
@@ -387,8 +393,8 @@ motion_forward_char (GtkTextIter *iter,
}
static gboolean
-motion_forward_char_same_line (GtkTextIter *iter,
- GtkSourceView *view)
+motion_forward_char_same_line (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
GtkTextIter begin = *iter;
@@ -403,8 +409,8 @@ motion_forward_char_same_line (GtkTextIter *iter,
}
static gboolean
-motion_backward_char (GtkTextIter *iter,
- GtkSourceView *view)
+motion_backward_char (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
GtkTextIter begin = *iter;
@@ -420,8 +426,8 @@ motion_backward_char (GtkTextIter *iter,
}
static gboolean
-motion_backward_char_same_line (GtkTextIter *iter,
- GtkSourceView *view)
+motion_backward_char_same_line (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
if (!gtk_text_iter_starts_line (iter))
{
@@ -432,8 +438,8 @@ motion_backward_char_same_line (GtkTextIter *iter,
}
static gboolean
-motion_prev_line (GtkTextIter *iter,
- GtkSourceView *view)
+motion_prev_line (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
guint line = gtk_text_iter_get_line (iter);
@@ -450,8 +456,8 @@ motion_prev_line (GtkTextIter *iter,
}
static gboolean
-motion_next_line (GtkTextIter *iter,
- GtkSourceView *view)
+motion_next_line (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
if (!gtk_text_iter_ends_line (iter))
{
@@ -462,17 +468,18 @@ motion_next_line (GtkTextIter *iter,
}
static gboolean
-motion_next_line_first_char (GtkTextIter *iter,
- GtkSourceView *view)
+motion_next_line_first_char (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
- return motion_next_line (iter, view) &&
- motion_line_first_char (iter, view);
+ return motion_next_line (iter, state) &&
+ motion_line_first_char (iter, state);
}
static gboolean
-motion_next_line_visual_column (GtkTextIter *iter,
- GtkSourceView *view)
+motion_next_line_visual_column (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
+ GtkSourceView *view = gtk_source_vim_state_get_view (GTK_SOURCE_VIM_STATE (state));
guint column;
/* TODO: We need a way to persist the visual column across
@@ -481,7 +488,7 @@ motion_next_line_visual_column (GtkTextIter *iter,
*/
column = gtk_source_view_get_visual_column (view, iter);
- if (!motion_next_line (iter, view))
+ if (!motion_next_line (iter, state))
return FALSE;
get_iter_at_visual_column (view, iter, column);
@@ -490,9 +497,10 @@ motion_next_line_visual_column (GtkTextIter *iter,
}
static gboolean
-motion_prev_line_visual_column (GtkTextIter *iter,
- GtkSourceView *view)
+motion_prev_line_visual_column (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
+ GtkSourceView *view = gtk_source_vim_state_get_view (GTK_SOURCE_VIM_STATE (state));
guint column;
/* TODO: We need a way to persist the visual column across
@@ -501,7 +509,7 @@ motion_prev_line_visual_column (GtkTextIter *iter,
*/
column = gtk_source_view_get_visual_column (view, iter);
- if (!motion_prev_line (iter, view))
+ if (!motion_prev_line (iter, state))
return FALSE;
get_iter_at_visual_column (view, iter, column);
@@ -510,8 +518,8 @@ motion_prev_line_visual_column (GtkTextIter *iter,
}
static gboolean
-motion_line_end (GtkTextIter *iter,
- GtkSourceView *view)
+motion_line_end (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
GtkTextIter begin = *iter;
@@ -523,8 +531,8 @@ motion_line_end (GtkTextIter *iter,
}
static gboolean
-motion_last_line_first_char (GtkTextIter *iter,
- GtkSourceView *view)
+motion_last_line_first_char (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
gtk_text_buffer_get_end_iter (gtk_text_iter_get_buffer (iter), iter);
gtk_text_iter_set_line_offset (iter, 0);
@@ -535,9 +543,10 @@ motion_last_line_first_char (GtkTextIter *iter,
}
static gboolean
-motion_screen_top (GtkTextIter *iter,
- GtkSourceView *view)
+motion_screen_top (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
+ GtkSourceView *view = gtk_source_vim_state_get_view (GTK_SOURCE_VIM_STATE (state));
GdkRectangle rect;
gtk_text_view_get_visible_rect (GTK_TEXT_VIEW (view), &rect);
@@ -547,9 +556,10 @@ motion_screen_top (GtkTextIter *iter,
}
static gboolean
-motion_screen_bottom (GtkTextIter *iter,
- GtkSourceView *view)
+motion_screen_bottom (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
+ GtkSourceView *view = gtk_source_vim_state_get_view (GTK_SOURCE_VIM_STATE (state));
GdkRectangle rect;
gtk_text_view_get_visible_rect (GTK_TEXT_VIEW (view), &rect);
@@ -559,9 +569,10 @@ motion_screen_bottom (GtkTextIter *iter,
}
static gboolean
-motion_screen_middle (GtkTextIter *iter,
- GtkSourceView *view)
+motion_screen_middle (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
+ GtkSourceView *view = gtk_source_vim_state_get_view (GTK_SOURCE_VIM_STATE (state));
GdkRectangle rect;
gtk_text_view_get_visible_rect (GTK_TEXT_VIEW (view), &rect);
@@ -571,64 +582,64 @@ motion_screen_middle (GtkTextIter *iter,
}
static gboolean
-motion_forward_word_start (GtkTextIter *iter,
- GtkSourceView *view)
+motion_forward_word_start (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
return forward_classified_start (iter, classify_word_newline_stop);
}
static gboolean
-motion_forward_WORD_start (GtkTextIter *iter,
- GtkSourceView *view)
+motion_forward_WORD_start (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
return forward_classified_start (iter, classify_WORD_newline_stop);
}
static gboolean
-motion_forward_word_end (GtkTextIter *iter,
- GtkSourceView *view)
+motion_forward_word_end (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
return forward_classified_end (iter, classify_word_newline_stop);
}
static gboolean
-motion_forward_WORD_end (GtkTextIter *iter,
- GtkSourceView *view)
+motion_forward_WORD_end (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
return forward_classified_end (iter, classify_WORD_newline_stop);
}
static gboolean
-motion_backward_word_start (GtkTextIter *iter,
- GtkSourceView *view)
+motion_backward_word_start (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
return backward_classified_start (iter, classify_word_newline_stop);
}
static gboolean
-motion_backward_WORD_start (GtkTextIter *iter,
- GtkSourceView *view)
+motion_backward_WORD_start (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
return backward_classified_start (iter, classify_WORD_newline_stop);
}
static gboolean
-motion_backward_word_end (GtkTextIter *iter,
- GtkSourceView *view)
+motion_backward_word_end (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
return backward_classified_end (iter, classify_word_newline_stop);
}
static gboolean
-motion_backward_WORD_end (GtkTextIter *iter,
- GtkSourceView *view)
+motion_backward_WORD_end (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
return backward_classified_end (iter, classify_WORD_newline_stop);
}
static gboolean
-motion_buffer_start (GtkTextIter *iter,
- GtkSourceView *view)
+motion_buffer_start (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
if (!gtk_text_iter_is_start (iter))
{
@@ -640,12 +651,12 @@ motion_buffer_start (GtkTextIter *iter,
}
static gboolean
-motion_buffer_start_first_char (GtkTextIter *iter,
- GtkSourceView *view)
+motion_buffer_start_first_char (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
{
GtkTextIter before = *iter;
- motion_buffer_start (iter, view);
+ motion_buffer_start (iter, state);
while (!gtk_text_iter_ends_line (iter) &&
g_unichar_isspace (gtk_text_iter_get_char (iter)))
@@ -657,6 +668,46 @@ motion_buffer_start_first_char (GtkTextIter *iter,
return !gtk_text_iter_equal (&before, iter);
}
+static gboolean
+motion_f_char (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
+{
+ GtkTextIter before = *iter;
+
+ while (!gtk_text_iter_ends_line (iter))
+ {
+ if (!gtk_text_iter_forward_char (iter))
+ break;
+
+ if (gtk_text_iter_get_char (iter) == state->f_char)
+ return TRUE;
+ }
+
+ *iter = before;
+
+ return FALSE;
+}
+
+static gboolean
+motion_F_char (GtkTextIter *iter,
+ GtkSourceVimMotion *state)
+{
+ GtkTextIter before = *iter;
+
+ while (!gtk_text_iter_starts_line (iter))
+ {
+ if (!gtk_text_iter_backward_char (iter))
+ break;
+
+ if (gtk_text_iter_get_char (iter) == state->f_char)
+ return TRUE;
+ }
+
+ *iter = before;
+
+ return FALSE;
+}
+
GtkSourceVimState *
gtk_source_vim_motion_new (void)
{
@@ -696,6 +747,16 @@ gtk_source_vim_motion_handle_keypress (GtkSourceVimState *state,
g_assert (GTK_SOURCE_IS_VIM_MOTION (self));
+ if (self->waiting_for_f_char)
+ {
+ if (string == NULL || string[0] == 0)
+ return gtk_source_vim_motion_bail (self);
+
+ self->f_char = g_utf8_get_char (string);
+ gtk_source_vim_state_pop (state);
+ return TRUE;
+ }
+
if (self->g_command)
{
switch (keyval)
@@ -818,7 +879,15 @@ gtk_source_vim_motion_handle_keypress (GtkSourceVimState *state,
return gtk_source_vim_motion_complete (self, motion_forward_WORD_end);
case GDK_KEY_f:
+ self->waiting_for_f_char = TRUE;
+ self->motion = motion_f_char;
+ return TRUE;
+
case GDK_KEY_F:
+ self->waiting_for_f_char = TRUE;
+ self->motion = motion_F_char;
+ return TRUE;
+
case GDK_KEY_n:
case GDK_KEY_N:
case GDK_KEY_parenleft:
@@ -920,9 +989,7 @@ gtk_source_vim_motion_apply (GtkSourceVimMotion *self,
do
{
- GtkSourceView *view = gtk_source_vim_state_get_view (GTK_SOURCE_VIM_STATE (self));
-
- if (!self->motion (iter, view))
+ if (!self->motion (iter, self))
{
return FALSE;
}
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]