refactor: move shell lock feature to base Shell class
This commit is contained in:
@@ -33,7 +33,7 @@ lua = dependency('lua')
|
||||
# pkg_config = import('pkgconfig')
|
||||
# gnome = import('gnome')
|
||||
|
||||
gtk_layer_shell = dependency('gtk4-layer-shell-0', version: '>=1.1.0')
|
||||
gtk_layer_shell = dependency('gtk4-layer-shell-0', version: '>=1.3.0')
|
||||
wayland_targets=[]
|
||||
|
||||
wl_protocols = [
|
||||
|
||||
@@ -1,20 +1,22 @@
|
||||
@import url("resource:///dev/iohub/diya/shell/css/virtual-keyboard.css");
|
||||
|
||||
#diya_login_shell
|
||||
.diya-login-shell
|
||||
{
|
||||
background-color: white;
|
||||
opacity: 0.9;
|
||||
}
|
||||
|
||||
#diya_login_shell label.diya-login-header {
|
||||
.diya-login-shell label.diya-login-header {
|
||||
font-size: 16px;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
#diya_login_shell label.diya-login-status {
|
||||
.diya-login-shell label.diya-login-status {
|
||||
font-size: 12px;
|
||||
color: red;
|
||||
}
|
||||
|
||||
#diya_login_shell button.diya-btn-show-vkb
|
||||
.diya-login-shell button.diya-btn-show-vkb
|
||||
{
|
||||
color: gray;
|
||||
min-width: 0px;
|
||||
|
||||
@@ -8,19 +8,18 @@
|
||||
#define DBUS_SERVER_NAME "dev.iohub.diya.SessionManager"
|
||||
#define DBUS_SERVER_PATH "/dev/iohub/diya/SessionManager"
|
||||
#define DBUS_SERVER_ERROR_NAME "dev.iohub.diya.SessionManager.Error"
|
||||
#define NAMESPACE "diya_login_shell"
|
||||
#define NAMESPACE "diya-login-shell"
|
||||
|
||||
struct _DiyaLoginShell
|
||||
{
|
||||
DiyaShell parent_object;
|
||||
GtkSessionLockInstance *lock;
|
||||
GtkWidget *username;
|
||||
GtkWidget *password;
|
||||
GtkWidget *status;
|
||||
guint bus_watch_id;
|
||||
GtkWidget *vkb_widget;
|
||||
GtkWidget *revealer;
|
||||
GList *windows;
|
||||
|
||||
};
|
||||
|
||||
G_DEFINE_FINAL_TYPE(DiyaLoginShell, diya_login_shell, DIYA_TYPE_SHELL);
|
||||
@@ -29,10 +28,6 @@ static void diya_login_shell_finalize(GObject *object)
|
||||
{
|
||||
DiyaLoginShell *self = DIYA_LOGIN_SHELL(object);
|
||||
g_debug("diya_login_shell_finalize: %s", diya_object_to_string(self));
|
||||
if (self->windows)
|
||||
{
|
||||
g_list_free(self->windows);
|
||||
}
|
||||
G_OBJECT_CLASS(diya_login_shell_parent_class)->finalize(object);
|
||||
}
|
||||
|
||||
@@ -40,27 +35,6 @@ static void diya_login_shell_dispose(GObject *object)
|
||||
{
|
||||
DiyaLoginShell *self = DIYA_LOGIN_SHELL(object);
|
||||
g_debug("diya_login_shell_dispose: %s", diya_object_to_string(self));
|
||||
if (self->lock)
|
||||
{
|
||||
if (gtk_session_lock_instance_is_locked(self->lock))
|
||||
{
|
||||
gtk_session_lock_instance_unlock(self->lock);
|
||||
}
|
||||
g_object_unref(self->lock);
|
||||
}
|
||||
if (self->windows)
|
||||
{
|
||||
// destroyed all windows and free list
|
||||
GList *it = NULL;
|
||||
for (it = self->windows; it; it = it->next)
|
||||
{
|
||||
if (it->data)
|
||||
{
|
||||
gtk_window_destroy(GTK_WINDOW(it->data));
|
||||
}
|
||||
}
|
||||
// g_list_free(self->windows);
|
||||
}
|
||||
if (self->bus_watch_id > 0)
|
||||
{
|
||||
g_bus_unwatch_name(self->bus_watch_id);
|
||||
@@ -71,11 +45,9 @@ static void diya_login_shell_dispose(GObject *object)
|
||||
static void diya_login_shell_init(DiyaLoginShell *self)
|
||||
{
|
||||
g_debug("diya_login_shell_init");
|
||||
self->lock = gtk_session_lock_instance_new();
|
||||
self->username = NULL;
|
||||
self->password = NULL;
|
||||
self->status = NULL;
|
||||
self->windows = NULL;
|
||||
self->bus_watch_id = 0;
|
||||
}
|
||||
|
||||
@@ -178,14 +150,44 @@ static void do_login(GtkButton *button, DiyaLoginShell *self)
|
||||
// g_application_quit(G_APPLICATION(self->app));
|
||||
}
|
||||
|
||||
static void add_new_monitor(DiyaLoginShell *self, GdkMonitor *monitor, gint position)
|
||||
|
||||
static void diya_login_on_shell_idle(DiyaShell* shell)
|
||||
{
|
||||
GtkWindow *window = GTK_WINDOW(gtk_application_window_new(diya_shell_get_application(DIYA_SHELL(self))));
|
||||
gtk_session_lock_instance_assign_window_to_monitor(self->lock, window, monitor);
|
||||
gtk_widget_set_name(GTK_WIDGET(window), NAMESPACE);
|
||||
(void) shell;
|
||||
g_debug("diya_login_on_shell_idle");
|
||||
diya_shell_power_display(shell, false);
|
||||
}
|
||||
|
||||
static void diya_login_on_shell_resume(DiyaShell* shell)
|
||||
{
|
||||
(void) shell;
|
||||
g_debug("diya_login_on_shell_resume");
|
||||
diya_shell_power_display(shell, true);
|
||||
}
|
||||
|
||||
static void diya_login_shell_active(DiyaShell *shell)
|
||||
{
|
||||
g_object_set(shell, DIYA_PROP_SHELL_IDLE_TIMEOUT, DEFAULT_IDLE_TIMEOUT, NULL);
|
||||
}
|
||||
|
||||
static void diya_login_shell_startup(DiyaShell *shell)
|
||||
{
|
||||
g_warning("diya_login_shell_startup");
|
||||
g_signal_connect(shell, DIYA_SIGNAL_SHELL_IDLE, G_CALLBACK(diya_login_on_shell_idle), NULL);
|
||||
g_signal_connect(shell, DIYA_SIGNAL_SHELL_RESUME, G_CALLBACK(diya_login_on_shell_resume), NULL);
|
||||
diya_shell_lock(shell);
|
||||
}
|
||||
|
||||
static GtkWindow* diya_login_shell_create_window(DiyaShell* shell)
|
||||
{
|
||||
DiyaLoginShell* self = DIYA_LOGIN_SHELL(shell);
|
||||
GtkApplication * app;
|
||||
g_object_get(shell, DIYA_PROP_SHELL_APPLICATION, &app, NULL);
|
||||
assert(app);
|
||||
GtkWindow *window = GTK_WINDOW(gtk_application_window_new(app));
|
||||
gtk_widget_add_css_class(GTK_WIDGET(window), NAMESPACE);
|
||||
|
||||
GtkWidget *grid = gtk_grid_new();
|
||||
gtk_window_set_child(window, grid);
|
||||
gtk_grid_set_row_homogeneous(GTK_GRID(grid), false);
|
||||
|
||||
GtkWidget *box = gtk_box_new(GTK_ORIENTATION_VERTICAL, 0);
|
||||
@@ -230,14 +232,14 @@ static void add_new_monitor(DiyaLoginShell *self, GdkMonitor *monitor, gint posi
|
||||
gtk_widget_set_can_focus(GTK_WIDGET(button), false);
|
||||
gtk_grid_attach(GTK_GRID(child_grid), button, 0, 0, 1, 1);
|
||||
// Not displayed, but allows testing that creating popups doesn't crash GTK
|
||||
gtk_widget_set_tooltip_text(button, "Login");
|
||||
//gtk_widget_set_tooltip_text(button, "Login");
|
||||
gtk_widget_set_hexpand(button, true);
|
||||
|
||||
button = gtk_toggle_button_new_with_label("⌨");
|
||||
gtk_widget_add_css_class(button, "diya-btn-show-vkb");
|
||||
gtk_grid_attach(GTK_GRID(child_grid), button, 1, 0, 1, 1);
|
||||
gtk_box_append(GTK_BOX(box), child_grid);
|
||||
gtk_widget_set_tooltip_text(button, "Show virtual keyboard");
|
||||
//gtk_widget_set_tooltip_text(button, "Show virtual keyboard");
|
||||
gtk_widget_set_can_focus(GTK_WIDGET(button), false);
|
||||
|
||||
self->status = gtk_label_new(NULL);
|
||||
@@ -265,73 +267,8 @@ static void add_new_monitor(DiyaLoginShell *self, GdkMonitor *monitor, gint posi
|
||||
gtk_widget_set_hexpand(box, true);
|
||||
gtk_widget_set_vexpand(box, false);
|
||||
|
||||
gtk_window_present(window);
|
||||
|
||||
self->windows = g_list_insert(self->windows, window, position);
|
||||
}
|
||||
|
||||
static void on_monitor_changed(GListModel *monitor_lists, guint position, guint removed, guint added, gpointer object)
|
||||
{
|
||||
g_debug("Monitor list changed at %d: added %d, removed %d", position, added, removed);
|
||||
DiyaLoginShell *self = DIYA_LOGIN_SHELL(object);
|
||||
if (removed > 0)
|
||||
{
|
||||
for (guint i = 0; i < removed; i++)
|
||||
{
|
||||
GtkWindow *win = GTK_WINDOW(g_list_nth(self->windows, position));
|
||||
if (win)
|
||||
{
|
||||
gtk_window_destroy(win);
|
||||
self->windows = g_list_remove(self->windows, win);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (added > 0)
|
||||
{
|
||||
for (guint i = 0; i < added; i++)
|
||||
{
|
||||
GdkMonitor *monitor = g_list_model_get_item(monitor_lists, position + i);
|
||||
add_new_monitor(self, monitor, position + i);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void diya_login_on_shell_idle(DiyaShell* shell)
|
||||
{
|
||||
(void) shell;
|
||||
g_debug("diya_login_on_shell_idle");
|
||||
diya_shell_power_display(shell, false);
|
||||
}
|
||||
|
||||
static void diya_login_on_shell_resume(DiyaShell* shell)
|
||||
{
|
||||
(void) shell;
|
||||
g_debug("diya_login_on_shell_resume");
|
||||
diya_shell_power_display(shell, true);
|
||||
}
|
||||
|
||||
static void diya_login_shell_active(DiyaShell *shell)
|
||||
{
|
||||
g_object_set(shell, DIYA_PROP_SHELL_IDLE_TIMEOUT, DEFAULT_IDLE_TIMEOUT, NULL);
|
||||
}
|
||||
|
||||
static void diya_login_shell_startup(DiyaShell *shell)
|
||||
{
|
||||
DiyaLoginShell *self = DIYA_LOGIN_SHELL(shell);
|
||||
if (!gtk_session_lock_instance_lock(self->lock))
|
||||
{
|
||||
g_object_unref(self);
|
||||
g_error("gtk_session_lock_instance_lock: Unable to lock the display");
|
||||
return;
|
||||
}
|
||||
GListModel *list = gdk_display_get_monitors(gdk_display_get_default());
|
||||
for (guint i = 0; i < g_list_model_get_n_items(list); i++)
|
||||
{
|
||||
GdkMonitor *monitor = g_list_model_get_item(list, i);
|
||||
add_new_monitor(self, monitor, -1);
|
||||
}
|
||||
g_signal_connect(shell, DIYA_SIGNAL_SHELL_IDLE, G_CALLBACK(diya_login_on_shell_idle), NULL);
|
||||
g_signal_connect(shell, DIYA_SIGNAL_SHELL_RESUME, G_CALLBACK(diya_login_on_shell_resume), NULL);
|
||||
gtk_window_set_child(window, grid);
|
||||
return window;
|
||||
}
|
||||
|
||||
static void diya_login_shell_class_init(DiyaLoginShellClass *class)
|
||||
@@ -343,7 +280,7 @@ static void diya_login_shell_class_init(DiyaLoginShellClass *class)
|
||||
// gobject_class->get_property = diya_lock_session_get_property;
|
||||
|
||||
DiyaShellClass *base_shell_class = DIYA_SHELL_CLASS(class);
|
||||
base_shell_class->monitor_changed_handle = on_monitor_changed;
|
||||
base_shell_class->build_lock_window = diya_login_shell_create_window;
|
||||
base_shell_class->startup_handle = diya_login_shell_startup;
|
||||
base_shell_class->active_handle = diya_login_shell_active;
|
||||
// base_shell_class->foreign_register = diya_session_shell_foreign_toplevel_register;
|
||||
|
||||
@@ -3,69 +3,38 @@
|
||||
#include <gtk/gtk.h>
|
||||
#include "session-lock.h"
|
||||
|
||||
static void unlock_session(GtkButton *button, DiyaSessionShell *shell)
|
||||
static void unlock_session(GtkButton *button, DiyaShell *shell)
|
||||
{
|
||||
(void)button;
|
||||
assert(shell);
|
||||
diya_session_shell_unlock(shell);
|
||||
diya_shell_unlock(shell);
|
||||
}
|
||||
|
||||
void diya_session_shell_lock(DiyaSessionShell* shell)
|
||||
GtkWindow* diya_session_lock_create(DiyaShell* shell)
|
||||
{
|
||||
assert(shell);
|
||||
GtkSessionLockInstance * lock;
|
||||
g_object_get(shell, DIYA_PROP_SESSION_LOCK, &lock, NULL);
|
||||
assert(lock);
|
||||
if(gtk_session_lock_instance_is_locked(lock))
|
||||
{
|
||||
g_warning("Shell session is already locked, doing nothing");
|
||||
return;
|
||||
}
|
||||
if(!gtk_session_lock_instance_lock(lock))
|
||||
{
|
||||
g_error("gtk_session_lock_instance_lock:Unable to lock the current session");
|
||||
return;
|
||||
}
|
||||
GtkApplication * app;
|
||||
g_object_get(shell, DIYA_PROP_SHELL_APPLICATION, &app, NULL);
|
||||
assert(app);
|
||||
|
||||
GdkDisplay *display = gdk_display_get_default();
|
||||
GListModel *monitors = gdk_display_get_monitors(display);
|
||||
guint n_monitors = g_list_model_get_n_items(monitors);
|
||||
GtkWindow *gtk_window = GTK_WINDOW(gtk_application_window_new(app));
|
||||
|
||||
for (guint i = 0; i < n_monitors; ++i)
|
||||
{
|
||||
GdkMonitor *monitor = g_list_model_get_item(monitors, i);
|
||||
GtkWidget *box = gtk_box_new(GTK_ORIENTATION_VERTICAL, 0);
|
||||
gtk_widget_set_halign(box, GTK_ALIGN_CENTER);
|
||||
gtk_widget_set_valign(box, GTK_ALIGN_CENTER);
|
||||
gtk_box_set_spacing(GTK_BOX (box), 10);
|
||||
|
||||
GtkWindow *gtk_window = GTK_WINDOW(gtk_application_window_new(app));
|
||||
gtk_session_lock_instance_assign_window_to_monitor(lock, gtk_window, monitor);
|
||||
GtkWidget *label = gtk_label_new("GTK Session Lock example");
|
||||
gtk_box_append(GTK_BOX(box), label);
|
||||
|
||||
GtkWidget *box = gtk_box_new(GTK_ORIENTATION_VERTICAL, 0);
|
||||
gtk_widget_set_halign(box, GTK_ALIGN_CENTER);
|
||||
gtk_widget_set_valign(box, GTK_ALIGN_CENTER);
|
||||
gtk_box_set_spacing(GTK_BOX (box), 10);
|
||||
GtkWidget *button = gtk_button_new_with_label("Unlock");
|
||||
g_signal_connect(button, "clicked", G_CALLBACK(unlock_session), shell);
|
||||
gtk_box_append(GTK_BOX(box), button);
|
||||
|
||||
GtkWidget *label = gtk_label_new("GTK Session Lock example");
|
||||
gtk_box_append(GTK_BOX(box), label);
|
||||
// Not displayed, but allows testing that creating popups doesn't crash GTK
|
||||
gtk_widget_set_tooltip_text(button, "Foo Bar Baz");
|
||||
|
||||
GtkWidget *button = gtk_button_new_with_label("Unlock");
|
||||
g_signal_connect(button, "clicked", G_CALLBACK(unlock_session), shell);
|
||||
gtk_box_append(GTK_BOX(box), button);
|
||||
gtk_window_set_child(GTK_WINDOW(gtk_window), box);
|
||||
|
||||
// Not displayed, but allows testing that creating popups doesn't crash GTK
|
||||
gtk_widget_set_tooltip_text(button, "Foo Bar Baz");
|
||||
|
||||
gtk_window_set_child(GTK_WINDOW(gtk_window), box);
|
||||
gtk_window_present(gtk_window);
|
||||
}
|
||||
}
|
||||
void diya_session_shell_unlock(DiyaSessionShell* shell)
|
||||
{
|
||||
assert(shell);
|
||||
GtkSessionLockInstance * lock;
|
||||
g_object_get(shell, DIYA_PROP_SESSION_LOCK, &lock, NULL);
|
||||
assert(lock);
|
||||
gtk_session_lock_instance_unlock(lock);
|
||||
g_debug("gtk_session_lock_instance_unlock: Shell unlocked");
|
||||
return gtk_window;
|
||||
}
|
||||
@@ -3,7 +3,6 @@
|
||||
|
||||
#include "session-shell.h"
|
||||
|
||||
void diya_session_shell_lock(DiyaSessionShell* shell);
|
||||
void diya_session_shell_unlock(DiyaSessionShell* shell);
|
||||
GtkWindow* diya_session_lock_create(DiyaShell* shell);
|
||||
|
||||
#endif
|
||||
@@ -1,7 +1,7 @@
|
||||
#include "session-shell.h"
|
||||
|
||||
#include <assert.h>
|
||||
#include <gtk4-session-lock.h>
|
||||
|
||||
#include <xkbcommon/xkbcommon.h>
|
||||
|
||||
#include "shell.h"
|
||||
@@ -17,7 +17,6 @@ enum
|
||||
{
|
||||
NO_PROP,
|
||||
SHELL_LAUNCHPAD_WIDGET,
|
||||
SHELL_LOCK_SESSION,
|
||||
SHELL_WINDOWS,
|
||||
N_PROPERTIES
|
||||
};
|
||||
@@ -29,7 +28,6 @@ struct _DiyaSessionShell
|
||||
DiyaShell parent;
|
||||
DiyaLauncher *launcher;
|
||||
GHashTable *windows;
|
||||
GtkSessionLockInstance *lock;
|
||||
GSettings *settings;
|
||||
};
|
||||
G_DEFINE_FINAL_TYPE(DiyaSessionShell, diya_session_shell, DIYA_TYPE_SHELL)
|
||||
@@ -47,10 +45,6 @@ static void diya_session_shell_dispose(GObject *object)
|
||||
DiyaSessionShell *self = DIYA_SESSION_SHELL(object);
|
||||
// g_hash_table_destroy(self->windows);
|
||||
g_debug("diya_session_shell_dispose: %s", diya_object_to_string(object));
|
||||
if (self->lock)
|
||||
{
|
||||
g_object_unref(self->lock);
|
||||
}
|
||||
if (self->launcher)
|
||||
{
|
||||
g_object_unref(self->launcher);
|
||||
@@ -88,10 +82,6 @@ static void diya_session_shell_get_property(GObject *object, guint property_id,
|
||||
assert(self->launcher);
|
||||
g_value_set_pointer(value, self->launcher);
|
||||
break;
|
||||
case SHELL_LOCK_SESSION:
|
||||
assert(self->lock);
|
||||
g_value_set_pointer(value, self->lock);
|
||||
break;
|
||||
case SHELL_WINDOWS:
|
||||
g_value_set_pointer(value, self->windows);
|
||||
break;
|
||||
@@ -180,7 +170,7 @@ void diya_session_init_settings(DiyaSessionShell* self)
|
||||
static void diya_session_shell_startup(DiyaShell *shell)
|
||||
{
|
||||
DiyaSessionShell* self = DIYA_SESSION_SHELL(shell);
|
||||
|
||||
|
||||
const gchar* const* dirs = g_get_system_config_dirs();
|
||||
|
||||
gchar* path = NULL;
|
||||
@@ -227,7 +217,7 @@ static void diya_session_shell_class_init(DiyaSessionShellClass *class)
|
||||
base_shell_class->foreign_register = diya_session_shell_foreign_toplevel_register;
|
||||
base_shell_class->startup_handle = diya_session_shell_startup;
|
||||
base_shell_class->active_handle = diya_session_shell_active;
|
||||
|
||||
base_shell_class->build_lock_window = diya_session_lock_create;
|
||||
/// base_class->to_string = diya_session_shell_to_string;
|
||||
gobject_class->dispose = diya_session_shell_dispose;
|
||||
gobject_class->finalize = diya_session_shell_finalize;
|
||||
@@ -235,7 +225,6 @@ static void diya_session_shell_class_init(DiyaSessionShellClass *class)
|
||||
gobject_class->get_property = diya_session_shell_get_property;
|
||||
|
||||
shell_properties[SHELL_LAUNCHPAD_WIDGET] = g_param_spec_pointer(DIYA_PROP_SESSION_LAUNCHPAD, NULL, "Shell launchpad", G_PARAM_READWRITE);
|
||||
shell_properties[SHELL_LOCK_SESSION] = g_param_spec_pointer(DIYA_PROP_SESSION_LOCK, NULL, "Shell lock session", G_PARAM_READABLE);
|
||||
shell_properties[SHELL_WINDOWS] = g_param_spec_pointer(DIYA_PROP_SESSION_WINDOWS, NULL, "Shell foreign windows", G_PARAM_READABLE);
|
||||
|
||||
g_object_class_install_properties(gobject_class, N_PROPERTIES, shell_properties);
|
||||
@@ -289,44 +278,6 @@ static void diya_session_shell_class_init(DiyaSessionShellClass *class)
|
||||
G_TYPE_NONE,
|
||||
1,
|
||||
G_TYPE_POINTER);
|
||||
g_signal_new(DIYA_SIGNAL_SESSION_LOCKED,
|
||||
DIYA_TYPE_SESSION_SHELL,
|
||||
G_SIGNAL_DETAILED |
|
||||
G_SIGNAL_ACTION |
|
||||
G_SIGNAL_RUN_FIRST,
|
||||
0,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
G_TYPE_NONE,
|
||||
0);
|
||||
g_signal_new(DIYA_SIGNAL_SESSION_UNLOCKED,
|
||||
DIYA_TYPE_SESSION_SHELL,
|
||||
G_SIGNAL_DETAILED |
|
||||
G_SIGNAL_ACTION |
|
||||
G_SIGNAL_RUN_FIRST,
|
||||
0,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
G_TYPE_NONE,
|
||||
0);
|
||||
}
|
||||
|
||||
static void on_session_locked(GtkSessionLockInstance *lock, DiyaSessionShell *shell)
|
||||
{
|
||||
(void)lock;
|
||||
assert(shell);
|
||||
g_message("Session locked successfully");
|
||||
g_signal_emit_by_name(shell, DIYA_SIGNAL_SESSION_LOCKED);
|
||||
}
|
||||
|
||||
static void on_session_unlocked(GtkSessionLockInstance *lock, DiyaSessionShell *shell)
|
||||
{
|
||||
(void)lock;
|
||||
assert(shell);
|
||||
g_message("Session unlocked");
|
||||
g_signal_emit_by_name(shell, DIYA_SIGNAL_SESSION_UNLOCKED);
|
||||
}
|
||||
|
||||
static void diya_session_shell_init(DiyaSessionShell *self)
|
||||
@@ -334,10 +285,6 @@ static void diya_session_shell_init(DiyaSessionShell *self)
|
||||
// self->app = NULL;
|
||||
self->launcher = NULL;
|
||||
self->settings = NULL;
|
||||
self->lock = gtk_session_lock_instance_new();
|
||||
g_signal_connect(self->lock, "locked", G_CALLBACK(on_session_locked), self);
|
||||
// g_signal_connect(lock, "failed", G_CALLBACK(failed), NULL);
|
||||
g_signal_connect(self->lock, "unlocked", G_CALLBACK(on_session_unlocked), self);
|
||||
self->windows = g_hash_table_new_full(g_direct_hash, g_direct_equal, NULL, g_object_unref);
|
||||
}
|
||||
|
||||
|
||||
@@ -9,11 +9,8 @@
|
||||
#define DIYA_SIGNAL_FOREIGN_WINDOW_STATE_CHANGED "foreign-window-state-changed"
|
||||
#define DIYA_SIGNAL_FOREIGN_WINDOW_ADDED "foreign-window-added"
|
||||
#define DIYA_SIGNAL_FOREIGN_WINDOW_REMOVED "foreign-window-removed"
|
||||
#define DIYA_SIGNAL_SESSION_LOCKED "session-locked"
|
||||
#define DIYA_SIGNAL_SESSION_UNLOCKED "session-unlocked"
|
||||
|
||||
#define DIYA_PROP_SESSION_LAUNCHPAD "launchpad"
|
||||
#define DIYA_PROP_SESSION_LOCK "session-lock"
|
||||
#define DIYA_PROP_SESSION_WINDOWS "windows"
|
||||
|
||||
#define SESSION_SHELL_SCHEMA_ID "dev.iohub.diya.session"
|
||||
|
||||
@@ -19,7 +19,7 @@ static void session_unlocked(DiyaSessionShell* shell, void* data)
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
DiyaSessionShell *shell = DIYA_SESSION_SHELL(g_object_new(DIYA_TYPE_SESSION_SHELL, "name","dev.iohub.diya.session", NULL));
|
||||
g_signal_connect(shell, DIYA_SIGNAL_SESSION_LOCKED, G_CALLBACK(session_locked), NULL);
|
||||
g_signal_connect(shell, DIYA_SIGNAL_SESSION_UNLOCKED, G_CALLBACK(session_unlocked), NULL);
|
||||
g_signal_connect(shell, DIYA_SIGNAL_SHELL_LOCKED, G_CALLBACK(session_locked), NULL);
|
||||
g_signal_connect(shell, DIYA_SIGNAL_SHELL_UNLOCKED, G_CALLBACK(session_unlocked), NULL);
|
||||
return diya_shell_run(DIYA_SHELL(shell), argc, argv);
|
||||
}
|
||||
|
||||
136
src/shell.c
136
src/shell.c
@@ -8,6 +8,7 @@
|
||||
#include "hook.h"
|
||||
#include <wayland-client-protocol.h>
|
||||
#include <gdk/wayland/gdkwayland.h>
|
||||
#include <gtk4-session-lock.h>
|
||||
|
||||
#define diya_shell_config_theme(priv) (g_strconcat(g_get_home_dir(), "/.themes/", priv->theme ? priv->theme : "default", "/gtk-4.0/gtk.css", NULL))
|
||||
#define diya_shell_config_theme_dir(priv) (g_strconcat(g_get_home_dir(), "/.themes/", priv->theme ? priv->theme : "default", "/gtk-4.0", NULL))
|
||||
@@ -19,6 +20,7 @@ enum
|
||||
PROP_SHELL_NAME,
|
||||
PROP_SHELL_THEME,
|
||||
PROP_SHELL_IDLE_TO,
|
||||
PROP_SHELL_LOCK,
|
||||
N_PROPERTIES
|
||||
};
|
||||
|
||||
@@ -36,6 +38,7 @@ typedef struct _DiyaShellPrivate
|
||||
DiyaHook *files_hook;
|
||||
gchar *theme;
|
||||
DiyaIdleNotification *idle_notif;
|
||||
GtkSessionLockInstance *lock;
|
||||
} DiyaShellPrivate;
|
||||
|
||||
G_DEFINE_TYPE_WITH_PRIVATE(DiyaShell, diya_shell, DIYA_TYPE_OBJECT);
|
||||
@@ -69,6 +72,14 @@ static void diya_shell_dispose(GObject *object)
|
||||
g_object_unref(priv->idle_notif);
|
||||
priv->idle_notif = NULL;
|
||||
}
|
||||
if (priv->lock)
|
||||
{
|
||||
if (gtk_session_lock_instance_is_locked(priv->lock))
|
||||
{
|
||||
gtk_session_lock_instance_unlock(priv->lock);
|
||||
}
|
||||
g_object_unref(priv->lock);
|
||||
}
|
||||
if (priv->wayland)
|
||||
{
|
||||
g_object_unref(priv->wayland);
|
||||
@@ -187,13 +198,14 @@ static void on_gtk_app_startup(GtkApplication *app, void *data)
|
||||
{
|
||||
class->startup_handle(shell);
|
||||
}
|
||||
/*
|
||||
if (class->monitor_changed_handle)
|
||||
{
|
||||
GListModel *monitor_list = gdk_display_get_monitors(gdk_display_get_default());
|
||||
g_debug("listen to monitor changed");
|
||||
g_signal_connect(monitor_list, "items-changed", G_CALLBACK(class->monitor_changed_handle), shell);
|
||||
}
|
||||
|
||||
*/
|
||||
}
|
||||
|
||||
static void on_gtk_app_active(GtkApplication *app, void *data)
|
||||
@@ -322,6 +334,10 @@ static void diya_shell_get_property(GObject *object, guint property_id, GValue *
|
||||
case PROP_SHELL_THEME:
|
||||
g_value_set_string(value, priv->theme);
|
||||
break;
|
||||
case PROP_SHELL_LOCK:
|
||||
// assert(priv->lock);
|
||||
g_value_set_pointer(value, priv->lock);
|
||||
break;
|
||||
case PROP_SHELL_IDLE_TO:
|
||||
if(priv->idle_notif)
|
||||
{
|
||||
@@ -338,6 +354,59 @@ static void diya_shell_get_property(GObject *object, guint property_id, GValue *
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static void on_shell_locked(GtkSessionLockInstance *lock, DiyaShell *shell)
|
||||
{
|
||||
(void)lock;
|
||||
assert(shell);
|
||||
g_message("Shell locked successfully");
|
||||
g_signal_emit_by_name(shell, DIYA_SIGNAL_SHELL_LOCKED);
|
||||
}
|
||||
|
||||
static void on_shell_unlocked(GtkSessionLockInstance *lock, DiyaShell *shell)
|
||||
{
|
||||
(void)lock;
|
||||
assert(shell);
|
||||
g_message("Shell unlocked");
|
||||
g_signal_emit_by_name(shell, DIYA_SIGNAL_SHELL_UNLOCKED);
|
||||
}
|
||||
|
||||
static void on_shell_lock_failed(GtkSessionLockInstance *lock, DiyaShell *shell)
|
||||
{
|
||||
(void)lock;
|
||||
assert(shell);
|
||||
g_critical("Unable to lock shell");
|
||||
g_signal_emit_by_name(shell, DIYA_SIGNAL_SHELL_LOCK_FAILED);
|
||||
}
|
||||
|
||||
static void on_monitor_present(GtkSessionLockInstance* lock, GdkMonitor *monitor, DiyaShell *shell)
|
||||
{
|
||||
assert(shell);
|
||||
g_debug("Build lock window for monitor");
|
||||
DiyaShellClass *class = DIYA_SHELL_GET_CLASS(shell);
|
||||
if(class->build_lock_window)
|
||||
{
|
||||
GtkWindow* window = class->build_lock_window(shell);
|
||||
gtk_session_lock_instance_assign_window_to_monitor(lock, window, monitor);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static void diya_shell_init_lock(DiyaShell* self)
|
||||
{
|
||||
DiyaShellPrivate *priv = diya_shell_get_instance_private(self);
|
||||
if(priv->lock)
|
||||
{
|
||||
return;
|
||||
}
|
||||
priv->lock = gtk_session_lock_instance_new();
|
||||
g_signal_connect(priv->lock, DIYA_SIGNAL_SHELL_LOCKED, G_CALLBACK(on_shell_locked), self);
|
||||
g_signal_connect(priv->lock, "failed", G_CALLBACK(on_shell_lock_failed), self);
|
||||
g_signal_connect(priv->lock, DIYA_SIGNAL_SHELL_UNLOCKED, G_CALLBACK(on_shell_unlocked), self);
|
||||
g_signal_connect(priv->lock, "monitor", G_CALLBACK(on_monitor_present), self);
|
||||
|
||||
}
|
||||
|
||||
static void diya_shell_init(DiyaShell *self)
|
||||
{
|
||||
DiyaShellPrivate *priv = diya_shell_get_instance_private(self);
|
||||
@@ -350,6 +419,7 @@ static void diya_shell_init(DiyaShell *self)
|
||||
priv->files_hook = NULL;
|
||||
priv->theme = NULL;
|
||||
priv->idle_notif = NULL;
|
||||
priv->lock = NULL;
|
||||
}
|
||||
|
||||
DiyaWayland *diya_shell_get_wayland(DiyaShell *shell)
|
||||
@@ -390,7 +460,7 @@ static void diya_shell_class_init(DiyaShellClass *class)
|
||||
|
||||
class->foreign_register = NULL;
|
||||
class->virtual_keyboard_register = diya_virtual_keyboard_register;
|
||||
class->monitor_changed_handle = NULL;
|
||||
class->build_lock_window = NULL;
|
||||
class->startup_handle = NULL;
|
||||
class->active_handle = NULL;
|
||||
class->reload_handle = NULL;
|
||||
@@ -400,6 +470,7 @@ static void diya_shell_class_init(DiyaShellClass *class)
|
||||
shell_properties[PROP_SHELL_APP] = g_param_spec_pointer(DIYA_PROP_SHELL_APPLICATION, NULL, "Shell application", G_PARAM_READABLE);
|
||||
shell_properties[PROP_SHELL_THEME] = g_param_spec_string(DIYA_PROP_SHELL_THEME, NULL, "Shell theme", NULL, G_PARAM_READWRITE);
|
||||
shell_properties[PROP_SHELL_IDLE_TO] = g_param_spec_uint(DIYA_PROP_SHELL_IDLE_TIMEOUT, NULL, "Shell IDLE timeout", 0, UINT32_MAX ,DEFAULT_IDLE_TIMEOUT, G_PARAM_READWRITE);
|
||||
shell_properties[PROP_SHELL_LOCK] = g_param_spec_pointer(DIYA_PROP_SHELL_LOCK, NULL, "Shell lock", G_PARAM_READABLE);
|
||||
|
||||
g_object_class_install_properties(gobject_class, N_PROPERTIES, shell_properties);
|
||||
|
||||
@@ -519,6 +590,39 @@ static void diya_shell_class_init(DiyaShellClass *class)
|
||||
G_TYPE_NONE,
|
||||
1,
|
||||
G_TYPE_POINTER);
|
||||
g_signal_new(DIYA_SIGNAL_SHELL_LOCKED,
|
||||
DIYA_TYPE_SHELL,
|
||||
G_SIGNAL_DETAILED |
|
||||
G_SIGNAL_ACTION |
|
||||
G_SIGNAL_RUN_FIRST,
|
||||
0,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
G_TYPE_NONE,
|
||||
0);
|
||||
g_signal_new(DIYA_SIGNAL_SHELL_UNLOCKED,
|
||||
DIYA_TYPE_SHELL,
|
||||
G_SIGNAL_DETAILED |
|
||||
G_SIGNAL_ACTION |
|
||||
G_SIGNAL_RUN_FIRST,
|
||||
0,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
G_TYPE_NONE,
|
||||
0);
|
||||
g_signal_new(DIYA_SIGNAL_SHELL_LOCK_FAILED,
|
||||
DIYA_TYPE_SHELL,
|
||||
G_SIGNAL_DETAILED |
|
||||
G_SIGNAL_ACTION |
|
||||
G_SIGNAL_RUN_FIRST,
|
||||
0,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
G_TYPE_NONE,
|
||||
0);
|
||||
}
|
||||
|
||||
static int diya_shell_handle_local_options(GApplication *application, GVariantDict *options, gpointer user_data)
|
||||
@@ -702,4 +806,32 @@ gboolean diya_shell_watch_script(DiyaShell* self, const gchar* script)
|
||||
priv->files_hook = diya_hook_new();
|
||||
}
|
||||
return diya_hook_install_lua(priv->files_hook, script);
|
||||
}
|
||||
|
||||
void diya_shell_lock(DiyaShell* self)
|
||||
{
|
||||
DiyaShellPrivate *priv = diya_shell_get_instance_private(self);
|
||||
if(!priv->lock)
|
||||
{
|
||||
diya_shell_init_lock(self);
|
||||
}
|
||||
if(gtk_session_lock_instance_is_locked(priv->lock))
|
||||
{
|
||||
g_warning("Shell session is already locked, doing nothing");
|
||||
return;
|
||||
}
|
||||
if(!gtk_session_lock_instance_lock(priv->lock))
|
||||
{
|
||||
g_error("gtk_session_lock_instance_lock:Unable to lock the current session");
|
||||
return;
|
||||
}
|
||||
}
|
||||
void diya_shell_unlock(DiyaShell* self)
|
||||
{
|
||||
DiyaShellPrivate *priv = diya_shell_get_instance_private(self);
|
||||
if(priv->lock)
|
||||
{
|
||||
gtk_session_lock_instance_unlock(priv->lock);
|
||||
g_debug("gtk_session_lock_instance_unlock: Shell unlocked");
|
||||
}
|
||||
}
|
||||
@@ -14,7 +14,7 @@
|
||||
#define DIYA_PROP_SHELL_APPLICATION "application"
|
||||
#define DIYA_PROP_SHELL_THEME "theme"
|
||||
#define DIYA_PROP_SHELL_IDLE_TIMEOUT "idle-timeout"
|
||||
|
||||
#define DIYA_PROP_SHELL_LOCK "lock"
|
||||
|
||||
#define DIYA_SIGNAL_SHELL_KEYBOARD_ENTER "keyboard-enter"
|
||||
#define DIYA_SIGNAL_SHELL_KEYBOARD_LEAVE "keyboard-leave"
|
||||
@@ -25,6 +25,9 @@
|
||||
#define DIYA_SIGNAL_SHELL_RESUME "resume"
|
||||
#define DIYA_SIGNAL_SHELL_WINDOW_ENTER "shell-window-enter"
|
||||
#define DIYA_SIGNAL_SHELL_WINDOW_LEAVE "shell-window-leave"
|
||||
#define DIYA_SIGNAL_SHELL_LOCKED "locked"
|
||||
#define DIYA_SIGNAL_SHELL_UNLOCKED "unlocked"
|
||||
#define DIYA_SIGNAL_SHELL_LOCK_FAILED "lock-failed"
|
||||
|
||||
#define DIYA_TYPE_SHELL (diya_shell_get_type())
|
||||
G_DECLARE_DERIVABLE_TYPE(DiyaShell, diya_shell, DIYA, SHELL, DiyaObject)
|
||||
@@ -38,7 +41,7 @@ struct _DiyaShellClass
|
||||
DiyaObjectClass parent_class;
|
||||
wl_protocol_manager_register_t foreign_register;
|
||||
wl_protocol_manager_register_t virtual_keyboard_register;
|
||||
void (*monitor_changed_handle)(GListModel* /*list*/,guint /*position*/, guint /*removed*/,guint /*added*/, gpointer);
|
||||
GtkWindow* (*build_lock_window)(DiyaShell*);
|
||||
void (*startup_handle)(DiyaShell*);
|
||||
void (*active_handle)(DiyaShell*);
|
||||
void (*reload_handle)(DiyaShell*);
|
||||
@@ -57,6 +60,8 @@ gboolean diya_shell_watch_script(DiyaShell* shell, const gchar* script);
|
||||
void diya_shell_unwatch_file(DiyaShell* shell, const gchar* file);
|
||||
void diya_shell_power_display(DiyaShell* shell, gboolean mode);
|
||||
void diya_shell_launch(DiyaShell* shell, GAppInfo* app);
|
||||
void diya_shell_lock(DiyaShell* shell);
|
||||
void diya_shell_unlock(DiyaShell* shell);
|
||||
|
||||
int diya_shell_run(DiyaShell* shell, int argc, char **argv);
|
||||
#endif
|
||||
@@ -1,5 +1,6 @@
|
||||
#include "taskbar-widget.h"
|
||||
#include "foreign.h"
|
||||
#include "session-lock.h"
|
||||
|
||||
#define DEFAULT_APP_ICON_NAME "application-x-executable-symbolic"
|
||||
|
||||
@@ -303,6 +304,7 @@ static void diya_dashboard_btn_test_clicked(GtkWidget *widget, gpointer user_dat
|
||||
DiyaShellWindow *self = user_data;
|
||||
DiyaSessionShell *shell = DIYA_SESSION_SHELL(diya_shell_window_get_shell(self));
|
||||
g_return_if_fail(DIYA_IS_SESSION_SHELL(shell));
|
||||
diya_shell_lock(DIYA_SHELL(shell));
|
||||
// TODO remove
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user