diff options
Diffstat (limited to 'src/mate-screensaver-preferences.c')
-rw-r--r-- | src/mate-screensaver-preferences.c | 253 |
1 files changed, 146 insertions, 107 deletions
diff --git a/src/mate-screensaver-preferences.c b/src/mate-screensaver-preferences.c index 44e0c7b..1bcdcaf 100644 --- a/src/mate-screensaver-preferences.c +++ b/src/mate-screensaver-preferences.c @@ -1,6 +1,7 @@ /* -*- Mode: C; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 8 -*- * * Copyright (C) 2004-2006 William Jon McCann <[email protected]> + * Copyright (C) 2012-2021 MATE Developers * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as @@ -92,10 +93,10 @@ static GSettings *session_settings = NULL; static GSettings *lockdown_settings = NULL; static MateDesktopThumbnailFactory *thumb_factory = NULL; -static gint32 +static gdouble config_get_activate_delay (gboolean *is_writable) { - gint32 delay; + gint delay; if (is_writable) { @@ -103,14 +104,12 @@ config_get_activate_delay (gboolean *is_writable) KEY_IDLE_DELAY); } - delay = g_settings_get_int (session_settings, KEY_IDLE_DELAY); - - if (delay < 1) + if ((delay = g_settings_get_int (session_settings, KEY_IDLE_DELAY)) < 1) { - delay = 1; + return 1.0; } - return delay; + return (gdouble) delay; } static void @@ -119,6 +118,31 @@ config_set_activate_delay (gint32 timeout) g_settings_set_int (session_settings, KEY_IDLE_DELAY, timeout); } +static gdouble +config_get_lock_delay (gboolean *is_writable) +{ + gint delay; + + if (is_writable) + { + *is_writable = g_settings_is_writable (screensaver_settings, + KEY_LOCK_DELAY); + } + + if ((delay = g_settings_get_int (screensaver_settings, KEY_LOCK_DELAY)) < 1) + { + return 0.0; + } + + return (gdouble) delay; +} + +static void +config_set_lock_delay (gint32 timeout) +{ + g_settings_set_int (screensaver_settings, KEY_LOCK_DELAY, timeout); +} + static int config_get_mode (gboolean *is_writable) { @@ -577,6 +601,16 @@ activate_delay_value_changed_cb (GtkRange *range, config_set_activate_delay ((gint32)value); } +static void +lock_delay_value_changed_cb (GtkRange *range, + gpointer user_data) +{ + gdouble value; + + value = gtk_range_get_value (range); + config_set_lock_delay ((gint32)value); +} + static int compare_theme_names (char *name_a, char *name_b, @@ -662,19 +696,20 @@ separator_func (GtkTreeModel *model, GtkTreeIter *iter, gpointer data) { - int column = GPOINTER_TO_INT (data); - char *text; + int column = GPOINTER_TO_INT (data); + gboolean res = FALSE; + char *text; gtk_tree_model_get (model, iter, column, &text, -1); if (text != NULL && strcmp (text, "__separator") == 0) { - return TRUE; + res = TRUE; } g_free (text); - return FALSE; + return res; } static void @@ -720,7 +755,7 @@ setup_treeview (GtkWidget *tree, select = gtk_tree_view_get_selection (GTK_TREE_VIEW (tree)); gtk_tree_selection_set_mode (select, GTK_SELECTION_SINGLE); - g_signal_connect (G_OBJECT (select), "changed", + g_signal_connect (select, "changed", G_CALLBACK (tree_selection_changed_cb), preview); @@ -933,10 +968,8 @@ drag_data_received_cb (GtkWidget *widget, static char * time_to_string_text (long time) { - char *secs, *mins, *hours, *string; - int sec, min, hour; - - int n, inc_len, len_minutes; + char *secs, *mins, *hours, *string; + int sec, min, hour; sec = time % 60; time = time - sec; @@ -953,60 +986,17 @@ time_to_string_text (long time) secs = g_strdup_printf (ngettext ("%d second", "%d seconds", sec), sec); - inc_len = strlen (g_strdup_printf (_("%s %s"), - g_strdup_printf (ngettext ("%d hour", - "%d hours", 1), 1), - g_strdup_printf (ngettext ("%d minute", - "%d minutes", 59), 59))) - 1; - - len_minutes = 0; - - for (n = 2; n < 60; n++) - { - if (n < 10) - { - if ((strlen (g_str_to_ascii (g_strdup_printf (ngettext ("%d minute", - "%d minutes", n), n), NULL)) - 2) > len_minutes) - - len_minutes = strlen (g_str_to_ascii (g_strdup_printf (ngettext ("%d minute", - "%d minutes", n), n), NULL)) - 2; - } - else - { - if ((strlen (g_str_to_ascii (g_strdup_printf (ngettext ("%d minute", - "%d minutes", n), n), NULL)) - 3) > len_minutes) - - len_minutes = strlen (g_str_to_ascii (g_strdup_printf (ngettext ("%d minute", - "%d minutes", n), n), NULL)) - 3; - } - } - - if ((strlen (g_str_to_ascii (g_strdup_printf (ngettext ("%d minute", - "%d minutes", 1), 1), NULL)) - 2) > len_minutes) - - len_minutes = strlen (g_str_to_ascii (g_strdup_printf (ngettext ("%d minute", - "%d minutes", 1), 1), NULL)) - 2; - - if (len_minutes < 1) - len_minutes = 1; - if (hour > 0) { if (sec > 0) - { /* hour:minutes:seconds */ string = g_strdup_printf (_("%s %s %s"), hours, mins, secs); - } else if (min > 0) - { /* hour:minutes */ string = g_strdup_printf (_("%s %s"), hours, mins); - } else - { /* hour */ string = g_strdup_printf (_("%s"), hours); - } } else if (min > 0) { @@ -1019,36 +1009,6 @@ time_to_string_text (long time) { /* minutes */ string = g_strdup_printf (_("%s"), mins); - - if (min < 10) - { - if (min == 1) - while (strlen (string) != (len_minutes + inc_len + 3)) - { - if (strlen (string) % 2 == 0) - string = g_strconcat (string, " ", NULL); - else - string = g_strconcat (" " , string, NULL); - } - else - while (strlen (string) != (len_minutes + inc_len)) - { - if (strlen (string) % 2 == 0) - string = g_strconcat (string, " ", NULL); - else - string = g_strconcat (" " , string, NULL); - } - } - else - { - while (strlen (string) != (len_minutes + inc_len - 1)) - { - if (strlen (string) % 2 == 0) - string = g_strconcat (string, " ", NULL); - else - string = g_strconcat (" " , string, NULL); - } - } } } else @@ -1068,10 +1028,70 @@ static char * format_value_callback_time (GtkScale *scale, gdouble value) { + gchar *time_str, *big_time_str; + GtkAdjustment *adj; + gdouble lower, range, delta; + gint pad_size; + + /* get the value representation as a string */ if (value == 0) - return g_strdup_printf (_("Never")); + time_str = g_strdup (_("Never")); + else + time_str = time_to_string_text ((long) (value * 60.0)); + + /* Now, adjust the string so the representation for the bounds are the + * longest ones, and try and adjust the length as smoothly as possible. + * The issue here is that GTK is using the lower and upper value + * representations to compute the largest expected value's bounding box, + * so those need to be bigger than anything else we might represent, + * otherwise layout gets messed up (wraps and overflows). To achieve this, + * we pad the values near each bound so its length is at least the same as + * the biggest actual value. We cannot really do anything perfect here + * because what matters is the pango layout size for the largest value, but + * we don't have access to enough information to create one matching what + * GTK will actually use, and even so it'd be trial-and-error until the + * layout is big enough. So the silly assumptions below are probably good + * enough. */ + adj = gtk_range_get_adjustment (GTK_RANGE (scale)); + lower = gtk_adjustment_get_lower (adj); + range = gtk_adjustment_get_upper (adj) - lower; + delta = range / 2 - (value - lower); + /* the largest (character-wise) time string we expect */ + big_time_str = time_to_string_text (7199 /* 1:59:59 */); + pad_size = ((g_utf8_strlen (big_time_str, -1) * (ABS (delta) / range)) - + g_utf8_strlen (time_str, -1)); + g_free (big_time_str); + if (pad_size > 0) + { + /* pad string with EM SPACE (U+2003) */ + GString *padded = g_string_new (NULL); + + /* adjust pad side in RTL locales that aren't actually translated, as + * a properly translated one would have text drawn RTL already */ + if (gtk_widget_get_direction (GTK_WIDGET (scale)) == GTK_TEXT_DIR_RTL) + { + const gchar *msg_plural = "%d minutes"; + if (ngettext ("%d minute", msg_plural, 2) == msg_plural) + delta *= -1; + } - return time_to_string_text (value * 60.0); + if (delta < 0) + { + for (gint i = 0; i < pad_size; i++) + g_string_append_unichar (padded, 0x2003); + g_string_append (padded, time_str); + } + else + { + g_string_append (padded, time_str); + for (gint i = 0; i < pad_size; i++) + g_string_append_unichar (padded, 0x2003); + } + g_free (time_str); + time_str = g_string_free (padded, FALSE); + } + + return time_str; } static void @@ -1089,7 +1109,11 @@ enabled_checkbox_toggled (GtkToggleButton *button, gpointer user_data) static void picture_filename_changed (GtkFileChooserButton *button, gpointer user_data) { - g_settings_set_string (screensaver_settings, "picture-filename", gtk_file_chooser_get_filename (GTK_FILE_CHOOSER (button))); + char *picture_filename; + + picture_filename = gtk_file_chooser_get_filename (GTK_FILE_CHOOSER (button)); + g_settings_set_string (screensaver_settings, "picture-filename", picture_filename); + g_free (picture_filename); } static void @@ -1149,11 +1173,11 @@ ui_set_enabled (gboolean enabled) } static void -ui_set_delay (int delay) +ui_set_delay (const char *name, gdouble delay) { GtkWidget *widget; - widget = GTK_WIDGET (gtk_builder_get_object (builder, "activate_delay_hscale")); + widget = GTK_WIDGET (gtk_builder_get_object (builder, name)); gtk_range_set_value (GTK_RANGE (widget), delay); } @@ -1196,8 +1220,14 @@ key_changed_cb (GSettings *settings, const gchar *key, gpointer data) int delay; delay = g_settings_get_int (settings, key); - ui_set_delay (delay); + ui_set_delay ("activate_delay_hscale", (gdouble) delay); + } + else if (strcmp (key, KEY_LOCK_DELAY) == 0) + { + int delay; + delay = g_settings_get_int (settings, key); + ui_set_delay ("lock_delay_hscale", (gdouble) delay); } else { @@ -1419,12 +1449,10 @@ spawn_command_line_on_display_sync (GdkDisplay *display, return retval; } - static GdkVisual * get_best_visual_for_display (GdkDisplay *display) { GdkScreen *screen; - char *command; char *std_output; int exit_status; GError *error; @@ -1436,19 +1464,18 @@ get_best_visual_for_display (GdkDisplay *display) visual = NULL; screen = gdk_display_get_default_screen (display); - command = g_build_filename (LIBEXECDIR, "mate-screensaver-gl-helper", NULL); - error = NULL; std_output = NULL; res = spawn_command_line_on_display_sync (display, - command, + MATE_SCREENSAVER_GL_HELPER_PATH, &std_output, NULL, &exit_status, &error); if (! res) { - gs_debug ("Could not run command '%s': %s", command, error->message); + gs_debug ("Could not run command '%s': %s", + MATE_SCREENSAVER_GL_HELPER_PATH, error->message); g_error_free (error); goto out; } @@ -1469,12 +1496,10 @@ get_best_visual_for_display (GdkDisplay *display) } out: g_free (std_output); - g_free (command); return visual; } - static void widget_set_best_visual (GtkWidget *widget) { @@ -1598,7 +1623,7 @@ init_capplet (void) GtkWidget *treeview; GtkWidget *list_scroller; GtkWidget *activate_delay_hscale; - GtkWidget *activate_delay_hbox; + GtkWidget *lock_delay_hscale; GtkWidget *label; GtkWidget *enabled_checkbox; GtkWidget *lock_checkbox; @@ -1647,7 +1672,7 @@ init_capplet (void) treeview = GTK_WIDGET (gtk_builder_get_object (builder, "savers_treeview")); list_scroller = GTK_WIDGET (gtk_builder_get_object (builder, "themes_scrolled_window")); activate_delay_hscale = GTK_WIDGET (gtk_builder_get_object (builder, "activate_delay_hscale")); - activate_delay_hbox = GTK_WIDGET (gtk_builder_get_object (builder, "activate_delay_hbox")); + lock_delay_hscale = GTK_WIDGET (gtk_builder_get_object (builder, "lock_delay_hscale")); enabled_checkbox = GTK_WIDGET (gtk_builder_get_object (builder, "enable_checkbox")); lock_checkbox = GTK_WIDGET (gtk_builder_get_object (builder, "lock_checkbox")); root_warning_label = GTK_WIDGET (gtk_builder_get_object (builder, "root_warning_label")); @@ -1662,6 +1687,8 @@ init_capplet (void) label = GTK_WIDGET (gtk_builder_get_object (builder, "activate_delay_label")); gtk_label_set_mnemonic_widget (GTK_LABEL (label), activate_delay_hscale); + label = GTK_WIDGET (gtk_builder_get_object (builder, "lock_delay_label")); + gtk_label_set_mnemonic_widget (GTK_LABEL (label), lock_delay_hscale); label = GTK_WIDGET (gtk_builder_get_object (builder, "savers_label")); gtk_label_set_mnemonic_widget (GTK_LABEL (label), treeview); @@ -1693,14 +1720,23 @@ init_capplet (void) NULL); activate_delay = config_get_activate_delay (&is_writable); - ui_set_delay (activate_delay); + ui_set_delay ("activate_delay_hscale", activate_delay); if (! is_writable) { - gtk_widget_set_sensitive (activate_delay_hbox, FALSE); + gtk_widget_set_sensitive (activate_delay_hscale, FALSE); } g_signal_connect (activate_delay_hscale, "format-value", G_CALLBACK (format_value_callback_time), NULL); + activate_delay = config_get_lock_delay (&is_writable); + ui_set_delay ("lock_delay_hscale", activate_delay); + if (! is_writable) + { + gtk_widget_set_sensitive (lock_delay_hscale, FALSE); + } + g_signal_connect (lock_delay_hscale, "format-value", + G_CALLBACK (format_value_callback_time), NULL); + gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (lock_checkbox), config_get_lock (&is_writable)); if (! is_writable) { @@ -1772,6 +1808,9 @@ init_capplet (void) g_signal_connect (activate_delay_hscale, "value-changed", G_CALLBACK (activate_delay_value_changed_cb), NULL); + g_signal_connect (lock_delay_hscale, "value-changed", + G_CALLBACK (lock_delay_value_changed_cb), NULL); + g_signal_connect (dialog, "response", G_CALLBACK (response_cb), NULL); |