1 /* JavaScript for SOGoMail */
5 if (typeof textMailAccounts != 'undefined')
6 mailAccounts = textMailAccounts.evalJSON(true);
8 var currentMessages = new Array();
9 var maxCachedMessages = 20;
10 var cachedMessages = new Array();
11 var currentMailbox = null;
12 var currentMailboxType = "";
14 var usersRightsWindowHeight = 320;
15 var usersRightsWindowWidth = 400;
21 function openMessageWindow(msguid, url) {
24 wId += "SOGo_msg_" + msguid;
25 markMailReadInWindow(window, msguid);
27 var msgWin = openMailComposeWindow(url, wId);
29 msgWin.messageId = msguid;
30 msgWin.messageURL = ApplicationBaseURL + currentMailbox + "/" + msguid;
37 function onMessageDoubleClick(event) {
40 if (currentMailboxType == "draft")
45 return openMessageWindowsForSelection(action, true);
48 function toggleMailSelect(sender) {
51 row.className = sender.checked ? "tableview_selected" : "tableview";
54 function openAddressbook(sender) {
57 urlstr = ApplicationBaseURL + "/../Contacts/?popup=YES";
58 var w = window.open(urlstr, "Addressbook",
59 "width=640,height=400,resizable=1,scrollbars=1,toolbar=0,"
60 + "location=no,directories=0,status=0,menubar=0,copyhistory=0");
66 function onMenuSharing(event) {
67 var folderID = document.menuTarget.getAttribute("dataname");
68 var type = document.menuTarget.getAttribute("datatype");
69 if (type == "additional")
70 window.alert(clabels["The user rights cannot be"
71 + " edited for this object!"]);
73 var urlstr = URLForFolderID(folderID) + "/acls";
74 openAclWindow(urlstr);
78 /* mail list DOM changes */
80 function markMailInWindow(win, msguid, markread) {
83 msgDiv = win.$("div_" + msguid);
86 msgDiv.removeClassName("mailer_unreadmailsubject");
87 msgDiv.addClassName("mailer_readmailsubject");
88 msgDiv = win.$("unreaddiv_" + msguid);
91 msgDiv.setAttribute("class", "mailerUnreadIcon");
92 msgDiv.setAttribute("id", "readdiv_" + msguid);
93 msgDiv.setAttribute("src", ResourcesURL + "/icon_read.gif");
94 msgDiv.setAttribute("onclick", "mailListMarkMessage(this,"
95 + " 'markMessageUnread', " + msguid
98 var title = msgDiv.getAttribute("title-markunread");
100 msgDiv.setAttribute("title", title);
104 msgDiv.removeClassName('mailer_readmailsubject');
105 msgDiv.addClassName('mailer_unreadmailsubject');
106 msgDiv = win.$("readdiv_" + msguid);
109 msgDiv.setAttribute("class", "mailerReadIcon");
110 msgDiv.setAttribute("id", "unreaddiv_" + msguid);
111 msgDiv.setAttribute("src", ResourcesURL + "/icon_unread.gif");
112 msgDiv.setAttribute("onclick", "mailListMarkMessage(this,"
113 + " 'markMessageRead', " + msguid
116 var title = msgDiv.getAttribute("title-markread");
118 msgDiv.setAttribute("title", title);
127 function markMailReadInWindow(win, msguid) {
128 /* this is called by UIxMailView with window.opener */
129 return markMailInWindow(win, msguid, true);
132 /* mail list reply */
134 function openMessageWindowsForSelection(action, firstOnly) {
135 if (document.body.hasClassName("popup"))
136 win = openMessageWindow(window.messageId,
137 window.messageURL + "/" + action);
139 var messageList = $("messageList");
140 var rows = messageList.getSelectedRowsId();
141 if (rows.length > 0) {
143 openMessageWindow(rows[0].substr(4),
144 ApplicationBaseURL + currentMailbox
145 + "/" + rows[0].substr(4)
148 for (var i = 0; i < rows.length; i++)
149 openMessageWindow(rows[i].substr(4),
150 ApplicationBaseURL + currentMailbox
151 + "/" + rows[i].substr(4)
154 window.alert(labels["Please select a message."]);
161 function mailListMarkMessage(event) {
162 var http = createHTTPClient();
163 var url = ApplicationBaseURL + currentMailbox + "/" + msguid + "/" + action;
166 // TODO: add parameter to signal that we are only interested in OK
167 http.open("POST", url, false /* not async */);
169 if (http.status != 200) {
170 // TODO: refresh page?
171 alert("Message Mark Failed: " + http.statusText);
172 window.location.reload();
175 markMailInWindow(window, msguid, markread);
179 window.location.href = url;
183 /* maillist row highlight */
185 var oldMaillistHighlight = null; // to remember deleted/selected style
187 function ml_highlight(sender) {
188 oldMaillistHighlight = sender.className;
189 if (oldMaillistHighlight == "tableview_highlight")
190 oldMaillistHighlight = null;
191 sender.className = "tableview_highlight";
194 function ml_lowlight(sender) {
195 if (oldMaillistHighlight) {
196 sender.className = oldMaillistHighlight;
197 oldMaillistHighlight = null;
200 sender.className = "tableview";
204 /* bulk delete of messages */
206 function uixDeleteSelectedMessages(sender) {
209 var messageList = $("messageList");
210 var rowIds = messageList.getSelectedRowsId();
212 for (var i = 0; i < rowIds.length; i++) {
214 var rowId = rowIds[i].substr(4);
215 /* send AJAX request (synchronously) */
217 var messageId = currentMailbox + "/" + rowId;
218 url = ApplicationBaseURL + messageId + "/trash";
219 http = createHTTPClient();
220 http.open("POST", url, false /* not async */);
223 if (!isHttpStatus204(http.status)) { /* request failed */
228 deleteCachedMessage(messageId);
229 if (currentMessages[currentMailbox] == rowId) {
230 var div = $('messageContent');
232 currentMessages[currentMailbox] = null;
237 /* remove from page */
238 /* line-through would be nicer, but hiding is OK too */
239 var row = $(rowIds[i]);
240 row.parentNode.removeChild(row);
244 alert("Could not delete " + failCount + " messages!");
249 function moveMessages(rowIds, folder) {
252 for (var i = 0; i < rowIds.length; i++) {
255 /* send AJAX request (synchronously) */
257 var messageId = currentMailbox + "/" + rowIds[i];
258 url = (ApplicationBaseURL + messageId
259 + "/move?tofolder=" + folder);
260 http = createHTTPClient();
261 http.open("GET", url, false /* not async */);
263 if (http.status == 200) {
264 var row = $("row_" + rowIds[i]);
265 row.parentNode.removeChild(row);
266 deleteCachedMessage(messageId);
267 if (currentMessages[currentMailbox] == rowIds[i]) {
268 var div = $('messageContent');
270 currentMessages[currentMailbox] = null;
273 else /* request failed */
276 /* remove from page */
278 /* line-through would be nicer, but hiding is OK too */
282 alert("Could not move " + failCount + " messages!");
287 function onMenuDeleteMessage(event) {
288 uixDeleteSelectedMessages();
289 preventDefault(event);
292 function onPrintCurrentMessage(event) {
293 var rowIds = $("messageList").getSelectedRowsId();
294 if (rowIds.length == 0) {
295 window.alert(labels["Please select a message to print."]);
297 else if (rowIds.length > 1) {
298 window.alert(labels["Please select only one message to print."]);
303 preventDefault(event);
306 function onMailboxTreeItemClick(event) {
307 var topNode = $("mailboxTree");
308 var mailbox = this.parentNode.getAttribute("dataname");
310 if (topNode.selectedEntry)
311 topNode.selectedEntry.deselect();
313 topNode.selectedEntry = this;
317 $("searchValue").value = "";
320 currentMailboxType = this.parentNode.getAttribute("datatype");
321 if (currentMailboxType == "account" || currentMailboxType == "additional") {
322 currentMailbox = mailbox;
323 $("messageContent").update();
324 var table = $("messageList");
325 var head = table.tHead;
326 var body = table.tBodies[0];
327 for (var i = body.rows.length; i > 0; i--)
330 head.rows[1].firstChild.update();
333 openMailbox(mailbox);
338 function _onMailboxMenuAction(menuEntry, error, actionName) {
339 var targetMailbox = menuEntry.mailbox.fullName();
341 if (targetMailbox == currentMailbox)
342 window.alert(labels[error]);
345 if (document.menuTarget.tagName == "DIV")
346 message = currentMessages[currentMailbox];
348 message = document.menuTarget.getAttribute("id").substr(4);
350 var urlstr = (URLForFolderID(currentMailbox) + "/" + message
351 + "/" + actionName + "?folder=" + targetMailbox);
352 triggerAjaxRequest(urlstr, folderRefreshCallback, currentMailbox);
356 function onMailboxMenuMove(event) {
357 _onMailboxMenuAction(this,
358 "Moving a message into its own folder is impossible!",
362 function onMailboxMenuCopy(event) {
363 _onMailboxMenuAction(this,
364 "Copying a message into its own folder is impossible!",
368 function refreshMailbox() {
369 var topWindow = getTopWindow();
371 topWindow.refreshCurrentFolder();
376 function onComposeMessage() {
377 var topWindow = getTopWindow();
379 topWindow.composeNewMessage();
384 function composeNewMessage() {
385 var account = currentMailbox.split("/")[1];
386 var url = ApplicationBaseURL + "/" + account + "/compose";
387 openMailComposeWindow(url);
390 function openMailbox(mailbox, reload, idx) {
391 if (mailbox != currentMailbox || reload) {
392 currentMailbox = mailbox;
393 var url = ApplicationBaseURL + encodeURI(mailbox) + "/view?noframe=1";
394 var messageContent = $("messageContent");
395 messageContent.update();
396 lastClickedRow = null; // from generic.js
400 currentMessage = currentMessages[mailbox];
401 if (currentMessage) {
402 loadMessage(currentMessage);
403 url += '&pageforuid=' + currentMessage;
407 var searchValue = search["value"];
408 if (searchValue && searchValue.length > 0)
409 url += ("&search=" + search["criteria"]
410 + "&value=" + escape(searchValue));
411 var sortAttribute = sorting["attribute"];
412 if (sortAttribute && sortAttribute.length > 0)
413 url += ("&sort=" + sorting["attribute"]
414 + "&asc=" + sorting["ascending"]);
416 url += "&idx=" + idx;
417 if (document.messageListAjaxRequest) {
418 document.messageListAjaxRequest.aborted = true;
419 document.messageListAjaxRequest.abort();
422 var mailboxContent = $("mailboxContent");
423 if (mailboxContent.getStyle('visibility') == "hidden") {
424 mailboxContent.setStyle({ visibility: "visible" });
425 var rightDragHandle = $("rightDragHandle");
426 rightDragHandle.setStyle({ visibility: "visible" });
427 messageContent.setStyle({ top: (rightDragHandle.offsetTop
428 + rightDragHandle.offsetHeight
431 document.messageListAjaxRequest
432 = triggerAjaxRequest(url, messageListCallback,
435 var quotasUrl = ApplicationBaseURL + mailbox + "/quotas";
436 document.quotasAjaxRequest
437 = triggerAjaxRequest(quotasUrl, quotasCallback);
441 function openMailboxAtIndex(event) {
442 openMailbox(currentMailbox, true, this.getAttribute("idx"));
447 function messageListCallback(http) {
448 var div = $('mailboxContent');
449 var table = $('messageList');
451 if (http.readyState == 4
452 && http.status == 200) {
453 document.messageListAjaxRequest = null;
457 var thead = table.tHead;
458 var tbody = table.tBodies[0];
459 var tmp = document.createElement('div');
460 $(tmp).update(http.responseText);
461 thead.rows[1].parentNode.replaceChild(tmp.firstChild.tHead.rows[1], thead.rows[1]);
462 table.replaceChild(tmp.firstChild.tBodies[0], tbody);
466 div.update(http.responseText);
467 table = $('messageList');
468 configureMessageListEvents(table);
469 TableKit.Resizable.init(table, {'trueResize' : true, 'keepWidth' : true});
471 configureMessageListBodyEvents(table);
473 var selected = http.callbackData;
475 var row = $("row_" + selected);
478 div.scrollTop = row.rowIndex * row.getHeight(); // scroll to selected message
481 $("messageContent").update();
486 if (sorting["attribute"] && sorting["attribute"].length > 0) {
487 var sortHeader = $(sorting["attribute"] + "Header");
490 var sortImages = $(table.tHead).getElementsByClassName("sortImage");
491 $(sortImages).each(function(item) {
495 var sortImage = createElement("img", "messageSortImage", "sortImage");
496 sortHeader.insertBefore(sortImage, sortHeader.firstChild);
497 if (sorting["ascending"])
498 sortImage.src = ResourcesURL + "/title_sortdown_12x12.png";
500 sortImage.src = ResourcesURL + "/title_sortup_12x12.png";
505 var data = http.responseText;
506 var msg = data.replace(/^(.*\n)*.*<p>((.*\n)*.*)<\/p>(.*\n)*.*$/, "$2");
507 log("messageListCallback: problem during ajax request (readyState = " + http.readyState + ", status = " + http.status + ", response = " + msg + ")");
511 function quotasCallback(http) {
512 if (http.readyState == 4
513 && http.status == 200) {
514 var hasQuotas = false;
516 var quotas = http.responseText.evalJSON(true);
517 for (var i in quotas) {
523 var treePath = currentMailbox.split("/");
524 var mbQuotas = quotas["/" + treePath[2]];
525 var used = mbQuotas["usedSpace"];
526 var max = mbQuotas["maxQuota"];
527 var percents = (Math.round(used * 10000 / max) / 100);
528 var format = labels["quotasFormat"];
529 var text = format.formatted(used, max, percents);
530 window.status = text;
535 function onMessageContextMenu(event) {
536 var menu = $('messageListMenu');
537 Event.observe(menu, "hideMenu", onMessageContextMenuHide);
538 popupMenu(event, "messageListMenu", this);
540 var topNode = $('messageList');
541 var selectedNodes = topNode.getSelectedRows();
542 for (var i = 0; i < selectedNodes.length; i++)
543 selectedNodes[i].deselect();
544 topNode.menuSelectedRows = selectedNodes;
545 topNode.menuSelectedEntry = this;
549 function onMessageContextMenuHide(event) {
550 var topNode = $('messageList');
552 if (topNode.menuSelectedEntry) {
553 topNode.menuSelectedEntry.deselect();
554 topNode.menuSelectedEntry = null;
556 if (topNode.menuSelectedRows) {
557 var nodes = topNode.menuSelectedRows;
558 for (var i = 0; i < nodes.length; i++)
560 topNode.menuSelectedRows = null;
564 function onFolderMenuClick(event) {
565 var onhide, menuName;
567 var menutype = this.parentNode.getAttribute("datatype");
569 if (menutype == "inbox") {
570 menuName = "inboxIconMenu";
571 } else if (menutype == "account") {
572 menuName = "accountIconMenu";
573 } else if (menutype == "trash") {
574 menuName = "trashIconMenu";
576 menuName = "mailboxIconMenu";
579 menuName = "mailboxIconMenu";
582 var menu = $(menuName);
583 Event.observe(menu, "hideMenu", onFolderMenuHide);
584 popupMenu(event, menuName, this.parentNode);
586 var topNode = $("mailboxTree");
587 if (topNode.selectedEntry)
588 topNode.selectedEntry.deselect();
589 if (topNode.menuSelectedEntry)
590 topNode.menuSelectedEntry.deselect();
591 topNode.menuSelectedEntry = this;
594 preventDefault(event);
597 function onFolderMenuHide(event) {
598 var topNode = $("mailboxTree");
600 if (topNode.menuSelectedEntry) {
601 topNode.menuSelectedEntry.deselect();
602 topNode.menuSelectedEntry = null;
604 if (topNode.selectedEntry)
605 topNode.selectedEntry.select();
608 function deleteCachedMessage(messageId) {
612 while (counter < cachedMessages.length
614 if (cachedMessages[counter]
615 && cachedMessages[counter]['idx'] == messageId) {
616 cachedMessages.splice(counter, 1);
623 function getCachedMessage(idx) {
627 while (counter < cachedMessages.length
629 if (cachedMessages[counter]
630 && cachedMessages[counter]['idx'] == currentMailbox + '/' + idx)
631 message = cachedMessages[counter];
638 function storeCachedMessage(cachedMessage) {
643 if (cachedMessages.length < maxCachedMessages)
644 oldest = cachedMessages.length;
646 while (cachedMessages[counter]) {
648 || cachedMessages[counter]['time'] < timeOldest) {
650 timeOldest = cachedMessages[counter]['time'];
659 cachedMessages[oldest] = cachedMessage;
662 function onMessageSelectionChange() {
663 var rows = this.getSelectedRowsId();
665 if (rows.length == 1) {
666 var idx = rows[0].substr(4);
668 if (currentMessages[currentMailbox] != idx) {
669 currentMessages[currentMailbox] = idx;
675 function loadMessage(idx) {
676 if (document.messageAjaxRequest) {
677 document.messageAjaxRequest.aborted = true;
678 document.messageAjaxRequest.abort();
681 var cachedMessage = getCachedMessage(idx);
683 if (cachedMessage == null) {
684 var url = (ApplicationBaseURL + currentMailbox + "/"
685 + idx + "/view?noframe=1");
686 document.messageAjaxRequest
687 = triggerAjaxRequest(url, messageCallback, idx);
688 markMailInWindow(window, idx, true);
690 var div = $('messageContent');
691 div.update(cachedMessage['text']);
692 cachedMessage['time'] = (new Date()).getTime();
693 document.messageAjaxRequest = null;
694 configureLinksInMessage();
698 function configureLinksInMessage() {
699 var messageDiv = $('messageContent');
700 var mailContentDiv = document.getElementsByClassName('mailer_mailcontent',
702 Event.observe(mailContentDiv, "contextmenu",
703 onMessageContentMenu.bindAsEventListener(mailContentDiv));
704 var anchors = messageDiv.getElementsByTagName('a');
705 for (var i = 0; i < anchors.length; i++)
706 if (anchors[i].href.substring(0,7) == "mailto:") {
707 Event.observe(anchors[i], "click",
708 onEmailAddressClick.bindAsEventListener(anchors[i]));
709 Event.observe(anchors[i], "contextmenu",
710 onEmailAddressClick.bindAsEventListener(anchors[i]));
713 Event.observe(anchors[i], "click",
714 onMessageAnchorClick);
716 var editDraftButton = $("editDraftButton");
718 Event.observe(editDraftButton, "click", onMessageEditDraft);
721 function onMessageContentMenu(event) {
722 popupMenu(event, 'messageContentMenu', this);
725 function onMessageEditDraft(event) {
726 return openMessageWindowsForSelection("edit", true);
729 function onEmailAddressClick(event) {
730 popupMenu(event, 'addressMenu', this);
733 function onMessageAnchorClick (event) {
734 window.open(this.href);
735 preventDefault(event);
738 function messageCallback(http) {
739 var div = $('messageContent');
741 if (http.readyState == 4
742 && http.status == 200) {
743 document.messageAjaxRequest = null;
744 div.update(http.responseText);
745 configureLinksInMessage();
747 if (http.callbackData) {
748 var cachedMessage = new Array();
749 cachedMessage['idx'] = currentMailbox + '/' + http.callbackData;
750 cachedMessage['time'] = (new Date()).getTime();
751 cachedMessage['text'] = http.responseText;
752 if (cachedMessage['text'].length < 30000)
753 storeCachedMessage(cachedMessage);
757 log("messageCallback: problem during ajax request: " + http.status);
760 function processMailboxMenuAction(mailbox) {
761 var currentNode, upperNode;
765 mailboxName = mailbox.getAttribute('mailboxname');
766 currentNode = mailbox;
770 && !currentNode.hasAttribute('mailboxaction'))
771 currentNode = currentNode.parentNode.parentNode.parentMenuItem;
775 action = currentNode.getAttribute('mailboxaction');
776 // var rows = collectSelectedRows();
777 // var rString = rows.join(', ');
778 // alert("performing '" + action + "' on " + rString
779 // + " to " + mailboxName);
783 var rowSelectionCount = 0;
787 function showElement(e, shouldShow) {
788 e.style.display = shouldShow ? "" : "none";
791 function enableElement(e, shouldEnable) {
795 if(e.hasAttribute("disabled"))
796 e.removeAttribute("disabled");
799 e.setAttribute("disabled", "1");
803 function validateControls() {
805 this.enableElement(e, rowSelectionCount > 0);
808 function moveTo(uri) {
809 alert("MoveTo: " + uri);
812 function deleteSelectedMails() {
815 /* message menu entries */
816 function onMenuOpenMessage(event) {
817 return openMessageWindowsForSelection('popupview');
820 function onMenuReplyToSender(event) {
821 return openMessageWindowsForSelection('reply');
824 function onMenuReplyToAll(event) {
825 return openMessageWindowsForSelection('replyall');
828 function onMenuForwardMessage(event) {
829 return openMessageWindowsForSelection('forward');
832 function onMenuViewMessageSource(event) {
833 var messageList = $("messageList");
834 var rows = messageList.getSelectedRowsId();
836 if (rows.length > 0) {
837 var url = (ApplicationBaseURL + currentMailbox + "/"
838 + rows[0].substr(4) + "/viewsource");
839 openMailComposeWindow(url);
842 preventDefault(event);
846 function newContactFromEmail(event) {
847 var mailto = document.menuTarget.innerHTML;
849 var email = extractEmailAddress(mailto);
850 var c_name = extractEmailName(mailto);
851 if (email.length > 0)
853 var url = UserFolderURL + "Contacts/new?contactEmail=" + email;
855 url += "&contactFN=" + c_name;
856 openContactWindow(url);
859 return false; /* stop following the link */
862 function newEmailTo(sender) {
863 return openMailTo(document.menuTarget.innerHTML);
866 function expandUpperTree(node) {
867 var currentNode = node.parentNode;
869 while (currentNode.className != "dtree") {
870 if (currentNode.className == 'clip') {
871 var id = currentNode.getAttribute("id");
872 var number = parseInt(id.substr(2));
874 var cn = mailboxTree.aNodes[number];
875 mailboxTree.nodeStatus(1, number, cn._ls);
878 currentNode = currentNode.parentNode;
882 function onHeaderClick(event) {
883 var headerId = this.getAttribute("id");
884 var newSortAttribute;
885 if (headerId == "subjectHeader")
886 newSortAttribute = "subject";
887 else if (headerId == "fromHeader")
888 newSortAttribute = "from";
889 else if (headerId == "dateHeader")
890 newSortAttribute = "date";
892 newSortAttribute = "arrival";
894 if (sorting["attribute"] == newSortAttribute)
895 sorting["ascending"] = !sorting["ascending"];
897 sorting["attribute"] = newSortAttribute;
898 sorting["ascending"] = true;
900 refreshCurrentFolder();
905 function refreshCurrentFolder() {
906 openMailbox(currentMailbox, true);
909 function refreshFolderByType(type) {
910 if (currentMailboxType == type)
911 refreshCurrentFolder();
914 var mailboxSpanAcceptType = function(type) {
915 return (type == "mailRow");
918 var mailboxSpanEnter = function() {
919 this.addClassName("_dragOver");
922 var mailboxSpanExit = function() {
923 this.removeClassName("_dragOver");
926 var mailboxSpanDrop = function(data) {
930 var folder = this.parentNode.parentNode.getAttribute("dataname");
931 if (folder != currentMailbox)
932 success = (moveMessages(data, folder) == 0);
940 var plusSignEnter = function() {
941 var nodeNr = parseInt(this.id.substr(2));
942 if (!mailboxTree.aNodes[nodeNr]._io)
943 this.plusSignTimer = setTimeout("openPlusSign('" + nodeNr + "');", 1000);
946 var plusSignExit = function() {
947 if (this.plusSignTimer) {
948 clearTimeout(this.plusSignTimer);
949 this.plusSignTimer = null;
953 function openPlusSign(nodeNr) {
954 mailboxTree.nodeStatus(1, nodeNr, mailboxTree.aNodes[nodeNr]._ls);
955 mailboxTree.aNodes[nodeNr]._io = 1;
956 this.plusSignTimer = null;
959 var messageListGhost = function () {
960 var newDiv = document.createElement("div");
961 // newDiv.style.width = "25px;";
962 // newDiv.style.height = "25px;";
963 newDiv.style.backgroundColor = "#aae;";
964 newDiv.style.border = "2px solid #a3a;";
965 newDiv.style.padding = "5px;";
966 newDiv.ghostOffsetX = 10;
967 newDiv.ghostOffsetY = 5;
969 var newImg = document.createElement("img");
970 newImg.src = ResourcesURL + "/message-mail.png";
972 var list = $("messageList");
973 var count = list.getSelectedRows().length;
974 newDiv.appendChild(newImg);
975 newDiv.appendChild(document.createElement("br"));
976 newDiv.appendChild(document.createTextNode(count + " messages..."));
981 var messageListData = function(type) {
982 var rows = this.parentNode.parentNode.getSelectedRowsId();
983 var msgIds = new Array();
984 for (var i = 0; i < rows.length; i++)
985 msgIds.push(rows[i].substr(4));
990 /* a model for a futur refactoring of the sortable table headers mechanism */
993 function configureMessageListEvents(table) {
995 table.multiselect = true;
996 // Each body row can load a message
997 Event.observe(table, "mousedown",
998 onMessageSelectionChange.bindAsEventListener(table));
1000 configureSortableTableHeaders(table);
1004 function configureMessageListBodyEvents(table) {
1007 var cell = table.tHead.rows[1].cells[0];
1008 if ($(cell).hasClassName("tbtv_navcell")) {
1009 var anchors = $(cell).childNodesWithTag("a");
1010 for (var i = 0; i < anchors.length; i++)
1011 Event.observe(anchors[i], "click", openMailboxAtIndex.bindAsEventListener(anchors[i]));
1014 rows = table.tBodies[0].rows;
1015 for (var i = 0; i < rows.length; i++) {
1016 Event.observe(rows[i], "mousedown", onRowClick);
1017 Event.observe(rows[i], "selectstart", listRowMouseDownHandler);
1018 Event.observe(rows[i], "contextmenu", onMessageContextMenu.bindAsEventListener(rows[i]));
1020 rows[i].dndTypes = function() { return new Array("mailRow"); };
1021 rows[i].dndGhost = messageListGhost;
1022 rows[i].dndDataForType = messageListData;
1023 document.DNDManager.registerSource(rows[i]);
1025 for (var j = 0; j < rows[i].cells.length; j++) {
1026 var cell = rows[i].cells[j];
1027 Event.observe(cell, "mousedown", listRowMouseDownHandler);
1028 if (j == 2 || j == 3 || j == 5)
1029 Event.observe(cell, "dblclick", onMessageDoubleClick.bindAsEventListener(cell));
1031 var img = cell.childNodesWithTag("img")[0];
1032 Event.observe(img, "click", mailListMarkMessage);
1039 function configureDragHandles() {
1040 var handle = $("verticalDragHandle");
1042 handle.addInterface(SOGoDragHandlesInterface);
1043 handle.leftMargin = 1;
1044 handle.leftBlock=$("leftPanel");
1045 handle.rightBlock=$("rightPanel");
1048 handle = $("rightDragHandle");
1050 handle.addInterface(SOGoDragHandlesInterface);
1051 handle.upperBlock=$("mailboxContent");
1052 handle.lowerBlock=$("messageContent");
1057 function initDnd() {
1058 // log("MailerUI initDnd");
1060 var tree = $("mailboxTree");
1062 var images = tree.getElementsByTagName("img");
1063 for (var i = 0; i < images.length; i++) {
1064 if (images[i].id[0] == 'j') {
1065 images[i].dndAcceptType = mailboxSpanAcceptType;
1066 images[i].dndEnter = plusSignEnter;
1067 images[i].dndExit = plusSignExit;
1068 document.DNDManager.registerDestination(images[i]);
1071 var nodes = document.getElementsByClassName("nodeName", tree);
1072 for (var i = 0; i < nodes.length; i++) {
1073 nodes[i].dndAcceptType = mailboxSpanAcceptType;
1074 nodes[i].dndEnter = mailboxSpanEnter;
1075 nodes[i].dndExit = mailboxSpanExit;
1076 nodes[i].dndDrop = mailboxSpanDrop;
1077 document.DNDManager.registerDestination(nodes[i]);
1084 function refreshContacts() {
1087 function openInbox(node) {
1089 openMailbox(node.parentNode.getAttribute("dataname"));
1090 var tree = $("mailboxTree");
1091 tree.selectedEntry = node;
1096 function initMailer(event) {
1097 if (!document.body.hasClassName("popup")) {
1103 function initMailboxTree() {
1104 mailboxTree = new dTree("mailboxTree");
1105 mailboxTree.config.folderLinks = true;
1106 mailboxTree.config.hideRoot = true;
1108 mailboxTree.icon.root = ResourcesURL + "/tbtv_account_17x17.gif";
1109 mailboxTree.icon.folder = ResourcesURL + "/tbtv_leaf_corner_17x17.gif";
1110 mailboxTree.icon.folderOpen = ResourcesURL + "/tbtv_leaf_corner_17x17.gif";
1111 mailboxTree.icon.node = ResourcesURL + "/tbtv_leaf_corner_17x17.gif";
1112 mailboxTree.icon.line = ResourcesURL + "/tbtv_line_17x17.gif";
1113 mailboxTree.icon.join = ResourcesURL + "/tbtv_junction_17x17.gif";
1114 mailboxTree.icon.joinBottom = ResourcesURL + "/tbtv_corner_17x17.gif";
1115 mailboxTree.icon.plus = ResourcesURL + "/tbtv_plus_17x17.gif";
1116 mailboxTree.icon.plusBottom = ResourcesURL + "/tbtv_corner_plus_17x17.gif";
1117 mailboxTree.icon.minus = ResourcesURL + "/tbtv_minus_17x17.gif";
1118 mailboxTree.icon.minusBottom = ResourcesURL + "/tbtv_corner_minus_17x17.gif";
1119 mailboxTree.icon.nlPlus = ResourcesURL + "/tbtv_corner_plus_17x17.gif";
1120 mailboxTree.icon.nlMinus = ResourcesURL + "/tbtv_corner_minus_17x17.gif";
1121 mailboxTree.icon.empty = ResourcesURL + "/empty.gif";
1123 mailboxTree.add(0, -1, '');
1125 mailboxTree.pendingRequests = mailAccounts.length;
1126 activeAjaxRequests += mailAccounts.length;
1127 for (var i = 0; i < mailAccounts.length; i++) {
1128 var url = ApplicationBaseURL + "/" + mailAccounts[i] + "/mailboxes";
1129 triggerAjaxRequest(url, onLoadMailboxesCallback, mailAccounts[i]);
1133 function updateMailboxTreeInPage() {
1134 $("folderTreeContent").update(mailboxTree);
1136 var inboxFound = false;
1137 var tree = $("mailboxTree");
1138 var nodes = document.getElementsByClassName("node", tree);
1139 for (i = 0; i < nodes.length; i++) {
1140 Event.observe(nodes[i], "click",
1141 onMailboxTreeItemClick.bindAsEventListener(nodes[i]));
1142 Event.observe(nodes[i], "contextmenu",
1143 onFolderMenuClick.bindAsEventListener(nodes[i]));
1145 && nodes[i].parentNode.getAttribute("datatype") == "inbox") {
1146 openInbox(nodes[i]);
1152 function mailboxMenuNode(type, name) {
1153 var newNode = document.createElement("li");
1154 var icon = MailerUIdTreeExtension.folderIcons[type];
1156 icon = "tbtv_leaf_corner_17x17.gif";
1157 var image = document.createElement("img");
1158 image.src = ResourcesURL + "/" + icon;
1159 newNode.appendChild(image);
1160 var displayName = MailerUIdTreeExtension.folderNames[type];
1163 newNode.appendChild(document.createTextNode(" " + displayName));
1168 function generateMenuForMailbox(mailbox, prefix, callback) {
1169 var menuDIV = document.createElement("div");
1170 $(menuDIV).addClassName("menu");
1171 menuDIV.setAttribute("id", prefix + "Submenu");
1172 var menu = document.createElement("ul");
1173 menuDIV.appendChild(menu);
1174 pageContent.appendChild(menuDIV);
1176 var callbacks = new Array();
1177 if (mailbox.type != "account") {
1178 var newNode = document.createElement("li");
1179 newNode.mailbox = mailbox;
1180 newNode.appendChild(document.createTextNode(labels["This Folder"]));
1181 menu.appendChild(newNode);
1182 menu.appendChild(document.createElement("li"));
1183 callbacks.push(callback);
1184 callbacks.push("-");
1187 var submenuCount = 0;
1188 for (var i = 0; i < mailbox.children.length; i++) {
1189 var child = mailbox.children[i];
1190 var newNode = mailboxMenuNode(child.type, child.name);
1191 menu.appendChild(newNode);
1192 if (child.children.length > 0) {
1193 var newPrefix = prefix + submenuCount;
1194 var newSubmenuId = generateMenuForMailbox(child, newPrefix, callback);
1195 callbacks.push(newSubmenuId);
1199 newNode.mailbox = child;
1200 callbacks.push(callback);
1203 initMenu(menuDIV, callbacks);
1205 return menuDIV.getAttribute("id");
1208 function updateMailboxMenus() {
1209 var mailboxActions = { move: onMailboxMenuMove,
1210 copy: onMailboxMenuCopy };
1212 for (key in mailboxActions) {
1213 var menuId = key + "MailboxMenu";
1214 var menuDIV = $(menuId);
1216 menuDIV.parentNode.removeChild(menuDIV);
1218 menuDIV = document.createElement("div");
1219 pageContent = $("pageContent");
1220 pageContent.appendChild(menuDIV);
1222 var menu = document.createElement("ul");
1223 menuDIV.appendChild(menu);
1225 $(menuDIV).addClassName("menu");
1226 menuDIV.setAttribute("id", menuId);
1228 var submenuIds = new Array();
1229 for (var i = 0; i < mailAccounts.length; i++) {
1230 var menuEntry = mailboxMenuNode("account", mailAccounts[i]);
1231 menu.appendChild(menuEntry);
1232 var mailbox = accounts[mailAccounts[i]];
1233 var newSubmenuId = generateMenuForMailbox(mailbox,
1234 key, mailboxActions[key]);
1235 submenuIds.push(newSubmenuId);
1237 initMenu(menuDIV, submenuIds);
1241 function onLoadMailboxesCallback(http) {
1242 if (http.readyState == 4
1243 && http.status == 200) {
1244 checkAjaxRequestsState();
1245 var newAccount = buildMailboxes(http.callbackData,
1247 accounts[http.callbackData] = newAccount;
1248 mailboxTree.addMailAccount(newAccount);
1249 mailboxTree.pendingRequests--;
1250 activeAjaxRequests--;
1251 if (!mailboxTree.pendingRequests) {
1252 updateMailboxTreeInPage();
1253 updateMailboxMenus();
1254 checkAjaxRequestsState();
1258 // var tree = $("mailboxTree");
1259 // var treeNodes = document.getElementsByClassName("dTreeNode", tree);
1261 // while (i < treeNodes.length
1262 // && treeNodes[i].getAttribute("dataname") != currentMailbox)
1264 // if (i < treeNodes.length) {
1265 // // log("found mailbox");
1266 // var links = document.getElementsByClassName("node", treeNodes[i]);
1267 // if (tree.selectedEntry)
1268 // tree.selectedEntry.deselect();
1269 // links[0].select();
1270 // tree.selectedEntry = links[0];
1271 // expandUpperTree(links[0]);
1275 function buildMailboxes(accountName, encoded) {
1276 var account = new Mailbox("account", accountName);
1277 var data = encoded.evalJSON(true);
1278 for (var i = 0; i < data.length; i++) {
1279 var currentNode = account;
1280 var names = data[i].path.split("/");
1281 for (var j = 1; j < (names.length - 1); j++) {
1282 var node = currentNode.findMailboxByName(names[j]);
1284 node = new Mailbox("additional", names[j]);
1285 currentNode.addMailbox(node);
1289 var basename = names[names.length-1];
1290 var leaf = currentNode.findMailboxByName(basename);
1292 leaf.type = data[i].type;
1294 leaf = new Mailbox(data[i].type, basename);
1295 currentNode.addMailbox(leaf);
1302 function onMenuCreateFolder(event) {
1303 var name = window.prompt(labels["Name :"], "");
1304 if (name && name.length > 0) {
1305 var folderID = document.menuTarget.getAttribute("dataname");
1306 var urlstr = URLForFolderID(folderID) + "/createFolder?name=" + name;
1307 triggerAjaxRequest(urlstr, folderOperationCallback);
1311 function onMenuRenameFolder(event) {
1312 var name = window.prompt(labels["Enter the new name of your folder :"]
1315 if (name && name.length > 0) {
1316 var folderID = document.menuTarget.getAttribute("dataname");
1317 var urlstr = URLForFolderID(folderID) + "/renameFolder?name=" + name;
1318 triggerAjaxRequest(urlstr, folderOperationCallback);
1322 function onMenuDeleteFolder(event) {
1323 var answer = window.confirm(labels["Do you really want to move this folder into the trash ?"]);
1325 var folderID = document.menuTarget.getAttribute("dataname");
1326 var urlstr = URLForFolderID(folderID) + "/deleteFolder";
1327 triggerAjaxRequest(urlstr, folderOperationCallback);
1331 function onMenuExpungeFolder(event) {
1332 var folderID = document.menuTarget.getAttribute("dataname");
1333 var urlstr = URLForFolderID(folderID) + "/expunge";
1335 triggerAjaxRequest(urlstr, folderRefreshCallback, folderID);
1338 function onMenuEmptyTrash(event) {
1339 var folderID = document.menuTarget.getAttribute("dataname");
1340 var urlstr = URLForFolderID(folderID) + "/emptyTrash";
1341 triggerAjaxRequest(urlstr, folderOperationCallback, folderID);
1343 if (folderID == currentMailbox) {
1344 var div = $('messageContent');
1345 for (var i = div.childNodes.length - 1; i > -1; i--)
1346 div.removeChild(div.childNodes[i]);
1347 refreshCurrentFolder();
1349 var msgID = currentMessages[folderID];
1351 deleteCachedMessage(folderID + "/" + msgID);
1354 function _onMenuChangeToXXXFolder(event, folder) {
1355 var type = document.menuTarget.getAttribute("datatype");
1356 if (type == "additional")
1357 window.alert(labels["You need to choose a non-virtual folder!"]);
1359 var folderID = document.menuTarget.getAttribute("dataname");
1360 var number = folderID.split("/").length;
1362 window.alert(labels["You need to choose a root subfolder!"]);
1364 var urlstr = URLForFolderID(folderID) + "/setAs" + folder + "Folder";
1365 triggerAjaxRequest(urlstr, folderOperationCallback);
1370 function onMenuChangeToDraftsFolder(event) {
1371 return _onMenuChangeToXXXFolder(event, "Drafts");
1374 function onMenuChangeToSentFolder(event) {
1375 return _onMenuChangeToXXXFolder(event, "Sent");
1378 function onMenuChangeToTrashFolder(event) {
1379 return _onMenuChangeToXXXFolder(event, "Trash");
1382 function folderOperationCallback(http) {
1383 if (http.readyState == 4
1384 && isHttpStatus204(http.status))
1387 window.alert(labels["Operation failed"]);
1390 function folderRefreshCallback(http) {
1391 if (http.readyState == 4
1392 && isHttpStatus204(http.status)) {
1393 var oldMailbox = http.callbackData;
1394 if (oldMailbox == currentMailbox)
1395 refreshCurrentFolder();
1398 window.alert(labels["Operation failed"]);
1401 function getMenus() {
1403 menus["accountIconMenu"] = new Array(null, null, onMenuCreateFolder, null,
1405 menus["inboxIconMenu"] = new Array(null, null, null, "-", null,
1406 onMenuCreateFolder, onMenuExpungeFolder,
1409 menus["trashIconMenu"] = new Array(null, null, null, "-", null,
1410 onMenuCreateFolder, onMenuExpungeFolder,
1411 onMenuEmptyTrash, "-", null,
1413 menus["mailboxIconMenu"] = new Array(null, null, null, "-", null,
1416 onMenuExpungeFolder,
1421 menus["addressMenu"] = new Array(newContactFromEmail, newEmailTo, null);
1422 menus["messageListMenu"] = new Array(onMenuOpenMessage, "-",
1423 onMenuReplyToSender,
1425 onMenuForwardMessage, null,
1426 "-", "moveMailboxMenu",
1427 "copyMailboxMenu", "label-menu",
1428 "mark-menu", "-", null,
1429 onMenuViewMessageSource, null,
1430 null, onMenuDeleteMessage);
1431 menus["messageContentMenu"] = new Array(onMenuReplyToSender,
1433 onMenuForwardMessage,
1434 null, "moveMailboxMenu",
1436 "-", "label-menu", "mark-menu",
1438 null, onMenuViewMessageSource,
1439 null, onPrintCurrentMessage,
1440 onMenuDeleteMessage);
1441 menus["folderTypeMenu"] = new Array(onMenuChangeToSentFolder,
1442 onMenuChangeToDraftsFolder,
1443 onMenuChangeToTrashFolder);
1445 menus["label-menu"] = new Array(null, "-", null , null, null, null , null,
1447 menus["mark-menu"] = new Array(null, null, null, null, "-", null, "-",
1449 menus["searchMenu"] = new Array(setSearchCriteria, setSearchCriteria,
1450 setSearchCriteria, setSearchCriteria,
1456 addEvent(window, 'load', initMailer);
1458 function Mailbox(type, name) {
1461 this.parentFolder = null;
1462 this.children = new Array();
1466 Mailbox.prototype.dump = function(indent) {
1469 log(" ".repeat(indent) + this.name);
1470 for (var i = 0; i < this.children.length; i++) {
1471 this.children[i].dump(indent + 2);
1475 Mailbox.prototype.fullName = function() {
1478 var currentFolder = this;
1479 while (currentFolder.parentFolder) {
1480 fullName = "/folder" + currentFolder.name + fullName;
1481 currentFolder = currentFolder.parentFolder;
1484 return "/" + currentFolder.name + fullName;
1487 Mailbox.prototype.findMailboxByName = function(name) {
1491 while (!mailbox && i < this.children.length)
1492 if (this.children[i].name == name)
1493 mailbox = this.children[i];
1500 Mailbox.prototype.addMailbox = function(mailbox) {
1501 mailbox.parentFolder = this;
1502 this.children.push(mailbox);