gtk2/gtk/gtktexttypes.c
Havoc Pennington a4762fbff4 update to reflect text widget changes.
2000-07-25  Havoc Pennington  <hp@redhat.com>

* gtk/testtext.c, gtk/testtextbuffer.c: update to reflect text
widget changes.

* gtk/gtktextview.h: To be consistent with usage of "line"
throughout the API to mean "newline-terminated thingy", change
MOVEMENT_LINE to be MOVEMENT_WRAPPED_LINE, and MOVEMENT_PARAGRAPH
to MOVEMENT_LINE.

(GtkTextView): Add flags for default editability, and whether to
show the cursor. Add functions to get/set that. Add

(gtk_text_view_get_iter_location): new function

* gtk/gtktexttypes.h: Move GtkTextLine typedef from here to
gtktextlayout.h
(g_convert): Add g_convert temporarily, will go in glib in a bit

* gtk/gtktexttagtable.h: include gtktexttag.h, and define
GtkTextTagTableForeach instead of brokenly using GHFunc.
Change gtk_text_tag_table_foreach() so it doesn't use GHFunc.

* gtk/gtktexttagprivate.h: Remove GtkTextStyleValues from here,
moved to public header.

* gtk/gtktexttag.h: Rename the "elide" attribute of tags to
"invisible", since "elide" was a bad name.
(gtk_text_tag_get_priority): Added

(GtkTextStyleValues): put this in public header, along with
functions to use it.

* gtk/gtktextmarkprivate.h: Include more headers, since we no
longer include gtktextbtree.h.

* gtk/gtktextmark.h: Add gtk_text_mark_ref, gtk_text_mark_unref,
gtk_text_mark_deleted

* gtk/gtktextlayout.h: Don't include the "really private" headers,
only buffer/iter. Forward declare GtkTextLIne and GtkTextLineData
to make this possible. Now we only need to install
gtktextlayout.h, not gtktextbtree.h and gtktext*private.h.
(However the Makefile.am isn't changed yet because of the
logistics of merging gtk-hp-patches piecemeal)

* gtk/gtktextiterprivate.h: include btree header, so it compiles;
rename gtk_text_iter_get_line to gtk_text_iter_get_text_line since
gtk_text_iter_get_line is now used in the public API for a
different purpose.

* gtk/gtktextiter.h: Clean up function names to be more
consistent. Always call char offset "offset" and byte index
"index". A "line" is always a line number.

(gtk_text_iter_is_last): new function, more efficient than
the existing way to check
(gtk_text_iter_is_first): new function, also more efficient

(gtk_text_iter_up_lines, gtk_text_iter_down_lines): Remove these

(gtk_text_iter_next_char, gtk_text_iter_prev_char): Renamed from
gtk_text_iter_forward_char, etc.

(gtk_text_iter_forward_to_tag_toggle): Renamed from
forward_find_tag_toggle, since this isn't a linear search

(GtkTextCharPredicate): rename from GtkTextViewCharPredicate

(gtk_text_iter_forward_search, gtk_text_iter_backward_search):
New functions, search for a buffer substring.

* gtk/gtktextbuffer.h: Add fields to store whether a paste is
interactive and default editable (since we need to store that info
until we receive the selection data).

Remove all the _at_char and at_line etc. versions of functions;
only have iterator versions.

