Code refactoring

This commit is contained in:
RainLoop Team 2015-04-06 23:32:19 +04:00
parent ffde4f03a8
commit b7709c8117
21 changed files with 291 additions and 192 deletions

View file

@ -209,11 +209,6 @@
Remote.messageList(Utils.emptyFunction, Cache.getFolderInboxName(), 0, SettingsStore.messagesPerPage(), '', true);
};
AppUser.prototype.reloadMessageListHelper = function (bEmptyList)
{
this.reloadMessageList(bEmptyList);
};
/**
* @param {Function} fResultFunc
* @returns {boolean}
@ -316,7 +311,7 @@
}
}
this.reloadMessageListHelper(0 === MessageStore.messageList().length);
this.reloadMessageList(0 === MessageStore.messageList().length);
this.quotaDebounce();
}
};

View file

@ -65,11 +65,6 @@
*/
CacheUserStorage.prototype.oMessageFlagsCache = {};
/**
* @type {Object}
*/
CacheUserStorage.prototype.oBodies = {};
/**
* @type {Object}
*/
@ -88,10 +83,8 @@
this.oFolderUidNextCache = {};
this.oMessageListHashCache = {};
this.oMessageFlagsCache = {};
this.oBodies = {};
};
/**
* @param {string} sEmail
* @param {Function} fCallback

View file

@ -30,7 +30,8 @@
};
Opentip.styles.rainloopTestTip = {
'extends': 'rainloop'
'extends': 'rainloop',
'className': 'rainloopTestTip'
};
module.exports = Opentip;

33
dev/External/ko.js vendored
View file

@ -20,6 +20,39 @@
}
;
ko.bindingHandlers.editor = {
'init': function (oElement, fValueAccessor) {
var
fValue = fValueAccessor(),
oEditor = null,
fUpdateEditorValue = function () {
if (oEditor)
{
oEditor.setHtmlOrPlain(fValue());
}
},
fUpdateKoValue = function () {
if (oEditor)
{
fValue(oEditor.getDataWithHtmlMark());
}
},
HtmlEditor = require('Common/HtmlEditor')
;
if (fValue)
{
oEditor = new HtmlEditor(oElement, fUpdateKoValue, fUpdateEditorValue, fUpdateKoValue);
fValue.__editor = oEditor;
fValue.__fetchEditorValue = fUpdateKoValue;
fValue.__updateEditorValue = fUpdateEditorValue;
fValue.subscribe(fUpdateEditorValue);
}
}
};
ko.bindingHandlers.tooltip = {
'init': function (oElement, fValueAccessor) {

View file

@ -71,7 +71,7 @@
};
/**
* @param {AjaxJsonMessage} oJson
* @param {Object} oJson
* @return {boolean}
*/
MessageSimpleModel.prototype.initByJson = function (oJson)
@ -85,14 +85,16 @@
this.subject = Utils.pString(oJson.Subject);
this.subjectPrefix = '';
this.subjectSuffix = this.subject;
if (Utils.isArray(oJson.SubjectParts))
{
this.subjectPrefix = Utils.pString(oJson.SubjectParts[0]);
this.subjectSuffix = Utils.pString(oJson.SubjectParts[1]);
}
else
{
this.subjectPrefix = '';
this.subjectSuffix = this.subject;
}
this.from = MessageHelper.emailArrayFromJson(oJson.From);
this.to = MessageHelper.emailArrayFromJson(oJson.To);
@ -132,7 +134,7 @@
/**
* @static
* @param {AjaxJsonMessage} oJson
* @param {Object} oJson
* @return {?MessageSimpleModel}
*/
MessageSimpleModel.newInstanceFromJson = function (oJson)

View file

