2 * Copyright (C) 2010-2011 Robert Ancell.
3 * Author: Robert Ancell <robert.ancell@canonical.com>
5 * This program is free software: you can redistribute it and/or modify it under
6 * the terms of the GNU General Public License as published by the Free Software
7 * Foundation, either version 3 of the License, or (at your option) any later
8 * version. See http://www.gnu.org/copyleft/gpl.html the full text of the
14 #include <glib/gi18n.h>
15 #include <cairo-xlib.h>
16 #include <gdk-pixbuf/gdk-pixbuf.h>
21 static LightDMGreeter *greeter;
22 static GtkWindow *login_window, *panel_window;
23 static GtkLabel *message_label, *prompt_label;
24 static GtkTreeView *user_view;
25 static GtkWidget *login_box, *prompt_box;
26 static GtkEntry *prompt_entry;
27 static GtkComboBox *session_combo;
28 static gchar *default_font_name, *default_theme_name;
29 static gboolean cancelling = FALSE, prompted = FALSE;
37 if (!gtk_combo_box_get_active_iter (session_combo, &iter))
38 return g_strdup (lightdm_greeter_get_default_session_hint (greeter));
40 gtk_tree_model_get (gtk_combo_box_get_model (session_combo), &iter, 1, &session, -1);
46 set_session (const gchar *session)
48 GtkTreeModel *model = gtk_combo_box_get_model (session_combo);
50 const gchar *default_session;
52 if (session && gtk_tree_model_get_iter_first (model, &iter))
58 gtk_tree_model_get (model, &iter, 1, &s, -1);
59 matched = strcmp (s, session) == 0;
63 gtk_combo_box_set_active_iter (session_combo, &iter);
66 } while (gtk_tree_model_iter_next (model, &iter));
69 /* If failed to find this session, then try the default */
70 default_session = lightdm_greeter_get_default_session_hint (greeter);
71 if (default_session && g_strcmp0 (session, default_session) != 0)
72 set_session (lightdm_greeter_get_default_session_hint (greeter));
76 set_message_label (const gchar *text)
78 gtk_widget_set_visible (GTK_WIDGET (message_label), strcmp (text, "") != 0);
79 gtk_label_set_text (message_label, text);
83 start_authentication (const gchar *username)
90 lightdm_greeter_authenticate (greeter, NULL);
92 else if (strcmp (username, "*guest") == 0)
94 lightdm_greeter_authenticate_as_guest (greeter);
100 user = lightdm_user_list_get_user_by_name (lightdm_user_list_get_instance (), username);
102 set_session (lightdm_user_get_session (user));
106 lightdm_greeter_authenticate (greeter, username);
111 cancel_authentication (void)
113 /* If in authentication then stop that first */
115 if (lightdm_greeter_get_in_authentication (greeter))
118 lightdm_greeter_cancel_authentication (greeter);
122 /* Start a new login or return to the user list */
123 if (lightdm_greeter_get_hide_users_hint (greeter))
124 start_authentication (NULL);
127 gtk_widget_hide (login_box);
128 gtk_widget_grab_focus (GTK_WIDGET (user_view));
137 session = get_session ();
138 if (!lightdm_greeter_start_session_sync (greeter, session, NULL))
140 set_message_label (_("Failed to start session"));
141 start_authentication (lightdm_greeter_get_authentication_user (greeter));
146 void user_treeview_row_activated_cb (GtkWidget *widget, GtkTreePath *path, GtkTreeViewColumn *column);
149 user_treeview_row_activated_cb (GtkWidget *widget, GtkTreePath *path, GtkTreeViewColumn *column)
151 GtkTreeModel *model = gtk_tree_view_get_model (user_view);
155 gtk_tree_model_get_iter (GTK_TREE_MODEL (model), &iter, path);
156 gtk_tree_model_get (GTK_TREE_MODEL (model), &iter, 0, &user, -1);
157 start_authentication (user);
164 GtkTreeModel *model = gtk_tree_view_get_model (user_view);
168 if (gtk_tree_selection_get_selected (gtk_tree_view_get_selection (user_view),
171 gtk_tree_model_get (GTK_TREE_MODEL (model), &iter, 0, &user, -1);
172 start_authentication (user);
179 gboolean user_treeview_button_press_event_cb (GtkWidget *widget, GdkEventButton *event);
182 user_treeview_button_press_event_cb (GtkWidget *widget, GdkEventButton *event)
184 /* Do it in the idle loop so the selection is done first */
185 g_idle_add (idle_select_cb, NULL);
189 void login_cb (GtkWidget *widget);
192 login_cb (GtkWidget *widget)
194 gtk_widget_set_sensitive (GTK_WIDGET (prompt_entry), FALSE);
195 set_message_label ("");
197 if (lightdm_greeter_get_is_authenticated (greeter))
199 else if (lightdm_greeter_get_in_authentication (greeter))
200 lightdm_greeter_respond (greeter, gtk_entry_get_text (prompt_entry));
202 start_authentication (lightdm_greeter_get_authentication_user (greeter));
205 void cancel_cb (GtkWidget *widget);
208 cancel_cb (GtkWidget *widget)
210 cancel_authentication ();
214 show_prompt_cb (LightDMGreeter *greeter, const gchar *text, LightDMPromptType type)
218 gtk_widget_show (GTK_WIDGET (login_box));
219 gtk_label_set_text (prompt_label, text);
220 gtk_widget_set_sensitive (GTK_WIDGET (prompt_entry), TRUE);
221 gtk_entry_set_text (prompt_entry, "");
222 gtk_entry_set_visibility (prompt_entry, type != LIGHTDM_PROMPT_TYPE_SECRET);
223 gtk_widget_show (GTK_WIDGET (prompt_box));
224 gtk_widget_grab_focus (GTK_WIDGET (prompt_entry));
228 show_message_cb (LightDMGreeter *greeter, const gchar *text, LightDMMessageType type)
230 set_message_label (text);
234 authentication_complete_cb (LightDMGreeter *greeter)
236 gtk_entry_set_text (prompt_entry, "");
240 cancel_authentication ();
244 gtk_widget_hide (prompt_box);
245 gtk_widget_show (login_box);
247 if (lightdm_greeter_get_is_authenticated (greeter))
256 set_message_label (_("Incorrect password, please try again"));
257 start_authentication (lightdm_greeter_get_authentication_user (greeter));
260 set_message_label (_("Failed to authenticate"));
265 autologin_timer_expired_cb (LightDMGreeter *greeter)
267 if (lightdm_greeter_get_autologin_guest_hint (greeter))
268 start_authentication ("*guest");
269 else if (lightdm_greeter_get_autologin_user_hint (greeter))
270 start_authentication (lightdm_greeter_get_autologin_user_hint (greeter));
274 center_window (GtkWindow *window)
277 GtkAllocation allocation;
278 GdkRectangle monitor_geometry;
280 screen = gtk_window_get_screen (window);
281 gdk_screen_get_monitor_geometry (screen, gdk_screen_get_primary_monitor (screen), &monitor_geometry);
282 gtk_widget_get_allocation (GTK_WIDGET (window), &allocation);
283 gtk_window_move (window,
284 monitor_geometry.x + (monitor_geometry.width - allocation.width) / 2,
285 monitor_geometry.y + (monitor_geometry.height - allocation.height) / 2);
288 void login_window_size_allocate_cb (GtkWidget *widget, GdkRectangle *allocation);
291 login_window_size_allocate_cb (GtkWidget *widget, GdkRectangle *allocation)
293 center_window (GTK_WINDOW (widget));
296 void suspend_cb (GtkWidget *widget, LightDMGreeter *greeter);
299 suspend_cb (GtkWidget *widget, LightDMGreeter *greeter)
301 lightdm_suspend (NULL);
304 void hibernate_cb (GtkWidget *widget, LightDMGreeter *greeter);
307 hibernate_cb (GtkWidget *widget, LightDMGreeter *greeter)
309 lightdm_hibernate (NULL);
312 void restart_cb (GtkWidget *widget, LightDMGreeter *greeter);
315 restart_cb (GtkWidget *widget, LightDMGreeter *greeter)
319 gtk_widget_hide (GTK_WIDGET (login_window));
321 dialog = gtk_message_dialog_new (NULL,
325 "%s", _("Are you sure you want to close all programs and restart the computer?"));
326 gtk_dialog_add_buttons (GTK_DIALOG (dialog), _("Return To Login"), FALSE, _("Restart"), TRUE, NULL);
327 gtk_widget_show_all (dialog);
328 center_window (GTK_WINDOW (dialog));
330 if (gtk_dialog_run (GTK_DIALOG (dialog)))
331 lightdm_restart (NULL);
333 gtk_widget_destroy (dialog);
334 gtk_widget_show (GTK_WIDGET (login_window));
337 void shutdown_cb (GtkWidget *widget, LightDMGreeter *greeter);
340 shutdown_cb (GtkWidget *widget, LightDMGreeter *greeter)
344 gtk_widget_hide (GTK_WIDGET (login_window));
346 dialog = gtk_message_dialog_new (NULL,
350 "%s", _("Are you sure you want to close all programs and shutdown the computer?"));
351 gtk_dialog_add_buttons (GTK_DIALOG (dialog), _("Return To Login"), FALSE, _("Shutdown"), TRUE, NULL);
352 gtk_widget_show_all (dialog);
353 center_window (GTK_WINDOW (dialog));
355 if (gtk_dialog_run (GTK_DIALOG (dialog)))
356 lightdm_shutdown (NULL);
358 gtk_widget_destroy (dialog);
359 gtk_widget_show (GTK_WIDGET (login_window));
363 user_added_cb (LightDMUserList *user_list, LightDMUser *user)
368 model = gtk_tree_view_get_model (user_view);
370 gtk_list_store_append (GTK_LIST_STORE (model), &iter);
371 gtk_list_store_set (GTK_LIST_STORE (model), &iter,
372 0, lightdm_user_get_name (user),
373 1, lightdm_user_get_display_name (user),
374 2, lightdm_user_get_logged_in (user) ? PANGO_WEIGHT_BOLD : PANGO_WEIGHT_NORMAL,
380 get_user_iter (const gchar *username, GtkTreeIter *iter)
384 model = gtk_tree_view_get_model (user_view);
386 if (!gtk_tree_model_get_iter_first (model, iter))
393 gtk_tree_model_get (model, iter, 0, &name, -1);
394 matched = g_strcmp0 (name, username) == 0;
398 } while (gtk_tree_model_iter_next (model, iter));
404 user_changed_cb (LightDMUserList *user_list, LightDMUser *user)
409 if (!get_user_iter (lightdm_user_get_name (user), &iter))
412 model = gtk_tree_view_get_model (user_view);
413 gtk_list_store_set (GTK_LIST_STORE (model), &iter,
414 0, lightdm_user_get_name (user),
415 1, lightdm_user_get_display_name (user),
416 2, lightdm_user_get_logged_in (user) ? PANGO_WEIGHT_BOLD : PANGO_WEIGHT_NORMAL,
422 user_removed_cb (LightDMUserList *user_list, LightDMUser *user)
427 if (!get_user_iter (lightdm_user_get_name (user), &iter))
430 model = gtk_tree_view_get_model (user_view);
431 gtk_list_store_remove (GTK_LIST_STORE (model), &iter);
434 void a11y_font_cb (GtkWidget *widget);
437 a11y_font_cb (GtkWidget *widget)
439 if (gtk_check_menu_item_get_active (GTK_CHECK_MENU_ITEM (widget)))
441 gchar *font_name, **tokens;
443 g_object_get (gtk_settings_get_default (), "gtk-font-name", &font_name, NULL);
444 tokens = g_strsplit (font_name, " ", 2);
445 if (g_strv_length (tokens) == 2)
447 gint size = atoi (tokens[1]);
451 font_name = g_strdup_printf ("%s %d", tokens[0], size + 10);
456 g_object_set (gtk_settings_get_default (), "gtk-font-name", font_name, NULL);
459 g_object_set (gtk_settings_get_default (), "gtk-font-name", default_font_name, NULL);
462 void a11y_contrast_cb (GtkWidget *widget);
465 a11y_contrast_cb (GtkWidget *widget)
467 if (gtk_check_menu_item_get_active (GTK_CHECK_MENU_ITEM (widget)))
468 g_object_set (gtk_settings_get_default (), "gtk-theme-name", "HighContrastInverse", NULL);
470 g_object_set (gtk_settings_get_default (), "gtk-theme-name", default_theme_name, NULL);
474 sigterm_cb (int signum)
482 const GList *items, *item;
486 g_signal_connect (lightdm_user_list_get_instance (), "user-added", G_CALLBACK (user_added_cb), NULL);
487 g_signal_connect (lightdm_user_list_get_instance (), "user-changed", G_CALLBACK (user_changed_cb), NULL);
488 g_signal_connect (lightdm_user_list_get_instance (), "user-removed", G_CALLBACK (user_removed_cb), NULL);
490 model = gtk_tree_view_get_model (user_view);
491 items = lightdm_user_list_get_users (lightdm_user_list_get_instance ());
492 for (item = items; item; item = item->next)
494 LightDMUser *user = item->data;
496 GdkPixbuf *pixbuf = NULL;
498 image = lightdm_user_get_image (user);
500 pixbuf = gdk_pixbuf_new_from_file_at_scale (image, 64, 64, TRUE, NULL);
502 pixbuf = gtk_icon_theme_load_icon (gtk_icon_theme_get_default (),
505 GTK_ICON_LOOKUP_USE_BUILTIN,
509 pixbuf = gdk_pixbuf_new (GDK_COLORSPACE_RGB, FALSE, 8, 64, 64);
510 memset (gdk_pixbuf_get_pixels (pixbuf), 0, gdk_pixbuf_get_height (pixbuf) * gdk_pixbuf_get_rowstride (pixbuf) * gdk_pixbuf_get_n_channels (pixbuf));
513 gtk_list_store_append (GTK_LIST_STORE (model), &iter);
514 gtk_list_store_set (GTK_LIST_STORE (model), &iter,
515 0, lightdm_user_get_name (user),
516 1, lightdm_user_get_display_name (user),
517 2, lightdm_user_get_logged_in (user) ? PANGO_WEIGHT_BOLD : PANGO_WEIGHT_NORMAL,
521 if (lightdm_greeter_get_select_user_hint (greeter) &&
522 strcmp (lightdm_greeter_get_select_user_hint (greeter), lightdm_user_get_name (user)) == 0)
523 gtk_tree_selection_select_iter (gtk_tree_view_get_selection (user_view), &iter);
525 if (lightdm_greeter_get_has_guest_account_hint (greeter))
527 gtk_list_store_append (GTK_LIST_STORE (model), &iter);
528 gtk_list_store_set (GTK_LIST_STORE (model), &iter,
531 2, PANGO_WEIGHT_NORMAL,
532 3, gtk_icon_theme_load_icon (gtk_icon_theme_get_default (), "stock_person", 64, 0, NULL),
534 if (lightdm_greeter_get_select_guest_hint (greeter))
535 gtk_tree_selection_select_iter (gtk_tree_view_get_selection (user_view), &iter);
538 gtk_list_store_append (GTK_LIST_STORE (model), &iter);
539 gtk_list_store_set (GTK_LIST_STORE (model), &iter,
542 2, PANGO_WEIGHT_NORMAL,
543 3, gtk_icon_theme_load_icon (gtk_icon_theme_get_default (), "stock_person", 64, 0, NULL),
547 static cairo_surface_t *
548 create_root_surface (GdkScreen *screen)
550 gint number, width, height;
553 cairo_surface_t *surface;
555 number = gdk_screen_get_number (screen);
556 width = gdk_screen_get_width (screen);
557 height = gdk_screen_get_height (screen);
559 /* Open a new connection so with Retain Permanent so the pixmap remains when the greeter quits */
561 display = XOpenDisplay (gdk_display_get_name (gdk_screen_get_display (screen)));
564 g_warning ("Failed to create root pixmap");
567 XSetCloseDownMode (display, RetainPermanent);
568 pixmap = XCreatePixmap (display, RootWindow (display, number), width, height, DefaultDepth (display, number));
569 XCloseDisplay (display);
571 /* Convert into a Cairo surface */
572 surface = cairo_xlib_surface_create (GDK_SCREEN_XDISPLAY (screen),
574 GDK_VISUAL_XVISUAL (gdk_screen_get_system_visual (screen)),
577 /* Use this pixmap for the background */
578 XSetWindowBackgroundPixmap (GDK_SCREEN_XDISPLAY (screen),
579 RootWindow (GDK_SCREEN_XDISPLAY (screen), number),
580 cairo_xlib_surface_get_drawable (surface));
587 main(int argc, char **argv)
590 GdkRectangle monitor_geometry;
593 const GList *items, *item;
595 GtkCellRenderer *renderer;
597 GdkPixbuf *background_pixbuf = NULL;
598 GdkColor background_color;
600 GError *error = NULL;
602 /* Disable global menus */
603 g_unsetenv ("UBUNTU_MENUPROXY");
605 signal (SIGTERM, sigterm_cb);
607 config = g_key_file_new ();
608 if (!g_key_file_load_from_file (config, CONFIG_FILE, G_KEY_FILE_NONE, &error) &&
609 !g_error_matches (error, G_FILE_ERROR, G_FILE_ERROR_NOENT))
610 g_warning ("Failed to load configuration from %s: %s\n", CONFIG_FILE, error->message);
611 g_clear_error (&error);
613 gtk_init (&argc, &argv);
615 greeter = lightdm_greeter_new ();
616 g_signal_connect (greeter, "show-prompt", G_CALLBACK (show_prompt_cb), NULL);
617 g_signal_connect (greeter, "show-message", G_CALLBACK (show_message_cb), NULL);
618 g_signal_connect (greeter, "authentication-complete", G_CALLBACK (authentication_complete_cb), NULL);
619 g_signal_connect (greeter, "autologin-timer-expired", G_CALLBACK (autologin_timer_expired_cb), NULL);
620 if (!lightdm_greeter_connect_sync (greeter, NULL))
623 /* Set default cursor */
624 gdk_window_set_cursor (gdk_get_default_root_window (), gdk_cursor_new (GDK_LEFT_PTR));
626 /* Load background */
627 value = g_key_file_get_value (config, "greeter", "background", NULL);
629 value = g_strdup ("#000000");
630 if (!gdk_color_parse (value, &background_color))
633 GError *error = NULL;
635 if (g_path_is_absolute (value))
636 path = g_strdup (value);
638 path = g_build_filename (GREETER_DATA_DIR, value, NULL);
640 g_debug ("Loading background %s", path);
641 background_pixbuf = gdk_pixbuf_new_from_file (path, &error);
642 if (!background_pixbuf)
643 g_warning ("Failed to load background: %s", error->message);
644 g_clear_error (&error);
648 g_debug ("Using background color %s", value);
651 /* Set the background */
652 for (i = 0; i < gdk_display_get_n_screens (gdk_display_get_default ()); i++)
655 cairo_surface_t *surface;
659 screen = gdk_display_get_screen (gdk_display_get_default (), i);
660 surface = create_root_surface (screen);
661 c = cairo_create (surface);
663 for (monitor = 0; monitor < gdk_screen_get_n_monitors (screen); monitor++)
665 gdk_screen_get_monitor_geometry (screen, monitor, &monitor_geometry);
667 if (background_pixbuf)
669 GdkPixbuf *pixbuf = gdk_pixbuf_scale_simple (background_pixbuf, monitor_geometry.width, monitor_geometry.height, GDK_INTERP_BILINEAR);
670 gdk_cairo_set_source_pixbuf (c, pixbuf, monitor_geometry.x, monitor_geometry.y);
671 g_object_unref (pixbuf);
674 gdk_cairo_set_source_color (c, &background_color);
680 /* Refresh background */
682 XClearWindow (GDK_SCREEN_XDISPLAY (screen), RootWindow (GDK_SCREEN_XDISPLAY (screen), i));
684 if (background_pixbuf)
685 g_object_unref (background_pixbuf);
687 /* Set GTK+ settings */
688 value = g_key_file_get_value (config, "greeter", "theme-name", NULL);
691 g_debug ("Using theme %s", value);
692 g_object_set (gtk_settings_get_default (), "gtk-theme-name", value, NULL);
695 g_object_get (gtk_settings_get_default (), "gtk-theme-name", &default_theme_name, NULL);
696 g_debug ("Default theme is '%s'", default_theme_name);
698 value = g_key_file_get_value (config, "greeter", "font-name", NULL);
701 g_debug ("Using font %s", value);
702 g_object_set (gtk_settings_get_default (), "gtk-font-name", value, NULL);
704 g_object_get (gtk_settings_get_default (), "gtk-font-name", &default_font_name, NULL);
705 value = g_key_file_get_value (config, "greeter", "xft-dpi", NULL);
707 g_object_set (gtk_settings_get_default (), "gtk-xft-dpi", (int) (1024 * atof (value)), NULL);
708 value = g_key_file_get_value (config, "greeter", "xft-antialias", NULL);
710 g_object_set (gtk_settings_get_default (), "gtk-xft-antialias", strcmp (value, "true") == 0, NULL);
712 value = g_key_file_get_value (config, "greeter", "xft-hintstyle", NULL);
714 g_object_set (gtk_settings_get_default (), "gtk-xft-hintstyle", value, NULL);
716 value = g_key_file_get_value (config, "greeter", "xft-rgba", NULL);
718 g_object_set (gtk_settings_get_default (), "gtk-xft-rgba", value, NULL);
721 /* Load out installed icons */
722 gtk_icon_theme_append_search_path (gtk_icon_theme_get_default (), GREETER_DATA_DIR);
724 gtk_icon_theme_get_search_path (gtk_icon_theme_get_default (), &path, NULL);
726 builder = gtk_builder_new ();
727 if (!gtk_builder_add_from_file (builder, GREETER_DATA_DIR "/greeter.ui", &error))
729 g_warning ("Error loading UI: %s", error->message);
732 g_clear_error (&error);
734 login_window = GTK_WINDOW (gtk_builder_get_object (builder, "login_window"));
735 login_box = GTK_WIDGET (gtk_builder_get_object (builder, "login_box"));
736 prompt_box = GTK_WIDGET (gtk_builder_get_object (builder, "prompt_box"));
737 prompt_label = GTK_LABEL (gtk_builder_get_object (builder, "prompt_label"));
738 prompt_entry = GTK_ENTRY (gtk_builder_get_object (builder, "prompt_entry"));
739 message_label = GTK_LABEL (gtk_builder_get_object (builder, "message_label"));
740 session_combo = GTK_COMBO_BOX (gtk_builder_get_object (builder, "session_combobox"));
741 panel_window = GTK_WINDOW (gtk_builder_get_object (builder, "panel_window"));
743 gtk_label_set_text (GTK_LABEL (gtk_builder_get_object (builder, "hostname_label")), lightdm_get_hostname ());
745 if (!lightdm_get_can_suspend ())
746 gtk_widget_hide (GTK_WIDGET (gtk_builder_get_object (builder, "suspend_menuitem")));
747 if (!lightdm_get_can_hibernate ())
748 gtk_widget_hide (GTK_WIDGET (gtk_builder_get_object (builder, "hibernate_menuitem")));
749 if (!lightdm_get_can_restart ())
750 gtk_widget_hide (GTK_WIDGET (gtk_builder_get_object (builder, "restart_menuitem")));
751 if (!lightdm_get_can_shutdown ())
752 gtk_widget_hide (GTK_WIDGET (gtk_builder_get_object (builder, "shutdown_menuitem")));
754 user_view = GTK_TREE_VIEW (gtk_builder_get_object (builder, "user_treeview"));
755 gtk_tree_view_insert_column_with_attributes (user_view, 0, "Face", gtk_cell_renderer_pixbuf_new(), "pixbuf", 3, NULL);
756 gtk_tree_view_insert_column_with_attributes (user_view, 1, "Name", gtk_cell_renderer_text_new(), "text", 1, "weight", 2, NULL);
758 if (lightdm_greeter_get_hide_users_hint (greeter))
759 start_authentication (NULL);
763 gtk_widget_show (GTK_WIDGET (user_view));
766 renderer = gtk_cell_renderer_text_new();
767 gtk_cell_layout_pack_start (GTK_CELL_LAYOUT (session_combo), renderer, TRUE);
768 gtk_cell_layout_add_attribute (GTK_CELL_LAYOUT (session_combo), renderer, "text", 0);
769 model = gtk_combo_box_get_model (session_combo);
770 items = lightdm_get_sessions ();
771 for (item = items; item; item = item->next)
773 LightDMSession *session = item->data;
775 gtk_widget_show (GTK_WIDGET (session_combo));
776 gtk_list_store_append (GTK_LIST_STORE (model), &iter);
777 gtk_list_store_set (GTK_LIST_STORE (model), &iter,
778 0, lightdm_session_get_name (session),
779 1, lightdm_session_get_key (session),
784 gtk_builder_connect_signals(builder, greeter);
786 gtk_widget_show (GTK_WIDGET (login_window));
787 center_window (login_window);
789 gtk_widget_show (GTK_WIDGET (panel_window));
790 GtkAllocation allocation;
791 gtk_widget_get_allocation (GTK_WIDGET (panel_window), &allocation);
792 gdk_screen_get_monitor_geometry (gdk_screen_get_default (), gdk_screen_get_primary_monitor (gdk_screen_get_default ()), &monitor_geometry);
793 gtk_window_resize (panel_window, monitor_geometry.width, allocation.height);
794 gtk_window_move (panel_window, monitor_geometry.x, monitor_geometry.y);
796 gtk_window_present (login_window);