~walkerlee/totem/pre-interview

« back to all changes in this revision

Viewing changes to src/plugins/screenshot/totem-screenshot-plugin.c

  • Committer: Package Import Robot
  • Author(s): Jeremy Bicha
  • Date: 2013-05-26 00:07:51 UTC
  • mfrom: (1.6.1) (24.1.4 experimental)
  • Revision ID: package-import@ubuntu.com-20130526000751-kv8ap3x1di4qq8j2
Tags: 3.8.2-0ubuntu1
* Sync with Debian. Remaining changes: 
* debian/control.in:
  - Drop build-depends on libepc-ui-dev and libgrilo-0.2-dev (in universe)
  - Drop libxtst-dev build-depends so that the (redundant) fake key presses
    for inhibiting the screensaver are disabled (LP: #1007438)
  - Build-depend on libzeitgeist-dev
  - Suggest rather than recommend gstreamer components in universe
  - Add totem-plugins-extra
  - Add XB-Npp-Description and XB-Npp-Filename header to the 
    totem-mozilla package to improve ubufox/ubuntu plugin db integration 
  - Refer to Firefox in totem-mozilla description instead of Iceweasel
  - Don't have totem-mozilla recommend any particular browser
  - Drop obsolete python library dependencies since iplayer is no longer
    included
* debian/totem-common.install, debian/source_totem.py:
  - Install Ubuntu apport debugging hook
* debian/totem-plugins-extra.install:
  - Universe plugins split out of totem-plugins (currently only gromit)
* debian/totem-plugins.install:    
  - Skip the plugins split to -extra and add the zeitgeist plugin
* debian/rules:
  - Build with --fail-missing, to ensure we install everything. 
    + Ignore libtotem.{,l}a since we delibrately don't install these.
  - Re-enable hardening, make sure both PIE and BINDNOW are used
    by setting hardening=+all. (LP: #1039604)
* debian/patches/91_quicklist_entries.patch:
  - Add static quicklist
* debian/patches/92_gst-plugins-good.patch:
  - Build without unnecessary gstreamer1.0-bad dependency
* debian/patches/93_grilo_optional.patch:
  - Allow building without grilo while grilo MIR is still pending
* debian/patches/correct_desktop_mimetypes.patch:
  - Don't list the mimetypes after the unity lists
* debian/patches/revert_shell_menu.patch: 
  - revert the use of a shell menu until indicator-appmenu can handle
    the mixed shell/traditional menus itself
* New upstream release

Show diffs side-by-side

added added

removed removed

Lines of Context:
33
33
#include <gdk/gdkkeysyms.h>
34
34
#include <libpeas/peas-activatable.h>
35
35
 
36
 
#ifdef HAVE_XFREE
37
 
#include <X11/XF86keysym.h>
38
 
#endif
39
 
 
40
36
#include "totem-plugin.h"
41
37
#include "totem-screenshot-plugin.h"
42
 
#include "totem-screenshot.h"
 
38
#include "screenshot-filename-builder.h"
43
39
#include "totem-gallery.h"
44
40
#include "totem-uri.h"
45
41
#include "backend/bacon-video-widget.h"
70
66
                      TotemScreenshotPlugin,
71
67
                      totem_screenshot_plugin)
72
68
 
 
69
typedef struct {
 
70
        TotemScreenshotPlugin *plugin;
 
71
        GdkPixbuf *pixbuf;
 
72
} ScreenshotSaveJob;
 
73
 
 
74
static void
 
75
screenshot_save_job_free (ScreenshotSaveJob *job)
 
76
{
 
77
        g_object_unref (job->pixbuf);
 
78
        g_slice_free (ScreenshotSaveJob, job);
 
79
}
 
80
 
 
81
static void
 
82
save_pixbuf_ready_cb (GObject *source,
 
83
                      GAsyncResult *res,
 
84
                      gpointer user_data)
 
85
{
 
86
        GError *error = NULL;
 
87
        ScreenshotSaveJob *job = (ScreenshotSaveJob *) user_data;
 
88
 
 
89
        if (gdk_pixbuf_save_to_stream_finish (res, &error) == FALSE) {
 
90
                g_warning ("Couldn't save screenshot: %s", error->message);
 
91
                g_error_free (error);
 
92
        }
 
93
 
 
94
        screenshot_save_job_free (job);
 
95
}
 
96
 
 
97
static void
 
98
save_file_create_ready_cb (GObject *source,
 
99
                           GAsyncResult *res,
 
100
                           gpointer user_data)
 
101
{
 
102
        GFileOutputStream *stream;
 
103
        GError *error = NULL;
 
104
        ScreenshotSaveJob *job = (ScreenshotSaveJob *) user_data;
 
105
 
 
106
        stream = g_file_create_finish (G_FILE (source), res, &error);
 
107
        if (stream == NULL) {
 
108
                char *path;
 
109
 
 
110
                path = g_file_get_path (G_FILE (source));
 
111
                g_warning ("Couldn't create a new file at '%s': %s", path, error->message);
 
112
                g_free (path);
 
113
 
 
114
                g_error_free (error);
 
115
                screenshot_save_job_free (job);
 
116
                return;
 
117
        }
 
118
 
 
119
        gdk_pixbuf_save_to_stream_async (job->pixbuf,
 
120
                                         G_OUTPUT_STREAM (stream),
 
121
                                         "png", NULL,
 
122
                                         save_pixbuf_ready_cb, job,
 
123
                                         "tEXt::Software", "totem",
 
124
                                         NULL);
 
125
 
 
126
        g_object_unref (stream);
 
127
}
 
128
 
 
129
static void
 
130
screenshot_name_ready_cb (GObject *source,
 
131
                          GAsyncResult *res,
 
132
                          gpointer user_data)
 
133
{
 
134
        GFile *save_file;
 
135
        char *save_path;
 
136
        GError *error = NULL;
 
137
        ScreenshotSaveJob *job = (ScreenshotSaveJob *) user_data;
 
138
 
 
139
        save_path = screenshot_build_filename_finish (res, &error);
 
140
        if (save_path == NULL) {
 
141
                g_warning ("Could not find a valid location to save the screenshot: %s", error->message);
 
142
                g_error_free (error);
 
143
                screenshot_save_job_free (job);
 
144
                return;
 
145
        }
 
146
 
 
147
        save_file = g_file_new_for_path (save_path);
 
148
        g_free (save_path);
 
149
 
 
150
        g_file_create_async (save_file,
 
151
                             G_FILE_CREATE_NONE,
 
152
                             G_PRIORITY_DEFAULT,
 
153
                             NULL,
 
154
                             save_file_create_ready_cb, job);
 
155
 
 
156
        g_object_unref (save_file);
 
157
}
 
158
 
 
159
static void
 
160
flash_area_done_cb (GObject *source_object,
 
161
                    GAsyncResult *res,
 
162
                    gpointer user_data)
 
163
{
 
164
        GVariant *variant;
 
165
 
 
166
        variant = g_dbus_proxy_call_finish (G_DBUS_PROXY (source_object), res, NULL);
 
167
        if (variant != NULL)
 
168
                g_variant_unref (variant);
 
169
}
 
170
 
 
171
static void
 
172
flash_area (GtkWidget *widget)
 
173
{
 
174
        GDBusProxy *proxy;
 
175
        GdkWindow *window;
 
176
        int x, y, w, h;
 
177
 
 
178
        window = gtk_widget_get_window (widget);
 
179
        gdk_window_get_origin (window, &x, &y);
 
180
        w = gdk_window_get_width (window);
 
181
        h = gdk_window_get_height (window);
 
182
 
 
183
        proxy = g_dbus_proxy_new_for_bus_sync (G_BUS_TYPE_SESSION,
 
184
                                               G_DBUS_PROXY_FLAGS_DO_NOT_LOAD_PROPERTIES |
 
185
                                               G_DBUS_PROXY_FLAGS_DO_NOT_CONNECT_SIGNALS |
 
186
                                               G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START,
 
187
                                               NULL,
 
188
                                               "org.gnome.Shell",
 
189
                                               "/org/gnome/Shell/Screenshot",
 
190
                                               "org.gnome.Shell.Screenshot",
 
191
                                               NULL, NULL);
 
192
        if (proxy == NULL)
 
193
                g_warning ("no proxy");
 
194
 
 
195
        g_dbus_proxy_call (proxy, "org.gnome.Shell.Screenshot.FlashArea",
 
196
                           g_variant_new ("(iiii)", x, y, w, h),
 
197
                           G_DBUS_CALL_FLAGS_NO_AUTO_START,
 
198
                           -1,
 
199
                           NULL,
 
200
                           flash_area_done_cb,
 
201
                           NULL);
 
202
}
 
203
 
73
204
static void
74
205
take_screenshot_action_cb (GtkAction *action, TotemScreenshotPlugin *self)
75
206
{
76
207
        TotemScreenshotPluginPrivate *priv = self->priv;
77
208
        GdkPixbuf *pixbuf;
78
 
        GtkWidget *dialog;
79
209
        GError *err = NULL;
 
210
        ScreenshotSaveJob *job;
 
211
        char *video_name;
80
212
 
81
213
        if (bacon_video_widget_get_logo_mode (priv->bvw) != FALSE)
82
214
                return;
90
222
                return;
91
223
        }
92
224
 
 
225
        flash_area (GTK_WIDGET (priv->bvw));
 
226
 
93
227
        pixbuf = bacon_video_widget_get_current_frame (priv->bvw);
94
228
        if (pixbuf == NULL) {
95
229
                totem_action_error (priv->totem, _("Totem could not get a screenshot of the video."), _("This is not supposed to happen; please file a bug report."));
96
230
                return;
97
231
        }
98
232
 
99
 
        dialog = totem_screenshot_new (priv->totem, pixbuf);
100
 
 
101
 
        gtk_dialog_run (GTK_DIALOG (dialog));
102
 
        gtk_widget_destroy (dialog);
103
 
        g_object_unref (pixbuf);
 
233
        video_name = totem_get_short_title (self->priv->totem);
 
234
 
 
235
        job = g_slice_new (ScreenshotSaveJob);
 
236
        job->plugin = self;
 
237
        job->pixbuf = pixbuf;
 
238
 
 
239
        screenshot_build_filename_async (NULL, video_name, screenshot_name_ready_cb, job);
 
240
 
 
241
        g_free (video_name);
104
242
}
105
243
 