@ -1,66 +0,0 @@
(function () {
'use strict';
var
_ = require('_'),
ko = require('ko'),
// Enums = require('Common/Enums'),
// Utils = require('Common/Utils'),
//
// MessageHelper = require('Helper/Message'),
AbstractModel = require('Knoin/AbstractModel')
;
/**
* @constructor
*/
function MessageStatesModel()
{
AbstractModel.call(this, 'MessageStatesModel');
this.flags = {};
this.states = {};
this.flags.unseen = ko.observable(false);
this.flags.deleted = ko.observable(false);
this.flags.flagged = ko.observable(false);
this.flags.answered = ko.observable(false);
this.flags.forwarded = ko.observable(false);
this.states.checked = ko.observable(false);
this.states.deleted = ko.observable(false);
this.states.selected = ko.observable(false);
this.states.focused = ko.observable(false);
this.states.showReadReceipt = ko.observable(false);
this.states.showExternalImages = ko.observable(false);
this.states.hasUnseenSubMessages = ko.observable(false);
this.states.hasFlaggedSubMessages = ko.observable(false);
this.threads = ko.observableArray([]);
}
_.extend(MessageStatesModel.prototype, AbstractModel.prototype);
MessageStatesModel.prototype.flags = {};
MessageStatesModel.prototype.states = {};
MessageStatesModel.prototype.clear = function ()
{
this.flags.unseen(false);
this.flags.deleted(false);
this.flags.flagged(false);
this.flags.answered(false);
this.flags.forwarded(false);
this.threads([]);
};
module.exports = MessageStatesModel;
}());

View file

@ -113,6 +113,49 @@
});
};
// UserAjaxUserPromises.prototype.messageList = function (sFolderFullNameRaw, iOffset, iLimit, sSearch, fTrigger)
// {
// sFolderFullNameRaw = Utils.pString(sFolderFullNameRaw);
// sSearch = Utils.pString(sSearch);
// iOffset = Utils.pInt(iOffset);
// iLimit = Utils.pInt(iLimit);
//
// var sFolderHash = Cache.getFolderHash(sFolderFullNameRaw);
//
// if ('' !== sFolderHash && ('' === sSearch || -1 === sSearch.indexOf('is:')))
// {
// return this.abort('MessageList')
// .getRequest('MessageList', fTrigger,
// Links.subQueryPrefix() + '/' + Base64.urlsafe_encode([
// sFolderFullNameRaw,
// iOffset,
// iLimit,
// sSearch,
// AppStore.projectHash(),
// sFolderHash,
// Cache.getFolderInboxName() === sFolderFullNameRaw ? Cache.getFolderUidNext(sFolderFullNameRaw) : '',
// AppStore.threadsAllowed() && SettingsStore.useThreads() ? '1' : '0',
// ''
// ].join(String.fromCharCode(0))))
// .then(PromisesPopulator.messageList);
// }
// else
// {
// return this.abort('MessageList')
// .postRequest('MessageList', fTrigger,{
// 'Folder': sFolderFullNameRaw,
// 'Offset': iOffset,
// 'Limit': iLimit,
// 'Search': sSearch,
// 'UidNext': Cache.getFolderInboxName() === sFolderFullNameRaw ? Cache.getFolderUidNext(sFolderFullNameRaw) : '',
// 'UseThreads': AppStore.threadsAllowed() && SettingsStore.useThreads() ? '1' : '0'
// })
// .then(PromisesPopulator.messageList);
// }
//
// return this.fastReject(Enums.Notification.UnknownError);
// };
//
// UserAjaxUserPromises.prototype.message = function (sFolderFullNameRaw, iUid, fTrigger)
// {
// sFolderFullNameRaw = Utils.pString(sFolderFullNameRaw);

View file

@ -85,11 +85,6 @@
MessageStore.messageListPage(iPage);
MessageStore.messageListSearch(sSearch);
// if (Enums.Layout.NoPreview === SettingsStore.layout() && MessageStore.message())
// {
// MessageStore.message(null);
// }
require('App/User').reloadMessageList();
}
};

View file

