mirror of
https://github.com/the-djmaze/snappymail.git
synced 2025-03-04 18:53:42 +08:00
Resolve issue #112
This commit is contained in:
parent
1f9e96f107
commit
ba477e25ff
12 changed files with 82 additions and 106 deletions
|
@ -1,8 +1,10 @@
|
|||
import { ComposeType, FolderType } from 'Common/EnumsUser';
|
||||
import { ComposeType/*, FolderType*/ } from 'Common/EnumsUser';
|
||||
import { EmailModel } from 'Model/Email';
|
||||
import { encodeHtml } from 'Common/Html';
|
||||
import { isArray } from 'Common/Utils';
|
||||
import { createElement } from 'Common/Globals';
|
||||
import { FolderUserStore } from 'Stores/User/Folder';
|
||||
import { SettingsUserStore } from 'Stores/User/Settings';
|
||||
|
||||
/**
|
||||
* @param {(string|number)} value
|
||||
|
@ -213,24 +215,20 @@ rl.Utils = {
|
|||
|
||||
/**
|
||||
* @param {Array} aSystem
|
||||
* @param {Array} aList
|
||||
* @param {Array=} aDisabled
|
||||
* @param {Array=} aHeaderLines
|
||||
* @param {Function=} fDisableCallback
|
||||
* @param {Function=} fRenameCallback
|
||||
* @param {boolean=} bSystem
|
||||
* @param {boolean=} bBuildUnvisible
|
||||
* @param {boolean=} bNoSelectSelectable Used in FolderCreatePopupView
|
||||
* @returns {Array}
|
||||
*/
|
||||
export function folderListOptionsBuilder(
|
||||
aSystem,
|
||||
aList,
|
||||
aDisabled,
|
||||
aHeaderLines,
|
||||
fDisableCallback,
|
||||
fRenameCallback,
|
||||
bSystem,
|
||||
bBuildUnvisible
|
||||
fDisableCallback,
|
||||
bNoSelectSelectable
|
||||
) {
|
||||
let /**
|
||||
* @type {?FolderModel}
|
||||
|
@ -238,71 +236,67 @@ export function folderListOptionsBuilder(
|
|||
bSep = false,
|
||||
aResult = [];
|
||||
|
||||
const sDeepPrefix = '\u00A0\u00A0\u00A0';
|
||||
const sDeepPrefix = '\u00A0\u00A0\u00A0',
|
||||
// FolderSystemPopupView should always be true
|
||||
showUnsubscribed = (aSystem.length || bNoSelectSelectable) ? !SettingsUserStore.hideUnsubscribed() : true;
|
||||
|
||||
bBuildUnvisible = undefined === bBuildUnvisible ? false : !!bBuildUnvisible;
|
||||
bSystem = null == bSystem ? 0 < aSystem.length : bSystem;
|
||||
fDisableCallback = null != fDisableCallback ? fDisableCallback : null;
|
||||
fRenameCallback = null != fRenameCallback ? fRenameCallback : null;
|
||||
fDisableCallback = fDisableCallback || (() => false);
|
||||
fRenameCallback = fRenameCallback || (oItem => oItem.name());
|
||||
|
||||
if (!isArray(aDisabled)) {
|
||||
aDisabled = [];
|
||||
}
|
||||
|
||||
if (!isArray(aHeaderLines)) {
|
||||
aHeaderLines = [];
|
||||
}
|
||||
|
||||
aHeaderLines.forEach(line => {
|
||||
isArray(aHeaderLines) && aHeaderLines.forEach(line =>
|
||||
aResult.push({
|
||||
id: line[0],
|
||||
name: line[1],
|
||||
system: false,
|
||||
dividerbar: false,
|
||||
disabled: false
|
||||
});
|
||||
});
|
||||
})
|
||||
);
|
||||
|
||||
bSep = true;
|
||||
aSystem.forEach(oItem => {
|
||||
aResult.push({
|
||||
id: oItem.fullNameRaw,
|
||||
name: fRenameCallback ? fRenameCallback(oItem) : oItem.name(),
|
||||
name: fRenameCallback(oItem),
|
||||
system: true,
|
||||
dividerbar: bSep,
|
||||
disabled:
|
||||
!oItem.selectable ||
|
||||
aDisabled.includes(oItem.fullNameRaw) ||
|
||||
(fDisableCallback ? fDisableCallback(oItem) : false)
|
||||
fDisableCallback(oItem)
|
||||
});
|
||||
bSep = false;
|
||||
});
|
||||
|
||||
bSep = true;
|
||||
aList.forEach(oItem => {
|
||||
// if (oItem.subscribed() || !oItem.exists || bBuildUnvisible)
|
||||
if (
|
||||
(oItem.subscribed() || !oItem.exists || bBuildUnvisible) &&
|
||||
(oItem.selectable || oItem.hasSubscribedSubfolders())
|
||||
FolderUserStore.folderList().forEach(oItem => {
|
||||
/*
|
||||
if ((oItem.subscribed() || !oItem.exists || bBuildUnvisible)
|
||||
&& (oItem.selectable || oItem.hasSubscribedSubfolders())
|
||||
&& (FolderType.User === oItem.type() || !bSystem || oItem.hasSubscribedSubfolders()) {
|
||||
) {
|
||||
if (FolderType.User === oItem.type() || !bSystem || oItem.hasSubscribedSubfolders()) {
|
||||
aResult.push({
|
||||
id: oItem.fullNameRaw,
|
||||
name:
|
||||
sDeepPrefix.repeat(oItem.deep + 1) +
|
||||
(fRenameCallback ? fRenameCallback(oItem) : oItem.name()),
|
||||
system: false,
|
||||
dividerbar: bSep,
|
||||
disabled:
|
||||
!oItem.selectable ||
|
||||
aDisabled.includes(oItem.fullNameRaw) ||
|
||||
(fDisableCallback ? fDisableCallback(oItem) : false)
|
||||
});
|
||||
bSep = false;
|
||||
}
|
||||
*/
|
||||
if (showUnsubscribed || oItem.subscribed() || !oItem.exists || oItem.hasSubscribedSubfolders()) {
|
||||
aResult.push({
|
||||
id: oItem.fullNameRaw,
|
||||
name:
|
||||
sDeepPrefix.repeat(oItem.deep) +
|
||||
fRenameCallback(oItem),
|
||||
system: false,
|
||||
dividerbar: bSep,
|
||||
disabled: !bNoSelectSelectable && (
|
||||
!oItem.selectable ||
|
||||
aDisabled.includes(oItem.fullNameRaw) ||
|
||||
fDisableCallback(oItem))
|
||||
});
|
||||
bSep = false;
|
||||
}
|
||||
|
||||
if (oItem.subscribed() && oItem.subFolders.length) {
|
||||
if (oItem.subFolders.length) {
|
||||
aResult = aResult.concat(
|
||||
folderListOptionsBuilder(
|
||||
[],
|
||||
|
@ -311,8 +305,7 @@ export function folderListOptionsBuilder(
|
|||
[],
|
||||
fDisableCallback,
|
||||
fRenameCallback,
|
||||
bSystem,
|
||||
bBuildUnvisible
|
||||
bNoSelectSelectable
|
||||
)
|
||||
);
|
||||
}
|
||||
|
|
|
@ -257,13 +257,13 @@ export class FolderModel extends AbstractModel {
|
|||
oFolder => (oFolder.subscribed() || oFolder.hasSubscribedSubfolders()) && !oFolder.isSystemFolder()
|
||||
),
|
||||
|
||||
canBeEdited: () => FolderType.User === folder.type() && folder.exists && folder.selectable,
|
||||
canBeEdited: () => FolderType.User === folder.type() && folder.exists/* && folder.selectable*/,
|
||||
|
||||
visible: () => {
|
||||
const isSubscribed = folder.subscribed(),
|
||||
isSubFolders = folder.hasSubscribedSubfolders();
|
||||
|
||||
return isSubscribed || (isSubFolders && (!folder.exists || !folder.selectable));
|
||||
return isSubscribed || (isSubFolders && (!folder.exists/* || !folder.selectable*/));
|
||||
},
|
||||
|
||||
isSystemFolder: () => FolderType.User !== folder.type(),
|
||||
|
|
|
@ -118,25 +118,16 @@ export class FoldersUserSettings {
|
|||
}
|
||||
}
|
||||
|
||||
subscribeFolder(folder) {
|
||||
toggleFolderSubscription(folder) {
|
||||
let subscribe = !folder.subscribed();
|
||||
Local.set(ClientSideKeyName.FoldersLashHash, '');
|
||||
Remote.folderSetSubscribe(()=>0, folder.fullNameRaw, true);
|
||||
folder.subscribed(true);
|
||||
Remote.folderSetSubscribe(()=>0, folder.fullNameRaw, subscribe);
|
||||
folder.subscribed(subscribe);
|
||||
}
|
||||
|
||||
unSubscribeFolder(folder) {
|
||||
Local.set(ClientSideKeyName.FoldersLashHash, '');
|
||||
Remote.folderSetSubscribe(()=>0, folder.fullNameRaw, false);
|
||||
folder.subscribed(false);
|
||||
}
|
||||
|
||||
checkableTrueFolder(folder) {
|
||||
Remote.folderSetCheckable(()=>0, folder.fullNameRaw, true);
|
||||
folder.checkable(true);
|
||||
}
|
||||
|
||||
checkableFalseFolder(folder) {
|
||||
Remote.folderSetCheckable(()=>0, folder.fullNameRaw, false);
|
||||
folder.checkable(false);
|
||||
toggleFolderCheckable(folder) {
|
||||
let checkable = !folder.checkable();
|
||||
Remote.folderSetCheckable(()=>0, folder.fullNameRaw, checkable);
|
||||
folder.checkable(checkable);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -3,7 +3,6 @@ import ko from 'ko';
|
|||
import { FolderType, FolderSortMode } from 'Common/EnumsUser';
|
||||
import { UNUSED_OPTION_VALUE } from 'Common/Consts';
|
||||
import { addObservablesTo, addSubscribablesTo } from 'Common/Utils';
|
||||
import { folderListOptionsBuilder } from 'Common/UtilsUser';
|
||||
import { getFolderInboxName, getFolderFromCacheList } from 'Common/Cache';
|
||||
import { SettingsGet } from 'Common/Globals';
|
||||
|
||||
|
@ -107,28 +106,6 @@ export const FolderUserStore = new class {
|
|||
this.folderListSystemNames().map(name => getFolderFromCacheList(name)).filter(v => v)
|
||||
);
|
||||
|
||||
this.folderMenuForMove = ko.computed(() =>
|
||||
folderListOptionsBuilder(
|
||||
this.folderListSystem(),
|
||||
this.folderList(),
|
||||
[this.currentFolderFullNameRaw()],
|
||||
[],
|
||||
null,
|
||||
(item) => (item ? item.localName() : '')
|
||||
)
|
||||
);
|
||||
|
||||
this.folderMenuForFilters = ko.computed(() =>
|
||||
folderListOptionsBuilder(
|
||||
this.folderListSystem(),
|
||||
this.folderList(),
|
||||
[this.sieveAllowFileintoInbox ? '' : 'INBOX'],
|
||||
[['', '']],
|
||||
null,
|
||||
(item) => (item ? item.localName() : '')
|
||||
)
|
||||
);
|
||||
|
||||
const
|
||||
fRemoveSystemFolderType = (observable) => () => {
|
||||
const folder = getFolderFromCacheList(observable());
|
||||
|
|
|
@ -111,6 +111,9 @@
|
|||
color: var(--folders-selected-color, #eee);
|
||||
}
|
||||
}
|
||||
&:not(.selectable) {
|
||||
font-style: italic;
|
||||
}
|
||||
|
||||
&.focused {
|
||||
background-color: #888;
|
||||
|
|
|
@ -34,6 +34,10 @@
|
|||
|
||||
.folder-item {
|
||||
|
||||
&:not(.selectable) {
|
||||
font-style: italic;
|
||||
}
|
||||
|
||||
&.system .folder-name {
|
||||
font-weight: bold;
|
||||
}
|
||||
|
|
|
@ -11,6 +11,8 @@ import { SieveUserStore } from 'Stores/User/Sieve';
|
|||
import { decorateKoCommands } from 'Knoin/Knoin';
|
||||
import { AbstractViewPopup } from 'Knoin/AbstractViews';
|
||||
|
||||
import { folderListOptionsBuilder } from 'Common/UtilsUser';
|
||||
|
||||
class FilterPopupView extends AbstractViewPopup {
|
||||
constructor() {
|
||||
super('Filter');
|
||||
|
@ -25,7 +27,15 @@ class FilterPopupView extends AbstractViewPopup {
|
|||
this.fTrueCallback = null;
|
||||
|
||||
this.defaultOptionsAfterRender = defaultOptionsAfterRender;
|
||||
this.folderSelectList = FolderUserStore.folderMenuForFilters;
|
||||
this.folderSelectList = ko.computed(() =>
|
||||
folderListOptionsBuilder(
|
||||
FolderUserStore.folderListSystem(),
|
||||
[FolderUserStore.sieveAllowFileintoInbox ? '' : 'INBOX'],
|
||||
[['', '']],
|
||||
item => item ? item.localName() : ''
|
||||
)
|
||||
);
|
||||
|
||||
|
||||
this.selectedFolderValue.subscribe(() => this.filter() && this.filter().actionValueError(false));
|
||||
|
||||
|
|
|
@ -25,14 +25,14 @@ class FolderCreatePopupView extends AbstractViewPopup {
|
|||
this.parentFolderSelectList = ko.computed(() =>
|
||||
folderListOptionsBuilder(
|
||||
[],
|
||||
FolderUserStore.folderList(),
|
||||
[],
|
||||
[['', '']],
|
||||
oItem =>
|
||||
oItem ? (oItem.isSystemFolder() ? oItem.name() + ' ' + oItem.manageFolderSystemName() : oItem.name()) : '',
|
||||
FolderUserStore.namespace
|
||||
? item => FolderUserStore.namespace !== item.fullNameRaw.substr(0, FolderUserStore.namespace.length)
|
||||
: null,
|
||||
oItem =>
|
||||
oItem ? (oItem.isSystemFolder() ? oItem.name() + ' ' + oItem.manageFolderSystemName() : oItem.name()) : ''
|
||||
true
|
||||
)
|
||||
);
|
||||
|
||||
|
|
|
@ -30,16 +30,11 @@ class FolderSystemPopupView extends AbstractViewPopup {
|
|||
this.folderSelectList = ko.computed(() =>
|
||||
folderListOptionsBuilder(
|
||||
[],
|
||||
FolderUserStore.folderList(),
|
||||
FolderUserStore.folderListSystemNames(),
|
||||
[
|
||||
['', this.sChooseOnText],
|
||||
[UNUSED_OPTION_VALUE, this.sUnuseText]
|
||||
],
|
||||
null,
|
||||
null,
|
||||
null,
|
||||
true
|
||||
]
|
||||
)
|
||||
);
|
||||
|
||||
|
|
|
@ -15,7 +15,7 @@ import { UNUSED_OPTION_VALUE } from 'Common/Consts';
|
|||
|
||||
import { doc, leftPanelDisabled, moveAction, Settings, SettingsGet } from 'Common/Globals';
|
||||
|
||||
import { computedPaginatorHelper, showMessageComposer } from 'Common/UtilsUser';
|
||||
import { computedPaginatorHelper, showMessageComposer, folderListOptionsBuilder } from 'Common/UtilsUser';
|
||||
import { FileInfo } from 'Common/File';
|
||||
|
||||
import { mailBox, serverRequest } from 'Common/Links';
|
||||
|
@ -78,7 +78,14 @@ export class MessageListMailBoxUserView extends AbstractViewRight {
|
|||
this.isMessageSelected = MessageUserStore.isMessageSelected;
|
||||
this.messageListSearch = MessageUserStore.listSearch;
|
||||
this.messageListError = MessageUserStore.listError;
|
||||
this.folderMenuForMove = FolderUserStore.folderMenuForMove;
|
||||
this.folderMenuForMove = ko.computed(() =>
|
||||
folderListOptionsBuilder(
|
||||
FolderUserStore.folderListSystem(),
|
||||
[FolderUserStore.currentFolderFullNameRaw()],
|
||||
[],
|
||||
item => item ? item.localName() : ''
|
||||
)
|
||||
);
|
||||
|
||||
this.useCheckboxesInList = SettingsUserStore.useCheckboxesInList;
|
||||
|
||||
|
|
|
@ -233,7 +233,7 @@ class Folder implements \JsonSerializable
|
|||
'FullName' => $this->FullName(),
|
||||
'FullNameRaw' => $this->FullNameRaw(),
|
||||
'Delimiter' => (string) $this->Delimiter(),
|
||||
'HasVisibleSubFolders' => $this->HasVisibleSubFolders(),
|
||||
// 'HasVisibleSubFolders' => $this->HasVisibleSubFolders(),
|
||||
'Subscribed' => $this->bSubscribed,
|
||||
'Exists' => $this->bExists,
|
||||
'Selectable' => $this->IsSelectable(),
|
||||
|
|
|
@ -14,14 +14,10 @@
|
|||
<span class="delete-folder e-action fontastic" data-bind="visible: canBeDeleted() && !deleteAccess(), click: function (oFolder) { $root.folderForDeletion(oFolder); }">🗑</span>
|
||||
</td>
|
||||
<td data-i18n="[title]SETTINGS_FOLDERS/HELP_SHOW_HIDE_FOLDER">
|
||||
<span class="unsubscribed-folder e-action fontastic" data-bind="visible: canBeSubscribed() && !subscribed(), click: function(oFolder) { $root.subscribeFolder(oFolder); }">👁</span>
|
||||
<span class="e-action fontastic" data-bind="visible: canBeSubscribed() && subscribed(), click: function(oFolder) { $root.unSubscribeFolder(oFolder); }">👁</span>
|
||||
<span class="e-action fontastic" data-bind="css: {'unsubscribed-folder':!subscribed()}, visible: canBeSubscribed(), click: function(oFolder) { $root.toggleFolderSubscription(oFolder); }">👁</span>
|
||||
</td>
|
||||
<td data-bind="visible: $root.displaySpecSetting" data-i18n="[title]SETTINGS_FOLDERS/HELP_CHECK_FOR_NEW_MESSAGES">
|
||||
<span class="unchecked-folder e-action" data-bind="visible: canBeSelected() && subscribed() && !checkable(), click: function(oFolder) { $root.checkableTrueFolder(oFolder); }">
|
||||
<i class="icon-check-mark-circle-two"></i>
|
||||
</span>
|
||||
<span class="check-folder e-action" data-bind="visible: canBeSelected() && subscribed() && checkable(), click: function(oFolder) { $root.checkableFalseFolder(oFolder); }">
|
||||
<span class="e-action" data-bind="css: {'check-folder':checkable(), 'unchecked-folder':!checkable()}, visible: canBeSelected() && subscribed(), click: function(oFolder) { $root.toggleFolderCheckable(oFolder); }">
|
||||
<i class="icon-check-mark-circle-two"></i>
|
||||
</span>
|
||||
</td>
|
||||
|
|
Loading…
Reference in a new issue