106
244
static void
132
270
window_key_press_event_cb (GtkWidget *window, GdkEventKey *event, TotemScreenshotPlugin *self)
133
271
{
134
272
        switch (event->keyval) {
135
 
#ifdef HAVE_XFREE
136
 
        case XF86XK_Save:
 
273
        case GDK_KEY_Save:
137
274
                take_screenshot_action_cb (NULL, self);
138
275
                break;
139
 
#endif /* HAVE_XFREE */
140
276
        case GDK_KEY_s:
141
277
        case GDK_KEY_S:
142
 
                if (event->state & GDK_CONTROL_MASK)
 
278
                if (event->state & GDK_CONTROL_MASK &&
 
279
                    event->state & GDK_MOD1_MASK)
143
280
                        take_screenshot_action_cb (NULL, self);
144
281
                else
145
282
                        return FALSE;
194
331
        TotemScreenshotPlugin *self = TOTEM_SCREENSHOT_PLUGIN (plugin);
195
332
        TotemScreenshotPluginPrivate *priv = self->priv;
196
333
        const GtkActionEntry menu_entries[] = {
197
 
                { "take-screenshot", "camera-photo", N_("Take _Screenshot..."), "<Ctrl>S", N_("Take a screenshot"), G_CALLBACK (take_screenshot_action_cb) },
 
334
                { "take-screenshot", "camera-photo", N_("Take _Screenshot"), "<Ctrl><Alt>S", N_("Take a screenshot"), G_CALLBACK (take_screenshot_action_cb) },
198
335
                { "take-gallery", NULL, N_("Create Screenshot _Gallery..."), NULL, N_("Create a gallery of screenshots"), G_CALLBACK (take_gallery_action_cb) }
199
336
        };
200
337
 
230
367
 
231
368
        priv->ui_merge_id = gtk_ui_manager_new_merge_id (manager);
232
369
        gtk_ui_manager_add_ui (manager, priv->ui_merge_id,
233
 
                               "/ui/tmw-menubar/edit/repeat-mode", "take-screenshot",
 
370
                               "/ui/tmw-menubar/edit/clear-playlist", "take-screenshot",
234
371
                               "take-screenshot", GTK_UI_MANAGER_AUTO, TRUE);
235
372
        gtk_ui_manager_add_ui (manager, priv->ui_merge_id,
236
 
                               "/ui/tmw-menubar/edit/repeat-mode", "take-gallery",
 
373
                               "/ui/tmw-menubar/edit/clear-playlist", "take-gallery",
237
374
                               "take-gallery", GTK_UI_MANAGER_AUTO, TRUE);
238
375
        gtk_ui_manager_add_ui (manager, priv->ui_merge_id,
239
 
                               "/ui/tmw-menubar/edit/repeat-mode", NULL,
 
376
                               "/ui/tmw-menubar/edit/clear-playlist", NULL,
240
377
                               NULL, GTK_UI_MANAGER_SEPARATOR, TRUE);
241
378
 
242
379
        /* Set up a GSettings watch for lockdown keys */