f19faeca855b26904ba0c1977293d73110e74238
[modest] / src / modest-ui-dimming-rules.c
1 /* Copyright (c) 2006, Nokia Corporation
2  * All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions are
6  * met:
7  *
8  * * Redistributions of source code must retain the above copyright
9  *   notice, this list of conditions and the following disclaimer.
10  * * Redistributions in binary form must reproduce the above copyright
11  *   notice, this list of conditions and the following disclaimer in the
12  *   documentation and/or other materials provided with the distribution.
13  * * Neither the name of the Nokia Corporation nor the names of its
14  *   contributors may be used to endorse or promote products derived from
15  *   this software without specific prior written permission.
16  *
17  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
18  * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
19  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
20  * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
21  * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
22  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
23  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
24  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
25  * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
26  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
27  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28  */
29  
30 #ifdef HAVE_CONFIG_H
31 #include <config.h>
32 #endif /*HAVE_CONFIG_H*/
33
34 #include <string.h>
35 #include "modest-ui-dimming-rules.h"
36 #include "modest-dimming-rule.h"
37 #include "modest-tny-folder.h"
38 #include "modest-tny-account.h"
39 #include "modest-text-utils.h"
40 #include <widgets/modest-attachments-view.h>
41 #include <modest-runtime.h>
42 #include <tny-simple-list.h>
43
44
45 static gboolean _folder_is_any_of_type (TnyFolder *folder, TnyFolderType types[], guint ntypes);
46 static gboolean _invalid_msg_selected (ModestMainWindow *win, gboolean unique, ModestDimmingRule *rule);
47 static gboolean _invalid_attach_selected (ModestWindow *win, 
48                                           gboolean unique, gboolean for_view, gboolean for_remove,
49                                           ModestDimmingRule *rule);
50 static gboolean _purged_attach_selected (ModestWindow *win, gboolean all, ModestDimmingRule *rule);
51 static gboolean _clipboard_is_empty (ModestWindow *win);
52 static gboolean _invalid_clipboard_selected (ModestWindow *win, ModestDimmingRule *rule);
53 static gboolean _selected_folder_not_writeable (ModestMainWindow *win, gboolean for_paste);
54 static gboolean _selected_folder_not_moveable (ModestMainWindow *win);
55 static gboolean _selected_folder_not_renameable (ModestMainWindow *win);
56 static gboolean _selected_folder_not_deletable (ModestMainWindow *win);
57 static gboolean _selected_folder_is_any_of_type (ModestWindow *win, TnyFolderType types[], guint ntypes);
58 static gboolean _selected_folder_is_root_or_inbox (ModestMainWindow *win);
59 static gboolean _selected_folder_is_MMC_or_POP_root (ModestMainWindow *win);
60 static gboolean _selected_folder_is_root (ModestMainWindow *win);
61 static gboolean _header_view_is_all_selected (ModestMainWindow *win);
62 static gboolean _selected_folder_is_empty (ModestMainWindow *win);
63 static gboolean _folder_view_has_focus (ModestWindow *win);
64 static gboolean _selected_folder_is_same_as_source (ModestWindow *win);
65 static gboolean _msg_download_in_progress (ModestMsgViewWindow *win);
66 static gboolean _msg_download_completed (ModestMainWindow *win);
67 static gboolean _selected_msg_sent_in_progress (ModestWindow *win);
68 static gboolean _sending_in_progress (ModestWindow *win);
69 static gboolean _invalid_folder_for_purge (ModestWindow *win, ModestDimmingRule *rule);
70 static gboolean _transfer_mode_enabled (ModestWindow *win);
71 static gboolean _selected_folder_has_subfolder_with_same_name (ModestWindow *win);
72 static void fill_list_of_caches (gpointer key, gpointer value, gpointer userdata);
73
74
75 static DimmedState *
76 _define_main_window_dimming_state (ModestMainWindow *window)
77 {
78         DimmedState *state = NULL;
79         GtkWidget *focused_widget = NULL;
80         GtkWidget *header_view = NULL;
81         GtkTreeModel *model = NULL;
82         TnyList *selected_headers = NULL;
83         TnyIterator *iter = NULL;
84         TnyHeader *header = NULL;
85         ModestCacheMgr *cache_mgr = NULL;
86         GHashTable *send_queue_cache = NULL;
87         ModestTnySendQueue *send_queue = NULL;
88         GSList *send_queues = NULL, *node = NULL;
89         ModestWindowMgr *mgr = NULL;
90         gboolean found = FALSE;
91         gchar *msg_uid = NULL;
92         TnyHeaderFlags flags;
93         gboolean all_deleted = TRUE;
94         gboolean all_seen = TRUE;
95         gboolean all_cached = TRUE;
96         gboolean all_has_attach = TRUE;
97
98         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(window), NULL);
99
100         /* Init state */
101         state = g_slice_new0 (DimmedState);
102         state->n_selected = 0;
103         state->already_opened_msg = FALSE;
104         state->any_marked_as_deleted = FALSE;
105         state->all_marked_as_deleted = FALSE;
106         state->any_marked_as_seen = FALSE;
107         state->all_marked_as_seen = FALSE;
108         state->any_marked_as_cached = FALSE;
109         state->all_marked_as_cached = FALSE;
110         state->any_has_attachments = FALSE;
111         state->all_has_attachments = FALSE;
112         state->sent_in_progress = FALSE;
113         state->all_selected = FALSE;
114
115         /* Get focused widget */
116         focused_widget = gtk_window_get_focus (GTK_WINDOW (window));
117         if (MODEST_IS_FOLDER_VIEW (focused_widget)) {
118                 state->n_selected++;
119                 return state;
120         } else if (MODEST_IS_HEADER_VIEW (focused_widget)) {
121                 header_view = focused_widget;           
122         } else {
123                 header_view = modest_main_window_get_child_widget (window, MODEST_WIDGET_TYPE_HEADER_VIEW);
124         }
125         
126         /* Get header view and selected headers */
127         selected_headers = modest_header_view_get_selected_headers (MODEST_HEADER_VIEW(header_view));
128         if (!selected_headers) 
129                 return state;
130
131         /* Examine selected headers */
132         iter = tny_list_create_iterator (selected_headers);
133         while (!tny_iterator_is_done (iter)) {
134                 header = TNY_HEADER (tny_iterator_get_current (iter));
135                 flags = tny_header_get_flags (header);
136                 
137                 /* No selected */
138                 state->n_selected++;
139                 
140                 /* Already opened */
141                 mgr = modest_runtime_get_window_mgr ();
142                 if (!state->already_opened_msg)
143                         state->already_opened_msg = modest_window_mgr_find_registered_header (mgr, header, NULL);
144                 
145
146                 /* Mark as deleted */           
147                 all_deleted = all_deleted && (flags & TNY_HEADER_FLAG_DELETED);
148                 state->all_marked_as_deleted = all_deleted;
149                 if (!state->any_marked_as_deleted)
150                         state->any_marked_as_deleted = flags & TNY_HEADER_FLAG_DELETED;
151                 
152                 /* Mark as seen */
153                 all_seen = all_seen && (flags & TNY_HEADER_FLAG_SEEN);
154                 state->all_marked_as_seen = all_seen;
155                 if (!state->any_marked_as_seen)
156                         state->any_marked_as_seen = flags & TNY_HEADER_FLAG_SEEN;
157                 
158                 /* Mark as cached */
159                 all_cached = all_cached && (flags & TNY_HEADER_FLAG_CACHED);
160                 state->all_marked_as_cached = all_cached;
161                 if (!state->any_marked_as_cached)
162                         state->any_marked_as_cached = flags & TNY_HEADER_FLAG_CACHED;
163                 
164                 /* Mark has_attachments */
165                 all_has_attach = all_has_attach && (flags & TNY_HEADER_FLAG_ATTACHMENTS);
166                 state->all_has_attachments = all_has_attach;
167                 if (!state->any_has_attachments)
168                         state->any_has_attachments = flags & TNY_HEADER_FLAG_ATTACHMENTS;
169         
170                 /* sent in progress */
171                 msg_uid = modest_tny_send_queue_get_msg_id (header);
172                 if (!state->sent_in_progress) {
173                         cache_mgr = modest_runtime_get_cache_mgr ();
174                         send_queue_cache = modest_cache_mgr_get_cache (cache_mgr,
175                                                                        MODEST_CACHE_MGR_CACHE_TYPE_SEND_QUEUE);
176                         
177                         g_hash_table_foreach (send_queue_cache, (GHFunc) fill_list_of_caches, &send_queues);
178                         
179                         for (node = send_queues; node != NULL && !found; node = g_slist_next (node)) {
180                                 send_queue = MODEST_TNY_SEND_QUEUE (node->data);
181                                 
182                                 /* Check if msg uid is being processed inside send queue */
183                                 found = modest_tny_send_queue_msg_is_being_sent (send_queue, msg_uid);          
184                         }
185                         state->sent_in_progress = found;
186                 }
187
188                 tny_iterator_next (iter);
189                 g_object_unref (header);
190         }
191
192         /* check if all the headers are selected or not */
193         model = gtk_tree_view_get_model(GTK_TREE_VIEW(header_view));
194         if (model != NULL){
195                 gint count;
196                 count = gtk_tree_model_iter_n_children(model, NULL);
197                 if(state->n_selected == count != 0)
198                         state->all_selected = TRUE;
199         }
200
201         /* Free */
202         g_free(msg_uid);
203         g_object_unref(selected_headers);
204         g_object_unref(iter);
205         g_slist_free (send_queues);
206         
207         return state;
208 }
209
210 static DimmedState *
211 _define_msg_view_window_dimming_state (ModestMsgViewWindow *window)
212 {
213         DimmedState *state = NULL;
214         TnyHeader *header = NULL;
215         ModestCacheMgr *cache_mgr = NULL;
216         GHashTable *send_queue_cache = NULL;
217         ModestTnySendQueue *send_queue = NULL;
218         GSList *send_queues = NULL, *node = NULL;
219         gboolean found = FALSE;
220         gchar *msg_uid = NULL;
221         TnyHeaderFlags flags;
222         gboolean all_deleted = TRUE;
223         gboolean all_seen = TRUE;
224         gboolean all_cached = TRUE;
225         gboolean all_has_attach = TRUE;
226                         
227         g_return_val_if_fail (MODEST_IS_MSG_VIEW_WINDOW(window), NULL);
228
229         /* Init state */
230         state = g_slice_new0 (DimmedState);
231         state->n_selected = 0;
232         state->already_opened_msg = FALSE;
233         state->any_marked_as_deleted = FALSE;
234         state->all_marked_as_deleted = FALSE;
235         state->any_marked_as_seen = FALSE;
236         state->all_marked_as_seen = FALSE;
237         state->any_marked_as_cached = FALSE;
238         state->all_marked_as_cached = FALSE;
239         state->any_has_attachments = FALSE;
240         state->all_has_attachments = FALSE;
241         state->sent_in_progress = FALSE;
242
243         header = modest_msg_view_window_get_header (MODEST_MSG_VIEW_WINDOW(window));
244         g_return_val_if_fail (TNY_IS_HEADER(header), state);
245         flags = tny_header_get_flags (header);
246
247         /* Selected */
248         state->n_selected++;
249
250         /* Mark as deleted */           
251         all_deleted = all_deleted && (flags & TNY_HEADER_FLAG_DELETED);
252         state->all_marked_as_deleted = all_deleted;
253         if (!state->any_marked_as_deleted)
254                 state->any_marked_as_deleted = flags & TNY_HEADER_FLAG_DELETED;
255         
256         /* Mark as seen */
257         all_seen = all_seen && (flags & TNY_HEADER_FLAG_SEEN);
258         state->all_marked_as_seen = all_seen;
259         if (!state->any_marked_as_seen)
260                 state->any_marked_as_seen = flags & TNY_HEADER_FLAG_SEEN;
261         
262         /* Mark as cached */
263         all_cached = all_cached && (flags & TNY_HEADER_FLAG_CACHED);
264         state->all_marked_as_cached = all_cached;
265         if (!state->any_marked_as_cached)
266                 state->any_marked_as_cached = flags & TNY_HEADER_FLAG_CACHED;
267         
268         /* Mark has_attachments */
269         all_has_attach = all_has_attach && (flags & TNY_HEADER_FLAG_ATTACHMENTS);
270         state->all_has_attachments = all_has_attach;
271         if (!state->any_has_attachments)
272                 state->any_has_attachments = flags & TNY_HEADER_FLAG_ATTACHMENTS;
273         
274         /* sent in progress */
275         msg_uid = modest_tny_send_queue_get_msg_id (header);
276         if (!state->sent_in_progress) {
277                 cache_mgr = modest_runtime_get_cache_mgr ();
278                 send_queue_cache = modest_cache_mgr_get_cache (cache_mgr,
279                                                                MODEST_CACHE_MGR_CACHE_TYPE_SEND_QUEUE);
280                 
281                 g_hash_table_foreach (send_queue_cache, (GHFunc) fill_list_of_caches, &send_queues);
282                 
283                 for (node = send_queues; node != NULL && !found; node = g_slist_next (node)) {
284                         send_queue = MODEST_TNY_SEND_QUEUE (node->data);
285                         
286                         /* Check if msg uid is being processed inside send queue */
287                         found = modest_tny_send_queue_msg_is_being_sent (send_queue, msg_uid);          
288                 }
289                 state->sent_in_progress = found;
290         }
291         
292         /* Free */
293         g_free(msg_uid);
294         g_object_unref (header);
295         g_slist_free (send_queues);
296
297         return state;
298 }
299
300    
301 DimmedState *
302 modest_ui_dimming_rules_define_dimming_state (ModestWindow *window)
303 {
304         DimmedState *state = NULL;
305
306         g_return_val_if_fail (MODEST_IS_WINDOW(window), NULL);
307         
308         if (MODEST_IS_MAIN_WINDOW (window)) 
309                 state = _define_main_window_dimming_state (MODEST_MAIN_WINDOW(window));
310         else if (MODEST_IS_MSG_VIEW_WINDOW (window)) {
311                 state = _define_msg_view_window_dimming_state (MODEST_MSG_VIEW_WINDOW(window));         
312         }
313         
314         return state;
315 }
316
317
318 gboolean 
319 modest_ui_dimming_rules_on_new_msg (ModestWindow *win, gpointer user_data)
320 {
321         ModestDimmingRule *rule = NULL;
322         gboolean dimmed = FALSE;
323
324         g_return_val_if_fail (MODEST_IS_MSG_VIEW_WINDOW(win), FALSE);
325         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
326         rule = MODEST_DIMMING_RULE (user_data);
327                 
328         /* Check dimmed rule */ 
329         if (!dimmed) {
330                 dimmed = _msg_download_in_progress (MODEST_MSG_VIEW_WINDOW(win));
331                 if (dimmed)
332                         modest_dimming_rule_set_notification (rule, "");
333         }
334
335         return dimmed;
336 }
337
338 gboolean 
339 modest_ui_dimming_rules_on_new_folder (ModestWindow *win, gpointer user_data)
340 {
341         ModestDimmingRule *rule = NULL;
342         GtkWidget *folder_view = NULL;
343         TnyFolderStore *parent_folder = NULL;
344         gboolean dimmed = FALSE;
345
346         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
347         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
348         rule = MODEST_DIMMING_RULE (user_data);
349
350         /* Get selected folder as parent of new folder to create */
351         folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
352                                                            MODEST_WIDGET_TYPE_FOLDER_VIEW);
353         parent_folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW(folder_view));
354         if (!parent_folder)
355                 return TRUE;
356         
357         if (TNY_IS_ACCOUNT (parent_folder)) {
358                 /* If it's the local account then do not dim */
359                 if (modest_tny_account_is_virtual_local_folders (TNY_ACCOUNT (parent_folder))) {
360                         dimmed = FALSE;
361                 } else {
362                         const gchar *proto_str = tny_account_get_proto (TNY_ACCOUNT (parent_folder));
363                         /* If it's POP then dim */
364                         dimmed = (modest_protocol_info_get_transport_store_protocol (proto_str) == 
365                                   MODEST_PROTOCOL_STORE_POP) ? TRUE : FALSE;
366                         if (dimmed)
367                                 modest_dimming_rule_set_notification (rule, _("mail_in_ui_folder_create_error"));
368                 }
369         } else {
370                 /* TODO: the specs say that only one level of subfolder is allowed, is this true ? */
371                 
372                 TnyFolderType types[3];
373                                 
374                 types[0] = TNY_FOLDER_TYPE_DRAFTS; 
375                 types[1] = TNY_FOLDER_TYPE_OUTBOX;
376                 types[2] = TNY_FOLDER_TYPE_SENT;
377
378                 /* Apply folder rules */        
379                 if (!dimmed) {
380                         dimmed = _selected_folder_not_writeable (MODEST_MAIN_WINDOW(win), FALSE);
381                         if (dimmed)
382                                 modest_dimming_rule_set_notification (rule, _("mail_in_ui_folder_create_error"));
383                 }
384                 if (!dimmed) {
385                         dimmed = _selected_folder_is_any_of_type (win, types, 3);
386                         if (dimmed)
387                                 modest_dimming_rule_set_notification (rule, _("mail_in_ui_folder_create_error"));
388                 }
389         }
390
391         /* if not the folder is selected then dim */
392         folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
393                                                            MODEST_WIDGET_TYPE_FOLDER_VIEW);
394         if (folder_view && !gtk_widget_is_focus (folder_view)) 
395                 dimmed = TRUE;
396
397         g_object_unref (parent_folder);
398
399         return dimmed;
400 }
401
402 gboolean 
403 modest_ui_dimming_rules_on_delete (ModestWindow *win, gpointer user_data)
404 {
405         ModestDimmingRule *rule = NULL;
406         GtkWidget *folder_view = NULL;
407         GtkWidget *header_view = NULL;  
408         gboolean dimmed = FALSE;
409
410         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
411         rule = MODEST_DIMMING_RULE (user_data);
412         
413         if (MODEST_IS_MAIN_WINDOW (win)) {
414                 /* Get the folder view */
415                 folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
416                                                                    MODEST_WIDGET_TYPE_FOLDER_VIEW);
417                 
418                 /* Get header view */
419                 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
420                                                            MODEST_WIDGET_TYPE_HEADER_VIEW);
421
422                 if (header_view && gtk_widget_is_focus (header_view)) 
423                         dimmed = modest_ui_dimming_rules_on_delete_msg (win, rule);
424
425                 if (folder_view && gtk_widget_is_focus (folder_view)) 
426                         dimmed = modest_ui_dimming_rules_on_delete_folder (win, rule);
427
428                 if (header_view && folder_view &&
429                     !gtk_widget_is_focus (header_view) &&
430                     !gtk_widget_is_focus (folder_view)) {
431                         dimmed = TRUE;
432                         modest_dimming_rule_set_notification (rule, dgettext("hildon-common-strings", "ckct_ib_nothing_to_delete"));                    
433                 }
434         } else {
435                 dimmed = modest_ui_dimming_rules_on_delete_folder (win, rule);
436         }
437
438         return dimmed;
439 }
440
441
442
443 gboolean 
444 modest_ui_dimming_rules_on_delete_folder (ModestWindow *win, gpointer user_data)
445 {
446         ModestDimmingRule *rule = NULL;
447         TnyFolderType types[6];
448         gboolean dimmed = FALSE;
449
450         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
451         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
452         rule = MODEST_DIMMING_RULE (user_data);
453
454         types[0] = TNY_FOLDER_TYPE_DRAFTS; 
455         types[1] = TNY_FOLDER_TYPE_OUTBOX;
456         types[2] = TNY_FOLDER_TYPE_SENT;
457         types[3] = TNY_FOLDER_TYPE_INBOX;
458         types[4] = TNY_FOLDER_TYPE_ROOT;
459         types[5] = TNY_FOLDER_TYPE_ARCHIVE;
460
461                 
462         /* Check dimmed rule */ 
463         if (!dimmed) {
464                 dimmed = _selected_folder_not_deletable (MODEST_MAIN_WINDOW(win));
465                 if (dimmed)
466                         modest_dimming_rule_set_notification (rule, _("mail_in_ui_folder_delete_error"));
467         }
468         if (!dimmed) {
469                 dimmed = _selected_folder_is_any_of_type (win, types, 6);
470                 if (dimmed)
471                         modest_dimming_rule_set_notification (rule, _("mail_in_ui_folder_delete_error"));
472         }
473         if (!dimmed) {
474                 dimmed = _selected_folder_is_root_or_inbox (MODEST_MAIN_WINDOW(win));
475                 if (dimmed)
476                         modest_dimming_rule_set_notification (rule, _("mail_in_ui_folder_delete_error"));
477         }
478         if (!dimmed) {
479                 dimmed = _selected_folder_is_MMC_or_POP_root (MODEST_MAIN_WINDOW(win));
480                 if (dimmed)
481                         modest_dimming_rule_set_notification (rule, _("mail_in_ui_folder_delete_error"));
482         }
483         if (!dimmed) {
484                 dimmed = _transfer_mode_enabled (win);
485                 if (dimmed)
486                         modest_dimming_rule_set_notification (rule, _CS("ckct_ib_unable_to_delete"));
487         }
488
489         return dimmed;
490 }
491
492 gboolean
493 modest_ui_dimming_rules_on_sort (ModestWindow *win, gpointer user_data)
494 {
495         ModestDimmingRule *rule = NULL;
496         gboolean dimmed = FALSE;
497
498         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
499         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
500         rule = MODEST_DIMMING_RULE (user_data);
501                 
502         /* Check dimmed rule */ 
503         if (!dimmed) {
504                 dimmed = _selected_folder_is_root (MODEST_MAIN_WINDOW(win));
505                 modest_dimming_rule_set_notification (rule, _CS("ckdg_ib_nothing_to_sort"));
506         }
507
508         if (!dimmed) {
509                 dimmed = _selected_folder_is_empty (MODEST_MAIN_WINDOW(win));
510                 modest_dimming_rule_set_notification (rule, _CS("ckdg_ib_nothing_to_sort"));
511         }
512
513         return dimmed;
514         
515 }
516
517 gboolean 
518 modest_ui_dimming_rules_on_rename_folder (ModestWindow *win, gpointer user_data)
519 {
520         ModestDimmingRule *rule = NULL;
521         TnyFolderType types[4];
522         gboolean dimmed = FALSE;
523
524         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
525         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
526         rule = MODEST_DIMMING_RULE (user_data);
527
528         types[0] = TNY_FOLDER_TYPE_DRAFTS; 
529         types[1] = TNY_FOLDER_TYPE_OUTBOX;
530         types[2] = TNY_FOLDER_TYPE_SENT;
531         types[3] = TNY_FOLDER_TYPE_ARCHIVE;
532         
533         /* Check dimmed rule */ 
534         if (!dimmed) {
535                 dimmed = _selected_folder_not_renameable (MODEST_MAIN_WINDOW(win));
536                 if (dimmed)
537                         modest_dimming_rule_set_notification (rule, "");
538         }
539         if (!dimmed) {
540                 dimmed = _selected_folder_is_root_or_inbox (MODEST_MAIN_WINDOW(win));
541                 if (dimmed)
542                         modest_dimming_rule_set_notification (rule, "");
543         }
544         if (!dimmed) {
545                 dimmed = _selected_folder_is_any_of_type (win, types, 4);
546                 if (dimmed)
547                         modest_dimming_rule_set_notification (rule, "");
548         }
549
550         return dimmed;
551 }
552
553 gboolean 
554 modest_ui_dimming_rules_on_open_msg (ModestWindow *win, gpointer user_data)
555 {
556         ModestDimmingRule *rule = NULL;
557         gboolean dimmed = FALSE;
558         const DimmedState *state = NULL;
559
560         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
561         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
562         rule = MODEST_DIMMING_RULE (user_data);
563         state = modest_window_get_dimming_state (win);          
564
565         /* Check dimmed rule */ 
566         if (!dimmed) {
567                 dimmed = _invalid_msg_selected (MODEST_MAIN_WINDOW(win), TRUE, user_data);
568         }
569         if (!dimmed) {
570                 dimmed = state->any_marked_as_deleted;
571                 if (dimmed)
572                         modest_dimming_rule_set_notification (rule, _("mcen_ib_message_already_deleted"));
573         }
574         if (!dimmed) {
575                 dimmed = _selected_msg_sent_in_progress (win);
576                 if (dimmed)
577                         modest_dimming_rule_set_notification (rule, _("mcen_ib_unable_to_open_while_sent"));
578         }
579
580         return dimmed;
581 }
582
583 gboolean 
584 modest_ui_dimming_rules_on_reply_msg (ModestWindow *win, gpointer user_data)
585 {
586         ModestDimmingRule *rule = NULL;
587         gboolean dimmed = FALSE;
588         TnyFolderType types[3];
589
590         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
591         rule = MODEST_DIMMING_RULE (user_data);
592
593         /* main window dimming rules */
594         if (MODEST_IS_MAIN_WINDOW(win)) {
595                 
596                 types[0] = TNY_FOLDER_TYPE_DRAFTS; 
597                 types[1] = TNY_FOLDER_TYPE_OUTBOX;
598                 types[2] = TNY_FOLDER_TYPE_ROOT;
599                 
600                 /* Check dimmed rule */ 
601                 if (!dimmed) {
602                         dimmed = _selected_folder_is_any_of_type (win, types, 3);                       
603                         if (dimmed)
604                                 modest_dimming_rule_set_notification (rule, _("mcen_ib_unable_to_reply"));
605                 }
606                 if (!dimmed) {
607                         dimmed = _selected_folder_is_empty (MODEST_MAIN_WINDOW(win));                   
608                         if (dimmed)
609                                 modest_dimming_rule_set_notification (rule, _("mcen_ib_nothing_to_reply"));
610                 }
611                 if (!dimmed) {
612                         dimmed = _invalid_msg_selected (MODEST_MAIN_WINDOW(win), TRUE, rule);
613                 }
614         /* msg view window dimming rules */
615         } else if (MODEST_IS_MSG_VIEW_WINDOW(win)) {
616                 
617                 /* Check dimmed rule */ 
618                 if (!dimmed) {
619                         dimmed = _transfer_mode_enabled (win);                  
620                         if (dimmed)
621                                 modest_dimming_rule_set_notification (rule, _("mail_ib_notavailable_downloading"));
622                 }
623                 if (!dimmed) {
624                         dimmed = _msg_download_in_progress (MODEST_MSG_VIEW_WINDOW (win));
625                         if (dimmed)
626                                 modest_dimming_rule_set_notification (rule, _("mcen_ib_unable_to_reply"));
627                 }
628         }
629         
630         return dimmed;
631 }
632
633
634 gboolean 
635 modest_ui_dimming_rules_on_contents_msg (ModestWindow *win, gpointer user_data)
636 {
637         ModestDimmingRule *rule = NULL;
638         gboolean dimmed = FALSE;
639
640         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
641         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
642         rule = MODEST_DIMMING_RULE (user_data);
643                 
644         /* Check dimmed rule */ 
645         if (!dimmed) {
646                 dimmed = _invalid_msg_selected (MODEST_MAIN_WINDOW(win), FALSE, user_data);
647         }
648         if (!dimmed) {
649                 dimmed = _msg_download_completed (MODEST_MAIN_WINDOW(win));
650                 if (dimmed)
651                         modest_dimming_rule_set_notification (rule, "");
652         }
653
654         return dimmed;
655 }
656
657 gboolean 
658 modest_ui_dimming_rules_always_dimmed (ModestWindow *win, gpointer user_data)
659 {
660         gboolean dimmed = FALSE;
661
662         g_return_val_if_fail (MODEST_IS_WINDOW(win), FALSE);
663                 
664         /* Check dimmed rule */ 
665         if (!dimmed)
666                 dimmed = TRUE;
667
668         return dimmed;
669 }
670
671 gboolean 
672 modest_ui_dimming_rules_on_delete_msg (ModestWindow *win, gpointer user_data)
673 {
674         ModestDimmingRule *rule = NULL;
675         guint n_messages = 0;
676         const DimmedState *state = NULL;
677         gboolean dimmed = FALSE;
678
679         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
680         rule = MODEST_DIMMING_RULE (user_data);
681         state = modest_window_get_dimming_state (win);          
682         
683         /* Check dimmed rule */         
684         if (MODEST_IS_MAIN_WINDOW (win)) {
685                 if (!dimmed) {
686                         dimmed = _selected_folder_is_empty (MODEST_MAIN_WINDOW(win));                   
687                         if (dimmed)
688                                 modest_dimming_rule_set_notification (rule, _CS("ckct_ib_nothing_to_delete"));
689                 }
690                 if (!dimmed) {
691                         dimmed = _invalid_msg_selected (MODEST_MAIN_WINDOW(win), FALSE, user_data);
692                 }
693                 if (!dimmed) {
694                         dimmed = state->already_opened_msg;
695                         n_messages = state->n_selected;
696                         if (dimmed) {
697                                 gchar *num = g_strdup_printf ("%d", n_messages);
698                                 gchar *message = g_strdup_printf(_("mcen_nc_unable_to_delete_n_messages"), num);
699                                 modest_dimming_rule_set_notification (rule, message);
700                                 g_free(message);
701                                 g_free(num);
702                         }
703                         
704                 }
705                 if (!dimmed) {
706                         dimmed = state->any_marked_as_deleted;
707                         if (dimmed) {
708                                 modest_dimming_rule_set_notification (rule, _("mcen_ib_message_already_deleted"));
709                         }
710                 }
711                 if (!dimmed) {
712                         dimmed = state->sent_in_progress;
713                         if (dimmed)
714                                 modest_dimming_rule_set_notification (rule, _CS("ckct_ib_unable_to_delete"));
715                 }
716         } 
717         else if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
718                 if (!dimmed) {
719                         dimmed = _transfer_mode_enabled (win);                  
720                         if (dimmed)
721                                 modest_dimming_rule_set_notification (rule, _("mail_ib_notavailable_downloading"));
722                 }
723                 if (!dimmed) {
724                         dimmed = state->any_marked_as_deleted;
725                         if (dimmed)
726                                 modest_dimming_rule_set_notification (rule, _("mcen_ib_message_already_deleted"));
727                 }
728                 
729                 /* The delete button should be dimmed when viewing an attachment,
730                  * but should be enabled when viewing a message from the list, 
731                  * or when viewing a search result.
732                  */
733                 if (!dimmed) {
734                         if (!modest_msg_view_window_is_search_result (MODEST_MSG_VIEW_WINDOW(win))) {
735                                 dimmed = !modest_msg_view_window_has_headers_model (MODEST_MSG_VIEW_WINDOW(win));
736                                 if (dimmed) {
737                                         modest_dimming_rule_set_notification (rule, _CS("ckct_ib_unable_to_delete"));
738                                 }
739                         }
740                 }
741         }
742
743         return dimmed;
744 }
745
746 gboolean 
747 modest_ui_dimming_rules_on_details (ModestWindow *win, gpointer user_data)
748 {
749         ModestDimmingRule *rule = NULL;
750         GtkWidget *header_view = NULL;
751         gboolean dimmed = FALSE;
752
753         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
754         rule = MODEST_DIMMING_RULE (user_data);
755         
756         /* main window dimming rules */
757         if (MODEST_IS_MAIN_WINDOW(win)) {
758                                 
759                 /* Check dimmed rule */
760                 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
761                                                                    MODEST_WIDGET_TYPE_HEADER_VIEW);
762                 
763                 /* If the header view has the focus: */
764                 if (header_view && gtk_widget_is_focus (header_view)) {
765                         /* Check dimmed rule */ 
766                         if (!dimmed)
767                                 dimmed = _invalid_msg_selected (MODEST_MAIN_WINDOW(win), TRUE, user_data);
768                 }
769                 else {
770                         /* If the folder view has the focus: */
771                         GtkWidget *folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
772                                 MODEST_WIDGET_TYPE_FOLDER_VIEW);
773                         if (folder_view && gtk_widget_is_focus (folder_view)) {
774                                 TnyFolderStore *folder_store
775                                         = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (folder_view));
776                                 if (folder_store) {
777                                         /* Only enable for folders, not accounts,
778                                          * though the UI spec is not clear about that.
779                                          * If we enable this for accounts then we must 
780                                          * add code to handle them in modest_ui_actions_on_details(). */
781                                         if (!TNY_IS_FOLDER(folder_store)) {
782                                                 dimmed = TRUE;
783                                                 modest_dimming_rule_set_notification (rule, "");
784                                         }
785
786                                         g_object_unref (folder_store);
787                                 }
788                         }
789
790                 }
791
792         /* msg view window dimming rules */
793         } else {
794
795                 /* Check dimmed rule */ 
796                 if (!dimmed) {
797                         if (MODEST_IS_MSG_VIEW_WINDOW (win))
798                                 dimmed = _msg_download_in_progress (MODEST_MSG_VIEW_WINDOW (win));
799                         if (dimmed)
800                                 modest_dimming_rule_set_notification (rule, "");
801                 }
802         }
803
804         return dimmed;
805 }
806
807
808 gboolean 
809 modest_ui_dimming_rules_on_mark_as_read_msg (ModestWindow *win, gpointer user_data)
810 {
811         ModestDimmingRule *rule = NULL;
812         TnyHeaderFlags flags;
813         const DimmedState *state = NULL;
814         gboolean dimmed = FALSE;
815
816         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
817         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
818         rule = MODEST_DIMMING_RULE (user_data);
819         state = modest_window_get_dimming_state (win);          
820         
821         flags = TNY_HEADER_FLAG_SEEN; 
822
823         /* Check dimmed rule */ 
824         if (!dimmed) {
825                 dimmed = _invalid_msg_selected (MODEST_MAIN_WINDOW(win), FALSE, user_data);
826         }
827         if (!dimmed) {
828                 dimmed = state->all_marked_as_seen;
829                 if (dimmed)
830                         modest_dimming_rule_set_notification (rule, "");
831         }       
832
833         return dimmed;
834 }
835
836 gboolean 
837 modest_ui_dimming_rules_on_mark_as_unread_msg (ModestWindow *win, gpointer user_data)
838 {
839         ModestDimmingRule *rule = NULL;
840         TnyHeaderFlags flags;
841         const DimmedState *state = NULL;
842         gboolean dimmed = FALSE;
843
844         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
845         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
846         rule = MODEST_DIMMING_RULE (user_data);
847         state = modest_window_get_dimming_state (win);          
848         
849         flags = TNY_HEADER_FLAG_SEEN; 
850
851         /* Check dimmed rule */ 
852         if (!dimmed)
853                 dimmed = _invalid_msg_selected (MODEST_MAIN_WINDOW(win), FALSE, user_data);
854         if (!dimmed) {
855                 dimmed = !state->any_marked_as_seen;
856                 if (dimmed)
857                         modest_dimming_rule_set_notification (rule, "");
858         }
859
860         return dimmed;
861 }
862
863 gboolean 
864 modest_ui_dimming_rules_on_move_to (ModestWindow *win, gpointer user_data)
865 {
866         ModestDimmingRule *rule = NULL;
867         gboolean dimmed = FALSE;
868
869         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
870         rule = MODEST_DIMMING_RULE (user_data);
871
872         if (MODEST_IS_MAIN_WINDOW (win)) 
873                 dimmed = modest_ui_dimming_rules_on_main_window_move_to (win, user_data);
874         else if (MODEST_IS_MSG_VIEW_WINDOW (win)) 
875                  dimmed = modest_ui_dimming_rules_on_view_window_move_to (win, user_data);
876
877         return dimmed;
878 }
879
880
881 gboolean 
882 modest_ui_dimming_rules_on_main_window_move_to (ModestWindow *win, gpointer user_data)
883 {
884         GtkWidget *folder_view = NULL;
885         ModestDimmingRule *rule = NULL;
886         guint n_messages = 0;
887         const DimmedState *state = NULL;
888         gboolean dimmed = FALSE;
889         
890         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), TRUE);
891         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
892         rule = MODEST_DIMMING_RULE (user_data);
893         state = modest_window_get_dimming_state (win);          
894         
895         /* Get the folder view */
896         folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
897                                                            MODEST_WIDGET_TYPE_FOLDER_VIEW);
898
899         
900         /* Check diming rules for folders transfer  */
901         if (gtk_widget_is_focus (folder_view)) {
902                 TnyFolderType types[5];
903                 
904                 types[0] = TNY_FOLDER_TYPE_DRAFTS; 
905                 types[1] = TNY_FOLDER_TYPE_OUTBOX;
906                 types[2] = TNY_FOLDER_TYPE_SENT;
907                 types[3] = TNY_FOLDER_TYPE_ROOT; 
908                 types[4] = TNY_FOLDER_TYPE_INBOX; 
909                 
910                 /* Apply folder rules */        
911                 if (!dimmed) {
912                         dimmed = _selected_folder_not_moveable (MODEST_MAIN_WINDOW(win));
913                         if (dimmed)
914                                 modest_dimming_rule_set_notification (rule, _("emev_bd_unabletomove_items"));
915                 }
916                 if (!dimmed) {
917                         dimmed = _selected_folder_is_any_of_type (win, types, 5);
918                         if (dimmed)
919                                 modest_dimming_rule_set_notification (rule, _("emev_bd_unabletomove_itemsr"));
920                 }
921         }
922         
923         /* Check diming rules for messages transfer  */
924         if (!dimmed) {
925                 dimmed = state->already_opened_msg;
926                 n_messages = state->n_selected;
927                 if (dimmed) {
928                         gchar *message = g_strdup_printf(_("emev_bd_unabletomove_items"), n_messages);
929                         modest_dimming_rule_set_notification (rule, message);
930                         g_free(message);
931                 }
932         }
933         if (!dimmed) {
934                 if (!gtk_widget_is_focus (folder_view))
935                         dimmed = _invalid_msg_selected (MODEST_MAIN_WINDOW(win), FALSE, user_data);
936                 
937         }
938         if (!dimmed) {
939                 dimmed = _selected_msg_sent_in_progress (win);
940                 if (dimmed)
941                         modest_dimming_rule_set_notification (rule, _("sfil_ib_unable_to_move_selected_items"));
942         }
943         
944         return dimmed;
945 }
946
947 gboolean 
948 modest_ui_dimming_rules_on_view_window_move_to (ModestWindow *win, gpointer user_data)
949 {
950         ModestDimmingRule *rule = NULL;
951         gboolean dimmed = FALSE;
952
953         g_return_val_if_fail (MODEST_IS_MSG_VIEW_WINDOW(win), FALSE);
954         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
955         rule = MODEST_DIMMING_RULE (user_data);
956
957         /* Check dimmed rule */ 
958         if (!dimmed) {
959                 dimmed = _transfer_mode_enabled (win);                  
960                 if (dimmed)
961                         modest_dimming_rule_set_notification (rule, _("mail_ib_notavailable_downloading"));
962         }
963         
964         if (!dimmed) {
965                 if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
966                         /* The move_to button should be dimmed when viewing an attachment,
967                          * but should be enabled when viewing a message from the list, 
968                          * or when viewing a search result.
969                          */
970                         if (!modest_msg_view_window_is_search_result (MODEST_MSG_VIEW_WINDOW(win))) {
971                                 dimmed = !modest_msg_view_window_has_headers_model (MODEST_MSG_VIEW_WINDOW (win));
972                         }
973                 }
974                 
975                 if (dimmed) 
976                         modest_dimming_rule_set_notification (rule, _("mcen_ib_unable_to_move_mail_attachment"));
977         }
978
979         return dimmed;
980 }
981
982 gboolean 
983 modest_ui_dimming_rules_on_find_msg (ModestWindow *win, gpointer user_data)
984 {
985         ModestDimmingRule *rule = NULL;
986         gboolean dimmed = FALSE;
987
988         g_return_val_if_fail (MODEST_IS_MSG_VIEW_WINDOW(win), FALSE);
989         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
990         rule = MODEST_DIMMING_RULE (user_data);
991
992         /* Check dimmed rule */ 
993         if (!dimmed) {
994                 dimmed = _transfer_mode_enabled (win);                  
995                 if (dimmed)
996                         modest_dimming_rule_set_notification (rule, _("mail_ib_notavailable_downloading"));
997         }
998
999         return dimmed;
1000 }
1001
1002 gboolean 
1003 modest_ui_dimming_rules_on_paste (ModestWindow *win, gpointer user_data)
1004 {
1005         ModestDimmingRule *rule = NULL;
1006         TnyFolderType types[3];
1007         gboolean dimmed = FALSE;
1008         
1009         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
1010         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
1011         rule = MODEST_DIMMING_RULE (user_data);
1012
1013         types[0] = TNY_FOLDER_TYPE_DRAFTS; 
1014         types[1] = TNY_FOLDER_TYPE_OUTBOX;
1015         types[2] = TNY_FOLDER_TYPE_SENT;
1016         
1017         /* Check dimmed rule */ 
1018         if (!dimmed) {
1019                 dimmed = _clipboard_is_empty (win);
1020                 if (dimmed)
1021                         modest_dimming_rule_set_notification (rule, 
1022                                                               dgettext("hildon-common-strings", 
1023                                                                        "ecoc_ib_edwin_nothing_to_paste"));
1024         }
1025         if (!dimmed) {
1026                 dimmed = _selected_folder_is_any_of_type (win, types, 3);
1027                 if (dimmed)
1028                         modest_dimming_rule_set_notification (rule, 
1029                                                               dgettext("hildon-common-strings", 
1030                                                                        "ckct_ib_unable_to_paste_here"));
1031         }
1032         if (!dimmed) {
1033                 dimmed = !_folder_view_has_focus (win);
1034                 if (dimmed)
1035                         modest_dimming_rule_set_notification (rule,
1036                                         dgettext("hildon-common-strings",
1037                                         "ckct_ib_unable_to_paste_here"));
1038         }
1039         if (!dimmed) {
1040                 dimmed = _selected_folder_not_writeable (MODEST_MAIN_WINDOW(win), TRUE);
1041                 if (dimmed) 
1042                         modest_dimming_rule_set_notification (rule, 
1043                                                               dgettext("hildon-common-strings", 
1044                                                                        "ckct_ib_unable_to_paste_here"));
1045         }
1046         if (!dimmed) {
1047                 dimmed = _selected_folder_is_same_as_source (win);
1048                 if (dimmed)
1049                         modest_dimming_rule_set_notification (rule, _("mcen_ib_unable_to_copy_samefolder"));
1050         }
1051         if (!dimmed) {
1052                 dimmed = _selected_folder_has_subfolder_with_same_name (win);
1053                 if (dimmed)
1054                         modest_dimming_rule_set_notification (rule, _("mcen_ib_unable_to_copy_samefolder"));
1055         }
1056
1057         return dimmed;
1058 }
1059
1060
1061 gboolean 
1062 modest_ui_dimming_rules_on_select_all (ModestWindow *win, gpointer user_data)
1063 {
1064         ModestDimmingRule *rule = NULL;
1065         gboolean dimmed = FALSE;
1066
1067         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
1068         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
1069         rule = MODEST_DIMMING_RULE (user_data);
1070
1071         /* Check dimmed rule */ 
1072         if (!dimmed)
1073                 dimmed = _selected_folder_is_empty (MODEST_MAIN_WINDOW(win));
1074
1075         if (!dimmed)
1076                 dimmed = _header_view_is_all_selected (MODEST_MAIN_WINDOW(win));
1077
1078         if (dimmed)
1079                 modest_dimming_rule_set_notification (rule, "");
1080                 
1081         return dimmed;
1082 }
1083
1084 gboolean 
1085 modest_ui_dimming_rules_on_view_attachments (ModestWindow *win, gpointer user_data)
1086 {
1087         ModestDimmingRule *rule = NULL;
1088         gboolean dimmed = FALSE;
1089
1090         g_return_val_if_fail (MODEST_IS_MSG_VIEW_WINDOW(win), FALSE);
1091         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
1092         rule = MODEST_DIMMING_RULE (user_data);
1093
1094         /* Check dimmed rule */ 
1095         if (!dimmed) 
1096                 dimmed = _invalid_attach_selected (win, TRUE, TRUE, FALSE, rule);                       
1097
1098         if (!dimmed) {
1099                 dimmed = _purged_attach_selected (win, FALSE, NULL);
1100                 if (dimmed) {
1101                         modest_dimming_rule_set_notification (rule, _("mail_ib_attach_not_local"));
1102                 }
1103         }
1104                 
1105         return dimmed;
1106 }
1107
1108 gboolean 
1109 modest_ui_dimming_rules_on_save_attachments (ModestWindow *win, gpointer user_data)
1110 {
1111         ModestDimmingRule *rule = NULL;
1112         gboolean dimmed = FALSE;
1113
1114         g_return_val_if_fail (MODEST_IS_MSG_VIEW_WINDOW(win), FALSE);
1115         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
1116         rule = MODEST_DIMMING_RULE (user_data);
1117
1118         /* Check dimmed rule */ 
1119         if (!dimmed) 
1120                 dimmed = _invalid_attach_selected (win, FALSE, FALSE, FALSE, rule);
1121
1122         if (!dimmed) {
1123                 dimmed = _purged_attach_selected (win, FALSE, NULL);
1124                 if (dimmed) {
1125                         modest_dimming_rule_set_notification (rule, _("mail_ib_attach_not_local"));
1126                 }
1127         }
1128                 
1129         return dimmed;
1130 }
1131
1132 gboolean 
1133 modest_ui_dimming_rules_on_remove_attachments (ModestWindow *win, gpointer user_data)
1134 {
1135         ModestDimmingRule *rule = NULL;
1136         const DimmedState *state = NULL;
1137         gboolean dimmed = FALSE;
1138
1139         g_return_val_if_fail (MODEST_IS_WINDOW(win), FALSE);
1140         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
1141         rule = MODEST_DIMMING_RULE (user_data);
1142         state = modest_window_get_dimming_state (win);          
1143
1144         /* Check in main window if there's only one message selected */
1145         if (!dimmed && MODEST_IS_MAIN_WINDOW (win)) {
1146                 dimmed = _invalid_msg_selected (MODEST_MAIN_WINDOW (win), TRUE, rule);
1147         }
1148
1149         /* Check in view window if there's any attachment selected */
1150         if (!dimmed && MODEST_IS_MSG_VIEW_WINDOW (win)) {
1151                 dimmed = _invalid_attach_selected (win, FALSE, FALSE, TRUE, NULL);
1152                 if (dimmed)
1153                         modest_dimming_rule_set_notification (rule, _("FIXME:no attachment selected"));
1154         }
1155
1156         /* cannot purge in editable drafts nor pop folders */
1157         if (!dimmed) {
1158                 dimmed = _invalid_folder_for_purge (win, rule);
1159         }
1160
1161         /* Check if the selected message in main window has attachments */
1162         if (!dimmed && MODEST_IS_MAIN_WINDOW (win)) {
1163                 dimmed = state->any_has_attachments;
1164                 if (dimmed)
1165                         modest_dimming_rule_set_notification (rule, _("mail_ib_unable_to_purge_attachments"));
1166         }
1167
1168         /* Check if all attachments are already purged */
1169         if (!dimmed) {
1170                 dimmed = _purged_attach_selected (win, TRUE, rule);
1171         }
1172
1173         /* Check if the message is already downloaded */
1174         if (!dimmed && MODEST_IS_MAIN_WINDOW (win)) {
1175                 dimmed = !_msg_download_completed (MODEST_MAIN_WINDOW (win));
1176                 if (dimmed)
1177                         modest_dimming_rule_set_notification (rule, _("mail_ib_attach_not_local"));
1178         }
1179
1180
1181         return dimmed;
1182 }
1183
1184 gboolean 
1185 modest_ui_dimming_rules_on_undo (ModestWindow *win, gpointer user_data)
1186 {
1187         ModestDimmingRule *rule = NULL;
1188         gboolean dimmed = FALSE;
1189         
1190         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
1191         rule = MODEST_DIMMING_RULE (user_data);
1192
1193         /* Check dimmed rule */ 
1194         if (!dimmed) {
1195                 dimmed = _clipboard_is_empty (win); 
1196                 if (dimmed)
1197                         modest_dimming_rule_set_notification (rule, "");
1198         }
1199                                 
1200         return dimmed;  
1201 }
1202
1203 gboolean 
1204 modest_ui_dimming_rules_on_cut (ModestWindow *win, gpointer user_data)
1205 {
1206         ModestDimmingRule *rule = NULL;
1207         const DimmedState *state = NULL;
1208         gboolean dimmed = FALSE;
1209         
1210         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
1211         rule = MODEST_DIMMING_RULE (user_data);
1212         state = modest_window_get_dimming_state (win);
1213
1214         /* Check common dimming rules */
1215         if (!dimmed) {
1216                 dimmed = _invalid_clipboard_selected (win, rule);
1217         }
1218
1219         /* Check window specific dimming rules */
1220         if (MODEST_IS_MAIN_WINDOW (win)) {
1221                 /* Get focused widget */
1222                 GtkWidget *focused = gtk_window_get_focus (GTK_WINDOW (win));
1223                 
1224                 if (MODEST_IS_HEADER_VIEW (focused)) {
1225                         if (!dimmed) { 
1226                                 dimmed = _selected_folder_is_empty (MODEST_MAIN_WINDOW(win));                   
1227                                 if (dimmed)
1228                                         modest_dimming_rule_set_notification (rule, "");
1229                         }
1230                         if (!dimmed) {
1231                                 dimmed = _selected_msg_sent_in_progress (win);
1232                                 if (dimmed)
1233                                         modest_dimming_rule_set_notification (rule, _("mcen_ib_unable_to_cut_mess"));
1234                         }
1235                         if (!dimmed) {
1236                                 dimmed = state->already_opened_msg;
1237                                 if(dimmed)
1238                                         modest_dimming_rule_set_notification (rule, _("mcen_ib_unable_to_cut_mess"));
1239                         }
1240                 }
1241                 else if (MODEST_IS_FOLDER_VIEW (focused)) {
1242                         TnyFolderType types[3];
1243                         
1244                         types[0] = TNY_FOLDER_TYPE_DRAFTS; 
1245                         types[1] = TNY_FOLDER_TYPE_OUTBOX;
1246                         types[2] = TNY_FOLDER_TYPE_SENT;
1247                         
1248                         /* Apply folder rules */        
1249                         if (!dimmed) {
1250                                 dimmed = _selected_folder_not_deletable (MODEST_MAIN_WINDOW(win));
1251                                 if (dimmed)
1252                                         modest_dimming_rule_set_notification (rule, _("emev_bd_unabletomove_items"));
1253                         }
1254                         if (!dimmed) {
1255                                 dimmed = _selected_folder_is_root_or_inbox (MODEST_MAIN_WINDOW(win));
1256                                 if (dimmed)
1257                                         modest_dimming_rule_set_notification (rule, _("emev_bd_unabletomove_itemsr"));
1258                         }
1259                         if (!dimmed) {
1260                                 dimmed = _selected_folder_is_any_of_type (win, types, 3);
1261                                 if (dimmed)
1262                                         modest_dimming_rule_set_notification (rule, _("emev_bd_unabletomove_itemsr"));
1263                         }
1264                 }
1265         }
1266
1267         return dimmed;
1268 }
1269
1270 gboolean 
1271 modest_ui_dimming_rules_on_copy (ModestWindow *win, gpointer user_data)
1272 {
1273         ModestDimmingRule *rule = NULL;
1274         const DimmedState *state = NULL;
1275         gboolean dimmed = FALSE;
1276         
1277         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
1278         rule = MODEST_DIMMING_RULE (user_data);
1279         state = modest_window_get_dimming_state (win);
1280
1281         /* Check common dimming rules */
1282         if (!dimmed) {
1283                 dimmed = _invalid_clipboard_selected (win, rule);
1284         }
1285         
1286         /* Check window specific dimming rules */
1287         if (MODEST_IS_MAIN_WINDOW (win)) {
1288                 /* Get focused widget */
1289                 GtkWidget *focused = gtk_window_get_focus (GTK_WINDOW (win));
1290                 
1291                 if (MODEST_IS_HEADER_VIEW (focused)) {
1292                         if (!dimmed) {
1293                                 dimmed = _selected_folder_is_empty (MODEST_MAIN_WINDOW(win));                   
1294                                 if (dimmed)
1295                                         modest_dimming_rule_set_notification (rule, "");
1296                         }               
1297                         if (!dimmed) {
1298                                 dimmed = _selected_msg_sent_in_progress (win);
1299                                 if (dimmed)
1300                                         modest_dimming_rule_set_notification (rule, _(""));
1301                         }
1302                         if (!dimmed) {
1303                                 dimmed = state->already_opened_msg;
1304                                 if(dimmed)
1305                                         modest_dimming_rule_set_notification (rule, _(""));
1306                         }
1307                 }
1308                 else if (MODEST_IS_FOLDER_VIEW (focused)) {
1309                         TnyFolderType types[3];
1310                         
1311                         types[0] = TNY_FOLDER_TYPE_DRAFTS; 
1312                         types[1] = TNY_FOLDER_TYPE_OUTBOX;
1313                         types[2] = TNY_FOLDER_TYPE_SENT;
1314
1315                         if (!dimmed) {
1316                                 dimmed = _selected_folder_is_root (MODEST_MAIN_WINDOW(win));
1317                                 if (dimmed)
1318                                         modest_dimming_rule_set_notification (rule, _(""));
1319                         }
1320                         if (!dimmed) {
1321                                 dimmed = _selected_folder_is_any_of_type (win, types, 3);
1322                                 if (dimmed)
1323                                         modest_dimming_rule_set_notification (rule, _(""));
1324                         }
1325                 }
1326         }
1327                 
1328         return dimmed;
1329 }
1330
1331 gboolean 
1332 modest_ui_dimming_rules_on_view_previous (ModestWindow *win, gpointer user_data)
1333 {
1334         ModestDimmingRule *rule = NULL;
1335         gboolean dimmed = FALSE;
1336         
1337         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
1338         rule = MODEST_DIMMING_RULE (user_data);
1339
1340         g_return_val_if_fail (MODEST_IS_MSG_VIEW_WINDOW(win), FALSE);
1341
1342         /* Check dimmed rule */
1343         if (!dimmed) {
1344                 dimmed = _transfer_mode_enabled (win);
1345                 if (dimmed)
1346                         modest_dimming_rule_set_notification (
1347                                         rule, _("mail_ib_notavailable_downloading"));
1348         }
1349         if (!dimmed) {
1350                 dimmed = modest_msg_view_window_first_message_selected (
1351                                 MODEST_MSG_VIEW_WINDOW(win));
1352                 modest_dimming_rule_set_notification (rule, NULL);
1353         }
1354
1355         return dimmed;
1356 }
1357
1358 gboolean 
1359 modest_ui_dimming_rules_on_view_next (ModestWindow *win, gpointer user_data)
1360 {
1361         ModestDimmingRule *rule = NULL;
1362         gboolean dimmed = FALSE;
1363
1364         g_return_val_if_fail (MODEST_IS_MSG_VIEW_WINDOW(win), FALSE);
1365         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
1366         rule = MODEST_DIMMING_RULE (user_data);
1367
1368         /* Check dimmed rule */ 
1369         if (!dimmed) {
1370                 dimmed = _transfer_mode_enabled (win);                  
1371                 if (dimmed)
1372                         modest_dimming_rule_set_notification (rule, _("mail_ib_notavailable_downloading"));
1373         }
1374         if (!dimmed) {
1375                 dimmed = modest_msg_view_window_last_message_selected (MODEST_MSG_VIEW_WINDOW (win));
1376                 modest_dimming_rule_set_notification (rule, NULL);
1377         }               
1378
1379         return dimmed;
1380 }
1381
1382
1383 gboolean 
1384 modest_ui_dimming_rules_on_tools_smtp_servers (ModestWindow *win, gpointer user_data)
1385 {
1386         const gboolean dimmed = 
1387                 !modest_account_mgr_has_accounts(modest_runtime_get_account_mgr(), 
1388                         TRUE);  
1389                 
1390         return dimmed;
1391 }
1392
1393 gboolean 
1394 modest_ui_dimming_rules_on_cancel_sending (ModestWindow *win, gpointer user_data)
1395 {
1396         ModestDimmingRule *rule = NULL;
1397         TnyFolderType types[1];
1398         guint n_messages = 0;
1399         const DimmedState *state = NULL;
1400         gboolean dimmed = FALSE;
1401
1402         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
1403         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
1404         rule = MODEST_DIMMING_RULE (user_data);
1405         state = modest_window_get_dimming_state (win);
1406
1407         types[0] = TNY_FOLDER_TYPE_OUTBOX; 
1408
1409         /* Check dimmed rules */        
1410         if (!dimmed) {
1411                 dimmed = state->already_opened_msg;
1412                 n_messages = state->n_selected;
1413                 if (dimmed) 
1414                         modest_dimming_rule_set_notification (rule, _("mcen_ib_message_unableto_cancel_send"));
1415         }
1416         if (!dimmed) {
1417                 dimmed = !_selected_folder_is_any_of_type (win, types, 1);
1418                 if (dimmed) 
1419                         modest_dimming_rule_set_notification (rule, "");
1420         }
1421         if (!dimmed) {
1422                 dimmed = !_sending_in_progress (win);
1423                 if (dimmed)
1424                         modest_dimming_rule_set_notification (rule, "");
1425         }
1426
1427         return dimmed;
1428 }
1429
1430 gboolean 
1431 modest_ui_dimming_rules_on_send_receive (ModestWindow *win, gpointer user_data)
1432 {
1433         ModestDimmingRule *rule = NULL;
1434         gboolean dimmed = FALSE;
1435         
1436         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
1437         rule = MODEST_DIMMING_RULE (user_data);
1438  
1439         /* Check dimmed rule */ 
1440         if (!dimmed) {
1441                 dimmed = !modest_account_mgr_has_accounts(modest_runtime_get_account_mgr(), 
1442                                                           TRUE);        
1443                 if (dimmed)
1444                         modest_dimming_rule_set_notification (rule, _("mcen_nc_no_email_acnts_defined"));
1445         }
1446
1447         return dimmed;
1448 }
1449
1450 gboolean
1451 modest_ui_dimming_rules_on_add_to_contacts (ModestWindow *win, gpointer user_data)
1452 {
1453         ModestDimmingRule *rule = NULL;
1454         gboolean dimmed = FALSE;
1455
1456         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (user_data), FALSE);
1457         rule = MODEST_DIMMING_RULE (user_data);
1458
1459         /* Check dimmed rule */
1460         if (!dimmed) {
1461                 GtkClipboard *clipboard = gtk_clipboard_get (GDK_SELECTION_PRIMARY);
1462                 gchar *selection = NULL;
1463                 selection = gtk_clipboard_wait_for_text (clipboard);
1464
1465                 dimmed = !((selection != NULL) && (modest_text_utils_validate_recipient (selection, NULL)));
1466         }
1467
1468         return dimmed;
1469 }
1470
1471 /* *********************** static utility functions ******************** */
1472
1473
1474 static gboolean
1475 _selected_folder_not_writeable (ModestMainWindow *win,
1476                                 gboolean for_paste)
1477 {
1478         GtkWidget *folder_view = NULL;
1479         TnyFolderStore *parent_folder = NULL;
1480         ModestEmailClipboard *clipboard = NULL;
1481         ModestTnyFolderRules rules;
1482         gboolean is_local_acc = FALSE;
1483         gboolean xfer_folders = FALSE;
1484         gboolean result = FALSE;
1485
1486         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
1487
1488         /* Get folder view */
1489         folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
1490                                                            MODEST_WIDGET_TYPE_FOLDER_VIEW);
1491         /* If no folder view, always dimmed */
1492         if (!folder_view)
1493                 return TRUE;
1494         
1495         /* Get selected folder as parent of new folder to create */
1496         parent_folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW(folder_view));
1497         if (!(parent_folder && TNY_IS_FOLDER(parent_folder))) {
1498                 /* If it's the local account and its transfering folders, then do not dim */            
1499                 if (TNY_IS_ACCOUNT (parent_folder)) {
1500                         is_local_acc = modest_tny_account_is_virtual_local_folders (TNY_ACCOUNT (parent_folder));
1501                         if (for_paste) {
1502                                 clipboard = modest_runtime_get_email_clipboard ();
1503                                 xfer_folders = modest_email_clipboard_folder_copied (clipboard);
1504                         }
1505                 }
1506
1507                 if (for_paste) 
1508                         result = !(is_local_acc && xfer_folders); 
1509                 else
1510                         result = !is_local_acc;
1511                 goto frees;             
1512         }
1513         
1514         /* Check dimmed rule */ 
1515         rules = modest_tny_folder_get_rules (TNY_FOLDER (parent_folder));
1516         result = rules & MODEST_FOLDER_RULES_FOLDER_NON_WRITEABLE;
1517
1518         /* free */
1519  frees:
1520         if (parent_folder != NULL)
1521                 g_object_unref (parent_folder);
1522
1523         return result;
1524 }
1525
1526 static gboolean
1527 _selected_folder_not_deletable (ModestMainWindow *win)
1528 {
1529         GtkWidget *folder_view = NULL;
1530         TnyFolderStore *parent_folder = NULL;
1531         ModestTnyFolderRules rules;
1532         gboolean result = FALSE;
1533
1534         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
1535
1536         /* Get folder view */
1537         folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
1538                                                            MODEST_WIDGET_TYPE_FOLDER_VIEW);
1539         /* If no folder view, always dimmed */
1540         if (!folder_view)
1541                 return TRUE;
1542         
1543         /* Get selected folder as parent of new folder to create */
1544         parent_folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW(folder_view));
1545         if (!(parent_folder && TNY_IS_FOLDER(parent_folder))) {
1546                 result = TRUE;
1547                 goto frees;             
1548         }
1549         
1550         /* Check dimmed rule */ 
1551         rules = modest_tny_folder_get_rules (TNY_FOLDER (parent_folder));
1552         result = rules & MODEST_FOLDER_RULES_FOLDER_NON_DELETABLE;
1553
1554         /* free */
1555  frees:
1556         if (parent_folder != NULL)
1557                 g_object_unref (parent_folder);
1558
1559         return result;
1560 }
1561
1562 static gboolean
1563 _selected_folder_not_moveable (ModestMainWindow *win)
1564 {
1565         GtkWidget *folder_view = NULL;
1566         TnyFolderStore *parent_folder = NULL;
1567         ModestTnyFolderRules rules;
1568         gboolean result = FALSE;
1569
1570         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
1571
1572         /* Get folder view */
1573         folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
1574                                                            MODEST_WIDGET_TYPE_FOLDER_VIEW);
1575         /* If no folder view, always dimmed */
1576         if (!folder_view)
1577                 return TRUE;
1578         
1579         /* Get selected folder as parent of new folder to create */
1580         parent_folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW(folder_view));
1581         if (!(parent_folder && TNY_IS_FOLDER(parent_folder))) {
1582                 result = TRUE;
1583                 goto frees;             
1584         }
1585         
1586         /* Check dimmed rule */ 
1587         rules = modest_tny_folder_get_rules (TNY_FOLDER (parent_folder));
1588         result = rules & MODEST_FOLDER_RULES_FOLDER_NON_MOVEABLE;
1589
1590         /* free */
1591  frees:
1592         if (parent_folder != NULL)
1593                 g_object_unref (parent_folder);
1594
1595         return result;
1596 }
1597
1598 static gboolean
1599 _selected_folder_not_renameable (ModestMainWindow *win)
1600 {
1601         GtkWidget *folder_view = NULL;
1602         TnyFolderStore *parent_folder = NULL;
1603         ModestTnyFolderRules rules;
1604         gboolean result = FALSE;
1605
1606         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
1607
1608         /* Get folder view */
1609         folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
1610                                                            MODEST_WIDGET_TYPE_FOLDER_VIEW);
1611         /* If no folder view, always dimmed */
1612         if (!folder_view)
1613                 return TRUE;
1614         
1615         /* Get selected folder as parent of new folder to create */
1616         parent_folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW(folder_view));
1617         if (!(parent_folder && TNY_IS_FOLDER(parent_folder))) {
1618                 result = TRUE;
1619                 goto frees;             
1620         }
1621         
1622         /* Check dimmed rule */ 
1623         rules = modest_tny_folder_get_rules (TNY_FOLDER (parent_folder));
1624         result = rules & MODEST_FOLDER_RULES_FOLDER_NON_RENAMEABLE;
1625
1626         /* free */
1627  frees:
1628         if (parent_folder != NULL)
1629                 g_object_unref (parent_folder);
1630
1631         return result;
1632 }
1633
1634 static gboolean
1635 _selected_folder_is_root_or_inbox (ModestMainWindow *win)
1636 {
1637         TnyFolderType types[2];
1638         gboolean result = FALSE;
1639
1640         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
1641
1642         types[0] = TNY_FOLDER_TYPE_ROOT; 
1643         types[1] = TNY_FOLDER_TYPE_INBOX; 
1644
1645         /* Check folder type */
1646         result = _selected_folder_is_any_of_type (MODEST_WINDOW(win), types, 2);
1647
1648         /* Check pop and MMC accounts */
1649         if (!result) {
1650                 result = _selected_folder_is_MMC_or_POP_root (win);
1651         }
1652                 
1653         return result;
1654 }
1655
1656
1657 static gboolean
1658 _selected_folder_is_root (ModestMainWindow *win)
1659 {
1660         TnyFolderType types[1];
1661         gboolean result = FALSE;
1662
1663         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
1664
1665         /* All accounts are root items: */
1666         GtkWidget *folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
1667                                                            MODEST_WIDGET_TYPE_FOLDER_VIEW);
1668         if (folder_view) {                                      
1669                 gboolean is_account = FALSE;
1670                 TnyFolderStore *folder_store = 
1671                         modest_folder_view_get_selected (MODEST_FOLDER_VIEW(folder_view));
1672                 if (folder_store) {
1673                         is_account = TNY_IS_ACCOUNT (folder_store);
1674                         g_object_unref (folder_store);
1675                         folder_store = NULL;
1676                 }
1677                 
1678                 if (is_account)
1679                         return TRUE;
1680         }
1681                 
1682         /* Try something more precise: */
1683         types[0] = TNY_FOLDER_TYPE_ROOT; 
1684
1685         /* Check folder type */
1686         result = _selected_folder_is_any_of_type (MODEST_WINDOW(win), types, 1);
1687                 
1688         /* Check pop and MMC accounts */
1689         if (!result) {
1690                 result = _selected_folder_is_MMC_or_POP_root (win);
1691         }
1692
1693         return result;
1694 }
1695
1696 static gboolean
1697 _selected_folder_is_MMC_or_POP_root (ModestMainWindow *win)
1698 {
1699         GtkWidget *folder_view = NULL;
1700         TnyFolderStore *parent_folder = NULL;
1701         gboolean result = FALSE;
1702
1703         folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
1704                                                            MODEST_WIDGET_TYPE_FOLDER_VIEW);
1705         if (!folder_view)
1706                 return FALSE;
1707
1708         /* Get selected folder as parent of new folder to create */
1709         parent_folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW(folder_view));
1710         if (!parent_folder)
1711                 return TRUE;
1712         
1713         if (TNY_IS_ACCOUNT (parent_folder)) {
1714                 /* If it's the local account then do not dim */
1715                 if (modest_tny_account_is_virtual_local_folders (TNY_ACCOUNT (parent_folder))) {
1716                         result = FALSE;
1717                 } else {
1718                                 /* If it's the MMC root folder then dim it */
1719                         if (!strcmp (tny_account_get_id (TNY_ACCOUNT (parent_folder)), MODEST_MMC_ACCOUNT_ID)) {
1720                                         result = TRUE;
1721                         } else {
1722                                 const gchar *proto_str = tny_account_get_proto (TNY_ACCOUNT (parent_folder));
1723                                 /* If it's POP then dim */
1724                                 result = (modest_protocol_info_get_transport_store_protocol (proto_str) == 
1725                                                   MODEST_PROTOCOL_STORE_POP) ? TRUE : FALSE;
1726                         }
1727                 }
1728         }
1729         g_object_unref (parent_folder);
1730
1731         return result;
1732 }
1733
1734 static gboolean
1735 _header_view_is_all_selected (ModestMainWindow *win)
1736 {
1737         const DimmedState *state = NULL;
1738
1739         g_return_val_if_fail (MODEST_IS_WINDOW(win), FALSE);
1740
1741         state = modest_window_get_dimming_state (MODEST_WINDOW(win));
1742
1743         return state->all_selected;
1744 }
1745
1746 static gboolean
1747 _selected_folder_is_empty (ModestMainWindow *win)
1748 {
1749         GtkWidget *folder_view = NULL;
1750         TnyFolderStore *folder = NULL;
1751         gboolean result = FALSE;
1752
1753         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
1754
1755         /* Get folder view */
1756         folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
1757                                                            MODEST_WIDGET_TYPE_FOLDER_VIEW);
1758         /* If no folder view, always dimmed */
1759         if (!folder_view)
1760                 return TRUE;
1761         
1762         /* Get selected folder as parent of new folder to create */
1763         folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW(folder_view));
1764         if (!(folder && TNY_IS_FOLDER(folder))) {
1765                 if (folder)
1766                         g_object_unref (folder);
1767                 return TRUE;
1768         }
1769         
1770         /* Check folder type */
1771         result = tny_folder_get_all_count (TNY_FOLDER (folder)) == 0;
1772
1773         /* free */
1774         g_object_unref (folder);
1775
1776         return result;
1777 }
1778
1779 static gboolean
1780 _folder_view_has_focus (ModestWindow *win)
1781 {
1782         GtkWidget *folder_view = NULL;
1783
1784         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
1785
1786         /* Get folder view */
1787         folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
1788                                                            MODEST_WIDGET_TYPE_FOLDER_VIEW);
1789         if (!folder_view)
1790                 return FALSE;
1791         
1792         if (gtk_widget_is_focus(folder_view))
1793                 return TRUE;
1794
1795         return FALSE;
1796 }
1797
1798 static gboolean
1799 _selected_folder_is_same_as_source (ModestWindow *win)
1800 {
1801         ModestEmailClipboard *clipboard = NULL;
1802         GtkWidget *folder_view = NULL;
1803         TnyFolderStore *folder = NULL;
1804         gboolean result = FALSE;
1805
1806         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
1807
1808         /* Get folder view */
1809         folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
1810                                                            MODEST_WIDGET_TYPE_FOLDER_VIEW);
1811         if (!folder_view)
1812                 return FALSE;
1813         
1814         /* Get selected folder as destination folder */
1815         folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW(folder_view));
1816         if (!(folder && TNY_IS_FOLDER(folder))) {
1817                 result = FALSE;
1818                 goto frees;
1819         }
1820         
1821         /* Check clipboard is cleared */
1822         clipboard = modest_runtime_get_email_clipboard ();
1823         if (modest_email_clipboard_cleared (clipboard)) {
1824                 result = FALSE;
1825                 goto frees;
1826         }
1827                 
1828         /* Check source folder */
1829         result = modest_email_clipboard_check_source_folder (clipboard, 
1830                                                              (const TnyFolder *) folder);
1831         
1832         /* Free */
1833  frees:
1834         g_object_unref (folder);
1835         
1836         return result;
1837 }
1838
1839 static gboolean
1840 _selected_folder_is_any_of_type (ModestWindow *win,
1841                                  TnyFolderType types[], 
1842                                  guint ntypes)
1843 {
1844         GtkWidget *folder_view = NULL;
1845         TnyFolderStore *folder = NULL;
1846         TnyFolderType folder_type;
1847         guint i=0;
1848         gboolean result = FALSE;
1849
1850         /*Get current folder */
1851         if (MODEST_IS_MAIN_WINDOW(win)) {
1852
1853                 /* Get folder view */
1854                 folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
1855                                                                    MODEST_WIDGET_TYPE_FOLDER_VIEW);
1856                 /* If no folder view, always dimmed */
1857                 if (!folder_view)
1858                         return FALSE;
1859         
1860                 /* Get selected folder as parent of new folder to create */
1861                 folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW(folder_view));
1862
1863                 if (!(folder && TNY_IS_FOLDER(folder))) {
1864                         if (folder)
1865                                 g_object_unref (folder);
1866                         return FALSE;
1867                 }
1868                 
1869                 /* Check folder type */
1870                 result = _folder_is_any_of_type (TNY_FOLDER(folder), types, ntypes);
1871         }
1872         else if (MODEST_IS_MSG_VIEW_WINDOW(win)) {
1873                 folder_type = modest_msg_view_window_get_folder_type (MODEST_MSG_VIEW_WINDOW (win));
1874                 for (i=0; i < ntypes; i++) {
1875                         result = result || folder_type == types[i];
1876                 }
1877         }
1878
1879
1880         /* free */
1881         g_object_unref (folder);
1882
1883         return result;  
1884 }
1885
1886 static gboolean
1887 _folder_is_any_of_type (TnyFolder *folder,
1888                         TnyFolderType types[], 
1889                         guint ntypes)
1890 {
1891         TnyFolderType folder_type;
1892         gboolean result = FALSE;
1893         guint i;
1894
1895         g_return_val_if_fail (TNY_IS_FOLDER(folder), FALSE);
1896
1897         /* Get folder type */
1898         folder_type = modest_tny_folder_guess_folder_type (folder);
1899                 
1900         /* Check foler type */
1901         for (i=0; i < ntypes; i++) {
1902                 result = result || folder_type == types[i];
1903         }
1904
1905         return result;
1906 }
1907
1908 static gboolean
1909 _clipboard_is_empty (ModestWindow *win)
1910 {
1911         gboolean result = FALSE;
1912         
1913         if (MODEST_IS_MAIN_WINDOW (win)) {
1914                 ModestEmailClipboard *clipboard = NULL;
1915                 clipboard = modest_runtime_get_email_clipboard ();
1916                 if (modest_email_clipboard_cleared (clipboard)) 
1917                  result = TRUE;  
1918         }
1919
1920         return result;
1921 }
1922
1923 static gboolean
1924 _invalid_clipboard_selected (ModestWindow *win,
1925                              ModestDimmingRule *rule) 
1926 {
1927         const DimmedState *state = NULL;
1928         gboolean result = FALSE;
1929
1930         g_return_val_if_fail (MODEST_IS_WINDOW(win), FALSE);
1931         state = modest_window_get_dimming_state (win);
1932
1933         if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
1934                 GtkClipboard *clipboard = NULL;
1935                 gchar *selection = NULL;
1936                 GtkWidget *focused = NULL;
1937
1938                 /* Get clipboard selection*/
1939                 clipboard = gtk_clipboard_get (GDK_SELECTION_PRIMARY);
1940                 selection = gtk_clipboard_wait_for_text (clipboard);
1941
1942                 /* Get focuesed widget */
1943                 focused = gtk_window_get_focus (GTK_WINDOW (win));
1944
1945                 /* Check dimming */
1946                 result = ((selection == NULL) || 
1947                           (MODEST_IS_ATTACHMENTS_VIEW (focused)));
1948                 
1949                 if (result)
1950                         modest_dimming_rule_set_notification (rule, "");
1951                 
1952                 if (selection != NULL) 
1953                         g_free(selection);
1954         }               
1955         else if (MODEST_IS_MAIN_WINDOW (win)) {
1956                 /* Check dimming */
1957                 result = state->n_selected == 0;
1958                 if (result)
1959                         modest_dimming_rule_set_notification (rule, _("mcen_ib_no_message_selected"));                  
1960         }
1961         
1962         return result;
1963 }
1964
1965
1966 static gboolean
1967 _invalid_attach_selected (ModestWindow *win,
1968                           gboolean unique,
1969                           gboolean for_view,
1970                           gboolean for_remove,
1971                           ModestDimmingRule *rule) 
1972 {
1973         GList *attachments, *node;
1974         gint n_selected;
1975         TnyHeaderFlags flags;
1976         gboolean nested_attachments = FALSE;
1977         gboolean selected_messages = FALSE;
1978         const DimmedState *state = NULL;
1979         gboolean result = FALSE;
1980
1981         g_return_val_if_fail (MODEST_IS_WINDOW(win), FALSE);
1982         state = modest_window_get_dimming_state (win);
1983
1984         if (MODEST_IS_MAIN_WINDOW (win)) {
1985                 flags = TNY_HEADER_FLAG_ATTACHMENTS;
1986                 if (!result)
1987                         result = !state->any_has_attachments;
1988         }
1989         else if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
1990                 
1991                 /* Get selected atachments */
1992                 attachments = modest_msg_view_window_get_attachments (MODEST_MSG_VIEW_WINDOW(win));
1993                 n_selected = g_list_length (attachments);
1994
1995                 /* Check unique */              
1996                 if (!result) {
1997                         if (unique) 
1998                                 result = n_selected != 1;
1999                         else
2000                                 
2001                                 result = n_selected < 1;
2002                 }
2003                 
2004                 /* Check attached type (view operation not required) */
2005                 if (!result && !for_view)  {
2006                         for (node = attachments; node != NULL && !result; node = g_list_next (node)) {
2007                                 TnyMimePart *mime_part = TNY_MIME_PART (node->data);
2008                                 TnyList *nested_list = tny_simple_list_new ();
2009                                 if (!for_remove && TNY_IS_MSG (mime_part)) {
2010                                         selected_messages = TRUE;
2011                                         result = TRUE;
2012                                 }
2013                                 tny_mime_part_get_parts (mime_part, nested_list);
2014                                 if (!for_remove && tny_list_get_length (nested_list) > 0) {
2015                                         nested_attachments = TRUE;
2016                                         result = TRUE;
2017                                 }
2018                                 g_object_unref (nested_list);
2019                         }
2020                 }
2021                 
2022                 /* Set notifications */
2023                 if (result && rule != NULL) {
2024                         if (selected_messages) {
2025                                 modest_dimming_rule_set_notification (rule, _("mcen_ib_unable_to_save_attach_mail"));
2026                         } else if (nested_attachments) {
2027                                 modest_dimming_rule_set_notification (rule, _("FIXME:unable to save attachments with nested elements"));
2028                         } else if (n_selected == 0) {
2029                                 modest_dimming_rule_set_notification (rule, _("FIXME:no attachment selected"));
2030                         } else if (unique) {
2031                                 modest_dimming_rule_set_notification (rule, _("mcen_ib_unable_to_display_more"));
2032                         }
2033                 }
2034                 
2035                 /* Free */
2036                 g_list_free (attachments);
2037         }
2038
2039         return result;
2040 }
2041
2042 static gboolean
2043 _purged_attach_selected (ModestWindow *win, gboolean all, ModestDimmingRule *rule) 
2044 {
2045         GList *attachments = NULL, *node;
2046         gint purged = 0;
2047         gint n_attachments = 0;
2048         gboolean result = FALSE;
2049
2050         /* This should check if _all_ the attachments are already purged. If only some
2051          * of them are purged, then it does not cause dim as there's a confirmation dialog
2052          * for removing only local attachments */
2053
2054         /* Get selected atachments */
2055         if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
2056                 attachments = modest_msg_view_window_get_attachments (MODEST_MSG_VIEW_WINDOW(win));
2057         } else if (MODEST_IS_MAIN_WINDOW (win)) {
2058                 /* If we're in main window, we won't know if there are already purged attachments */
2059                 return FALSE;
2060         }
2061
2062         if (attachments == NULL)
2063                 return FALSE;
2064
2065         for (node = attachments; node != NULL; node = g_list_next (node)) {
2066                 TnyMimePart *mime_part = TNY_MIME_PART (node->data);
2067                 if (tny_mime_part_is_purged (mime_part)) {
2068                         purged++;
2069                 }
2070                 n_attachments++;
2071         }
2072                 
2073         /* Free */
2074         g_list_free (attachments);
2075
2076         if (all)
2077                 result = (purged == n_attachments);
2078         else
2079                 result = (purged > 0);
2080
2081         if (result && (rule != NULL))
2082                 modest_dimming_rule_set_notification (rule, _("mail_ib_attachment_already_purged"));
2083
2084         return result;
2085 }
2086
2087 static gboolean
2088 _invalid_msg_selected (ModestMainWindow *win,
2089                        gboolean unique,
2090                        ModestDimmingRule *rule) 
2091 {
2092         GtkWidget *folder_view = NULL;
2093         const DimmedState *state = NULL;
2094         gboolean result = FALSE;
2095
2096         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), FALSE);
2097         g_return_val_if_fail (MODEST_IS_DIMMING_RULE (rule), FALSE);
2098         state = modest_window_get_dimming_state (MODEST_WINDOW(win));
2099                 
2100         /* Get folder view to check focus */
2101         folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
2102                                                            MODEST_WIDGET_TYPE_FOLDER_VIEW);
2103
2104         /* Check dimmed rule (TODO: check focus on widgets */   
2105         if (!result) {
2106                 result = ((state->n_selected == 0 ) ||
2107                           (gtk_widget_is_focus (folder_view)));
2108                 if (result)
2109                         modest_dimming_rule_set_notification (rule, _("mcen_ib_no_message_selected"));
2110         }
2111         if (!result && unique) {
2112                 result = state->n_selected > 1;
2113                 if (result)
2114                         modest_dimming_rule_set_notification (rule, _("mcen_ib_select_one_message"));
2115         }
2116
2117         return result;
2118 }
2119
2120
2121 static gboolean
2122 _msg_download_in_progress (ModestMsgViewWindow *win)
2123 {
2124         gboolean result = FALSE;
2125
2126         g_return_val_if_fail (MODEST_IS_MSG_VIEW_WINDOW (win), FALSE);
2127
2128         result = modest_msg_view_window_toolbar_on_transfer_mode (win);
2129
2130         return result;
2131 }
2132
2133 static gboolean
2134 _msg_download_completed (ModestMainWindow *win)
2135 {
2136         const DimmedState *state = modest_window_get_dimming_state (MODEST_WINDOW(win));
2137         return state->any_marked_as_cached;
2138 }
2139
2140 static void 
2141 fill_list_of_caches (gpointer key, gpointer value, gpointer userdata)
2142 {
2143         GSList **send_queues = (GSList **) userdata;
2144         *send_queues = g_slist_prepend (*send_queues, value);
2145 }
2146
2147 static gboolean
2148 _selected_msg_sent_in_progress (ModestWindow *win)
2149 {
2150         const DimmedState *state = modest_window_get_dimming_state (win);
2151         return state->sent_in_progress;
2152 }
2153
2154
2155 static gboolean
2156 _sending_in_progress (ModestWindow *win)
2157 {
2158         gboolean result = FALSE;
2159         
2160         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW (win), FALSE);
2161
2162         /* Check if send operation is in progress */
2163         result = modest_main_window_send_receive_in_progress (MODEST_MAIN_WINDOW (win));
2164
2165         return result;
2166 }
2167
2168 static gboolean
2169 _invalid_folder_for_purge (ModestWindow *win, 
2170                            ModestDimmingRule *rule)
2171 {
2172         TnyMsg *msg = NULL;
2173         TnyFolder *folder = NULL;
2174         TnyAccount *account = NULL;
2175         gboolean result = FALSE;
2176
2177         if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
2178
2179                 /* Get folder and account of message */
2180                 msg = modest_msg_view_window_get_message (MODEST_MSG_VIEW_WINDOW (win));
2181                 g_return_val_if_fail(msg != NULL, TRUE);                        
2182                 folder = tny_msg_get_folder (msg);      
2183                 if (folder == NULL) {
2184                         modest_dimming_rule_set_notification (rule, _("mail_ib_unable_to_purge_attachments"));
2185                         goto frees;
2186                 }
2187                 g_object_unref (msg);
2188         } else if (MODEST_IS_MAIN_WINDOW (win)) {
2189                 GtkWidget *folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
2190                                                                               MODEST_WIDGET_TYPE_FOLDER_VIEW);
2191                 if (!folder_view)
2192                         return FALSE;
2193                 folder = TNY_FOLDER (modest_folder_view_get_selected (MODEST_FOLDER_VIEW (folder_view)));
2194                 if (folder == NULL || ! TNY_IS_FOLDER (folder))
2195                         goto frees;             
2196         } else {
2197                 g_return_val_if_reached (FALSE);
2198         }
2199         account = modest_tny_folder_get_account (folder);
2200         if (account == NULL) goto frees;                        
2201                 
2202         /* Check account */
2203         if (modest_tny_account_is_virtual_local_folders (TNY_ACCOUNT (account))) {
2204                 TnyFolderType types[2];
2205                 types[0] = TNY_FOLDER_TYPE_DRAFTS;
2206                 types[1] = TNY_FOLDER_TYPE_OUTBOX;
2207                 
2208                 if (_selected_folder_is_any_of_type (win, types, 2)) {
2209                         result = TRUE;
2210                         modest_dimming_rule_set_notification (rule, _("mail_ib_unable_to_purge_editable_msg"));
2211                 } else {
2212                         /* We're currently disabling purge in any local store */
2213                         result = TRUE;
2214                         modest_dimming_rule_set_notification (rule, _("mail_ib_unable_to_purge_attachments"));
2215                 }
2216         } else {
2217                 const gchar *proto_str = tny_account_get_proto (TNY_ACCOUNT (account));
2218                 /* If it's POP then dim */
2219                 if (modest_protocol_info_get_transport_store_protocol (proto_str) == 
2220                     MODEST_PROTOCOL_STORE_POP) {
2221                         GList *attachments = NULL;
2222                         gint n_selected = 0;
2223                         result = TRUE;
2224                         
2225                         /* TODO: This check is here to prevent a gwarning, but this looks like a logic error.
2226                          * murrayc */
2227                         if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
2228                                 attachments = modest_msg_view_window_get_attachments (MODEST_MSG_VIEW_WINDOW(win));
2229                                 n_selected = g_list_length (attachments);
2230                                 g_list_free (attachments);
2231                         }
2232                         
2233                         modest_dimming_rule_set_notification (rule, 
2234                                                               ngettext ("mail_ib_unable_to_pure_attach_pop_mail_singular",
2235                                                                         "mail_ib_unable_to_pure_attach_pop_mail_plural", 
2236                                                                         n_selected));
2237                 }
2238         }
2239         
2240 frees:
2241         if (folder != NULL)
2242                 g_object_unref (folder);
2243         if (account != NULL)
2244                 g_object_unref (account);
2245         
2246         return result;
2247 }
2248
2249 static gboolean
2250 _transfer_mode_enabled (ModestWindow *win)
2251 {
2252         gboolean result = FALSE;
2253
2254         /* Check dimming */
2255         if (MODEST_IS_MSG_VIEW_WINDOW(win)) {
2256                 result = modest_msg_view_window_transfer_mode_enabled (MODEST_MSG_VIEW_WINDOW (win));
2257         } else if (MODEST_IS_MAIN_WINDOW(win)) {
2258                 result = modest_main_window_transfer_mode_enabled (MODEST_MAIN_WINDOW (win));
2259         } else {
2260                 g_warning("_transfer_mode_enabled called with wrong window type");
2261         }
2262
2263         return result;
2264 }
2265
2266 static gboolean
2267 _selected_folder_has_subfolder_with_same_name (ModestWindow *win)
2268 {
2269         GtkWidget *folder_view = NULL;
2270         TnyFolderStore *folder = NULL;
2271         ModestEmailClipboard *clipboard = NULL;
2272         const gchar *folder_name = NULL;
2273         gboolean result = FALSE;
2274
2275         g_return_val_if_fail (MODEST_IS_MAIN_WINDOW(win), TRUE);
2276
2277         /*Get current parent folder */
2278         folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
2279                                                            MODEST_WIDGET_TYPE_FOLDER_VIEW);
2280         /* If no folder view, always dimmed */
2281         if (!folder_view) return FALSE;
2282         
2283         /* Get selected folder as parent of new folder to create */
2284         folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW(folder_view));     
2285         if (!(folder && TNY_IS_FOLDER(folder))) goto frees;
2286         
2287         /* get modest clipboard and source folder */
2288         clipboard = modest_runtime_get_email_clipboard ();
2289         folder_name = modest_email_clipboard_get_folder_name (clipboard);
2290         if (folder_name == NULL) goto frees;
2291
2292         /* Check source subfolders names */
2293         result = modest_tny_folder_has_subfolder_with_name (folder, folder_name);
2294         
2295         
2296         /* Free */
2297  frees:
2298         if (folder != NULL) 
2299                 g_object_unref (folder);
2300
2301
2302         return result;
2303 }       
2304