user-accounts: Simplify generated password handling
Move the 'generate password' icon into the entry to make the focus chain more straightforward. Also switch from generating a choice of 6 passwords in a menu, just put put the next choice directly into the entry. To keep the password generation keyboard accessible, add a 'Generate password' context menu item. https://bugzilla.gnome.org/show_bug.cgi?id=633601 https://bugzilla.gnome.org/show_bug.cgi?id=658522
This commit is contained in:
parent
359f029419
commit
a7beb087db
2 changed files with 55 additions and 128 deletions
|
@ -206,30 +206,13 @@
|
|||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="visibility">False</property>
|
||||
<property name="secondary-icon-name">system-run-symbolic</property>
|
||||
<property name="secondary-icon-tooltip-text" translatable="yes">Generate a password</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="position">0</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkButton" id="generate-again-button">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="receives_default">False</property>
|
||||
<property name="tooltip_text" translatable="yes">Choose a generated password</property>
|
||||
<child>
|
||||
<object class="GtkImage" id="generate-again-image">
|
||||
<property name="visible">True</property>
|
||||
<property name="stock">gtk-execute</property>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">False</property>
|
||||
<property name="position">1</property>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="position">0</property>
|
||||
|
|
|
@ -50,8 +50,6 @@ struct _UmPasswordDialog {
|
|||
GtkWidget *strength_indicator_label;
|
||||
GtkWidget *normal_hint_entry;
|
||||
GtkWidget *normal_hint_label;
|
||||
GtkWidget *generate_button;
|
||||
GtkWidget *generate_menu;
|
||||
GtkWidget *show_password_button;
|
||||
GtkWidget *ok_button;
|
||||
|
||||
|
@ -62,88 +60,35 @@ struct _UmPasswordDialog {
|
|||
gboolean old_password_ok;
|
||||
|
||||
PasswdHandler *passwd_handler;
|
||||
|
||||
gchar **generated;
|
||||
gint next_generated;
|
||||
};
|
||||
|
||||
static void
|
||||
generate_clicked (GtkButton *button,
|
||||
UmPasswordDialog *um)
|
||||
{
|
||||
gtk_menu_popup (GTK_MENU (um->generate_menu),
|
||||
NULL, NULL,
|
||||
(GtkMenuPositionFunc) popup_menu_below_button, um->generate_button,
|
||||
0, gtk_get_current_event_time ());
|
||||
|
||||
gtk_widget_set_has_tooltip (um->generate_button, FALSE);
|
||||
}
|
||||
|
||||
static void
|
||||
generate_draw (GtkWidget *widget,
|
||||
cairo_t *cr,
|
||||
UmPasswordDialog *um)
|
||||
{
|
||||
if (!gtk_widget_is_sensitive (widget))
|
||||
return;
|
||||
|
||||
down_arrow (gtk_widget_get_style_context (widget),
|
||||
cr,
|
||||
gtk_widget_get_allocated_width (widget) - 12,
|
||||
gtk_widget_get_allocated_height (widget) - 12,
|
||||
12, 12);
|
||||
}
|
||||
|
||||
static void
|
||||
activate_password_item (GtkMenuItem *item,
|
||||
UmPasswordDialog *um)
|
||||
{
|
||||
const char *password;
|
||||
|
||||
password = gtk_menu_item_get_label (item);
|
||||
|
||||
gtk_entry_set_text (GTK_ENTRY (um->password_entry), password);
|
||||
gtk_entry_set_text (GTK_ENTRY (um->verify_entry), "");
|
||||
gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (um->show_password_button), TRUE);
|
||||
gtk_widget_grab_focus (um->verify_entry);
|
||||
}
|
||||
|
||||
static void generate_passwords (UmPasswordDialog *um);
|
||||
|
||||
static void
|
||||
activate_generate_item (GtkMenuItem *item,
|
||||
UmPasswordDialog *um)
|
||||
{
|
||||
generate_passwords (um);
|
||||
generate_clicked (GTK_BUTTON (um->generate_button), um);
|
||||
}
|
||||
|
||||
static void
|
||||
on_generate_menu_unmap (GtkWidget *menu,
|
||||
UmPasswordDialog *um)
|
||||
{
|
||||
gtk_widget_set_has_tooltip (um->generate_button, TRUE);
|
||||
}
|
||||
|
||||
static void
|
||||
generate_passwords (UmPasswordDialog *um)
|
||||
generate_one_password (GtkWidget *widget,
|
||||
UmPasswordDialog *um)
|
||||
{
|
||||
gint min_len, max_len;
|
||||
gchar *output, *err, *cmdline;
|
||||
gchar *output, *err, *cmdline, *p;
|
||||
gint status;
|
||||
GError *error;
|
||||
gint i;
|
||||
GtkWidget *item;
|
||||
|
||||
if (um->generated && um->generated[um->next_generated]) {
|
||||
gtk_entry_set_text (GTK_ENTRY (um->password_entry), um->generated[um->next_generated]);
|
||||
gtk_entry_set_text (GTK_ENTRY (um->verify_entry), "");
|
||||
um->next_generated++;
|
||||
return;
|
||||
}
|
||||
|
||||
g_strfreev (um->generated);
|
||||
um->generated = NULL;
|
||||
um->next_generated = 0;
|
||||
|
||||
min_len = 6;
|
||||
max_len = 12;
|
||||
|
||||
if (um->generate_menu) {
|
||||
gtk_widget_destroy (um->generate_menu);
|
||||
}
|
||||
|
||||
um->generate_menu = gtk_menu_new ();
|
||||
g_signal_connect (um->generate_menu, "unmap",
|
||||
G_CALLBACK (on_generate_menu_unmap), um);
|
||||
|
||||
cmdline = g_strdup_printf ("apg -n 6 -M SNC -m %d -x %d", min_len, max_len);
|
||||
cmdline = g_strdup_printf ("apg -n 10 -M SNC -m %d -x %d", min_len, max_len);
|
||||
error = NULL;
|
||||
output = NULL;
|
||||
err = NULL;
|
||||
|
@ -151,19 +96,16 @@ generate_passwords (UmPasswordDialog *um)
|
|||
g_warning ("Failed to run apg: %s", error->message);
|
||||
g_error_free (error);
|
||||
} else if (WEXITSTATUS (status) == 0) {
|
||||
char **lines;
|
||||
lines = g_strsplit (output, "\n", 0);
|
||||
for (i = 0; lines[i]; i++) {
|
||||
if (lines[i][0] == 0)
|
||||
continue;
|
||||
p = output;
|
||||
if (*p == '\n')
|
||||
p++;
|
||||
if (p[strlen(p) - 1] == '\n')
|
||||
p[strlen(p) - 1] = '\0';
|
||||
um->generated = g_strsplit (p, "\n", -1);
|
||||
|
||||
item = gtk_menu_item_new_with_label (lines[i]);
|
||||
g_signal_connect (item, "activate",
|
||||
G_CALLBACK (activate_password_item), um);
|
||||
gtk_widget_show (item);
|
||||
gtk_menu_shell_append (GTK_MENU_SHELL (um->generate_menu), item);
|
||||
}
|
||||
g_strfreev (lines);
|
||||
gtk_entry_set_text (GTK_ENTRY (um->password_entry), um->generated[0]);
|
||||
gtk_entry_set_text (GTK_ENTRY (um->verify_entry), "");
|
||||
um->next_generated = 1;
|
||||
} else {
|
||||
g_warning ("agp returned an error: %s", err);
|
||||
}
|
||||
|
@ -171,16 +113,29 @@ generate_passwords (UmPasswordDialog *um)
|
|||
g_free (cmdline);
|
||||
g_free (output);
|
||||
g_free (err);
|
||||
}
|
||||
|
||||
item = gtk_separator_menu_item_new ();
|
||||
gtk_widget_show (item);
|
||||
gtk_menu_shell_append (GTK_MENU_SHELL (um->generate_menu), item);
|
||||
static void
|
||||
activate_icon (GtkEntry *entry,
|
||||
GtkEntryIconPosition pos,
|
||||
GdkEventButton *event,
|
||||
UmPasswordDialog *um)
|
||||
{
|
||||
generate_one_password (GTK_WIDGET (entry), um);
|
||||
}
|
||||
|
||||
item = gtk_menu_item_new_with_label (_("More choices..."));
|
||||
static void
|
||||
populate_menu (GtkEntry *entry,
|
||||
GtkMenu *menu,
|
||||
UmPasswordDialog *um)
|
||||
{
|
||||
GtkWidget *item;
|
||||
|
||||
item = gtk_menu_item_new_with_mnemonic (_("_Generate a password"));
|
||||
g_signal_connect (item, "activate",
|
||||
G_CALLBACK (activate_generate_item), um);
|
||||
G_CALLBACK (generate_one_password), um);
|
||||
gtk_widget_show (item);
|
||||
gtk_menu_shell_append (GTK_MENU_SHELL (um->generate_menu), item);
|
||||
gtk_menu_shell_append (GTK_MENU_SHELL (menu), item);
|
||||
}
|
||||
|
||||
/* This code is based on the Master Password dialog in Firefox
|
||||
|
@ -411,8 +366,7 @@ action_changed (GtkComboBox *combo,
|
|||
active = gtk_combo_box_get_active (combo);
|
||||
if (active == 0) {
|
||||
gtk_widget_set_sensitive (um->password_entry, TRUE);
|
||||
gtk_widget_set_sensitive (um->generate_button, TRUE);
|
||||
gtk_widget_set_has_tooltip (um->generate_button, TRUE);
|
||||
gtk_entry_set_icon_sensitive (GTK_ENTRY (um->password_entry), GTK_ENTRY_ICON_SECONDARY, TRUE);
|
||||
gtk_widget_set_sensitive (um->verify_entry, TRUE);
|
||||
gtk_widget_set_sensitive (um->old_password_entry, TRUE);
|
||||
gtk_widget_set_sensitive (um->normal_hint_entry, TRUE);
|
||||
|
@ -424,8 +378,7 @@ action_changed (GtkComboBox *combo,
|
|||
}
|
||||
else {
|
||||
gtk_widget_set_sensitive (um->password_entry, FALSE);
|
||||
gtk_widget_set_sensitive (um->generate_button, FALSE);
|
||||
gtk_widget_set_has_tooltip (um->generate_button, FALSE);
|
||||
gtk_entry_set_icon_sensitive (GTK_ENTRY (um->password_entry), GTK_ENTRY_ICON_SECONDARY, FALSE);
|
||||
gtk_widget_set_sensitive (um->verify_entry, FALSE);
|
||||
gtk_widget_set_sensitive (um->old_password_entry, FALSE);
|
||||
gtk_widget_set_sensitive (um->normal_hint_entry, FALSE);
|
||||
|
@ -670,6 +623,11 @@ um_password_dialog_new (void)
|
|||
G_CALLBACK (password_entry_changed), um);
|
||||
gtk_entry_set_visibility (GTK_ENTRY (widget), FALSE);
|
||||
|
||||
g_signal_connect (widget, "icon-press",
|
||||
G_CALLBACK (activate_icon), um);
|
||||
g_signal_connect (widget, "populate-popup",
|
||||
G_CALLBACK (populate_menu), um);
|
||||
|
||||
um->password_entry = widget;
|
||||
|
||||
widget = (GtkWidget *) gtk_builder_get_object (builder, "old-password-entry");
|
||||
|
@ -700,18 +658,6 @@ um_password_dialog_new (void)
|
|||
widget = (GtkWidget *) gtk_builder_get_object (builder, "strength-indicator-label");
|
||||
gtk_label_set_width_chars (GTK_LABEL (widget), len);
|
||||
|
||||
|
||||
widget = (GtkWidget *) gtk_builder_get_object (builder, "generate-again-button");
|
||||
g_signal_connect (widget, "clicked",
|
||||
G_CALLBACK (generate_clicked), um);
|
||||
#if 0
|
||||
g_signal_connect (widget, "state-changed",
|
||||
G_CALLBACK (generate_state_changed), um);
|
||||
#endif
|
||||
um->generate_button = widget;
|
||||
g_signal_connect_after (widget, "draw",
|
||||
G_CALLBACK (generate_draw), um);
|
||||
|
||||
um->normal_hint_entry = (GtkWidget *) gtk_builder_get_object (builder, "normal-hint-entry");
|
||||
|
||||
/* Label size hack.
|
||||
|
@ -728,8 +674,6 @@ um_password_dialog_new (void)
|
|||
|
||||
g_object_unref (builder);
|
||||
|
||||
generate_passwords (um);
|
||||
|
||||
return um;
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue