From a2dd71cd0a16fe04b1f074e7cd5a95c35a70e9e7 Mon Sep 17 00:00:00 2001 From: Carlos Garcia Campos Date: Mon, 9 Jul 2007 16:13:27 +0000 Subject: [PATCH] Redraw only form field region instead of the whole page when reloading a 2007-07-09 Carlos Garcia Campos * shell/ev-pixbuf-cache.[ch]: (ev_pixbuf_cache_class_init), (dispose_cache_job_info), (job_finished_cb), (move_one_job), (add_job), (add_job_if_needed), (ev_pixbuf_cache_get_surface), (ev_pixbuf_cache_get_link_mapping), (ev_pixbuf_cache_get_image_mapping), (ev_pixbuf_cache_get_form_field_mapping), (ev_pixbuf_cache_get_text_mapping), (ev_pixbuf_cache_reload_page): * shell/ev-view.c: (ev_view_form_field_get_region), (ev_view_form_field_button_create_widget), (ev_view_form_field_text_save), (ev_view_form_field_choice_save), (job_finished_cb): Redraw only form field region instead of the whole page when reloading a page to show changes on the form field. svn path=/trunk/; revision=2565 --- ChangeLog | 17 ++++++++ shell/ev-pixbuf-cache.c | 94 ++++++++++++++++++++++++++--------------- shell/ev-pixbuf-cache.h | 5 ++- shell/ev-view.c | 44 ++++++++++++++++++- 4 files changed, 121 insertions(+), 39 deletions(-) diff --git a/ChangeLog b/ChangeLog index f19add66..eeceffe5 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,20 @@ +2007-07-09 Carlos Garcia Campos + + * shell/ev-pixbuf-cache.[ch]: (ev_pixbuf_cache_class_init), + (dispose_cache_job_info), (job_finished_cb), (move_one_job), + (add_job), (add_job_if_needed), (ev_pixbuf_cache_get_surface), + (ev_pixbuf_cache_get_link_mapping), + (ev_pixbuf_cache_get_image_mapping), + (ev_pixbuf_cache_get_form_field_mapping), + (ev_pixbuf_cache_get_text_mapping), (ev_pixbuf_cache_reload_page): + * shell/ev-view.c: (ev_view_form_field_get_region), + (ev_view_form_field_button_create_widget), + (ev_view_form_field_text_save), (ev_view_form_field_choice_save), + (job_finished_cb): + + Redraw only form field region instead of the whole page when + reloading a page to show changes on the form field. + 2007-07-09 Carlos Garcia Campos * shell/ev-view.c: (ev_view_form_field_choice_save): diff --git a/shell/ev-pixbuf-cache.c b/shell/ev-pixbuf-cache.c index 46928674..4516f75d 100644 --- a/shell/ev-pixbuf-cache.c +++ b/shell/ev-pixbuf-cache.c @@ -3,6 +3,7 @@ #include "ev-page-cache.h" #include "ev-selection.h" #include "ev-document-images.h" +#include "ev-document-forms.h" #include "ev-image.h" #include "ev-form-field.h" @@ -11,6 +12,9 @@ typedef struct _CacheJobInfo EvJob *job; EvRenderContext *rc; + /* Region of the page that needs to be drawn */ + GdkRegion *region; + /* Data we get from rendering */ cairo_surface_t *surface; GList *link_mapping; @@ -114,13 +118,15 @@ ev_pixbuf_cache_class_init (EvPixbufCacheClass *class) object_class->finalize = ev_pixbuf_cache_finalize; object_class->dispose = ev_pixbuf_cache_dispose; - signals[JOB_FINISHED] = g_signal_new ("job-finished", - G_OBJECT_CLASS_TYPE (object_class), - G_SIGNAL_RUN_LAST | G_SIGNAL_ACTION, - G_STRUCT_OFFSET (EvPixbufCacheClass, job_finished), - NULL, NULL, - g_cclosure_marshal_VOID__VOID, - G_TYPE_NONE, 0); + signals[JOB_FINISHED] = + g_signal_new ("job-finished", + G_OBJECT_CLASS_TYPE (object_class), + G_SIGNAL_RUN_LAST | G_SIGNAL_ACTION, + G_STRUCT_OFFSET (EvPixbufCacheClass, job_finished), + NULL, NULL, + g_cclosure_marshal_VOID__POINTER, + G_TYPE_NONE, 1, + G_TYPE_POINTER); } static void @@ -155,6 +161,10 @@ dispose_cache_job_info (CacheJobInfo *job_info, cairo_surface_destroy (job_info->surface); job_info->surface = NULL; } + if (job_info->region) { + gdk_region_destroy (job_info->region); + job_info->region = NULL; + } if (job_info->link_mapping) { ev_link_mapping_free (job_info->link_mapping); job_info->link_mapping = NULL; @@ -239,7 +249,7 @@ job_finished_cb (EvJob *job, job_info = find_job_cache (pixbuf_cache, job_render->rc->page); copy_job_to_job_info (job_render, job_info, pixbuf_cache); - g_signal_emit (pixbuf_cache, signals[JOB_FINISHED], 0); + g_signal_emit (pixbuf_cache, signals[JOB_FINISHED], 0, job_info->region); } /* This checks a job to see if the job would generate the right sized pixbuf @@ -326,6 +336,7 @@ move_one_job (CacheJobInfo *job_info, *target_page = *job_info; job_info->job = NULL; + job_info->region = NULL; job_info->surface = NULL; job_info->link_mapping = NULL; job_info->image_mapping = NULL; @@ -336,8 +347,6 @@ move_one_job (CacheJobInfo *job_info, } } - - static void ev_pixbuf_cache_update_range (EvPixbufCache *pixbuf_cache, gint start_page, @@ -548,6 +557,7 @@ static void add_job (EvPixbufCache *pixbuf_cache, CacheJobInfo *job_info, EvPageCache *page_cache, + GdkRegion *region, gint width, gint height, gint page, @@ -570,6 +580,10 @@ add_job (EvPixbufCache *pixbuf_cache, ev_render_context_set_scale (job_info->rc, scale); } + if (job_info->region) + gdk_region_destroy (job_info->region); + job_info->region = region ? gdk_region_copy (region) : NULL; + /* Figure out what else we need for this job */ if (job_info->link_mapping == NULL) include_links = TRUE; @@ -598,7 +612,9 @@ add_job (EvPixbufCache *pixbuf_cache, include_text, include_selection); ev_job_queue_add_job (job_info->job, priority); - g_signal_connect (job_info->job, "finished", G_CALLBACK (job_finished_cb), pixbuf_cache); + g_signal_connect (job_info->job, "finished", + G_CALLBACK (job_finished_cb), + pixbuf_cache); } static void @@ -623,7 +639,7 @@ add_job_if_needed (EvPixbufCache *pixbuf_cache, cairo_image_surface_get_height (job_info->surface) == height) return; - add_job (pixbuf_cache, job_info, page_cache, + add_job (pixbuf_cache, job_info, page_cache, NULL, width, height, page, rotation, scale, priority); } @@ -717,7 +733,7 @@ ev_pixbuf_cache_get_surface (EvPixbufCache *pixbuf_cache, if (job_info->job && EV_JOB (job_info->job)->finished) { copy_job_to_job_info (EV_JOB_RENDER (job_info->job), job_info, pixbuf_cache); - g_signal_emit (pixbuf_cache, signals[JOB_FINISHED], 0); + g_signal_emit (pixbuf_cache, signals[JOB_FINISHED], 0, job_info->region); } return job_info->surface; @@ -737,7 +753,7 @@ ev_pixbuf_cache_get_link_mapping (EvPixbufCache *pixbuf_cache, if (job_info->job && EV_JOB (job_info->job)->finished) { copy_job_to_job_info (EV_JOB_RENDER (job_info->job), job_info, pixbuf_cache); - g_signal_emit (pixbuf_cache, signals[JOB_FINISHED], 0); + g_signal_emit (pixbuf_cache, signals[JOB_FINISHED], 0, job_info->region); } return job_info->link_mapping; @@ -760,12 +776,35 @@ ev_pixbuf_cache_get_image_mapping (EvPixbufCache *pixbuf_cache, if (job_info->job && EV_JOB (job_info->job)->finished) { copy_job_to_job_info (EV_JOB_RENDER (job_info->job), job_info, pixbuf_cache); - g_signal_emit (pixbuf_cache, signals[JOB_FINISHED], 0); + g_signal_emit (pixbuf_cache, signals[JOB_FINISHED], 0, job_info->region); } return job_info->image_mapping; } +GList * +ev_pixbuf_cache_get_form_field_mapping (EvPixbufCache *pixbuf_cache, + gint page) +{ + CacheJobInfo *job_info; + + if (!EV_IS_DOCUMENT_FORMS (pixbuf_cache->document)) + return NULL; + + job_info = find_job_cache (pixbuf_cache, page); + if (job_info == NULL) + return NULL; + + /* We don't need to wait for the idle to handle the callback */ + if (job_info->job && + EV_JOB (job_info->job)->finished) { + copy_job_to_job_info (EV_JOB_RENDER(job_info->job), job_info, pixbuf_cache); + g_signal_emit (pixbuf_cache, signals[JOB_FINISHED], 0, job_info->region); + } + + return job_info->form_field_mapping; +} + static gboolean new_selection_surface_needed (EvPixbufCache *pixbuf_cache, CacheJobInfo *job_info, @@ -824,7 +863,7 @@ ev_pixbuf_cache_get_text_mapping (EvPixbufCache *pixbuf_cache, if (job_info->job && EV_JOB (job_info->job)->finished) { copy_job_to_job_info (EV_JOB_RENDER (job_info->job), job_info, pixbuf_cache); - g_signal_emit (pixbuf_cache, signals[JOB_FINISHED], 0); + g_signal_emit (pixbuf_cache, signals[JOB_FINISHED], 0, job_info->region); } return job_info->text_mapping; @@ -1135,10 +1174,11 @@ ev_pixbuf_cache_get_selection_list (EvPixbufCache *pixbuf_cache) } void -ev_pixbuf_cache_reload_page (EvPixbufCache *pixbuf_cache, +ev_pixbuf_cache_reload_page (EvPixbufCache *pixbuf_cache, + GdkRegion *region, gint page, gint rotation, - gfloat scale) + gdouble scale) { CacheJobInfo *job_info; EvPageCache *page_cache; @@ -1152,25 +1192,9 @@ ev_pixbuf_cache_reload_page (EvPixbufCache *pixbuf_cache, ev_page_cache_get_size (page_cache, page, rotation, scale, &width, &height); - add_job (pixbuf_cache, job_info, page_cache, + add_job (pixbuf_cache, job_info, page_cache, region, width, height, page, rotation, scale, EV_JOB_PRIORITY_HIGH); } -GList * -ev_pixbuf_cache_get_form_field_mapping (EvPixbufCache *pixbuf_cache, - gint page) -{ - CacheJobInfo *job_info; - - job_info = find_job_cache (pixbuf_cache, page); - if (job_info == NULL) - return NULL; - - if (job_info->job && - EV_JOB (job_info->job)->finished) { - copy_job_to_job_info (EV_JOB_RENDER(job_info->job), job_info, pixbuf_cache); - } - return job_info->form_field_mapping; -} diff --git a/shell/ev-pixbuf-cache.h b/shell/ev-pixbuf-cache.h index a8ff30ab..d2116cdb 100644 --- a/shell/ev-pixbuf-cache.h +++ b/shell/ev-pixbuf-cache.h @@ -69,10 +69,11 @@ GList *ev_pixbuf_cache_get_form_field_mapping (EvPixbufCache *pixbuf_cach gint page); void ev_pixbuf_cache_clear (EvPixbufCache *pixbuf_cache); void ev_pixbuf_cache_style_changed (EvPixbufCache *pixbuf_cache); -void ev_pixbuf_cache_reload_page (EvPixbufCache *pixbuf_cache, +void ev_pixbuf_cache_reload_page (EvPixbufCache *pixbuf_cache, + GdkRegion *region, gint page, gint rotation, - gfloat scale); + gdouble scale); /* Selection */ cairo_surface_t *ev_pixbuf_cache_get_selection_surface (EvPixbufCache *pixbuf_cache, gint page, diff --git a/shell/ev-view.c b/shell/ev-view.c index f46f1652..44af4212 100644 --- a/shell/ev-view.c +++ b/shell/ev-view.c @@ -231,6 +231,7 @@ static void find_changed_cb (EvDocument int page, EvView *view); static void job_finished_cb (EvPixbufCache *pixbuf_cache, + GdkRegion *region, EvView *view); static void page_changed_cb (EvPageCache *page_cache, int new_page, @@ -1598,6 +1599,24 @@ ev_view_get_form_field_at_location (EvView *view, return NULL; } +static GdkRegion * +ev_view_form_field_get_region (EvView *view, + EvFormField *field) +{ + EvRectangle field_area; + GdkRectangle view_area; + GList *forms_mapping; + + forms_mapping = ev_pixbuf_cache_get_form_field_mapping (view->pixbuf_cache, + field->page); + ev_form_field_mapping_get_area (forms_mapping, field, &field_area); + doc_rect_to_view_rect (view, field->page, &field_area, &view_area); + view_area.x -= view->scroll_x; + view_area.y -= view->scroll_y; + + return gdk_region_rectangle (&view_area); +} + static gboolean ev_view_forms_remove_widgets (EvView *view) { @@ -1624,16 +1643,21 @@ ev_view_form_field_button_create_widget (EvView *view, break; case EV_FORM_FIELD_BUTTON_CHECK: case EV_FORM_FIELD_BUTTON_RADIO: { - gboolean state; + gboolean state; + GdkRegion *field_region; + field_region = ev_view_form_field_get_region (view, field); + state = ev_document_forms_form_field_button_get_state (EV_DOCUMENT_FORMS (view->document), field); ev_document_forms_form_field_button_set_state (EV_DOCUMENT_FORMS (view->document), field, !state); ev_pixbuf_cache_reload_page (view->pixbuf_cache, + field_region, field->page, view->rotation, view->scale); + gdk_region_destroy (field_region); } break; } @@ -1651,14 +1675,19 @@ ev_view_form_field_text_save (EvView *view, if (field->changed) { EvFormFieldText *field_text = EV_FORM_FIELD_TEXT (field); + GdkRegion *field_region; + + field_region = ev_view_form_field_get_region (view, field); ev_document_forms_form_field_text_set_text (EV_DOCUMENT_FORMS (view->document), field, field_text->text); field->changed = FALSE; ev_pixbuf_cache_reload_page (view->pixbuf_cache, + field_region, field->page, view->rotation, view->scale); + gdk_region_destroy (field_region); } } @@ -1757,6 +1786,9 @@ ev_view_form_field_choice_save (EvView *view, if (field->changed) { GList *l; EvFormFieldChoice *field_choice = EV_FORM_FIELD_CHOICE (field); + GdkRegion *field_region; + + field_region = ev_view_form_field_get_region (view, field); if (field_choice->is_editable) { ev_document_forms_form_field_choice_set_text (EV_DOCUMENT_FORMS (view->document), @@ -1771,9 +1803,11 @@ ev_view_form_field_choice_save (EvView *view, } field->changed = FALSE; ev_pixbuf_cache_reload_page (view->pixbuf_cache, + field_region, field->page, view->rotation, view->scale); + gdk_region_destroy (field_region); } } @@ -3895,9 +3929,15 @@ find_changed_cb (EvDocument *document, int page, EvView *view) static void job_finished_cb (EvPixbufCache *pixbuf_cache, + GdkRegion *region, EvView *view) { - gtk_widget_queue_draw (GTK_WIDGET (view)); + if (region) { + gdk_window_invalidate_region (view->layout.bin_window, + region, TRUE); + } else { + gtk_widget_queue_draw (GTK_WIDGET (view)); + } } static void -- 2.43.5