4
* Copyright 2013 Alex <alex@linuxonly.ru>
6
* This program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
* the Free Software Foundation; either version 3 of the License, or
9
* (at your option) any later version.
11
* This program is distributed in the hope that it will be useful,
12
* but WITHOUT ANY WARRANTY; without even the implied warranty of
13
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14
* GNU General Public License for more details.
16
* You should have received a copy of the GNU General Public License
17
* along with this program. If not, see <http://www.gnu.org/licenses/>.
21
#include <glib/gi18n.h>
28
#include "resources.h"
31
static void mmgui_ayatana_indicator_server_clicked_signal(MessagingMenuApp *server, guint timestamp, gpointer user_data)
33
mmgui_ayatana_t ayatana;
35
ayatana = (mmgui_ayatana_t)user_data;
37
if (ayatana == NULL) return;
39
if (ayatana->eventcb != NULL) {
40
(ayatana->eventcb)(MMGUI_AYATANA_EVENT_SERVER, ayatana, NULL, ayatana->userdata);
44
static void mmgui_ayatana_indicator_client_clicked_signal(MessagingMenuApp *indicator, guint timestamp, gpointer user_data)
46
mmgui_ayatana_t ayatana;
48
ayatana = (mmgui_ayatana_t)user_data;
50
if (ayatana == NULL) return;
52
if (ayatana->eventcb != NULL) {
53
(ayatana->eventcb)(MMGUI_AYATANA_EVENT_CLIENT, ayatana, NULL, ayatana->userdata);
57
static void mmgui_ayatana_indicator_server_show_signal(IndicateServer *arg0, guint arg1, gpointer user_data)
59
mmgui_ayatana_t ayatana;
61
ayatana = (mmgui_ayatana_t)user_data;
63
if (ayatana == NULL) return;
65
if (ayatana->eventcb != NULL) {
66
(ayatana->eventcb)(MMGUI_AYATANA_EVENT_SERVER, ayatana, NULL, ayatana->userdata);
70
static void mmgui_ayatana_indicator_client_show_signal(IndicateServer *arg0, guint arg1, gpointer user_data)
72
mmgui_ayatana_t ayatana;
74
ayatana = (mmgui_ayatana_t)user_data;
76
if (ayatana == NULL) return;
78
if (ayatana->eventcb != NULL) {
79
(ayatana->eventcb)(MMGUI_AYATANA_EVENT_CLIENT, ayatana, NULL, ayatana->userdata);
83
static gchar *mmgui_ayatana_get_desktiop_file_id(gchar *filepath)
87
if (filepath == NULL) return NULL;
89
pathlen = strlen(filepath);
91
if (pathlen == 0) return NULL;
93
for (sym = pathlen; sym >= 0; sym--) {
94
if (filepath[sym] == '/') {
99
return filepath+sym+1;
102
static gboolean mmgui_ayatana_setup_menu(mmgui_ayatana_t ayatana)
104
if (ayatana == NULL) return FALSE;
106
if (ayatana->library == MMGUI_AYATANA_LIB_MESSAGINGMENU) {
108
ayatana->backend.mmenu.server = (ayatana->backend.mmenu.messaging_menu_app_new)(mmgui_ayatana_get_desktiop_file_id(RESOURCE_DESKTOP_FILE));
109
if (ayatana->backend.mmenu.server == NULL) {
112
(ayatana->backend.mmenu.messaging_menu_app_register)(ayatana->backend.mmenu.server);
113
g_signal_connect(G_OBJECT(ayatana->backend.mmenu.server), "activate-source", G_CALLBACK(mmgui_ayatana_indicator_server_clicked_signal), ayatana);
115
} else if (ayatana->library == MMGUI_AYATANA_LIB_INDICATE) {
117
ayatana->backend.ind.server = (ayatana->backend.ind.indicate_server_ref_default)();
118
if (ayatana->backend.ind.server == NULL) {
121
(ayatana->backend.ind.indicate_server_set_type)(ayatana->backend.ind.server, "message.im");
122
(ayatana->backend.ind.indicate_server_set_desktop_file)(ayatana->backend.ind.server, RESOURCE_DESKTOP_FILE);
123
(ayatana->backend.ind.indicate_server_show)(ayatana->backend.ind.server);
124
g_signal_connect(G_OBJECT(ayatana->backend.ind.server), "server-display", G_CALLBACK(mmgui_ayatana_indicator_server_show_signal), ayatana);
126
ayatana->backend.ind.client = (ayatana->backend.ind.indicate_indicator_new_with_server)(ayatana->backend.ind.server);
127
if (ayatana->backend.ind.client != NULL) {
128
(ayatana->backend.ind.indicate_indicator_set_property)(ayatana->backend.ind.client, "subtype", "im");
129
(ayatana->backend.ind.indicate_indicator_set_property)(ayatana->backend.ind.client, "sender", _("Unread SMS"));
130
(ayatana->backend.ind.indicate_indicator_set_property)(ayatana->backend.ind.client, "draw_attention", "false");
131
(ayatana->backend.ind.indicate_indicator_set_property)(ayatana->backend.ind.client, "count", "");
132
(ayatana->backend.ind.indicate_indicator_show)(ayatana->backend.ind.client);
133
g_signal_connect(G_OBJECT(ayatana->backend.ind.client), "user-display", G_CALLBACK(mmgui_ayatana_indicator_client_show_signal), ayatana);
141
static gboolean mmgui_ayatana_clean_menu(mmgui_ayatana_t ayatana)
143
if (ayatana == NULL) return FALSE;
145
if (ayatana->library == MMGUI_AYATANA_LIB_MESSAGINGMENU) {
146
if (ayatana->backend.mmenu.server != NULL) {
147
(ayatana->backend.mmenu.messaging_menu_app_remove_source)(ayatana->backend.mmenu.server, "sms");
148
(ayatana->backend.mmenu.messaging_menu_app_unregister)(ayatana->backend.mmenu.server);
151
} else if (ayatana->library == MMGUI_AYATANA_LIB_INDICATE) {
152
if (ayatana->backend.ind.server != NULL) {
153
if (ayatana->backend.ind.client != NULL) {
154
(ayatana->backend.ind.indicate_indicator_hide)(ayatana->backend.ind.client);
155
g_object_unref(G_OBJECT(ayatana->backend.ind.client));
157
(ayatana->backend.ind.indicate_server_hide)(ayatana->backend.ind.server);
158
g_object_unref(G_OBJECT(ayatana->backend.ind.server));
166
mmgui_ayatana_t mmgui_ayatana_new(mmgui_libpaths_cache_t libcache, mmgui_ayatana_event_callback callback, gpointer userdata)
168
mmgui_ayatana_t ayatana;
171
ayatana = g_new0(struct _mmgui_ayatana, 1);
174
ayatana->module = NULL;
175
ayatana->library = MMGUI_AYATANA_LIB_NULL;
176
ayatana->eventcb = callback;
177
ayatana->userdata = userdata;
179
/*Open module for libmessaging-menu*/
180
ayatana->module = g_module_open(mmgui_libpaths_cache_get_library_name(libcache, "libmessaging-menu"), G_MODULE_BIND_LAZY);
182
if (ayatana->module != NULL) {
184
libopened = libopened && g_module_symbol(ayatana->module, "messaging_menu_app_new", (gpointer *)&(ayatana->backend.mmenu.messaging_menu_app_new));
185
libopened = libopened && g_module_symbol(ayatana->module, "messaging_menu_app_register", (gpointer *)&(ayatana->backend.mmenu.messaging_menu_app_register));
186
libopened = libopened && g_module_symbol(ayatana->module, "messaging_menu_app_unregister", (gpointer *)&(ayatana->backend.mmenu.messaging_menu_app_unregister));
187
libopened = libopened && g_module_symbol(ayatana->module, "messaging_menu_app_append_source", (gpointer *)&(ayatana->backend.mmenu.messaging_menu_app_append_source));
188
libopened = libopened && g_module_symbol(ayatana->module, "messaging_menu_app_remove_source", (gpointer *)&(ayatana->backend.mmenu.messaging_menu_app_remove_source));
189
libopened = libopened && g_module_symbol(ayatana->module, "messaging_menu_app_set_source_count", (gpointer *)&(ayatana->backend.mmenu.messaging_menu_app_set_source_count));
190
libopened = libopened && g_module_symbol(ayatana->module, "messaging_menu_app_draw_attention", (gpointer *)&(ayatana->backend.mmenu.messaging_menu_app_draw_attention));
191
libopened = libopened && g_module_symbol(ayatana->module, "messaging_menu_app_remove_attention", (gpointer *)&(ayatana->backend.mmenu.messaging_menu_app_remove_attention));
192
libopened = libopened && g_module_symbol(ayatana->module, "messaging_menu_app_has_source", (gpointer *)&(ayatana->backend.mmenu.messaging_menu_app_has_source));
193
/*Try to set up menu*/
195
ayatana->library = MMGUI_AYATANA_LIB_MESSAGINGMENU;
196
if (!mmgui_ayatana_setup_menu(ayatana)) {
197
ayatana->library = MMGUI_AYATANA_LIB_NULL;
200
/*If some functions not exported or menu not set up, close library*/
201
if ((!libopened) || (ayatana->library == MMGUI_AYATANA_LIB_NULL)) {
202
ayatana->backend.mmenu.messaging_menu_app_new = NULL;
203
ayatana->backend.mmenu.messaging_menu_app_register = NULL;
204
ayatana->backend.mmenu.messaging_menu_app_unregister = NULL;
205
ayatana->backend.mmenu.messaging_menu_app_append_source = NULL;
206
ayatana->backend.mmenu.messaging_menu_app_remove_source = NULL;
207
ayatana->backend.mmenu.messaging_menu_app_set_source_count = NULL;
208
ayatana->backend.mmenu.messaging_menu_app_draw_attention = NULL;
209
ayatana->backend.mmenu.messaging_menu_app_remove_attention = NULL;
211
g_module_close(ayatana->module);
212
ayatana->module = NULL;
213
ayatana->library = MMGUI_AYATANA_LIB_NULL;
217
if ((ayatana->library == MMGUI_AYATANA_LIB_NULL) && (ayatana->module == NULL)) {
218
/*Open module for libindicate*/
219
ayatana->module = g_module_open(mmgui_libpaths_cache_get_library_name(libcache, "libindicate"), G_MODULE_BIND_LAZY);
221
if (ayatana->module != NULL) {
223
libopened = libopened && g_module_symbol(ayatana->module, "indicate_server_ref_default", (gpointer *)&(ayatana->backend.ind.indicate_server_ref_default));
224
libopened = libopened && g_module_symbol(ayatana->module, "indicate_server_set_type", (gpointer *)&(ayatana->backend.ind.indicate_server_set_type));
225
libopened = libopened && g_module_symbol(ayatana->module, "indicate_server_set_desktop_file", (gpointer *)&(ayatana->backend.ind.indicate_server_set_desktop_file));
226
libopened = libopened && g_module_symbol(ayatana->module, "indicate_server_show", (gpointer *)&(ayatana->backend.ind.indicate_server_show));
227
libopened = libopened && g_module_symbol(ayatana->module, "indicate_server_hide", (gpointer *)&(ayatana->backend.ind.indicate_server_hide));
228
libopened = libopened && g_module_symbol(ayatana->module, "indicate_indicator_new_with_server", (gpointer *)&(ayatana->backend.ind.indicate_indicator_new_with_server));
229
libopened = libopened && g_module_symbol(ayatana->module, "indicate_indicator_set_property", (gpointer *)&(ayatana->backend.ind.indicate_indicator_set_property));
230
libopened = libopened && g_module_symbol(ayatana->module, "indicate_indicator_show", (gpointer *)&(ayatana->backend.ind.indicate_indicator_show));
231
libopened = libopened && g_module_symbol(ayatana->module, "indicate_indicator_hide", (gpointer *)&(ayatana->backend.ind.indicate_indicator_hide));
232
/*Try to set up menu*/
234
ayatana->library = MMGUI_AYATANA_LIB_INDICATE;
235
if (!mmgui_ayatana_setup_menu(ayatana)) {
236
ayatana->library = MMGUI_AYATANA_LIB_NULL;
239
/*If some functions not exported or menu not set up, close library*/
240
if ((!libopened) || (ayatana->library == MMGUI_AYATANA_LIB_NULL)) {
241
ayatana->backend.ind.indicate_server_ref_default = NULL;
242
ayatana->backend.ind.indicate_server_set_type = NULL;
243
ayatana->backend.ind.indicate_server_set_desktop_file = NULL;
244
ayatana->backend.ind.indicate_server_show = NULL;
245
ayatana->backend.ind.indicate_server_hide = NULL;
246
ayatana->backend.ind.indicate_indicator_new_with_server = NULL;
247
ayatana->backend.ind.indicate_indicator_set_property = NULL;
248
ayatana->backend.ind.indicate_indicator_show = NULL;
249
ayatana->backend.ind.indicate_indicator_hide = NULL;
251
g_module_close(ayatana->module);
252
ayatana->module = NULL;
253
ayatana->library = MMGUI_AYATANA_LIB_NULL;
258
if ((!libopened) || (ayatana->library == MMGUI_AYATANA_LIB_NULL)) {
266
void mmgui_ayatana_close(mmgui_ayatana_t ayatana)
268
if (ayatana == NULL) return;
270
mmgui_ayatana_clean_menu(ayatana);
272
if (ayatana->module != NULL) {
273
g_module_close(ayatana->module);
279
void mmgui_ayatana_set_unread_messages_number(mmgui_ayatana_t ayatana, guint number)
285
if (ayatana == NULL) return;
287
if (ayatana->library == MMGUI_AYATANA_LIB_MESSAGINGMENU) {
288
if (ayatana->backend.mmenu.server != NULL) {
289
if ((ayatana->backend.mmenu.messaging_menu_app_has_source)(ayatana->backend.mmenu.server, "sms")) {
291
(ayatana->backend.mmenu.messaging_menu_app_set_source_count)(ayatana->backend.mmenu.server, "sms", number);
292
(ayatana->backend.mmenu.messaging_menu_app_remove_attention)(ayatana->backend.mmenu.server, "sms");
294
(ayatana->backend.mmenu.messaging_menu_app_remove_source)(ayatana->backend.mmenu.server, "sms");
298
file = g_file_new_for_path(RESOURCE_SMS_UNREAD);
299
icon = g_file_icon_new(file);
300
(ayatana->backend.mmenu.messaging_menu_app_append_source)(ayatana->backend.mmenu.server, "sms", icon, _("Unread messages"));
301
(ayatana->backend.mmenu.messaging_menu_app_set_source_count)(ayatana->backend.mmenu.server, "sms", number);
302
(ayatana->backend.mmenu.messaging_menu_app_draw_attention)(ayatana->backend.mmenu.server, "sms");
303
g_signal_connect(G_OBJECT(ayatana->backend.mmenu.server), "activate-source::sms", G_CALLBACK(mmgui_ayatana_indicator_client_clicked_signal), ayatana);
304
g_object_unref(icon);
305
g_object_unref(file);
309
} else if (ayatana->library == MMGUI_AYATANA_LIB_INDICATE) {
310
if (ayatana->backend.ind.server != NULL) {
311
if (ayatana->backend.ind.client != NULL) {
313
memset(numstr, 0, sizeof(numstr));
314
snprintf(numstr, sizeof(numstr), "%u", number);
315
(ayatana->backend.ind.indicate_indicator_set_property)(ayatana->backend.ind.client, "draw_attention", "true");
316
(ayatana->backend.ind.indicate_indicator_set_property)(ayatana->backend.ind.client, "count", numstr);
318
(ayatana->backend.ind.indicate_indicator_set_property)(ayatana->backend.ind.client, "draw_attention", "false");
319
(ayatana->backend.ind.indicate_indicator_set_property)(ayatana->backend.ind.client, "count", "");