diff --git a/meson.build b/meson.build index 8e3f17c..efdb87b 100644 --- a/meson.build +++ b/meson.build @@ -1,6 +1,6 @@ project('diya-shell', ['c'], - version: '0.1.1', + version: '0.1.2', license: 'MIT', meson_version: '>=0.58.0', default_options: ['c_std=gnu11', 'warning_level=3']) @@ -39,7 +39,8 @@ wl_protocols = [ wl_protocol_dir / 'staging/ext-session-lock/ext-session-lock-v1', wl_protocol_dir / 'staging/ext-idle-notify/ext-idle-notify-v1', 'protocols/wlr-foreign-toplevel-management-unstable-v1', - 'protocols/virtual-keyboard-unstable-v1' + 'protocols/virtual-keyboard-unstable-v1', + 'protocols/wlr-output-power-management-unstable-v1', ] foreach proto : wl_protocols @@ -66,6 +67,7 @@ base = [ 'src/virtual-keyboard.c', 'src/widgets/virtual-keyboard-widgets.c', 'src/files-monitor.c', + 'src/idle.c', wayland_targets ] @@ -77,7 +79,6 @@ dm_src = [ 'src/foreign.c', 'src/session-lock.c', 'src/session.c', - 'src/idle.c', 'src/widgets/base-widgets.c', 'src/widgets/taskbar-widget.c', 'src/widgets/dashboard-widget.c', diff --git a/protocols/wlr-output-power-management-unstable-v1.xml b/protocols/wlr-output-power-management-unstable-v1.xml new file mode 100644 index 0000000..20dbb77 --- /dev/null +++ b/protocols/wlr-output-power-management-unstable-v1.xml @@ -0,0 +1,128 @@ + + + + Copyright © 2019 Purism SPC + + Permission is hereby granted, free of charge, to any person obtaining a + copy of this software and associated documentation files (the "Software"), + to deal in the Software without restriction, including without limitation + the rights to use, copy, modify, merge, publish, distribute, sublicense, + and/or sell copies of the Software, and to permit persons to whom the + Software is furnished to do so, subject to the following conditions: + + The above copyright notice and this permission notice (including the next + paragraph) shall be included in all copies or substantial portions of the + Software. + + THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + DEALINGS IN THE SOFTWARE. + + + + This protocol allows clients to control power management modes + of outputs that are currently part of the compositor space. The + intent is to allow special clients like desktop shells to power + down outputs when the system is idle. + + To modify outputs not currently part of the compositor space see + wlr-output-management. + + Warning! The protocol described in this file is experimental and + backward incompatible changes may be made. Backward compatible changes + may be added together with the corresponding interface version bump. + Backward incompatible changes are done by bumping the version number in + the protocol and interface names and resetting the interface version. + Once the protocol is to be declared stable, the 'z' prefix and the + version number in the protocol and interface names are removed and the + interface version number is reset. + + + + + This interface is a manager that allows creating per-output power + management mode controls. + + + + + Create an output power management mode control that can be used to + adjust the power management mode for a given output. + + + + + + + + All objects created by the manager will still remain valid, until their + appropriate destroy request has been called. + + + + + + + This object offers requests to set the power management mode of + an output. + + + + + + + + + + + + + + Set an output's power save mode to the given mode. The mode change + is effective immediately. If the output does not support the given + mode a failed event is sent. + + + + + + + Report the power management mode change of an output. + + The mode event is sent after an output changed its power + management mode. The reason can be a client using set_mode or the + compositor deciding to change an output's mode. + This event is also sent immediately when the object is created + so the client is informed about the current power management mode. + + + + + + + This event indicates that the output power management mode control + is no longer valid. This can happen for a number of reasons, + including: + - The output doesn't support power management + - Another client already has exclusive power management mode control + for this output + - The output disappeared + + Upon receiving this event, the client should destroy this object. + + + + + + Destroys the output power management mode control object. + + + + diff --git a/src/idle.c b/src/idle.c index a56d0f9..1806f4f 100644 --- a/src/idle.c +++ b/src/idle.c @@ -112,12 +112,6 @@ static const struct ext_idle_notification_v1_listener g_idle_listener_impl = .resumed = diya_resume }; -void diya_idle_manager_register(gpointer mngr, DiyaShell *shell) -{ - (void) mngr; - (void) shell; -} - DiyaIdleNotification* diya_shell_get_idle_notification(DiyaShell* shell, guint timeout_ms) { DiyaWayland *wayland = diya_shell_get_wayland(shell); @@ -135,7 +129,7 @@ DiyaIdleNotification* diya_shell_get_idle_notification(DiyaShell* shell, guint t } -guint diya_shell_notification_get_timeout(DiyaIdleNotification* self) +guint diya_idle_notification_get_timeout(DiyaIdleNotification* self) { return self->timeout; } \ No newline at end of file diff --git a/src/idle.h b/src/idle.h index 117d2cc..593e002 100644 --- a/src/idle.h +++ b/src/idle.h @@ -13,5 +13,5 @@ USE_CLASS(DiyaShell); void diya_idle_manager_register(gpointer mngr, DiyaShell *shell); DiyaIdleNotification* diya_shell_get_idle_notification(DiyaShell* shell, guint timeout_ms); -guint diya_shell_notification_get_timeout(DiyaIdleNotification* self); +guint diya_idle_notification_get_timeout(DiyaIdleNotification* self); #endif /* DIYAC_IDLE_H */ \ No newline at end of file diff --git a/src/input.c b/src/input.c index 4ab8ba2..99ade8d 100644 --- a/src/input.c +++ b/src/input.c @@ -237,6 +237,7 @@ DiyaInput *diya_input_new(DiyaShell *shell) DiyaWayland *wayland = diya_shell_get_wayland(shell); assert(wayland); struct wl_seat *seat = diya_wayland_get_seat(wayland); + assert(seat); wl_seat_add_listener(seat, &wl_seat_listener, self); return self; } diff --git a/src/login-shell.c b/src/login-shell.c index 3be0730..26891f6 100644 --- a/src/login-shell.c +++ b/src/login-shell.c @@ -296,6 +296,20 @@ static void on_monitor_changed(GListModel *monitor_lists, guint position, guint } } +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_startup(DiyaShell *shell) { DiyaLoginShell *self = DIYA_LOGIN_SHELL(shell); @@ -311,6 +325,8 @@ static void diya_login_shell_startup(DiyaShell *shell) 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); } static void diya_login_shell_class_init(DiyaLoginShellClass *class) diff --git a/src/session-shell.c b/src/session-shell.c index 408d5b8..494fd63 100644 --- a/src/session-shell.c +++ b/src/session-shell.c @@ -29,7 +29,6 @@ struct _DiyaSessionShell DiyaLauncher *launcher; GHashTable *windows; GtkSessionLockInstance *lock; - DiyaIdleNotification* idle_notif; }; G_DEFINE_FINAL_TYPE(DiyaSessionShell, diya_session_shell, DIYA_TYPE_SHELL) @@ -58,11 +57,6 @@ static void diya_session_shell_dispose(GObject *object) { g_object_unref(self->launcher); } - if (self->idle_notif) - { - g_object_unref(self->idle_notif); - self->idle_notif = NULL; - } G_OBJECT_CLASS(diya_session_shell_parent_class)->dispose(object); } @@ -142,18 +136,18 @@ static void diya_session_on_key_pressed(DiyaShell* shell, struct xkb_keymap *xkb */ } -static void diya_session_shell_idle(DiyaIdleNotification* notif, DiyaSessionShell* shell) +static void diya_session_on_shell_idle(DiyaShell* shell) { - assert(DIYA_IS_IDLE_NOTIFICATION(notif)); - assert(DIYA_IS_SESSION_SHELL(shell)); - g_debug("Shell IDLE"); + (void) shell; + g_debug("diya_session_on_shell_idle"); + diya_shell_power_display(shell, false); } -static void diya_session_shell_resume(DiyaIdleNotification* notif, DiyaSessionShell* shell) +static void diya_session_on_shell_resume(DiyaShell* shell) { - assert(DIYA_IS_IDLE_NOTIFICATION(notif)); - assert(DIYA_IS_SESSION_SHELL(shell)); - g_critical("Shell RESUME"); + (void) shell; + g_debug("diya_session_on_shell_resume"); + diya_shell_power_display(shell, true); } static void diya_session_shell_startup(DiyaShell *shell) @@ -162,15 +156,8 @@ static void diya_session_shell_startup(DiyaShell *shell) diya_session_shell_init_background(self); diya_session_shell_launcher_init(self); g_signal_connect(shell, DIYA_SIGNAL_SHELL_KEY_PRESSED, G_CALLBACK(diya_session_on_key_pressed), NULL); - - /** - * TODO: - * - read timeout from setting - * - implement widget that handle idle (turn off display + lock) - */ - self->idle_notif = diya_shell_get_idle_notification(shell, 5000); - g_signal_connect(self->idle_notif, DIYA_SIGNAL_IDLE_NOTIF_IDLE, G_CALLBACK(diya_session_shell_idle), self); - g_signal_connect(self->idle_notif, DIYA_SIGNAL_IDLE_NOTIF_RESUME, G_CALLBACK(diya_session_shell_resume), self); + g_signal_connect(shell, DIYA_SIGNAL_SHELL_IDLE, G_CALLBACK(diya_session_on_shell_idle), NULL); + g_signal_connect(shell, DIYA_SIGNAL_SHELL_RESUME, G_CALLBACK(diya_session_on_shell_resume), NULL); } static void diya_session_shell_active(DiyaShell *shell) @@ -185,7 +172,6 @@ static void diya_session_shell_class_init(DiyaSessionShellClass *class) DiyaShellClass *base_shell_class = DIYA_SHELL_CLASS(class); base_shell_class->foreign_register = diya_session_shell_foreign_toplevel_register; - base_shell_class->idle_notifier_register = diya_idle_manager_register; base_shell_class->startup_handle = diya_session_shell_startup; base_shell_class->active_handle = diya_session_shell_active; @@ -297,7 +283,6 @@ static void diya_session_shell_init(DiyaSessionShell *self) self->background = NULL; self->launcher = NULL; self->lock = gtk_session_lock_instance_new(); - self->idle_notif = NULL; 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); diff --git a/src/shell.c b/src/shell.c index 80ef655..9064ebc 100644 --- a/src/shell.c +++ b/src/shell.c @@ -4,6 +4,12 @@ #include "virtual-keyboard.h" #include "files-monior.h" #include "input.h" +#include "idle.h" +#include "wlr-output-power-management-unstable-v1.h" +#include +#include + +#define DEFAULT_IDLE_TIMEOUT 60*1000 // 1m #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)) @@ -14,6 +20,7 @@ enum PROP_SHELL_APP, PROP_SHELL_NAME, PROP_SHELL_THEME, + PROP_SHELL_IDLE_TO, N_PROPERTIES }; @@ -30,6 +37,7 @@ typedef struct _DiyaShellPrivate DiyaInput *input; DiyaFilesMonitor *files_watchdog; gchar *theme; + DiyaIdleNotification *idle_notif; } DiyaShellPrivate; G_DEFINE_TYPE_WITH_PRIVATE(DiyaShell, diya_shell, DIYA_TYPE_OBJECT); @@ -75,6 +83,11 @@ static void diya_shell_dispose(GObject *object) g_object_unref(priv->files_watchdog); priv->files_watchdog = NULL; } + if (priv->idle_notif) + { + g_object_unref(priv->idle_notif); + priv->idle_notif = NULL; + } G_OBJECT_CLASS(diya_shell_parent_class)->dispose(object); if (priv->app) { @@ -153,6 +166,18 @@ void on_diya_shell_theme_file_changed(GFileMonitor *monitor, GFile *file, GFile g_free(fpath); } +static void diya_shell_idle(DiyaIdleNotification *notif, DiyaShell *shell) +{ + assert(DIYA_IS_IDLE_NOTIFICATION(notif)); + g_signal_emit_by_name(shell, DIYA_SIGNAL_SHELL_IDLE); +} + +static void diya_shell_resume(DiyaIdleNotification *notif, DiyaShell *shell) +{ + assert(DIYA_IS_IDLE_NOTIFICATION(notif)); + g_signal_emit_by_name(shell, DIYA_SIGNAL_SHELL_RESUME); +} + static void on_gtk_app_startup(GtkApplication *app, void *data) { (void)app; @@ -171,8 +196,8 @@ static void on_gtk_app_startup(GtkApplication *app, void *data) gchar *dir = diya_shell_config_theme_dir(priv); diya_shell_watch_file(shell, dir, G_CALLBACK(on_diya_shell_theme_file_changed), (gpointer)shell); g_free(dir); - diya_shell_reload(shell); + diya_shell_reload(shell); if (class->startup_handle) { class->startup_handle(shell); @@ -190,6 +215,12 @@ static void on_gtk_app_active(GtkApplication *app, void *data) (void)app; DiyaShell *shell = data; DiyaShellClass *class = DIYA_SHELL_GET_CLASS(shell); + // DiyaShellPrivate *priv = diya_shell_get_instance_private(shell); + /** + * TODO: read timeout from setting + */ + g_object_set(shell, DIYA_PROP_SHELL_IDLE_TIMEOUT, DEFAULT_IDLE_TIMEOUT, NULL); + if (class->active_handle) { class->active_handle(shell); @@ -243,6 +274,15 @@ static void diya_shell_set_property(GObject *object, guint property_id, const GV priv->name = g_strdup(g_value_get_string(value)); init_gtk_application(self); break; + case PROP_SHELL_IDLE_TO: + if(priv->idle_notif) + { + g_object_unref(priv->idle_notif); + } + priv->idle_notif = diya_shell_get_idle_notification(self, g_value_get_uint(value)); + g_signal_connect(priv->idle_notif, DIYA_SIGNAL_IDLE_NOTIF_IDLE, G_CALLBACK(diya_shell_idle), self); + g_signal_connect(priv->idle_notif, DIYA_SIGNAL_IDLE_NOTIF_RESUME, G_CALLBACK(diya_shell_resume), self); + break; case PROP_SHELL_THEME: { const gchar *theme = g_value_get_string(value); @@ -281,6 +321,16 @@ 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_IDLE_TO: + if(priv->idle_notif) + { + g_value_set_uint(value, diya_idle_notification_get_timeout(priv->idle_notif)); + } + else + { + g_value_set_uint(value, 0); + } + break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; @@ -298,6 +348,7 @@ static void diya_shell_init(DiyaShell *self) priv->input = NULL; priv->files_watchdog = NULL; priv->theme = NULL; + priv->idle_notif = NULL; } DiyaWayland *diya_shell_get_wayland(DiyaShell *shell) @@ -338,7 +389,6 @@ static void diya_shell_class_init(DiyaShellClass *class) class->foreign_register = NULL; class->virtual_keyboard_register = diya_virtual_keyboard_register; - class->idle_notifier_register = NULL; class->monitor_changed_handle = NULL; class->startup_handle = NULL; class->active_handle = NULL; @@ -348,7 +398,7 @@ static void diya_shell_class_init(DiyaShellClass *class) shell_properties[PROP_SHELL_NAME] = g_param_spec_string(DIYA_PROP_SHELL_NAME, NULL, "Shell name", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); 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_APP] = g_param_spec_pointer(DIYA_PROP_SHELL_APPLICATION, NULL, "Shell application", G_PARAM_READABLE); + 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); g_object_class_install_properties(gobject_class, N_PROPERTIES, shell_properties); @@ -422,12 +472,34 @@ static void diya_shell_class_init(DiyaShellClass *class) G_TYPE_POINTER, G_TYPE_UINT, G_TYPE_UINT); + g_signal_new(DIYA_SIGNAL_SHELL_IDLE, + 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_RESUME, + 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) { - (void) application; - (void) user_data; + (void)application; + (void)user_data; #ifdef __SHELL_VERSION__ guint32 count; if (g_variant_dict_lookup(options, "version", "b", &count)) @@ -526,7 +598,6 @@ void diya_shell_monitor_input(DiyaShell *self) return; } priv->input = diya_input_new(self); - // TODO mapping signals } gboolean diya_shell_watch_file(DiyaShell *self, const gchar *file, GCallback callback, gpointer userdata) @@ -565,4 +636,27 @@ void diya_shell_launch(DiyaShell *self, GAppInfo *app) g_error_free(error); return; } +} + +void diya_shell_power_display(DiyaShell* self, gboolean mode) +{ + DiyaShellPrivate *priv = diya_shell_get_instance_private(self); + struct zwlr_output_power_manager_v1 * mngr = diya_wayland_get_output_mngr(priv->wayland); + if(!mngr) + { + g_warning("Output power manager protocol is not available"); + return; + } + GdkDisplay *display = gdk_display_get_default(); + GListModel *monitors = gdk_display_get_monitors(display); + guint n_monitors = g_list_model_get_n_items(monitors); + + for (guint i = 0; i < n_monitors; ++i) + { + GdkMonitor *monitor = g_list_model_get_item(monitors, i); + struct wl_output * output = gdk_wayland_monitor_get_wl_output(monitor); + struct zwlr_output_power_v1 * output_power = zwlr_output_power_manager_v1_get_output_power(mngr, output); + zwlr_output_power_v1_set_mode(output_power, mode? ZWLR_OUTPUT_POWER_V1_MODE_ON: ZWLR_OUTPUT_POWER_V1_MODE_OFF); + zwlr_output_power_v1_destroy(output_power); + } } \ No newline at end of file diff --git a/src/shell.h b/src/shell.h index 46a548a..60e4d54 100644 --- a/src/shell.h +++ b/src/shell.h @@ -11,6 +11,7 @@ #define DIYA_PROP_SHELL_NAME "name" #define DIYA_PROP_SHELL_APPLICATION "application" #define DIYA_PROP_SHELL_THEME "theme" +#define DIYA_PROP_SHELL_IDLE_TIMEOUT "idle-timeout" #define DIYA_SIGNAL_SHELL_KEYBOARD_ENTER "keyboard-enter" @@ -18,6 +19,8 @@ #define DIYA_SIGNAL_SHELL_KEY_PRESSED "key-pressed" #define DIYA_SIGNAL_SHELL_KEY_RELEASED "key-released" #define DIYA_SIGNAL_SHELL_KEYBOARD_MODIFIER_CHANGED "keyboard-modifier-changed" +#define DIYA_SIGNAL_SHELL_IDLE "idle" +#define DIYA_SIGNAL_SHELL_RESUME "resume" #define DIYA_TYPE_SHELL (diya_shell_get_type()) G_DECLARE_DERIVABLE_TYPE(DiyaShell, diya_shell, DIYA, SHELL, DiyaObject) @@ -31,7 +34,6 @@ struct _DiyaShellClass DiyaObjectClass parent_class; wl_protocol_manager_register_t foreign_register; wl_protocol_manager_register_t virtual_keyboard_register; - wl_protocol_manager_register_t idle_notifier_register; void (*monitor_changed_handle)(GListModel* /*list*/,guint /*position*/, guint /*removed*/,guint /*added*/, gpointer); void (*startup_handle)(DiyaShell*); void (*active_handle)(DiyaShell*); @@ -48,6 +50,7 @@ DiyaVirtualKeyboard* diya_shell_get_virtual_keyboard(DiyaShell* shell, const gch void diya_shell_monitor_input(DiyaShell* shell); gboolean diya_shell_watch_file(DiyaShell* shell, const gchar* file, GCallback callback, gpointer userdata); 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); int diya_shell_run(DiyaShell* shell, int argc, char **argv); diff --git a/src/wayland.c b/src/wayland.c index e2df76e..9fb97a1 100644 --- a/src/wayland.c +++ b/src/wayland.c @@ -4,6 +4,7 @@ #include "wlr-foreign-toplevel-management-unstable-v1.h" #include "virtual-keyboard-unstable-v1.h" #include "ext-idle-notify-v1.h" +#include "wlr-output-power-management-unstable-v1.h" #include "wayland.h" #include "shell.h" @@ -17,6 +18,7 @@ struct _DiyaWayland struct zwlr_foreign_toplevel_manager_v1 * foreign_toplevel_mngr; struct zwp_virtual_keyboard_manager_v1 * virtual_keyboard_mngr; struct ext_idle_notifier_v1 * idle_notifier_mngr; + struct zwlr_output_power_manager_v1 * zwlr_output_power_manager_v1; }; G_DEFINE_FINAL_TYPE(DiyaWayland, diya_wayland, DIYA_TYPE_SHELL_OBJECT) @@ -39,6 +41,11 @@ static void diya_wayland_finalize(GObject* object) ext_idle_notifier_v1_destroy(self->idle_notifier_mngr); self->idle_notifier_mngr = NULL; } + if(self->zwlr_output_power_manager_v1) + { + zwlr_output_power_manager_v1_destroy(self->zwlr_output_power_manager_v1); + self->zwlr_output_power_manager_v1 = NULL; + } g_debug("diya_wayland_finalize: %s", diya_object_to_string(object)); G_OBJECT_CLASS(diya_wayland_parent_class)->finalize(object); } @@ -59,6 +66,7 @@ static void diya_wayland_init(DiyaWayland * self) self->foreign_toplevel_mngr = NULL; self->virtual_keyboard_mngr = NULL; self->idle_notifier_mngr = NULL; + self->zwlr_output_power_manager_v1 = NULL; } static const gchar* diya_wayland_to_string(DiyaObject* object) @@ -92,14 +100,15 @@ static void handle_global(void *data, struct wl_registry *registry, uint32_t nam foreign_toplevel_register(registry,name); */ (void) version; - DiyaShell * shell = data; - DiyaShellClass * class = DIYA_SHELL_GET_CLASS(shell); - DiyaWayland * wayland; - g_object_get(shell, DIYA_PROP_SHELL_WAYLAND, &wayland, NULL); + DiyaWayland *wayland = data; + DiyaShell * shell = diya_shell_object_get_shell(data); + assert(DIYA_IS_WAYLAND(wayland)); - g_debug("WAYLAND GLOBAL: %s", interface); + assert(DIYA_IS_SHELL(shell)); - if (g_strcmp0(interface, zwlr_foreign_toplevel_manager_v1_interface.name) == 0) + DiyaShellClass * class = DIYA_SHELL_GET_CLASS(shell); + g_debug("WAYLAND GLOBAL: %s", interface); + if (!wayland->foreign_toplevel_mngr && g_strcmp0(interface, zwlr_foreign_toplevel_manager_v1_interface.name) == 0) { if(class->foreign_register) { @@ -109,7 +118,7 @@ static void handle_global(void *data, struct wl_registry *registry, uint32_t nam class->foreign_register(wayland->foreign_toplevel_mngr, shell); } } - if (g_strcmp0(interface, zwp_virtual_keyboard_manager_v1_interface.name) == 0) + if (!wayland->virtual_keyboard_mngr && g_strcmp0(interface, zwp_virtual_keyboard_manager_v1_interface.name) == 0) { if(class->virtual_keyboard_register) { @@ -125,26 +134,28 @@ static void handle_global(void *data, struct wl_registry *registry, uint32_t nam diya_session_shell_session_lock_register(registry, name); } */ - else if (g_strcmp0(interface, wl_compositor_interface.name) == 0) + else if (!wayland->compositor && g_strcmp0(interface, wl_compositor_interface.name) == 0) { wayland->compositor = wl_registry_bind(registry, name, &wl_compositor_interface, 4); } - else if (g_strcmp0(interface, wl_shm_interface.name) == 0) + else if (!wayland->shm && g_strcmp0(interface, wl_shm_interface.name) == 0) { wayland->shm = wl_registry_bind(registry, name, &wl_shm_interface, 1); } - else if (g_strcmp0(interface, wl_seat_interface.name) == 0) + else if (!wayland->seat && g_strcmp0(interface, wl_seat_interface.name) == 0) { wayland->seat = wl_registry_bind(registry, name, &wl_seat_interface, 7); } - else if(g_strcmp0(interface, ext_idle_notifier_v1_interface.name) == 0) + else if(!wayland->idle_notifier_mngr && g_strcmp0(interface, ext_idle_notifier_v1_interface.name) == 0) { - if(class->idle_notifier_register) - { - g_debug("Wayland: register ext_idle_notifier_v1_interface"); - wayland->idle_notifier_mngr = wl_registry_bind(registry, name, &ext_idle_notifier_v1_interface, 1);; - class->idle_notifier_register(wayland->idle_notifier_mngr, shell); - } + g_debug("Wayland: register ext_idle_notifier_v1_interface"); + wayland->idle_notifier_mngr = wl_registry_bind(registry, name, &ext_idle_notifier_v1_interface, 1);; + } + else if (!wayland->zwlr_output_power_manager_v1 && g_strcmp0(interface, zwlr_output_power_manager_v1_interface.name) == 0) + { + g_debug("Wayland: register zwlr_output_power_manager_v1_interface"); + wayland->zwlr_output_power_manager_v1 = wl_registry_bind(registry, name, &zwlr_output_power_manager_v1_interface, 1); + //class->power_manager_register(wayland->zwlr_output_power_manager_v1, shell); } } @@ -172,16 +183,15 @@ DiyaWayland* diya_wayland_new(DiyaShell *shell) return NULL; } DiyaWayland * wayland = g_object_new(DIYA_TYPE_WAYLAND, "shell", shell, NULL); - //g_object_set(wayland, "shell", shell, NULL); registry = wl_display_get_registry(display); - wl_registry_add_listener(registry, ®istry_listener, (void*)shell); + wl_registry_add_listener(registry, ®istry_listener, (void*)wayland); // wl_display_roundtrip(display); // wayland_monitor_probe(); // GdkMonitor *mon = wayland_monitor_get_default(); // g_info("default output: %s", (gchar *)g_object_get_data(G_OBJECT(mon), "xdg_name")); // wl_display_roundtrip(display); - // wl_display_roundtrip(display); + //wl_display_roundtrip(display); return wayland; } @@ -229,4 +239,9 @@ struct zwp_virtual_keyboard_manager_v1* diya_wayland_get_virtual_keyboard_mngr(D struct ext_idle_notifier_v1* diya_wayland_get_idle_mngr(DiyaWayland* self) { return self->idle_notifier_mngr; +} + +struct zwlr_output_power_manager_v1 * diya_wayland_get_output_mngr(DiyaWayland* self) +{ + return self->zwlr_output_power_manager_v1; } \ No newline at end of file diff --git a/src/wayland.h b/src/wayland.h index 9c0afd6..6c9f9e3 100644 --- a/src/wayland.h +++ b/src/wayland.h @@ -14,5 +14,6 @@ struct wl_shm_pool * diya_wayland_create_shm_pool(DiyaWayland * self, int fd, gu struct wl_seat* diya_wayland_get_seat(DiyaWayland* self); struct zwp_virtual_keyboard_manager_v1* diya_wayland_get_virtual_keyboard_mngr(DiyaWayland* self); struct ext_idle_notifier_v1* diya_wayland_get_idle_mngr(DiyaWayland* self); +struct zwlr_output_power_manager_v1 * diya_wayland_get_output_mngr(DiyaWayland* self); DiyaWayland* diya_wayland_new(DiyaShell *shell); #endif \ No newline at end of file