[gtksourceview/wip/chergert/snippets] make snippet use a queue of chunks w/ embedded list link



commit 6389d5bec948dc008a132c704c1a9bf6e689b3a1
Author: Christian Hergert <chergert redhat com>
Date:   Fri Jan 24 12:47:56 2020 -0800

    make snippet use a queue of chunks w/ embedded list link

 gtksourceview/gtksourcesnippet.c              | 111 ++++++++++++++------------
 gtksourceview/gtksourcesnippetchunk-private.h |  20 +++++
 gtksourceview/gtksourcesnippetchunk.c         |  21 +----
 3 files changed, 85 insertions(+), 67 deletions(-)
---
diff --git a/gtksourceview/gtksourcesnippet.c b/gtksourceview/gtksourcesnippet.c
index ffc7d3d7..f97a8a9d 100644
--- a/gtksourceview/gtksourcesnippet.c
+++ b/gtksourceview/gtksourcesnippet.c
@@ -32,7 +32,8 @@ struct _GtkSourceSnippet
 
        GtkSourceSnippetContext *context;
        GtkTextBuffer           *buffer;
-       GPtrArray               *chunks;
+
+       GQueue                   chunks;
        GtkSourceSnippetChunk   *current_chunk;
 
        GtkTextMark             *mark_begin;
@@ -75,11 +76,13 @@ static void gtk_source_snippet_update_marks (GtkSourceSnippet *snippet);
 static void gtk_source_snippet_update_tags  (GtkSourceSnippet *self);
 
 static inline void
-print_chunk_positions (GtkSourceSnippet *snippet)
+print_chunk_positions (GtkSourceSnippet *self)
 {
-       for (guint i = 0; i < snippet->chunks->len; i++)
+       guint i = 0;
+
+       for (const GList *l = self->chunks.head; l; l = l->next)
        {
-               GtkSourceSnippetChunk *chunk = g_ptr_array_index (snippet->chunks, i);
+               GtkSourceSnippetChunk *chunk = l->data;
                GtkTextIter begin, end;
 
                if (_gtk_source_snippet_chunk_get_bounds (chunk, &begin, &end))
@@ -94,6 +97,8 @@ print_chunk_positions (GtkSourceSnippet *snippet)
                                    real_text);
                        g_free (real_text);
                }
+
+               i++;
        }
 }
 
