diff --git a/include/gtklock.h b/include/gtklock.h index 64c2f72..63930ba 100644 --- a/include/gtklock.h +++ b/include/gtklock.h @@ -6,13 +6,13 @@ #pragma once #include -#include +#include struct Window; struct GtkLock { GtkApplication *app; - GtkSessionLockLock *lock; + GtkSessionLockInstance *lock; pid_t parent; GArray *windows; diff --git a/meson.build b/meson.build index 7335cdf..2ffa314 100644 --- a/meson.build +++ b/meson.build @@ -13,8 +13,8 @@ major_version = version[0] minor_version = version[1] micro_version = version[2] -gtk = dependency('gtk+-3.0') -gtk_session_lock = dependency('gtk-session-lock-0') +gtk = dependency('gtk4') +gtk_session_lock = dependency('gtk4-layer-shell') gmodule_export = dependency('gmodule-export-2.0') pam = meson.get_compiler('c').find_library('pam') diff --git a/meson.options b/meson.options new file mode 100644 index 0000000..6694662 --- /dev/null +++ b/meson.options @@ -0,0 +1 @@ +ption('man-pages', type: 'feature', value: 'auto', description: 'Generate and install man pages') diff --git a/meson_options.txt b/meson_options.txt deleted file mode 100644 index e40a23d..0000000 --- a/meson_options.txt +++ /dev/null @@ -1 +0,0 @@ -option('man-pages', type: 'feature', value: 'auto', description: 'Generate and install man pages') diff --git a/res/gtklock.ui b/res/gtklock.ui index 4a2ca89..562887c 100644 --- a/res/gtklock.ui +++ b/res/gtklock.ui @@ -1,136 +1,154 @@ - - window-box - 100 - center - center - vertical - 10 - - - info-box - center - vertical - 5 - - - time-box - center - vertical - - - clock-label - center - - - - - date-label - center - - - - - - - - - none - 0 - - - 5 - 5 - - - input-label - Password: - - - 0 - 0 - - - - - input-field - 380 - 0 - 0 - password - view-reveal-symbolic - - - - - 1 - 0 - 2 - - - - - none - 1 - - - never - 256 - 1 - - - - - vertical - 1 - - - - - - - - - 1 - 1 - 2 - - - - - end - 5 - - - warning-label - - - - - error-label - - - - - unlock-button - Unlock - - - - - - - 1 - 2 - 2 - - - - - - - + + + 1 + window-box + 100 + 100 + 100 + 100 + center + center + vertical + 10 + + + 1 + info-box + center + vertical + 5 + + + 1 + time-box + center + vertical + + + 1 + clock-label + center + + + + + 1 + date-label + center + + + + + + + + + 1 + none + + + 1 + 5 + 5 + + + 1 + input-label + Password: + + 0 + 0 + + + + + + 1 + input-field + 380 + 0 + password + view-reveal-symbolic + + + + 1 + 0 + 2 + + + + + + 1 + unlock-button + Unlock + + + + + + + 1 + none + + + 1 + never + 256 + 1 + + + 1 + + + 1 + vertical + 1 + + + + + + + + 1 + 1 + 2 + + + + + + 1 + end + 5 + + 1 + 2 + 2 + + + + 1 + warning-label + + + + + 1 + error-label + + + + + + + + + diff --git a/src/auth.c b/src/auth.c index 53e6628..f4329ba 100644 --- a/src/auth.c +++ b/src/auth.c @@ -82,7 +82,7 @@ static void auth_child(const char *s, int *err, int *out) { pwd = getpwuid(getuid()); if(pwd == NULL) { perror("getpwnam"); - exit(EXIT_FAILURE); + _Exit(EXIT_FAILURE); } char *username = pwd->pw_name; @@ -93,16 +93,20 @@ static void auth_child(const char *s, int *err, int *out) { pam_status = pam_start("gtklock", username, &conv, &handle); if(pam_status != PAM_SUCCESS) { fprintf(stderr, "pam_start() failed"); - exit(EXIT_FAILURE); + _Exit(EXIT_FAILURE); } int ret = pam_authenticate((pam_handle_t *)handle, 0); pam_status = ret; + if (pam_status != PAM_SUCCESS){ + fprintf(stderr, "Wrong password\n"); + _Exit(EXIT_FAILURE); + } pam_status = pam_setcred((pam_handle_t *)handle, PAM_REFRESH_CRED); if(pam_end(handle, pam_status) != PAM_SUCCESS) fprintf(stderr, "pam_end() failed"); - if(ret == PAM_SUCCESS) exit(EXIT_SUCCESS); - exit(EXIT_FAILURE); + if(ret == PAM_SUCCESS) _Exit(EXIT_SUCCESS); + _Exit(EXIT_FAILURE); } enum pwcheck auth_pw_check(const char *s) { @@ -162,10 +166,12 @@ enum pwcheck auth_pw_check(const char *s) { return PW_MESSAGE; } - int status; - if(waitpid(pid, &status, WNOHANG) != 0 && WIFEXITED(status)) { + siginfo_t info; + if(waitid(P_PID, pid, &info, WEXITED)==0){ pid = -2; - if(WEXITSTATUS(status) == EXIT_SUCCESS) return PW_SUCCESS; + if(WIFEXITED(info.si_status) && WEXITSTATUS(info.si_status) == EXIT_SUCCESS){ + return PW_SUCCESS; + } else return PW_FAILURE; } return PW_WAIT; diff --git a/src/gtklock.c b/src/gtklock.c index 80b8884..c0d8e23 100644 --- a/src/gtklock.c +++ b/src/gtklock.c @@ -82,6 +82,7 @@ void gtklock_idle_hide(struct GtkLock *gtklock) { } void gtklock_idle_show(struct GtkLock *gtklock) { + //printf("KEY PRESSED SHOWING!\n"); if(gtklock->hidden) { gtklock->hidden = FALSE; module_on_idle_show(gtklock); @@ -112,7 +113,7 @@ static gboolean signal_handler(gpointer data) { return FALSE; } -static void locked(GtkSessionLockLock *lock, void *data) { +static void locked(GtkSessionLockInstance *lock, void *data) { struct GtkLock *gtklock = (struct GtkLock *)data; g_unix_signal_add(SIGUSR1, G_SOURCE_FUNC(signal_handler), gtklock); @@ -123,8 +124,9 @@ static void locked(GtkSessionLockLock *lock, void *data) { return; } -static void finished(GtkSessionLockLock *lock, void *data) { - gtk_session_lock_lock_destroy(lock); +static void finished(GtkSessionLockInstance *lock, void *data) { + + // gtk_session_lock_lock_destroy(lock); report_error_and_exit("Failed to lock session"); } @@ -133,13 +135,17 @@ void gtklock_activate(struct GtkLock *gtklock) { if(!gtk_session_lock_is_supported()) report_error_and_exit("Your compositor doesn't support ext-session-lock"); - gtklock->lock = gtk_session_lock_prepare_lock(); + + gtklock->lock = gtk_session_lock_instance_new(); + // Gets here fine! g_signal_connect(gtklock->lock, "locked", G_CALLBACK(locked), gtklock); g_signal_connect(gtklock->lock, "finished", G_CALLBACK(finished), NULL); - gtk_session_lock_lock_lock(gtklock->lock); + // If i lock, then my session doesn't show :( + //gtk_session_lock_lock_lock(gtklock->lock); + //gtk_session_lock_instance_lock(gtklock->lock); gtklock->draw_time_source = g_timeout_add(1000, G_SOURCE_FUNC(update_time_handler), gtklock); gtklock_update_clocks(gtklock); @@ -149,6 +155,7 @@ void gtklock_activate(struct GtkLock *gtklock) { } void gtklock_shutdown(struct GtkLock *gtklock) { + printf("Exiting now :) \n"); if(gtklock->draw_time_source > 0) { g_source_remove(gtklock->draw_time_source); gtklock->draw_time_source = 0; @@ -158,12 +165,13 @@ void gtklock_shutdown(struct GtkLock *gtklock) { gtklock->idle_hide_source = 0; } - gtk_session_lock_lock_unlock_and_destroy(gtklock->lock); + // gtk_session_lock_lock_unlock_and_destroy(gtklock->lock); + gtk_session_lock_instance_unlock(gtklock->lock); gdk_display_sync(gdk_display_get_default()); for(guint idx = 0; idx < gtklock->windows->len; idx++) { struct Window *ctx = g_array_index(gtklock->windows, struct Window *, idx); - gtk_widget_destroy(ctx->window); + gtk_window_destroy(GTK_WINDOW(ctx->window)); } if(gtklock->unlock_command) exec_command(gtklock->unlock_command); diff --git a/src/source.c b/src/source.c index ad2ac22..534bc5c 100644 --- a/src/source.c +++ b/src/source.c @@ -103,8 +103,9 @@ static void monitors_removed(GdkDisplay *display, GdkMonitor *monitor, gpointer gtklock->focused_window = NULL; if(any_window) window_swap_focus(any_window, w); } - gtk_session_lock_unmap_lock_window(GTK_WINDOW(w->window)); - gtk_widget_destroy(w->window); + + // gtk_session_lock_unmap_lock_window(GTK_WINDOW(w->window)); + gtk_window_destroy(GTK_WINDOW(w->window)); } module_on_output_change(gtklock); } @@ -156,9 +157,10 @@ static void activate(GtkApplication *app, gpointer user_data) { GArray *priority_monitors = g_array_new(FALSE, TRUE, sizeof(GdkMonitor *)); GHashTable *priority_monitor_names = g_hash_table_new_full(g_direct_hash, g_direct_equal, NULL, g_free); - for(int i = 0; i < gdk_display_get_n_monitors(display); ++i) { - char *name = gdk_screen_get_monitor_plug_name(gdk_screen_get_default(), i); - GdkMonitor *monitor = gdk_display_get_monitor(display, i); + GListModel* monitors2 = gdk_display_get_monitors(display); + for(int i = 0; i < g_list_model_get_n_items(monitors2); ++i) { + GdkMonitor *monitor = g_list_model_get_item (monitors2, i); + char *name = gdk_monitor_get_model(monitor); if(find_priority_monitor(name)) { g_hash_table_insert(priority_monitor_names, monitor, name); @@ -174,12 +176,16 @@ static void activate(GtkApplication *app, gpointer user_data) { gpointer data = g_array_steal(priority_monitors, &len); g_array_prepend_vals(monitors, data, len); + gtk_session_lock_instance_lock(gtklock->lock); + for(guint idx = 0; idx < monitors->len; idx++) create_window(g_array_index(monitors, GdkMonitor *, idx)); if(gtklock->windows->len) gtklock_focus_window(gtklock, g_array_index(gtklock->windows, struct Window *, 0)); g_array_unref(monitors); g_array_unref(priority_monitors); g_hash_table_unref(priority_monitor_names); + + } static void shutdown(GtkApplication *app, gpointer user_data) { @@ -198,15 +204,24 @@ static void attach_style(const gchar *format, ...) { va_start(args, format); char *buff = g_strdup_vprintf(format, args); va_end(args); - - gtk_css_provider_load_from_data(provider, buff, -1, &err); + gtk_css_provider_load_from_string(provider, buff); + // Now we need to connect to the CssProvider::parsing-error signal to check error! + /* if(err != NULL) { g_warning("Style loading failed: %s", err->message); g_error_free(err); - } else { - gtk_style_context_add_provider_for_screen(gdk_screen_get_default(), - GTK_STYLE_PROVIDER(provider), GTK_STYLE_PROVIDER_PRIORITY_APPLICATION); } + */ + GdkDisplay *display = gdk_display_get_default(); + if(display == NULL){ + display = gdk_display_open(NULL); // NULL uses the default display name + } + if(display == NULL){ + g_warning("Failed to open display"); + return; + } + gtk_style_context_add_provider_for_display(gdk_display_get_default(), + GTK_STYLE_PROVIDER(provider), GTK_STYLE_PROVIDER_PRIORITY_APPLICATION); g_object_unref(provider); g_free(buff); @@ -216,14 +231,16 @@ static void attach_custom_style(const gchar *path) { GtkCssProvider *provider = gtk_css_provider_new(); GError *err = NULL; - gtk_css_provider_load_from_path(provider, path, &err); + gtk_css_provider_load_from_path(provider, path); + /* + // Again we need to actually connect to a signal now! if(err != NULL) { g_warning("Custom style loading failed: %s", err->message); g_error_free(err); - } else { - gtk_style_context_add_provider_for_screen(gdk_screen_get_default(), - GTK_STYLE_PROVIDER(provider), GTK_STYLE_PROVIDER_PRIORITY_APPLICATION+1); } + */ + gtk_style_context_add_provider_for_display(gdk_display_get_default(), + GTK_STYLE_PROVIDER(provider), GTK_STYLE_PROVIDER_PRIORITY_APPLICATION+1); g_object_unref(provider); } @@ -265,6 +282,7 @@ static gboolean signal_handler(gpointer data) { #endif int main(int argc, char **argv) { + gtk_init(); setlocale(LC_ALL, ""); bindtextdomain(GETTEXT_PACKAGE, LOCALEDIR); bind_textdomain_codeset(GETTEXT_PACKAGE, "UTF-8"); @@ -295,7 +313,7 @@ int main(int argc, char **argv) { g_option_group_add_entries(debug_group, debug_entries); g_option_context_add_group(option_context, config_group); g_option_context_add_group(option_context, debug_group); - g_option_context_add_group(option_context, gtk_get_option_group(TRUE)); + //g_option_context_add_group(option_context, gtk_get_option_group(TRUE)); g_option_context_parse(option_context, &argc, &argv, NULL); GArray *modules = g_array_new(FALSE, TRUE, sizeof(GModule *)); diff --git a/src/window.c b/src/window.c index b5859cb..6a60117 100644 --- a/src/window.c +++ b/src/window.c @@ -7,7 +7,7 @@ #include #include -#include +#include #include "util.h" #include "window.h" @@ -50,8 +50,8 @@ void window_update_date(struct Window *ctx) { static void window_setup_messages(struct Window *ctx); static void window_close_message(GtkInfoBar *bar, gint response, gpointer data) { - struct Window *ctx = window_by_widget(gtk_widget_get_toplevel(GTK_WIDGET(bar))); - gtk_widget_destroy(GTK_WIDGET(bar)); + struct Window *ctx = window_by_widget(GTK_WIDGET(gtk_widget_get_root(GTK_WIDGET(bar)))); + gtk_widget_unrealize(GTK_WIDGET(bar)); for(guint idx = 0; idx < gtklock->errors->len; idx++) { char *err = g_array_index(gtklock->errors, char *, idx); if(err == data) { @@ -76,22 +76,24 @@ static GtkInfoBar *window_new_message(struct Window *ctx, char *msg) { GtkWidget *bar = gtk_info_bar_new(); gtk_info_bar_set_show_close_button(GTK_INFO_BAR(bar), TRUE); g_signal_connect(bar, "response", G_CALLBACK(window_close_message), msg); - gtk_container_add(GTK_CONTAINER(ctx->message_box), bar); + gtk_box_append(GTK_BOX(ctx->message_box), bar); - GtkWidget *content_area = gtk_info_bar_get_content_area(GTK_INFO_BAR(bar)); GtkWidget *label = gtk_label_new(msg); - gtk_container_add(GTK_CONTAINER(content_area), label); - - gtk_widget_show_all(bar); + gtk_info_bar_add_child(GTK_INFO_BAR(bar), label); return GTK_INFO_BAR(bar); } static void destroy_callback(GtkWidget* widget, gpointer _data) { - gtk_widget_destroy(widget); + gtk_widget_unrealize(widget); } static void window_setup_messages(struct Window *ctx) { - gtk_container_foreach(GTK_CONTAINER(ctx->message_box), destroy_callback, NULL); + GtkWidget *child = gtk_widget_get_first_child(ctx->message_box); + while (child != NULL) { + destroy_callback(child, NULL); // Call the callback for each child + child = gtk_widget_get_next_sibling(child); // Move to the next child + } + gtk_revealer_set_reveal_child(GTK_REVEALER(ctx->message_revealer), FALSE); gtk_widget_hide(ctx->message_revealer); @@ -102,7 +104,6 @@ static void window_setup_messages(struct Window *ctx) { gtk_revealer_set_reveal_child(GTK_REVEALER(ctx->message_revealer), TRUE); gtk_widget_show(ctx->message_revealer); - gtk_widget_show_all(ctx->message_scrolled_window); } for(guint idx = 0; idx < gtklock->messages->len; idx++) { char *msg = g_array_index(gtklock->messages, char *, idx); @@ -111,7 +112,6 @@ static void window_setup_messages(struct Window *ctx) { gtk_revealer_set_reveal_child(GTK_REVEALER(ctx->message_revealer), TRUE); gtk_widget_show(ctx->message_revealer); - gtk_widget_show_all(ctx->message_scrolled_window); } } @@ -120,8 +120,8 @@ static void window_set_busy(struct Window *ctx, gboolean busy) { if(busy) g_application_mark_busy(G_APPLICATION(gtklock->app)); else g_application_unmark_busy(G_APPLICATION(gtklock->app)); - GdkCursor *cursor = gdk_cursor_new_from_name(gtk_widget_get_display(ctx->window), busy ? "wait" : "default"); - gdk_window_set_cursor(gtk_widget_get_window(ctx->window), cursor); + GdkCursor *cursor = gdk_cursor_new_from_name(busy ? "wait" : "default", NULL); + gtk_widget_set_cursor(GTK_WIDGET(gtk_widget_get_root(ctx->window)), cursor); g_object_unref(cursor); gtk_widget_set_sensitive(ctx->unlock_button, !busy); @@ -131,7 +131,8 @@ static void window_set_busy(struct Window *ctx, gboolean busy) { static gboolean window_pw_failure(gpointer data) { struct Window *ctx = data; window_set_busy(ctx, FALSE); - gtk_entry_set_text(GTK_ENTRY(ctx->input_field), ""); + GtkEntryBuffer* buffer = gtk_entry_get_buffer(GTK_ENTRY(ctx->input_field)); + gtk_entry_buffer_delete_text(buffer, 0, -1); // delete all text gtk_entry_grab_focus_without_selecting(GTK_ENTRY(ctx->input_field)); gtk_label_set_text(GTK_LABEL(ctx->error_label), _("Login failed")); return G_SOURCE_REMOVE; @@ -144,9 +145,10 @@ static gboolean window_pw_message(gpointer data) { static gpointer window_pw_wait(gpointer data) { struct Window *ctx = data; - const char *password = gtk_entry_get_text((GtkEntry*)ctx->input_field); + GtkEntryBuffer* buffer = gtk_entry_get_buffer(GTK_ENTRY(ctx->input_field)); + const char *password = gtk_entry_buffer_get_text(buffer); while(TRUE) { - enum pwcheck ret = auth_pw_check(password); + enum pwcheck ret = auth_pw_check(password); // lets me through on success or failure, unless account is locked`` switch(ret) { case PW_FAILURE: g_main_context_invoke(NULL, window_pw_failure, ctx); @@ -159,6 +161,7 @@ static gpointer window_pw_wait(gpointer data) { char *err = auth_get_error(); g_array_append_val(gtklock->errors, err); g_main_context_invoke(NULL, window_pw_message, ctx); + return NULL; } break; case PW_MESSAGE: @@ -166,6 +169,7 @@ static gpointer window_pw_wait(gpointer data) { char *msg = auth_get_message(); g_array_append_val(gtklock->messages, msg); g_main_context_invoke(NULL, window_pw_message, ctx); + return NULL; } break; case PW_WAIT: @@ -197,7 +201,7 @@ void window_pw_toggle_vis(GtkEntry* entry, GtkEntryIconPosition icon_pos) { static void window_destroy_notify(GtkWidget *widget, gpointer data) { struct Window *win = window_by_widget(widget); module_on_window_destroy(gtklock, win); - gtk_widget_destroy(widget); + gtk_widget_unrealize(widget); gtklock_remove_window(gtklock, win); } @@ -219,8 +223,10 @@ void window_swap_focus(struct Window *win, struct Window *old) { g_object_get(GTK_ENTRY(old->input_field), "cursor-position", &cursor_pos, NULL); // Move content - gtk_entry_set_text(GTK_ENTRY(win->input_field), gtk_entry_get_text(GTK_ENTRY(old->input_field))); - gtk_entry_set_text(GTK_ENTRY(old->input_field), ""); + GtkEntryBuffer* old_buffer = gtk_entry_get_buffer(GTK_ENTRY(old->input_field)); + GtkEntryBuffer* new_buffer = gtk_entry_get_buffer(GTK_ENTRY(win->input_field)); + gtk_entry_buffer_set_text(new_buffer, gtk_entry_buffer_get_text(old_buffer), -1); + gtk_entry_buffer_delete_text(old_buffer, 0, -1); // delete all text // Update new cursor position g_signal_emit_by_name(GTK_ENTRY(win->input_field), "move-cursor", GTK_MOVEMENT_BUFFER_ENDS, -1, FALSE); @@ -238,8 +244,8 @@ void window_idle_hide(struct Window *ctx) { GtkStyleContext *context = gtk_widget_get_style_context(ctx->window); gtk_style_context_add_class(context, "hidden"); gtk_revealer_set_reveal_child(GTK_REVEALER(ctx->body_revealer), FALSE); - GdkCursor *cursor = gdk_cursor_new_for_display(gtk_widget_get_display(ctx->window), GDK_BLANK_CURSOR); - gdk_window_set_cursor(gtk_widget_get_window(ctx->window), cursor); + GdkCursor *cursor = gdk_cursor_new_from_name("none",NULL); + gtk_widget_set_cursor(GTK_WIDGET(gtk_widget_get_root(ctx->window)), cursor); g_object_unref(cursor); } @@ -250,30 +256,47 @@ void window_idle_show(struct Window *ctx) { gtk_revealer_set_reveal_child(GTK_REVEALER(ctx->body_revealer), TRUE); gtk_entry_grab_focus_without_selecting(GTK_ENTRY(ctx->input_field)); } - GdkCursor *cursor = gdk_cursor_new_from_name(gtk_widget_get_display(ctx->window), "default"); - gdk_window_set_cursor(gtk_widget_get_window(ctx->window), cursor); + GdkCursor *cursor = gdk_cursor_new_from_name("default",NULL); + gtk_widget_set_cursor(GTK_WIDGET(gtk_widget_get_root(ctx->window)), cursor); g_object_unref(cursor); } -static gboolean window_idle_key(GtkWidget *self, GdkEventKey event, gpointer user_data) { +static gboolean window_idle_key(GtkWidget *drawing_area, + guint keyval, + guint keycode, + GdkModifierType state, + GtkEventControllerKey *event_controller){ gtklock_idle_show(gtklock); return FALSE; } -static gboolean window_idle_motion(GtkWidget *self, GdkEventMotion event, gpointer user_data) { +//static gboolean window_idle_motion(GtkWidget *self, GdkMotionEvent *event, gpointer user_data) { +static void window_idle_motion ( + GtkEventControllerMotion* self, + gdouble x, + gdouble y, + gpointer user_data) { gtklock_idle_show(gtklock); - return FALSE; + //return FALSE; } -static void window_caps_state_changed(GdkKeymap *self, gpointer user_data) { +static void window_caps_state_changed(GtkWidget *drawing_area, + guint keyval, + guint keycode, + GdkModifierType state, + GtkEventControllerKey *event_controller) { struct Window *w = gtklock->focused_window; if(!w || !w->warning_label) return; - - if(gdk_keymap_get_caps_lock_state(self)) gtk_label_set_text(GTK_LABEL(w->warning_label), _("Caps Lock is on")); + GdkDisplay *display = gtk_widget_get_display(w->window); + // now lets get the primary seat for the display + GdkSeat *seat = gdk_display_get_default_seat(display); + // now lets get the keyboard device for the seat finally + GdkDevice *device = gdk_seat_get_keyboard(seat); + if(gdk_device_get_caps_lock_state(device)) gtk_label_set_text(GTK_LABEL(w->warning_label), _("Caps Lock is on")); else gtk_label_set_text(GTK_LABEL(w->warning_label), ""); } -static gboolean entry_button_press(GtkWidget *widget, GdkEventButton *event, gpointer data) { - if(event->button != 1) return TRUE; +static gboolean entry_button_press(GtkWidget *widget, GdkButtonEvent *event, gpointer data) { + if(gdk_button_event_get_button(GDK_EVENT(event)) != 1) return TRUE; return FALSE; } @@ -290,7 +313,8 @@ struct Window *create_window(GdkMonitor *monitor) { struct Window *w = g_malloc0(sizeof(struct Window) + gtklock->modules->len * sizeof(void *)); if(!w) report_error_and_exit("Failed allocation"); - g_array_append_val(gtklock->windows, w); + //g_array_append_val(gtklock->windows, w); + g_array_append_vals(gtklock->windows, &w, 1); w->monitor = monitor; w->window = gtk_application_window_new(gtklock->app); @@ -298,9 +322,17 @@ struct Window *create_window(GdkMonitor *monitor) { if(gtklock->follow_focus) g_signal_connect(w->window, "enter-notify-event", G_CALLBACK(window_enter_notify), NULL); if(gtklock->use_idle_hide || gtklock->hidden) { - gtk_widget_add_events(w->window, GDK_POINTER_MOTION_MASK); - g_signal_connect(w->window, "key-press-event", G_CALLBACK(window_idle_key), NULL); - g_signal_connect(w->window, "motion-notify-event", G_CALLBACK(window_idle_motion), NULL); + //gtk_widget_add_events(w->window, GDK_POINTER_MOTION_MASK); + GtkEventController *motion_controller = gtk_event_controller_motion_new(); + GtkEventController *event_controller = gtk_event_controller_key_new (); + gtk_event_controller_set_propagation_phase(event_controller, GTK_PHASE_CAPTURE); + g_signal_connect(event_controller, "key-pressed", G_CALLBACK(window_idle_key), NULL); + gtk_widget_add_controller (GTK_WIDGET (w->window), event_controller); + gtk_widget_add_controller (GTK_WIDGET (w->window), motion_controller); + gtk_widget_set_focusable(w->window, TRUE); + //g_signal_connect(w->window, "key-pressed", G_CALLBACK(window_idle_key), NULL); + g_signal_connect(motion_controller, "motion", G_CALLBACK(window_idle_motion), NULL); + g_signal_connect(event_controller, "key-released", G_CALLBACK(window_idle_key), NULL); } GdkDisplay *display = gtk_widget_get_display(w->window); @@ -311,48 +343,55 @@ struct Window *create_window(GdkMonitor *monitor) { Related issue: https://gitlab.gnome.org/GNOME/gtk/-/issues/4982 */ char *name = NULL; - GdkScreen *screen = gtk_widget_get_screen(w->window); - for(int i = 0; i < gdk_display_get_n_monitors(display); i++) { - GdkMonitor *monitor = gdk_display_get_monitor(display, i); + GListModel* monitors = gdk_display_get_monitors(display); + for(int i = 0; i < g_list_model_get_n_items(monitors); i++) { + GdkMonitor *monitor = g_list_model_get_item (monitors, i); if(monitor != w->monitor) continue; - name = gdk_screen_get_monitor_plug_name(screen, i); + name = gdk_monitor_get_model(monitor); } - GdkKeymap *keymap = gdk_keymap_get_for_display(display); - g_signal_connect(keymap, "state-changed", G_CALLBACK(window_caps_state_changed), NULL); + GtkEventController *event_controller2 = gtk_event_controller_key_new (); + //GdkKeymapKey *keymapkey = gdk_display_get_keymap(display); + //g_signal_connect_object(event_controller2, "key-pressed", G_CALLBACK(window_caps_state_changed), w->window, G_CONNECT_SWAPPED); + //g_signal_connect(keymapkey, "state-changed", G_CALLBACK(window_caps_state_changed), NULL); if(name) { gtk_widget_set_name(w->window, name); - g_free(name); + //g_free(name); // THIS BREAKS EVERYTHING! } gtk_window_set_title(GTK_WINDOW(w->window), "Lockscreen"); gtk_window_set_decorated(GTK_WINDOW(w->window), FALSE); - gtk_widget_realize(w->window); - gtk_session_lock_lock_new_surface(gtklock->lock, GTK_WINDOW(w->window), monitor); + + gtk_session_lock_instance_assign_window_to_monitor(gtklock->lock, GTK_WINDOW(w->window), monitor); + //gtk_widget_realize(w->window); + //gtk_session_lock_lock_new_surface(gtklock->lock, GTK_WINDOW(w->window), monitor); w->overlay = gtk_overlay_new(); - gtk_container_add(GTK_CONTAINER(w->window), w->overlay); - - GtkBuilder *builder = NULL; - if(gtklock->layout_path) builder = gtk_builder_new_from_file(gtklock->layout_path); - else builder = gtk_builder_new_from_resource("/gtklock/gtklock.ui"); + gtk_window_set_child(GTK_WINDOW(w->window), w->overlay); - gtk_builder_connect_signals(builder, w); + GtkBuilder *builder = gtk_builder_new(); + //gtk_builder_set_current_object(builder, (void*)w); + if(gtklock->layout_path) gtk_builder_add_from_file(builder, gtklock->layout_path, NULL); + else gtk_builder_add_from_resource(builder, "/gtklock/gtklock.ui", NULL); w->window_box = GTK_WIDGET(gtk_builder_get_object(builder, "window-box")); - gtk_container_add(GTK_CONTAINER(w->overlay), w->window_box); + //gtk_container_add(GTK_CONTAINER(w->overlay), w->window_box); + gtk_overlay_set_child(GTK_OVERLAY(w->overlay), w->window_box); w->body_revealer = GTK_WIDGET(gtk_builder_get_object(builder, "body-revealer")); w->body_grid = GTK_WIDGET(gtk_builder_get_object(builder, "body-grid")); w->input_label = GTK_WIDGET(gtk_builder_get_object(builder, "input-label")); w->input_field = GTK_WIDGET(gtk_builder_get_object(builder, "input-field")); - g_signal_connect(w->input_field, "button-press-event", G_CALLBACK(entry_button_press), NULL); + //g_signal_connect(w->input_field, "button-press-event", G_CALLBACK(entry_button_press), NULL); + g_signal_connect(w->input_field, "activate", G_CALLBACK(window_pw_check), (gpointer)(w)); + g_signal_connect(w->input_field, "icon-release", G_CALLBACK(window_pw_toggle_vis), NULL); w->message_revealer = GTK_WIDGET(gtk_builder_get_object(builder, "message-revealer")); w->message_scrolled_window = GTK_WIDGET(gtk_builder_get_object(builder, "message-scrolled-window")); w->message_box = GTK_WIDGET(gtk_builder_get_object(builder, "message-box")); w->unlock_button = GTK_WIDGET(gtk_builder_get_object(builder, "unlock-button")); + g_signal_connect(w->unlock_button, "clicked", G_CALLBACK(window_pw_check), (gpointer)w); w->error_label = GTK_WIDGET(gtk_builder_get_object(builder, "error-label")); w->warning_label = GTK_WIDGET(gtk_builder_get_object(builder, "warning-label")); @@ -365,11 +404,15 @@ struct Window *create_window(GdkMonitor *monitor) { w->date_label = GTK_WIDGET(gtk_builder_get_object(builder, "date-label")); window_update_date(w); + // we don't need to do this, the locker does it for us + + //gtk_window_present(GTK_WINDOW(w->window)); + if(gtklock->hidden) window_idle_hide(w); module_on_window_create(gtklock, w); - gtk_widget_show_all(w->window); g_object_unref(builder); + return w; } diff --git a/subprojects/gtk4-layer-shell.wrap b/subprojects/gtk4-layer-shell.wrap new file mode 100644 index 0000000..cdf82b5 --- /dev/null +++ b/subprojects/gtk4-layer-shell.wrap @@ -0,0 +1,7 @@ +[wrap-git] +directory = gtk4-layer-shell +url = git@github.com:wmww/gtk4-layer-shell.git +revision = 948622589fbfc8cb6bf1f436ba06592d5802e255 + +[provide] +dependency_names = gtk4-layer-shell