[gnome-panel/wip/muktupavels/lock-screen-applet: 1/3] action-button: add lock screen applet



commit c8c8ca19f93ab7b4c7c47d783c4fdc0660111235
Author: Alberts Muktupāvels <alberts muktupavels gmail com>
Date:   Thu Apr 16 17:35:39 2020 +0300

    action-button: add lock screen applet

 configure.ac                                      |   1 +
 modules/action-button/Makefile.am                 |  46 +++
 modules/action-button/action-button.gresource.xml |   6 +
 modules/action-button/gp-action-button-module.c   |  53 +++
 modules/action-button/gp-lock-screen-applet.c     | 441 ++++++++++++++++++++++
 modules/action-button/gp-lock-screen-applet.h     |  34 ++
 modules/action-button/gp-lock-screen-menu.ui      |  18 +
 modules/action-button/org.gnome.ScreenSaver.xml   |  14 +
 modules/menu/org.gnome.ScreenSaver.xml            |   4 +
 po/POTFILES.in                                    |   2 +
 10 files changed, 619 insertions(+)
---
diff --git a/configure.ac b/configure.ac
index 204c09c78..e90e99848 100644
--- a/configure.ac
+++ b/configure.ac
@@ -153,6 +153,7 @@ PKG_CHECK_MODULES([LIBGNOME_PANEL], [
 PKG_CHECK_MODULES([ACTION_BUTTON], [
   gio-unix-2.0 >= $GLIB_REQUIRED
   gtk+-3.0 >= $GTK_REQUIRED
+  libsystemd >= $LIBSYSTEMD_REQUIRED
 ])
 
 PKG_CHECK_MODULES(FISH, gtk+-3.0 >= $GTK_REQUIRED cairo >= $CAIRO_REQUIRED)
diff --git a/modules/action-button/Makefile.am b/modules/action-button/Makefile.am
index 06409d3fc..873ad4f14 100644
--- a/modules/action-button/Makefile.am
+++ b/modules/action-button/Makefile.am
@@ -24,6 +24,9 @@ org_gnome_gnome_panel_action_button_la_SOURCES = \
        gp-action-button.c \
        gp-action-button.h \
        gp-action-button-module.c \
+       gp-lock-screen-applet.c \
+       gp-lock-screen-applet.h \
+       $(BUILT_SOURCES) \
        $(NULL)
 
 org_gnome_gnome_panel_action_button_la_LIBADD = \
@@ -38,4 +41,47 @@ org_gnome_gnome_panel_action_button_la_LDFLAGS = \
        $(AM_LDFLAGS) \
        $(NULL)
 
+ui_FILES = \
+       gp-lock-screen-menu.ui \
+       $(NULL)
+
+action_button_resources = \
+       $(shell $(GLIB_COMPILE_RESOURCES) \
+               --sourcedir=$(srcdir) \
+               --generate-dependencies \
+               $(srcdir)/action-button.gresource.xml)
+
+action-button-resources.c: action-button.gresource.xml $(action_button_resources)
+       $(AM_V_GEN) $(GLIB_COMPILE_RESOURCES) \
+               --target=$@ --sourcedir=$(srcdir) \
+               --generate --c-name action_button $<
+
+action-button-resources.h: action-button.gresource.xml
+       $(AM_V_GEN) $(GLIB_COMPILE_RESOURCES) \
+               --target=$@ --sourcedir=$(srcdir) \
+               --generate --c-name action_button $<
+
+gpab-screensaver-gen.h:
+gpab-screensaver-gen.c: org.gnome.ScreenSaver.xml
+       $(AM_V_GEN) $(GDBUS_CODEGEN) --c-namespace Gpab \
+               --generate-c-code gpab-screensaver-gen \
+               $(srcdir)/org.gnome.ScreenSaver.xml
+
+BUILT_SOURCES = \
+       action-button-resources.c \
+       action-button-resources.h \
+       gpab-screensaver-gen.c \
+       gpab-screensaver-gen.h \
+       $(NULL)
+
+EXTRA_DIST = \
+       action-button.gresource.xml \
+       org.gnome.ScreenSaver.xml \
+       $(ui_FILES) \
+       $(NULL)
+
+CLEANFILES = \
+       $(BUILT_SOURCES) \
+       $(NULL)
+
 -include $(top_srcdir)/git.mk
diff --git a/modules/action-button/action-button.gresource.xml 
b/modules/action-button/action-button.gresource.xml
new file mode 100644
index 000000000..94539db53
--- /dev/null
+++ b/modules/action-button/action-button.gresource.xml
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<gresources>
+  <gresource prefix="/org/gnome/gnome-panel/modules/action-button">
+    <file compressed="true">gp-lock-screen-menu.ui</file>
+  </gresource>
+</gresources>
diff --git a/modules/action-button/gp-action-button-module.c b/modules/action-button/gp-action-button-module.c
index c44dc2dad..377f4b7de 100644
--- a/modules/action-button/gp-action-button-module.c
+++ b/modules/action-button/gp-action-button-module.c
@@ -20,6 +20,52 @@
 #include <glib/gi18n-lib.h>
 #include <libgnome-panel/gp-module.h>
 
+#include "gp-lock-screen-applet.h"
+
+static GpAppletInfo *
+action_button_get_applet_info (const char *id)
+{
+  GpGetAppletTypeFunc type_func;
+  const char *name;
+  const char *description;
+  const char *icon;
+  GpIsDisabledFunc is_disabled_func;
+  GpAppletInfo *info;
+
+  is_disabled_func = NULL;
+
+  if (g_strcmp0 (id, "lock-screen") == 0)
+    {
+      type_func = gp_lock_screen_applet_get_type;
+      name = _("Lock Screen");
+      description = _("Protect your computer from unauthorized use");
+      icon = "system-lock-screen";
+
+      is_disabled_func = gp_lock_screen_applet_is_disabled;
+    }
+  else
+    {
+      g_assert_not_reached ();
+      return NULL;
+    }
+
+  info = gp_applet_info_new (type_func, name, description, icon);
+
+  if (is_disabled_func != NULL)
+    gp_applet_info_set_is_disabled (info, is_disabled_func);
+
+  return info;
+}
+
+static const char *
+action_button_get_applet_id_from_iid (const char *iid)
+{
+  if (g_strcmp0 (iid, "PanelInternalFactory::ActionButton:lock") == 0)
+    return "lock-screen";
+
+  return NULL;
+}
+
 void
 gp_module_load (GpModule *module)
 {
@@ -31,4 +77,11 @@ gp_module_load (GpModule *module)
 
   gp_module_set_id (module, "org.gnome.gnome-panel.action-button");
   gp_module_set_version (module, PACKAGE_VERSION);
+
+  gp_module_set_applet_ids (module,
+                            "lock-screen",
+                            NULL);
+
+  gp_module_set_get_applet_info (module, action_button_get_applet_info);
+  gp_module_set_compatibility (module, action_button_get_applet_id_from_iid);
 }
diff --git a/modules/action-button/gp-lock-screen-applet.c b/modules/action-button/gp-lock-screen-applet.c
new file mode 100644
index 000000000..fa20bb706
--- /dev/null
+++ b/modules/action-button/gp-lock-screen-applet.c
@@ -0,0 +1,441 @@
+/*
+ * Copyright (C) 2020 Alberts Muktupāvels
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "config.h"
+#include "gp-lock-screen-applet.h"
+
+#include <gio/gdesktopappinfo.h>
+#include <glib/gi18n-lib.h>
+#include <systemd/sd-journal.h>
+
+#include "gpab-screensaver-gen.h"
+
+struct _GpLockScreenApplet
+{
+  GpActionButtonApplet  parent;
+
+  GDesktopAppInfo      *lock_panel;
+
+  GpabScreensaverGen   *screensaver;
+};
+
+G_DEFINE_TYPE (GpLockScreenApplet,
+               gp_lock_screen_applet,
+               GP_TYPE_ACTION_BUTTON_APPLET)
+
+static void
+error_response_cb (GtkWidget *widget,
+                   int        response_id,
+                   gpointer   user_data)
+{
+  gtk_widget_destroy (widget);
+}
+
+static void
+show_error_message (GtkWindow  *parent,
+                    const char *primary_text,
+                    const char *secondary_text)
+{
+  GtkWidget *dialog;
+
+  dialog = gtk_message_dialog_new (parent,
+                                   GTK_DIALOG_DESTROY_WITH_PARENT,
+                                   GTK_MESSAGE_ERROR,
+                                   GTK_BUTTONS_CLOSE,
+                                   "%s",
+                                   primary_text);
+
+  gtk_message_dialog_format_secondary_text (GTK_MESSAGE_DIALOG (dialog),
+                                            "%s",
+                                            secondary_text);
+
+  g_signal_connect (dialog, "response", G_CALLBACK (error_response_cb), NULL);
+
+  gtk_window_present (GTK_WINDOW (dialog));
+}
+
+
+static void
+lockdown_changed (GpLockScreenApplet *self)
+{
+  GpLockdownFlags lockdowns;
+  gboolean applet_sensitive;
+  gboolean properties_enabled;
+  GAction *action;
+
+  lockdowns = gp_applet_get_lockdowns (GP_APPLET (self));
+
+  applet_sensitive = TRUE;
+
+  if ((lockdowns & GP_LOCKDOWN_FLAGS_APPLET) == GP_LOCKDOWN_FLAGS_APPLET ||
+      (lockdowns & GP_LOCKDOWN_FLAGS_LOCK_SCREEN) == GP_LOCKDOWN_FLAGS_LOCK_SCREEN)
+    applet_sensitive = FALSE;
+
+  gtk_widget_set_sensitive (GTK_WIDGET (self), applet_sensitive);
+
+  action = gp_applet_menu_lookup_action (GP_APPLET (self), "lock-screen");
+  g_simple_action_set_enabled (G_SIMPLE_ACTION (action), applet_sensitive);
+
+  properties_enabled = (lockdowns & GP_LOCKDOWN_FLAGS_LOCKED_DOWN) != GP_LOCKDOWN_FLAGS_LOCKED_DOWN &&
+                       (lockdowns & GP_LOCKDOWN_FLAGS_LOCK_SCREEN) != GP_LOCKDOWN_FLAGS_LOCK_SCREEN &&
+                       self->lock_panel != NULL;
+
+  action = gp_applet_menu_lookup_action (GP_APPLET (self), "properties");
+  g_simple_action_set_enabled (G_SIMPLE_ACTION (action), properties_enabled);
+}
+
+static void
+lockdowns_cb (GpApplet           *applet,
+              GParamSpec         *pspec,
+              GpLockScreenApplet *self)
+{
+  lockdown_changed (self);
+}
+
+static void
+lock_cb (GObject      *source,
+         GAsyncResult *res,
+         gpointer      user_data)
+{
+  GError *error;
+
+  error = NULL;
+  gpab_screensaver_gen_call_lock_finish (GPAB_SCREENSAVER_GEN (source),
+                                         res,
+                                         &error);
+
+  if (g_error_matches (error, G_IO_ERROR, G_IO_ERROR_CANCELLED))
+    {
+      g_error_free (error);
+      return;
+    }
+
+  if (error)
+    {
+      g_warning ("Could not ask screensaver to lock: %s",
+                 error->message);
+
+      g_error_free (error);
+      return;
+    }
+}
+
+static void
+lock_screen (GpLockScreenApplet *self)
+{
+  if (!self->screensaver)
+    {
+      g_warning ("Screensaver service not available.");
+      return;
+    }
+
+  gpab_screensaver_gen_call_lock (self->screensaver,
+                                  NULL,
+                                  lock_cb,
+                                  self);
+}
+
+static void
+lock_screen_cb (GSimpleAction *action,
+                GVariant      *parameter,
+                gpointer       user_data)
+{
+  lock_screen (GP_LOCK_SCREEN_APPLET (user_data));
+}
+
+static void
+set_active_cb (GObject      *source,
+               GAsyncResult *res,
+               gpointer      user_data)
+{
+  GError *error;
+
+  error = NULL;
+  gpab_screensaver_gen_call_set_active_finish (GPAB_SCREENSAVER_GEN (source),
+                                               res,
+                                               &error);
+
+  if (g_error_matches (error, G_IO_ERROR, G_IO_ERROR_CANCELLED))
+    {
+      g_error_free (error);
+      return;
+    }
+
+  if (error)
+    {
+      g_warning ("Could not ask screensaver to activate: %s",
+                 error->message);
+
+      g_error_free (error);
+      return;
+    }
+}
+
+static void
+screensaver_cb (GSimpleAction *action,
+                GVariant      *parameter,
+                gpointer       user_data)
+{
+  GpLockScreenApplet *self;
+
+  self = GP_LOCK_SCREEN_APPLET (user_data);
+
+  if (!self->screensaver)
+    {
+      g_warning ("Screensaver service not available.");
+      return;
+    }
+
+  gpab_screensaver_gen_call_set_active (self->screensaver,
+                                        TRUE,
+                                        NULL,
+                                        set_active_cb,
+                                        self);
+}
+
+static void
+child_setup (gpointer user_data)
+{
+  GAppInfo *info;
+  const gchar *id;
+  gint stdout_fd;
+  gint stderr_fd;
+
+  info = G_APP_INFO (user_data);
+  id = g_app_info_get_id (info);
+
+  stdout_fd = sd_journal_stream_fd (id, LOG_INFO, FALSE);
+  if (stdout_fd >= 0)
+    {
+      dup2 (stdout_fd, STDOUT_FILENO);
+      close (stdout_fd);
+    }
+
+  stderr_fd = sd_journal_stream_fd (id, LOG_WARNING, FALSE);
+  if (stderr_fd >= 0)
+    {
+      dup2 (stderr_fd, STDERR_FILENO);
+      close (stderr_fd);
+    }
+}
+
+static void
+close_pid (GPid     pid,
+           gint     status,
+           gpointer user_data)
+{
+  g_spawn_close_pid (pid);
+}
+
+static void
+pid_cb (GDesktopAppInfo *info,
+        GPid             pid,
+        gpointer         user_data)
+{
+  g_child_watch_add (pid, close_pid, NULL);
+}
+
+static void
+properties_cb (GSimpleAction *action,
+               GVariant      *parameter,
+               gpointer       user_data)
+{
+  GpLockScreenApplet *self;
+  GSpawnFlags flags;
+  GError *error;
+
+  self = GP_LOCK_SCREEN_APPLET (user_data);
+
+  g_assert (self->lock_panel != NULL);
+
+  flags = G_SPAWN_SEARCH_PATH | G_SPAWN_DO_NOT_REAP_CHILD;
+
+  error = NULL;
+  g_desktop_app_info_launch_uris_as_manager (self->lock_panel,
+                                             NULL,
+                                             NULL,
+                                             flags,
+                                             child_setup,
+                                             self->lock_panel,
+                                             pid_cb,
+                                             NULL,
+                                             &error);
+
+  if (error != NULL)
+    {
+      show_error_message (NULL,
+                          _("Could not launch application"),
+                          error->message);
+
+      g_error_free (error);
+    }
+}
+
+static const GActionEntry lock_screen_menu_actions[] =
+{
+  { "lock-screen", lock_screen_cb, NULL, NULL, NULL },
+  { "screensaver", screensaver_cb, NULL, NULL, NULL },
+  { "properties", properties_cb, NULL, NULL, NULL },
+  { NULL }
+};
+
+static void
+setup_menu (GpLockScreenApplet *self)
+{
+  GpApplet *applet;
+  const char *resource;
+
+  applet = GP_APPLET (self);
+
+  resource = "/org/gnome/gnome-panel/modules/action-button/gp-lock-screen-menu.ui";
+  gp_applet_setup_menu_from_resource (applet, resource, lock_screen_menu_actions);
+
+  lockdown_changed (self);
+}
+
+static void
+setup_applet (GpLockScreenApplet *self)
+{
+  const char *text;
+  AtkObject *atk;
+
+  setup_menu (self);
+
+  gp_action_button_applet_set_icon_name (GP_ACTION_BUTTON_APPLET (self),
+                                         "system-lock-screen");
+
+  text = _("Protect your computer from unauthorized use");
+
+  atk = gtk_widget_get_accessible (GTK_WIDGET (self));
+  atk_object_set_name (atk, text);
+  atk_object_set_description (atk, text);
+
+  gtk_widget_set_tooltip_text (GTK_WIDGET (self), text);
+
+  g_object_bind_property (self,
+                          "enable-tooltips",
+                          self,
+                          "has-tooltip",
+                          G_BINDING_DEFAULT | G_BINDING_SYNC_CREATE);
+
+  lockdown_changed (self);
+}
+
+static void
+screensaver_proxy_ready_cb (GObject      *source_object,
+                            GAsyncResult *res,
+                            gpointer      user_data)
+{
+  GError *error;
+  GpabScreensaverGen *screensaver;
+  GpLockScreenApplet *self;
+
+  error = NULL;
+  screensaver = gpab_screensaver_gen_proxy_new_for_bus_finish (res, &error);
+
+  if (g_error_matches (error, G_IO_ERROR, G_IO_ERROR_CANCELLED))
+    {
+      g_error_free (error);
+      return;
+    }
+
+  self = GP_LOCK_SCREEN_APPLET (user_data);
+  self->screensaver = screensaver;
+
+  if (error)
+    {
+      g_warning ("%s", error->message);
+      g_error_free (error);
+
+      return;
+    }
+}
+
+static void
+gp_lock_screen_applet_constructed (GObject *object)
+{
+  G_OBJECT_CLASS (gp_lock_screen_applet_parent_class)->constructed (object);
+  setup_applet (GP_LOCK_SCREEN_APPLET (object));
+}
+
+static void
+gp_lock_screen_applet_dispose (GObject *object)
+{
+  GpLockScreenApplet *self;
+
+  self = GP_LOCK_SCREEN_APPLET (object);
+
+  g_clear_object (&self->lock_panel);
+  g_clear_object (&self->screensaver);
+
+  G_OBJECT_CLASS (gp_lock_screen_applet_parent_class)->dispose (object);
+}
+
+static void
+gp_lock_screen_applet_clicked (GpActionButtonApplet *applet)
+{
+  lock_screen (GP_LOCK_SCREEN_APPLET (applet));
+}
+
+static void
+gp_lock_screen_applet_class_init (GpLockScreenAppletClass *self_class)
+{
+  GObjectClass *object_class;
+  GpActionButtonAppletClass *action_button_applet_class;
+
+  object_class = G_OBJECT_CLASS (self_class);
+  action_button_applet_class = GP_ACTION_BUTTON_APPLET_CLASS (self_class);
+
+  object_class->constructed = gp_lock_screen_applet_constructed;
+  object_class->dispose = gp_lock_screen_applet_dispose;
+
+  action_button_applet_class->clicked = gp_lock_screen_applet_clicked;
+}
+
+static void
+gp_lock_screen_applet_init (GpLockScreenApplet *self)
+{
+  self->lock_panel = g_desktop_app_info_new ("gnome-lock-panel.desktop");
+
+  gpab_screensaver_gen_proxy_new_for_bus (G_BUS_TYPE_SESSION,
+                                          G_DBUS_PROXY_FLAGS_NONE,
+                                          "org.gnome.ScreenSaver",
+                                          "/org/gnome/ScreenSaver",
+                                          NULL,
+                                          screensaver_proxy_ready_cb,
+                                          self);
+
+  g_signal_connect (self,
+                    "notify::lockdowns",
+                    G_CALLBACK (lockdowns_cb),
+                    self);
+}
+
+gboolean
+gp_lock_screen_applet_is_disabled (GpLockdownFlags   flags,
+                                   char            **reason)
+{
+  if ((flags & GP_LOCKDOWN_FLAGS_LOCK_SCREEN) != GP_LOCKDOWN_FLAGS_LOCK_SCREEN)
+    return FALSE;
+
+  if (reason != NULL)
+    *reason = g_strdup (_("Disabled because “disable-lock-screen” setting in "
+                          "“org.gnome.desktop.lockdown” GSettings schema is "
+                          "set to true."));
+
+  return FALSE;
+}
diff --git a/modules/action-button/gp-lock-screen-applet.h b/modules/action-button/gp-lock-screen-applet.h
new file mode 100644
index 000000000..534b068a7
--- /dev/null
+++ b/modules/action-button/gp-lock-screen-applet.h
@@ -0,0 +1,34 @@
+/*
+ * Copyright (C) 2020 Alberts Muktupāvels
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef GP_LOCK_SCREEN_APPLET_H
+#define GP_LOCK_SCREEN_APPLET_H
+
+#include "gp-action-button-applet.h"
+
+G_BEGIN_DECLS
+
+#define GP_TYPE_LOCK_SCREEN_APPLET (gp_lock_screen_applet_get_type ())
+G_DECLARE_FINAL_TYPE (GpLockScreenApplet, gp_lock_screen_applet,
+                      GP, LOCK_SCREEN_APPLET, GpActionButtonApplet)
+
+gboolean gp_lock_screen_applet_is_disabled (GpLockdownFlags   flags,
+                                            char            **reason);
+
+G_END_DECLS
+
+#endif
diff --git a/modules/action-button/gp-lock-screen-menu.ui b/modules/action-button/gp-lock-screen-menu.ui
new file mode 100644
index 000000000..da20c0e9c
--- /dev/null
+++ b/modules/action-button/gp-lock-screen-menu.ui
@@ -0,0 +1,18 @@
+<interface>
+  <menu id="lock-screen-menu">
+    <section>
+      <item>
+        <attribute name="label" translatable="yes">_Lock Screen</attribute>
+        <attribute name="action">lock-screen.lock-screen</attribute>
+      </item>
+      <item>
+        <attribute name="label" translatable="yes">_Activate Screensaver</attribute>
+        <attribute name="action">lock-screen.screensaver</attribute>
+      </item>
+      <item>
+        <attribute name="label" translatable="yes">_Properties</attribute>
+        <attribute name="action">lock-screen.properties</attribute>
+      </item>
+    </section>
+  </menu>
+</interface>
diff --git a/modules/action-button/org.gnome.ScreenSaver.xml b/modules/action-button/org.gnome.ScreenSaver.xml
new file mode 100644
index 000000000..bdac16c2e
--- /dev/null
+++ b/modules/action-button/org.gnome.ScreenSaver.xml
@@ -0,0 +1,14 @@
+<?xml version="1.0" encoding="UTF-8" ?>
+<!DOCTYPE node PUBLIC "-//freedesktop//DTD D-BUS Object Introspection 1.0//EN"
+"http://www.freedesktop.org/standards/dbus/1.0/introspect.dtd";>
+<node>
+  <interface name="org.gnome.ScreenSaver">
+    <annotation name="org.gtk.GDBus.C.Name" value="ScreensaverGen" />
+
+    <method name="Lock" />
+
+    <method name="SetActive">
+      <arg name="value" direction="in" type="b" />
+    </method>
+  </interface>
+</node>
diff --git a/modules/menu/org.gnome.ScreenSaver.xml b/modules/menu/org.gnome.ScreenSaver.xml
index c5b0594af..bdac16c2e 100644
--- a/modules/menu/org.gnome.ScreenSaver.xml
+++ b/modules/menu/org.gnome.ScreenSaver.xml
@@ -6,5 +6,9 @@
     <annotation name="org.gtk.GDBus.C.Name" value="ScreensaverGen" />
 
     <method name="Lock" />
+
+    <method name="SetActive">
+      <arg name="value" direction="in" type="b" />
+    </method>
   </interface>
 </node>
diff --git a/po/POTFILES.in b/po/POTFILES.in
index 68573d77d..c1552ff18 100644
--- a/po/POTFILES.in
+++ b/po/POTFILES.in
@@ -34,6 +34,8 @@ gnome-panel/panel-util.c
 libgnome-panel/gp-initial-setup-dialog.c
 libgnome-panel/gp-module.c
 modules/action-button/gp-action-button-module.c
+modules/action-button/gp-lock-screen-applet.c
+modules/action-button/gp-lock-screen-menu.ui
 modules/clock/calendar-client.c
 modules/clock/calendar-window.c
 modules/clock/clock-applet.c


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]