summaryrefslogtreecommitdiff
path: root/src/glibext
diff options
context:
space:
mode:
Diffstat (limited to 'src/glibext')
-rw-r--r--src/glibext/gbufferline.c12
-rw-r--r--src/glibext/gbufferline.h2
-rw-r--r--src/glibext/gbuffersegment.c101
-rw-r--r--src/glibext/gbuffersegment.h6
-rw-r--r--src/glibext/gcodebuffer.c121
-rw-r--r--src/glibext/gcodebuffer.h10
6 files changed, 238 insertions, 14 deletions
diff --git a/src/glibext/gbufferline.c b/src/glibext/gbufferline.c
index ac838b8..0422af5 100644
--- a/src/glibext/gbufferline.c
+++ b/src/glibext/gbufferline.c
@@ -1010,15 +1010,15 @@ GSList *g_buffer_line_highlight_all_same_segments(const GBufferLine *line, GSLis
* *
* Description : Ajoute du texte à formater dans une ligne donnée. *
* *
-* Retour : - *
+* Retour : Portion de texte mis en place, voire NULL. *
* *
* Remarques : - *
* *
******************************************************************************/
-void g_buffer_line_insert_text(GBufferLine *line, BufferLineColumn column, const char *text, size_t length, RenderingTagType type)
+GBufferSegment *g_buffer_line_insert_text(GBufferLine *line, BufferLineColumn column, const char *text, size_t length, RenderingTagType type)
{
- GBufferSegment *segment; /* Portion de texte à ajouter */
+ GBufferSegment *result; /* Portion de texte à renvoyer */
if (length == 0)
return;
@@ -1031,8 +1031,10 @@ void g_buffer_line_insert_text(GBufferLine *line, BufferLineColumn column, const
else
line->last_used = column;
- segment = g_buffer_segment_new(type, text, length);
- g_buffer_line_add_segment(line, column, segment);
+ result = g_buffer_segment_new(type, text, length);
+ g_buffer_line_add_segment(line, column, result);
+
+ return result;
}
diff --git a/src/glibext/gbufferline.h b/src/glibext/gbufferline.h
index bf703ab..3a00ce0 100644
--- a/src/glibext/gbufferline.h
+++ b/src/glibext/gbufferline.h
@@ -122,7 +122,7 @@ GBufferSegment *g_buffer_line_find_near_segment(const GBufferLine *, GBufferSegm
GSList *g_buffer_line_highlight_all_same_segments(const GBufferLine *, GSList *, const GBufferSegment *);
/* Ajoute du texte à formater dans une ligne donnée. */
-void g_buffer_line_insert_text(GBufferLine *, BufferLineColumn, const char *, size_t, RenderingTagType);
+GBufferSegment *g_buffer_line_insert_text(GBufferLine *, BufferLineColumn, const char *, size_t, RenderingTagType);
/* Donne le texte représenté par une ligne de tampon. */
char *g_buffer_line_get_text(const GBufferLine *, BufferLineColumn, BufferLineColumn, bool);
diff --git a/src/glibext/gbuffersegment.c b/src/glibext/gbuffersegment.c
index 27891a8..d25d728 100644
--- a/src/glibext/gbuffersegment.c
+++ b/src/glibext/gbuffersegment.c
@@ -98,6 +98,8 @@ struct _GBufferSegment
{
GObject parent; /* A laisser en premier */
+ GObject *creator; /* Objet à l'origine du segment*/
+
char *text; /* Texte brut conservé */
fnv64_t hash; /* Empreinte pour comparaisons */
@@ -131,6 +133,12 @@ static void g_buffer_segment_class_init(GBufferSegmentClass *);
/* Procède à l'initialisation d'un fragment de texte. */
static void g_buffer_segment_init(GBufferSegment *);
+/* Supprime toutes les références externes. */
+static void g_buffer_segment_dispose(GBufferSegment *);
+
+/* Procède à la libération totale de la mémoire. */
+static void g_buffer_segment_finalize(GBufferSegment *);
+
/* Définit les dernières propriétés de rendu restantes. */
static void g_buffer_segment_prepare(GBufferSegment *, size_t);
@@ -154,6 +162,7 @@ G_DEFINE_TYPE(GBufferSegment, g_buffer_segment, G_TYPE_OBJECT);
static void g_buffer_segment_class_init(GBufferSegmentClass *class)
{
+ GObjectClass *object; /* Autre version de la classe */
GtkStyleContext *context; /* Contexte pour les styles */
GtkWidgetPath *path; /* Chemin d'accès aux thèmes */
gchar *filename; /* Accès à une image 1x1 */
@@ -164,6 +173,11 @@ static void g_buffer_segment_class_init(GBufferSegmentClass *class)
cairo_text_extents_t extents; /* Couverture des caractères */
RenderingTagType i; /* Boucle de parcours */
+ object = G_OBJECT_CLASS(class);
+
+ object->dispose = (GObjectFinalizeFunc/* ! */)g_buffer_segment_dispose;
+ object->finalize = (GObjectFinalizeFunc)g_buffer_segment_finalize;
+
/* Création d'un contexte d'accès */
path = gtk_widget_path_new();
@@ -285,6 +299,47 @@ static void g_buffer_segment_init(GBufferSegment *segment)
/******************************************************************************
* *
+* Paramètres : segment = instance d'objet GLib à traiter. *
+* *
+* Description : Supprime toutes les références externes. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static void g_buffer_segment_dispose(GBufferSegment *segment)
+{
+ if (segment->creator != NULL)
+ g_object_unref(segment->creator);
+
+ G_OBJECT_CLASS(g_buffer_segment_parent_class)->dispose(G_OBJECT(segment));
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : segment = instance d'objet GLib à traiter. *
+* *
+* Description : Procède à la libération totale de la mémoire. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static void g_buffer_segment_finalize(GBufferSegment *segment)
+{
+ G_OBJECT_CLASS(g_buffer_segment_parent_class)->finalize(G_OBJECT(segment));
+
+}
+
+
+/******************************************************************************
+* *
* Paramètres : type = propriétés de la zone de texte. *
* text = chaîne de caractères à traiter. *
* length = quantité de ces caractères. *
@@ -359,6 +414,52 @@ static void g_buffer_segment_prepare(GBufferSegment *segment, size_t length)
/******************************************************************************
* *
+* Paramètres : segment = instance de segment à compléter. *
+* obj = instance GLib quelconque à mémoriser. *
+* *
+* Description : Associe à un segment un objet GLib identifié comme créateur. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+void g_buffer_segment_set_creator(GBufferSegment *segment, GObject *obj)
+{
+ if (segment->creator != NULL)
+ g_object_unref(segment->creator);
+
+ segment->creator = obj;
+ g_object_ref(obj);
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : segment = instance de segment à compléter. *
+* *
+* Description : Renvoie vers un éventuel objet lié en tant que créateur. *
+* *
+* Retour : Instance GLib quelconque ou NULL si aucune référencée. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+GObject *g_buffer_segment_get_creator(const GBufferSegment *segment)
+{
+ if (segment->creator != NULL)
+ g_object_ref(segment->creator);
+
+ return segment->creator;
+
+}
+
+
+/******************************************************************************
+* *
* Paramètres : segment = fragment de texte à consulter. *
* ref = segment de référence servant à la comparaison. *
* *
diff --git a/src/glibext/gbuffersegment.h b/src/glibext/gbuffersegment.h
index ace4e42..51bfb2a 100644
--- a/src/glibext/gbuffersegment.h
+++ b/src/glibext/gbuffersegment.h
@@ -106,6 +106,12 @@ GType g_buffer_segment_get_type(void);
/* Crée un nouveau fragment de texte avec des propriétés. */
GBufferSegment *g_buffer_segment_new(RenderingTagType, const char *, size_t);
+/* Associe à un segment un objet GLib identifié comme créateur. */
+void g_buffer_segment_set_creator(GBufferSegment *, GObject *);
+
+/* Renvoie vers un éventuel objet lié en tant que créateur. */
+GObject *g_buffer_segment_get_creator(const GBufferSegment *);
+
/* Indique si les textes de deux segments sont identiques. */
bool g_buffer_segment_compare(const GBufferSegment *, const GBufferSegment *);
diff --git a/src/glibext/gcodebuffer.c b/src/glibext/gcodebuffer.c
index 4b5378d..ac6e807 100644
--- a/src/glibext/gcodebuffer.c
+++ b/src/glibext/gcodebuffer.c
@@ -145,6 +145,7 @@ struct _GBufferView
GCodeBuffer *buffer; /* Tampon de code visualisé */
vmpa_t start; /* Première ligne intégrée */
vmpa_t end; /* Dernière ligne intégrée */
+ size_t first_index; /* Indice de la première ligne */
gint line_height; /* Hauteur maximale des lignes */
gint max_widths[BLC_COUNT]; /* Taille cachée des colonnes */
@@ -813,6 +814,8 @@ static void g_buffer_view_class_init(GBufferViewClass *class)
static void g_buffer_view_init(GBufferView *buffer)
{
+ buffer->first_index = 0;
+
g_buffer_view_reset_required_height(buffer);
g_buffer_view_reset_required_widths(buffer);
@@ -1156,6 +1159,112 @@ gint g_buffer_view_get_height(const GBufferView *view)
/******************************************************************************
* *
+* Paramètres : view = visualisation à consulter. *
+* x = abscisse comprise dans le segment recherché. [OUT] *
+* y = ordonnée comprise dans la ligne recherchée. *
+* idx = indice de la ligne trouvée ou NULL. [OUT] *
+* display = règles d'affichage des colonnes modulables. *
+* segment = portion de texte recherchée ou NULL. [OUT] *
+* *
+* Description : Fournit la ligne et son segment présents à une position. *
+* *
+* Retour : Ligne retrouvée ou NULL si aucune. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+GBufferLine *g_buffer_view_find_line_and_segment_at(GBufferView *view, gint *x, gint y, size_t *idx, const bool *display, GBufferSegment **segment)
+{
+ GBufferLine *result; /* Ligne trouvée à retourner */
+ gint lheight; /* Hauteur d'une ligne */
+ size_t index; /* Indice attendu */
+
+ /* Recherche d'une ligne correspondante */
+
+ lheight = g_buffer_view_get_line_height(view);
+ index = view->first_index + y / lheight;
+
+ if (idx != NULL)
+ *idx = index;
+
+ result = (index < view->buffer->used ? view->buffer->lines[index] : NULL);
+
+ /* Recherche du segment visé éventuel */
+
+ if (result != NULL && segment != NULL)
+ {
+ if (*x < view->left_text)
+ *segment = NULL;
+
+ else
+ *segment = g_buffer_line_get_segment_at(result, view->max_widths, display, x, GDK_SCROLL_LEFT, true);
+
+ }
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : view = vue de tampon à mettre à jour. *
+* x = abscisse de la zone principale à traiter. *
+* y = ordonnée de la zone principale à traiter. *
+* display = règles d'affichage des colonnes modulables. *
+* caret = position du curseur à construire. [OUT] *
+* *
+* Description : Calcule la position idéale de curseur pour un point donné. *
+* *
+* Retour : Adresse si une a pu être déterminée, NULL sinon. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+const vmpa2t *g_buffer_view_compute_caret(GBufferView *view, gint x, gint y, const bool *display, GdkRectangle *caret)
+{
+ gint remaining; /* Copie de travail modifiable */
+ size_t index; /* Indice de ligne de tampon */
+ GBufferLine *line; /* Ligne à la position courante*/
+ GBufferSegment *segment; /* Segment présent sur la place*/
+
+ remaining = x;
+
+ line = g_buffer_view_find_line_and_segment_at(view, &remaining, y, &index, display, &segment);
+
+ if (line == NULL) return NULL;
+ if (segment == NULL) printf(" -- no segment\n");
+ if (segment == NULL) return NULL;
+
+
+
+
+
+ printf("\n[BASE] tronc = %d reste = %d dernier = %d largeur = %d\n",
+ x - remaining, remaining, g_buffer_segment_get_caret_position(segment, remaining),
+ g_buffer_segment_get_width(segment));
+
+ printf(" '%s'\n", g_buffer_segment_get_text(segment, false));
+
+
+
+
+ caret->x = (x - remaining) + g_buffer_segment_get_caret_position(segment, remaining);
+
+ caret->y = (index - view->first_index) * view->line_height;
+
+ caret->width = 2;
+ caret->height = view->line_height;
+
+ return get_mrange_addr(g_buffer_line_get_range(line));
+
+}
+
+
+/******************************************************************************
+* *
* Paramètres : view = vue de tampon à mettre à jour. *
* line = ligne correspondant à la position. *
* index = indice de cette même ligne dans le tampon. *
@@ -1171,7 +1280,7 @@ gint g_buffer_view_get_height(const GBufferView *view)
* *
******************************************************************************/
-const vmpa2t *g_buffer_view_compute_caret(GBufferView *view, GBufferLine *line, size_t index, gint x, const bool *display, GdkRectangle *caret)
+const vmpa2t *g_buffer_view_compute_caret_old(GBufferView *view, GBufferLine *line, size_t index, gint x, const bool *display, GdkRectangle *caret)
{
gint tmp_x; /* Copie de travail modifiable */
GBufferSegment *segment; /* Segment visé par le pointeur*/
@@ -1428,7 +1537,7 @@ const vmpa2t *g_buffer_view_move_caret(GBufferView *view, GdkRectangle *caret, b
if (index > first)
{
line = view->buffer->lines[index - 1];
- result = g_buffer_view_compute_caret(view, line, index - 1, caret->x, display, caret);
+ result = g_buffer_view_compute_caret_old(view, line, index - 1, caret->x, display, caret);
}
break;
@@ -1438,7 +1547,7 @@ const vmpa2t *g_buffer_view_move_caret(GBufferView *view, GdkRectangle *caret, b
if (index < last)
{
line = view->buffer->lines[index + 1];
- result = g_buffer_view_compute_caret(view, line, index + 1, caret->x, display, caret);
+ result = g_buffer_view_compute_caret_old(view, line, index + 1, caret->x, display, caret);
}
break;
@@ -1453,7 +1562,7 @@ const vmpa2t *g_buffer_view_move_caret(GBufferView *view, GdkRectangle *caret, b
if (!moved && index > first)
{
line = view->buffer->lines[index - 1];
- result = g_buffer_view_compute_caret(view, line, index - 1, INT_MAX, display, caret);
+ result = g_buffer_view_compute_caret_old(view, line, index - 1, INT_MAX, display, caret);
}
break;
@@ -1468,7 +1577,7 @@ const vmpa2t *g_buffer_view_move_caret(GBufferView *view, GdkRectangle *caret, b
if (!moved && index < last)
{
line = view->buffer->lines[index + 1];
- result = g_buffer_view_compute_caret(view, line, index + 1, left_pos, display, caret);
+ result = g_buffer_view_compute_caret_old(view, line, index + 1, left_pos, display, caret);
}
break;
@@ -1486,7 +1595,7 @@ const vmpa2t *g_buffer_view_move_caret(GBufferView *view, GdkRectangle *caret, b
/*
if (result && !computed)
- result = g_buffer_view_compute_caret(view, caret->x, caret->y, caret, display, NULL);
+ result = g_buffer_view_compute_caret_old(view, caret->x, caret->y, caret, display, NULL);
*/
return result;
diff --git a/src/glibext/gcodebuffer.h b/src/glibext/gcodebuffer.h
index 5fd4e7b..e607b9c 100644
--- a/src/glibext/gcodebuffer.h
+++ b/src/glibext/gcodebuffer.h
@@ -128,8 +128,14 @@ gint g_buffer_view_get_width(GBufferView *, const bool *);
/* Fournit la hauteur requise par une visualisation. */
gint g_buffer_view_get_height(const GBufferView *);
+/* Fournit la ligne et son segment présents à une position. */
+GBufferLine *g_buffer_view_find_line_and_segment_at(GBufferView *, gint *, gint, size_t *, const bool *, GBufferSegment **);
+
+/* Calcule la position idéale de curseur pour un point donné. */
+const vmpa2t *g_buffer_view_compute_caret(GBufferView *, gint, gint, const bool *, GdkRectangle *);
+
/* Calcule la position idéale de curseur pour un point donné. */
-const vmpa2t *g_buffer_view_compute_caret(GBufferView *, GBufferLine *, size_t, gint, const bool *, GdkRectangle *);
+const vmpa2t *g_buffer_view_compute_caret_old(GBufferView *, GBufferLine *, size_t, gint, const bool *, GdkRectangle *) __attribute__ ((deprecated));
/* Déplace le curseur au sein d'une vue de tampon. */
const vmpa2t *g_buffer_view_move_caret(GBufferView *, GdkRectangle *, bool, GdkScrollDirection, const bool *);
@@ -147,7 +153,7 @@ void g_buffer_view_draw(const GBufferView *, cairo_t *, gint, gint, const cairo_
void g_buffer_view_export(const GBufferView *, buffer_export_context *, BufferExportType, const bool *);
/* Fournit la ligne présente à une ordonnée donnée. */
-GBufferLine *g_buffer_view_find_line_at(GBufferView *, gint, size_t *);
+GBufferLine *g_buffer_view_find_line_at(GBufferView *, gint, size_t *) __attribute__ ((deprecated));
/* Indique la position d'affichage d'une adresse donnée. */
bool g_buffer_view_get_address_coordinates(GBufferView *, const vmpa2t *, gint *, gint *, bool);