[gitg] Fixed enabling/disabling diff view, showing normal file contents
- From: Jesse van den Kieboom <jessevdk src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gitg] Fixed enabling/disabling diff view, showing normal file contents
- Date: Sun, 30 May 2010 18:19:43 +0000 (UTC)
commit 2a05cbe6df78f50dc80b98d850aad2340c2af8df
Author: Jesse van den Kieboom <jessevdk gnome org>
Date: Sun May 30 20:19:02 2010 +0200
Fixed enabling/disabling diff view, showing normal file contents
gitg/gitg-commit-view.c | 150 ++++++++++++--------
gitg/gitg-diff-view.c | 371 +++++++++++++++++++++++++++++++++++------------
gitg/gitg-runner.c | 8 +-
gitg/gitg-utils.c | 88 ++++++++---
4 files changed, 438 insertions(+), 179 deletions(-)
---
diff --git a/gitg/gitg-commit-view.c b/gitg/gitg-commit-view.c
index f39d553..b2c1c0f 100644
--- a/gitg/gitg-commit-view.c
+++ b/gitg/gitg-commit-view.c
@@ -188,91 +188,118 @@ set_icon_data_func(GitgCommitView *view, GtkTreeView *treeview, GtkCellRenderer
static void
set_language(GitgCommitView *view, GtkSourceLanguage *language)
{
- GtkSourceBuffer *buffer = GTK_SOURCE_BUFFER(gtk_text_view_get_buffer(GTK_TEXT_VIEW(view->priv->changes_view)));
+ GtkTextView *text_view;
+ GtkSourceBuffer *buffer;
- gtk_source_buffer_set_language(buffer, language);
- gitg_diff_view_set_diff_enabled(GITG_DIFF_VIEW(view->priv->changes_view), FALSE);
+ text_view = GTK_TEXT_VIEW (view->priv->changes_view);
+ buffer = GTK_SOURCE_BUFFER (gtk_text_view_get_buffer (text_view));
+
+ gtk_source_buffer_set_language (buffer, language);
+ gitg_diff_view_set_diff_enabled (GITG_DIFF_VIEW (view->priv->changes_view),
+ FALSE);
}
static void
-set_diff_language(GitgCommitView *view)
+set_diff_language (GitgCommitView *view)
{
- GtkSourceLanguageManager *manager = gtk_source_language_manager_get_default();
- GtkSourceLanguage *language = gtk_source_language_manager_get_language(manager, "gitgdiff");
+ GtkSourceLanguageManager *manager = gtk_source_language_manager_get_default ();
+ GtkSourceLanguage *language = gtk_source_language_manager_get_language (manager, "gitgdiff");
- set_language(view, language);
- gitg_diff_view_set_diff_enabled(GITG_DIFF_VIEW(view->priv->changes_view), TRUE);
- gtk_widget_set_sensitive(GTK_WIDGET(view->priv->hscale_context), TRUE);
+ set_language (view, language);
+ gitg_diff_view_set_diff_enabled (GITG_DIFF_VIEW(view->priv->changes_view), TRUE);
+ gtk_widget_set_sensitive (GTK_WIDGET(view->priv->hscale_context), TRUE);
}
static void
-show_binary_information(GitgCommitView *view)
+show_binary_information (GitgCommitView *view)
{
- set_language(view, NULL);
- gtk_widget_set_sensitive(GTK_WIDGET(view->priv->hscale_context), FALSE);
+ set_language (view, NULL);
+
+ gtk_widget_set_sensitive (GTK_WIDGET (view->priv->hscale_context), FALSE);
- gtk_text_buffer_set_text(gtk_text_view_get_buffer(GTK_TEXT_VIEW(view->priv->changes_view)), _("Cannot display file content as text"), -1);
+ gtk_text_buffer_set_text (gtk_text_view_get_buffer (GTK_TEXT_VIEW (view->priv->changes_view)),
+ _("Cannot display file content as text"),
+ -1);
}
static void
-on_changes_update(GitgRunner *runner, gchar **buffer, GitgCommitView *view)
+on_changes_update (GitgRunner *runner, gchar **buffer, GitgCommitView *view)
{
gchar *line;
- GtkTextBuffer *buf = gtk_text_view_get_buffer(GTK_TEXT_VIEW(view->priv->changes_view));
+ GtkTextBuffer *buf = gtk_text_view_get_buffer (GTK_TEXT_VIEW(view->priv->changes_view));
GtkTextIter iter;
- gtk_text_buffer_get_end_iter(buf, &iter);
+ gtk_text_buffer_get_end_iter (buf, &iter);
while ((line = *(buffer++)))
{
- if (view->priv->is_diff && g_str_has_prefix(line, "@@"))
+ if (view->priv->is_diff && g_str_has_prefix (line, "@@"))
{
if (view->priv->current_changes & GITG_CHANGED_FILE_CHANGES_UNSTAGED)
- gtk_source_buffer_create_source_mark(GTK_SOURCE_BUFFER(buf), NULL, CATEGORY_STAGE_HUNK, &iter);
+ {
+ gtk_source_buffer_create_source_mark (GTK_SOURCE_BUFFER(buf),
+ NULL,
+ CATEGORY_STAGE_HUNK,
+ &iter);
+ }
else
- gtk_source_buffer_create_source_mark(GTK_SOURCE_BUFFER(buf), NULL, CATEGORY_UNSTAGE_HUNK, &iter);
+ {
+ gtk_source_buffer_create_source_mark (GTK_SOURCE_BUFFER(buf),
+ NULL,
+ CATEGORY_UNSTAGE_HUNK,
+ &iter);
+ }
}
- gtk_text_buffer_insert(buf, &iter, line, -1);
- gtk_text_buffer_insert(buf, &iter, "\n", -1);
+ gtk_text_buffer_insert (buf, &iter, line, -1);
+ gtk_text_buffer_insert (buf, &iter, "\n", -1);
}
- if (gtk_source_buffer_get_language(GTK_SOURCE_BUFFER(buf)) == NULL)
+ if (gtk_source_buffer_get_language (GTK_SOURCE_BUFFER(buf)) == NULL)
{
- gchar *content_type = gitg_utils_guess_content_type(GTK_TEXT_BUFFER(buf));
+ gchar *content_type = gitg_utils_guess_content_type (GTK_TEXT_BUFFER(buf));
- if (content_type && !gitg_utils_can_display_content_type(content_type))
+ if (content_type && !gitg_utils_can_display_content_type (content_type))
{
- gitg_runner_cancel(runner);
- show_binary_information(view);
+ gitg_runner_cancel (runner);
+ show_binary_information (view);
}
else if (content_type)
{
- GtkSourceLanguage *language = gitg_utils_get_language(NULL, content_type);
- set_language(view, language);
- gtk_widget_set_sensitive(GTK_WIDGET(view->priv->hscale_context), FALSE);
+ GtkSourceLanguage *language = gitg_utils_get_language (NULL, content_type);
+ set_language (view, language);
+ gtk_widget_set_sensitive (GTK_WIDGET (view->priv->hscale_context), FALSE);
}
- g_free(content_type);
+ g_free (content_type);
}
- while (gtk_events_pending())
- gtk_main_iteration();
+ while (gtk_events_pending ())
+ {
+ gtk_main_iteration ();
+ }
}
static void
-connect_update(GitgCommitView *view)
+connect_update (GitgCommitView *view)
{
- view->priv->update_id = g_signal_connect(view->priv->runner, "update", G_CALLBACK(on_changes_update), view);
+ view->priv->update_id = g_signal_connect (view->priv->runner,
+ "update",
+ G_CALLBACK (on_changes_update),
+ view);
}
static void
-set_current_file(GitgCommitView *view, GitgChangedFile *file, GitgChangedFileChanges changes)
+set_current_file (GitgCommitView *view,
+ GitgChangedFile *file,
+ GitgChangedFileChanges changes)
{
if (view->priv->current_file != NULL)
- g_object_unref(view->priv->current_file);
+ {
+ g_object_unref (view->priv->current_file);
+ }
- view->priv->current_file = file ? g_object_ref(file) : NULL;
+ view->priv->current_file = file ? g_object_ref (file) : NULL;
view->priv->current_changes = changes;
}
@@ -403,63 +430,66 @@ unselect_tree_view(GtkTreeView *view)
}
static void
-unstaged_selection_changed(GtkTreeSelection *selection, GitgCommitView *view)
+unstaged_selection_changed (GtkTreeSelection *selection,
+ GitgCommitView *view)
{
GtkTreeModel *model;
GtkTreeIter iter;
- if (!check_selection(view->priv->tree_view_unstaged, &iter, view))
+ if (!check_selection (view->priv->tree_view_unstaged, &iter, view))
+ {
return;
+ }
- model = gtk_tree_view_get_model(view->priv->tree_view_unstaged);
- unselect_tree_view(view->priv->tree_view_staged);
+ model = gtk_tree_view_get_model (view->priv->tree_view_unstaged);
+ unselect_tree_view (view->priv->tree_view_staged);
GitgChangedFile *file;
- gtk_tree_model_get(model, &iter, COLUMN_FILE, &file, -1);
- GitgChangedFileStatus status = gitg_changed_file_get_status(file);
- GFile *f = gitg_changed_file_get_file(file);
+ gtk_tree_model_get (model, &iter, COLUMN_FILE, &file, -1);
+ GitgChangedFileStatus status = gitg_changed_file_get_status (file);
+ GFile *f = gitg_changed_file_get_file (file);
if (status == GITG_CHANGED_FILE_STATUS_NEW)
{
- gchar *content_type = gitg_utils_get_content_type(f);
+ gchar *content_type = gitg_utils_get_content_type (f);
- if (!gitg_utils_can_display_content_type(content_type))
+ if (!gitg_utils_can_display_content_type (content_type))
{
- show_binary_information(view);
+ show_binary_information (view);
}
else
{
- GInputStream *stream = G_INPUT_STREAM(g_file_read(f, NULL, NULL));
+ GInputStream *stream = G_INPUT_STREAM (g_file_read (f, NULL, NULL));
if (!stream)
{
- show_binary_information(view);
+ show_binary_information (view);
}
else
{
- gchar *basename = g_file_get_basename(f);
- GtkSourceLanguage *language = gitg_utils_get_language(basename, content_type);
- g_free(basename);
+ gchar *basename = g_file_get_basename (f);
+ GtkSourceLanguage *language = gitg_utils_get_language (basename, content_type);
+ g_free (basename);
- set_language(view, language);
- gtk_widget_set_sensitive(GTK_WIDGET(view->priv->hscale_context), FALSE);
+ set_language (view, language);
+ gtk_widget_set_sensitive (GTK_WIDGET (view->priv->hscale_context), FALSE);
view->priv->is_diff = FALSE;
- connect_update(view);
+ connect_update (view);
- gitg_runner_run_stream(view->priv->runner, stream, NULL);
- g_object_unref(stream);
+ gitg_runner_run_stream (view->priv->runner, stream, NULL);
+ g_object_unref (stream);
}
}
- g_free(content_type);
+ g_free (content_type);
}
else
{
- set_diff_language(view);
+ set_diff_language (view);
view->priv->is_diff = TRUE;
- connect_update(view);
+ connect_update (view);
gchar *path = gitg_repository_relative (view->priv->repository, f);
diff --git a/gitg/gitg-diff-view.c b/gitg/gitg-diff-view.c
index db97dc3..ffa9e8f 100644
--- a/gitg/gitg-diff-view.c
+++ b/gitg/gitg-diff-view.c
@@ -46,8 +46,16 @@
#define GITG_DIFF_ITER_SET_REGION(iter, region) ((iter)->userdata2 = region)
#define GITG_DIFF_ITER_SET_VIEW(iter, view) ((iter)->userdata = view)
-static void on_buffer_insert_text(GtkTextBuffer *buffer, GtkTextIter *iter, gchar const *text, gint len, GitgDiffView *view);
-static void on_buffer_delete_range(GtkTextBuffer *buffer, GtkTextIter *start, GtkTextIter *end, GitgDiffView *view);
+static void on_buffer_insert_text (GtkTextBuffer *buffer,
+ GtkTextIter *iter,
+ gchar const *text,
+ gint len,
+ GitgDiffView *view);
+
+static void on_buffer_delete_range (GtkTextBuffer *buffer,
+ GtkTextIter *start,
+ GtkTextIter *end,
+ GitgDiffView *view);
static void
line_renderer_size_func (GtkSourceGutter *gutter,
@@ -60,7 +68,10 @@ line_renderer_data_func (GtkSourceGutter *gutter,
gboolean current_line,
GitgDiffView *view);
-static gboolean on_idle_scan(GitgDiffView *view);
+static void disable_diff_view (GitgDiffView *view);
+static void enable_diff_view (GitgDiffView *view);
+
+static gboolean on_idle_scan (GitgDiffView *view);
/* Signals */
enum
@@ -139,50 +150,53 @@ static gboolean gitg_diff_view_expose(GtkWidget *widget, GdkEventExpose *event);
static guint diff_view_signals[NUM_SIGNALS] = {0,};
static void
-region_free(Region *region)
+region_free (Region *region,
+ gboolean all)
{
if (!region)
+ {
return;
+ }
- region_free(region->next);
+ if (all)
+ {
+ region_free (region->next, all);
+ }
+ else
+ {
+ if (region->next)
+ {
+ region->next->prev = region->prev;
+ }
+
+ if (region->prev)
+ {
+ region->prev->next = region->next;
+ }
+ }
if (region->type == GITG_DIFF_ITER_TYPE_HEADER)
- g_slice_free(Header, (Header *)region);
+ {
+ g_slice_free (Header, (Header *)region);
+ }
else
- g_slice_free(Hunk, (Hunk *)region);
+ {
+ g_slice_free (Hunk, (Hunk *)region);
+ }
}
static void
-regions_free(GitgDiffView *view, gboolean remove_signals)
+regions_free (GitgDiffView *view)
{
- region_free(view->priv->regions);
- g_sequence_remove_range(g_sequence_get_begin_iter(view->priv->regions_index), g_sequence_get_end_iter(view->priv->regions_index));
+ region_free (view->priv->regions, TRUE);
+
+ g_sequence_remove_range (g_sequence_get_begin_iter (view->priv->regions_index),
+ g_sequence_get_end_iter (view->priv->regions_index));
view->priv->regions = NULL;
view->priv->last_region = NULL;
view->priv->last_scan_line = 0;
view->priv->max_line_count = 99;
-
- if (view->priv->scan_id)
- {
- g_source_remove(view->priv->scan_id);
- view->priv->scan_id = 0;
- }
-
- if (view->priv->current_buffer && remove_signals)
- {
- g_signal_handlers_disconnect_by_func(view->priv->current_buffer, G_CALLBACK(on_buffer_insert_text), view);
- g_signal_handlers_disconnect_by_func(view->priv->current_buffer, G_CALLBACK(on_buffer_delete_range), view);
-
- gtk_text_tag_table_remove (gtk_text_buffer_get_tag_table(view->priv->current_buffer), view->priv->invisible_tag);
- gtk_text_tag_table_remove (gtk_text_buffer_get_tag_table(view->priv->current_buffer), view->priv->subheader_tag);
-
- g_object_unref (view->priv->current_buffer);
-
- view->priv->current_buffer = NULL;
- view->priv->invisible_tag = NULL;
- view->priv->subheader_tag = NULL;
- }
}
static void
@@ -190,9 +204,13 @@ gitg_diff_view_finalize (GObject *object)
{
GitgDiffView *view = GITG_DIFF_VIEW (object);
- regions_free (view, TRUE);
+ regions_free (view);
g_sequence_free (view->priv->regions_index);
+ disable_diff_view (view);
+
+ g_object_unref (view->priv->line_renderer);
+
if (view->priv->label_func &&
view->priv->label_func_destroy_notify)
{
@@ -203,40 +221,60 @@ gitg_diff_view_finalize (GObject *object)
}
static void
-set_diff_enabled(GitgDiffView *view, gboolean enabled)
+set_diff_enabled (GitgDiffView *view,
+ gboolean enabled)
{
- view->priv->diff_enabled = enabled;
- gtk_widget_queue_draw(GTK_WIDGET(view));
+ if (enabled == view->priv->diff_enabled)
+ {
+ return;
+ }
+
+ if (enabled)
+ {
+ enable_diff_view (view);
+ }
+ else
+ {
+ disable_diff_view (view);
+ }
+
+ gtk_widget_queue_draw (GTK_WIDGET(view));
}
static void
-gitg_diff_view_set_property(GObject *object, guint prop_id, const GValue *value, GParamSpec *pspec)
+gitg_diff_view_set_property (GObject *object,
+ guint prop_id,
+ const GValue *value,
+ GParamSpec *pspec)
{
GitgDiffView *self = GITG_DIFF_VIEW(object);
switch (prop_id)
{
case PROP_DIFF_ENABLED:
- set_diff_enabled(self, g_value_get_boolean(value));
+ set_diff_enabled(self, g_value_get_boolean (value));
break;
default:
- G_OBJECT_WARN_INVALID_PROPERTY_ID(object, prop_id, pspec);
+ G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
break;
}
}
static void
-gitg_diff_view_get_property(GObject *object, guint prop_id, GValue *value, GParamSpec *pspec)
+gitg_diff_view_get_property (GObject *object,
+ guint prop_id,
+ GValue *value,
+ GParamSpec *pspec)
{
- GitgDiffView *self = GITG_DIFF_VIEW(object);
+ GitgDiffView *self = GITG_DIFF_VIEW (object);
switch (prop_id)
{
case PROP_DIFF_ENABLED:
- g_value_set_boolean(value, self->priv->diff_enabled);
+ g_value_set_boolean (value, self->priv->diff_enabled);
break;
default:
- G_OBJECT_WARN_INVALID_PROPERTY_ID(object, prop_id, pspec);
+ G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
break;
}
}
@@ -262,7 +300,7 @@ gitg_diff_view_class_init(GitgDiffViewClass *klass)
widget_class->expose_event = gitg_diff_view_expose;
diff_view_signals[HEADER_ADDED] =
- g_signal_new ("header-added",
+ g_signal_new ("header-added",
G_OBJECT_CLASS_TYPE (object_class),
G_SIGNAL_RUN_LAST,
G_STRUCT_OFFSET (GitgDiffViewClass, header_added),
@@ -273,7 +311,7 @@ gitg_diff_view_class_init(GitgDiffViewClass *klass)
G_TYPE_POINTER);
diff_view_signals[HUNK_ADDED] =
- g_signal_new ("hunk-added",
+ g_signal_new ("hunk-added",
G_OBJECT_CLASS_TYPE (object_class),
G_SIGNAL_RUN_LAST,
G_STRUCT_OFFSET (GitgDiffViewClass, hunk_added),
@@ -290,57 +328,145 @@ gitg_diff_view_class_init(GitgDiffViewClass *klass)
FALSE,
G_PARAM_READWRITE));
- g_type_class_add_private(object_class, sizeof(GitgDiffViewPrivate));
+ g_type_class_add_private (object_class, sizeof(GitgDiffViewPrivate));
}
static void
-on_buffer_set(GitgDiffView *self, GParamSpec *spec, gpointer userdata)
+disable_diff_view (GitgDiffView *view)
{
- /* remove all regions for a new buffer */
- regions_free(self, TRUE);
+ if (!view->priv->diff_enabled)
+ {
+ return;
+ }
+
+ regions_free (view);
+
+ if (view->priv->scan_id)
+ {
+ g_source_remove (view->priv->scan_id);
+ view->priv->scan_id = 0;
+ }
+
+ if (view->priv->current_buffer)
+ {
+ GtkTextTagTable *table;
+ GtkSourceGutter *gutter;
+
+ table = gtk_text_buffer_get_tag_table (view->priv->current_buffer);
+
+ g_signal_handlers_disconnect_by_func (view->priv->current_buffer,
+ G_CALLBACK (on_buffer_insert_text),
+ view);
+
+ g_signal_handlers_disconnect_by_func (view->priv->current_buffer,
+ G_CALLBACK (on_buffer_delete_range),
+ view);
+
+ gtk_text_tag_table_remove (table, view->priv->invisible_tag);
+ gtk_text_tag_table_remove (table, view->priv->subheader_tag);
+
+ g_object_unref (view->priv->current_buffer);
- self->priv->current_buffer = g_object_ref(gtk_text_view_get_buffer(GTK_TEXT_VIEW(self)));
- g_signal_connect_after(self->priv->current_buffer, "insert-text", G_CALLBACK(on_buffer_insert_text), self);
- g_signal_connect_after(self->priv->current_buffer, "delete-range", G_CALLBACK(on_buffer_delete_range), self);
+ view->priv->current_buffer = NULL;
+ view->priv->invisible_tag = NULL;
+ view->priv->subheader_tag = NULL;
- self->priv->scan_id = g_idle_add((GSourceFunc)on_idle_scan, self);
- self->priv->invisible_tag = gtk_text_buffer_create_tag(self->priv->current_buffer, "GitgHunkInvisible", "invisible", TRUE, NULL);
- self->priv->subheader_tag = gtk_text_buffer_create_tag(self->priv->current_buffer, "GitgHunkSubHeader", "invisible", TRUE, NULL);
+ gutter = gtk_source_view_get_gutter (GTK_SOURCE_VIEW (view),
+ GTK_TEXT_WINDOW_LEFT);
+
+ gtk_source_gutter_remove (gutter,
+ GTK_CELL_RENDERER (view->priv->line_renderer));
+ }
- gtk_text_tag_set_priority (self->priv->subheader_tag,
- gtk_text_tag_table_get_size (gtk_text_buffer_get_tag_table (self->priv->current_buffer)) - 1);
+ view->priv->diff_enabled = FALSE;
}
static void
-gitg_diff_view_init (GitgDiffView *self)
+enable_diff_view (GitgDiffView *view)
{
+ GtkTextBuffer *buffer;
+ GtkTextTagTable *table;
GtkSourceGutter *gutter;
- self->priv = GITG_DIFF_VIEW_GET_PRIVATE (self);
+ if (view->priv->diff_enabled)
+ {
+ disable_diff_view (view);
+ }
- self->priv->regions_index = g_sequence_new (NULL);
- self->priv->line_renderer = gitg_diff_line_renderer_new ();
+ buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (view));
+ view->priv->current_buffer = g_object_ref (buffer);
- g_object_set (self->priv->line_renderer, "xpad", 2, NULL);
+ g_signal_connect_after (buffer,
+ "insert-text",
+ G_CALLBACK (on_buffer_insert_text),
+ view);
+
+ g_signal_connect_after (buffer,
+ "delete-range",
+ G_CALLBACK (on_buffer_delete_range),
+ view);
+
+ view->priv->scan_id = g_idle_add ((GSourceFunc)on_idle_scan, view);
+
+ view->priv->invisible_tag = gtk_text_buffer_create_tag (view->priv->current_buffer,
+ "GitgHunkInvisible",
+ "invisible",
+ TRUE,
+ NULL);
+
+ view->priv->subheader_tag = gtk_text_buffer_create_tag (view->priv->current_buffer,
+ "GitgHunkSubHeader",
+ "invisible",
+ TRUE,
+ NULL);
- gutter = gtk_source_view_get_gutter (GTK_SOURCE_VIEW (self), GTK_TEXT_WINDOW_LEFT);
+ table = gtk_text_buffer_get_tag_table (view->priv->current_buffer);
+
+ gtk_text_tag_set_priority (view->priv->subheader_tag,
+ gtk_text_tag_table_get_size (table) - 1);
+
+ gutter = gtk_source_view_get_gutter (GTK_SOURCE_VIEW (view),
+ GTK_TEXT_WINDOW_LEFT);
gtk_source_gutter_insert (gutter,
- GTK_CELL_RENDERER (self->priv->line_renderer),
+ GTK_CELL_RENDERER (view->priv->line_renderer),
0);
gtk_source_gutter_set_cell_data_func (gutter,
- GTK_CELL_RENDERER (self->priv->line_renderer),
+ GTK_CELL_RENDERER (view->priv->line_renderer),
(GtkSourceGutterDataFunc)line_renderer_data_func,
- self,
+ view,
NULL);
gtk_source_gutter_set_cell_size_func (gutter,
- GTK_CELL_RENDERER (self->priv->line_renderer),
+ GTK_CELL_RENDERER (view->priv->line_renderer),
(GtkSourceGutterSizeFunc)line_renderer_size_func,
- self,
+ view,
NULL);
+ view->priv->diff_enabled = TRUE;
+}
+
+static void
+on_buffer_set (GitgDiffView *self, GParamSpec *spec, gpointer userdata)
+{
+ if (self->priv->diff_enabled)
+ {
+ enable_diff_view (self);
+ }
+}
+
+static void
+gitg_diff_view_init (GitgDiffView *self)
+{
+ self->priv = GITG_DIFF_VIEW_GET_PRIVATE (self);
+
+ self->priv->regions_index = g_sequence_new (NULL);
+ self->priv->line_renderer = gitg_diff_line_renderer_new ();
+
+ g_object_ref (self->priv->line_renderer);
+ g_object_set (self->priv->line_renderer, "xpad", 2, NULL);
+
g_signal_connect (self, "notify::buffer", G_CALLBACK (on_buffer_set), NULL);
}
@@ -921,6 +1047,11 @@ gitg_diff_view_get_start_iter(GitgDiffView *view, GitgDiffIter *iter)
g_return_val_if_fail(GITG_IS_DIFF_VIEW(view), FALSE);
g_return_val_if_fail(iter != NULL, FALSE);
+ if (!view->priv->diff_enabled)
+ {
+ return FALSE;
+ }
+
region_to_iter (view, view->priv->regions, iter);
return GITG_DIFF_ITER_GET_REGION (iter) != NULL;
}
@@ -1109,24 +1240,34 @@ header_parse_index(GitgDiffView *view, Header *header)
}
gboolean
-gitg_diff_iter_get_index(GitgDiffIter *iter, gchar **from, gchar **to)
+gitg_diff_iter_get_index (GitgDiffIter *iter,
+ gchar **from,
+ gchar **to)
{
Region *region = GITG_DIFF_ITER_GET_REGION (iter);
while (region && region->type != GITG_DIFF_ITER_TYPE_HEADER)
+ {
region = region->prev;
+ }
if (!region)
+ {
return FALSE;
+ }
Header *header = (Header *)region;
gboolean ret = TRUE;
if (!*(header->index_to))
+ {
ret = header_parse_index (GITG_DIFF_ITER_GET_VIEW (iter), header);
+ }
if (!ret)
+ {
return FALSE;
+ }
*from = header->index_from;
*to = header->index_to;
@@ -1134,67 +1275,86 @@ gitg_diff_iter_get_index(GitgDiffIter *iter, gchar **from, gchar **to)
return TRUE;
}
-static gboolean
-iter_in_view(GitgDiffView *view, GtkTextIter *iter)
+static gboolean
+iter_in_view (GitgDiffView *view,
+ GtkTextIter *iter)
{
GtkTextIter start;
GtkTextIter end;
GdkRectangle rect;
- GtkTextView *textview = GTK_TEXT_VIEW(view);
+ GtkTextView *textview = GTK_TEXT_VIEW (view);
- gtk_text_view_get_visible_rect(textview, &rect);
- gtk_text_view_get_iter_at_location(textview, &start, rect.x, rect.y);
- gtk_text_view_get_iter_at_location(textview, &end, rect.x + rect.width, rect.y + rect.height);
+ gtk_text_view_get_visible_rect (textview, &rect);
+ gtk_text_view_get_iter_at_location (textview, &start, rect.x, rect.y);
+ gtk_text_view_get_iter_at_location (textview, &end, rect.x + rect.width, rect.y + rect.height);
return gtk_text_iter_in_range(iter, &start, &end) || gtk_text_iter_equal(iter, &end);
}
static gboolean
-try_scan(GitgDiffView *view)
+try_scan (GitgDiffView *view)
{
- gint lines = gtk_text_buffer_get_line_count(view->priv->current_buffer);
+ gint lines = gtk_text_buffer_get_line_count (view->priv->current_buffer);
if (view->priv->last_scan_line > lines)
+ {
return FALSE;
+ }
- guint num = MIN(lines - view->priv->last_scan_line, IDLE_SCAN_COUNT);
+ guint num = MIN (lines - view->priv->last_scan_line, IDLE_SCAN_COUNT);
if (num == 0)
+ {
return FALSE;
+ }
gchar str[8];
- g_snprintf(str, sizeof(str), "%u", view->priv->max_line_count);
- guint max_line = strlen(str);
+ g_snprintf (str, sizeof (str), "%u", view->priv->max_line_count);
+ guint max_line = strlen (str);
guint last = view->priv->last_scan_line;
- ensure_scan(view, view->priv->last_scan_line + num);
- g_snprintf(str, sizeof(str), "%u", view->priv->max_line_count);
+ ensure_scan (view, view->priv->last_scan_line + num);
+ g_snprintf (str, sizeof (str), "%u", view->priv->max_line_count);
- if (strlen(str) > max_line)
- gtk_widget_queue_draw(GTK_WIDGET(view));
+ if (strlen (str) > max_line)
+ {
+ gtk_widget_queue_draw (GTK_WIDGET (view));
+ }
return last != view->priv->last_scan_line;
}
static void
-on_buffer_delete_range(GtkTextBuffer *buffer, GtkTextIter *start, GtkTextIter *end, GitgDiffView *view)
+on_buffer_delete_range (GtkTextBuffer *buffer,
+ GtkTextIter *start,
+ GtkTextIter *end,
+ GitgDiffView *view)
{
if (view->priv->ignore_changes)
{
return;
}
- regions_free(view, FALSE);
+ regions_free (view);
- if (iter_in_view(view, start) || iter_in_view(view, end))
- try_scan(view);
+ if (iter_in_view (view, start) || iter_in_view (view, end))
+ {
+ try_scan (view);
+ }
if (!view->priv->scan_id)
- view->priv->scan_id = g_idle_add((GSourceFunc)on_idle_scan, view);
+ {
+ view->priv->scan_id = g_idle_add ((GSourceFunc)on_idle_scan,
+ view);
+ }
}
-static void
-on_buffer_insert_text(GtkTextBuffer *buffer, GtkTextIter *iter, gchar const *text, gint len, GitgDiffView *view)
+static void
+on_buffer_insert_text (GtkTextBuffer *buffer,
+ GtkTextIter *iter,
+ gchar const *text,
+ gint len,
+ GitgDiffView *view)
{
if (view->priv->ignore_changes)
{
@@ -1202,18 +1362,24 @@ on_buffer_insert_text(GtkTextBuffer *buffer, GtkTextIter *iter, gchar const *tex
}
/* if region is in current view and not scanned, issue scan now */
- if (iter_in_view(view, iter))
- try_scan(view);
+ if (iter_in_view (view, iter))
+ {
+ try_scan (view);
+ }
if (!view->priv->scan_id)
- view->priv->scan_id = g_idle_add((GSourceFunc)on_idle_scan, view);
+ {
+ view->priv->scan_id = g_idle_add ((GSourceFunc)on_idle_scan, view);
+ }
}
-static gboolean
-on_idle_scan(GitgDiffView *view)
+static gboolean
+on_idle_scan (GitgDiffView *view)
{
if (try_scan(view))
+ {
return TRUE;
+ }
view->priv->scan_id = 0;
return FALSE;
@@ -1228,6 +1394,11 @@ gitg_diff_view_get_header_at_iter (GitgDiffView *view,
g_return_val_if_fail (iter != NULL, FALSE);
g_return_val_if_fail (diff_iter != NULL, FALSE);
+ if (!view->priv->diff_enabled)
+ {
+ return FALSE;
+ }
+
ensure_scan (view, gtk_text_iter_get_line (iter));
Region *region = find_current_region (view, gtk_text_iter_get_line (iter));
@@ -1250,6 +1421,11 @@ gitg_diff_view_get_hunk_at_iter (GitgDiffView *view,
g_return_val_if_fail (iter != NULL, FALSE);
g_return_val_if_fail (diff_iter != NULL, FALSE);
+ if (!view->priv->diff_enabled)
+ {
+ return FALSE;
+ }
+
ensure_scan (view, gtk_text_iter_get_line (iter));
Region *region = find_current_region (view, gtk_text_iter_get_line (iter));
@@ -1309,6 +1485,11 @@ gitg_diff_view_get_line_type (GitgDiffView *view, GtkTextIter const *iter)
g_return_val_if_fail (GITG_IS_DIFF_VIEW (view), GITG_DIFF_LINE_TYPE_NONE);
g_return_val_if_fail (iter != NULL, GITG_DIFF_LINE_TYPE_NONE);
+ if (!view->priv->diff_enabled)
+ {
+ return GITG_DIFF_LINE_TYPE_NONE;
+ }
+
GitgDiffIter diff_iter;
if (!gitg_diff_view_get_hunk_at_iter (view, iter, &diff_iter))
diff --git a/gitg/gitg-runner.c b/gitg/gitg-runner.c
index 6c9991e..c151ea0 100644
--- a/gitg/gitg-runner.c
+++ b/gitg/gitg-runner.c
@@ -470,9 +470,15 @@ read_output_ready(GInputStream *stream, GAsyncResult *result, AsyncData *data)
if (read == 0)
{
/* End */
- gchar *b[] = {data->runner->priv->buffer, NULL};
+ gchar *converted = gitg_utils_convert_utf8 (data->runner->priv->buffer,
+ -1);
+
+ gchar *b[] = {converted, NULL};
+
g_signal_emit(data->runner, runner_signals[UPDATE], 0, b);
+ g_free (converted);
+
gint status = 0;
waitpid(data->runner->priv->pid, &status, 0);
diff --git a/gitg/gitg-utils.c b/gitg/gitg-utils.c
index 361c7e3..cb49a7f 100644
--- a/gitg/gitg-utils.c
+++ b/gitg/gitg-utils.c
@@ -205,55 +205,97 @@ gitg_utils_export_files (GitgRepository *repository,
return ret;
}
+static void
+utf8_validate_fallback (gchar *text,
+ gssize size)
+{
+ gchar const *end;
+
+ while (!g_utf8_validate (text, size, &end))
+ {
+ *((gchar *)end) = '?';
+ }
+}
+
static gchar *
-convert_fallback (gchar const *text, gssize size, gchar const *fallback)
+convert_fallback (gchar const *text,
+ gssize size,
+ gchar const *fallback)
{
gchar *res;
gsize read, written;
- GString *str = g_string_new("");
-
- while ((res = g_convert(text, size, "UTF-8", "ASCII", &read, &written, NULL))
- == NULL) {
- res = g_convert(text, read, "UTF-8", "ASCII", NULL, NULL, NULL);
- str = g_string_append(str, res);
+ GString *str = g_string_new ("");
+
+ while ((res = g_convert(text,
+ size,
+ "UTF-8",
+ "ASCII",
+ &read,
+ &written,
+ NULL)) == NULL)
+ {
+ res = g_convert (text, read, "UTF-8", "ASCII", NULL, NULL, NULL);
+ str = g_string_append (str, res);
- str = g_string_append(str, fallback);
+ str = g_string_append (str, fallback);
text = text + read + 1;
size = size - read;
}
- str = g_string_append(str, res);
- g_free(res);
+ str = g_string_append (str, res);
+ g_free (res);
- res = str->str;
- g_string_free(str, FALSE);
- return res;
+ utf8_validate_fallback (str->str, str->len);
+ return g_string_free (str, FALSE);
}
gchar *
-gitg_utils_convert_utf8(gchar const *str, gssize size)
+gitg_utils_convert_utf8 (gchar const *str, gssize size)
{
static gchar *encodings[] = {
"ISO-8859-15",
"ASCII"
};
- if (g_utf8_validate(str, size, NULL))
- return g_strndup(str, size == -1 ? strlen(str) : size);
+ if (str == NULL)
+ {
+ return NULL;
+ }
+
+ if (size == -1)
+ {
+ size = strlen (str);
+ }
+
+ if (g_utf8_validate (str, size, NULL))
+ {
+ return g_strndup (str, size);
+ }
int i;
- for (i = 0; i < sizeof(encodings) / sizeof(gchar *); ++i)
+ for (i = 0; i < sizeof (encodings) / sizeof (gchar *); ++i)
{
gsize read;
gsize written;
- gchar *ret = g_convert(str, size, "UTF-8", encodings[i], &read, &written, NULL);
+ gchar *ret = g_convert (str,
+ size,
+ "UTF-8",
+ encodings[i],
+ &read,
+ &written,
+ NULL);
- if (ret)
+ if (ret && read == size)
+ {
+ utf8_validate_fallback (ret, written);
return ret;
+ }
+
+ g_free (ret);
}
- return convert_fallback(str, size, "?");
+ return convert_fallback (str, size, "?");
}
guint
@@ -302,10 +344,10 @@ gitg_utils_get_content_type(GFile *file)
}
gboolean
-gitg_utils_can_display_content_type(gchar const *content_type)
+gitg_utils_can_display_content_type (gchar const *content_type)
{
- return g_content_type_is_a(content_type, "text/plain") ||
- g_content_type_equals(content_type, "application/octet-stream");
+ return g_content_type_is_a (content_type, "text/plain") ||
+ g_content_type_equals (content_type, "application/octet-stream");
}
GtkSourceLanguage *
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]