@ -55,12 +55,12 @@
this.messageListDisableAutoSelect = ko.observable(false).extend({'falseTimeout': 500});
// message viewer
this.message = ko.observable(null);
this.selectorMessageSelected = ko.observable(null);
this.selectorMessageFocused = ko.observable(null);
// message viewer
this.message = ko.observable(null);
this.message.viewTrigger = ko.observable(false);
this.messageLastThreadUidsData = ko.observable(null);
@ -403,6 +403,24 @@
}
};
MessageUserStore.prototype.addBlockquoteSwitcherCallback = function ()
{
var $self = $(this);
if ('' !== Utils.trim(($self.text())))
{
$self.addClass('rl-bq-switcher hidden-bq');
$('<span class="rlBlockquoteSwitcher"><i class="icon-ellipsis" /></span>')
.insertBefore($self)
.on('click.rlBlockquoteSwitcher', function () {
$self.toggleClass('hidden-bq');
Utils.windowResize();
})
.after('<br />')
.before('<br />')
;
}
};
/**
* @param {Object} oMessageTextBody
*/
@ -416,19 +434,7 @@
if ($oList && 0 < $oList.length)
{
$oList.each(function () {
var $self = $(this);
$self.addClass('rl-bq-switcher hidden-bq');
$('<span class="rlBlockquoteSwitcher"><i class="icon-ellipsis" /></span>')
.insertBefore($self)
.click(function () {
$self.toggleClass('hidden-bq');
Utils.windowResize();
})
.after('<br />')
.before('<br />')
;
});
$oList.each(this.addBlockquoteSwitcherCallback);
}
}
};

View file

@ -1,9 +1,9 @@
.g-ui-user-select-none {
webkit-touch-callout: none;
user-select: none;
standard-user-select: none;
touch-callout: none;
// webkit-touch-callout: none;
// user-select: none;
// standard-user-select: none;
// touch-callout: none;
}
.g-ui-user-select-allow {

View file

@ -130,3 +130,31 @@
}
}
}
.cke_dialog {
a:hover {
text-decoration: none;
}
.cke_dialog_ui_labeled_content {
margin-top: 5px;
margin-bottom: 5px;
}
.cke_dialog_ui_input_select, .cke_dialog_ui_input_text, .cke_dialog_ui_input_textarea {
box-shadow: none;
border-radius: 2px;
&:focus {
outline: 0;
border: 1px solid #999;
}
}
.cke_dialog_ui_input_select, .cke_dialog_ui_input_text {
height: 25px;
line-height: 25px;
}
}

View file

@ -37,4 +37,8 @@
.ot-content {
font-size: 13px;
}
&.style-rainloopTestTip .ot-content {
color: red;
}
}

View file

