[gedit/docstream2: 1/16] Add gedit-document-input-stream and test.
- From: Jesse van den Kieboom <jessevdk src gnome org>
- To: svn-commits-list gnome org
- Cc:
- Subject: [gedit/docstream2: 1/16] Add gedit-document-input-stream and test.
- Date: Sat, 23 Jan 2010 13:30:14 +0000 (UTC)
commit 28b5d00aa3b4eb7f84dbe51b7e83d05de56d39c7
Author: Ignacio Casal Quinteiro <icq gnome org>
Date: Mon Jan 18 20:45:38 2010 +0100
Add gedit-document-input-stream and test.
gedit/Makefile.am | 2 +
gedit/gedit-document-input-stream.c | 320 +++++++++++++++++++++++++++++++++++
gedit/gedit-document-input-stream.h | 65 +++++++
tests/Makefile.am | 3 +
tests/document-input-stream.c | 118 +++++++++++++
5 files changed, 508 insertions(+), 0 deletions(-)
---
diff --git a/gedit/Makefile.am b/gedit/Makefile.am
index 295d0bf..9836e77 100644
--- a/gedit/Makefile.am
+++ b/gedit/Makefile.am
@@ -65,6 +65,7 @@ endif
NOINST_H_FILES = \
gedit-close-button.h \
gedit-dirs.h \
+ gedit-document-input-stream.h \
gedit-document-loader.h \
gedit-document-saver.h \
gedit-documents-panel.h \
@@ -151,6 +152,7 @@ libgedit_la_SOURCES = \
gedit-debug.c \
gedit-dirs.c \
gedit-document.c \
+ gedit-document-input-stream.c \
gedit-document-loader.c \
gedit-gio-document-loader.c \
gedit-document-saver.c \
diff --git a/gedit/gedit-document-input-stream.c b/gedit/gedit-document-input-stream.c
new file mode 100644
index 0000000..73a27eb
--- /dev/null
+++ b/gedit/gedit-document-input-stream.c
@@ -0,0 +1,320 @@
+/*
+ * gedit-document-input-stream.c
+ * This file is part of gedit
+ *
+ * Copyright (C) 2010 - Ignacio Casal Quinteiro
+ *
+ * gedit is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * gedit is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with gedit; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor,
+ * Boston, MA 02110-1301 USA
+ */
+
+
+#include "config.h"
+
+#include <glib.h>
+#include <gio/gio.h>
+#include <string.h>
+
+#include "gedit-document-input-stream.h"
+
+G_DEFINE_TYPE (GeditDocumentInputStream, gedit_document_input_stream, G_TYPE_INPUT_STREAM);
+
+struct _GeditDocumentInputStreamPrivate
+{
+ GtkTextBuffer *buffer;
+ GtkTextMark *pos;
+
+ /* store the trailing line */
+ gchar *line;
+ gsize line_len;
+};
+
+enum
+{
+ PROP_0,
+ PROP_BUFFER
+};
+
+static gssize gedit_document_input_stream_read (GInputStream *stream,
+ void *buffer,
+ gsize count,
+ GCancellable *cancellable,
+ GError **error);
+static gboolean gedit_document_input_stream_close (GInputStream *stream,
+ GCancellable *cancellable,
+ GError **error);
+
+static void
+gedit_document_input_stream_finalize (GObject *object)
+{
+ GeditDocumentInputStream *stream = GEDIT_DOCUMENT_INPUT_STREAM (object);
+
+ g_free (stream->priv->line);
+
+ G_OBJECT_CLASS (gedit_document_input_stream_parent_class)->finalize (object);
+}
+
+static void
+gedit_document_input_stream_dispose (GObject *object)
+{
+ GeditDocumentInputStream *stream = GEDIT_DOCUMENT_INPUT_STREAM (object);
+
+ if (stream->priv->pos != NULL)
+ {
+ gtk_text_buffer_delete_mark (stream->priv->buffer,
+ stream->priv->pos);
+
+ stream->priv->pos = NULL;
+ }
+
+ G_OBJECT_CLASS (gedit_document_input_stream_parent_class)->dispose (object);
+}
+
+static void
+gedit_document_input_stream_set_property (GObject *object,
+ guint prop_id,
+ const GValue *value,
+ GParamSpec *pspec)
+{
+ GeditDocumentInputStream *stream = GEDIT_DOCUMENT_INPUT_STREAM (object);
+
+ switch (prop_id)
+ {
+ case PROP_BUFFER:
+ stream->priv->buffer = GTK_TEXT_BUFFER (g_value_get_object (value));
+ break;
+
+ default:
+ G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
+ break;
+ }
+}
+
+static void
+gedit_document_input_stream_get_property (GObject *object,
+ guint prop_id,
+ GValue *value,
+ GParamSpec *pspec)
+{
+ GeditDocumentInputStream *stream = GEDIT_DOCUMENT_INPUT_STREAM (object);
+
+ switch (prop_id)
+ {
+ case PROP_BUFFER:
+ g_value_set_object (value, stream->priv->buffer);
+ break;
+
+ default:
+ G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
+ break;
+ }
+}
+
+static void
+gedit_document_input_stream_class_init (GeditDocumentInputStreamClass *klass)
+{
+ GObjectClass *gobject_class = G_OBJECT_CLASS (klass);
+ GInputStreamClass *stream_class = G_INPUT_STREAM_CLASS (klass);
+
+ g_type_class_add_private (klass, sizeof (GeditDocumentInputStreamPrivate));
+
+ gobject_class->finalize = gedit_document_input_stream_finalize;
+ gobject_class->dispose = gedit_document_input_stream_dispose;
+ gobject_class->get_property = gedit_document_input_stream_get_property;
+ gobject_class->set_property = gedit_document_input_stream_set_property;
+
+ stream_class->read_fn = gedit_document_input_stream_read;
+ stream_class->close_fn = gedit_document_input_stream_close;
+
+ g_object_class_install_property (gobject_class,
+ PROP_BUFFER,
+ g_param_spec_object ("buffer",
+ "Buffer",
+ "The buffer which is read",
+ GTK_TYPE_TEXT_BUFFER,
+ G_PARAM_READWRITE |
+ G_PARAM_CONSTRUCT_ONLY));
+}
+
+static void
+gedit_document_input_stream_init (GeditDocumentInputStream *stream)
+{
+ stream->priv = G_TYPE_INSTANCE_GET_PRIVATE (stream,
+ GEDIT_TYPE_DOCUMENT_INPUT_STREAM,
+ GeditDocumentInputStreamPrivate);
+
+ stream->priv->line = NULL;
+ stream->priv->line_len = 0;
+ stream->priv->pos = NULL;
+}
+
+/**
+ * gedit_document_input_stream_new:
+ * @buffer: a #GtkTextBuffer
+ *
+ * Reads the data from @buffer.
+ *
+ * Returns: a new #GInputStream to read @buffer
+ */
+GInputStream *
+gedit_document_input_stream_new (GtkTextBuffer *buffer)
+{
+ GeditDocumentInputStream *stream;
+
+ g_return_val_if_fail (GTK_IS_TEXT_BUFFER (buffer), NULL);
+
+ stream = g_object_new (GEDIT_TYPE_DOCUMENT_INPUT_STREAM,
+ "buffer", buffer,
+ NULL);
+
+ return G_INPUT_STREAM (stream);
+}
+
+gsize
+gedit_document_input_stream_get_total_size (GeditDocumentInputStream *stream)
+{
+ g_return_val_if_fail (GEDIT_IS_DOCUMENT_INPUT_STREAM (stream), 0);
+
+ return gtk_text_buffer_get_char_count (stream->priv->buffer);
+}
+
+gsize
+gedit_document_input_stream_tell (GeditDocumentInputStream *stream)
+{
+ GtkTextIter iter;
+
+ g_return_val_if_fail (GEDIT_IS_DOCUMENT_INPUT_STREAM (stream), 0);
+
+ gtk_text_buffer_get_iter_at_mark (stream->priv->buffer,
+ &iter,
+ stream->priv->pos);
+
+ return gtk_text_iter_get_offset (&iter);
+}
+
+static gsize
+read_line (GeditDocumentInputStream *stream,
+ gchar *outbuf,
+ gsize space_left)
+{
+ GtkTextIter start, next, end;
+ gchar *buf;
+ gsize read, bytes;
+
+ gtk_text_buffer_get_iter_at_mark (stream->priv->buffer,
+ &start,
+ stream->priv->pos);
+
+ end = next = start;
+
+ if (gtk_text_iter_is_end (&start))
+ return 0;
+
+ if (!gtk_text_iter_ends_line (&end))
+ gtk_text_iter_forward_line (&end);
+
+ buf = gtk_text_iter_get_slice (&start, &end);
+ bytes = gtk_text_iter_get_bytes_in_line (&start);
+
+ if (bytes > space_left)
+ {
+ gchar *ptr;
+ gint offset;
+
+ ptr = buf;
+
+ while ((ptr - buf) < space_left)
+ ptr = g_utf8_next_char (ptr);
+
+ if ((ptr - buf) > space_left)
+ ptr = g_utf8_prev_char (ptr);
+
+ memcpy (outbuf + read, buf, (ptr - buf));
+ read = (ptr - buf);
+
+ offset = gtk_text_iter_get_line_offset (&start);
+ gtk_text_iter_set_line_offset (&start, offset + read);
+ }
+ else
+ {
+ memcpy (outbuf + read, buf, bytes);
+ read = bytes;
+
+ start = end;
+ }
+
+ g_free (buf);
+
+ gtk_text_buffer_move_mark (stream->priv->buffer,
+ stream->priv->pos,
+ &start);
+
+ return read;
+}
+
+static gssize
+gedit_document_input_stream_read (GInputStream *stream,
+ void *buffer,
+ gsize count,
+ GCancellable *cancellable,
+ GError **error)
+{
+ GeditDocumentInputStream *dstream;
+ gssize space_left, read, n;
+
+ dstream = GEDIT_DOCUMENT_INPUT_STREAM (stream);
+
+ if (g_cancellable_set_error_if_cancelled (cancellable, error))
+ return -1;
+
+ if (dstream->priv->pos == NULL)
+ {
+ GtkTextIter start;
+
+ gtk_text_buffer_get_start_iter (dstream->priv->buffer, &start);
+
+ dstream->priv->pos = gtk_text_mark_new (NULL, TRUE);
+
+ gtk_text_buffer_add_mark (dstream->priv->buffer,
+ dstream->priv->pos,
+ &start);
+ }
+
+ space_left = count;
+ read = 0;
+
+ do
+ {
+ n = read_line (dstream, buffer + read, space_left);
+ read += n;
+ space_left -= n;
+ } while (space_left > 0 && n != 0);
+
+ return read;
+}
+
+static gboolean
+gedit_document_input_stream_close (GInputStream *stream,
+ GCancellable *cancellable,
+ GError **error)
+{
+ GeditDocumentInputStream *dstream = GEDIT_DOCUMENT_INPUT_STREAM (stream);
+
+ g_free (dstream->priv->line);
+ dstream->priv->line = NULL;
+ dstream->priv->line_len = 0;
+
+ return TRUE;
+}
diff --git a/gedit/gedit-document-input-stream.h b/gedit/gedit-document-input-stream.h
new file mode 100644
index 0000000..ec686fa
--- /dev/null
+++ b/gedit/gedit-document-input-stream.h
@@ -0,0 +1,65 @@
+/*
+ * gedit-document-input-stream.h
+ * This file is part of gedit
+ *
+ * Copyright (C) 2010 - Ignacio Casal Quinteiro
+ *
+ * gedit is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * gedit is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with gedit; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor,
+ * Boston, MA 02110-1301 USA
+ */
+
+#ifndef __GEDIT_DOCUMENT_INPUT_STREAM_H__
+#define __GEDIT_DOCUMENT_INPUT_STREAM_H__
+
+#include <gio/gio.h>
+#include <gtk/gtk.h>
+
+G_BEGIN_DECLS
+
+#define GEDIT_TYPE_DOCUMENT_INPUT_STREAM (gedit_document_input_stream_get_type ())
+#define GEDIT_DOCUMENT_INPUT_STREAM(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GEDIT_TYPE_DOCUMENT_INPUT_STREAM, GeditDocumentInputStream))
+#define GEDIT_DOCUMENT_INPUT_STREAM_CONST(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GEDIT_TYPE_DOCUMENT_INPUT_STREAM, GeditDocumentInputStream const))
+#define GEDIT_DOCUMENT_INPUT_STREAM_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GEDIT_TYPE_DOCUMENT_INPUT_STREAM, GeditDocumentInputStreamClass))
+#define GEDIT_IS_DOCUMENT_INPUT_STREAM(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GEDIT_TYPE_DOCUMENT_INPUT_STREAM))
+#define GEDIT_IS_DOCUMENT_INPUT_STREAM_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GEDIT_TYPE_DOCUMENT_INPUT_STREAM))
+#define GEDIT_DOCUMENT_INPUT_STREAM_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GEDIT_TYPE_DOCUMENT_INPUT_STREAM, GeditDocumentInputStreamClass))
+
+typedef struct _GeditDocumentInputStream GeditDocumentInputStream;
+typedef struct _GeditDocumentInputStreamClass GeditDocumentInputStreamClass;
+typedef struct _GeditDocumentInputStreamPrivate GeditDocumentInputStreamPrivate;
+
+struct _GeditDocumentInputStream
+{
+ GInputStream parent;
+
+ GeditDocumentInputStreamPrivate *priv;
+};
+
+struct _GeditDocumentInputStreamClass
+{
+ GInputStreamClass parent_class;
+};
+
+GType gedit_document_input_stream_get_type (void) G_GNUC_CONST;
+
+GInputStream *gedit_document_input_stream_new (GtkTextBuffer *buffer);
+
+gsize gedit_document_input_stream_get_total_size (GeditDocumentInputStream *stream);
+
+gsize gedit_document_input_stream_tell (GeditDocumentInputStream *stream);
+
+G_END_DECLS
+
+#endif /* __GEDIT_DOCUMENT_INPUT_STREAM_H__ */
diff --git a/tests/Makefile.am b/tests/Makefile.am
index 0b5248e..ed07cd4 100644
--- a/tests/Makefile.am
+++ b/tests/Makefile.am
@@ -8,3 +8,6 @@ TEST_PROGS = smart-converter
smart_converter_SOURCES = smart-converter.c
smart_converter_LDADD = $(progs_ldadd)
+TEST_PROGS += document-input-stream
+document_input_stream_SOURCES = document-input-stream.c
+document_input_stream_LDADD = $(progs_ldadd)
diff --git a/tests/document-input-stream.c b/tests/document-input-stream.c
new file mode 100644
index 0000000..5af9a44
--- /dev/null
+++ b/tests/document-input-stream.c
@@ -0,0 +1,118 @@
+/*
+ * document-input-stream.c
+ * This file is part of gedit
+ *
+ * Copyright (C) 2010 - Ignacio Casal Quinteiro
+ *
+ * gedit is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * gedit is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with gedit; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor,
+ * Boston, MA 02110-1301 USA
+ */
+
+
+#include "gedit-document-input-stream.h"
+#include <gio/gio.h>
+#include <gtk/gtk.h>
+#include <glib.h>
+#include <string.h>
+
+#define TEXT_TO_TEST "hello this is some text\nsencond line of the text"
+
+static void
+test_single_read ()
+{
+ GtkTextBuffer *buf;
+ GInputStream *in;
+ gsize r;
+ GError *err = NULL;
+ gchar *b;
+
+ buf = gtk_text_buffer_new (NULL);
+
+ gtk_text_buffer_set_text (buf, TEXT_TO_TEST, -1);
+
+ b = g_malloc (200);
+ in = gedit_document_input_stream_new (buf);
+
+ r = g_input_stream_read (in, b, strlen (TEXT_TO_TEST), NULL, &err);
+
+ g_assert_no_error (err);
+
+ g_assert_cmpint (r, >, 0);
+
+ b[strlen (TEXT_TO_TEST)] = '\0';
+
+ g_assert_cmpstr (b, ==, TEXT_TO_TEST);
+}
+
+static void
+test_consecutive_read ()
+{
+ GtkTextBuffer *buf;
+ GInputStream *in;
+ gsize r, n;
+ GError *err = NULL;
+ gchar *b;
+
+ buf = gtk_text_buffer_new (NULL);
+
+ gtk_text_buffer_set_text (buf, TEXT_TO_TEST, -1);
+
+ b = g_malloc (200);
+ in = gedit_document_input_stream_new (buf);
+
+ n = 0;
+
+ do
+ {
+ r = g_input_stream_read (in, b + n, 6, NULL, &err);
+ n += r;
+ g_assert_no_error (err);
+ } while (r != 0);
+
+ g_assert_cmpint (n, >, 0);
+
+ g_assert_cmpstr (b, ==, TEXT_TO_TEST);
+}
+
+static void
+test_size ()
+{
+ GtkTextBuffer *buf;
+ GInputStream *in;
+ gsize size;
+
+ buf = gtk_text_buffer_new (NULL);
+
+ gtk_text_buffer_set_text (buf, TEXT_TO_TEST, -1);
+
+ in = gedit_document_input_stream_new (buf);
+
+ size = gedit_document_input_stream_get_total_size (GEDIT_DOCUMENT_INPUT_STREAM (in));
+
+ g_assert_cmpint (size, ==, strlen (TEXT_TO_TEST));
+}
+
+int main (int argc,
+ char *argv[])
+{
+ g_type_init ();
+ g_test_init (&argc, &argv, NULL);
+
+ g_test_add_func ("/document-input-stream/single_read", test_single_read);
+ g_test_add_func ("/document-input-stream/consecutive_read", test_consecutive_read);
+ g_test_add_func ("/document-input-stream/size", test_size);
+
+ return g_test_run ();
+}
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]