diff --git a/SoObjects/Mailer/SOGoMailAccount.m b/SoObjects/Mailer/SOGoMailAccount.m
index 4350a9bfc..600f2d636 100644
--- a/SoObjects/Mailer/SOGoMailAccount.m
+++ b/SoObjects/Mailer/SOGoMailAccount.m
@@ -400,7 +400,7 @@ static NSString *inboxFolderName = @"INBOX";
{
NSString *folderType;
- if ([folderName isEqualToString: [NSString stringWithFormat: @"/%@", inboxFolderName]])
+ if ([folderName isEqualToString: inboxFolderName])
folderType = @"inbox";
else if ([folderName isEqualToString: [self draftsFolderNameInContext: context]])
folderType = @"draft";
@@ -408,6 +408,10 @@ static NSString *inboxFolderName = @"INBOX";
folderType = @"sent";
else if ([folderName isEqualToString: [self trashFolderNameInContext: context]])
folderType = @"trash";
+ else if ([folderName isEqualToString: otherUsersFolderName])
+ folderType = @"otherUsers";
+ else if ([folderName isEqualToString: sharedFoldersName])
+ folderType = @"shared";
else
folderType = @"folder";
diff --git a/UI/MailerUI/UIxMailFolderActions.m b/UI/MailerUI/UIxMailFolderActions.m
index 1b45b902b..a88d716ba 100644
--- a/UI/MailerUI/UIxMailFolderActions.m
+++ b/UI/MailerUI/UIxMailFolderActions.m
@@ -187,6 +187,7 @@
NGImap4Connection *connection;
NSException *error;
NSURL *srcURL, *destURL;
+ NSDictionary *jsonResponse;
NSMutableDictionary *moduleSettings, *threadsCollapsed;
NSString *currentMailbox, *currentAccount, *keyForMsgUIDs;
@@ -202,8 +203,10 @@
error = [connection moveMailboxAtURL: srcURL toURL: destURL];
if (error)
{
- response = [self responseWithStatus: 500];
- [response appendContentString: @"Unable to move folder."];
+ jsonResponse = [NSDictionary dictionaryWithObject: [self labelForKey: @"Unable to move folder."]
+ forKey: @"error"];
+ response = [self responseWithStatus: 500
+ andString: [jsonResponse jsonRepresentation]];
}
else
{
@@ -232,8 +235,10 @@
}
else
{
- response = [self responseWithStatus: 500];
- [response appendContentString: @"Unable to move folder."];
+ jsonResponse = [NSDictionary dictionaryWithObject: [self labelForKey: @"Unable to move folder."]
+ forKey: @"error"];
+ response = [self responseWithStatus: 500
+ andString: [jsonResponse jsonRepresentation]];
}
return response;
diff --git a/UI/Templates/MailerUI/UIxMailMainFrame.wox b/UI/Templates/MailerUI/UIxMailMainFrame.wox
index b1d8215db..893c54cb2 100644
--- a/UI/Templates/MailerUI/UIxMailMainFrame.wox
+++ b/UI/Templates/MailerUI/UIxMailMainFrame.wox
@@ -240,29 +240,15 @@
diff --git a/UI/WebServerResources/js/Common/ui-desktop.js b/UI/WebServerResources/js/Common/ui-desktop.js
index e7b64ab69..66e4000ea 100644
--- a/UI/WebServerResources/js/Common/ui-desktop.js
+++ b/UI/WebServerResources/js/Common/ui-desktop.js
@@ -143,36 +143,28 @@
.directive('sgFolderTree', function(RecursionHelper) {
return {
restrict: 'E',
- replace: true,
scope: {
root: '=sgRoot',
folder: '=sgFolder',
setFolder: '=sgSetFolder'
},
template:
- '' +
- '
' +
- ' ' +
- ' ' +
- ' ' +
- ' ' +
- ' ' +
- ' ' +
- ' ' +
+ '' +
+ ' ' +
+ ' ' +
+ ' ' +
+ ' ' +
+ ' ' +
+ ' ' +
' ' +
' ' +
- ' ' +
- ' ' +
- ' ' +
- ' ' +
- ' ' +
- '
' +
- ' ',
+ ' ' +
+ '' +
+ '',
compile: function(element) {
return RecursionHelper.compile(element, function(scope, iElement, iAttrs, controller, transcludeFn) {
// Set CSS class for folder hierarchical level
diff --git a/UI/WebServerResources/js/Mailer/account-model.js b/UI/WebServerResources/js/Mailer/account-model.js
index 1d40c2150..23d9a0e88 100644
--- a/UI/WebServerResources/js/Mailer/account-model.js
+++ b/UI/WebServerResources/js/Mailer/account-model.js
@@ -70,13 +70,14 @@
* @function $getMailboxes
* @memberof Account.prototype
* @desc Fetch the list of mailboxes for the current account.
+ * @param {object} [options] - force a reload
* @returns a promise of the HTTP operation
*/
- Account.prototype.$getMailboxes = function() {
+ Account.prototype.$getMailboxes = function(options) {
var _this = this,
deferred = Account.$q.defer();
- if (this.$mailboxes) {
+ if (this.$mailboxes && !(options && options.reload)) {
deferred.resolve(this.$mailboxes);
}
else {
@@ -161,6 +162,26 @@
return mailbox;
};
+ /**
+ * @function $newMailbox
+ * @memberof Account.prototype
+ * @desc Create a new mailbox on the server and refresh the list of mailboxes.
+ * @returns a promise of the HTTP operations
+ */
+ Account.prototype.$newMailbox = function(path, name) {
+ var _this = this,
+ deferred = Account.$q.defer();
+
+ Account.$$resource.post(path, 'createFolder', {name: name}).then(function() {
+ _this.$getMailboxes({reload: true});
+ deferred.resolve();
+ }, function(response) {
+ deferred.reject(response.error);
+ });
+
+ return deferred.promise;
+ };
+
/**
* @function $newMessage
* @memberof Account.prototype
diff --git a/UI/WebServerResources/js/Mailer/mailbox-model.js b/UI/WebServerResources/js/Mailer/mailbox-model.js
index 65b7bd769..558ef7e2d 100644
--- a/UI/WebServerResources/js/Mailer/mailbox-model.js
+++ b/UI/WebServerResources/js/Mailer/mailbox-model.js
@@ -13,7 +13,15 @@
// Data is immediately available
if (typeof futureMailboxData.then !== 'function') {
angular.extend(this, futureMailboxData);
- this.id = this.$id();
+ if (this.name && !this.path) {
+ // Create a new mailbox on the server
+ var newMailboxData = Mailbox.$$resource.create('createFolder', this.name);
+ this.$unwrap(newMailboxData);
+ }
+ else {
+ this.id = this.$id();
+ this.isEditable = this.$isEditable();
+ }
}
else {
// The promise will be unwrapped first
@@ -49,28 +57,6 @@
/* Factory registration in Angular module */
.factory('sgMailbox', Mailbox.$factory);
- /**
- * @function $delete
- * @memberof Mailbox.prototype
- * @desc Delete the mailbox from the server
- * @returns a promise of the HTTP operation
- */
- Mailbox.prototype.$delete = function() {
- var _this = this,
- d = Mailbox.$q.defer(),
- promise;
-
- promise = Mailbox.$$resource.remove(this.id);
-
- promise.then(function() {
- _this.$account.$getMailboxes();
- d.resolve(true);
- }, function(data, status) {
- d.reject(data);
- });
- return d.promise;
- };
-
/**
* @memberof Mailbox
* @desc Fetch list of mailboxes of a specific account
@@ -207,6 +193,38 @@
return loaded;
};
+ /**
+ * @function $isEditable
+ * @memberof Mailbox.prototype
+ * @desc Checks if the mailbox is editable based on its type.
+ * @returns true if the mailbox is not a special folder.
+ */
+ Mailbox.prototype.$isEditable = function() {
+ return _.contains(['folder', 'inbox', 'draft', 'sent', 'trash'], this.type);
+ };
+
+ /**
+ * @function $delete
+ * @memberof Mailbox.prototype
+ * @desc Delete the mailbox from the server
+ * @returns a promise of the HTTP operation
+ */
+ Mailbox.prototype.$delete = function() {
+ var _this = this,
+ d = Mailbox.$q.defer(),
+ promise;
+
+ promise = Mailbox.$$resource.remove(this.id);
+
+ promise.then(function() {
+ _this.$account.$getMailboxes({reload: true});
+ d.resolve(true);
+ }, function(data, status) {
+ d.reject(data);
+ });
+ return d.promise;
+ };
+
/**
* @function $deleteMessages
* @memberof Mailbox.prototype
diff --git a/UI/WebServerResources/js/MailerUI.js b/UI/WebServerResources/js/MailerUI.js
index 70b66ad2d..9c4dbba68 100644
--- a/UI/WebServerResources/js/MailerUI.js
+++ b/UI/WebServerResources/js/MailerUI.js
@@ -179,6 +179,15 @@
.controller('MailboxesCtrl', ['$scope', '$rootScope', '$stateParams', '$state', '$timeout', '$modal', 'sgFocus', 'encodeUriFilter', 'sgDialog', 'sgAccount', 'sgMailbox', 'stateAccounts', function($scope, $rootScope, $stateParams, $state, $timeout, $modal, focus, encodeUriFilter, Dialog, Account, Mailbox, stateAccounts) {
$scope.accounts = stateAccounts;
+ $scope.newFolder = function(parentFolder) {
+ Dialog.prompt(l('New folder'),
+ l('Enter the new name of your folder :'))
+ .then(function(name) {
+ if (name && name.length > 0) {
+ parentFolder.$newMailbox(parentFolder.id, name);
+ }
+ });
+ };
$scope.setCurrentFolder = function(account, folder) {
$rootScope.currentFolder = folder;
$state.go('mail.account.mailbox', { accountId: account.id, mailboxId: encodeUriFilter(folder.path) });
diff --git a/UI/WebServerResources/scss/MailerUI.scss b/UI/WebServerResources/scss/MailerUI.scss
index b8bef8e7c..7089b5bae 100644
--- a/UI/WebServerResources/scss/MailerUI.scss
+++ b/UI/WebServerResources/scss/MailerUI.scss
@@ -148,8 +148,6 @@ $column-gutter: 0;
#mailboxesList {
position: absolute;
- overflow: auto;
- overflow-x: hidden;
top: $topbar-height;
bottom: 0;
background-color: #333;
@@ -157,6 +155,36 @@ $column-gutter: 0;
@media #{$medium-up} {
@include grid-column($columns:3);
}
+ .newItemsToolbar {
+ margin-top: rem-calc(6);
+ text-align: center;
+ text-transform: uppercase;
+ }
+ .scrollView {
+ position: absolute;
+ overflow: auto;
+ overflow-x: hidden;
+ top: $topbar-height;
+ bottom: 0;
+ right: 0;
+ left: 0;
+ label {
+ padding-right: 0;
+ button {
+ float: right;
+ background-color: transparent;
+ padding: 0;
+ margin: 0;
+ width: 32px;
+ }
+ }
+ }
+ .buttonsToolbar {
+ border-top: $off-canvas-link-border-bottom;
+ position: absolute;
+ bottom: 0px;
+ width: 100%;
+ }
}
#messagesList, #messageEditor {