screenshot: Adopt GIO's async pattern
A custom callback type is more convenient, but only as long as no other callback type is required. We are about to add functionality that does not return the filename to a screenshot saved on disk, so prepare for that by moving to GIO's generic async callback pattern. https://gitlab.gnome.org/GNOME/gnome-shell/issues/286
This commit is contained in:
parent
304c667bca
commit
da537cda43
@ -110,7 +110,7 @@ var ScreenshotService = new Lang.Class({
|
|||||||
y + height <= global.screen_height;
|
y + height <= global.screen_height;
|
||||||
},
|
},
|
||||||
|
|
||||||
_onScreenshotComplete(obj, result, area, filenameUsed, flash, invocation) {
|
_onScreenshotComplete(result, area, filenameUsed, flash, invocation) {
|
||||||
if (result) {
|
if (result) {
|
||||||
if (flash) {
|
if (flash) {
|
||||||
let flashspot = new Flashspot(area);
|
let flashspot = new Flashspot(area);
|
||||||
@ -157,9 +157,15 @@ var ScreenshotService = new Lang.Class({
|
|||||||
if (!screenshot)
|
if (!screenshot)
|
||||||
return;
|
return;
|
||||||
screenshot.screenshot_area (x, y, width, height, filename,
|
screenshot.screenshot_area (x, y, width, height, filename,
|
||||||
(obj, result, area, filenameUsed) => {
|
(o, res) => {
|
||||||
this._onScreenshotComplete(obj, result, area, filenameUsed,
|
try {
|
||||||
flash, invocation);
|
let [result, area, filenameUsed] =
|
||||||
|
screenshot.screenshot_area_finish(res);
|
||||||
|
this._onScreenshotComplete(result, area, filenameUsed,
|
||||||
|
flash, invocation);
|
||||||
|
} catch (e) {
|
||||||
|
invocation.return_gerror (e);
|
||||||
|
}
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
@ -169,9 +175,15 @@ var ScreenshotService = new Lang.Class({
|
|||||||
if (!screenshot)
|
if (!screenshot)
|
||||||
return;
|
return;
|
||||||
screenshot.screenshot_window (include_frame, include_cursor, filename,
|
screenshot.screenshot_window (include_frame, include_cursor, filename,
|
||||||
(obj, result, area, filenameUsed) => {
|
(o, res) => {
|
||||||
this._onScreenshotComplete(obj, result, area, filenameUsed,
|
try {
|
||||||
flash, invocation);
|
let [result, area, filenameUsed] =
|
||||||
|
screenshot.screenshot_window_finish(res);
|
||||||
|
this._onScreenshotComplete(result, area, filenameUsed,
|
||||||
|
flash, invocation);
|
||||||
|
} catch (e) {
|
||||||
|
invocation.return_gerror (e);
|
||||||
|
}
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
@ -181,9 +193,15 @@ var ScreenshotService = new Lang.Class({
|
|||||||
if (!screenshot)
|
if (!screenshot)
|
||||||
return;
|
return;
|
||||||
screenshot.screenshot(include_cursor, filename,
|
screenshot.screenshot(include_cursor, filename,
|
||||||
(obj, result, area, filenameUsed) => {
|
(o, res) => {
|
||||||
this._onScreenshotComplete(obj, result, area, filenameUsed,
|
try {
|
||||||
flash, invocation);
|
let [result, area, filenameUsed] =
|
||||||
|
screenshot.screenshot_finish(res);
|
||||||
|
this._onScreenshotComplete(result, area, filenameUsed,
|
||||||
|
flash, invocation);
|
||||||
|
} catch (e) {
|
||||||
|
invocation.return_gerror (e);
|
||||||
|
}
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
|
@ -38,8 +38,6 @@ struct _ShellScreenshotPrivate
|
|||||||
|
|
||||||
gboolean include_cursor;
|
gboolean include_cursor;
|
||||||
gboolean include_frame;
|
gboolean include_frame;
|
||||||
|
|
||||||
ShellScreenshotCallback callback;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
G_DEFINE_TYPE_WITH_PRIVATE (ShellScreenshot, shell_screenshot, G_TYPE_OBJECT);
|
G_DEFINE_TYPE_WITH_PRIVATE (ShellScreenshot, shell_screenshot, G_TYPE_OBJECT);
|
||||||
@ -59,17 +57,15 @@ shell_screenshot_init (ShellScreenshot *screenshot)
|
|||||||
|
|
||||||
static void
|
static void
|
||||||
on_screenshot_written (GObject *source,
|
on_screenshot_written (GObject *source,
|
||||||
GAsyncResult *result,
|
GAsyncResult *task,
|
||||||
gpointer user_data)
|
gpointer user_data)
|
||||||
{
|
{
|
||||||
ShellScreenshot *screenshot = SHELL_SCREENSHOT (source);
|
ShellScreenshot *screenshot = SHELL_SCREENSHOT (source);
|
||||||
ShellScreenshotPrivate *priv = screenshot->priv;
|
ShellScreenshotPrivate *priv = screenshot->priv;
|
||||||
|
GTask *result = user_data;
|
||||||
|
|
||||||
if (priv->callback)
|
g_task_return_boolean (result, g_task_propagate_boolean (G_TASK (task), NULL));
|
||||||
priv->callback (screenshot,
|
g_object_unref (result);
|
||||||
g_task_propagate_boolean (G_TASK (result), NULL),
|
|
||||||
&priv->screenshot_area,
|
|
||||||
priv->filename_used);
|
|
||||||
|
|
||||||
g_clear_pointer (&priv->image, cairo_surface_destroy);
|
g_clear_pointer (&priv->image, cairo_surface_destroy);
|
||||||
g_clear_pointer (&priv->filename, g_free);
|
g_clear_pointer (&priv->filename, g_free);
|
||||||
@ -313,14 +309,15 @@ _draw_cursor_image (MetaCursorTracker *tracker,
|
|||||||
|
|
||||||
static void
|
static void
|
||||||
grab_screenshot (ClutterActor *stage,
|
grab_screenshot (ClutterActor *stage,
|
||||||
ShellScreenshot *screenshot)
|
GTask *result)
|
||||||
{
|
{
|
||||||
MetaDisplay *display;
|
MetaDisplay *display;
|
||||||
MetaCursorTracker *tracker;
|
MetaCursorTracker *tracker;
|
||||||
int width, height;
|
int width, height;
|
||||||
GTask *result;
|
|
||||||
GSettings *settings;
|
GSettings *settings;
|
||||||
|
ShellScreenshot *screenshot = g_task_get_source_object (result);
|
||||||
ShellScreenshotPrivate *priv = screenshot->priv;
|
ShellScreenshotPrivate *priv = screenshot->priv;
|
||||||
|
GTask *task;
|
||||||
|
|
||||||
display = shell_global_get_display (priv->global);
|
display = shell_global_get_display (priv->global);
|
||||||
meta_display_get_size (display, &width, &height);
|
meta_display_get_size (display, &width, &height);
|
||||||
@ -380,19 +377,20 @@ grab_screenshot (ClutterActor *stage,
|
|||||||
}
|
}
|
||||||
g_object_unref (settings);
|
g_object_unref (settings);
|
||||||
|
|
||||||
g_signal_handlers_disconnect_by_func (stage, (void *)grab_screenshot, (gpointer)screenshot);
|
g_signal_handlers_disconnect_by_func (stage, grab_screenshot, result);
|
||||||
|
|
||||||
result = g_task_new (screenshot, NULL, on_screenshot_written, NULL);
|
task = g_task_new (screenshot, NULL, on_screenshot_written, result);
|
||||||
g_task_run_in_thread (result, write_screenshot_thread);
|
g_task_run_in_thread (task, write_screenshot_thread);
|
||||||
g_object_unref (result);
|
g_object_unref (task);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
grab_area_screenshot (ClutterActor *stage,
|
grab_area_screenshot (ClutterActor *stage,
|
||||||
ShellScreenshot *screenshot)
|
GTask *result)
|
||||||
{
|
{
|
||||||
GTask *result;
|
ShellScreenshot *screenshot = g_task_get_source_object (result);
|
||||||
ShellScreenshotPrivate *priv = screenshot->priv;
|
ShellScreenshotPrivate *priv = screenshot->priv;
|
||||||
|
GTask *task;
|
||||||
|
|
||||||
do_grab_screenshot (screenshot,
|
do_grab_screenshot (screenshot,
|
||||||
CLUTTER_STAGE (stage),
|
CLUTTER_STAGE (stage),
|
||||||
@ -401,18 +399,19 @@ grab_area_screenshot (ClutterActor *stage,
|
|||||||
priv->screenshot_area.width,
|
priv->screenshot_area.width,
|
||||||
priv->screenshot_area.height);
|
priv->screenshot_area.height);
|
||||||
|
|
||||||
g_signal_handlers_disconnect_by_func (stage, (void *)grab_area_screenshot, (gpointer)screenshot);
|
g_signal_handlers_disconnect_by_func (stage, grab_area_screenshot, result);
|
||||||
result = g_task_new (screenshot, NULL, on_screenshot_written, NULL);
|
task = g_task_new (screenshot, NULL, on_screenshot_written, result);
|
||||||
g_task_run_in_thread (result, write_screenshot_thread);
|
g_task_run_in_thread (task, write_screenshot_thread);
|
||||||
g_object_unref (result);
|
g_object_unref (task);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
grab_window_screenshot (ClutterActor *stage,
|
grab_window_screenshot (ClutterActor *stage,
|
||||||
ShellScreenshot *screenshot)
|
GTask *result)
|
||||||
{
|
{
|
||||||
|
ShellScreenshot *screenshot = g_task_get_source_object (result);
|
||||||
ShellScreenshotPrivate *priv = screenshot->priv;
|
ShellScreenshotPrivate *priv = screenshot->priv;
|
||||||
GTask *result;
|
GTask *task;
|
||||||
GSettings *settings;
|
GSettings *settings;
|
||||||
MetaDisplay *display = shell_global_get_display (priv->global);
|
MetaDisplay *display = shell_global_get_display (priv->global);
|
||||||
MetaCursorTracker *tracker;
|
MetaCursorTracker *tracker;
|
||||||
@ -451,10 +450,31 @@ grab_window_screenshot (ClutterActor *stage,
|
|||||||
}
|
}
|
||||||
g_object_unref (settings);
|
g_object_unref (settings);
|
||||||
|
|
||||||
g_signal_handlers_disconnect_by_func (stage, (void *)grab_window_screenshot, (gpointer)screenshot);
|
g_signal_handlers_disconnect_by_func (stage, grab_window_screenshot, result);
|
||||||
result = g_task_new (screenshot, NULL, on_screenshot_written, NULL);
|
task = g_task_new (screenshot, NULL, on_screenshot_written, result);
|
||||||
g_task_run_in_thread (result, write_screenshot_thread);
|
g_task_run_in_thread (task, write_screenshot_thread);
|
||||||
g_object_unref (result);
|
g_object_unref (task);
|
||||||
|
}
|
||||||
|
|
||||||
|
static gboolean
|
||||||
|
finish_screenshot (ShellScreenshot *screenshot,
|
||||||
|
GAsyncResult *result,
|
||||||
|
cairo_rectangle_int_t **area,
|
||||||
|
const char **filename_used,
|
||||||
|
GError **error)
|
||||||
|
{
|
||||||
|
ShellScreenshotPrivate *priv = screenshot->priv;
|
||||||
|
|
||||||
|
if (!g_task_propagate_boolean (G_TASK (result), error))
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
if (area)
|
||||||
|
*area = &priv->screenshot_area;
|
||||||
|
|
||||||
|
if (filename_used)
|
||||||
|
*filename_used = priv->filename_used;
|
||||||
|
|
||||||
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -464,39 +484,79 @@ grab_window_screenshot (ClutterActor *stage,
|
|||||||
* @filename: The filename for the screenshot
|
* @filename: The filename for the screenshot
|
||||||
* @callback: (scope async): function to call returning success or failure
|
* @callback: (scope async): function to call returning success or failure
|
||||||
* of the async grabbing
|
* of the async grabbing
|
||||||
|
* @user_data: the data to pass to callback function
|
||||||
*
|
*
|
||||||
* Takes a screenshot of the whole screen
|
* Takes a screenshot of the whole screen
|
||||||
* in @filename as png image.
|
* in @filename as png image.
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
void
|
void
|
||||||
shell_screenshot_screenshot (ShellScreenshot *screenshot,
|
shell_screenshot_screenshot (ShellScreenshot *screenshot,
|
||||||
gboolean include_cursor,
|
gboolean include_cursor,
|
||||||
const char *filename,
|
const char *filename,
|
||||||
ShellScreenshotCallback callback)
|
GAsyncReadyCallback callback,
|
||||||
|
gpointer user_data)
|
||||||
{
|
{
|
||||||
ClutterActor *stage;
|
ClutterActor *stage;
|
||||||
ShellScreenshotPrivate *priv = screenshot->priv;
|
ShellScreenshotPrivate *priv = screenshot->priv;
|
||||||
|
GTask *result;
|
||||||
|
|
||||||
if (priv->filename != NULL) {
|
if (priv->filename != NULL) {
|
||||||
if (callback)
|
if (callback)
|
||||||
callback (screenshot, FALSE, NULL, "");
|
g_task_report_new_error (screenshot,
|
||||||
|
callback,
|
||||||
|
user_data,
|
||||||
|
shell_screenshot_screenshot,
|
||||||
|
G_IO_ERROR,
|
||||||
|
G_IO_ERROR_PENDING,
|
||||||
|
"Only one screenshot operation at a time "
|
||||||
|
"is permitted");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
result = g_task_new (screenshot, NULL, callback, user_data);
|
||||||
|
g_task_set_source_tag (result, shell_screenshot_screenshot);
|
||||||
|
|
||||||
priv->filename = g_strdup (filename);
|
priv->filename = g_strdup (filename);
|
||||||
priv->callback = callback;
|
|
||||||
priv->include_cursor = include_cursor;
|
priv->include_cursor = include_cursor;
|
||||||
|
|
||||||
stage = CLUTTER_ACTOR (shell_global_get_stage (priv->global));
|
stage = CLUTTER_ACTOR (shell_global_get_stage (priv->global));
|
||||||
|
|
||||||
meta_disable_unredirect_for_display (shell_global_get_display (priv->global));
|
meta_disable_unredirect_for_display (shell_global_get_display (priv->global));
|
||||||
|
|
||||||
g_signal_connect_after (stage, "paint", G_CALLBACK (grab_screenshot), (gpointer)screenshot);
|
g_signal_connect_after (stage, "paint", G_CALLBACK (grab_screenshot), result);
|
||||||
|
|
||||||
clutter_actor_queue_redraw (stage);
|
clutter_actor_queue_redraw (stage);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* shell_screenshot_screenshot_finish:
|
||||||
|
* @screenshot: the #ShellScreenshot
|
||||||
|
* @result: the #GAsyncResult that was provided to the callback
|
||||||
|
* @area: (out) (transfer none): the area that was grabbed in screen coordinates
|
||||||
|
* @filename_used: (out) (transfer none): the name of the file the screenshot
|
||||||
|
* was written to
|
||||||
|
* @error: #GError for error reporting
|
||||||
|
*
|
||||||
|
* Finish the asynchronous operation started by shell_screenshot_screenshot()
|
||||||
|
* and obtain its result.
|
||||||
|
*
|
||||||
|
* Returns: whether the operation was successful
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
gboolean
|
||||||
|
shell_screenshot_screenshot_finish (ShellScreenshot *screenshot,
|
||||||
|
GAsyncResult *result,
|
||||||
|
cairo_rectangle_int_t **area,
|
||||||
|
const char **filename_used,
|
||||||
|
GError **error)
|
||||||
|
{
|
||||||
|
g_return_val_if_fail (g_async_result_is_tagged (result,
|
||||||
|
shell_screenshot_screenshot),
|
||||||
|
FALSE);
|
||||||
|
return finish_screenshot (screenshot, result, area, filename_used, error);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* shell_screenshot_screenshot_area:
|
* shell_screenshot_screenshot_area:
|
||||||
* @screenshot: the #ShellScreenshot
|
* @screenshot: the #ShellScreenshot
|
||||||
@ -507,45 +567,85 @@ shell_screenshot_screenshot (ShellScreenshot *screenshot,
|
|||||||
* @filename: The filename for the screenshot
|
* @filename: The filename for the screenshot
|
||||||
* @callback: (scope async): function to call returning success or failure
|
* @callback: (scope async): function to call returning success or failure
|
||||||
* of the async grabbing
|
* of the async grabbing
|
||||||
|
* @user_data: the data to pass to callback function
|
||||||
*
|
*
|
||||||
* Takes a screenshot of the passed in area and saves it
|
* Takes a screenshot of the passed in area and saves it
|
||||||
* in @filename as png image.
|
* in @filename as png image.
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
void
|
void
|
||||||
shell_screenshot_screenshot_area (ShellScreenshot *screenshot,
|
shell_screenshot_screenshot_area (ShellScreenshot *screenshot,
|
||||||
int x,
|
int x,
|
||||||
int y,
|
int y,
|
||||||
int width,
|
int width,
|
||||||
int height,
|
int height,
|
||||||
const char *filename,
|
const char *filename,
|
||||||
ShellScreenshotCallback callback)
|
GAsyncReadyCallback callback,
|
||||||
|
gpointer user_data)
|
||||||
{
|
{
|
||||||
ClutterActor *stage;
|
ClutterActor *stage;
|
||||||
ShellScreenshotPrivate *priv = screenshot->priv;
|
ShellScreenshotPrivate *priv = screenshot->priv;
|
||||||
|
GTask *result;
|
||||||
|
|
||||||
if (priv->filename != NULL) {
|
if (priv->filename != NULL) {
|
||||||
if (callback)
|
if (callback)
|
||||||
callback (screenshot, FALSE, NULL, "");
|
g_task_report_new_error (screenshot,
|
||||||
|
callback,
|
||||||
|
NULL,
|
||||||
|
shell_screenshot_screenshot_area,
|
||||||
|
G_IO_ERROR,
|
||||||
|
G_IO_ERROR_PENDING,
|
||||||
|
"Only one screenshot operation at a time "
|
||||||
|
"is permitted");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
result = g_task_new (screenshot, NULL, callback, user_data);
|
||||||
|
g_task_set_source_tag (result, shell_screenshot_screenshot_area);
|
||||||
|
|
||||||
priv->filename = g_strdup (filename);
|
priv->filename = g_strdup (filename);
|
||||||
priv->screenshot_area.x = x;
|
priv->screenshot_area.x = x;
|
||||||
priv->screenshot_area.y = y;
|
priv->screenshot_area.y = y;
|
||||||
priv->screenshot_area.width = width;
|
priv->screenshot_area.width = width;
|
||||||
priv->screenshot_area.height = height;
|
priv->screenshot_area.height = height;
|
||||||
priv->callback = callback;
|
|
||||||
|
|
||||||
stage = CLUTTER_ACTOR (shell_global_get_stage (priv->global));
|
stage = CLUTTER_ACTOR (shell_global_get_stage (priv->global));
|
||||||
|
|
||||||
meta_disable_unredirect_for_display (shell_global_get_display (shell_global_get ()));
|
meta_disable_unredirect_for_display (shell_global_get_display (shell_global_get ()));
|
||||||
|
|
||||||
g_signal_connect_after (stage, "paint", G_CALLBACK (grab_area_screenshot), (gpointer)screenshot);
|
g_signal_connect_after (stage, "paint", G_CALLBACK (grab_area_screenshot), result);
|
||||||
|
|
||||||
clutter_actor_queue_redraw (stage);
|
clutter_actor_queue_redraw (stage);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* shell_screenshot_screenshot_area_finish:
|
||||||
|
* @screenshot: the #ShellScreenshot
|
||||||
|
* @result: the #GAsyncResult that was provided to the callback
|
||||||
|
* @area: (out) (transfer none): the area that was grabbed in screen coordinates
|
||||||
|
* @filename_used: (out) (transfer none): the name of the file the screenshot
|
||||||
|
* was written to
|
||||||
|
* @error: #GError for error reporting
|
||||||
|
*
|
||||||
|
* Finish the asynchronous operation started by shell_screenshot_screenshot_area()
|
||||||
|
* and obtain its result.
|
||||||
|
*
|
||||||
|
* Returns: whether the operation was successful
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
gboolean
|
||||||
|
shell_screenshot_screenshot_area_finish (ShellScreenshot *screenshot,
|
||||||
|
GAsyncResult *result,
|
||||||
|
cairo_rectangle_int_t **area,
|
||||||
|
const char **filename_used,
|
||||||
|
GError **error)
|
||||||
|
{
|
||||||
|
g_return_val_if_fail (g_async_result_is_tagged (result,
|
||||||
|
shell_screenshot_screenshot_area),
|
||||||
|
FALSE);
|
||||||
|
return finish_screenshot (screenshot, result, area, filename_used, error);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* shell_screenshot_screenshot_window:
|
* shell_screenshot_screenshot_window:
|
||||||
* @screenshot: the #ShellScreenshot
|
* @screenshot: the #ShellScreenshot
|
||||||
@ -554,31 +654,43 @@ shell_screenshot_screenshot_area (ShellScreenshot *screenshot,
|
|||||||
* @filename: The filename for the screenshot
|
* @filename: The filename for the screenshot
|
||||||
* @callback: (scope async): function to call returning success or failure
|
* @callback: (scope async): function to call returning success or failure
|
||||||
* of the async grabbing
|
* of the async grabbing
|
||||||
|
* @user_data: the data to pass to callback function
|
||||||
*
|
*
|
||||||
* Takes a screenshot of the focused window (optionally omitting the frame)
|
* Takes a screenshot of the focused window (optionally omitting the frame)
|
||||||
* in @filename as png image.
|
* in @filename as png image.
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
void
|
void
|
||||||
shell_screenshot_screenshot_window (ShellScreenshot *screenshot,
|
shell_screenshot_screenshot_window (ShellScreenshot *screenshot,
|
||||||
gboolean include_frame,
|
gboolean include_frame,
|
||||||
gboolean include_cursor,
|
gboolean include_cursor,
|
||||||
const char *filename,
|
const char *filename,
|
||||||
ShellScreenshotCallback callback)
|
GAsyncReadyCallback callback,
|
||||||
|
gpointer user_data)
|
||||||
{
|
{
|
||||||
ShellScreenshotPrivate *priv = screenshot->priv;
|
ShellScreenshotPrivate *priv = screenshot->priv;
|
||||||
MetaDisplay *display = shell_global_get_display (priv->global);
|
MetaDisplay *display = shell_global_get_display (priv->global);
|
||||||
ClutterActor *stage;
|
ClutterActor *stage;
|
||||||
MetaWindow *window = meta_display_get_focus_window (display);
|
MetaWindow *window = meta_display_get_focus_window (display);
|
||||||
|
GTask *result;
|
||||||
|
|
||||||
if (priv->filename != NULL || !window) {
|
if (priv->filename != NULL || !window) {
|
||||||
if (callback)
|
if (callback)
|
||||||
callback (screenshot, FALSE, NULL, "");
|
g_task_report_new_error (screenshot,
|
||||||
|
callback,
|
||||||
|
NULL,
|
||||||
|
shell_screenshot_screenshot_window,
|
||||||
|
G_IO_ERROR,
|
||||||
|
G_IO_ERROR_PENDING,
|
||||||
|
"Only one screenshot operation at a time "
|
||||||
|
"is permitted");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
result = g_task_new (screenshot, NULL, callback, user_data);
|
||||||
|
g_task_set_source_tag (result, shell_screenshot_screenshot_window);
|
||||||
|
|
||||||
priv->filename = g_strdup (filename);
|
priv->filename = g_strdup (filename);
|
||||||
priv->callback = callback;
|
|
||||||
priv->include_frame = include_frame;
|
priv->include_frame = include_frame;
|
||||||
priv->include_cursor = include_cursor;
|
priv->include_cursor = include_cursor;
|
||||||
|
|
||||||
@ -586,11 +698,39 @@ shell_screenshot_screenshot_window (ShellScreenshot *screenshot,
|
|||||||
|
|
||||||
meta_disable_unredirect_for_display (shell_global_get_display (shell_global_get ()));
|
meta_disable_unredirect_for_display (shell_global_get_display (shell_global_get ()));
|
||||||
|
|
||||||
g_signal_connect_after (stage, "paint", G_CALLBACK (grab_window_screenshot), (gpointer)screenshot);
|
g_signal_connect_after (stage, "paint", G_CALLBACK (grab_window_screenshot), result);
|
||||||
|
|
||||||
clutter_actor_queue_redraw (stage);
|
clutter_actor_queue_redraw (stage);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* shell_screenshot_screenshot_window_finish:
|
||||||
|
* @screenshot: the #ShellScreenshot
|
||||||
|
* @result: the #GAsyncResult that was provided to the callback
|
||||||
|
* @area: (out) (transfer none): the area that was grabbed in screen coordinates
|
||||||
|
* @filename_used: (out) (transfer none): the name of the file the screenshot
|
||||||
|
* was written to
|
||||||
|
* @error: #GError for error reporting
|
||||||
|
*
|
||||||
|
* Finish the asynchronous operation started by shell_screenshot_screenshot_window()
|
||||||
|
* and obtain its result.
|
||||||
|
*
|
||||||
|
* Returns: whether the operation was successful
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
gboolean
|
||||||
|
shell_screenshot_screenshot_window_finish (ShellScreenshot *screenshot,
|
||||||
|
GAsyncResult *result,
|
||||||
|
cairo_rectangle_int_t **area,
|
||||||
|
const char **filename_used,
|
||||||
|
GError **error)
|
||||||
|
{
|
||||||
|
g_return_val_if_fail (g_async_result_is_tagged (result,
|
||||||
|
shell_screenshot_screenshot_window),
|
||||||
|
FALSE);
|
||||||
|
return finish_screenshot (screenshot, result, area, filename_used, error);
|
||||||
|
}
|
||||||
|
|
||||||
ShellScreenshot *
|
ShellScreenshot *
|
||||||
shell_screenshot_new (void)
|
shell_screenshot_new (void)
|
||||||
{
|
{
|
||||||
|
@ -16,28 +16,41 @@ G_DECLARE_FINAL_TYPE (ShellScreenshot, shell_screenshot,
|
|||||||
|
|
||||||
ShellScreenshot *shell_screenshot_new (void);
|
ShellScreenshot *shell_screenshot_new (void);
|
||||||
|
|
||||||
typedef void (*ShellScreenshotCallback) (ShellScreenshot *screenshot,
|
void shell_screenshot_screenshot_area (ShellScreenshot *screenshot,
|
||||||
gboolean success,
|
int x,
|
||||||
cairo_rectangle_int_t *screenshot_area,
|
int y,
|
||||||
const gchar *filename_used);
|
int width,
|
||||||
|
int height,
|
||||||
|
const char *filename,
|
||||||
|
GAsyncReadyCallback callback,
|
||||||
|
gpointer user_data);
|
||||||
|
gboolean shell_screenshot_screenshot_area_finish (ShellScreenshot *screenshot,
|
||||||
|
GAsyncResult *result,
|
||||||
|
cairo_rectangle_int_t **area,
|
||||||
|
const char **filename_used,
|
||||||
|
GError **error);
|
||||||
|
|
||||||
void shell_screenshot_screenshot_area (ShellScreenshot *screenshot,
|
void shell_screenshot_screenshot_window (ShellScreenshot *screenshot,
|
||||||
int x,
|
gboolean include_frame,
|
||||||
int y,
|
gboolean include_cursor,
|
||||||
int width,
|
const char *filename,
|
||||||
int height,
|
GAsyncReadyCallback callback,
|
||||||
const char *filename,
|
gpointer user_data);
|
||||||
ShellScreenshotCallback callback);
|
gboolean shell_screenshot_screenshot_window_finish (ShellScreenshot *screenshot,
|
||||||
|
GAsyncResult *result,
|
||||||
|
cairo_rectangle_int_t **area,
|
||||||
|
const char **filename_used,
|
||||||
|
GError **error);
|
||||||
|
|
||||||
void shell_screenshot_screenshot_window (ShellScreenshot *screenshot,
|
void shell_screenshot_screenshot (ShellScreenshot *screenshot,
|
||||||
gboolean include_frame,
|
gboolean include_cursor,
|
||||||
gboolean include_cursor,
|
const char *filename,
|
||||||
const char *filename,
|
GAsyncReadyCallback callback,
|
||||||
ShellScreenshotCallback callback);
|
gpointer user_data);
|
||||||
|
gboolean shell_screenshot_screenshot_finish (ShellScreenshot *screenshot,
|
||||||
void shell_screenshot_screenshot (ShellScreenshot *screenshot,
|
GAsyncResult *result,
|
||||||
gboolean include_cursor,
|
cairo_rectangle_int_t **area,
|
||||||
const char *filename,
|
const char **filename_used,
|
||||||
ShellScreenshotCallback callback);
|
GError **error);
|
||||||
|
|
||||||
#endif /* ___SHELL_SCREENSHOT_H__ */
|
#endif /* ___SHELL_SCREENSHOT_H__ */
|
||||||
|
Loading…
Reference in New Issue
Block a user