@@ -101,8 +106,6 @@ static GtkSourceSnippetChunk *
 get_chunk_at_iter (GtkSourceSnippet *self,
                    GtkTextIter      *iter)
 {
-       GtkSourceSnippetChunk *chunk;
-
        g_assert (GTK_SOURCE_IS_SNIPPET (self));
        g_assert (iter != NULL);
 
@@ -117,9 +120,9 @@ get_chunk_at_iter (GtkSourceSnippet *self,
                return self->current_chunk;
        }
 
-       for (guint i = 0; i < self->chunks->len; i++)
+       for (const GList *l = self->chunks.head; l; l = l->next)
        {
-               chunk = g_ptr_array_index (self->chunks, i);
+               GtkSourceSnippetChunk *chunk = l->data;
 
                if (_gtk_source_snippet_chunk_contains (chunk, iter))
                {
@@ -222,14 +225,12 @@ gtk_source_snippet_copy (GtkSourceSnippet *self)
                            "description", self->description,
                            NULL);
 
-       for (guint i = 0; i < self->chunks->len; i++)
+       for (const GList *l = self->chunks.head; l; l = l->next)
        {
-               GtkSourceSnippetChunk *old_chunk;
-               GtkSourceSnippetChunk *new_chunk;
+               GtkSourceSnippetChunk *old_chunk = l->data;
+               GtkSourceSnippetChunk *new_chunk = gtk_source_snippet_chunk_copy (old_chunk);
 
-               old_chunk = g_ptr_array_index (self->chunks, i);
-               new_chunk = gtk_source_snippet_chunk_copy (old_chunk);
-               gtk_source_snippet_add_chunk (ret, new_chunk);
+               gtk_source_snippet_add_chunk (ret, g_steal_pointer (&new_chunk));
        }
 
        return g_steal_pointer (&ret);
@@ -271,7 +272,7 @@ gtk_source_snippet_get_n_chunks (GtkSourceSnippet *self)
 {
        g_return_val_if_fail (GTK_SOURCE_IS_SNIPPET (self), 0);
 
-       return self->chunks->len;
+       return self->chunks.length;
 }
 
 /**
@@ -291,8 +292,8 @@ gtk_source_snippet_get_nth_chunk (GtkSourceSnippet *self,
 {
        g_return_val_if_fail (GTK_SOURCE_IS_SNIPPET (self), 0);
 
-       if (nth < self->chunks->len)
-               return g_ptr_array_index (self->chunks, nth);
+       if (nth < self->chunks.length)
+               return g_queue_peek_nth (&self->chunks, nth);
 
        return NULL;
 }
@@ -529,9 +530,9 @@ _gtk_source_snippet_move_next (GtkSourceSnippet *self)
 
        self->focus_position++;
 
-       for (guint i = 0; i < self->chunks->len; i++)
+       for (const GList *l = self->chunks.head; l; l = l->next)
        {
-               GtkSourceSnippetChunk *chunk = g_ptr_array_index (self->chunks, i);
+               GtkSourceSnippetChunk *chunk = l->data;
 
                if (gtk_source_snippet_chunk_get_focus_position (chunk) == self->focus_position)
                {
@@ -540,9 +541,9 @@ _gtk_source_snippet_move_next (GtkSourceSnippet *self)
                }
        }
 
-       for (guint i = 0; i < self->chunks->len; i++)
+       for (const GList *l = self->chunks.head; l; l = l->next)
        {
-               GtkSourceSnippetChunk *chunk = g_ptr_array_index (self->chunks, i);
+               GtkSourceSnippetChunk *chunk = l->data;
 
                if (gtk_source_snippet_chunk_get_focus_position (chunk) == 0)
                {
@@ -582,9 +583,9 @@ _gtk_source_snippet_move_previous (GtkSourceSnippet *self)
 
        self->focus_position = MAX (1, self->focus_position - 1);
 
-       for (guint i = 0; i < self->chunks->len; i++)
+       for (const GList *l = self->chunks.head; l; l = l->next)
        {
-               GtkSourceSnippetChunk *chunk = g_ptr_array_index (self->chunks, i);
+               GtkSourceSnippetChunk *chunk = l->data;
 
                if (gtk_source_snippet_chunk_get_focus_position (chunk) == self->focus_position)
                {
@@ -603,7 +604,7 @@ gtk_source_snippet_update_context (GtkSourceSnippet *self)
 
        g_return_if_fail (GTK_SOURCE_IS_SNIPPET (self));
 
-       if (self->chunks == NULL || self->chunks->len == 0)
+       if (self->chunks.length == 0)
        {
                return;
        }
@@ -612,9 +613,9 @@ gtk_source_snippet_update_context (GtkSourceSnippet *self)
 
        _gtk_source_snippet_context_emit_changed (context);
 
-       for (guint i = 0; i < self->chunks->len; i++)
+       for (const GList *l = self->chunks.head; l; l = l->next)
        {
-               GtkSourceSnippetChunk *chunk = g_ptr_array_index (self->chunks, i);
+               GtkSourceSnippetChunk *chunk = l->data;
                gint focus_position;
 
                g_assert (GTK_SOURCE_IS_SNIPPET_CHUNK (chunk));
@@ -676,9 +677,9 @@ gtk_source_snippet_update_tags (GtkSourceSnippet *self)
        buffer = gtk_text_mark_get_buffer (self->mark_begin);
        tag = _gtk_source_buffer_get_snippet_focus_tag (GTK_SOURCE_BUFFER (buffer));
 
-       for (guint i = 0; i < self->chunks->len; i++)
+       for (const GList *l = self->chunks.head; l; l = l->next)
        {
-               GtkSourceSnippetChunk *chunk = g_ptr_array_index (self->chunks, i);
+               GtkSourceSnippetChunk *chunk = l->data;
                gint focus_position = gtk_source_snippet_chunk_get_focus_position (chunk);
 
                if (focus_position >= 0)
@@ -725,14 +726,13 @@ _gtk_source_snippet_begin (GtkSourceSnippet *self,
 
        gtk_text_buffer_begin_user_action (buffer);
 
-       for (guint i = 0; i < self->chunks->len; i++)
+       for (const GList *l = self->chunks.head; l; l = l->next)
        {
-               GtkSourceSnippetChunk *chunk;
+               GtkSourceSnippetChunk *chunk = l->data;
                GtkTextMark *begin;
                GtkTextMark *end;
                const gchar *text;
 
-               chunk = g_ptr_array_index (self->chunks, i);
                text = gtk_source_snippet_chunk_get_text (chunk);
 
                begin = gtk_text_buffer_create_mark (buffer, NULL, iter, TRUE);
@@ -779,8 +779,13 @@ gtk_source_snippet_add_chunk (GtkSourceSnippet      *self,
        g_return_if_fail (GTK_SOURCE_IS_SNIPPET (self));
        g_return_if_fail (GTK_SOURCE_IS_SNIPPET_CHUNK (chunk));
        g_return_if_fail (!self->inserted);
+       g_return_if_fail (chunk->link.data != NULL);
+       g_return_if_fail (chunk->link.prev == NULL);
+       g_return_if_fail (chunk->link.next == NULL);
+
+       g_object_ref_sink (chunk);
 
-       g_ptr_array_add (self->chunks, g_object_ref_sink (chunk));
+       g_queue_push_tail_link (&self->chunks, &chunk->link);
 
        gtk_source_snippet_chunk_set_context (chunk, self->context);
 
@@ -834,7 +839,7 @@ gtk_source_snippet_update_marks (GtkSourceSnippet *snippet)
        print_chunk_positions (snippet);
 #endif
 
-       if (snippet->chunks->len == 0)
+       if (snippet->chunks.length == 0)
        {
                return;
        }
@@ -846,10 +851,10 @@ gtk_source_snippet_update_marks (GtkSourceSnippet *snippet)
         * That can happen when text is inserted at the beginning of a chunk as
         * the right gravity mark from the adjacent chunk will be moved.
         */
-       for (guint i = 0; i < snippet->chunks->len - 1; i++)
+       for (const GList *l = snippet->chunks.head; l && l->next; l = l->next)
        {
-               GtkSourceSnippetChunk *chunk = g_ptr_array_index (snippet->chunks, i);
-               GtkSourceSnippetChunk *next = g_ptr_array_index (snippet->chunks, i + 1);
+               GtkSourceSnippetChunk *chunk = l->data;
+               GtkSourceSnippetChunk *next = l->next->data;
                GtkTextIter begin, end;
                GtkTextIter next_begin, next_end;
 
@@ -882,10 +887,10 @@ gtk_source_snippet_update_marks (GtkSourceSnippet *snippet)
         * have adjacent chunks and the gravity keeps the mark in the wrong
         * position relative to other marks.
         */
-       for (guint i = 1; i < snippet->chunks->len; i++)
+       for (const GList *l = g_queue_peek_nth_link (&snippet->chunks, 1); l; l = l->next)
        {
-               GtkSourceSnippetChunk *chunk = g_ptr_array_index (snippet->chunks, i);
-               GtkSourceSnippetChunk *prev = g_ptr_array_index (snippet->chunks, i - 1);
+               GtkSourceSnippetChunk *chunk = l->data;
+               GtkSourceSnippetChunk *prev = l->prev->data;
                GtkTextIter begin, end;
                GtkTextIter prev_begin, prev_end;
 
@@ -918,9 +923,9 @@ gtk_source_snippet_rewrite_updated_chunks (GtkSourceSnippet *self)
 
        current = self->current_chunk;
 
-       for (guint i = 0; i < self->chunks->len; i++)
+       for (const GList *l = self->chunks.head; l; l = l->next)
        {
-               GtkSourceSnippetChunk *chunk = g_ptr_array_index (self->chunks, i);
+               GtkSourceSnippetChunk *chunk = l->data;
                GtkTextIter begin;
                GtkTextIter end;
                const gchar *text;
@@ -948,9 +953,11 @@ gtk_source_snippet_rewrite_updated_chunks (GtkSourceSnippet *self)
                g_free (real_text);
        }
 
-       guint pos;
-       if (g_ptr_array_find (self->chunks, current, &pos))
-               g_print ("!!!! reseting current chunk to %d\n", pos);
+       if (current)
+               g_print ("!!!! reseting current chunk to %d\n",
+                        g_list_position (self->chunks.head, &current->link));
+       else
+               g_print ("!!!! clearing current chunk\n");
 
        self->current_chunk = current;
 }
@@ -1120,13 +1127,12 @@ gtk_source_snippet_get_context (GtkSourceSnippet *self)
 
        if (self->context == NULL)
        {
-               GtkSourceSnippetChunk *chunk;
-
                self->context = gtk_source_snippet_context_new ();
 
-               for (guint i = 0; i < self->chunks->len; i++)
+               for (const GList *l = self->chunks.head; l; l = l->next)
                {
-                       chunk = g_ptr_array_index (self->chunks, i);
+                       GtkSourceSnippetChunk *chunk = l->data;
+
                        gtk_source_snippet_chunk_set_context (chunk, self->context);
                }
        }
@@ -1151,7 +1157,13 @@ gtk_source_snippet_dispose (GObject *object)
                g_clear_object (&self->mark_end);
        }
 
-       g_clear_pointer (&self->chunks, g_ptr_array_unref);
+       while (self->chunks.length > 0)
+       {
+               GtkSourceSnippetChunk *chunk = self->chunks.head->data;
+
+               g_queue_unlink (&self->chunks, &chunk->link);
+               g_object_unref (chunk);
+       }
 
        g_clear_object (&self->buffer);
        g_clear_object (&self->context);
@@ -1321,7 +1333,6 @@ static void
 gtk_source_snippet_init (GtkSourceSnippet *self)
 {
        self->max_focus_position = -1;
-       self->chunks = g_ptr_array_new_with_free_func (g_object_unref);
 }
 
 gchar *
diff --git a/gtksourceview/gtksourcesnippetchunk-private.h b/gtksourceview/gtksourcesnippetchunk-private.h
index 071b7cbb..473ca506 100644
--- a/gtksourceview/gtksourcesnippetchunk-private.h
+++ b/gtksourceview/gtksourcesnippetchunk-private.h
@@ -23,6 +23,26 @@
 
 G_BEGIN_DECLS
 
+struct _GtkSourceSnippetChunk
+{
+       GInitiallyUnowned        parent_instance;
+
+       GList                    link;
+
+       GtkSourceSnippetContext *context;
+       gchar                   *spec;
+       gchar                   *text;
+       GtkTextMark             *begin_mark;
+       GtkTextMark             *end_mark;
+
+       gulong                   context_changed_handler;
+
+       gint                     focus_position;
+
+       guint                    text_set : 1;
+};
+
+
 GtkTextMark *_gtk_source_snippet_chunk_get_begin_mark (GtkSourceSnippetChunk *chunk);
 void         _gtk_source_snippet_chunk_set_begin_mark (GtkSourceSnippetChunk *chunk,
                                                        GtkTextMark           *end_mark);
diff --git a/gtksourceview/gtksourcesnippetchunk.c b/gtksourceview/gtksourcesnippetchunk.c
index 75cf276e..2412ab73 100644
--- a/gtksourceview/gtksourcesnippetchunk.c
+++ b/gtksourceview/gtksourcesnippetchunk.c
@@ -35,23 +35,6 @@
  * Since: 5.0
  */
 
-struct _GtkSourceSnippetChunk
-{
-       GInitiallyUnowned        parent_instance;
-
-       GtkSourceSnippetContext *context;
-       gchar                   *spec;
-       gchar                   *text;
-       GtkTextMark             *begin_mark;
-       GtkTextMark             *end_mark;
-
-       gulong                   context_changed_handler;
-
-       gint                     focus_position;
-
-       guint                    text_set : 1;
-};
-
 G_DEFINE_TYPE (GtkSourceSnippetChunk, gtk_source_snippet_chunk, G_TYPE_INITIALLY_UNOWNED)
 
 enum {
@@ -274,6 +257,9 @@ gtk_source_snippet_chunk_finalize (GObject *object)
 {
        GtkSourceSnippetChunk *chunk = (GtkSourceSnippetChunk *)object;
 
+       g_assert (chunk->link.prev == NULL);
+       g_assert (chunk->link.next == NULL);
+
        g_clear_pointer (&chunk->begin_mark, delete_and_unref_mark);
        g_clear_pointer (&chunk->end_mark, delete_and_unref_mark);
        g_clear_pointer (&chunk->spec, g_free);
@@ -415,6 +401,7 @@ gtk_source_snippet_chunk_class_init (GtkSourceSnippetChunkClass *klass)
 static void
 gtk_source_snippet_chunk_init (GtkSourceSnippetChunk *chunk)
 {
+       chunk->link.data = chunk;
        chunk->focus_position = -1;
        chunk->spec = g_strdup ("");
 }


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]