refactor resource + add taskbar application switcher
This commit is contained in:
parent
363d0d1678
commit
2a88d12bfa
@ -1,4 +1,4 @@
|
|||||||
@import url("resource:///dev/iohub/diya/shell/virtual-keyboard.css");
|
@import url("resource:///dev/iohub/diya/shell/css/virtual-keyboard.css");
|
||||||
|
|
||||||
#diya_login_shell
|
#diya_login_shell
|
||||||
{
|
{
|
@ -1,4 +1,4 @@
|
|||||||
@import url("resource:///dev/iohub/diya/shell/virtual-keyboard.css");
|
@import url("resource:///dev/iohub/diya/shell/css/virtual-keyboard.css");
|
||||||
|
|
||||||
diya-taskbar
|
diya-taskbar
|
||||||
{
|
{
|
@ -1,9 +1,10 @@
|
|||||||
<?xml version="1.0" encoding="UTF-8"?>
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
<gresources>
|
<gresources>
|
||||||
<gresource prefix="/dev/iohub/diya/shell">
|
<gresource prefix="/dev/iohub/diya/shell/css">
|
||||||
<file alias="dev.iohub.diya.login-shell.css">resources/login-shell.css</file>
|
<file alias="dev.iohub.diya.login-shell.css">resources/css/login-shell.css</file>
|
||||||
<file alias="virtual-keyboard.css">resources/virtual-keyboard.css</file>
|
<file alias="virtual-keyboard.css">resources/css/virtual-keyboard.css</file>
|
||||||
<file alias="default.keymap">resources/default.keymap</file>
|
</gresource>
|
||||||
<!--file alias="virtuail-keyboard.ui">resources/ui/virtual-keyboard.ui</file-->
|
<gresource prefix="/dev/iohub/diya/shell/vkb">
|
||||||
|
<file alias="default.keymap">resources/vkb/default.keymap</file>
|
||||||
</gresource>
|
</gresource>
|
||||||
</gresources>
|
</gresources>
|
@ -1,10 +1,17 @@
|
|||||||
<?xml version="1.0" encoding="UTF-8"?>
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
<gresources>
|
<gresources>
|
||||||
<gresource prefix="/dev/iohub/diya/shell">
|
<gresource prefix="/dev/iohub/diya/shell/vkb">
|
||||||
<file alias="dev.iohub.diya.session-shell.css">resources/session-shell.css</file>
|
<file alias="default.keymap">resources/vkb/default.keymap</file>
|
||||||
<file alias="virtual-keyboard.css">resources/virtual-keyboard.css</file>
|
</gresource>
|
||||||
<file alias="default.keymap">resources/default.keymap</file>
|
<gresource prefix="/dev/iohub/diya/shell/ui">
|
||||||
<file alias="dashboard.ui">resources/ui/dashboard.ui</file>
|
<file alias="dashboard.ui">resources/ui/dashboard.ui</file>
|
||||||
<file alias="taskbar.ui">resources/ui/taskbar.ui</file>
|
<file alias="taskbar.ui">resources/ui/taskbar.ui</file>
|
||||||
</gresource>
|
</gresource>
|
||||||
|
<gresource prefix="/dev/iohub/diya/shell/css">
|
||||||
|
<file alias="dev.iohub.diya.session-shell.css">resources/css/session-shell.css</file>
|
||||||
|
<file alias="virtual-keyboard.css">resources/css/virtual-keyboard.css</file>
|
||||||
|
</gresource>
|
||||||
|
<gresource prefix="/dev/iohub/diya/shell/icons/scalable">
|
||||||
|
<file alias="gear">resources/icons/scalable/gear.svg</file>
|
||||||
|
</gresource>
|
||||||
</gresources>
|
</gresources>
|
1
resources/icons/scalable/gear.svg
Normal file
1
resources/icons/scalable/gear.svg
Normal file
@ -0,0 +1 @@
|
|||||||
|
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 48 48" width="48px" height="48px"><linearGradient id="L4rKfs~Qrm~k0Pk8MRsoza" x1="32.012" x2="15.881" y1="32.012" y2="15.881" gradientUnits="userSpaceOnUse"><stop offset="0" stop-color="#fff"/><stop offset=".242" stop-color="#f2f2f2"/><stop offset="1" stop-color="#ccc"/></linearGradient><circle cx="24" cy="24" r="11.5" fill="url(#L4rKfs~Qrm~k0Pk8MRsoza)"/><linearGradient id="L4rKfs~Qrm~k0Pk8MRsozb" x1="17.45" x2="28.94" y1="17.45" y2="28.94" gradientUnits="userSpaceOnUse"><stop offset="0" stop-color="#0d61a9"/><stop offset=".363" stop-color="#0e5fa4"/><stop offset=".78" stop-color="#135796"/><stop offset="1" stop-color="#16528c"/></linearGradient><circle cx="24" cy="24" r="7" fill="url(#L4rKfs~Qrm~k0Pk8MRsozb)"/><linearGradient id="L4rKfs~Qrm~k0Pk8MRsozc" x1="5.326" x2="38.082" y1="5.344" y2="38.099" gradientUnits="userSpaceOnUse"><stop offset="0" stop-color="#889097"/><stop offset=".331" stop-color="#848c94"/><stop offset=".669" stop-color="#78828b"/><stop offset="1" stop-color="#64717c"/></linearGradient><path fill="url(#L4rKfs~Qrm~k0Pk8MRsozc)" d="M43.407,19.243c-2.389-0.029-4.702-1.274-5.983-3.493c-1.233-2.136-1.208-4.649-0.162-6.693 c-2.125-1.887-4.642-3.339-7.43-4.188C28.577,6.756,26.435,8,24,8s-4.577-1.244-5.831-3.131c-2.788,0.849-5.305,2.301-7.43,4.188 c1.046,2.044,1.071,4.557-0.162,6.693c-1.281,2.219-3.594,3.464-5.983,3.493C4.22,20.77,4,22.358,4,24 c0,1.284,0.133,2.535,0.364,3.752c2.469-0.051,4.891,1.208,6.213,3.498c1.368,2.37,1.187,5.204-0.22,7.345 c2.082,1.947,4.573,3.456,7.34,4.375C18.827,40.624,21.221,39,24,39s5.173,1.624,6.303,3.971c2.767-0.919,5.258-2.428,7.34-4.375 c-1.407-2.141-1.588-4.975-0.22-7.345c1.322-2.29,3.743-3.549,6.213-3.498C43.867,26.535,44,25.284,44,24 C44,22.358,43.78,20.77,43.407,19.243z M24,34.5c-5.799,0-10.5-4.701-10.5-10.5c0-5.799,4.701-10.5,10.5-10.5S34.5,18.201,34.5,24 C34.5,29.799,29.799,34.5,24,34.5z"/></svg>
|
After Width: | Height: | Size: 1.9 KiB |
@ -6,6 +6,7 @@
|
|||||||
<property name="default-height">400</property-->
|
<property name="default-height">400</property-->
|
||||||
<child>
|
<child>
|
||||||
<object class="GtkBox" id="taskbar">
|
<object class="GtkBox" id="taskbar">
|
||||||
|
<property name="hexpand">1</property>
|
||||||
<property name="orientation">horizontal</property>
|
<property name="orientation">horizontal</property>
|
||||||
<child>
|
<child>
|
||||||
<object class="GtkToggleButton" id="btn_toggle">
|
<object class="GtkToggleButton" id="btn_toggle">
|
||||||
@ -14,6 +15,19 @@
|
|||||||
<!--signal name="toggled" handler="diya_dashboard_toggle"/-->
|
<!--signal name="toggled" handler="diya_dashboard_toggle"/-->
|
||||||
</object>
|
</object>
|
||||||
</child>
|
</child>
|
||||||
|
|
||||||
|
<child>
|
||||||
|
<object class="GtkScrolledWindow">
|
||||||
|
<property name="hexpand">1</property>
|
||||||
|
<property name="vscrollbar-policy">never</property>
|
||||||
|
<child>
|
||||||
|
<object class="GtkListView" id="apps_list">
|
||||||
|
<property name="orientation">horizontal</property>
|
||||||
|
</object>
|
||||||
|
</child>
|
||||||
|
</object>
|
||||||
|
</child>
|
||||||
|
|
||||||
</object>
|
</object>
|
||||||
</child>
|
</child>
|
||||||
</template>
|
</template>
|
||||||
|
@ -184,6 +184,7 @@ static void toplevel_handle_app_id(void *data,
|
|||||||
assert(win);
|
assert(win);
|
||||||
g_object_set(win, "appid", app_id, NULL);
|
g_object_set(win, "appid", app_id, NULL);
|
||||||
g_debug("New appid for: %s", diya_object_to_string(win));
|
g_debug("New appid for: %s", diya_object_to_string(win));
|
||||||
|
g_signal_emit_by_name(shell, DIYA_SIGNAL_FOREIGN_WINDOW_ADDED, (void *)win);
|
||||||
}
|
}
|
||||||
static void toplevel_handle_output_enter(void *data,
|
static void toplevel_handle_output_enter(void *data,
|
||||||
struct zwlr_foreign_toplevel_handle_v1 *handle,
|
struct zwlr_foreign_toplevel_handle_v1 *handle,
|
||||||
@ -218,9 +219,10 @@ static void toplevel_handle_state(void *data,
|
|||||||
wstate |= DIYA_WIN_STATE_FOCUS;
|
wstate |= DIYA_WIN_STATE_FOCUS;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
g_debug("toplevel_handle_state: (%.04x) active: %d, full screen %d, maximize %d, minimize %d", wstate, wstate & DIYA_WIN_STATE_FOCUS,
|
g_debug("toplevel_handle_state %s: (%.04x) active: %d, full screen %d, maximize %d, minimize %d", diya_object_to_string(win), wstate, wstate & DIYA_WIN_STATE_FOCUS,
|
||||||
wstate & DIYA_WIN_STATE_FULLSCREEN, wstate & DIYA_WIN_STATE_MAXIMIZE, wstate & DIYA_WIN_STATE_MINIMIZE);
|
wstate & DIYA_WIN_STATE_FULLSCREEN, wstate & DIYA_WIN_STATE_MAXIMIZE, wstate & DIYA_WIN_STATE_MINIMIZE);
|
||||||
g_object_set(win, "state", wstate, NULL);
|
g_object_set(win, "state", wstate, NULL);
|
||||||
|
g_signal_emit_by_name(shell, DIYA_SIGNAL_FOREIGN_WINDOW_STATE_CHANGED, (void *)win, (guint)wstate);
|
||||||
}
|
}
|
||||||
static void toplevel_handle_done(void *data,
|
static void toplevel_handle_done(void *data,
|
||||||
struct zwlr_foreign_toplevel_handle_v1 *handle)
|
struct zwlr_foreign_toplevel_handle_v1 *handle)
|
||||||
@ -229,6 +231,7 @@ static void toplevel_handle_done(void *data,
|
|||||||
assert(shell);
|
assert(shell);
|
||||||
DiyaForeignWindow *win = diya_session_shell_get_window(shell, handle);
|
DiyaForeignWindow *win = diya_session_shell_get_window(shell, handle);
|
||||||
assert(win);
|
assert(win);
|
||||||
|
g_debug("toplevel_handle_done: finish");
|
||||||
g_signal_emit_by_name(shell, DIYA_SIGNAL_FOREIGN_WINDOW_CHANGED, (void *)win);
|
g_signal_emit_by_name(shell, DIYA_SIGNAL_FOREIGN_WINDOW_CHANGED, (void *)win);
|
||||||
}
|
}
|
||||||
static void toplevel_handle_closed(void *data,
|
static void toplevel_handle_closed(void *data,
|
||||||
@ -335,6 +338,9 @@ DiyaShell* diya_foreign_window_get_shell(DiyaForeignWindow* self)
|
|||||||
}
|
}
|
||||||
void diya_foreign_window_set_state(DiyaForeignWindow* self, enum diya_win_state state, bool value)
|
void diya_foreign_window_set_state(DiyaForeignWindow* self, enum diya_win_state state, bool value)
|
||||||
{
|
{
|
||||||
|
DiyaShell* shell = diya_foreign_window_get_shell(self);
|
||||||
|
DiyaWayland* wl = diya_shell_get_wayland(shell);
|
||||||
|
assert(wl);
|
||||||
if(state & DIYA_WIN_STATE_MINIMIZE)
|
if(state & DIYA_WIN_STATE_MINIMIZE)
|
||||||
{
|
{
|
||||||
if(value)
|
if(value)
|
||||||
@ -361,9 +367,6 @@ void diya_foreign_window_set_state(DiyaForeignWindow* self, enum diya_win_state
|
|||||||
|
|
||||||
if(state & DIYA_WIN_STATE_FULLSCREEN)
|
if(state & DIYA_WIN_STATE_FULLSCREEN)
|
||||||
{
|
{
|
||||||
DiyaShell* shell = diya_foreign_window_get_shell(self);
|
|
||||||
DiyaWayland* wl = diya_shell_get_wayland(shell);
|
|
||||||
assert(wl);
|
|
||||||
struct wl_output* output = diya_wayland_get_output(wl, 0);
|
struct wl_output* output = diya_wayland_get_output(wl, 0);
|
||||||
if(value)
|
if(value)
|
||||||
{
|
{
|
||||||
@ -374,9 +377,56 @@ void diya_foreign_window_set_state(DiyaForeignWindow* self, enum diya_win_state
|
|||||||
zwlr_foreign_toplevel_handle_v1_unset_fullscreen(self->handle);
|
zwlr_foreign_toplevel_handle_v1_unset_fullscreen(self->handle);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if(state & DIYA_WIN_STATE_FOCUS)
|
||||||
|
{
|
||||||
|
if(value)
|
||||||
|
{
|
||||||
|
struct wl_seat* seat = diya_wayland_get_seat(wl);
|
||||||
|
zwlr_foreign_toplevel_handle_v1_activate(self->handle, seat);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
bool diya_foreign_window_is_toplevel(DiyaForeignWindow* self)
|
bool diya_foreign_window_is_toplevel(DiyaForeignWindow* self)
|
||||||
{
|
{
|
||||||
return self->parent_win == NULL;
|
return self->parent_win == NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static gint app_info_str_cmp(GAppInfo* info, const char* id)
|
||||||
|
{
|
||||||
|
return g_strcmp0(g_app_info_get_executable(info), id);
|
||||||
|
}
|
||||||
|
|
||||||
|
GAppInfo* diya_foreign_window_get_app_info(DiyaForeignWindow* self)
|
||||||
|
{
|
||||||
|
if(! self->appid)
|
||||||
|
{
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
GList* apps = g_app_info_get_all();
|
||||||
|
GList* found = g_list_find_custom(apps, self->appid, (GCompareFunc)app_info_str_cmp);
|
||||||
|
GAppInfo* info = NULL;
|
||||||
|
if(found && found->data)
|
||||||
|
{
|
||||||
|
assert(G_IS_APP_INFO(found->data));
|
||||||
|
info = g_object_ref(found->data);
|
||||||
|
}
|
||||||
|
g_list_free_full(apps, g_object_unref);
|
||||||
|
return info;
|
||||||
|
}
|
||||||
|
|
||||||
|
enum diya_win_state diya_foreign_window_get_state(DiyaForeignWindow* window)
|
||||||
|
{
|
||||||
|
return window->state;
|
||||||
|
}
|
||||||
|
|
||||||
|
DiyaForeignWindow* diya_foreign_window_get_top_level(DiyaForeignWindow* self)
|
||||||
|
{
|
||||||
|
DiyaForeignWindow* win = self;
|
||||||
|
while(win->parent_win)
|
||||||
|
{
|
||||||
|
win = win->parent_win;
|
||||||
|
}
|
||||||
|
return win;
|
||||||
|
}
|
@ -22,5 +22,8 @@ void diya_session_shell_foreign_toplevel_register(struct wl_registry *registry,
|
|||||||
DiyaShell* diya_foreign_window_get_shell(DiyaForeignWindow* window);
|
DiyaShell* diya_foreign_window_get_shell(DiyaForeignWindow* window);
|
||||||
|
|
||||||
void diya_foreign_window_set_state(DiyaForeignWindow* window, enum diya_win_state state, bool value);
|
void diya_foreign_window_set_state(DiyaForeignWindow* window, enum diya_win_state state, bool value);
|
||||||
|
enum diya_win_state diya_foreign_window_get_state(DiyaForeignWindow* window);
|
||||||
bool diya_foreign_window_is_toplevel(DiyaForeignWindow* window);
|
bool diya_foreign_window_is_toplevel(DiyaForeignWindow* window);
|
||||||
|
DiyaForeignWindow* diya_foreign_window_get_top_level(DiyaForeignWindow* window);
|
||||||
|
GAppInfo* diya_foreign_window_get_app_info(DiyaForeignWindow* window);
|
||||||
#endif
|
#endif
|
@ -25,24 +25,7 @@ enum
|
|||||||
|
|
||||||
static GParamSpec *g_prop[N_PROPERTIES] = {0};
|
static GParamSpec *g_prop[N_PROPERTIES] = {0};
|
||||||
|
|
||||||
|
/*
|
||||||
static void on_foreign_window_change(DiyaSessionShell* shell, DiyaForeignWindow * win, gpointer data)
|
|
||||||
{
|
|
||||||
(void) data;
|
|
||||||
assert(win);
|
|
||||||
assert(shell);
|
|
||||||
g_warning("on_foreign_window_change: WINDOW CHANGE %s, shell %s", diya_object_to_string(DIYA_OBJECT(win)), diya_object_to_string(DIYA_OBJECT(shell)));
|
|
||||||
}
|
|
||||||
|
|
||||||
static void on_foreign_window_removed(DiyaSessionShell* shell, DiyaForeignWindow * win, gpointer data)
|
|
||||||
{
|
|
||||||
(void) data;
|
|
||||||
assert(win);
|
|
||||||
assert(shell);
|
|
||||||
g_warning("on_foreign_window_removed: WINDOW REMOVED %s, shell %s", diya_object_to_string(DIYA_OBJECT(win)), diya_object_to_string(DIYA_OBJECT(shell)));
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
static void show_windows(GtkWidget *widget,gpointer data)
|
static void show_windows(GtkWidget *widget,gpointer data)
|
||||||
{
|
{
|
||||||
(void) widget;
|
(void) widget;
|
||||||
@ -63,6 +46,7 @@ static void show_windows(GtkWidget *widget,gpointer data)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
static void diya_launcher_dispose(GObject* object)
|
static void diya_launcher_dispose(GObject* object)
|
||||||
{
|
{
|
||||||
@ -158,46 +142,15 @@ void diya_session_shell_launcher_init(DiyaSessionShell * shell)
|
|||||||
g_object_set(shell, "launchpad", self, NULL);
|
g_object_set(shell, "launchpad", self, NULL);
|
||||||
//g_signal_connect (GTK_WINDOW(dashboard), "destroy", G_CALLBACK (on_launcher_destroy), NULL);
|
//g_signal_connect (GTK_WINDOW(dashboard), "destroy", G_CALLBACK (on_launcher_destroy), NULL);
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
GtkWidget *box = gtk_box_new (GTK_ORIENTATION_HORIZONTAL, 5);
|
|
||||||
gtk_box_set_homogeneous (GTK_BOX (box), TRUE);
|
|
||||||
gtk_window_set_child (GTK_WINDOW (gtk_window), box);
|
|
||||||
gtk_widget_set_halign (box, GTK_ALIGN_CENTER);
|
|
||||||
gtk_widget_set_valign (box, GTK_ALIGN_CENTER);
|
|
||||||
GtkWidget * button = gtk_button_new_with_label ("lock");
|
|
||||||
g_signal_connect (button, "clicked", G_CALLBACK (session_lock), shell);
|
|
||||||
gtk_box_append (GTK_BOX (box), button);
|
|
||||||
|
|
||||||
button = gtk_button_new_with_label ("show all windows");
|
|
||||||
g_signal_connect (button, "clicked", G_CALLBACK (show_windows), shell);
|
|
||||||
gtk_box_append (GTK_BOX (box), button);
|
|
||||||
|
|
||||||
button = gtk_button_new_with_label ("Dashboard");
|
|
||||||
g_signal_connect (button, "clicked", G_CALLBACK (show_dashboard), shell);
|
|
||||||
gtk_box_append (GTK_BOX (box), button);
|
|
||||||
|
|
||||||
//g_signal_connect (gtk_window, "orientation-changed", G_CALLBACK (on_orientation_changed), NULL);
|
|
||||||
*/
|
|
||||||
|
|
||||||
gtk_window_present (GTK_WINDOW (taskbar));
|
gtk_window_present (GTK_WINDOW (taskbar));
|
||||||
|
|
||||||
g_signal_connect (shell, DIYA_SIGNAL_FOREIGN_WINDOW_CHANGED, G_CALLBACK (on_foreign_window_change), NULL);
|
GtkIconTheme* theme = gtk_icon_theme_get_for_display(gdk_display_get_default());
|
||||||
g_signal_connect (shell, DIYA_SIGNAL_FOREIGN_WINDOW_REMOVED, G_CALLBACK (on_foreign_window_removed), NULL);
|
char**icons = gtk_icon_theme_get_icon_names (theme);
|
||||||
|
g_warning("List all icons");
|
||||||
GList *apps = g_app_info_get_all ();
|
for(int i = 0; icons[i] != NULL; i++)
|
||||||
GList * l;
|
|
||||||
for (l = apps; l != NULL; l = l->next)
|
|
||||||
{
|
{
|
||||||
gpointer element_data = l->data;
|
g_debug("ICON: %s", icons[i]);
|
||||||
|
|
||||||
g_warning("%s", g_app_info_get_display_name(element_data));
|
|
||||||
g_warning("%s", g_app_info_get_id(element_data));
|
|
||||||
g_warning("%s", g_app_info_get_name(element_data));
|
|
||||||
g_warning("%s", g_app_info_get_executable(element_data));
|
|
||||||
//g_warning("%s", g_app_info_get_icon(element_data));
|
|
||||||
}
|
}
|
||||||
g_list_free_full(apps, g_object_unref);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void diya_launcher_show_dashboard(DiyaLauncher* self, gboolean value)
|
void diya_launcher_show_dashboard(DiyaLauncher* self, gboolean value)
|
||||||
|
@ -183,6 +183,31 @@ static void diya_session_shell_class_init(DiyaSessionShellClass *class)
|
|||||||
G_TYPE_NONE,
|
G_TYPE_NONE,
|
||||||
1,
|
1,
|
||||||
G_TYPE_POINTER);
|
G_TYPE_POINTER);
|
||||||
|
g_signal_new(DIYA_SIGNAL_FOREIGN_WINDOW_STATE_CHANGED,
|
||||||
|
DIYA_TYPE_SESSION_SHELL,
|
||||||
|
G_SIGNAL_DETAILED |
|
||||||
|
G_SIGNAL_ACTION |
|
||||||
|
G_SIGNAL_RUN_FIRST,
|
||||||
|
0,
|
||||||
|
NULL,
|
||||||
|
NULL,
|
||||||
|
NULL,
|
||||||
|
G_TYPE_NONE,
|
||||||
|
2,
|
||||||
|
G_TYPE_POINTER,
|
||||||
|
G_TYPE_UINT);
|
||||||
|
g_signal_new(DIYA_SIGNAL_FOREIGN_WINDOW_ADDED,
|
||||||
|
DIYA_TYPE_SESSION_SHELL,
|
||||||
|
G_SIGNAL_DETAILED |
|
||||||
|
G_SIGNAL_ACTION |
|
||||||
|
G_SIGNAL_RUN_FIRST,
|
||||||
|
0,
|
||||||
|
NULL,
|
||||||
|
NULL,
|
||||||
|
NULL,
|
||||||
|
G_TYPE_NONE,
|
||||||
|
1,
|
||||||
|
G_TYPE_POINTER);
|
||||||
g_signal_new(DIYA_SIGNAL_FOREIGN_WINDOW_REMOVED,
|
g_signal_new(DIYA_SIGNAL_FOREIGN_WINDOW_REMOVED,
|
||||||
DIYA_TYPE_SESSION_SHELL,
|
DIYA_TYPE_SESSION_SHELL,
|
||||||
G_SIGNAL_DETAILED |
|
G_SIGNAL_DETAILED |
|
||||||
|
@ -6,6 +6,8 @@
|
|||||||
#include "base.h"
|
#include "base.h"
|
||||||
|
|
||||||
#define DIYA_SIGNAL_FOREIGN_WINDOW_CHANGED "foreign-window-changed"
|
#define DIYA_SIGNAL_FOREIGN_WINDOW_CHANGED "foreign-window-changed"
|
||||||
|
#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_FOREIGN_WINDOW_REMOVED "foreign-window-removed"
|
||||||
#define DIYA_SIGNAL_SESSION_LOCKED "session-locked"
|
#define DIYA_SIGNAL_SESSION_LOCKED "session-locked"
|
||||||
#define DIYA_SIGNAL_SESSION_UNLOCKED "session-unlocked"
|
#define DIYA_SIGNAL_SESSION_UNLOCKED "session-unlocked"
|
||||||
|
@ -105,7 +105,7 @@ static void diya_shell_reload_theme(DiyaShell *shell)
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
g_warning("diya_shell_reload_theme: Unable to load CSS from file: %s. Fallback to default theme", css_file);
|
g_warning("diya_shell_reload_theme: Unable to load CSS from file: %s. Fallback to default theme", css_file);
|
||||||
gchar* css_resource = g_strconcat("/dev/iohub/diya/shell/", priv->name, ".css", NULL);
|
gchar* css_resource = g_strconcat("/dev/iohub/diya/shell/css/", priv->name, ".css", NULL);
|
||||||
gtk_css_provider_load_from_resource(priv->css_provider, css_resource);
|
gtk_css_provider_load_from_resource(priv->css_provider, css_resource);
|
||||||
g_free(css_resource);
|
g_free(css_resource);
|
||||||
}
|
}
|
||||||
|
@ -326,7 +326,7 @@ DiyaVirtualKeyboard *diya_virtual_keyboard_new(DiyaShell *shell, const gchar *ke
|
|||||||
{
|
{
|
||||||
GError *error = NULL;
|
GError *error = NULL;
|
||||||
g_warning("No keymap file specified. Loading default keymap from resource");
|
g_warning("No keymap file specified. Loading default keymap from resource");
|
||||||
GBytes *bytes = g_resources_lookup_data("/dev/iohub/diya/shell/default.keymap", 0, &error);
|
GBytes *bytes = g_resources_lookup_data("/dev/iohub/diya/shell/vkb/default.keymap", 0, &error);
|
||||||
if (error != NULL)
|
if (error != NULL)
|
||||||
{
|
{
|
||||||
g_critical("Unable to read keymap file from resource %s", error->message);
|
g_critical("Unable to read keymap file from resource %s", error->message);
|
||||||
|
@ -19,6 +19,14 @@ static guint diya_dashboard_list_model_get_n_items(GListModel *list)
|
|||||||
static gpointer diya_dashboard_list_model_get_item(GListModel *list, guint position)
|
static gpointer diya_dashboard_list_model_get_item(GListModel *list, guint position)
|
||||||
{
|
{
|
||||||
DiyaDashboardListModel *self = DIYA_DASHBOARD_LIST_MODEL(list);
|
DiyaDashboardListModel *self = DIYA_DASHBOARD_LIST_MODEL(list);
|
||||||
|
if(self->appinfos == NULL)
|
||||||
|
{
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
if(position >= g_list_length(self->appinfos))
|
||||||
|
{
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
return g_object_ref(g_list_nth_data(self->appinfos, position));
|
return g_object_ref(g_list_nth_data(self->appinfos, position));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -71,7 +79,7 @@ void diya_dashboard_list_model_append(DiyaDashboardListModel *self, GAppInfo *in
|
|||||||
g_list_model_items_changed(G_LIST_MODEL(self), g_list_length(self->appinfos) - 1, 0, 1);
|
g_list_model_items_changed(G_LIST_MODEL(self), g_list_length(self->appinfos) - 1, 0, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
static gint diya_dashboard_app_info_cmd(GAppInfo *a, GAppInfo *b)
|
static gint diya_dashboard_app_info_cmp(GAppInfo *a, GAppInfo *b)
|
||||||
{
|
{
|
||||||
return !g_app_info_equal(a, b);
|
return !g_app_info_equal(a, b);
|
||||||
}
|
}
|
||||||
@ -79,7 +87,7 @@ static gint diya_dashboard_app_info_cmd(GAppInfo *a, GAppInfo *b)
|
|||||||
gboolean diya_dashboard_list_model_contain(DiyaDashboardListModel *self, GAppInfo *info)
|
gboolean diya_dashboard_list_model_contain(DiyaDashboardListModel *self, GAppInfo *info)
|
||||||
{
|
{
|
||||||
GList *found = NULL;
|
GList *found = NULL;
|
||||||
found = g_list_find_custom(self->appinfos, info, (GCompareFunc)diya_dashboard_app_info_cmd);
|
found = g_list_find_custom(self->appinfos, info, (GCompareFunc)diya_dashboard_app_info_cmp);
|
||||||
return found != NULL;
|
return found != NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -163,11 +171,11 @@ static GtkWidget *diya_dashboard_create_app_icon_widget(void *item, void *user_d
|
|||||||
return widget;
|
return widget;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int diya_dashboard_app_info_cmp(GAppInfo *a, GAppInfo *b, gpointer user_data)
|
static int diya_dashboard_app_info_sort_cmp(GAppInfo *a, GAppInfo *b, gpointer user_data)
|
||||||
{
|
{
|
||||||
(void)user_data; // Unused parameter
|
(void)user_data; // Unused parameter
|
||||||
const gchar *name_a = g_app_info_get_id(a);
|
const gchar *name_a = g_app_info_get_display_name(a);
|
||||||
const gchar *name_b = g_app_info_get_id(b);
|
const gchar *name_b = g_app_info_get_display_name(b);
|
||||||
return g_strcmp0(name_a, name_b);
|
return g_strcmp0(name_a, name_b);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -229,7 +237,7 @@ static void diya_dashboard_widget_init(DiyaDashboardWidget *self)
|
|||||||
// g_signal_connect(event_controller, "key-pressed", G_CALLBACK(on_diya_dashboard_key_press), self);
|
// g_signal_connect(event_controller, "key-pressed", G_CALLBACK(on_diya_dashboard_key_press), self);
|
||||||
// gtk_widget_add_controller(GTK_WIDGET(self), event_controller);
|
// gtk_widget_add_controller(GTK_WIDGET(self), event_controller);
|
||||||
self->list_model = g_object_new(DIYA_TYPE_DASHBOARD_LIST_MODEL, NULL);
|
self->list_model = g_object_new(DIYA_TYPE_DASHBOARD_LIST_MODEL, NULL);
|
||||||
self->sorter = GTK_SORTER(gtk_custom_sorter_new((GCompareDataFunc)diya_dashboard_app_info_cmp, NULL, NULL));
|
self->sorter = GTK_SORTER(gtk_custom_sorter_new((GCompareDataFunc)diya_dashboard_app_info_sort_cmp, NULL, NULL));
|
||||||
self->sort_model = gtk_sort_list_model_new(G_LIST_MODEL(self->list_model), self->sorter);
|
self->sort_model = gtk_sort_list_model_new(G_LIST_MODEL(self->list_model), self->sorter);
|
||||||
self->filter = GTK_FILTER(gtk_custom_filter_new((GtkCustomFilterFunc)diya_app_info_filter_func, self, NULL));
|
self->filter = GTK_FILTER(gtk_custom_filter_new((GtkCustomFilterFunc)diya_app_info_filter_func, self, NULL));
|
||||||
self->proxy_model = gtk_filter_list_model_new(G_LIST_MODEL(self->sort_model), self->filter);
|
self->proxy_model = gtk_filter_list_model_new(G_LIST_MODEL(self->sort_model), self->filter);
|
||||||
@ -322,7 +330,7 @@ static void diya_dashboard_widget_class_init(DiyaDashboardWidgetClass *class)
|
|||||||
// DiyaShellWindowClass* base_class = DIYA_SHELL_WINDOW_CLASS(class);
|
// DiyaShellWindowClass* base_class = DIYA_SHELL_WINDOW_CLASS(class);
|
||||||
// base_class->setup = diya_dashboard_widget_setup;
|
// base_class->setup = diya_dashboard_widget_setup;
|
||||||
|
|
||||||
gtk_widget_class_set_template_from_resource(GTK_WIDGET_CLASS(class), "/dev/iohub/diya/shell/dashboard.ui");
|
gtk_widget_class_set_template_from_resource(GTK_WIDGET_CLASS(class), "/dev/iohub/diya/shell/ui/dashboard.ui");
|
||||||
gtk_widget_class_bind_template_child(GTK_WIDGET_CLASS(class), DiyaDashboardWidget, revealer);
|
gtk_widget_class_bind_template_child(GTK_WIDGET_CLASS(class), DiyaDashboardWidget, revealer);
|
||||||
gtk_widget_class_bind_template_child(GTK_WIDGET_CLASS(class), DiyaDashboardWidget, search_entry);
|
gtk_widget_class_bind_template_child(GTK_WIDGET_CLASS(class), DiyaDashboardWidget, search_entry);
|
||||||
gtk_widget_class_bind_template_child(GTK_WIDGET_CLASS(class), DiyaDashboardWidget, app_list_box);
|
gtk_widget_class_bind_template_child(GTK_WIDGET_CLASS(class), DiyaDashboardWidget, app_list_box);
|
||||||
|
@ -1,11 +1,121 @@
|
|||||||
#include "taskbar-widget.h"
|
#include "taskbar-widget.h"
|
||||||
|
#include "foreign.h"
|
||||||
|
|
||||||
|
#define DEFAULT_APP_ICON_NAME "application-x-executable-symbolic"
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Implementation of list model
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
struct _DiyaTaskbarListModel
|
||||||
|
{
|
||||||
|
GObject parent_instance;
|
||||||
|
GList *apps;
|
||||||
|
};
|
||||||
|
|
||||||
|
static guint diya_taskbar_list_model_get_n_items(GListModel *list)
|
||||||
|
{
|
||||||
|
DiyaTaskbarListModel *self = DIYA_TASKBAR_LIST_MODEL(list);
|
||||||
|
return g_list_length(self->apps);
|
||||||
|
}
|
||||||
|
|
||||||
|
static gpointer diya_taskbar_list_model_get_item(GListModel *list, guint position)
|
||||||
|
{
|
||||||
|
DiyaTaskbarListModel *self = DIYA_TASKBAR_LIST_MODEL(list);
|
||||||
|
if(self->apps == NULL)
|
||||||
|
{
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
if(position >= g_list_length(self->apps))
|
||||||
|
{
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
return g_object_ref(g_list_nth_data(self->apps, position));
|
||||||
|
}
|
||||||
|
|
||||||
|
static GType diya_taskbar_list_model_get_item_type(GListModel *list)
|
||||||
|
{
|
||||||
|
(void)list; // Unused parameter
|
||||||
|
return DIYA_TYPE_FOREIGN_WINDOW;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void diya_taskbar_list_model_interface_init(GListModelInterface *iface)
|
||||||
|
{
|
||||||
|
iface->get_n_items = diya_taskbar_list_model_get_n_items;
|
||||||
|
iface->get_item = diya_taskbar_list_model_get_item;
|
||||||
|
iface->get_item_type = diya_taskbar_list_model_get_item_type;
|
||||||
|
}
|
||||||
|
|
||||||
|
G_DEFINE_TYPE_WITH_CODE(DiyaTaskbarListModel, diya_taskbar_list_model, G_TYPE_OBJECT, G_IMPLEMENT_INTERFACE(G_TYPE_LIST_MODEL, diya_taskbar_list_model_interface_init))
|
||||||
|
|
||||||
|
static void diya_taskbar_list_model_finalize(GObject *object)
|
||||||
|
{
|
||||||
|
g_debug("diya_taskbar_list_model_finalize");
|
||||||
|
DiyaTaskbarListModel *self = DIYA_TASKBAR_LIST_MODEL(object);
|
||||||
|
g_list_free_full(self->apps, g_object_unref);
|
||||||
|
G_OBJECT_CLASS(diya_taskbar_list_model_parent_class)->finalize(object);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void diya_taskbar_list_model_dispose(GObject *object)
|
||||||
|
{
|
||||||
|
(void)object;
|
||||||
|
g_debug("diya_taskbar_list_model_dispose");
|
||||||
|
G_OBJECT_CLASS(diya_taskbar_list_model_parent_class)->dispose(object);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void diya_taskbar_list_model_init(DiyaTaskbarListModel *self)
|
||||||
|
{
|
||||||
|
self->apps = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void diya_taskbar_list_model_class_init(DiyaTaskbarListModelClass *class)
|
||||||
|
{
|
||||||
|
GObjectClass *gobject_class = G_OBJECT_CLASS(class);
|
||||||
|
gobject_class->finalize = diya_taskbar_list_model_finalize;
|
||||||
|
gobject_class->dispose = diya_taskbar_list_model_dispose;
|
||||||
|
}
|
||||||
|
|
||||||
|
void diya_taskbar_list_model_append(DiyaTaskbarListModel *self, DiyaForeignWindow *window)
|
||||||
|
{
|
||||||
|
self->apps = g_list_append(self->apps, g_object_ref(window));
|
||||||
|
// self->appinfos = g_list_reverse(self->appinfos);
|
||||||
|
g_list_model_items_changed(G_LIST_MODEL(self), g_list_length(self->apps) - 1, 0, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
void diya_taskbar_list_model_remove(DiyaTaskbarListModel *self, DiyaForeignWindow *window)
|
||||||
|
{
|
||||||
|
gint index = g_list_index(self->apps, window);
|
||||||
|
if (index < 0)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
self->apps = g_list_remove(self->apps, window);
|
||||||
|
g_object_unref(window);
|
||||||
|
g_list_model_items_changed(G_LIST_MODEL(self), index, 1, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
gboolean diya_taskbar_list_model_contain(DiyaTaskbarListModel *self, DiyaForeignWindow *info)
|
||||||
|
{
|
||||||
|
GList *found = NULL;
|
||||||
|
found = g_list_find(self->apps, info);
|
||||||
|
return found != NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Implement of taskbar widget
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
struct _DiyaTaskbarWidget
|
struct _DiyaTaskbarWidget
|
||||||
{
|
{
|
||||||
DiyaShellWindow parent;
|
DiyaShellWindow parent;
|
||||||
GtkWidget *btn_toggle;
|
GtkWidget *btn_toggle;
|
||||||
bool active_dashboard;
|
bool active_dashboard;
|
||||||
|
GtkWidget *apps_list;
|
||||||
|
GtkSingleSelection *proxy_model;
|
||||||
|
DiyaTaskbarListModel *model;
|
||||||
|
GtkListItemFactory *factory;
|
||||||
|
guint selection_changed_sig_id;
|
||||||
};
|
};
|
||||||
|
|
||||||
enum
|
enum
|
||||||
@ -17,52 +127,216 @@ enum
|
|||||||
|
|
||||||
static GParamSpec *g_prop[N_PROPERTIES] = {0};
|
static GParamSpec *g_prop[N_PROPERTIES] = {0};
|
||||||
|
|
||||||
|
G_DEFINE_TYPE(DiyaTaskbarWidget, diya_taskbar_widget, DIYA_TYPE_SHELL_WINDOW)
|
||||||
|
|
||||||
G_DEFINE_TYPE (DiyaTaskbarWidget, diya_taskbar_widget, DIYA_TYPE_SHELL_WINDOW)
|
static void diya_taskbar_widget_dispose(GObject *object)
|
||||||
|
|
||||||
static void diya_taskbar_widget_dispose(GObject* object)
|
|
||||||
{
|
{
|
||||||
(void) object;
|
DiyaTaskbarWidget *self = DIYA_TASKBAR_WIDGET(object);
|
||||||
g_debug("diya_taskbar_widget_dispose");
|
g_debug("diya_taskbar_widget_dispose");
|
||||||
|
if (self->proxy_model)
|
||||||
|
{
|
||||||
|
g_object_unref(self->proxy_model);
|
||||||
|
}
|
||||||
|
if (self->factory)
|
||||||
|
{
|
||||||
|
g_object_unref(self->factory);
|
||||||
|
}
|
||||||
G_OBJECT_CLASS(diya_taskbar_widget_parent_class)->dispose(object);
|
G_OBJECT_CLASS(diya_taskbar_widget_parent_class)->dispose(object);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void diya_taskbar_widget_init(DiyaTaskbarWidget * self)
|
static void diya_taskbar_setup_apps_list_cb(GtkListItemFactory *factory, GtkListItem *list_item)
|
||||||
{
|
{
|
||||||
g_debug("diya_taskbar_widget_init");
|
(void) factory;
|
||||||
gtk_widget_init_template (GTK_WIDGET(self));
|
GtkWidget *image;
|
||||||
self->active_dashboard = false;
|
image = gtk_image_new();
|
||||||
//builder = gtk_builder_new_from_resource ("/org/gtk/exampleapp/gears-menu.ui");
|
gtk_image_set_icon_size(GTK_IMAGE(image), GTK_ICON_SIZE_LARGE);
|
||||||
// GtkWindow* win = GTK_WINDOW(self);
|
gtk_list_item_set_child(list_item, image);
|
||||||
|
}
|
||||||
|
|
||||||
// g_object_bind_property(self->btn_toggle, "active", self->revealer, "reveal-child", G_SETTINGS_BIND_DEFAULT);
|
static void diya_taskbar_bind_apps_list_cb(GtkListItemFactory *factory, GtkListItem *list_item)
|
||||||
// gtk_widget_set_can_focus(self->revealer, false);
|
{
|
||||||
|
(void) factory;
|
||||||
|
GtkWidget *image;
|
||||||
|
DiyaForeignWindow *win;
|
||||||
|
image = gtk_list_item_get_child(list_item);
|
||||||
|
win = gtk_list_item_get_item(list_item);
|
||||||
|
GAppInfo* info = diya_foreign_window_get_app_info(win);
|
||||||
|
if(info)
|
||||||
|
{
|
||||||
|
assert(G_IS_APP_INFO(info));
|
||||||
|
gtk_image_set_from_gicon(GTK_IMAGE(image), g_app_info_get_icon(info));
|
||||||
|
g_object_unref(info);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// get default icon from theme
|
||||||
|
GtkIconTheme* theme = gtk_icon_theme_get_for_display(gdk_display_get_default());
|
||||||
|
if(gtk_icon_theme_has_icon(theme, DEFAULT_APP_ICON_NAME))
|
||||||
|
{
|
||||||
|
gtk_image_set_from_icon_name(GTK_IMAGE(image), DEFAULT_APP_ICON_NAME);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// fallback to default icon in resource
|
||||||
|
gtk_image_set_from_resource(GTK_IMAGE(image), "/dev/iohub/diya/shell/icons/scalable/gear");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
//g_signal_connect (GTK_WINDOW(taskbar), "destroy", G_CALLBACK (on_launcher_destroy), NULL);
|
static guint g_list_model_get_item_index(GListModel *model, gpointer item)
|
||||||
|
{
|
||||||
|
for(guint i = 0; i < g_list_model_get_n_items(model); i++)
|
||||||
|
{
|
||||||
|
if(g_list_model_get_item(model, i) == item)
|
||||||
|
{
|
||||||
|
return i;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return GTK_INVALID_LIST_POSITION;
|
||||||
|
}
|
||||||
|
|
||||||
// int layer shell for window
|
static void on_foreign_window_state_changed(DiyaSessionShell* shell, DiyaForeignWindow* win, enum diya_win_state state, DiyaTaskbarWidget *self)
|
||||||
gtk_layer_init_for_window (GTK_WINDOW(self));
|
{
|
||||||
// anchor window to all edges
|
(void) shell;
|
||||||
gtk_layer_set_anchor (GTK_WINDOW(self), GTK_LAYER_SHELL_EDGE_LEFT, true);
|
DiyaForeignWindow *top_level = diya_foreign_window_get_top_level(win);
|
||||||
gtk_layer_set_anchor (GTK_WINDOW(self), GTK_LAYER_SHELL_EDGE_RIGHT, true);
|
guint index = g_list_model_get_item_index(G_LIST_MODEL(self->model), top_level);
|
||||||
gtk_layer_set_anchor (GTK_WINDOW(self), GTK_LAYER_SHELL_EDGE_TOP, false);
|
guint current_index = gtk_single_selection_get_selected(self->proxy_model);
|
||||||
gtk_layer_set_anchor (GTK_WINDOW(self), GTK_LAYER_SHELL_EDGE_BOTTOM, true);
|
g_debug("Current index %d, selected index %d", current_index, index);
|
||||||
gtk_layer_set_namespace(GTK_WINDOW(self), "diya-taskbar");
|
|
||||||
// set margin on window
|
|
||||||
for (int i = 0; i < GTK_LAYER_SHELL_EDGE_ENTRY_NUMBER; i++)
|
|
||||||
gtk_layer_set_margin (GTK_WINDOW(self), i, 0);
|
|
||||||
gtk_layer_set_layer (GTK_WINDOW(self), GTK_LAYER_SHELL_LAYER_TOP);
|
|
||||||
gtk_layer_set_keyboard_mode (GTK_WINDOW(self), GTK_LAYER_SHELL_KEYBOARD_MODE_ON_DEMAND);
|
|
||||||
// the top launcher shall be exclusive
|
|
||||||
gtk_layer_auto_exclusive_zone_enable (GTK_WINDOW(self));
|
|
||||||
|
|
||||||
g_object_bind_property(self->btn_toggle, "active", self, DIYA_PROP_TASKBAR_SHOW_DASHBOARD, G_BINDING_BIDIRECTIONAL);
|
g_signal_handler_block(self->proxy_model, self->selection_changed_sig_id);
|
||||||
|
if((state & DIYA_WIN_STATE_FOCUS) && !(state & DIYA_WIN_STATE_MINIMIZE))
|
||||||
|
{
|
||||||
|
if(index != GTK_INVALID_LIST_POSITION)
|
||||||
|
{
|
||||||
|
gtk_selection_model_select_item(GTK_SELECTION_MODEL(self->proxy_model), index, true);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// get the widget under the cursor
|
||||||
|
|
||||||
|
if(current_index == index)
|
||||||
|
{
|
||||||
|
gtk_selection_model_unselect_item(GTK_SELECTION_MODEL(self->proxy_model), current_index);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
g_signal_handler_unblock(self->proxy_model, self->selection_changed_sig_id);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void on_foreign_window_added(DiyaSessionShell *shell, DiyaForeignWindow *win, DiyaTaskbarWidget *self)
|
||||||
|
{
|
||||||
|
(void) shell;
|
||||||
|
g_debug("Window added %s (toplevel %d)", diya_object_to_string(win), diya_foreign_window_is_toplevel(win));
|
||||||
|
if(!diya_foreign_window_is_toplevel(win))
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if(diya_taskbar_list_model_contain(self->model, win))
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
diya_taskbar_list_model_append(self->model, win);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void on_foreign_window_removed(DiyaSessionShell *shell, DiyaForeignWindow *win, DiyaTaskbarWidget *self)
|
||||||
|
{
|
||||||
|
(void) shell;
|
||||||
|
if (!diya_foreign_window_is_toplevel(win))
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (diya_taskbar_list_model_contain(self->model, win))
|
||||||
|
{
|
||||||
|
diya_taskbar_list_model_remove(self->model, win);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void diya_taskbar_list_model_selection_changed_cb(GtkSelectionModel *model, guint position, guint n_items, gpointer user_data)
|
||||||
|
{
|
||||||
|
(void) n_items;
|
||||||
|
(void) user_data;
|
||||||
|
(void) position;
|
||||||
|
DiyaForeignWindow *win = gtk_single_selection_get_selected_item(GTK_SINGLE_SELECTION(model));
|
||||||
|
DiyaTaskbarWidget *self = DIYA_TASKBAR_WIDGET(user_data);
|
||||||
|
if(gtk_selection_model_is_selected(GTK_SELECTION_MODEL(model), position))
|
||||||
|
{
|
||||||
|
g_debug("Activating window: %s", diya_object_to_string(win));
|
||||||
|
enum diya_win_state state = diya_foreign_window_get_state(win);
|
||||||
|
if(state & DIYA_WIN_STATE_MINIMIZE)
|
||||||
|
{
|
||||||
|
diya_foreign_window_set_state(win, DIYA_WIN_STATE_MINIMIZE, false);
|
||||||
|
}
|
||||||
|
if(self->active_dashboard)
|
||||||
|
{
|
||||||
|
g_object_set(self, DIYA_PROP_TASKBAR_SHOW_DASHBOARD, !self->active_dashboard, NULL);
|
||||||
|
}
|
||||||
|
diya_foreign_window_set_state(win, DIYA_WIN_STATE_FOCUS, true);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
diya_foreign_window_set_state(win, DIYA_WIN_STATE_MINIMIZE, true);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void diya_taskbar_applist_enter(GtkEventControllerFocus *controller, DiyaTaskbarWidget* self)
|
||||||
|
{
|
||||||
|
g_debug("diya_taskbar_applist_enter");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static void diya_taskbar_applist_leave(GtkEventControllerFocus *controller, DiyaTaskbarWidget* self)
|
||||||
|
{
|
||||||
|
g_debug("diya_taskbar_applist_leaver");
|
||||||
|
}
|
||||||
|
|
||||||
|
static void diya_taskbar_widget_init(DiyaTaskbarWidget *self)
|
||||||
|
{
|
||||||
|
g_debug("diya_taskbar_widget_init");
|
||||||
|
gtk_widget_init_template(GTK_WIDGET(self));
|
||||||
|
self->active_dashboard = false;
|
||||||
|
|
||||||
|
// int layer shell for window
|
||||||
|
gtk_layer_init_for_window(GTK_WINDOW(self));
|
||||||
|
// anchor window to all edges
|
||||||
|
gtk_layer_set_anchor(GTK_WINDOW(self), GTK_LAYER_SHELL_EDGE_LEFT, true);
|
||||||
|
gtk_layer_set_anchor(GTK_WINDOW(self), GTK_LAYER_SHELL_EDGE_RIGHT, true);
|
||||||
|
gtk_layer_set_anchor(GTK_WINDOW(self), GTK_LAYER_SHELL_EDGE_TOP, false);
|
||||||
|
gtk_layer_set_anchor(GTK_WINDOW(self), GTK_LAYER_SHELL_EDGE_BOTTOM, true);
|
||||||
|
gtk_layer_set_namespace(GTK_WINDOW(self), "diya-taskbar");
|
||||||
|
// set margin on window
|
||||||
|
for (int i = 0; i < GTK_LAYER_SHELL_EDGE_ENTRY_NUMBER; i++)
|
||||||
|
gtk_layer_set_margin(GTK_WINDOW(self), i, 0);
|
||||||
|
gtk_layer_set_layer(GTK_WINDOW(self), GTK_LAYER_SHELL_LAYER_TOP);
|
||||||
|
gtk_layer_set_keyboard_mode(GTK_WINDOW(self), GTK_LAYER_SHELL_KEYBOARD_MODE_ON_DEMAND);
|
||||||
|
// the top launcher shall be exclusive
|
||||||
|
gtk_layer_auto_exclusive_zone_enable(GTK_WINDOW(self));
|
||||||
|
|
||||||
|
g_object_bind_property(self->btn_toggle, "active", self, DIYA_PROP_TASKBAR_SHOW_DASHBOARD, G_BINDING_BIDIRECTIONAL);
|
||||||
|
|
||||||
|
self->factory = gtk_signal_list_item_factory_new();
|
||||||
|
g_signal_connect(self->factory, "setup", G_CALLBACK(diya_taskbar_setup_apps_list_cb), NULL);
|
||||||
|
g_signal_connect(self->factory, "bind", G_CALLBACK(diya_taskbar_bind_apps_list_cb), NULL);
|
||||||
|
// applists
|
||||||
|
self->model = DIYA_TASKBAR_LIST_MODEL(g_object_new(DIYA_TYPE_TASKBAR_LIST_MODEL, NULL));
|
||||||
|
self->proxy_model = gtk_single_selection_new (G_LIST_MODEL(self->model));
|
||||||
|
gtk_single_selection_set_autoselect(self->proxy_model, false);
|
||||||
|
gtk_single_selection_set_can_unselect(self->proxy_model, true);
|
||||||
|
gtk_list_view_set_model(GTK_LIST_VIEW(self->apps_list), GTK_SELECTION_MODEL(self->proxy_model));
|
||||||
|
gtk_list_view_set_factory(GTK_LIST_VIEW(self->apps_list), GTK_LIST_ITEM_FACTORY(self->factory));
|
||||||
|
// gtk_list_view_set_single_click_activate(GTK_LIST_VIEW(self->apps_list), true);
|
||||||
|
|
||||||
|
self->selection_changed_sig_id = g_signal_connect(GTK_SELECTION_MODEL(self->proxy_model), "selection-changed", G_CALLBACK(diya_taskbar_list_model_selection_changed_cb), self);
|
||||||
|
|
||||||
|
// event handle
|
||||||
|
GtkEventController *controller = gtk_event_controller_focus_new();
|
||||||
|
g_signal_connect(controller, "enter", G_CALLBACK(diya_taskbar_applist_enter), self);
|
||||||
|
g_signal_connect(controller, "leave", G_CALLBACK(diya_taskbar_applist_leave), self);
|
||||||
|
gtk_widget_add_controller(GTK_WIDGET(self->apps_list), GTK_EVENT_CONTROLLER(controller));
|
||||||
|
}
|
||||||
|
|
||||||
static void diya_taskbar_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec)
|
static void diya_taskbar_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec)
|
||||||
{
|
{
|
||||||
DiyaTaskbarWidget * self = DIYA_TASKBAR_WIDGET(object);
|
DiyaTaskbarWidget *self = DIYA_TASKBAR_WIDGET(object);
|
||||||
|
|
||||||
switch (property_id)
|
switch (property_id)
|
||||||
{
|
{
|
||||||
@ -70,26 +344,25 @@ static void diya_taskbar_set_property(GObject *object, guint property_id, const
|
|||||||
self->active_dashboard = g_value_get_boolean(value);
|
self->active_dashboard = g_value_get_boolean(value);
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
|
G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void diya_taskbar_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec)
|
static void diya_taskbar_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec)
|
||||||
{
|
{
|
||||||
DiyaTaskbarWidget * self = DIYA_TASKBAR_WIDGET(object);
|
DiyaTaskbarWidget *self = DIYA_TASKBAR_WIDGET(object);
|
||||||
switch (property_id)
|
switch (property_id)
|
||||||
{
|
{
|
||||||
case PROP_SHOW_DASHBOARD:
|
case PROP_SHOW_DASHBOARD:
|
||||||
g_value_set_boolean(value, self->active_dashboard);
|
g_value_set_boolean(value, self->active_dashboard);
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
|
G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
static void diya_dashboard_toggle(GtkToggleButton* btn, DiyaTaskbarWidget* self)
|
static void diya_dashboard_toggle(GtkToggleButton* btn, DiyaTaskbarWidget* self)
|
||||||
{
|
{
|
||||||
@ -105,24 +378,36 @@ static void diya_dashboard_toggle(GtkToggleButton* btn, DiyaTaskbarWidget* self)
|
|||||||
}
|
}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
static void diya_taskbar_widget_setup(DiyaShellWindow* win)
|
||||||
|
{
|
||||||
|
DiyaTaskbarWidget* self = DIYA_TASKBAR_WIDGET(win);
|
||||||
|
DiyaSessionShell *shell = DIYA_SESSION_SHELL(diya_shell_window_get_shell(DIYA_SHELL_WINDOW(self)));
|
||||||
|
g_signal_connect(shell, DIYA_SIGNAL_FOREIGN_WINDOW_ADDED, G_CALLBACK(on_foreign_window_added), self);
|
||||||
|
g_signal_connect(shell, DIYA_SIGNAL_FOREIGN_WINDOW_STATE_CHANGED, G_CALLBACK(on_foreign_window_state_changed), self);
|
||||||
|
g_signal_connect(shell, DIYA_SIGNAL_FOREIGN_WINDOW_REMOVED, G_CALLBACK(on_foreign_window_removed), self);
|
||||||
|
}
|
||||||
|
|
||||||
static void diya_taskbar_widget_class_init(DiyaTaskbarWidgetClass* class)
|
static void diya_taskbar_widget_class_init(DiyaTaskbarWidgetClass *class)
|
||||||
{
|
{
|
||||||
GObjectClass *gobject_class = G_OBJECT_CLASS(class);
|
GObjectClass *gobject_class = G_OBJECT_CLASS(class);
|
||||||
gobject_class->dispose = diya_taskbar_widget_dispose;
|
gobject_class->dispose = diya_taskbar_widget_dispose;
|
||||||
gobject_class->set_property = diya_taskbar_set_property;
|
gobject_class->set_property = diya_taskbar_set_property;
|
||||||
gobject_class->get_property = diya_taskbar_get_property;
|
gobject_class->get_property = diya_taskbar_get_property;
|
||||||
|
|
||||||
gtk_widget_class_set_template_from_resource (GTK_WIDGET_CLASS (class),"/dev/iohub/diya/shell/taskbar.ui");
|
DiyaShellWindowClass *window_class = DIYA_SHELL_WINDOW_CLASS(class);
|
||||||
gtk_widget_class_bind_template_child (GTK_WIDGET_CLASS (class), DiyaTaskbarWidget, btn_toggle);
|
window_class->setup = diya_taskbar_widget_setup;
|
||||||
|
|
||||||
|
gtk_widget_class_set_template_from_resource(GTK_WIDGET_CLASS(class), "/dev/iohub/diya/shell/ui/taskbar.ui");
|
||||||
|
gtk_widget_class_bind_template_child(GTK_WIDGET_CLASS(class), DiyaTaskbarWidget, btn_toggle);
|
||||||
|
gtk_widget_class_bind_template_child(GTK_WIDGET_CLASS(class), DiyaTaskbarWidget, apps_list);
|
||||||
|
|
||||||
// gtk_widget_class_bind_template_callback (GTK_WIDGET_CLASS (class), diya_dashboard_toggle);
|
// gtk_widget_class_bind_template_callback (GTK_WIDGET_CLASS (class), diya_dashboard_toggle);
|
||||||
|
|
||||||
gtk_widget_class_set_css_name(GTK_WIDGET_CLASS(class), "diya-taskbar");
|
gtk_widget_class_set_css_name(GTK_WIDGET_CLASS(class), "diya-taskbar");
|
||||||
//gtk_widget_class_bind_template_child(GTK_WIDGET_CLASS (class), ExampleAppWindow, stack);
|
// gtk_widget_class_bind_template_child(GTK_WIDGET_CLASS (class), ExampleAppWindow, stack);
|
||||||
//gtk_widget_class_bind_template_callback (GTK_WIDGET_CLASS (class), search_text_changed);
|
// gtk_widget_class_bind_template_callback (GTK_WIDGET_CLASS (class), search_text_changed);
|
||||||
|
|
||||||
g_prop[PROP_SHOW_DASHBOARD] = g_param_spec_boolean(DIYA_PROP_TASKBAR_SHOW_DASHBOARD, NULL, "Show/hide dashboard", false, G_PARAM_READWRITE); //
|
g_prop[PROP_SHOW_DASHBOARD] = g_param_spec_boolean(DIYA_PROP_TASKBAR_SHOW_DASHBOARD, NULL, "Show/hide dashboard", false, G_PARAM_READWRITE); //
|
||||||
|
|
||||||
g_object_class_install_properties (gobject_class, N_PROPERTIES, g_prop);
|
g_object_class_install_properties(gobject_class, N_PROPERTIES, g_prop);
|
||||||
}
|
}
|
@ -4,9 +4,12 @@
|
|||||||
#include "session-shell.h"
|
#include "session-shell.h"
|
||||||
#include "base-widgets.h"
|
#include "base-widgets.h"
|
||||||
|
|
||||||
#define DIYA_PROP_TASKBAR_SHOW_DASHBOARD "show-dashboard"
|
#define DIYA_PROP_TASKBAR_SHOW_DASHBOARD "show-taskbar"
|
||||||
|
|
||||||
#define DIYA_TYPE_TASKBAR_WIDGET (diya_taskbar_widget_get_type())
|
#define DIYA_TYPE_TASKBAR_WIDGET (diya_taskbar_widget_get_type())
|
||||||
G_DECLARE_FINAL_TYPE (DiyaTaskbarWidget, diya_taskbar_widget, DIYA, TASKBAR_WIDGET, DiyaShellWindow)
|
G_DECLARE_FINAL_TYPE (DiyaTaskbarWidget, diya_taskbar_widget, DIYA, TASKBAR_WIDGET, DiyaShellWindow)
|
||||||
|
|
||||||
|
#define DIYA_TYPE_TASKBAR_LIST_MODEL (diya_taskbar_list_model_get_type())
|
||||||
|
G_DECLARE_FINAL_TYPE (DiyaTaskbarListModel, diya_taskbar_list_model, DIYA, TASKBAR_LIST_MODEL, GObject)
|
||||||
|
|
||||||
#endif
|
#endif
|
Loading…
x
Reference in New Issue
Block a user