Issue #431: handle logoff, reboot and shutdown events.

GIMP will now inhibit the LOGOUT event on OSes which support it.
This commit is contained in:
Jehan 2023-04-04 22:41:07 +02:00
parent c71c93bb0f
commit bce051d2a4
4 changed files with 105 additions and 0 deletions

View file

@ -67,6 +67,7 @@ gimp_console_app_new (Gimp *gimp,
GimpConsoleApp *app;
app = g_object_new (GIMP_TYPE_CONSOLE_APP,
"application-id", GIMP_APPLICATION_ID,
"gimp", gimp,
"filenames", filenames,
"as-new", as_new,

View file

@ -20,6 +20,8 @@
G_BEGIN_DECLS
#define GIMP_APPLICATION_ID "org.gimp.GIMP"
enum
{
GIMP_CORE_APP_PROP_0,

View file

@ -131,6 +131,7 @@ gimp_app_new (Gimp *gimp,
GimpApp *app;
app = g_object_new (GIMP_TYPE_APP,
"application-id", GIMP_APPLICATION_ID,
"gimp", gimp,
"filenames", filenames,
"as-new", as_new,

View file

@ -108,6 +108,8 @@
#include "icon-themes.h"
#include "themes.h"
#include "gimp-intl.h"
/* local function prototypes */
@ -186,6 +188,10 @@ static GimpMetadataRotationPolicy
GimpContext *context,
gboolean *dont_ask);
static void gui_inhibit (Gimp *gimp);
static void gui_image_disconnect (GimpImage *image,
Gimp *gimp);
/* public functions */
@ -424,6 +430,25 @@ gui_display_create (Gimp *gimp,
gimp_context_set_display (context, display);
}
if (image)
{
g_signal_handlers_disconnect_by_func (image,
G_CALLBACK (gui_inhibit),
gimp);
g_signal_handlers_disconnect_by_func (image,
G_CALLBACK (gui_image_disconnect),
gimp);
g_signal_connect_swapped (image, "dirty",
G_CALLBACK (gui_inhibit),
gimp);
g_signal_connect_swapped (image, "clean",
G_CALLBACK (gui_inhibit),
gimp);
g_signal_connect_after (image, "disconnect",
G_CALLBACK (gui_image_disconnect),
gimp);
}
return display;
}
@ -923,3 +948,79 @@ gui_query_rotation_policy (Gimp *gimp,
return metadata_rotation_import_dialog_run (image, context,
NULL, dont_ask);
}
static void
gui_inhibit (Gimp *gimp)
{
static gint cookie = 0;
GtkApplication *app;
app = GTK_APPLICATION (g_application_get_default ());
if (gtk_application_is_inhibited (app, GTK_APPLICATION_INHIBIT_LOGOUT))
{
gtk_application_uninhibit (app, cookie);
cookie = 0;
}
if (gimp_displays_dirty (gimp))
{
GimpContainer *images;
gint num_images;
gchar *reason;
GimpImage *image;
GList *list;
GtkWindow *window = NULL;
images = gimp_displays_get_dirty_images (gimp);
num_images = gimp_container_get_n_children (images);
image = (GimpImage *) gimp_container_get_first_child (images);
g_object_unref (images);
for (list = gimp_get_display_iter (gimp); list; list = list->next)
{
GimpDisplay *display = list->data;
if (gimp_display_get_image (display) == image)
{
GimpDisplayShell *shell;
GtkWidget *toplevel;
shell = gimp_display_get_shell (display);
toplevel = gtk_widget_get_toplevel (GTK_WIDGET (shell));
if (GTK_IS_WINDOW (toplevel))
{
window = GTK_WINDOW (toplevel);
break;
}
}
}
/* TRANSLATORS: unless your language msgstr[0] applies to 1 only (as in
* English), replace "one" with %d.
*/
reason = g_strdup_printf (ngettext ("There is one image with unsaved changes!",
"There are %d images with unsaved changes!",
num_images),
num_images);
cookie = gtk_application_inhibit (app, window,
GTK_APPLICATION_INHIBIT_LOGOUT,
reason);
g_free (reason);
}
}
static void
gui_image_disconnect (GimpImage *image,
Gimp *gimp)
{
gui_inhibit (gimp);
g_signal_handlers_disconnect_by_func (image,
G_CALLBACK (gui_inhibit),
gimp);
g_signal_handlers_disconnect_by_func (image,
G_CALLBACK (gui_image_disconnect),
gimp);
}