From cf86d6dbba60e46a3dc3d186bff1f05e2fa76d14 Mon Sep 17 00:00:00 2001
From: Cyrille Bagard <nocbos@gmail.com>
Date: Sun, 17 Jan 2016 20:09:43 +0100
Subject: Updated the width of a modified line.

---
 ChangeLog                 | 12 ++++++++
 src/arch/immediate.c      | 26 ++++++++++--------
 src/glibext/gbufferline.c | 70 +++++++++++++++++++++++++++++++----------------
 src/glibext/gbufferline.h |  3 --
 src/glibext/gcodebuffer.c | 68 +++++++++++++++++++++++++++++++++++++++++++--
 5 files changed, 140 insertions(+), 39 deletions(-)

diff --git a/ChangeLog b/ChangeLog
index 98a2406..c3fcf8f 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,17 @@
 16-01-17  Cyrille Bagard <nocbos@gmail.com>
 
+	* src/arch/immediate.c:
+	Fix a bug: use IMM_MAX_SIZE as limit for snprintf(), not VMPA_MAX_SIZE.
+
+	* src/glibext/gbufferline.c:
+	* src/glibext/gbufferline.h:
+	Update the width of a modified line. Clean the code.
+
+	* src/glibext/gcodebuffer.c:
+	Prepare the update of the whole buffer width by adding a useful function.
+
+16-01-17  Cyrille Bagard <nocbos@gmail.com>
+
 	* src/gtkext/gtkviewpanel.c:
 	Reset output arguments in gtk_view_panel_get_position() in all cases.
 
