[gnome-photos] Encode the origin of the zoom event in the zoom-in/out GActions
- From: Debarshi Ray <debarshir src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gnome-photos] Encode the origin of the zoom event in the zoom-in/out GActions
- Date: Tue, 17 Oct 2017 08:46:31 +0000 (UTC)
commit ca66ca7aa4a88cede77af9c804f79a5000962447
Author: Debarshi Ray <debarshir gnome org>
Date: Thu Oct 12 00:25:20 2017 +0200
Encode the origin of the zoom event in the zoom-in/out GActions
A subsequent commit will add support for zooming with touch gestures.
This added flexibility readies the GActions for that.
The current zooming interface provided by the zoom-in/out GActions is
based on the notion of incremental steps. Each step represents one
press/release of an accelerator key or mouse button, or one notch on
the mouse's scroll wheel. A new zoom value is calculated for each step.
However, touch gestures are different. The content needs to stick to
the touch points while the gesture is active. This means that the ratio
of the new and initial zoom values should be equal to the ratio of the
distance between the touch points and their initial distance. This is
unlike the notion of discrete steps where the content would jump to
the next zoom level.
Commit 9590011fedb8e088 had hacked in the ability to encode the origin
of the zoom event by using positive and negative arguments. This has
been made more explicit by having a separate enumerated value for it.
https://bugzilla.gnome.org/show_bug.cgi?id=783922
src/Makefile.am | 2 +
src/photos-application.c | 19 ++++++--
src/photos-enums.c.template | 1 +
src/photos-preview-view.c | 70 ++++++++++++++++++++--------
src/photos-utils.c | 107 +++++++++++++++++++++++++++++++++++++++++++
src/photos-utils.h | 18 +++++++
src/photos-zoom-controls.c | 8 +++-
src/photos-zoom-controls.ui | 4 +-
8 files changed, 203 insertions(+), 26 deletions(-)
---
diff --git a/src/Makefile.am b/src/Makefile.am
index 8bb7897..f8ff96a 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -506,6 +506,7 @@ stamp-photos-enums.h: photos-enums.h.template
--template $(srcdir)/photos-enums.h.template \
$(srcdir)/photos-item-manager.h \
$(srcdir)/photos-operation-insta-common.h \
+ $(srcdir)/photos-utils.h \
) >> xgen-etbh \
&& ( cmp -s xgen-etbh photos-enums.h || cp xgen-etbh photos-enums.h ) \
&& rm -f xgen-etbh \
@@ -518,6 +519,7 @@ photos-enums.c: photos-enums.c.template
--template $(srcdir)/photos-enums.c.template \
$(srcdir)/photos-item-manager.h \
$(srcdir)/photos-operation-insta-common.h \
+ $(srcdir)/photos-utils.h \
) >> xgen-etbc \
&& ( cmp -s xgen-etbc photos-enums.c || cp xgen-etbc photos-enums.c ) \
&& rm -f xgen-etbc \
diff --git a/src/photos-application.c b/src/photos-application.c
index 3a4b02c..4957d98 100644
--- a/src/photos-application.c
+++ b/src/photos-application.c
@@ -1853,6 +1853,7 @@ photos_application_startup (GApplication *application)
const gchar *zoom_best_fit_accels[3] = {"<Primary>0", NULL};
const gchar *zoom_in_accels[3] = {"<Primary>plus", "<Primary>equal", NULL};
const gchar *zoom_out_accels[2] = {"<Primary>minus", NULL};
+ gchar *detailed_action_name = NULL;
photos_debug (PHOTOS_DEBUG_APPLICATION, "PhotosApplication::startup");
@@ -2062,10 +2063,10 @@ photos_application_startup (GApplication *application)
self->zoom_best_fit_action = g_simple_action_new ("zoom-best-fit", NULL);
g_action_map_add_action (G_ACTION_MAP (self), G_ACTION (self->zoom_best_fit_action));
- self->zoom_in_action = g_simple_action_new ("zoom-in", G_VARIANT_TYPE_DOUBLE);
+ self->zoom_in_action = g_simple_action_new ("zoom-in", G_VARIANT_TYPE_VARDICT);
g_action_map_add_action (G_ACTION_MAP (self), G_ACTION (self->zoom_in_action));
- self->zoom_out_action = g_simple_action_new ("zoom-out", G_VARIANT_TYPE_DOUBLE);
+ self->zoom_out_action = g_simple_action_new ("zoom-out", G_VARIANT_TYPE_VARDICT);
g_action_map_add_action (G_ACTION_MAP (self), G_ACTION (self->zoom_out_action));
g_signal_connect_swapped (self->state->mode_cntrlr,
@@ -2089,8 +2090,18 @@ photos_application_startup (GApplication *application)
gtk_application_set_accels_for_action (GTK_APPLICATION (self), "app.search", search_accels);
gtk_application_set_accels_for_action (GTK_APPLICATION (self), "app.select-all", select_all_accels);
gtk_application_set_accels_for_action (GTK_APPLICATION (self), "app.zoom-best-fit", zoom_best_fit_accels);
- gtk_application_set_accels_for_action (GTK_APPLICATION (self), "app.zoom-in(-1.0)", zoom_in_accels);
- gtk_application_set_accels_for_action (GTK_APPLICATION (self), "app.zoom-out(-1.0)", zoom_out_accels);
+
+ detailed_action_name = photos_utils_print_zoom_action_detailed_name ("app.zoom-in",
+ 1.0,
+
PHOTOS_ZOOM_EVENT_KEYBOARD_ACCELERATOR);
+ gtk_application_set_accels_for_action (GTK_APPLICATION (self), detailed_action_name, zoom_in_accels);
+ g_free (detailed_action_name);
+
+ detailed_action_name = photos_utils_print_zoom_action_detailed_name ("app.zoom-out",
+ 1.0,
+
PHOTOS_ZOOM_EVENT_KEYBOARD_ACCELERATOR);
+ gtk_application_set_accels_for_action (GTK_APPLICATION (self), detailed_action_name, zoom_out_accels);
+ g_free (detailed_action_name);
g_signal_connect_swapped (self->state->item_mngr,
"items-changed",
diff --git a/src/photos-enums.c.template b/src/photos-enums.c.template
index 3b07c67..e93d20d 100644
--- a/src/photos-enums.c.template
+++ b/src/photos-enums.c.template
@@ -5,6 +5,7 @@
#include "photos-enums.h"
#include "photos-item-manager.h"
#include "photos-operation-insta-common.h"
+#include "photos-utils.h"
/*** END file-header ***/
diff --git a/src/photos-preview-view.c b/src/photos-preview-view.c
index 771036a..6d90873 100644
--- a/src/photos-preview-view.c
+++ b/src/photos-preview-view.c
@@ -410,7 +410,7 @@ photos_preview_view_scroll_event (GtkWidget *widget, GdkEvent *event, gpointer u
goto out;
delta_abs = fabs (event->scroll.delta_y);
- parameter = g_variant_new_double (delta_abs);
+ parameter = photos_utils_create_zoom_target_value (delta_abs, PHOTOS_ZOOM_EVENT_SCROLL);
parameter = g_variant_ref_sink (parameter);
if (event->scroll.delta_y < 0.0)
@@ -856,30 +856,46 @@ photos_preview_view_zoom_in (PhotosPreviewView *self, GVariant *parameter)
{
GtkWidget *view;
GtkWidget *view_container;
+ PhotosZoomEvent event;
gboolean best_fit;
gdouble delta;
- gdouble delta_abs;
gdouble zoom;
gdouble zoom_factor;
gdouble zoom_factor_for_delta;
g_return_if_fail (self->zoom_best_fit > 0.0);
- delta = g_variant_get_double (parameter);
- g_return_if_fail (photos_utils_equal_double (delta, -1.0) || delta >= 0.0);
+ event = photos_utils_get_zoom_event (parameter);
+ g_return_if_fail (event != PHOTOS_ZOOM_EVENT_NONE);
+
+ delta = photos_utils_get_zoom_delta (parameter);
+ g_return_if_fail ((event == PHOTOS_ZOOM_EVENT_KEYBOARD_ACCELERATOR && photos_utils_equal_double (delta,
1.0))
+ || (event == PHOTOS_ZOOM_EVENT_MOUSE_CLICK && photos_utils_equal_double (delta, 1.0))
+ || (event == PHOTOS_ZOOM_EVENT_SCROLL && delta >= 0.0));
view_container = gtk_stack_get_visible_child (GTK_STACK (self->stack));
view = photos_preview_view_get_view_from_view_container (view_container);
best_fit = photos_image_view_get_best_fit (PHOTOS_IMAGE_VIEW (view));
- if (delta >= 0.0)
- zoom_factor = best_fit ? ZOOM_FACTOR_2 : ZOOM_FACTOR_3;
- else
- zoom_factor = best_fit ? ZOOM_FACTOR_1 : ZOOM_FACTOR_2;
+ switch (event)
+ {
+ case PHOTOS_ZOOM_EVENT_KEYBOARD_ACCELERATOR:
+ case PHOTOS_ZOOM_EVENT_MOUSE_CLICK:
+ zoom_factor = best_fit ? ZOOM_FACTOR_1 : ZOOM_FACTOR_2;
+ break;
+
+ case PHOTOS_ZOOM_EVENT_SCROLL:
+ zoom_factor = best_fit ? ZOOM_FACTOR_2 : ZOOM_FACTOR_3;
+ break;
+
+ case PHOTOS_ZOOM_EVENT_NONE:
+ default:
+ g_assert_not_reached ();
+ break;
+ }
- delta_abs = fabs (delta);
- zoom_factor_for_delta = pow (zoom_factor, delta_abs);
+ zoom_factor_for_delta = pow (zoom_factor, delta);
zoom = photos_image_view_get_zoom (PHOTOS_IMAGE_VIEW (view));
zoom *= zoom_factor_for_delta;
@@ -898,27 +914,43 @@ photos_preview_view_zoom_out (PhotosPreviewView *self, GVariant *parameter)
{
GtkWidget *view;
GtkWidget *view_container;
+ PhotosZoomEvent event;
gdouble delta;
- gdouble delta_abs;
gdouble zoom;
gdouble zoom_factor;
gdouble zoom_factor_for_delta;
g_return_if_fail (self->zoom_best_fit > 0.0);
- delta = g_variant_get_double (parameter);
- g_return_if_fail (photos_utils_equal_double (delta, -1.0) || delta >= 0.0);
+ event = photos_utils_get_zoom_event (parameter);
+ g_return_if_fail (event != PHOTOS_ZOOM_EVENT_NONE);
+
+ delta = photos_utils_get_zoom_delta (parameter);
+ g_return_if_fail ((event == PHOTOS_ZOOM_EVENT_KEYBOARD_ACCELERATOR && photos_utils_equal_double (delta,
1.0))
+ || (event == PHOTOS_ZOOM_EVENT_MOUSE_CLICK && photos_utils_equal_double (delta, 1.0))
+ || (event == PHOTOS_ZOOM_EVENT_SCROLL && delta >= 0.0));
view_container = gtk_stack_get_visible_child (GTK_STACK (self->stack));
view = photos_preview_view_get_view_from_view_container (view_container);
- if (delta >= 0.0)
- zoom_factor = ZOOM_FACTOR_3;
- else
- zoom_factor = ZOOM_FACTOR_2;
+ switch (event)
+ {
+ case PHOTOS_ZOOM_EVENT_KEYBOARD_ACCELERATOR:
+ case PHOTOS_ZOOM_EVENT_MOUSE_CLICK:
+ zoom_factor = ZOOM_FACTOR_2;
+ break;
+
+ case PHOTOS_ZOOM_EVENT_SCROLL:
+ zoom_factor = ZOOM_FACTOR_3;
+ break;
+
+ case PHOTOS_ZOOM_EVENT_NONE:
+ default:
+ g_assert_not_reached ();
+ break;
+ }
- delta_abs = fabs (delta);
- zoom_factor_for_delta = pow (zoom_factor, delta_abs);
+ zoom_factor_for_delta = pow (zoom_factor, delta);
zoom = photos_image_view_get_zoom (PHOTOS_IMAGE_VIEW (view));
zoom /= zoom_factor_for_delta;
diff --git a/src/photos-utils.c b/src/photos-utils.c
index d48bb18..71a8d56 100644
--- a/src/photos-utils.c
+++ b/src/photos-utils.c
@@ -35,6 +35,7 @@
#include <libgd/gd.h>
#include "photos-application.h"
+#include "photos-enums.h"
#include "photos-error.h"
#include "photos-facebook-item.h"
#include "photos-flickr-item.h"
@@ -394,6 +395,41 @@ photos_utils_create_thumbnail (GFile *file,
}
+GVariant *
+photos_utils_create_zoom_target_value (gdouble delta, PhotosZoomEvent event)
+{
+ GEnumClass *zoom_event_class = NULL;
+ GEnumValue *event_value;
+ GVariant *delta_value;
+ GVariant *event_nick_value;
+ GVariant *ret_val = NULL;
+ GVariantBuilder builder;
+ const gchar *event_nick = "none";
+
+ g_return_val_if_fail (delta >= 0.0, NULL);
+ g_return_val_if_fail (event != PHOTOS_ZOOM_EVENT_NONE, NULL);
+
+ g_variant_builder_init (&builder, G_VARIANT_TYPE_VARDICT);
+
+ delta_value = g_variant_new_double (delta);
+ g_variant_builder_add (&builder, "{sv}", "delta", delta_value);
+
+ zoom_event_class = G_ENUM_CLASS (g_type_class_ref (PHOTOS_TYPE_ZOOM_EVENT));
+
+ event_value = g_enum_get_value (zoom_event_class, (gint) event);
+ if (event_value != NULL)
+ event_nick = event_value->value_nick;
+
+ event_nick_value = g_variant_new_string (event_nick);
+ g_variant_builder_add (&builder, "{sv}", "event", event_nick_value);
+
+ ret_val = g_variant_builder_end (&builder);
+
+ g_type_class_unref (zoom_event_class);
+ return ret_val;
+}
+
+
static GIcon *
photos_utils_get_thumbnail_icon (const gchar *uri)
{
@@ -482,6 +518,57 @@ photos_utils_get_icon_from_cursor (TrackerSparqlCursor *cursor)
}
+gdouble
+photos_utils_get_zoom_delta (GVariant *dictionary)
+{
+ gdouble delta;
+ gdouble ret_val = -1.0;
+
+ g_return_val_if_fail (dictionary != NULL, -1.0);
+ g_return_val_if_fail (g_variant_is_of_type (dictionary, G_VARIANT_TYPE_VARDICT), -1.0);
+
+ if (!g_variant_lookup (dictionary, "delta", "d", &delta))
+ goto out;
+
+ ret_val = delta;
+
+ out:
+ g_return_val_if_fail (ret_val >= 0.0, -1.0);
+ return ret_val;
+}
+
+
+PhotosZoomEvent
+photos_utils_get_zoom_event (GVariant *dictionary)
+{
+ GEnumClass *zoom_event_class = NULL;
+ GEnumValue *event_value;
+ PhotosZoomEvent ret_val = PHOTOS_ZOOM_EVENT_NONE;
+ const gchar *event_str;
+
+ g_return_val_if_fail (dictionary != NULL, PHOTOS_ZOOM_EVENT_NONE);
+ g_return_val_if_fail (g_variant_is_of_type (dictionary, G_VARIANT_TYPE_VARDICT), PHOTOS_ZOOM_EVENT_NONE);
+
+ if (!g_variant_lookup (dictionary, "event", "&s", &event_str))
+ goto out;
+
+ zoom_event_class = G_ENUM_CLASS (g_type_class_ref (PHOTOS_TYPE_ZOOM_EVENT));
+
+ event_value = g_enum_get_value_by_nick (zoom_event_class, event_str);
+ if (event_value == NULL)
+ event_value = g_enum_get_value_by_name (zoom_event_class, event_str);
+ if (event_value == NULL)
+ goto out;
+
+ ret_val = (PhotosZoomEvent) event_value->value;
+
+ out:
+ g_clear_pointer (&zoom_event_class, g_type_class_unref);
+ g_return_val_if_fail (ret_val != PHOTOS_ZOOM_EVENT_NONE, PHOTOS_ZOOM_EVENT_NONE);
+ return ret_val;
+}
+
+
GdkPixbuf *
photos_utils_downscale_pixbuf_for_scale (GdkPixbuf *pixbuf, gint size, gint scale)
{
@@ -1225,6 +1312,26 @@ photos_utils_object_list_free_full (GList *objects)
}
+gchar *
+photos_utils_print_zoom_action_detailed_name (const gchar *action_name, gdouble delta, PhotosZoomEvent event)
+{
+ GVariant *target_value;
+ gchar *ret_val = NULL;
+
+ g_return_val_if_fail (action_name != NULL && action_name[0] != '\0', NULL);
+ g_return_val_if_fail (delta >= 0.0, NULL);
+ g_return_val_if_fail (event != PHOTOS_ZOOM_EVENT_NONE, NULL);
+
+ target_value = photos_utils_create_zoom_target_value (delta, event);
+ target_value = g_variant_ref_sink (target_value);
+
+ ret_val = g_action_print_detailed_name (action_name, target_value);
+
+ g_variant_unref (target_value);
+ return ret_val;
+}
+
+
static gboolean
photos_utils_adjustment_can_scroll (GtkAdjustment *adjustment)
{
diff --git a/src/photos-utils.h b/src/photos-utils.h
index 9bb9de1..e40ef2a 100644
--- a/src/photos-utils.h
+++ b/src/photos-utils.h
@@ -52,6 +52,14 @@ G_BEGIN_DECLS
"http://www.semanticdesktop.org/ontologies/2007/03/22/nfo#image-category-screenshot"
#define PHOTOS_EXPORT_SUBPATH "Exports"
+typedef enum
+{
+ PHOTOS_ZOOM_EVENT_NONE,
+ PHOTOS_ZOOM_EVENT_KEYBOARD_ACCELERATOR,
+ PHOTOS_ZOOM_EVENT_MOUSE_CLICK,
+ PHOTOS_ZOOM_EVENT_SCROLL
+} PhotosZoomEvent;
+
GdkPixbuf *photos_utils_center_pixbuf (GdkPixbuf *pixbuf, gint size);
gchar *photos_utils_convert_path_to_uri (const gchar *path);
@@ -72,8 +80,14 @@ gboolean photos_utils_create_thumbnail (GFile *file,
GCancellable *cancellable,
GError **error);
+GVariant *photos_utils_create_zoom_target_value (gdouble delta, PhotosZoomEvent event);
+
GIcon *photos_utils_get_icon_from_cursor (TrackerSparqlCursor *cursor);
+gdouble photos_utils_get_zoom_delta (GVariant *dictionary);
+
+PhotosZoomEvent photos_utils_get_zoom_event (GVariant *dictionary);
+
GdkPixbuf *photos_utils_downscale_pixbuf_for_scale (GdkPixbuf *pixbuf, gint size, gint scale);
void photos_utils_draw_rectangle_handles (cairo_t *cr,
@@ -159,6 +173,10 @@ void photos_utils_list_box_header_func (GtkListBoxRow *row,
void photos_utils_object_list_free_full (GList *objects);
+gchar *photos_utils_print_zoom_action_detailed_name (const gchar *action_name,
+ gdouble delta,
+ PhotosZoomEvent event);
+
gboolean photos_utils_scrolled_window_can_scroll (GtkScrolledWindow *scrolled_window);
void photos_utils_scrolled_window_scroll (GtkScrolledWindow *scrolled_window,
diff --git a/src/photos-zoom-controls.c b/src/photos-zoom-controls.c
index 388cf2c..726e722 100644
--- a/src/photos-zoom-controls.c
+++ b/src/photos-zoom-controls.c
@@ -25,6 +25,7 @@
#include <gio/gio.h>
+#include "photos-utils.h"
#include "photos-zoom-controls.h"
@@ -74,7 +75,12 @@ photos_zoom_controls_update_buttons (PhotosZoomControls *self)
}
else
{
- gtk_actionable_set_action_target (GTK_ACTIONABLE (self->zoom_toggle_button), "d", -1.0);
+ GVariant *target_value = NULL;
+
+ target_value = photos_utils_create_zoom_target_value (1.0, PHOTOS_ZOOM_EVENT_MOUSE_CLICK);
+ g_assert_true (g_variant_is_floating (target_value));
+
+ gtk_actionable_set_action_target_value (GTK_ACTIONABLE (self->zoom_toggle_button), target_value);
gtk_actionable_set_action_name (GTK_ACTIONABLE (self->zoom_toggle_button), "app.zoom-in");
}
diff --git a/src/photos-zoom-controls.ui b/src/photos-zoom-controls.ui
index 65e1d13..b5d2e66 100644
--- a/src/photos-zoom-controls.ui
+++ b/src/photos-zoom-controls.ui
@@ -39,7 +39,7 @@
<child>
<object class="GtkButton" id="zoom_in_button">
<property name="action_name">app.zoom-in</property>
- <property name="action_target">-1.0</property>
+ <property name="action_target">{ 'delta': <1.0>, 'event': <'mouse-click'>
}</property>
<style>
<class name="image-button"/>
<class name="osd"/>
@@ -54,7 +54,7 @@
<child>
<object class="GtkButton" id="zoom_out_button">
<property name="action_name">app.zoom-out</property>
- <property name="action_target">-1.0</property>
+ <property name="action_target">{ 'delta': <1.0>, 'event': <'mouse-click'>
}</property>
<style>
<class name="image-button"/>
<class name="osd"/>
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]