Add _interactive() versions of functions, that consider the
editability of text. (FIXME add interactive flag to the
insert/delete signals per Darin's suggestion)

(gtk_text_buffer_get_tag_table): new function, demand-creates the
tag table if necessary

Remove declaration of gtk_text_buffer_get_iter_from_string

(_gtk_text_buffer_get_btree): private/internal function, added.


* gtk/gtktextbtree.h: Remove forward decl of GtkTextLineData.
(gtk_text_line_is_last): new function
2000-07-25 23:59:38 +00:00

232 lines
4.3 KiB
C

#include "gtktexttypes.h"
/*
* Tab array
*/
GtkTextTabArray*
gtk_text_view_tab_array_new(guint size)
{
GtkTextTabArray *array;
array = g_new0(GtkTextTabArray, 1);
array->refcount = 1;
array->numTabs = size;
array->tabs = g_new0(GtkTextTab, size);
return array;
}
void
gtk_text_view_tab_array_ref(GtkTextTabArray *tab_array)
{
g_return_if_fail(tab_array != NULL);
tab_array->refcount += 1;
}
void
gtk_text_view_tab_array_unref(GtkTextTabArray *tab_array)
{
g_return_if_fail(tab_array != NULL);
g_return_if_fail(tab_array->refcount > 0);
tab_array->refcount -= 1;
if (tab_array->refcount == 0)
{
g_free(tab_array->tabs);
g_free(tab_array);
}
}
/* These are used to represent embedded non-character objects
* if you return a string representation of a text buffer
*/
const gunichar gtk_text_unknown_char = 0xFFFD;
const gchar gtk_text_unknown_char_utf8[] = { 0xEF, 0xBF, 0xBD, '\0' };
static inline gboolean
inline_byte_begins_utf8_char(const gchar *byte)
{
return ((*byte & 0xC0) != 0x80);
}
gboolean
gtk_text_byte_begins_utf8_char(const gchar *byte)
{
return inline_byte_begins_utf8_char(byte);
}
guint
gtk_text_utf_to_latin1_char(const gchar *p, guchar *l1_ch)
{
guint charlen;
gunichar ch;
g_assert(inline_byte_begins_utf8_char(p));
charlen = g_utf8_next_char (p) - p;
ch = g_utf8_get_char (p);
g_assert(ch != '\0');
if (ch > 0xff)
*l1_ch = '?';
else
*l1_ch = ch;
return charlen;
}
gchar*
gtk_text_utf_to_latin1(const gchar *p, gint len)
{
GString *str;
guint i;
gchar *retval;
str = g_string_new("");
i = 0;
while (i < len)
{
guchar ch;
guint charlen;
charlen = gtk_text_utf_to_latin1_char(p+i, &ch);
g_string_append_c(str, ch);
i += charlen;
}
retval = str->str;
g_string_free(str, FALSE);
return retval;
}
gchar*
gtk_text_latin1_to_utf (const gchar *latin1, gint len)
{
gint i;
GString *retval;
gchar *str;
retval = g_string_new("");
i = 0;
while (i < len)
{
gchar utf[7];
gint count;
count = g_unichar_to_utf8 ((guchar)latin1[i], utf);
utf[count] = '\0';
g_string_append(retval, utf);
++i;
}
str = retval->str;
g_string_free(retval, FALSE);
return str;
}
#include <iconv.h>
#include <errno.h>
#include <string.h>
gchar*
g_convert (const gchar *str,
gint len,
const gchar *to_codeset,
const gchar *from_codeset,
gint *bytes_converted)
{
gchar *dest;
gchar *outp;
const gchar *p;
size_t inbytes_remaining;
size_t outbytes_remaining;
size_t err;
iconv_t cd;
size_t outbuf_size;
g_return_val_if_fail (str != NULL, NULL);
g_return_val_if_fail (to_codeset != NULL, NULL);
g_return_val_if_fail (from_codeset != NULL, NULL);
cd = iconv_open (to_codeset, from_codeset);
if (cd == (iconv_t) -1)
{
/* Something went wrong. */
if (errno == EINVAL)
g_warning ("Conversion from character set `%s' to `%s' is not supported",
from_codeset, to_codeset);
else
g_warning ("Failed to convert character set `%s' to `%s': %s",
from_codeset, to_codeset, strerror (errno));
if (bytes_converted)
*bytes_converted = 0;
return NULL;
}
if (len < 0)
len = strlen (str);
p = str;
inbytes_remaining = len;
outbuf_size = len + 1; /* + 1 for nul in case len == 1 */
outbytes_remaining = outbuf_size - 1; /* -1 for nul */
outp = dest = g_malloc (outbuf_size);
again:
err = iconv (cd, &p, &inbytes_remaining, &outp, &outbytes_remaining);
if (err == (size_t) -1)
{
if (errno == E2BIG)
{
size_t used = outp - dest;
outbuf_size *= 2;
dest = g_realloc (dest, outbuf_size);
outp = dest + used;
outbytes_remaining = outbuf_size - used - 1; /* -1 for nul */
goto again;
}
else
g_warning ("iconv() failed: %s", strerror (errno));
}
*outp = '\0';
if (iconv_close (cd) != 0)
g_warning ("Failed to close iconv() conversion descriptor: %s",
strerror (errno));
if (bytes_converted)
*bytes_converted = p - str;
if (p == str)
{
g_free (dest);
return NULL;
}
else
return dest;
}