1 #include "e_mod_main.h"
2
3 /* Config function protos */
4 static Config *_notification_cfg_new(void);
5 static void _notification_cfg_free(Config *cfg);
6
7 /* Global variables */
8 E_Module *notification_mod = NULL;
9 Config *notification_cfg = NULL;
10
11 static E_Config_DD *conf_edd = NULL;
12
13 static unsigned int offline_id;
14 static unsigned int pres_id;
15
16 static unsigned int
_notification_notify(E_Notification_Notify * n)17 _notification_notify(E_Notification_Notify *n)
18 {
19 unsigned int new_id;
20
21 if (e_desklock_state_get()) return 0;
22
23 notification_cfg->next_id++;
24 new_id = notification_cfg->next_id;
25 notification_popup_notify(n, new_id);
26
27 return new_id;
28 }
29
30 static void
_notification_id_update(void * d,unsigned int id)31 _notification_id_update(void *d, unsigned int id)
32 {
33 uintptr_t *update_id = d;
34
35 *update_id = id;
36 }
37
38 static void
_notification_show_common(const char * summary,const char * body,unsigned int * update_id)39 _notification_show_common(const char *summary,
40 const char *body,
41 unsigned int *update_id)
42 {
43 E_Notification_Notify n;
44 memset(&n, 0, sizeof(E_Notification_Notify));
45 n.app_name = "enlightenment";
46 n.replaces_id = *update_id;
47 n.icon.icon = "enlightenment";
48 n.summary = summary;
49 n.body = body;
50 n.urgency = E_NOTIFICATION_NOTIFY_URGENCY_CRITICAL;
51 e_notification_client_send(&n, _notification_id_update, update_id);
52 }
53
54 static void
_notification_show_presentation(Eina_Bool enabled)55 _notification_show_presentation(Eina_Bool enabled)
56 {
57 const char *summary, *body;
58
59 if (enabled)
60 {
61 summary = _("Entered Presentation Mode");
62 body = _("Enlightenment has now entered <b>presentation</b> mode."
63 "<ps/>During presentation mode, screen saver, lock and "
64 "power saving will be disabled so you are not interrupted.");
65 }
66 else
67 {
68 summary = _("Exited Presentation Mode");
69 body = _("Presentation mode has been exited."
70 "<ps/>Now screen saver, lock and "
71 "power saving settings will be restored.");
72 }
73
74 _notification_show_common(summary, body, &pres_id);
75 }
76
77 static void
_notification_show_offline(Eina_Bool enabled)78 _notification_show_offline(Eina_Bool enabled)
79 {
80 const char *summary, *body;
81
82 if (enabled)
83 {
84 summary = _("Enter Offline Mode");
85 body = _("Enlightenment is in <b>offline</b> mode.<ps/>"
86 "During offline mode, modules that use network will stop "
87 "polling remote services.");
88 }
89 else
90 {
91 summary = _("Exited Offline Mode");
92 body = _("Now in <b>online</b> mode.<ps/>"
93 "Now modules that use network will "
94 "resume regular tasks.");
95 }
96
97 _notification_show_common(summary, body, &offline_id);
98 }
99
100 static Eina_Bool
_notification_cb_config_mode_changed(Config * m_cfg,int type EINA_UNUSED,void * event EINA_UNUSED)101 _notification_cb_config_mode_changed(Config *m_cfg,
102 int type EINA_UNUSED,
103 void *event EINA_UNUSED)
104 {
105 if (m_cfg->last_config_mode.presentation != e_config->mode.presentation)
106 {
107 m_cfg->last_config_mode.presentation = e_config->mode.presentation;
108 _notification_show_presentation(e_config->mode.presentation);
109 }
110
111 if (m_cfg->last_config_mode.offline != e_config->mode.offline)
112 {
113 m_cfg->last_config_mode.offline = e_config->mode.offline;
114 _notification_show_offline(e_config->mode.offline);
115 }
116
117 return EINA_TRUE;
118 }
119
120 static Eina_Bool
_notification_cb_initial_mode_timer(Config * m_cfg)121 _notification_cb_initial_mode_timer(Config *m_cfg)
122 {
123 if (e_config->mode.presentation)
124 _notification_show_presentation(1);
125 if (e_config->mode.offline)
126 _notification_show_offline(1);
127
128 m_cfg->initial_mode_timer = NULL;
129 return EINA_FALSE;
130 }
131
132 /* Module Api Functions */
133 E_API E_Module_Api e_modapi = {E_MODULE_API_VERSION, "Notification"};
134
135 static const E_Notification_Server_Info server_info = {
136 .name = "e17",
137 .vendor = "enlightenment.org",
138 .version = "0.17",
139 .spec_version = "1.2",
140 .capabilities = { "body", "body-markup", NULL }
141 };
142
143 /* Callbacks */
144 static unsigned int
_notification_cb_notify(void * data EINA_UNUSED,E_Notification_Notify * n)145 _notification_cb_notify(void *data EINA_UNUSED, E_Notification_Notify *n)
146 {
147 return _notification_notify(n);
148 }
149
150 static void
_notification_cb_close(void * data EINA_UNUSED,unsigned int id)151 _notification_cb_close(void *data EINA_UNUSED, unsigned int id)
152 {
153 notification_popup_close(id);
154 }
155
156 E_API void *
e_modapi_init(E_Module * m)157 e_modapi_init(E_Module *m)
158 {
159 char buf[PATH_MAX];
160
161 snprintf(buf, sizeof(buf), "%s/e-module-notification.edj", m->dir);
162 /* register config panel entry */
163 e_configure_registry_category_add("extensions", 90, _("Extensions"), NULL,
164 "preferences-extensions");
165 e_configure_registry_item_add("extensions/notification", 30,
166 _("Notification"), NULL,
167 buf, e_int_config_notification_module);
168
169
170 conf_edd = E_CONFIG_DD_NEW("Notification_Config", Config);
171 #undef T
172 #undef D
173 #define T Config
174 #define D conf_edd
175 E_CONFIG_VAL(D, T, version, INT);
176 E_CONFIG_VAL(D, T, show_low, INT);
177 E_CONFIG_VAL(D, T, show_normal, INT);
178 E_CONFIG_VAL(D, T, show_critical, INT);
179 E_CONFIG_VAL(D, T, corner, INT);
180 E_CONFIG_VAL(D, T, timeout, FLOAT);
181 E_CONFIG_VAL(D, T, force_timeout, INT);
182 E_CONFIG_VAL(D, T, ignore_replacement, INT);
183 E_CONFIG_VAL(D, T, dual_screen, INT);
184
185 notification_cfg = e_config_domain_load("module.notification", conf_edd);
186 if (notification_cfg &&
187 !(e_util_module_config_check(_("Notification Module"),
188 notification_cfg->version,
189 MOD_CONFIG_FILE_VERSION)))
190 {
191 _notification_cfg_free(notification_cfg);
192 notification_cfg = NULL;
193 }
194
195 if (!notification_cfg)
196 notification_cfg = _notification_cfg_new();
197 /* upgrades */
198 if (notification_cfg->version - (MOD_CONFIG_FILE_EPOCH * 1000000) < 1)
199 {
200 if (notification_cfg->dual_screen) notification_cfg->dual_screen = POPUP_DISPLAY_POLICY_MULTI;
201 }
202 notification_cfg->version = MOD_CONFIG_FILE_VERSION;
203
204 /* set up the notification daemon */
205 if (!e_notification_server_register(&server_info, _notification_cb_notify,
206 _notification_cb_close, NULL))
207 {
208 e_util_dialog_show(_("Error during notification server initialization"),
209 _("Ensure there's no other module acting as a server "
210 "and that D-Bus is correctly installed and "
211 "running"));
212 return NULL;
213 }
214
215 notification_cfg->last_config_mode.presentation = e_config->mode.presentation;
216 notification_cfg->last_config_mode.offline = e_config->mode.offline;
217 notification_cfg->handler = ecore_event_handler_add
218 (E_EVENT_CONFIG_MODE_CHANGED, (Ecore_Event_Handler_Cb)_notification_cb_config_mode_changed,
219 notification_cfg);
220 notification_cfg->initial_mode_timer = ecore_timer_loop_add
221 (0.1, (Ecore_Task_Cb)_notification_cb_initial_mode_timer, notification_cfg);
222
223 notification_mod = m;
224
225 return m;
226 }
227
228 E_API int
e_modapi_shutdown(E_Module * m EINA_UNUSED)229 e_modapi_shutdown(E_Module *m EINA_UNUSED)
230 {
231 if (notification_cfg->initial_mode_timer)
232 ecore_timer_del(notification_cfg->initial_mode_timer);
233
234 if (notification_cfg->handler)
235 ecore_event_handler_del(notification_cfg->handler);
236
237 if (notification_cfg->cfd) e_object_del(E_OBJECT(notification_cfg->cfd));
238 e_configure_registry_item_del("extensions/notification");
239 e_configure_registry_category_del("extensions");
240
241 notification_popup_shutdown();
242 e_notification_server_unregister();
243
244
245 _notification_cfg_free(notification_cfg);
246 E_CONFIG_DD_FREE(conf_edd);
247 notification_mod = NULL;
248
249 return 1;
250 }
251
252 E_API int
e_modapi_save(E_Module * m EINA_UNUSED)253 e_modapi_save(E_Module *m EINA_UNUSED)
254 {
255 return e_config_domain_save("module.notification", conf_edd, notification_cfg);
256 }
257
258 static Config *
_notification_cfg_new(void)259 _notification_cfg_new(void)
260 {
261 Config *cfg;
262
263 cfg = E_NEW(Config, 1);
264 cfg->cfd = NULL;
265 cfg->version = MOD_CONFIG_FILE_VERSION;
266 cfg->show_low = 0;
267 cfg->show_normal = 1;
268 cfg->show_critical = 1;
269 cfg->timeout = 5.0;
270 cfg->force_timeout = 0;
271 cfg->ignore_replacement = 0;
272 cfg->dual_screen = POPUP_DISPLAY_POLICY_FIRST;
273 cfg->corner = CORNER_TR;
274
275 return cfg;
276 }
277
278 static void
_notification_cfg_free(Config * cfg)279 _notification_cfg_free(Config *cfg)
280 {
281 free(cfg);
282 }
283