@ -131,10 +131,42 @@
this.sendSuccessButSaveError = ko.observable(false);
this.savedError = ko.observable(false);
this.sendErrorDesc = ko.observable('');
this.savedErrorDesc = ko.observable('');
this.sendError.subscribe(function (bValue) {
if (!bValue)
{
this.sendErrorDesc('');
}
}, this);
this.savedError.subscribe(function (bValue) {
if (!bValue)
{
this.savedErrorDesc('');
}
}, this);
this.sendSuccessButSaveError.subscribe(function (bValue) {
if (!bValue)
{
this.savedErrorDesc('');
}
}, this);
this.savedTime = ko.observable(0);
this.savedOrSendingText = ko.observable('');
this.savedTimeText = ko.computed(function () {
return 0 < this.savedTime() ? Translator.i18n('COMPOSE/SAVED_TIME', {
'TIME': Momentor.format(this.savedTime() - 1, 'LT')
}) : '';
}, this);
this.emptyToError = ko.observable(false);
this.emptyToErrorTooltip = ko.computed(function () {
return this.emptyToError() ? Translator.i18n('COMPOSE/EMPTY_TO_ERROR_DESC') : '';
}, this);
this.attachmentsInProcessError = ko.observable(false);
this.attachmentsInErrorError = ko.observable(false);
@ -597,27 +629,25 @@
{
var
aIdentities = IdentityStore.identities(),
iResultIndex = 1000,
oResultIdentity = null,
oIdentitiesCache = {},
fFindHelper = function (oItem) {
if (oResultIdentity)
{
return true;
}
fEachHelper = function (oItem) {
if (!oResultIdentity && oItem && oItem.email && oIdentitiesCache[oItem.email])
if (oItem && oItem.email && oIdentitiesCache[oItem.email])
{
oResultIdentity = oIdentitiesCache[oItem.email];
return true;
if (!oResultIdentity || iResultIndex > oIdentitiesCache[oItem.email][1])
{
oResultIdentity = oIdentitiesCache[oItem.email][0];
iResultIndex = oIdentitiesCache[oItem.email][1];
}
}
return false;
}
;
_.each(aIdentities, function (oItem) {
oIdentitiesCache[oItem.email()] = oItem;
_.each(aIdentities, function (oItem, iIndex) {
oIdentitiesCache[oItem.email()] = [oItem, iIndex];
});
if (oMessage)
@ -630,10 +660,10 @@
case Enums.ComposeType.ReplyAll:
case Enums.ComposeType.Forward:
case Enums.ComposeType.ForwardAsAttachment:
_.find(_.union(oMessage.to, oMessage.cc, oMessage.bcc, oMessage.deliveredTo), fFindHelper);
_.each(_.union(oMessage.to, oMessage.cc, oMessage.bcc, oMessage.deliveredTo), fEachHelper);
break;
case Enums.ComposeType.Draft:
_.find(_.union(oMessage.from, oMessage.replyTo), fFindHelper);
_.each(_.union(oMessage.from, oMessage.replyTo), fEachHelper);
break;
}
}
@ -673,7 +703,7 @@
if (oData && Enums.Notification.CantSaveMessage === oData.ErrorCode)
{
this.sendSuccessButSaveError(true);
window.alert(Utils.trim(Translator.i18n('COMPOSE/SAVED_ERROR_ON_SEND')));
this.savedErrorDesc(Utils.trim(Translator.i18n('COMPOSE/SAVED_ERROR_ON_SEND')));
}
else
{
@ -681,7 +711,7 @@
oData && oData.ErrorMessage ? oData.ErrorMessage : '');
this.sendError(true);
window.alert(sMessage || Translator.getNotification(Enums.Notification.CantSendMessage));
this.sendErrorDesc(sMessage || Translator.getNotification(Enums.Notification.CantSendMessage));
}
}
@ -717,12 +747,6 @@
this.savedTime(window.Math.round((new window.Date()).getTime() / 1000));
this.savedOrSendingText(
0 < this.savedTime() ? Translator.i18n('COMPOSE/SAVED_TIME', {
'TIME': Momentor.format(this.savedTime() - 1, 'LT')
}) : ''
);
if (this.bFromDraft)
{
Cache.setFolderHash(this.draftFolder(), '');
@ -733,7 +757,7 @@
if (!bResult)
{
this.savedError(true);
this.savedOrSendingText(Translator.getNotification(Enums.Notification.CantSaveMessage));
this.savedErrorDesc(Translator.getNotification(Enums.Notification.CantSaveMessage));
}
this.reloadDraftFolder();
@ -1046,16 +1070,12 @@
oText = $(oMessage.body).clone();
if (oText)
{
oText.find('blockquote.rl-bq-switcher').each(function () {
$(this).removeClass('rl-bq-switcher hidden-bq');
});
oText.find('.rlBlockquoteSwitcher').each(function () {
$(this).remove();
});
}
oText.find('blockquote.rl-bq-switcher').removeClass('rl-bq-switcher hidden-bq');
oText.find('.rlBlockquoteSwitcher').off('.rlBlockquoteSwitcher').remove();
oText.find('[data-html-editor-font-wrapper]').removeAttr('data-html-editor-font-wrapper');
oText.find('[data-html-editor-font-wrapper]').removeAttr('data-html-editor-font-wrapper');
sText = oText.html();
sText = oText.html();
}
switch (sComposeType)
{
@ -2058,7 +2078,6 @@
this.sendSuccessButSaveError(false);
this.savedError(false);
this.savedTime(0);
this.savedOrSendingText('');
this.emptyToError(false);
this.attachmentsInProcessError(false);

View file

@ -11,7 +11,6 @@
Globals = require('Common/Globals'),
Utils = require('Common/Utils'),
Translator = require('Common/Translator'),
HtmlEditor = require('Common/HtmlEditor'),
Remote = require('Remote/User/Ajax'),
@ -33,9 +32,6 @@
this.edit = ko.observable(false);
this.owner = ko.observable(false);
this.editor = null;
this.signatureDom = ko.observable(null);
this.email = ko.observable('').validateEmail();
this.email.focused = ko.observable(false);
this.name = ko.observable('');
@ -70,7 +66,10 @@
this.addOrEditIdentityCommand = Utils.createCommand(this, function () {
this.populateSignatureFromEditor();
if (this.signature && this.signature.__fetchEditorValue)
{
this.signature.__fetchEditorValue();
}
if (!this.email.hasError())
{
@ -158,36 +157,6 @@
this.submitRequest(false);
this.submitError('');
if (this.editor)
{
this.editor.setPlain('', false);
}
};
IdentityPopupView.prototype.populateSignatureFromEditor = function ()
{
if (this.editor)
{
this.signature(this.editor.getDataWithHtmlMark());
}
};
IdentityPopupView.prototype.editorSetSignature = function (sSignature)
{
if (!this.editor && this.signatureDom())
{
var self = this;
this.editor = new HtmlEditor(self.signatureDom(), function () {
self.populateSignatureFromEditor();
}, function () {
self.editor.setHtmlOrPlain(sSignature);
});
}
else
{
this.editor.setHtmlOrPlain(sSignature);
}
};
/**
@ -215,8 +184,6 @@
{
this.id = Utils.fakeMd5();
}
this.editorSetSignature(this.signature());
};
IdentityPopupView.prototype.onShowWithDelay = function ()

View file

@ -61,11 +61,17 @@
this.submitRequest(true);
_.delay(function () {
mKeyPair = PgpStore.openpgp.generateKeyPair({
'userId': sUserID,
'numBits': Utils.pInt(self.keyBitLength()),
'passphrase': Utils.trim(self.password())
});
mKeyPair = false;
try {
mKeyPair = PgpStore.openpgp.generateKeyPair({
'userId': sUserID,
'numBits': Utils.pInt(self.keyBitLength()),
'passphrase': Utils.trim(self.password())
});
} catch (e) {
// window.console.log(e);
}
if (mKeyPair && mKeyPair.privateKeyArmored)
{
@ -78,6 +84,7 @@
}
self.submitRequest(false);
}, 100);
return true;

View file

@ -79,12 +79,14 @@
&nbsp;&nbsp;
<span data-i18n="TAB_LICENSING/BUTTON_PURCHASE"></span>
</a>
<!--
&nbsp;&nbsp;
<a class="btn" data-bind="click: showTrialForm, visible: !licensing()">
<i class="icon-eye"></i>
&nbsp;&nbsp;
<span data-i18n="TAB_LICENSING/BUTTON_TRIAL"></span>
</a>
-->
</div>
</div>
</div>

View file

@ -1,12 +1,12 @@
<div class="popups">
<div class="modal hide b-compose" data-backdrop="static" data-bind="modal: modalVisibility, css: {'loading': saving() || sending()}">
<div class="modal-header b-header-toolbar g-ui-user-select-none">
<a class="btn btn-large button-send" data-bind="command: sendCommand, css: {'btn-danger': sendError, 'btn-warning': sendSuccessButSaveError }">
<a class="btn btn-large button-send" data-bind="command: sendCommand, tooltipForTest: sendErrorDesc, css: {'btn-danger': sendError, 'btn-warning': sendSuccessButSaveError }">
<i data-bind="css: {'icon-paper-plane': !sending(), 'icon-spinner animated big': sending(), 'icon-white': sendError() || sendSuccessButSaveError()}"></i>
&nbsp;&nbsp;
<span class="i18n" data-i18n="COMPOSE/BUTTON_SEND"></span>
</a>
<a class="btn button-save" data-bind="command: saveCommand, css: {'btn-danger': savedError }">
<a class="btn button-save" data-bind="command: saveCommand, tooltipForTest: savedErrorDesc, css: {'btn-danger': savedError }">
<i data-bind="css: {'icon-floppy': !saving(), 'icon-spinner animated': saving(), 'icon-white': savedError()}"></i>
&nbsp;&nbsp;
<span class="i18n" data-i18n="COMPOSE/BUTTON_SAVE"></span>
@ -18,7 +18,7 @@
<a class="btn btn-danger button-delete button-delete-transitions" data-bind="command: deleteCommand">
<i class="icon-trash icon-white"></i>
</a>
<span class="saved-text" data-bind="text: savedOrSendingText, css: { 'errorDesc': savedError }"></span>
<span class="saved-text" data-bind="text: savedTimeText"></span>
</div>
<div class="modal-body">
<div>

View file

@ -81,7 +81,7 @@
</div>
</div>
<div class="control-group">
<div class="e-signature-place" data-bind="initDom: signatureDom"></div>
<div class="e-signature-place" data-bind="editor: signature"></div>
</div>
</div>
</div>

View file

@ -0,0 +1,64 @@
<div class="popups">
<div class="modal hide b-filter-content g-ui-user-select-none" data-bind="modal: modalVisibility">
<div>
<div class="modal-header">
<button type="button" class="close" data-bind="command: cancelCommand">&times;</button>
<h3>
<span class="i18n" data-i18n="POPUPS_FILTER/TITLE_CREATE_FILTER" data-bind="visible: isNew"></span>
<span class="i18n" data-i18n="POPUPS_FILTER/TITLE_EDIT_FILTER" data-bind="visible: !isNew()"></span>
</h3>
</div>
<div class="modal-body">
<div class="row filter" data-bind="with: filter, i18nInit: filter">
<div class="span9" data-bind="i18nInit: true">
<div class="control-group" data-bind="css: {'error': name.error}">
<div class="controls">
<input type="text" class="i18n span5"
data-bind="value: name, hasFocus: name.focused"
autocorrect="off" autocapitalize="off" spellcheck="false"
data-i18n="[placeholder]POPUPS_FILTER/FILTER_NAME"
/>
</div>
</div>
<div class="legend i18n" data-i18n="POPUPS_FILTER/LEGEND_CONDITIONS"></div>
<div>
<div data-bind="visible: 1 < conditions().length">
<select class="span4" data-bind="value: conditionsType">
<option value="Any" class="i18n"
data-i18n="POPUPS_FILTER/SELECT_MATCH_ANY"></option>
<option value="All" class="i18n"
data-i18n="POPUPS_FILTER/SELECT_MATCH_ALL"></option>
</select>
</div>
<div data-bind="visible: 0 < conditions().length, foreach: conditions">
<div data-bind="template: {'name': template(), 'data': $data}"></div>
</div>
<div data-bind="visible: 0 === conditions().length">
<span class="i18n" data-i18n="POPUPS_FILTER/ALL_INCOMING_MESSAGES_DESC"></span>
</div>
<br />
<a class="btn" data-bind="click: addCondition, i18nInit: true">
<i class="icon-plus"></i>
&nbsp;&nbsp;
<span class="i18n" data-i18n="POPUPS_FILTER/BUTTON_ADD_CONDITION"></span>
</a>
</div>
<br />
<div class="legend i18n" data-i18n="POPUPS_FILTER/LEGEND_ACTIONS"></div>
<select class="span3" data-bind="options: $root.actionTypeOptions, value: actionType, optionsText: 'name', optionsValue: 'id'"></select>
<div data-bind="template: {'name': actionTemplate()}, i18nUpdate: actionTemplate"></div>
</div>
</div>
</div>
<div class="modal-footer">
<a class="btn buttonSave" data-bind="command: saveFilter">
<i class="icon-ok"></i>
&nbsp;&nbsp;
<span class="i18n" data-i18n="POPUPS_FILTER/BUTTON_DONE"></span>
</a>
</div>
</div>
</div>
</div>

View file

@ -27,4 +27,10 @@ disableContextMenu:function(){return false;this.on("contextmenu",
proto:{addTarget:function(a,e){a.on("contextmenu",function(a){
-->
proto:{addTarget:function(a,e){a.on("contextmenu",function(a){return false;
proto:{addTarget:function(a,e){a.on("contextmenu",function(a){return false;
---
var a=this.$.nodeName.toLowerCase();
-->
var a=(this.$?(this.$.nodeName||''):'').toLowerCase();

View file

@ -27,4 +27,4 @@ disableContextMenu:function(){return false;this.on("contextmenu",
proto:{addTarget:function(a,e){a.on("contextmenu",function(a){
-->
proto:{addTarget:function(a,e){a.on("contextmenu",function(a){return false;
proto:{addTarget:function(a,e){a.on("contextmenu",function(a){return false;