diff --git a/src/js/client.js b/src/js/client.js
index 67ff7b402..cb89a4593 100644
--- a/src/js/client.js
+++ b/src/js/client.js
@@ -450,7 +450,7 @@ angular.module('Application').service('Client', ['$http', '$interval', '$timeout
transformRequest: angular.identity
};
- post('/api/v1/settings/cloudron_avatar', fd, config, function (error, data, status) {
+ post('/api/v1/branding/cloudron_avatar', fd, config, function (error, data, status) {
if (error) return callback(error);
if (status !== 202) return callback(new ClientError(status, data));
callback(null);
@@ -462,7 +462,7 @@ angular.module('Application').service('Client', ['$http', '$interval', '$timeout
name: name
};
- post('/api/v1/settings/cloudron_name', data, null, function (error, data, status) {
+ post('/api/v1/branding/cloudron_name', data, null, function (error, data, status) {
if (error) return callback(error);
if (status !== 202) return callback(new ClientError(status, data));
callback(null);
diff --git a/src/views/branding.html b/src/views/branding.html
index cc49954c9..facf93eb0 100644
--- a/src/views/branding.html
+++ b/src/views/branding.html
@@ -1,9 +1,95 @@
+
+
+
+
+
+
+
+
![]()
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
Branding
+
+
About
+
+
+
+
+
+
+ Name
+
+
+ {{ config.cloudronName }}
+
+
+
+
+
+
+
+
Footer
diff --git a/src/views/branding.js b/src/views/branding.js
index a3abf9c7d..153e77582 100644
--- a/src/views/branding.js
+++ b/src/views/branding.js
@@ -37,9 +37,188 @@ angular.module('Application').controller('BrandingController', ['$scope', '$loca
}
};
+ $scope.avatarChange = {
+ busy: false,
+ error: {},
+ avatar: null,
+ availableAvatars: [{
+ file: null,
+ data: null,
+ url: '/img/avatars/logo.png',
+ }, {
+ file: null,
+ data: null,
+ url: '/img/avatars/logo-green.png'
+ }, {
+ file: null,
+ data: null,
+ url: '/img/avatars/logo-orange.png'
+ }, {
+ file: null,
+ data: null,
+ url: '/img/avatars/logo-darkblue.png'
+ }, {
+ file: null,
+ data: null,
+ url: '/img/avatars/logo-red.png'
+ }, {
+ file: null,
+ data: null,
+ url: '/img/avatars/logo-yellow.png'
+ }, {
+ file: null,
+ data: null,
+ url: '/img/avatars/logo-black.png'
+ }],
+
+ getBlobFromImg: function (img, callback) {
+ var size = 256;
+
+ var canvas = document.createElement('canvas');
+ canvas.width = size;
+ canvas.height = size;
+
+ var imageDimensionRatio = img.width / img.height;
+ var canvasDimensionRatio = canvas.width / canvas.height;
+ var renderableHeight, renderableWidth, xStart, yStart;
+
+ if (imageDimensionRatio > canvasDimensionRatio) {
+ renderableHeight = canvas.height;
+ renderableWidth = img.width * (renderableHeight / img.height);
+ xStart = (canvas.width - renderableWidth) / 2;
+ yStart = 0;
+ } else if (imageDimensionRatio < canvasDimensionRatio) {
+ renderableWidth = canvas.width;
+ renderableHeight = img.height * (renderableWidth / img.width);
+ xStart = 0;
+ yStart = (canvas.height - renderableHeight) / 2;
+ } else {
+ renderableHeight = canvas.height;
+ renderableWidth = canvas.width;
+ xStart = 0;
+ yStart = 0;
+ }
+
+ var ctx = canvas.getContext('2d');
+ ctx.clearRect(0, 0, canvas.width, canvas.height);
+ ctx.drawImage(img, xStart, yStart, renderableWidth, renderableHeight);
+
+ canvas.toBlob(callback);
+ },
+
+ doChangeAvatar: function () {
+ $scope.avatarChange.error.avatar = null;
+ $scope.avatarChange.busy = true;
+
+ var img = document.getElementById('previewAvatar');
+ $scope.avatarChange.avatar.file = $scope.avatarChange.getBlobFromImg(img, function (blob) {
+ Client.changeCloudronAvatar(blob, function (error) {
+ if (error) {
+ console.error('Unable to change cloudron avatar.', error);
+ } else {
+ Client.resetAvatar();
+ }
+
+ $('#avatarChangeModal').modal('hide');
+ $scope.avatarChange.avatarChangeReset();
+ });
+ });
+ },
+
+ setPreviewAvatar: function (avatar) {
+ $scope.avatarChange.avatar = avatar;
+ },
+
+ avatarChangeReset: function () {
+ $scope.avatarChange.error.avatar = null;
+ $scope.avatarChange.avatar = null;
+ $scope.avatarChange.busy = false;
+ },
+
+ showChangeAvatar: function () {
+ $scope.avatarChange.avatarChangeReset();
+ $('#avatarChangeModal').modal('show');
+ },
+
+ showCustomAvatarSelector: function () {
+ $('#avatarFileInput').click();
+ }
+ };
+
+ $('#avatarFileInput').get(0).onchange = function (event) {
+ var fr = new FileReader();
+ fr.onload = function () {
+ $scope.$apply(function () {
+ var tmp = {
+ file: event.target.files[0],
+ data: fr.result,
+ url: null
+ };
+
+ $scope.avatarChange.availableAvatars.push(tmp);
+ $scope.avatarChange.setPreviewAvatar(tmp);
+ });
+ };
+ fr.readAsDataURL(event.target.files[0]);
+ };
+
+ $scope.cloudronNameChange = {
+ busy: false,
+ error: {},
+ name: '',
+
+ reset: function () {
+ $scope.cloudronNameChange.busy = false;
+ $scope.cloudronNameChange.error.name = null;
+ $scope.cloudronNameChange.name = '';
+
+ $scope.cloudronNameChangeForm.$setUntouched();
+ $scope.cloudronNameChangeForm.$setPristine();
+ },
+
+ show: function () {
+ $scope.cloudronNameChange.reset();
+ $scope.cloudronNameChange.name = $scope.config.cloudronName;
+ $('#cloudronNameChangeModal').modal('show');
+ },
+
+ submit: function () {
+ $scope.cloudronNameChange.error.name = null;
+ $scope.cloudronNameChange.busy = true;
+
+ Client.changeCloudronName($scope.cloudronNameChange.name, function (error) {
+ $scope.cloudronNameChange.busy = false;
+
+ if (error) {
+ if (error.statusCode === 400) {
+ $scope.cloudronNameChange.error.name = 'Invalid name';
+ $scope.cloudronNameChange.name = '';
+ $('#inputCloudronName').focus();
+ $scope.cloudronNameChangeForm.password.$setPristine();
+ } else {
+ console.error('Unable to change name.', error);
+ return;
+ }
+ }
+
+ $scope.cloudronNameChange.reset();
+ $('#cloudronNameChangeModal').modal('hide');
+
+ Client.refreshConfig();
+ });
+ }
+ };
+
Client.onReady(function () {
$scope.footer.refresh();
});
+ // setup all the dialog focus handling
+ ['cloudronNameChangeModal'].forEach(function (id) {
+ $('#' + id).on('shown.bs.modal', function () {
+ $(this).find("[autofocus]:first").focus();
+ });
+ });
+
$('.modal-backdrop').remove();
}]);
diff --git a/src/views/settings.html b/src/views/settings.html
index b1a169c32..e404b30b1 100644
--- a/src/views/settings.html
+++ b/src/views/settings.html
@@ -38,62 +38,6 @@
-
-
-
-
-
-
-
![]()
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
@@ -142,58 +86,6 @@
Settings
-
-
About
-
-
-
-
-
-
-
-
- | Name |
- {{ config.cloudronName }} |
-
-
- | Version |
- {{ config.version }} |
-
-
- | Provider |
- {{ prettyProviderName(config.provider) }} |
-
-
- | |
-
-
- | Update Error: |
- {{ update.errorMessage }} |
-
-
- |
-
- {{ update.message }}
- |
-
-
- |
-
-
-
- |
-
-
-
-
-
-
Cloudron.io Account
@@ -288,14 +180,13 @@
-
App Updates
+ Updates
-
Configure the update schedule for the apps
-
{{ autoUpdate.error }}
+
Configure the update schedule for apps
@@ -303,25 +194,25 @@
-
-
-
-
+
+
+
{{ update.message }}
+
+
{{ update.errorMessage }}
+
+
+
+
+
+
+
+
+
diff --git a/src/views/settings.js b/src/views/settings.js
index 0e4b4c954..16bbc0164 100644
--- a/src/views/settings.js
+++ b/src/views/settings.js
@@ -24,12 +24,23 @@ angular.module('Application').controller('SettingsController', ['$scope', '$loca
$scope.update = {
error: {}, // this is for the dialog
busy: false,
+ checking: false,
percent: 0,
message: 'Downloading',
errorMessage: '', // this shows inline
taskId: '',
skipBackup: false,
+ checkNow: function () {
+ $scope.update.checking = true;
+
+ Client.checkForUpdates(function (error) {
+ if (error) Client.error(error);
+
+ $scope.update.checking = false;
+ });
+ },
+
show: function () {
$scope.update.error.generic = null;
$scope.update.busy = false;
@@ -117,118 +128,6 @@ angular.module('Application').controller('SettingsController', ['$scope', '$loca
}
};
- $scope.avatarChange = {
- busy: false,
- error: {},
- avatar: null,
- availableAvatars: [{
- file: null,
- data: null,
- url: '/img/avatars/logo.png',
- }, {
- file: null,
- data: null,
- url: '/img/avatars/logo-green.png'
- }, {
- file: null,
- data: null,
- url: '/img/avatars/logo-orange.png'
- }, {
- file: null,
- data: null,
- url: '/img/avatars/logo-darkblue.png'
- }, {
- file: null,
- data: null,
- url: '/img/avatars/logo-red.png'
- }, {
- file: null,
- data: null,
- url: '/img/avatars/logo-yellow.png'
- }, {
- file: null,
- data: null,
- url: '/img/avatars/logo-black.png'
- }],
-
- getBlobFromImg: function (img, callback) {
- var size = 256;
-
- var canvas = document.createElement('canvas');
- canvas.width = size;
- canvas.height = size;
-
- var imageDimensionRatio = img.width / img.height;
- var canvasDimensionRatio = canvas.width / canvas.height;
- var renderableHeight, renderableWidth, xStart, yStart;
-
- if (imageDimensionRatio > canvasDimensionRatio) {
- renderableHeight = canvas.height;
- renderableWidth = img.width * (renderableHeight / img.height);
- xStart = (canvas.width - renderableWidth) / 2;
- yStart = 0;
- } else if (imageDimensionRatio < canvasDimensionRatio) {
- renderableWidth = canvas.width;
- renderableHeight = img.height * (renderableWidth / img.width);
- xStart = 0;
- yStart = (canvas.height - renderableHeight) / 2;
- } else {
- renderableHeight = canvas.height;
- renderableWidth = canvas.width;
- xStart = 0;
- yStart = 0;
- }
-
- var ctx = canvas.getContext('2d');
- ctx.clearRect(0, 0, canvas.width, canvas.height);
- ctx.drawImage(img, xStart, yStart, renderableWidth, renderableHeight);
-
- canvas.toBlob(callback);
- },
-
- doChangeAvatar: function () {
- $scope.avatarChange.error.avatar = null;
- $scope.avatarChange.busy = true;
-
- var img = document.getElementById('previewAvatar');
- $scope.avatarChange.avatar.file = $scope.avatarChange.getBlobFromImg(img, function (blob) {
- Client.changeCloudronAvatar(blob, function (error) {
- if (error) {
- console.error('Unable to change cloudron avatar.', error);
- } else {
- Client.resetAvatar();
- }
-
- $('#avatarChangeModal').modal('hide');
- $scope.avatarChange.avatarChangeReset();
- });
- });
- },
-
- setPreviewAvatar: function (avatar) {
- $scope.avatarChange.avatar = avatar;
- },
-
- avatarChangeReset: function () {
- $scope.avatarChange.error.avatar = null;
- $scope.avatarChange.avatar = null;
- $scope.avatarChange.busy = false;
- },
-
- showChangeAvatar: function () {
- $scope.avatarChange.avatarChangeReset();
- $('#avatarChangeModal').modal('show');
- },
-
- showCustomAvatarSelector: function () {
- $('#avatarFileInput').click();
- }
- };
-
- $scope.s3like = function (provider) {
- return provider === 's3' || provider === 'minio' || provider === 's3-v4-compat' || provider === 'exoscale-sos' || provider === 'digitalocean-spaces';
- };
-
$scope.timeZone = {
busy: false,
success: false,
@@ -252,38 +151,25 @@ angular.module('Application').controller('SettingsController', ['$scope', '$loca
$scope.timeZone.success = true;
});
}
- }
+ };
$scope.autoUpdate = {
busy: false,
- success: false,
- error: '',
pattern: '',
currentPattern: '',
- checkNow: function () {
- $scope.autoUpdate.busy = true;
-
- Client.checkForUpdates(function (error) {
- if (error) $scope.autoUpdate.error = error.message;
-
- $scope.autoUpdate.busy = false;
- });
- },
-
submit: function () {
if ($scope.autoUpdate.pattern === $scope.autoUpdate.currentPattern) return;
- $scope.autoUpdate.error = '';
$scope.autoUpdate.busy = true;
- $scope.autoUpdate.success = false;
Client.setAppAutoupdatePattern($scope.autoUpdate.pattern, function (error) {
- if (error) $scope.autoUpdate.error = error.message;
+ if (error) Client.error(error);
else $scope.autoUpdate.currentPattern = $scope.autoUpdate.pattern;
- $scope.autoUpdate.busy = false;
- $scope.autoUpdate.success = true;
+ $timeout(function () {
+ $scope.autoUpdate.busy = false;
+ }, 3000);
});
}
};
@@ -334,23 +220,6 @@ angular.module('Application').controller('SettingsController', ['$scope', '$loca
Client.openSubscriptionSetup($scope.subscription);
};
- $('#avatarFileInput').get(0).onchange = function (event) {
- var fr = new FileReader();
- fr.onload = function () {
- $scope.$apply(function () {
- var tmp = {
- file: event.target.files[0],
- data: fr.result,
- url: null
- };
-
- $scope.avatarChange.availableAvatars.push(tmp);
- $scope.avatarChange.setPreviewAvatar(tmp);
- });
- };
- fr.readAsDataURL(event.target.files[0]);
- };
-
$scope.registryConfig = {
busy: false,
error: null,
@@ -403,53 +272,6 @@ angular.module('Application').controller('SettingsController', ['$scope', '$loca
}
};
- $scope.cloudronNameChange = {
- busy: false,
- error: {},
- name: '',
-
- reset: function () {
- $scope.cloudronNameChange.busy = false;
- $scope.cloudronNameChange.error.name = null;
- $scope.cloudronNameChange.name = '';
-
- $scope.cloudronNameChangeForm.$setUntouched();
- $scope.cloudronNameChangeForm.$setPristine();
- },
-
- show: function () {
- $scope.cloudronNameChange.reset();
- $scope.cloudronNameChange.name = $scope.config.cloudronName;
- $('#cloudronNameChangeModal').modal('show');
- },
-
- submit: function () {
- $scope.cloudronNameChange.error.name = null;
- $scope.cloudronNameChange.busy = true;
-
- Client.changeCloudronName($scope.cloudronNameChange.name, function (error) {
- $scope.cloudronNameChange.busy = false;
-
- if (error) {
- if (error.statusCode === 400) {
- $scope.cloudronNameChange.error.name = 'Invalid name';
- $scope.cloudronNameChange.name = '';
- $('#inputCloudronName').focus();
- $scope.cloudronNameChangeForm.password.$setPristine();
- } else {
- console.error('Unable to change name.', error);
- return;
- }
- }
-
- $scope.cloudronNameChange.reset();
- $('#cloudronNameChangeModal').modal('hide');
-
- Client.refreshConfig();
- });
- }
- };
-
Client.onReady(function () {
getAutoupdatePattern();
getRegistryConfig();
@@ -461,7 +283,7 @@ angular.module('Application').controller('SettingsController', ['$scope', '$loca
});
// setup all the dialog focus handling
- ['planChangeModal', 'appstoreLoginModal', 'cloudronNameChangeModal'].forEach(function (id) {
+ ['planChangeModal', 'appstoreLoginModal'].forEach(function (id) {
$('#' + id).on('shown.bs.modal', function () {
$(this).find("[autofocus]:first").focus();
});