diff --git a/src/arch/immediate.c b/src/arch/immediate.c
index 288b364..85d98a0 100644
--- a/src/arch/immediate.c
+++ b/src/arch/immediate.c
@@ -915,47 +915,51 @@ size_t g_imm_operand_to_string(const GImmOperand *operand, AsmSyntax syntax, cha
     switch (operand->size)
     {
         case MDS_UNDEFINED:
-            result = snprintf(value, VMPA_MAX_SIZE, "<? undef value ?>");
+            result = snprintf(value, IMM_MAX_SIZE, "<? undef value ?>");
             break;
 
         case MDS_4_BITS_UNSIGNED:
-            result = snprintf(value, VMPA_MAX_SIZE, format, (uint8_t)operand->raw);
+            result = snprintf(value, IMM_MAX_SIZE, format, (uint8_t)operand->raw);
             break;
 
         case MDS_8_BITS_UNSIGNED:
-            result = snprintf(value, VMPA_MAX_SIZE, format, (uint8_t)operand->raw);
+            result = snprintf(value, IMM_MAX_SIZE, format, (uint8_t)operand->raw);
             break;
 
         case MDS_16_BITS_UNSIGNED:
-            result = snprintf(value, VMPA_MAX_SIZE, format, (uint16_t)operand->raw);
+            result = snprintf(value, IMM_MAX_SIZE, format, (uint16_t)operand->raw);
             break;
 
         case MDS_32_BITS_UNSIGNED:
-            result = snprintf(value, VMPA_MAX_SIZE, format, (uint32_t)operand->raw);
+            result = snprintf(value, IMM_MAX_SIZE, format, (uint32_t)operand->raw);
             break;
 
         case MDS_64_BITS_UNSIGNED:
-            result = snprintf(value, VMPA_MAX_SIZE, format, (uint64_t)operand->raw);
+            result = snprintf(value, IMM_MAX_SIZE, format, (uint64_t)operand->raw);
             break;
 
         case MDS_4_BITS_SIGNED:
-            result = snprintf(value, VMPA_MAX_SIZE, format, (int8_t)operand->raw);
+            result = snprintf(value, IMM_MAX_SIZE, format, (int8_t)operand->raw);
             break;
 
         case MDS_8_BITS_SIGNED:
-            result = snprintf(value, VMPA_MAX_SIZE, format, (int8_t)operand->raw);
+            result = snprintf(value, IMM_MAX_SIZE, format, (int8_t)operand->raw);
             break;
 
         case MDS_16_BITS_SIGNED:
-            result = snprintf(value, VMPA_MAX_SIZE, format, (int16_t)operand->raw);
+            result = snprintf(value, IMM_MAX_SIZE, format, (int16_t)operand->raw);
             break;
 
         case MDS_32_BITS_SIGNED:
-            result = snprintf(value, VMPA_MAX_SIZE, format, (int32_t)operand->raw);
+            result = snprintf(value, IMM_MAX_SIZE, format, (int32_t)operand->raw);
             break;
 
         case MDS_64_BITS_SIGNED:
-            result = snprintf(value, VMPA_MAX_SIZE, format, (int64_t)operand->raw);
+            result = snprintf(value, IMM_MAX_SIZE, format, (int64_t)operand->raw);
+            break;
+
+        default:
+            assert(false);
             break;
 
     }
diff --git a/src/glibext/gbufferline.c b/src/glibext/gbufferline.c
index 1a17a9c..d09758f 100644
--- a/src/glibext/gbufferline.c
+++ b/src/glibext/gbufferline.c
@@ -56,6 +56,9 @@ typedef struct _buffer_line_column
 /* Réinitialise une colonne de ligne. */
 static void reset_column(buffer_line_column *);
 
+/* Recalcule la largeur d'une colonne de segments. */
+static void refresh_column_width(buffer_line_column *);
+
 /* Fournit la quantité de pixels requise pour l'impression. */
 static gint get_column_width(const buffer_line_column *);
 
@@ -174,6 +177,30 @@ static void reset_column(buffer_line_column *column)
 
 /******************************************************************************
 *                                                                             *
+*  Paramètres  : column  = colonne de ligne à mettre à jour.                  *
+*                                                                             *
+*  Description : Recalcule la largeur d'une colonne de segments.              *
+*                                                                             *
+*  Retour      : -                                                            *
+*                                                                             *
+*  Remarques   : -                                                            *
+*                                                                             *
+******************************************************************************/
+
+static void refresh_column_width(buffer_line_column *column)
+{
+    size_t i;                               /* Boucle de parcours          */
+
+    column->max_width = 0;
+
+    for (i = 0; i < column->count; i++)
+        column->max_width += g_buffer_segment_get_width(column->segments[i]);
+
+}
+
+
+/******************************************************************************
+*                                                                             *
 *  Paramètres  : column  = colonne de ligne à consulter.                      *
 *                                                                             *
 *  Description : Fournit la quantité de pixels requise pour l'impression.     *
@@ -827,27 +854,6 @@ void g_buffer_line_fill_for_instr(GBufferLine *line, MemoryDataSize psize, Memor
 
 /******************************************************************************
 *                                                                             *
-*  Paramètres  : line    = ligne à venir compléter.                           *
-*                index   = index de la colonne visée par la procédure.        *
-*                segment = fragment de texte à ajouter à la colonne.          *
-*                                                                             *
-*  Description : Ajoute un fragment de texte à une colonne de ligne.          *
-*                                                                             *
-*  Retour      : -                                                            *
-*                                                                             *
-*  Remarques   : -                                                            *
-*                                                                             *
-******************************************************************************/
-
-void g_buffer_line_add_segment(GBufferLine *line, BufferLineColumn index, GBufferSegment *segment)
-{
-    add_segment_to_column(&line->columns[index], segment);
-
-}
-
-
-/******************************************************************************
-*                                                                             *
 *  Paramètres  : line       = ligne à venir consulter.                        *
 *                max_widths = largeurs de colonne à respecter.                *
 *                display    = règles d'affichage des colonnes modulables.     *
@@ -1190,7 +1196,24 @@ GBufferSegment *g_buffer_line_find_segment_from_creator(const GBufferLine *line,
 
 static void on_line_segment_changed(GBufferSegment *segment, GBufferLine *line)
 {
-    g_signal_emit_by_name(line, "content-changed");
+    BufferLineColumn i;                     /* Boucle de parcours          */
+    buffer_line_column *column;
+
+    /* Actualisation de la largeur de la colonne */
+
+    for (i = 0; i < BLC_COUNT; i++)
+    {
+        column = &line->columns[i];
+
+        if (column_has_segment(column, segment, NULL))
+        {
+            refresh_column_width(column);
+            break;
+        }
+
+    }
+
+    g_signal_emit_by_name(line, "content-changed", segment);
 
 }
 
