From 74927c03a4877b0d4dc96fd7b1e3b83dbe07e933 Mon Sep 17 00:00:00 2001 From: Sven Neumann Date: Wed, 14 Mar 2007 10:01:08 +0000 Subject: [PATCH] cache the display scale factors in the GimpDisplayShell struct and 2007-03-14 Sven Neumann * app/display/gimpdisplayshell.[ch]: cache the display scale factors in the GimpDisplayShell struct and recalculate it in gimp_display_shell_scale_factor_changed(). * app/display/gimpdisplayshell-scale.c (gimp_display_shell_scale_set_dot_for_dot) * app/display/gimpdisplayshell-handlers.c (gimp_display_shell_resolution_changed_handler) (gimp_display_shell_monitor_res_notify_handler): update the scale factors by calling gimp_display_shell_scale_factor_changed(). * app/display/gimpdisplayshell-transform.c * app/display/gimpnavigationeditor.c: code cleanup. svn path=/trunk/; revision=22118 --- ChangeLog | 16 +++++ app/display/gimpdisplayshell-handlers.c | 4 ++ app/display/gimpdisplayshell-scale.c | 2 + app/display/gimpdisplayshell-transform.c | 80 +++++++----------------- app/display/gimpdisplayshell.c | 28 +++++++++ app/display/gimpdisplayshell.h | 11 ++-- app/display/gimpnavigationeditor.c | 49 ++++++--------- 7 files changed, 99 insertions(+), 91 deletions(-) diff --git a/ChangeLog b/ChangeLog index f5b4d2bac4..f1c0541cfd 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,19 @@ +2007-03-14 Sven Neumann + + * app/display/gimpdisplayshell.[ch]: cache the display scale + factors in the GimpDisplayShell struct and recalculate it in + gimp_display_shell_scale_factor_changed(). + + * app/display/gimpdisplayshell-scale.c + (gimp_display_shell_scale_set_dot_for_dot) + * app/display/gimpdisplayshell-handlers.c + (gimp_display_shell_resolution_changed_handler) + (gimp_display_shell_monitor_res_notify_handler): update the scale + factors by calling gimp_display_shell_scale_factor_changed(). + + * app/display/gimpdisplayshell-transform.c + * app/display/gimpnavigationeditor.c: code cleanup. + 2007-03-14 Sven Neumann * app/base/pixel-surround.c (struct _PixelSurround): documentation. diff --git a/app/display/gimpdisplayshell-handlers.c b/app/display/gimpdisplayshell-handlers.c index 2376c5538d..a55664aa82 100644 --- a/app/display/gimpdisplayshell-handlers.c +++ b/app/display/gimpdisplayshell-handlers.c @@ -416,6 +416,8 @@ static void gimp_display_shell_resolution_changed_handler (GimpImage *image, GimpDisplayShell *shell) { + gimp_display_shell_scale_factor_changed (shell); + if (shell->dot_for_dot) { gimp_display_shell_scale_setup (shell); @@ -585,6 +587,8 @@ gimp_display_shell_monitor_res_notify_handler (GObject *config, shell->monitor_yres = GIMP_DISPLAY_CONFIG (config)->monitor_yres; } + gimp_display_shell_scale_factor_changed (shell); + if (! shell->dot_for_dot) { gimp_display_shell_scale_setup (shell); diff --git a/app/display/gimpdisplayshell-scale.c b/app/display/gimpdisplayshell-scale.c index 8d0906a864..5960077d4e 100644 --- a/app/display/gimpdisplayshell-scale.c +++ b/app/display/gimpdisplayshell-scale.c @@ -266,6 +266,8 @@ gimp_display_shell_scale_set_dot_for_dot (GimpDisplayShell *shell, shell->dot_for_dot = dot_for_dot; + gimp_display_shell_scale_factor_changed (shell); + gimp_display_shell_scale_resize (shell, GIMP_DISPLAY_CONFIG (gimp->config)->resize_windows_on_zoom, TRUE); diff --git a/app/display/gimpdisplayshell-transform.c b/app/display/gimpdisplayshell-transform.c index 357f1d52c3..e8065476ef 100644 --- a/app/display/gimpdisplayshell-transform.c +++ b/app/display/gimpdisplayshell-transform.c @@ -48,20 +48,14 @@ gimp_display_shell_transform_coordinate (GimpDisplayShell *shell, GimpCoords *image_coords, GimpCoords *display_coords) { - gdouble scalex; - gdouble scaley; - g_return_if_fail (GIMP_IS_DISPLAY_SHELL (shell)); g_return_if_fail (image_coords != NULL); g_return_if_fail (display_coords != NULL); *display_coords = *image_coords; - scalex = SCALEFACTOR_X (shell); - scaley = SCALEFACTOR_Y (shell); - - display_coords->x = scalex * image_coords->x; - display_coords->y = scaley * image_coords->y; + display_coords->x = SCALEFACTOR_X (shell) * image_coords->x; + display_coords->y = SCALEFACTOR_Y (shell) * image_coords->y; display_coords->x += - shell->offset_x + shell->disp_xoffset; display_coords->y += - shell->offset_y + shell->disp_yoffset; @@ -81,23 +75,17 @@ gimp_display_shell_untransform_coordinate (GimpDisplayShell *shell, GimpCoords *display_coords, GimpCoords *image_coords) { - gdouble scalex; - gdouble scaley; - g_return_if_fail (GIMP_IS_DISPLAY_SHELL (shell)); g_return_if_fail (display_coords != NULL); g_return_if_fail (image_coords != NULL); *image_coords = *display_coords; - scalex = SCALEFACTOR_X (shell); - scaley = SCALEFACTOR_Y (shell); - image_coords->x = display_coords->x - shell->disp_xoffset + shell->offset_x; image_coords->y = display_coords->y - shell->disp_yoffset + shell->offset_y; - image_coords->x /= scalex; - image_coords->y /= scaley; + image_coords->x /= SCALEFACTOR_X (shell); + image_coords->y /= SCALEFACTOR_Y (shell); } void @@ -108,19 +96,13 @@ gimp_display_shell_transform_xy (GimpDisplayShell *shell, gint *ny, gboolean use_offsets) { - gdouble scalex; - gdouble scaley; - gint offset_x = 0; - gint offset_y = 0; + gint offset_x = 0; + gint offset_y = 0; g_return_if_fail (GIMP_IS_DISPLAY_SHELL (shell)); g_return_if_fail (nx != NULL); g_return_if_fail (ny != NULL); - /* transform from image coordinates to screen coordinates */ - scalex = SCALEFACTOR_X (shell); - scaley = SCALEFACTOR_Y (shell); - if (use_offsets) { GimpItem *item; @@ -129,8 +111,8 @@ gimp_display_shell_transform_xy (GimpDisplayShell *shell, gimp_item_offsets (item, &offset_x, &offset_y); } - x = (scalex * (x + offset_x) - shell->offset_x); - y = (scaley * (y + offset_y) - shell->offset_y); + x = SCALEFACTOR_X (shell) * (x + offset_x) - shell->offset_x; + y = SCALEFACTOR_Y (shell) * (y + offset_y) - shell->offset_y; /* The projected coordinates can easily overflow a gint in the case of big images at high zoom levels, so we clamp them here to avoid problems. */ @@ -166,10 +148,8 @@ gimp_display_shell_untransform_xy (GimpDisplayShell *shell, gboolean round, gboolean use_offsets) { - gdouble scalex; - gdouble scaley; - gint offset_x = 0; - gint offset_y = 0; + gint offset_x = 0; + gint offset_y = 0; g_return_if_fail (GIMP_IS_DISPLAY_SHELL (shell)); g_return_if_fail (nx != NULL); @@ -178,10 +158,6 @@ gimp_display_shell_untransform_xy (GimpDisplayShell *shell, x -= shell->disp_xoffset; y -= shell->disp_yoffset; - /* transform from screen coordinates to image coordinates */ - scalex = SCALEFACTOR_X (shell); - scaley = SCALEFACTOR_Y (shell); - if (use_offsets) { GimpItem *item; @@ -192,13 +168,13 @@ gimp_display_shell_untransform_xy (GimpDisplayShell *shell, if (round) { - *nx = ROUND ((x + shell->offset_x) / scalex - offset_x); - *ny = ROUND ((y + shell->offset_y) / scaley - offset_y); + *nx = ROUND ((x + shell->offset_x) / SCALEFACTOR_X (shell) - offset_x); + *ny = ROUND ((y + shell->offset_y) / SCALEFACTOR_Y (shell) - offset_y); } else { - *nx = (gint) ((x + shell->offset_x) / scalex - offset_x); - *ny = (gint) ((y + shell->offset_y) / scaley - offset_y); + *nx = (gint) ((x + shell->offset_x) / SCALEFACTOR_X (shell) - offset_x); + *ny = (gint) ((y + shell->offset_y) / SCALEFACTOR_Y (shell) - offset_y); } } @@ -223,19 +199,13 @@ gimp_display_shell_transform_xy_f (GimpDisplayShell *shell, gdouble *ny, gboolean use_offsets) { - gdouble scalex; - gdouble scaley; - gint offset_x = 0; - gint offset_y = 0; + gint offset_x = 0; + gint offset_y = 0; g_return_if_fail (GIMP_IS_DISPLAY_SHELL (shell)); g_return_if_fail (nx != NULL); g_return_if_fail (ny != NULL); - /* transform from gimp coordinates to screen coordinates */ - scalex = SCALEFACTOR_X (shell); - scaley = SCALEFACTOR_Y (shell); - if (use_offsets) { GimpItem *item; @@ -244,8 +214,8 @@ gimp_display_shell_transform_xy_f (GimpDisplayShell *shell, gimp_item_offsets (item, &offset_x, &offset_y); } - *nx = scalex * (x + offset_x) - shell->offset_x; - *ny = scaley * (y + offset_y) - shell->offset_y; + *nx = SCALEFACTOR_X (shell) * (x + offset_x) - shell->offset_x; + *ny = SCALEFACTOR_Y (shell) * (y + offset_y) - shell->offset_y; *nx += shell->disp_xoffset; *ny += shell->disp_yoffset; @@ -273,10 +243,8 @@ gimp_display_shell_untransform_xy_f (GimpDisplayShell *shell, gdouble *ny, gboolean use_offsets) { - gdouble scalex; - gdouble scaley; - gint offset_x = 0; - gint offset_y = 0; + gint offset_x = 0; + gint offset_y = 0; g_return_if_fail (GIMP_IS_DISPLAY_SHELL (shell)); g_return_if_fail (nx != NULL); @@ -285,10 +253,6 @@ gimp_display_shell_untransform_xy_f (GimpDisplayShell *shell, x -= shell->disp_xoffset; y -= shell->disp_yoffset; - /* transform from screen coordinates to gimp coordinates */ - scalex = SCALEFACTOR_X (shell); - scaley = SCALEFACTOR_Y (shell); - if (use_offsets) { GimpItem *item; @@ -297,8 +261,8 @@ gimp_display_shell_untransform_xy_f (GimpDisplayShell *shell, gimp_item_offsets (item, &offset_x, &offset_y); } - *nx = (x + shell->offset_x) / scalex - offset_x; - *ny = (y + shell->offset_y) / scaley - offset_y; + *nx = (x + shell->offset_x) / SCALEFACTOR_X (shell) - offset_x; + *ny = (y + shell->offset_y) / SCALEFACTOR_Y (shell) - offset_y; } /** diff --git a/app/display/gimpdisplayshell.c b/app/display/gimpdisplayshell.c index abac7d189c..ec669a2c4d 100644 --- a/app/display/gimpdisplayshell.c +++ b/app/display/gimpdisplayshell.c @@ -221,6 +221,9 @@ gimp_display_shell_init (GimpDisplayShell *shell) shell->offset_x = 0; shell->offset_y = 0; + shell->scale_factor_x = 1.0; + shell->scale_factor_y = 1.0; + shell->last_scale = 0.0; shell->last_scale_time = 0; shell->last_offset_x = 0; @@ -323,6 +326,11 @@ gimp_display_shell_init (GimpDisplayShell *shell) GDK_VISIBILITY_NOTIFY_MASK | GDK_SCROLL_MASK)); + /* zoom model callback */ + g_signal_connect_swapped (shell->zoom, "zoomed", + G_CALLBACK (gimp_display_shell_scale_factor_changed), + shell); + /* active display callback */ g_signal_connect (shell, "button-press-event", G_CALLBACK (gimp_display_shell_events), @@ -1096,6 +1104,26 @@ gimp_display_shell_reconnect (GimpDisplayShell *shell) gimp_display_shell_scaled (shell); } +/* + * We used to calculate the scale factor in the SCALEFACTOR_X() and + * SCALEFACTOR_Y() macros. But since these are rather frequently + * called and the values rarely change, we now store them in the + * shell and call this function whenever they need to be recalculated. + */ +void +gimp_display_shell_scale_factor_changed (GimpDisplayShell *shell) +{ + g_return_if_fail (GIMP_IS_DISPLAY_SHELL (shell)); + + shell->scale_factor_x = (gimp_zoom_model_get_factor (shell->zoom) + * SCREEN_XRES (shell) + / shell->display->image->xresolution); + + shell->scale_factor_y = (gimp_zoom_model_get_factor (shell->zoom) + * SCREEN_YRES (shell) + / shell->display->image->yresolution); +} + void gimp_display_shell_scaled (GimpDisplayShell *shell) { diff --git a/app/display/gimpdisplayshell.h b/app/display/gimpdisplayshell.h index d5e3d53eb5..46e265937b 100644 --- a/app/display/gimpdisplayshell.h +++ b/app/display/gimpdisplayshell.h @@ -35,10 +35,8 @@ (s)->display->image->yresolution : (s)->monitor_yres) /* calculate scale factors (double) */ -#define SCALEFACTOR_X(s) (gimp_zoom_model_get_factor ((s)->zoom) \ - * SCREEN_XRES(s) / (s)->display->image->xresolution) -#define SCALEFACTOR_Y(s) (gimp_zoom_model_get_factor ((s)->zoom) \ - * SCREEN_YRES(s) / (s)->display->image->yresolution) +#define SCALEFACTOR_X(s) (s->scale_factor_x) +#define SCALEFACTOR_Y(s) (s->scale_factor_y) /* scale values */ #define SCALEX(s,x) PROJ_ROUND ((x) * SCALEFACTOR_X(s)) @@ -83,6 +81,9 @@ struct _GimpDisplayShell gint offset_x; /* offset of display image into raw image */ gint offset_y; + gdouble scale_factor_x; /* cache for scale factor */ + gdouble scale_factor_y; /* cache for scale factor */ + gdouble last_scale; /* scale used when reverting zoom */ guint last_scale_time; /* time when last_scale was set */ gint last_offset_x; /* offsets used when reverting zoom */ @@ -200,6 +201,8 @@ GtkWidget * gimp_display_shell_new (GimpDisplay *display, void gimp_display_shell_reconnect (GimpDisplayShell *shell); +void gimp_display_shell_scale_factor_changed (GimpDisplayShell *shell); + void gimp_display_shell_scaled (GimpDisplayShell *shell); void gimp_display_shell_scrolled (GimpDisplayShell *shell); diff --git a/app/display/gimpnavigationeditor.c b/app/display/gimpnavigationeditor.c index b2ba92ca24..29ab189a88 100644 --- a/app/display/gimpnavigationeditor.c +++ b/app/display/gimpnavigationeditor.c @@ -323,19 +323,19 @@ gimp_navigation_editor_new_private (GimpMenuFactory *menu_factory, if (shell) { - GimpDisplayConfig *config; + Gimp *gimp = shell->display->image->gimp; + GimpDisplayConfig *config = GIMP_DISPLAY_CONFIG (gimp->config); GimpView *view; editor = g_object_new (GIMP_TYPE_NAVIGATION_EDITOR, NULL); - config = GIMP_DISPLAY_CONFIG (shell->display->image->gimp->config); - view = GIMP_VIEW (editor->view); + view = GIMP_VIEW (editor->view); gimp_view_renderer_set_size (view->renderer, config->nav_preview_size * 3, view->renderer->border_width); gimp_view_renderer_set_context (view->renderer, - gimp_get_user_context (shell->display->image->gimp)); + gimp_get_user_context (gimp)); gimp_navigation_editor_set_shell (editor, shell); @@ -492,18 +492,14 @@ gimp_navigation_editor_marker_changed (GimpNavigationView *view, { if (editor->shell) { - gdouble xratio; - gdouble yratio; - gint xoffset; - gint yoffset; + GimpDisplayShell *shell = editor->shell; + gint xoffset; + gint yoffset; - xratio = SCALEFACTOR_X (editor->shell); - yratio = SCALEFACTOR_Y (editor->shell); + xoffset = RINT (x * SCALEFACTOR_X (shell) - shell->offset_x); + yoffset = RINT (y * SCALEFACTOR_Y (shell) - shell->offset_y); - xoffset = RINT (x * xratio - editor->shell->offset_x); - yoffset = RINT (y * yratio - editor->shell->offset_y); - - gimp_display_shell_scroll (editor->shell, xoffset, yoffset); + gimp_display_shell_scroll (shell, xoffset, yoffset); } } @@ -638,22 +634,17 @@ gimp_navigation_editor_shell_reconnect (GimpDisplayShell *shell, static void gimp_navigation_editor_update_marker (GimpNavigationEditor *editor) { - GimpViewRenderer *renderer; - gdouble xratio; - gdouble yratio; + GimpViewRenderer *renderer = GIMP_VIEW (editor->view)->renderer; + GimpDisplayShell *shell = editor->shell; + gdouble xratio = SCALEFACTOR_X (shell); + gdouble yratio = SCALEFACTOR_Y (shell); - renderer = GIMP_VIEW (editor->view)->renderer; - - xratio = SCALEFACTOR_X (editor->shell); - yratio = SCALEFACTOR_Y (editor->shell); - - if (renderer->dot_for_dot != editor->shell->dot_for_dot) - gimp_view_renderer_set_dot_for_dot (renderer, - editor->shell->dot_for_dot); + if (renderer->dot_for_dot != shell->dot_for_dot) + gimp_view_renderer_set_dot_for_dot (renderer, shell->dot_for_dot); gimp_navigation_view_set_marker (GIMP_NAVIGATION_VIEW (editor->view), - editor->shell->offset_x / xratio, - editor->shell->offset_y / yratio, - editor->shell->disp_width / xratio, - editor->shell->disp_height / yratio); + shell->offset_x / xratio, + shell->offset_y / yratio, + shell->disp_width / xratio, + shell->disp_height / yratio); }