snappymail/dev/ViewModels/MailBoxMessageListViewModel.js

937 lines
25 KiB
JavaScript
Raw Normal View History

/* RainLoop Webmail (c) RainLoop Team | Licensed under CC BY-NC-SA 3.0 */
2014-08-21 23:08:34 +08:00
(function (module) {
2014-08-21 23:08:34 +08:00
'use strict';
2014-08-21 23:08:34 +08:00
var
$ = require('../External/jquery.js'),
_ = require('../External/underscore.js'),
ko = require('../External/ko.js'),
key = require('../External/key.js'),
ifvisible = require('../External/ifvisible.js'),
Jua = require('../External/Jua.js'),
Utils = require('../Common/Utils.js'),
Enums = require('../Common/Enums.js'),
Consts = require('../Common/Consts.js'),
Globals = require('../Common/Globals.js'),
LinkBuilder = require('../Common/LinkBuilder.js'),
2014-08-22 23:08:56 +08:00
Events = require('../Common/Events.js'),
Selector = require('../Common/Selector.js'),
2014-08-21 23:08:34 +08:00
2014-08-22 23:08:56 +08:00
AppSettings = require('../Storages/AppSettings.js'),
2014-08-21 23:08:34 +08:00
Cache = require('../Storages/WebMailCacheStorage.js'),
2014-08-22 23:08:56 +08:00
Data = require('../Storages/WebMailDataStorage.js'),
2014-08-21 23:08:34 +08:00
Remote = require('../Storages/WebMailAjaxRemoteStorage.js'),
2014-08-22 23:08:56 +08:00
RL = require('../Boots/RainLoopApp.js'),
2014-08-21 23:08:34 +08:00
kn = require('../Knoin/Knoin.js'),
KnoinAbstractViewModel = require('../Knoin/KnoinAbstractViewModel.js'),
PopupsComposeViewModel = require('./Popups/PopupsComposeViewModel.js')
;
2014-08-21 23:08:34 +08:00
/**
* @constructor
* @extends KnoinAbstractViewModel
*/
function MailBoxMessageListViewModel()
{
KnoinAbstractViewModel.call(this, 'Right', 'MailMessageList');
2014-08-21 23:08:34 +08:00
this.sLastUid = null;
this.bPrefetch = false;
this.emptySubjectValue = '';
2014-08-22 23:08:56 +08:00
this.hideDangerousActions = !!AppSettings.settingsGet('HideDangerousActions');
2014-08-22 23:08:56 +08:00
this.popupVisibility = Globals.popupVisibility;
2014-08-22 23:08:56 +08:00
this.message = Data.message;
this.messageList = Data.messageList;
this.folderList = Data.folderList;
this.currentMessage = Data.currentMessage;
this.isMessageSelected = Data.isMessageSelected;
this.messageListSearch = Data.messageListSearch;
this.messageListError = Data.messageListError;
this.folderMenuForMove = Data.folderMenuForMove;
2014-08-22 23:08:56 +08:00
this.useCheckboxesInList = Data.useCheckboxesInList;
2014-08-22 23:08:56 +08:00
this.mainMessageListSearch = Data.mainMessageListSearch;
this.messageListEndFolder = Data.messageListEndFolder;
2014-08-22 23:08:56 +08:00
this.messageListChecked = Data.messageListChecked;
this.messageListCheckedOrSelected = Data.messageListCheckedOrSelected;
this.messageListCheckedOrSelectedUidsWithSubMails = Data.messageListCheckedOrSelectedUidsWithSubMails;
this.messageListCompleteLoadingThrottle = Data.messageListCompleteLoadingThrottle;
2014-08-21 23:08:34 +08:00
Utils.initOnStartOrLangChange(function () {
this.emptySubjectValue = Utils.i18n('MESSAGE_LIST/EMPTY_SUBJECT_TEXT');
}, this);
2013-12-13 07:23:47 +08:00
2014-08-22 23:08:56 +08:00
this.userQuota = Data.userQuota;
this.userUsageSize = Data.userUsageSize;
this.userUsageProc = Data.userUsageProc;
2014-08-21 23:08:34 +08:00
this.moveDropdownTrigger = ko.observable(false);
this.moreDropdownTrigger = ko.observable(false);
2014-08-21 23:08:34 +08:00
// append drag and drop
this.dragOver = ko.observable(false).extend({'throttle': 1});
this.dragOverEnter = ko.observable(false).extend({'throttle': 1});
this.dragOverArea = ko.observable(null);
this.dragOverBodyArea = ko.observable(null);
2014-08-21 23:08:34 +08:00
this.messageListItemTemplate = ko.computed(function () {
2014-08-22 23:08:56 +08:00
return Enums.Layout.NoPreview !== Data.layout() ?
2014-08-21 23:08:34 +08:00
'MailMessageListItem' : 'MailMessageListItemNoPreviewPane';
});
2014-08-21 23:08:34 +08:00
this.messageListSearchDesc = ko.computed(function () {
2014-08-22 23:08:56 +08:00
var sValue = Data.messageListEndSearch();
2014-08-21 23:08:34 +08:00
return '' === sValue ? '' : Utils.i18n('MESSAGE_LIST/SEARCH_RESULT_FOR', {'SEARCH': sValue});
});
2014-08-22 23:08:56 +08:00
this.messageListPagenator = ko.computed(Utils.computedPagenatorHelper(Data.messageListPage, Data.messageListPageCount));
2014-08-21 23:08:34 +08:00
this.checkAll = ko.computed({
'read': function () {
2014-08-22 23:08:56 +08:00
return 0 < Data.messageListChecked().length;
2014-08-21 23:08:34 +08:00
},
2014-08-21 23:08:34 +08:00
'write': function (bValue) {
bValue = !!bValue;
2014-08-22 23:08:56 +08:00
_.each(Data.messageList(), function (oMessage) {
2014-08-21 23:08:34 +08:00
oMessage.checked(bValue);
});
}
});
2014-08-21 23:08:34 +08:00
this.inputMessageListSearchFocus = ko.observable(false);
2013-12-16 06:02:03 +08:00
2014-08-21 23:08:34 +08:00
this.sLastSearchValue = '';
this.inputProxyMessageListSearch = ko.computed({
'read': this.mainMessageListSearch,
'write': function (sValue) {
this.sLastSearchValue = sValue;
},
'owner': this
});
2014-08-21 23:08:34 +08:00
this.isIncompleteChecked = ko.computed(function () {
var
2014-08-22 23:08:56 +08:00
iM = Data.messageList().length,
iC = Data.messageListChecked().length
2014-08-21 23:08:34 +08:00
;
return 0 < iM && 0 < iC && iM > iC;
}, this);
this.hasMessages = ko.computed(function () {
return 0 < this.messageList().length;
}, this);
this.hasCheckedOrSelectedLines = ko.computed(function () {
return 0 < this.messageListCheckedOrSelected().length;
}, this);
this.isSpamFolder = ko.computed(function () {
2014-08-22 23:08:56 +08:00
return Data.spamFolder() === this.messageListEndFolder() &&
'' !== Data.spamFolder();
2014-08-21 23:08:34 +08:00
}, this);
this.isSpamDisabled = ko.computed(function () {
2014-08-22 23:08:56 +08:00
return Consts.Values.UnuseOptionValue === Data.spamFolder();
2014-08-21 23:08:34 +08:00
}, this);
this.isTrashFolder = ko.computed(function () {
2014-08-22 23:08:56 +08:00
return Data.trashFolder() === this.messageListEndFolder() &&
'' !== Data.trashFolder();
2014-08-21 23:08:34 +08:00
}, this);
this.isDraftFolder = ko.computed(function () {
2014-08-22 23:08:56 +08:00
return Data.draftFolder() === this.messageListEndFolder() &&
'' !== Data.draftFolder();
2014-08-21 23:08:34 +08:00
}, this);
this.isSentFolder = ko.computed(function () {
2014-08-22 23:08:56 +08:00
return Data.sentFolder() === this.messageListEndFolder() &&
'' !== Data.sentFolder();
2014-08-21 23:08:34 +08:00
}, this);
this.isArchiveFolder = ko.computed(function () {
2014-08-22 23:08:56 +08:00
return Data.archiveFolder() === this.messageListEndFolder() &&
'' !== Data.archiveFolder();
2014-08-21 23:08:34 +08:00
}, this);
this.isArchiveDisabled = ko.computed(function () {
2014-08-22 23:08:56 +08:00
return Consts.Values.UnuseOptionValue === Data.archiveFolder();
2014-08-21 23:08:34 +08:00
}, this);
this.canBeMoved = this.hasCheckedOrSelectedLines;
this.clearCommand = Utils.createCommand(this, function () {
2014-08-22 23:08:56 +08:00
kn.showScreenPopup(PopupsFolderClearViewModel, [Data.currentFolder()]);
2014-08-21 23:08:34 +08:00
});
this.multyForwardCommand = Utils.createCommand(this, function () {
2014-08-22 23:08:56 +08:00
kn.showScreenPopup(PopupsComposeViewModel, [Enums.ComposeType.ForwardAsAttachment, Data.messageListCheckedOrSelected()]);
2014-08-21 23:08:34 +08:00
}, this.canBeMoved);
this.deleteWithoutMoveCommand = Utils.createCommand(this, function () {
RL.deleteMessagesFromFolder(Enums.FolderType.Trash,
2014-08-22 23:08:56 +08:00
Data.currentFolderFullNameRaw(),
Data.messageListCheckedOrSelectedUidsWithSubMails(), false);
2014-08-21 23:08:34 +08:00
}, this.canBeMoved);
this.deleteCommand = Utils.createCommand(this, function () {
RL.deleteMessagesFromFolder(Enums.FolderType.Trash,
2014-08-22 23:08:56 +08:00
Data.currentFolderFullNameRaw(),
Data.messageListCheckedOrSelectedUidsWithSubMails(), true);
2014-08-21 23:08:34 +08:00
}, this.canBeMoved);
this.archiveCommand = Utils.createCommand(this, function () {
RL.deleteMessagesFromFolder(Enums.FolderType.Archive,
2014-08-22 23:08:56 +08:00
Data.currentFolderFullNameRaw(),
Data.messageListCheckedOrSelectedUidsWithSubMails(), true);
2014-08-21 23:08:34 +08:00
}, this.canBeMoved);
this.spamCommand = Utils.createCommand(this, function () {
RL.deleteMessagesFromFolder(Enums.FolderType.Spam,
2014-08-22 23:08:56 +08:00
Data.currentFolderFullNameRaw(),
Data.messageListCheckedOrSelectedUidsWithSubMails(), true);
2014-08-21 23:08:34 +08:00
}, this.canBeMoved);
this.notSpamCommand = Utils.createCommand(this, function () {
RL.deleteMessagesFromFolder(Enums.FolderType.NotSpam,
2014-08-22 23:08:56 +08:00
Data.currentFolderFullNameRaw(),
Data.messageListCheckedOrSelectedUidsWithSubMails(), true);
2014-08-21 23:08:34 +08:00
}, this.canBeMoved);
this.moveCommand = Utils.createCommand(this, Utils.emptyFunction, this.canBeMoved);
this.reloadCommand = Utils.createCommand(this, function () {
2014-08-22 23:08:56 +08:00
if (!Data.messageListCompleteLoadingThrottle())
2014-08-21 23:08:34 +08:00
{
RL.reloadMessageList(false, true);
}
});
this.quotaTooltip = _.bind(this.quotaTooltip, this);
this.selector = new Selector(this.messageList, this.currentMessage,
'.messageListItem .actionHandle', '.messageListItem.selected', '.messageListItem .checkboxMessage',
'.messageListItem.focused');
this.selector.on('onItemSelect', _.bind(function (oMessage) {
if (oMessage)
{
2014-08-22 23:08:56 +08:00
Data.message(Data.staticMessageList.populateByMessageListItem(oMessage));
this.populateMessageBody(Data.message());
2014-08-21 23:08:34 +08:00
2014-08-22 23:08:56 +08:00
if (Enums.Layout.NoPreview === Data.layout())
2014-08-21 23:08:34 +08:00
{
kn.setHash(LinkBuilder.messagePreview(), true);
2014-08-22 23:08:56 +08:00
Data.message.focused(true);
2014-08-21 23:08:34 +08:00
}
}
else
{
2014-08-22 23:08:56 +08:00
Data.message(null);
2014-08-21 23:08:34 +08:00
}
}, this));
this.selector.on('onItemGetUid', function (oMessage) {
return oMessage ? oMessage.generateUid() : '';
});
2014-08-22 23:08:56 +08:00
Data.messageListEndHash.subscribe(function () {
2014-08-21 23:08:34 +08:00
this.selector.scrollToTop();
}, this);
2014-08-22 23:08:56 +08:00
Data.layout.subscribe(function (mValue) {
2014-08-21 23:08:34 +08:00
this.selector.autoSelect(Enums.Layout.NoPreview !== mValue);
}, this);
2014-08-22 23:08:56 +08:00
Data.layout.valueHasMutated();
2014-08-21 23:08:34 +08:00
2014-08-22 23:08:56 +08:00
Events
2014-08-21 23:08:34 +08:00
.sub('mailbox.message-list.selector.go-down', function () {
this.selector.goDown(true);
}, this)
.sub('mailbox.message-list.selector.go-up', function () {
this.selector.goUp(true);
}, this)
;
kn.constructorEnd(this);
}
2014-08-21 23:08:34 +08:00
kn.extendAsViewModel('MailBoxMessageListViewModel', MailBoxMessageListViewModel);
/**
* @type {string}
*/
MailBoxMessageListViewModel.prototype.emptySubjectValue = '';
MailBoxMessageListViewModel.prototype.searchEnterAction = function ()
{
2014-08-21 23:08:34 +08:00
this.mainMessageListSearch(this.sLastSearchValue);
this.inputMessageListSearchFocus(false);
};
/**
* @returns {string}
*/
MailBoxMessageListViewModel.prototype.printableMessageCountForDeletion = function ()
{
2014-08-21 23:08:34 +08:00
var iCnt = this.messageListCheckedOrSelectedUidsWithSubMails().length;
return 1 < iCnt ? ' (' + (100 > iCnt ? iCnt : '99+') + ')' : '';
};
2014-08-21 23:08:34 +08:00
MailBoxMessageListViewModel.prototype.cancelSearch = function ()
{
this.mainMessageListSearch('');
this.inputMessageListSearchFocus(false);
};
/**
* @param {string} sToFolderFullNameRaw
* @return {boolean}
*/
MailBoxMessageListViewModel.prototype.moveSelectedMessagesToFolder = function (sToFolderFullNameRaw, bCopy)
{
2014-08-21 23:08:34 +08:00
if (this.canBeMoved())
{
2014-08-21 23:08:34 +08:00
RL.moveMessagesToFolder(
2014-08-22 23:08:56 +08:00
Data.currentFolderFullNameRaw(),
Data.messageListCheckedOrSelectedUidsWithSubMails(), sToFolderFullNameRaw, bCopy);
}
2014-08-21 23:08:34 +08:00
return false;
};
MailBoxMessageListViewModel.prototype.dragAndDronHelper = function (oMessageListItem)
{
if (oMessageListItem)
{
2014-08-21 23:08:34 +08:00
oMessageListItem.checked(true);
}
2014-08-21 23:08:34 +08:00
var
oEl = Utils.draggeblePlace(),
2014-08-22 23:08:56 +08:00
aUids = Data.messageListCheckedOrSelectedUidsWithSubMails()
2014-08-21 23:08:34 +08:00
;
2014-08-22 23:08:56 +08:00
oEl.data('rl-folder', Data.currentFolderFullNameRaw());
2014-08-21 23:08:34 +08:00
oEl.data('rl-uids', aUids);
oEl.find('.text').text('' + aUids.length);
2014-08-21 23:08:34 +08:00
_.defer(function () {
2014-08-22 23:08:56 +08:00
var aUids = Data.messageListCheckedOrSelectedUidsWithSubMails();
2014-08-21 23:08:34 +08:00
oEl.data('rl-uids', aUids);
oEl.find('.text').text('' + aUids.length);
});
2014-08-21 23:08:34 +08:00
return oEl;
};
2014-08-21 23:08:34 +08:00
/**
* @param {string} sResult
* @param {AjaxJsonDefaultResponse} oData
* @param {boolean} bCached
*/
MailBoxMessageListViewModel.prototype.onMessageResponse = function (sResult, oData, bCached)
{
2014-08-22 23:08:56 +08:00
Data.hideMessageBodies();
Data.messageLoading(false);
2014-08-21 23:08:34 +08:00
if (Enums.StorageResultType.Success === sResult && oData && oData.Result)
{
2014-08-22 23:08:56 +08:00
Data.setMessage(oData, bCached);
2014-08-21 23:08:34 +08:00
}
else if (Enums.StorageResultType.Unload === sResult)
{
2014-08-22 23:08:56 +08:00
Data.message(null);
Data.messageError('');
2014-08-21 23:08:34 +08:00
}
else if (Enums.StorageResultType.Abort !== sResult)
{
2014-08-22 23:08:56 +08:00
Data.message(null);
Data.messageError((oData && oData.ErrorCode ?
2014-08-21 23:08:34 +08:00
Utils.getNotification(oData.ErrorCode) :
Utils.getNotification(Enums.Notification.UnknownError)));
}
};
MailBoxMessageListViewModel.prototype.populateMessageBody = function (oMessage)
{
if (oMessage)
{
if (Remote.message(this.onMessageResponse, oMessage.folderFullNameRaw, oMessage.uid))
{
2014-08-22 23:08:56 +08:00
Data.messageLoading(true);
2014-08-21 23:08:34 +08:00
}
else
{
Utils.log('Error: Unknown message request: ' + oMessage.folderFullNameRaw + ' ~ ' + oMessage.uid + ' [e-101]');
}
}
2014-08-21 23:08:34 +08:00
};
/**
* @param {string} sFolderFullNameRaw
* @param {number} iSetAction
* @param {Array=} aMessages = null
*/
MailBoxMessageListViewModel.prototype.setAction = function (sFolderFullNameRaw, iSetAction, aMessages)
{
var
aUids = [],
oFolder = null,
iAlreadyUnread = 0
;
2014-08-21 23:08:34 +08:00
if (Utils.isUnd(aMessages))
{
2014-08-22 23:08:56 +08:00
aMessages = Data.messageListChecked();
2014-08-21 23:08:34 +08:00
}
2014-08-21 23:08:34 +08:00
aUids = _.map(aMessages, function (oMessage) {
return oMessage.uid;
});
2014-08-21 23:08:34 +08:00
if ('' !== sFolderFullNameRaw && 0 < aUids.length)
{
switch (iSetAction) {
case Enums.MessageSetAction.SetSeen:
2014-08-21 23:08:34 +08:00
_.each(aMessages, function (oMessage) {
if (oMessage.unseen())
{
iAlreadyUnread++;
}
oMessage.unseen(false);
Cache.storeMessageFlagsToCache(oMessage);
});
oFolder = Cache.getFolderFromCacheList(sFolderFullNameRaw);
if (oFolder)
{
2014-08-21 23:08:34 +08:00
oFolder.messageCountUnread(oFolder.messageCountUnread() - iAlreadyUnread);
}
2014-08-21 23:08:34 +08:00
Remote.messageSetSeen(Utils.emptyFunction, sFolderFullNameRaw, aUids, true);
break;
case Enums.MessageSetAction.UnsetSeen:
2014-08-21 23:08:34 +08:00
_.each(aMessages, function (oMessage) {
if (oMessage.unseen())
{
iAlreadyUnread++;
}
oMessage.unseen(true);
Cache.storeMessageFlagsToCache(oMessage);
});
oFolder = Cache.getFolderFromCacheList(sFolderFullNameRaw);
if (oFolder)
{
2014-08-21 23:08:34 +08:00
oFolder.messageCountUnread(oFolder.messageCountUnread() - iAlreadyUnread + aUids.length);
}
2014-08-21 23:08:34 +08:00
Remote.messageSetSeen(Utils.emptyFunction, sFolderFullNameRaw, aUids, false);
break;
case Enums.MessageSetAction.SetFlag:
_.each(aMessages, function (oMessage) {
oMessage.flagged(true);
Cache.storeMessageFlagsToCache(oMessage);
});
Remote.messageSetFlagged(Utils.emptyFunction, sFolderFullNameRaw, aUids, true);
break;
case Enums.MessageSetAction.UnsetFlag:
_.each(aMessages, function (oMessage) {
oMessage.flagged(false);
Cache.storeMessageFlagsToCache(oMessage);
});
Remote.messageSetFlagged(Utils.emptyFunction, sFolderFullNameRaw, aUids, false);
break;
}
RL.reloadFlagsCurrentMessageListAndMessageFromCache();
}
2014-08-21 23:08:34 +08:00
};
2014-04-09 04:59:22 +08:00
2014-08-21 23:08:34 +08:00
/**
* @param {string} sFolderFullNameRaw
* @param {number} iSetAction
*/
MailBoxMessageListViewModel.prototype.setActionForAll = function (sFolderFullNameRaw, iSetAction)
2014-04-09 04:59:22 +08:00
{
2014-08-21 23:08:34 +08:00
var
oFolder = null,
2014-08-22 23:08:56 +08:00
aMessages = Data.messageList()
2014-08-21 23:08:34 +08:00
;
2014-04-09 04:59:22 +08:00
2014-08-21 23:08:34 +08:00
if ('' !== sFolderFullNameRaw)
2014-04-09 04:59:22 +08:00
{
2014-08-21 23:08:34 +08:00
oFolder = Cache.getFolderFromCacheList(sFolderFullNameRaw);
2014-04-09 04:59:22 +08:00
2014-08-21 23:08:34 +08:00
if (oFolder)
{
switch (iSetAction) {
case Enums.MessageSetAction.SetSeen:
oFolder = Cache.getFolderFromCacheList(sFolderFullNameRaw);
if (oFolder)
{
_.each(aMessages, function (oMessage) {
oMessage.unseen(false);
});
2014-04-09 04:59:22 +08:00
2014-08-21 23:08:34 +08:00
oFolder.messageCountUnread(0);
Cache.clearMessageFlagsFromCacheByFolder(sFolderFullNameRaw);
}
2014-04-09 04:59:22 +08:00
2014-08-21 23:08:34 +08:00
Remote.messageSetSeenToAll(Utils.emptyFunction, sFolderFullNameRaw, true);
break;
case Enums.MessageSetAction.UnsetSeen:
oFolder = Cache.getFolderFromCacheList(sFolderFullNameRaw);
if (oFolder)
{
_.each(aMessages, function (oMessage) {
oMessage.unseen(true);
});
oFolder.messageCountUnread(oFolder.messageCountAll());
Cache.clearMessageFlagsFromCacheByFolder(sFolderFullNameRaw);
}
Remote.messageSetSeenToAll(Utils.emptyFunction, sFolderFullNameRaw, false);
break;
}
RL.reloadFlagsCurrentMessageListAndMessageFromCache();
}
}
2014-08-21 23:08:34 +08:00
};
2014-04-09 04:59:22 +08:00
2014-08-21 23:08:34 +08:00
MailBoxMessageListViewModel.prototype.listSetSeen = function ()
{
2014-08-22 23:08:56 +08:00
this.setAction(Data.currentFolderFullNameRaw(), Enums.MessageSetAction.SetSeen, Data.messageListCheckedOrSelected());
2014-08-21 23:08:34 +08:00
};
2014-04-09 04:59:22 +08:00
2014-08-21 23:08:34 +08:00
MailBoxMessageListViewModel.prototype.listSetAllSeen = function ()
{
2014-08-22 23:08:56 +08:00
this.setActionForAll(Data.currentFolderFullNameRaw(), Enums.MessageSetAction.SetSeen);
2014-08-21 23:08:34 +08:00
};
2014-04-09 04:59:22 +08:00
2014-08-21 23:08:34 +08:00
MailBoxMessageListViewModel.prototype.listUnsetSeen = function ()
{
2014-08-22 23:08:56 +08:00
this.setAction(Data.currentFolderFullNameRaw(), Enums.MessageSetAction.UnsetSeen, Data.messageListCheckedOrSelected());
2014-08-21 23:08:34 +08:00
};
2014-04-09 04:59:22 +08:00
2014-08-21 23:08:34 +08:00
MailBoxMessageListViewModel.prototype.listSetFlags = function ()
{
2014-08-22 23:08:56 +08:00
this.setAction(Data.currentFolderFullNameRaw(), Enums.MessageSetAction.SetFlag, Data.messageListCheckedOrSelected());
2014-08-21 23:08:34 +08:00
};
2014-08-21 23:08:34 +08:00
MailBoxMessageListViewModel.prototype.listUnsetFlags = function ()
{
2014-08-22 23:08:56 +08:00
this.setAction(Data.currentFolderFullNameRaw(), Enums.MessageSetAction.UnsetFlag, Data.messageListCheckedOrSelected());
2014-08-21 23:08:34 +08:00
};
2014-08-21 23:08:34 +08:00
MailBoxMessageListViewModel.prototype.flagMessages = function (oCurrentMessage)
{
var
2014-08-21 23:08:34 +08:00
aChecked = this.messageListCheckedOrSelected(),
aCheckedUids = []
;
2014-08-21 23:08:34 +08:00
if (oCurrentMessage)
{
2014-08-21 23:08:34 +08:00
if (0 < aChecked.length)
{
aCheckedUids = _.map(aChecked, function (oMessage) {
return oMessage.uid;
});
}
2014-08-21 23:08:34 +08:00
if (0 < aCheckedUids.length && -1 < Utils.inArray(oCurrentMessage.uid, aCheckedUids))
{
2014-08-21 23:08:34 +08:00
this.setAction(oCurrentMessage.folderFullNameRaw, oCurrentMessage.flagged() ?
Enums.MessageSetAction.UnsetFlag : Enums.MessageSetAction.SetFlag, aChecked);
}
else
{
2014-08-21 23:08:34 +08:00
this.setAction(oCurrentMessage.folderFullNameRaw, oCurrentMessage.flagged() ?
Enums.MessageSetAction.UnsetFlag : Enums.MessageSetAction.SetFlag, [oCurrentMessage]);
}
2014-08-21 23:08:34 +08:00
}
};
2014-08-21 23:08:34 +08:00
MailBoxMessageListViewModel.prototype.flagMessagesFast = function (bFlag)
{
var
aChecked = this.messageListCheckedOrSelected(),
aFlagged = []
;
if (0 < aChecked.length)
{
aFlagged = _.filter(aChecked, function (oMessage) {
return oMessage.flagged();
});
2014-08-21 23:08:34 +08:00
if (Utils.isUnd(bFlag))
{
this.setAction(aChecked[0].folderFullNameRaw,
aChecked.length === aFlagged.length ? Enums.MessageSetAction.UnsetFlag : Enums.MessageSetAction.SetFlag, aChecked);
}
else
{
this.setAction(aChecked[0].folderFullNameRaw,
!bFlag ? Enums.MessageSetAction.UnsetFlag : Enums.MessageSetAction.SetFlag, aChecked);
}
}
2014-08-21 23:08:34 +08:00
};
2014-08-21 23:08:34 +08:00
MailBoxMessageListViewModel.prototype.seenMessagesFast = function (bSeen)
{
var
aChecked = this.messageListCheckedOrSelected(),
aUnseen = []
;
2014-08-21 23:08:34 +08:00
if (0 < aChecked.length)
{
aUnseen = _.filter(aChecked, function (oMessage) {
return oMessage.unseen();
});
2014-08-21 23:08:34 +08:00
if (Utils.isUnd(bSeen))
{
2014-08-21 23:08:34 +08:00
this.setAction(aChecked[0].folderFullNameRaw,
0 < aUnseen.length ? Enums.MessageSetAction.SetSeen : Enums.MessageSetAction.UnsetSeen, aChecked);
}
2014-08-21 23:08:34 +08:00
else
{
2014-08-21 23:08:34 +08:00
this.setAction(aChecked[0].folderFullNameRaw,
bSeen ? Enums.MessageSetAction.SetSeen : Enums.MessageSetAction.UnsetSeen, aChecked);
}
2014-08-21 23:08:34 +08:00
}
};
2014-08-21 23:08:34 +08:00
MailBoxMessageListViewModel.prototype.onBuild = function (oDom)
{
2014-08-21 23:08:34 +08:00
var
2014-08-22 23:08:56 +08:00
self = this
2014-08-21 23:08:34 +08:00
;
2014-08-21 23:08:34 +08:00
this.oContentVisible = $('.b-content', oDom);
this.oContentScrollable = $('.content', this.oContentVisible);
2014-08-21 23:08:34 +08:00
this.oContentVisible.on('click', '.fullThreadHandle', function () {
var
aList = [],
oMessage = ko.dataFor(this)
;
2014-08-21 23:08:34 +08:00
if (oMessage && !oMessage.lastInCollapsedThreadLoading())
{
2014-08-22 23:08:56 +08:00
Data.messageListThreadFolder(oMessage.folderFullNameRaw);
2014-08-22 23:08:56 +08:00
aList = Data.messageListThreadUids();
2014-08-21 23:08:34 +08:00
if (oMessage.lastInCollapsedThread())
{
2014-08-21 23:08:34 +08:00
aList.push(0 < oMessage.parentUid() ? oMessage.parentUid() : oMessage.uid);
}
else
{
2014-08-21 23:08:34 +08:00
aList = _.without(aList, 0 < oMessage.parentUid() ? oMessage.parentUid() : oMessage.uid);
}
2014-08-21 23:08:34 +08:00
2014-08-22 23:08:56 +08:00
Data.messageListThreadUids(_.uniq(aList));
2014-08-21 23:08:34 +08:00
oMessage.lastInCollapsedThreadLoading(true);
oMessage.lastInCollapsedThread(!oMessage.lastInCollapsedThread());
RL.reloadMessageList();
}
return false;
2014-08-21 23:08:34 +08:00
});
this.selector.init(this.oContentVisible, this.oContentScrollable, Enums.KeyState.MessageList);
oDom
.on('click', '.messageList .b-message-list-wrapper', function () {
if (self.message.focused())
{
self.message.focused(false);
}
})
.on('click', '.e-pagenator .e-page', function () {
var oPage = ko.dataFor(this);
if (oPage)
{
kn.setHash(LinkBuilder.mailBox(
2014-08-22 23:08:56 +08:00
Data.currentFolderFullNameHash(),
2014-08-21 23:08:34 +08:00
oPage.value,
2014-08-22 23:08:56 +08:00
Data.messageListSearch()
2014-08-21 23:08:34 +08:00
));
}
})
.on('click', '.messageList .checkboxCkeckAll', function () {
self.checkAll(!self.checkAll());
})
.on('click', '.messageList .messageListItem .flagParent', function () {
self.flagMessages(ko.dataFor(this));
})
;
this.initUploaderForAppend();
this.initShortcuts();
2014-08-22 23:08:56 +08:00
if (!Globals.bMobileDevice && AppSettings.capa(Enums.Capa.Prefetch) && ifvisible)
2014-08-21 23:08:34 +08:00
{
ifvisible.setIdleDuration(10);
ifvisible.idle(function () {
self.prefetchNextTick();
});
}
2014-08-21 23:08:34 +08:00
};
2014-08-21 23:08:34 +08:00
MailBoxMessageListViewModel.prototype.initShortcuts = function ()
{
var self = this;
2014-05-27 20:54:41 +08:00
2014-08-21 23:08:34 +08:00
// disable print
key('ctrl+p, command+p', Enums.KeyState.MessageList, function () {
return false;
});
2014-08-21 23:08:34 +08:00
// archive (zip)
key('z', [Enums.KeyState.MessageList, Enums.KeyState.MessageView], function () {
self.archiveCommand();
return false;
});
2014-08-21 23:08:34 +08:00
// delete
key('delete, shift+delete, shift+3', Enums.KeyState.MessageList, function (event, handler) {
if (event)
{
2014-08-22 23:08:56 +08:00
if (0 < Data.messageListCheckedOrSelected().length)
2014-08-21 23:08:34 +08:00
{
if (handler && 'shift+delete' === handler.shortcut)
{
self.deleteWithoutMoveCommand();
}
else
{
self.deleteCommand();
}
}
2014-04-09 04:59:22 +08:00
2014-08-21 23:08:34 +08:00
return false;
}
});
2014-08-21 23:08:34 +08:00
// check mail
key('ctrl+r, command+r', [Enums.KeyState.FolderList, Enums.KeyState.MessageList, Enums.KeyState.MessageView], function () {
self.reloadCommand();
return false;
});
2014-08-21 23:08:34 +08:00
// check all
key('ctrl+a, command+a', Enums.KeyState.MessageList, function () {
self.checkAll(!(self.checkAll() && !self.isIncompleteChecked()));
return false;
});
2014-04-09 04:59:22 +08:00
2014-08-21 23:08:34 +08:00
// write/compose (open compose popup)
key('w,c', [Enums.KeyState.MessageList, Enums.KeyState.MessageView], function () {
kn.showScreenPopup(PopupsComposeViewModel);
return false;
});
2014-04-09 04:59:22 +08:00
2014-08-21 23:08:34 +08:00
// important - star/flag messages
key('i', [Enums.KeyState.MessageList, Enums.KeyState.MessageView], function () {
self.flagMessagesFast();
return false;
});
2014-08-21 23:08:34 +08:00
// move
key('m', Enums.KeyState.MessageList, function () {
self.moveDropdownTrigger(true);
return false;
2014-08-21 23:08:34 +08:00
});
2014-08-21 23:08:34 +08:00
// read
key('q', [Enums.KeyState.MessageList, Enums.KeyState.MessageView], function () {
self.seenMessagesFast(true);
return false;
});
2014-08-21 23:08:34 +08:00
// unread
key('u', [Enums.KeyState.MessageList, Enums.KeyState.MessageView], function () {
self.seenMessagesFast(false);
return false;
});
2014-08-21 23:08:34 +08:00
key('shift+f', [Enums.KeyState.MessageList, Enums.KeyState.MessageView], function () {
self.multyForwardCommand();
return false;
});
2014-08-21 23:08:34 +08:00
// search input focus
key('/', [Enums.KeyState.MessageList, Enums.KeyState.MessageView], function () {
self.inputMessageListSearchFocus(true);
return false;
});
2014-08-21 23:08:34 +08:00
// cancel search
key('esc', Enums.KeyState.MessageList, function () {
if ('' !== self.messageListSearchDesc())
{
self.cancelSearch();
return false;
}
});
2014-08-21 23:08:34 +08:00
// change focused state
key('tab, shift+tab, left, right', Enums.KeyState.MessageList, function (event, handler) {
if (event && handler && 'shift+tab' === handler.shortcut || 'left' === handler.shortcut)
{
self.folderList.focused(true);
}
else if (self.message())
{
self.message.focused(true);
}
return false;
});
// TODO
key('ctrl+left, command+left', Enums.KeyState.MessageView, function () {
return false;
});
// TODO
key('ctrl+right, command+right', Enums.KeyState.MessageView, function () {
return false;
});
};
MailBoxMessageListViewModel.prototype.prefetchNextTick = function ()
{
if (!this.bPrefetch && !ifvisible.now() && this.viewModelVisibility())
{
2014-08-21 23:08:34 +08:00
var
self = this,
oMessage = _.find(this.messageList(), function (oMessage) {
return oMessage &&
!Cache.hasRequestedMessage(oMessage.folderFullNameRaw, oMessage.uid);
})
;
if (oMessage)
{
this.bPrefetch = true;
2014-08-21 23:08:34 +08:00
Cache.addRequestedMessage(oMessage.folderFullNameRaw, oMessage.uid);
2014-08-21 23:08:34 +08:00
Remote.message(function (sResult, oData) {
2014-08-21 23:08:34 +08:00
var bNext = !!(Enums.StorageResultType.Success === sResult && oData && oData.Result);
2014-08-21 23:08:34 +08:00
_.delay(function () {
self.bPrefetch = false;
if (bNext)
{
self.prefetchNextTick();
}
}, 1000);
2014-08-21 23:08:34 +08:00
}, oMessage.folderFullNameRaw, oMessage.uid);
}
}
2014-08-21 23:08:34 +08:00
};
MailBoxMessageListViewModel.prototype.composeClick = function ()
{
2014-08-21 23:08:34 +08:00
kn.showScreenPopup(PopupsComposeViewModel);
};
2014-08-21 23:08:34 +08:00
MailBoxMessageListViewModel.prototype.advancedSearchClick = function ()
{
kn.showScreenPopup(PopupsAdvancedSearchViewModel);
};
MailBoxMessageListViewModel.prototype.quotaTooltip = function ()
{
return Utils.i18n('MESSAGE_LIST/QUOTA_SIZE', {
'SIZE': Utils.friendlySize(this.userUsageSize()),
'PROC': this.userUsageProc(),
'LIMIT': Utils.friendlySize(this.userQuota())
});
};
2013-12-09 06:14:55 +08:00
2014-08-21 23:08:34 +08:00
MailBoxMessageListViewModel.prototype.initUploaderForAppend = function ()
{
2014-08-22 23:08:56 +08:00
if (!AppSettings.settingsGet('AllowAppendMessage') || !this.dragOverArea())
2014-08-21 23:08:34 +08:00
{
return false;
2014-08-21 23:08:34 +08:00
}
var oJua = new Jua({
'action': LinkBuilder.append(),
'name': 'AppendFile',
'queueSize': 1,
'multipleSizeLimit': 1,
'disableFolderDragAndDrop': true,
'hidden': {
'Folder': function () {
2014-08-22 23:08:56 +08:00
return Data.currentFolderFullNameRaw();
2014-08-21 23:08:34 +08:00
}
},
'dragAndDropElement': this.dragOverArea(),
'dragAndDropBodyElement': this.dragOverBodyArea()
});
oJua
.on('onDragEnter', _.bind(function () {
this.dragOverEnter(true);
}, this))
.on('onDragLeave', _.bind(function () {
this.dragOverEnter(false);
}, this))
.on('onBodyDragEnter', _.bind(function () {
this.dragOver(true);
}, this))
.on('onBodyDragLeave', _.bind(function () {
this.dragOver(false);
}, this))
.on('onSelect', _.bind(function (sUid, oData) {
if (sUid && oData && 'message/rfc822' === oData['Type'])
{
2014-08-22 23:08:56 +08:00
Data.messageListLoading(true);
2014-08-21 23:08:34 +08:00
return true;
}
return false;
}, this))
.on('onComplete', _.bind(function () {
RL.reloadMessageList(true, true);
}, this))
;
return !!oJua;
};
2014-08-22 23:08:56 +08:00
module.exports = MailBoxMessageListViewModel;
2014-08-21 23:08:34 +08:00
}(module));