diff options
author | Havoc Pennington <hp@redhat.com> | 2001-10-03 20:29:55 +0000 |
---|---|---|
committer | Havoc Pennington <hp@src.gnome.org> | 2001-10-03 20:29:55 +0000 |
commit | 07458e1e02c9a2b935d2dae3c2f9b59b330a77f5 (patch) | |
tree | d3865a496c6095ea714c1e175b00412c6d83b6be /pango/break.c | |
parent | fcb2ec7803e96f6dc0f859cebc004dcc75584c89 (diff) | |
download | pango-07458e1e02c9a2b935d2dae3c2f9b59b330a77f5.tar.gz |
require one more log attr in the buffer passed in, to account for the end
2001-10-03 Havoc Pennington <hp@redhat.com>
* pango/break.c (pango_break)
(pango_default_break) (pango_get_log_attrs): require one more
log attr in the buffer passed in, to account for the end position
(pango_default_break): allow length of -1
* pango/pango-engine.h (struct _PangoEngineLang): change
script_break virtual function to match pango_break
* pango/pango-layout.c (get_items_log_attrs): update pango_break usage
Diffstat (limited to 'pango/break.c')
-rw-r--r-- | pango/break.c | 69 |
1 files changed, 54 insertions, 15 deletions
diff --git a/pango/break.c b/pango/break.c index de898895..342a94a8 100644 --- a/pango/break.c +++ b/pango/break.c @@ -364,7 +364,7 @@ typedef enum /** * pango_default_break: * @text: text to break - * @length: length of text in bytes + * @length: length of text in bytes (or -1 is allowed if text is nul-terminated) * @analysis: a #PangoAnalysis for the text * @attrs: logical attributes to fill in * @@ -381,8 +381,9 @@ void pango_default_break (const gchar *text, gint length, PangoAnalysis *analysis, - PangoLogAttr *attrs) -{ + PangoLogAttr *attrs, + int attrs_len) +{ /* The rationale for all this is in section 5.15 of the Unicode 3.0 book */ /* This is a default break implementation that should work for nearly all @@ -393,8 +394,8 @@ pango_default_break (const gchar *text, * before we start, and then never assign FALSE to anything */ - const gchar *next = text; - const gchar *end = text + length; + const gchar *next; + const gchar *end; gint i = 0; gunichar prev_wc; gunichar next_wc; @@ -413,6 +414,12 @@ pango_default_break (const gchar *text, g_return_if_fail (text != NULL); g_return_if_fail (attrs != NULL); + + if (length < 0) + length = strlen (text); + + next = text; + end = text + length; if (next == end) return; @@ -433,12 +440,27 @@ pango_default_break (const gchar *text, GUnicodeBreakType break_type; BreakOpportunity break_op; + if (i >= attrs_len) + { + g_warning ("pango_default_break(): the array of PangoLogAttr passed in must have at least N+1 elements, if there are N characters in the text being broken"); + return; + } + wc = next_wc; next = g_utf8_next_char (next); - if (next >= end) - next_wc = 0; + if (next == end) + { + /* This is how we fill in the last element (end position) of the + * attr array - assume there's a newline off the end of @text. + */ + next_wc = '\n'; + } + else if (next > end) + { + next_wc = 0; + } else { next_wc = g_utf8_get_char (next); @@ -1259,7 +1281,8 @@ void pango_break (const gchar *text, gint length, PangoAnalysis *analysis, - PangoLogAttr *attrs) + PangoLogAttr *attrs, + int attrs_len) { g_return_if_fail (text != NULL); g_return_if_fail (analysis != NULL); @@ -1270,9 +1293,9 @@ pango_break (const gchar *text, if (analysis->lang_engine && analysis->lang_engine->script_break) - (* analysis->lang_engine->script_break) (text, length, analysis, attrs); + (* analysis->lang_engine->script_break) (text, length, analysis, attrs, attrs_len); else - pango_default_break (text, length, analysis, attrs); + pango_default_break (text, length, analysis, attrs, attrs_len); } /** @@ -1377,16 +1400,24 @@ pango_find_paragraph_boundary (const gchar *text, * @length: length in bytes of @text * @level: embedding level, or -1 if unknown * @language: language tag - * @log_attrs: array with one PangoLogAttr per character in @text, to be filled in + * @log_attrs: array with one #PangoLogAttr per character in @text, plus one extra, to be filled in + * @attrs_len: length of @log_attrs array * - * Computes a PangoLogAttr for each character in @text + * Computes a PangoLogAttr for each character in @text. The @log_attrs + * array must have one #PangoLogAttr for each position in @text; if + * @text contains N characters, it has N+1 positions, including the + * last position at the end of the text. @text should be an entire + * paragraph; logical attributes can't be computed without context + * (for example you need to see spaces on either side of a word to know the + * word is a word). */ void pango_get_log_attrs (const char *text, int length, int level, PangoLanguage *language, - PangoLogAttr *log_attrs) + PangoLogAttr *log_attrs, + int attrs_len) { int n_chars; PangoMap *lang_map; @@ -1419,6 +1450,12 @@ pango_get_log_attrs (const char *text, n_chars = g_utf8_strlen (text, length); + if (attrs_len < (n_chars + 1)) + { + g_warning ("pango_get_log_attrs(): length of PangoLogAttr array must be at least the number of chars in the text plus one more for the end position"); + return; + } + lang_map = pango_find_map (language, engine_type_id, render_type_id); range_start = text; @@ -1449,7 +1486,8 @@ pango_get_log_attrs (const char *text, pango_break (range_start, pos - range_start, &analysis, - log_attrs + chars_broken); + log_attrs + chars_broken, + attrs_len - chars_broken); chars_broken += chars_in_range; @@ -1473,6 +1511,7 @@ pango_get_log_attrs (const char *text, pango_break (range_start, end - range_start, &analysis, - log_attrs + chars_broken); + log_attrs + chars_broken, + attrs_len - chars_broken); } |