From 15ecfbc6effda513ca18e81b419b0eaf02daa0d5 Mon Sep 17 00:00:00 2001 From: hiro Date: Tue, 8 Mar 2005 06:14:33 +0000 Subject: optimized making of clickable URI. git-svn-id: svn://sylpheed.sraoss.jp/sylpheed/trunk@153 ee746299-78ed-0310-b773-934348b2243d --- ChangeLog | 8 ++++++++ ChangeLog.ja | 8 ++++++++ configure.in | 2 +- src/gtkutils.c | 25 +++++++++++++++++++++++++ src/gtkutils.h | 7 +++++++ src/textview.c | 41 ++++++++++++++++++++++------------------- 6 files changed, 71 insertions(+), 20 deletions(-) diff --git a/ChangeLog b/ChangeLog index b89b0ab7..6a8aa8ab 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,11 @@ +2005-03-08 + + * src/textview.c: textview_make_clickable_parts(): optimized the + URI search (fixes freeze at extremely long lines with many '@'). + * src/gtkutils.[ch]: gtkut_text_buffer_insert_with_tag_by_name(): + new. Force linebreak of long lines (> 8190 chars) to prevent the + slowdown of GtkTextView. + 2005-03-07 * src/mainwindow.c diff --git a/ChangeLog.ja b/ChangeLog.ja index 568a0ceb..30acbb69 100644 --- a/ChangeLog.ja +++ b/ChangeLog.ja @@ -1,3 +1,11 @@ +2005-03-08 + + * src/textview.c: textview_make_clickable_parts(): URI 検索を最適化 + (多数の '@' を持つ極端に長い行におけるフリーズを修正)。 + * src/gtkutils.[ch]: gtkut_text_buffer_insert_with_tag_by_name(): + 新規。 GtkTextView の速度低下を防止するために、長い行(> 8190 文字) + で強制的に改行。 + 2005-03-07 * src/mainwindow.c diff --git a/configure.in b/configure.in index f8c2967d..265111f1 100644 --- a/configure.in +++ b/configure.in @@ -9,7 +9,7 @@ MINOR_VERSION=9 MICRO_VERSION=5 INTERFACE_AGE=0 BINARY_AGE=0 -EXTRA_VERSION= +EXTRA_VERSION=+svn VERSION=$MAJOR_VERSION.$MINOR_VERSION.$MICRO_VERSION$EXTRA_VERSION dnl set $target diff --git a/src/gtkutils.c b/src/gtkutils.c index 1047d874..211cd1f5 100644 --- a/src/gtkutils.c +++ b/src/gtkutils.c @@ -556,6 +556,31 @@ gboolean gtkut_text_buffer_find_backward(GtkTextBuffer *buffer, return found; } +#define MAX_TEXT_LINE_LEN 8190 + +void gtkut_text_buffer_insert_with_tag_by_name(GtkTextBuffer *buffer, + GtkTextIter *iter, + const gchar *text, + gint len, + const gchar *tag) +{ + if (len < 0) + len = strlen(text); + + gtk_text_buffer_insert_with_tags_by_name + (buffer, iter, text, len, tag, NULL); + + if (text[len - 1] != '\n') { + /* somehow returns invalid value first (bug?), + so call it twice */ + gtk_text_iter_get_chars_in_line(iter); + if (gtk_text_iter_get_chars_in_line(iter) > MAX_TEXT_LINE_LEN) { + gtk_text_buffer_insert_with_tags_by_name + (buffer, iter, "\n", 1, tag, NULL); + } + } +} + gchar *gtkut_text_view_get_selection(GtkTextView *textview) { GtkTextBuffer *buffer; diff --git a/src/gtkutils.h b/src/gtkutils.h index 959864d6..55cdf957 100644 --- a/src/gtkutils.h +++ b/src/gtkutils.h @@ -150,6 +150,13 @@ gboolean gtkut_text_buffer_find_backward(GtkTextBuffer *buffer, gboolean case_sens, GtkTextIter *match_pos); +void gtkut_text_buffer_insert_with_tag_by_name + (GtkTextBuffer *buffer, + GtkTextIter *iter, + const gchar *text, + gint len, + const gchar *tag); + gchar *gtkut_text_view_get_selection (GtkTextView *textview); void gtkut_window_popup (GtkWidget *window); diff --git a/src/textview.c b/src/textview.c index f31b2483..456ad883 100644 --- a/src/textview.c +++ b/src/textview.c @@ -882,6 +882,9 @@ static void textview_make_clickable_parts(TextView *textview, }; const gint PARSE_ELEMS = sizeof parser / sizeof parser[0]; + /* flags for search optimization */ + gboolean do_search[] = {TRUE, TRUE, TRUE, TRUE, TRUE, TRUE}; + gint n; const gchar *walk, *bp, *ep; @@ -898,20 +901,23 @@ static void textview_make_clickable_parts(TextView *textview, end positions */ for (walk = linebuf, n = 0;;) { gint last_index = PARSE_ELEMS; - gchar *scanpos = NULL; + const gchar *scanpos = NULL; /* FIXME: this looks phony. scanning for anything in the parse table */ for (n = 0; n < PARSE_ELEMS; n++) { - gchar *tmp; - - tmp = parser[n].search(walk, parser[n].needle); - if (tmp) { - if (scanpos == NULL || tmp < scanpos) { - scanpos = tmp; - last_index = n; - } - } + const gchar *tmp; + + if (do_search[n]) { + tmp = parser[n].search(walk, parser[n].needle); + if (tmp) { + if (scanpos == NULL || tmp < scanpos) { + scanpos = tmp; + last_index = n; + } + } else + do_search[n] = FALSE; + } } if (scanpos) { @@ -955,11 +961,11 @@ static void textview_make_clickable_parts(TextView *textview, } if (*normal_text) - gtk_text_buffer_insert_with_tags_by_name - (buffer, &iter, normal_text, -1, fg_tag, NULL); + gtkut_text_buffer_insert_with_tag_by_name + (buffer, &iter, normal_text, -1, fg_tag); } else { - gtk_text_buffer_insert_with_tags_by_name - (buffer, &iter, linebuf, -1, fg_tag, NULL); + gtkut_text_buffer_insert_with_tag_by_name + (buffer, &iter, linebuf, -1, fg_tag); } } @@ -972,7 +978,7 @@ static void textview_write_line(TextView *textview, const gchar *str, GtkTextBuffer *buffer; GtkTextIter iter; gchar buf[BUFFSIZE]; - gchar *fg_color; + gchar *fg_color = NULL; gint quotelevel = -1; gchar quote_tag_str[10]; @@ -986,7 +992,6 @@ static void textview_write_line(TextView *textview, const gchar *str, strcrchomp(buf); //if (prefs_common.conv_mb_alnum) conv_mb_alnum(buf); - fg_color = NULL; /* change color of quotation >, foo>, _> ... ok, , foo bar>, foo-> ... ng @@ -1005,9 +1010,7 @@ static void textview_write_line(TextView *textview, const gchar *str, } } - if (quotelevel == -1) - fg_color = NULL; - else { + if (quotelevel != -1) { g_snprintf(quote_tag_str, sizeof(quote_tag_str), "quote%d", quotelevel); fg_color = quote_tag_str; -- cgit v1.2.3