diff --git a/ChangeLog b/ChangeLog index 0ead866c2e..bd204d0c57 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,15 @@ +2003-04-04 Sven Neumann + + * app/display/gimpdisplayshell-scale.c + (gimp_display_shell_scale_fit): extended range of possible zoom + ratios like in the other scaling routines. + + * app/display/gimpdisplayshell-scale.[ch] + * app/display/gimpdisplayshell.[ch] + * app/gui/image-menu.c + * app/gui/view-commands.[ch]: added a dialog to menually enter the + zoom ratio. Fixes bug #65057. + 2003-04-03 Michael Natterer Added preliminary support for image templates. Not finished diff --git a/app/actions/view-commands.c b/app/actions/view-commands.c index 86e97d8dd4..9bcef5363d 100644 --- a/app/actions/view-commands.c +++ b/app/actions/view-commands.c @@ -109,6 +109,27 @@ view_zoom_cmd_callback (GtkWidget *widget, gimp_display_shell_scale (shell, action); } +void +view_zoom_other_cmd_callback (GtkWidget *widget, + gpointer data) +{ + GimpDisplay *gdisp; + GimpDisplayShell *shell; + return_if_no_display (gdisp, data); + + if (! GTK_CHECK_MENU_ITEM (widget)->active) + return; + + shell = GIMP_DISPLAY_SHELL (gdisp->shell); + + /* check if we are activated by the user or from image_menu_set_zoom() */ + if (shell->scale != shell->other_scale) + gimp_display_shell_scale_dialog (shell); + + /* flag as dirty */ + shell->other_scale |= (1 << 30); +} + void view_dot_for_dot_cmd_callback (GtkWidget *widget, gpointer data) diff --git a/app/actions/view-commands.h b/app/actions/view-commands.h index 8e5f737eaa..2bd402d7c7 100644 --- a/app/actions/view-commands.h +++ b/app/actions/view-commands.h @@ -29,6 +29,8 @@ void view_zoom_fit_cmd_callback (GtkWidget *widget, void view_zoom_cmd_callback (GtkWidget *widget, gpointer data, guint action); +void view_zoom_other_cmd_callback (GtkWidget *widget, + gpointer data); void view_dot_for_dot_cmd_callback (GtkWidget *widget, gpointer data); void view_fullscreen_cmd_callback (GtkWidget *widget, diff --git a/app/display/gimpdisplayshell-draw.c b/app/display/gimpdisplayshell-draw.c index bc739337aa..b5faa9b185 100644 --- a/app/display/gimpdisplayshell-draw.c +++ b/app/display/gimpdisplayshell-draw.c @@ -188,7 +188,8 @@ gimp_display_shell_init (GimpDisplayShell *shell) shell->popup_factory = NULL; shell->qmask_factory = NULL; - shell->scale = 0; + shell->scale = 0x101; + shell->other_scale = 0; shell->dot_for_dot = TRUE; shell->offset_x = 0; @@ -246,6 +247,7 @@ gimp_display_shell_init (GimpDisplayShell *shell) shell->warning_dialog = NULL; shell->info_dialog = NULL; + shell->scale_dialog = NULL; shell->nav_popup = NULL; shell->filters = NULL; diff --git a/app/display/gimpdisplayshell-draw.h b/app/display/gimpdisplayshell-draw.h index d227d25190..d77980a582 100644 --- a/app/display/gimpdisplayshell-draw.h +++ b/app/display/gimpdisplayshell-draw.h @@ -94,6 +94,7 @@ struct _GimpDisplayShell gdouble monitor_yres; gint scale; /* scale factor from original raw image */ + gint other_scale; /* scale factor entered in Zoom->Other */ gboolean dot_for_dot; /* is monitor resolution being ignored? */ gint offset_x; /* offset of display image into raw image */ @@ -153,6 +154,7 @@ struct _GimpDisplayShell GtkWidget *warning_dialog; /* close warning dialog */ InfoDialog *info_dialog; /* image information dialog */ + GtkWidget *scale_dialog; /* scale (zoom) dialog */ GtkWidget *nav_popup; /* navigation popup */ GList *filters; /* color display conversion stuff */ diff --git a/app/display/gimpdisplayshell-scale.c b/app/display/gimpdisplayshell-scale.c index 3f8712e69d..45133779ae 100644 --- a/app/display/gimpdisplayshell-scale.c +++ b/app/display/gimpdisplayshell-scale.c @@ -23,6 +23,7 @@ #include #include "libgimpbase/gimpbase.h" +#include "libgimpwidgets/gimpwidgets.h" #include "display-types.h" @@ -35,6 +36,8 @@ #include "tools/tool_manager.h" +#include "widgets/gimpviewabledialog.h" + #include "gimpdisplay.h" #include "gimpdisplayshell.h" #include "gimpdisplayshell-scale.h" @@ -42,12 +45,19 @@ #include "gimpdisplayshell-title.h" #include "gimpstatusbar.h" +#include "gimp-intl.h" + /* local function prototypes */ -static gdouble img2real (GimpDisplayShell *shell, - gboolean xdir, - gdouble a); +static void gimp_display_shell_scale_dialog_ok (GtkWidget *widget, + gpointer data); +static void gimp_display_shell_scale_dialog_cancel (GtkWidget *widget, + gpointer data); + +static gdouble img2real (GimpDisplayShell *shell, + gboolean xdir, + gdouble a); /* public functions */ @@ -265,7 +275,7 @@ gimp_display_shell_scale_fit (GimpDisplayShell *shell) gint scalesrc = 1; gint scaledest = 1; gint i; - gint best_i = 0x10; + gint best_i = 0xFF; g_return_if_fail (GIMP_IS_DISPLAY_SHELL (shell)); @@ -298,7 +308,7 @@ gimp_display_shell_scale_fit (GimpDisplayShell *shell) if (zoom_factor < 1.0) { - for (i = 0x10; i > 0; i--) + for (i = 0xFF; i > 0; i--) { scalesrc = i; scaledest = floor ((gdouble) scalesrc * zoom_factor); @@ -328,7 +338,7 @@ gimp_display_shell_scale_fit (GimpDisplayShell *shell) } else { - for (i = 0x10; i > 0; i--) + for (i = 0xFF; i > 0; i--) { scaledest = i; scalesrc = ceil ((gdouble) scaledest / zoom_factor); @@ -427,8 +437,124 @@ gimp_display_shell_scale_resize (GimpDisplayShell *shell, } +typedef struct +{ + GimpDisplayShell *shell; + GtkObject *src_adj; + GtkObject *dest_adj; +} ScaleDialogData; + +void +gimp_display_shell_scale_dialog (GimpDisplayShell *shell) +{ + ScaleDialogData *data; + GtkWidget *hbox; + GtkWidget *spin; + GtkWidget *label; + + g_return_if_fail (GIMP_IS_DISPLAY_SHELL (shell)); + + if (shell->scale_dialog) + { + gtk_window_present (GTK_WINDOW (shell->scale_dialog)); + return; + } + + data = g_new (ScaleDialogData, 1); + data->shell = shell; + + shell->scale_dialog = + gimp_viewable_dialog_new (GIMP_VIEWABLE (shell->gdisp->gimage), + _("Zoom Ratio"), "display_scale", + GTK_STOCK_ZOOM_100, + _("Select Zoom Ratio"), + gimp_standard_help_func, + "dialogs/display_scale.html", + + GTK_STOCK_CANCEL, gimp_display_shell_scale_dialog_cancel, + data, NULL, NULL, FALSE, TRUE, + + GTK_STOCK_OK, gimp_display_shell_scale_dialog_ok, + data, NULL, NULL, TRUE, FALSE, + + NULL); + + g_object_weak_ref (G_OBJECT (shell->scale_dialog), + (GWeakNotify) g_free, data); + g_object_add_weak_pointer (G_OBJECT (shell->scale_dialog), + (gpointer *) &shell->scale_dialog); + + gtk_window_set_transient_for (GTK_WINDOW (shell->scale_dialog), + GTK_WINDOW (shell)); + gtk_window_set_destroy_with_parent (GTK_WINDOW (shell->scale_dialog), TRUE); + + hbox = gtk_hbox_new (FALSE, 4); + gtk_container_set_border_width (GTK_CONTAINER (hbox), 8); + gtk_container_add (GTK_CONTAINER (GTK_DIALOG (shell->scale_dialog)->vbox), + hbox); + gtk_widget_show (hbox); + + label = gtk_label_new (_("Zoom Ratio:")); + gtk_box_pack_start (GTK_BOX (hbox), label, FALSE, FALSE, 0); + gtk_widget_show (label); + + if (!shell->other_scale) + shell->other_scale = shell->scale; + + spin = gimp_spin_button_new (&data->dest_adj, + (shell->other_scale & 0xFF00) >> 8, 1, 0xFF, + 1, 8, 1, 1, 0); + gtk_box_pack_start (GTK_BOX (hbox), spin, TRUE, TRUE, 0); + gtk_widget_show (spin); + + label = gtk_label_new (":"); + gtk_box_pack_start (GTK_BOX (hbox), label, FALSE, FALSE, 0); + gtk_widget_show (label); + + spin = gimp_spin_button_new (&data->src_adj, + (shell->other_scale & 0xFF), 1, 0xFF, + 1, 8, 1, 1, 0); + gtk_box_pack_start (GTK_BOX (hbox), spin, TRUE, TRUE, 0); + gtk_widget_show (spin); + + gtk_widget_show (shell->scale_dialog); +} + + /* private functions */ +static void +gimp_display_shell_scale_dialog_ok (GtkWidget *widget, + gpointer data) +{ + ScaleDialogData *dialog = (ScaleDialogData *) data; + + gint scale_src; + gint scale_dest; + + scale_src = gtk_adjustment_get_value (GTK_ADJUSTMENT (dialog->src_adj)); + scale_dest = gtk_adjustment_get_value (GTK_ADJUSTMENT (dialog->dest_adj)); + + gimp_display_shell_scale (dialog->shell, scale_dest * 100 + scale_src); + dialog->shell->other_scale |= (1 << 30); + + gtk_widget_destroy (dialog->shell->scale_dialog); +} + +static void +gimp_display_shell_scale_dialog_cancel (GtkWidget *widget, + gpointer data) +{ + ScaleDialogData *dialog = (ScaleDialogData *) data; + + /* need to emit "scaled" to get the menu updated */ + gimp_display_shell_scaled (dialog->shell); + dialog->shell->other_scale |= (1 << 30); + + gtk_widget_destroy (dialog->shell->scale_dialog); +} + + /* scale image coord to realworld units (cm, inches, pixels) * * 27/Feb/1999 I tried inlining this, but the result was slightly diff --git a/app/display/gimpdisplayshell-scale.h b/app/display/gimpdisplayshell-scale.h index eec8c08a3a..9c946c7e8e 100644 --- a/app/display/gimpdisplayshell-scale.h +++ b/app/display/gimpdisplayshell-scale.h @@ -38,6 +38,7 @@ void gimp_display_shell_scale_shrink_wrap (GimpDisplayShell *shell); void gimp_display_shell_scale_resize (GimpDisplayShell *shell, gboolean resize_window, gboolean redisplay); +void gimp_display_shell_scale_dialog (GimpDisplayShell *shell); #endif /* __GIMP_DISPLAY_SHELL_SCALE_H__ */ diff --git a/app/display/gimpdisplayshell.c b/app/display/gimpdisplayshell.c index bc739337aa..b5faa9b185 100644 --- a/app/display/gimpdisplayshell.c +++ b/app/display/gimpdisplayshell.c @@ -188,7 +188,8 @@ gimp_display_shell_init (GimpDisplayShell *shell) shell->popup_factory = NULL; shell->qmask_factory = NULL; - shell->scale = 0; + shell->scale = 0x101; + shell->other_scale = 0; shell->dot_for_dot = TRUE; shell->offset_x = 0; @@ -246,6 +247,7 @@ gimp_display_shell_init (GimpDisplayShell *shell) shell->warning_dialog = NULL; shell->info_dialog = NULL; + shell->scale_dialog = NULL; shell->nav_popup = NULL; shell->filters = NULL; diff --git a/app/display/gimpdisplayshell.h b/app/display/gimpdisplayshell.h index d227d25190..d77980a582 100644 --- a/app/display/gimpdisplayshell.h +++ b/app/display/gimpdisplayshell.h @@ -94,6 +94,7 @@ struct _GimpDisplayShell gdouble monitor_yres; gint scale; /* scale factor from original raw image */ + gint other_scale; /* scale factor entered in Zoom->Other */ gboolean dot_for_dot; /* is monitor resolution being ignored? */ gint offset_x; /* offset of display image into raw image */ @@ -153,6 +154,7 @@ struct _GimpDisplayShell GtkWidget *warning_dialog; /* close warning dialog */ InfoDialog *info_dialog; /* image information dialog */ + GtkWidget *scale_dialog; /* scale (zoom) dialog */ GtkWidget *nav_popup; /* navigation popup */ GList *filters; /* color display conversion stuff */ diff --git a/app/gui/image-menu.c b/app/gui/image-menu.c index 67f1155b18..fb4b69d521 100644 --- a/app/gui/image-menu.c +++ b/app/gui/image-menu.c @@ -355,8 +355,11 @@ GimpItemFactoryEntry image_menu_entries[] = view_zoom_cmd_callback, 116, "/View/Zoom/16:1" }, NULL, "view/zoom.html", NULL }, - { { "/View/Zoom/Other", NULL, - NULL, 0, "/View/Zoom/16:1" }, + + MENU_SEPARATOR ("/View/Zoom/---"), + + { { "/View/Zoom/Other...", NULL, + view_zoom_other_cmd_callback, 0, "/View/Zoom/16:1" }, NULL, "view/zoom.html", NULL }, @@ -1259,16 +1262,17 @@ image_menu_update (GtkItemFactory *item_factory, SET_SENSITIVE ("/View/Zoom/Zoom Out", gdisp); SET_SENSITIVE ("/View/Zoom/Zoom to Fit Window", gdisp); - SET_SENSITIVE ("/View/Zoom/16:1", gdisp); - SET_SENSITIVE ("/View/Zoom/8:1", gdisp); - SET_SENSITIVE ("/View/Zoom/4:1", gdisp); - SET_SENSITIVE ("/View/Zoom/2:1", gdisp); - SET_SENSITIVE ("/View/Zoom/1:1", gdisp); - SET_SENSITIVE ("/View/Zoom/1:2", gdisp); - SET_SENSITIVE ("/View/Zoom/1:4", gdisp); - SET_SENSITIVE ("/View/Zoom/1:8", gdisp); - SET_SENSITIVE ("/View/Zoom/1:16", gdisp); - SET_SENSITIVE ("/View/Zoom/Other", gdisp); + SET_SENSITIVE ("/View/Zoom/16:1", gdisp); + SET_SENSITIVE ("/View/Zoom/8:1", gdisp); + SET_SENSITIVE ("/View/Zoom/4:1", gdisp); + SET_SENSITIVE ("/View/Zoom/2:1", gdisp); + SET_SENSITIVE ("/View/Zoom/1:1", gdisp); + SET_SENSITIVE ("/View/Zoom/1:2", gdisp); + SET_SENSITIVE ("/View/Zoom/1:4", gdisp); + SET_SENSITIVE ("/View/Zoom/1:8", gdisp); + SET_SENSITIVE ("/View/Zoom/1:16", gdisp); + + SET_SENSITIVE ("/View/Zoom/Other...", gdisp); if (gdisp) image_menu_set_zoom (item_factory, shell); @@ -1430,21 +1434,15 @@ image_menu_set_zoom (GtkItemFactory *item_factory, } } - if (menu) + if (!menu) { - gimp_item_factory_set_label (item_factory, "/View/Zoom/Other",_("Other")); - gimp_item_factory_set_sensitive (item_factory, "/View/Zoom/Other", FALSE); - } - else - { - menu = "/View/Zoom/Other"; - - label = g_strdup_printf (_("Other (%d:%d)"), scaledest, scalesrc); + menu = "/View/Zoom/Other..."; + label = g_strdup_printf (_("Other (%d:%d) ..."), scaledest, scalesrc); gimp_item_factory_set_label (item_factory, menu, label); - gimp_item_factory_set_sensitive (item_factory, menu, TRUE); + g_free (label); - g_free (label); + shell->other_scale = shell->scale; } gimp_item_factory_set_active (item_factory, menu, TRUE); diff --git a/app/gui/view-commands.c b/app/gui/view-commands.c index 86e97d8dd4..9bcef5363d 100644 --- a/app/gui/view-commands.c +++ b/app/gui/view-commands.c @@ -109,6 +109,27 @@ view_zoom_cmd_callback (GtkWidget *widget, gimp_display_shell_scale (shell, action); } +void +view_zoom_other_cmd_callback (GtkWidget *widget, + gpointer data) +{ + GimpDisplay *gdisp; + GimpDisplayShell *shell; + return_if_no_display (gdisp, data); + + if (! GTK_CHECK_MENU_ITEM (widget)->active) + return; + + shell = GIMP_DISPLAY_SHELL (gdisp->shell); + + /* check if we are activated by the user or from image_menu_set_zoom() */ + if (shell->scale != shell->other_scale) + gimp_display_shell_scale_dialog (shell); + + /* flag as dirty */ + shell->other_scale |= (1 << 30); +} + void view_dot_for_dot_cmd_callback (GtkWidget *widget, gpointer data) diff --git a/app/gui/view-commands.h b/app/gui/view-commands.h index 8e5f737eaa..2bd402d7c7 100644 --- a/app/gui/view-commands.h +++ b/app/gui/view-commands.h @@ -29,6 +29,8 @@ void view_zoom_fit_cmd_callback (GtkWidget *widget, void view_zoom_cmd_callback (GtkWidget *widget, gpointer data, guint action); +void view_zoom_other_cmd_callback (GtkWidget *widget, + gpointer data); void view_dot_for_dot_cmd_callback (GtkWidget *widget, gpointer data); void view_fullscreen_cmd_callback (GtkWidget *widget, diff --git a/app/menus/image-menu.c b/app/menus/image-menu.c index 67f1155b18..fb4b69d521 100644 --- a/app/menus/image-menu.c +++ b/app/menus/image-menu.c @@ -355,8 +355,11 @@ GimpItemFactoryEntry image_menu_entries[] = view_zoom_cmd_callback, 116, "/View/Zoom/16:1" }, NULL, "view/zoom.html", NULL }, - { { "/View/Zoom/Other", NULL, - NULL, 0, "/View/Zoom/16:1" }, + + MENU_SEPARATOR ("/View/Zoom/---"), + + { { "/View/Zoom/Other...", NULL, + view_zoom_other_cmd_callback, 0, "/View/Zoom/16:1" }, NULL, "view/zoom.html", NULL }, @@ -1259,16 +1262,17 @@ image_menu_update (GtkItemFactory *item_factory, SET_SENSITIVE ("/View/Zoom/Zoom Out", gdisp); SET_SENSITIVE ("/View/Zoom/Zoom to Fit Window", gdisp); - SET_SENSITIVE ("/View/Zoom/16:1", gdisp); - SET_SENSITIVE ("/View/Zoom/8:1", gdisp); - SET_SENSITIVE ("/View/Zoom/4:1", gdisp); - SET_SENSITIVE ("/View/Zoom/2:1", gdisp); - SET_SENSITIVE ("/View/Zoom/1:1", gdisp); - SET_SENSITIVE ("/View/Zoom/1:2", gdisp); - SET_SENSITIVE ("/View/Zoom/1:4", gdisp); - SET_SENSITIVE ("/View/Zoom/1:8", gdisp); - SET_SENSITIVE ("/View/Zoom/1:16", gdisp); - SET_SENSITIVE ("/View/Zoom/Other", gdisp); + SET_SENSITIVE ("/View/Zoom/16:1", gdisp); + SET_SENSITIVE ("/View/Zoom/8:1", gdisp); + SET_SENSITIVE ("/View/Zoom/4:1", gdisp); + SET_SENSITIVE ("/View/Zoom/2:1", gdisp); + SET_SENSITIVE ("/View/Zoom/1:1", gdisp); + SET_SENSITIVE ("/View/Zoom/1:2", gdisp); + SET_SENSITIVE ("/View/Zoom/1:4", gdisp); + SET_SENSITIVE ("/View/Zoom/1:8", gdisp); + SET_SENSITIVE ("/View/Zoom/1:16", gdisp); + + SET_SENSITIVE ("/View/Zoom/Other...", gdisp); if (gdisp) image_menu_set_zoom (item_factory, shell); @@ -1430,21 +1434,15 @@ image_menu_set_zoom (GtkItemFactory *item_factory, } } - if (menu) + if (!menu) { - gimp_item_factory_set_label (item_factory, "/View/Zoom/Other",_("Other")); - gimp_item_factory_set_sensitive (item_factory, "/View/Zoom/Other", FALSE); - } - else - { - menu = "/View/Zoom/Other"; - - label = g_strdup_printf (_("Other (%d:%d)"), scaledest, scalesrc); + menu = "/View/Zoom/Other..."; + label = g_strdup_printf (_("Other (%d:%d) ..."), scaledest, scalesrc); gimp_item_factory_set_label (item_factory, menu, label); - gimp_item_factory_set_sensitive (item_factory, menu, TRUE); + g_free (label); - g_free (label); + shell->other_scale = shell->scale; } gimp_item_factory_set_active (item_factory, menu, TRUE); diff --git a/po/POTFILES.in b/po/POTFILES.in index 09bcafa62e..f9a1b1debc 100644 --- a/po/POTFILES.in +++ b/po/POTFILES.in @@ -67,6 +67,7 @@ app/display/gimpdisplayshell-callbacks.c app/display/gimpdisplayshell-dnd.c app/display/gimpdisplayshell-filter-dialog.c app/display/gimpdisplayshell-layer-select.c +app/display/gimpdisplayshell-scale.c app/display/gimpdisplayshell-title.c app/display/gimpnavigationview.c app/display/gimpprogress.c