@@ -1226,7 +1249,8 @@ GBufferSegment *g_buffer_line_insert_text(GBufferLine *line, BufferLineColumn co
         line->last_used = column;
 
     result = g_buffer_segment_new(type, text, length);
-    g_buffer_line_add_segment(line, column, result);
+
+    add_segment_to_column(&line->columns[column], result);
 
     g_signal_connect(result, "content-changed", G_CALLBACK(on_line_segment_changed), line);
 
diff --git a/src/glibext/gbufferline.h b/src/glibext/gbufferline.h
index 13ba87b..643e899 100644
--- a/src/glibext/gbufferline.h
+++ b/src/glibext/gbufferline.h
@@ -113,9 +113,6 @@ void g_buffer_line_fill_mrange(GBufferLine *, MemoryDataSize, MemoryDataSize);
 /* Construit le tronc commun d'une ligne d'instruction. */
 void g_buffer_line_fill_for_instr(GBufferLine *, MemoryDataSize, MemoryDataSize, const GBinContent *, bool);
 
-/* Ajoute un fragment de texte à une colonne de ligne. */
-void g_buffer_line_add_segment(GBufferLine *, BufferLineColumn, GBufferSegment *) __attribute__ ((deprecated));
-
 /* Donne le segment présent à une abscisse donnée. */
 GBufferSegment *g_buffer_line_get_segment_at(const GBufferLine *, const gint [BLC_COUNT], const bool *, gint *, gint *, GdkScrollDirection, bool);
 
diff --git a/src/glibext/gcodebuffer.c b/src/glibext/gcodebuffer.c
index 1654a72..5644552 100644
--- a/src/glibext/gcodebuffer.c
+++ b/src/glibext/gcodebuffer.c
@@ -135,7 +135,7 @@ static size_t _g_code_buffer_get_index_from_address(const GCodeBuffer *, const v
 static size_t _g_code_buffer_get_index_from_address_new(const GCodeBuffer *, const vmpa2t *, bool);
 
 /* Convertit une adresse en indice de ligne. */
-static size_t g_code_buffer_get_index_from_address(GCodeBuffer *, const vmpa2t *, bool);
+static size_t g_code_buffer_get_index_from_address(const GCodeBuffer *, const vmpa2t *, bool);
 
 /* Actualise les largeurs maximales par groupes de lignes. */
 static void g_code_buffer_update_line_max_widths(const GCodeBuffer *, size_t, size_t);
@@ -149,6 +149,9 @@ static void on_line_flag_flip(GBufferLine *, BufferLineFlags, BufferLineFlags, G
 /* Ajoute une nouvelle ligne à une position donnée. */
 static GBufferLine *g_code_buffer_create_new_line(GCodeBuffer *, size_t, const mrange_t *);
 
+/* Retrouve l'indice associé à une ligne au sein d'un tampon. */
+static size_t g_code_buffer_find_index_by_line(const GCodeBuffer *, const GBufferLine *);
+
 
 
 /* ---------------------- VUE PARTICULIERE D'UN TAMPON DE CODE ---------------------- */
@@ -498,6 +501,15 @@ static size_t _g_code_buffer_get_index_from_address_new(const GCodeBuffer *buffe
     const mrange_t *range;                  /* Couverture d'une ligne      */
 
 
+    /**
+     * FIXME
+     *
+     * Cette fonction ne semble plus avoir d'utilité.
+     *
+     * g_code_buffer_get_index_from_address() semble être un bon remplacement.
+     *
+     */
+
     for (result = 0; result < buffer->used; result++)
     {
         range = g_buffer_line_get_range(buffer->lines[result]);
@@ -556,7 +568,7 @@ static size_t _g_code_buffer_get_index_from_address_new(const GCodeBuffer *buffe
 *                                                                             *
 ******************************************************************************/
 
-static size_t g_code_buffer_get_index_from_address(GCodeBuffer *buffer, const vmpa2t *addr, bool first)
+static size_t g_code_buffer_get_index_from_address(const GCodeBuffer *buffer, const vmpa2t *addr, bool first)
 {
     size_t result;                          /* Indice à retourner          */
     GBufferLine **found;                    /* Renvoi vers une trouvaille  */
@@ -981,6 +993,58 @@ GBufferLine *g_code_buffer_find_line_by_index(const GCodeBuffer *buffer, size_t
 
 /******************************************************************************
 *                                                                             *
+*  Paramètres  : buffer = tampon de lignes à consulter.                       *
+*                line   = ligne dont l'indice est à retrouver.                *
+*                                                                             *
+*  Description : Retrouve l'indice associé à une ligne au sein d'un tampon.   *
+*                                                                             *
+*  Retour      : Indice de l'adresse trouvée, ou le nombre de lignes sinon.   *
+*                                                                             *
+*  Remarques   : -                                                            *
+*                                                                             *
+******************************************************************************/
+
+static size_t g_code_buffer_find_index_by_line(const GCodeBuffer *buffer, const GBufferLine *line)
+{
+    size_t result;                          /* Indice trouvé à retourner   */
+    const mrange_t *range;                  /* Emplacement de la ligne     */
+    const mrange_t *next;                   /* Emplacement suivant         */
+
+    range = g_buffer_line_get_range(line);
+
+    result = g_code_buffer_get_index_from_address(buffer, get_mrange_addr(range), true);
+
+    /**
+     * Comme plusieurs lignes consécutives peuvent avoir la même adresse,
+     * on parcourt les lignes suivantes pour retrouver la ligne recherchée.
+     */
+
+    if (result < buffer->used)
+    {
+        while (buffer->lines[result] != line)
+        {
+            if (++result == buffer->used)
+                break;
+
+            next = g_buffer_line_get_range(buffer->lines[result]);
+
+            if (cmp_vmpa(get_mrange_addr(range), get_mrange_addr(next)) != 0)
+            {
+                result = buffer->used;
+                break;
+            }
+
+        }
+
+    }
+
+    return result;
+
+}
+
+
+/******************************************************************************
+*                                                                             *
 *  Paramètres  : buffer = composant GTK à mettre à jour.                      *
 *                                                                             *
 *  Description : Augmente l'indentation des prochaines lignes.                *
-- 
cgit v0.11.2-87-g4458