theme plugins

This commit is contained in:
antelle 2017-02-21 22:05:18 +01:00
parent 0c155c1e6a
commit e459b8ef7b
15 changed files with 137 additions and 27 deletions

View File

@ -21,6 +21,16 @@ const SettingsManager = {
'zh-CN': '汉语'
},
allThemes: {
fb: 'setGenThemeFb',
db: 'setGenThemeDb',
sd: 'setGenThemeSd',
sl: 'setGenThemeSl',
wh: 'setGenThemeWh',
te: 'setGenThemeTe',
hc: 'setGenThemeHc'
},
customLocales: {
},

View File

@ -452,6 +452,7 @@
"setPlInstallBtnProgress": "Installing",
"setPlUninstallBtn": "Uninstall",
"setPlLocaleBtn": "Switch to this language",
"setPlThemeBtn": "Switch to this theme",
"setPlJs": "code",
"setPlCss": "styles",
"setPlLoc": "language",

View File

@ -7,6 +7,7 @@ const Logger = require('../util/logger');
const SettingsManager = require('../comp/settings-manager');
const IoCache = require('../storage/io-cache');
const AppSettingsModel = require('../models/app-settings-model');
const BaseLocale = require('../locales/base.json');
const commonLogger = new Logger('plugin');
const io = new IoCache({
@ -171,7 +172,7 @@ const Plugin = Backbone.Model.extend({
const manifest = this.get('manifest');
const promises = [];
if (this.resources.css) {
promises.push(this.applyCss(manifest.name, this.resources.css));
promises.push(this.applyCss(manifest.name, this.resources.css, manifest.theme));
}
if (this.resources.js) {
promises.push(this.applyJs(manifest.name, this.resources.js));
@ -229,10 +230,15 @@ const Plugin = Backbone.Model.extend({
});
},
applyCss(name, data) {
applyCss(name, data, theme) {
return Promise.resolve().then(() => {
const text = kdbxweb.ByteUtils.bytesToString(data);
this.createElementInHead('style', 'plugin-css-' + name, 'text/css', text);
if (theme) {
const locKey = this.getThemeLocaleKey(theme.name);
SettingsManager.allThemes[theme.name] = locKey;
BaseLocale[locKey] = theme.title;
}
this.logger.debug('Plugin style installed');
});
},
@ -300,6 +306,18 @@ const Plugin = Backbone.Model.extend({
}
},
getThemeLocaleKey(name) {
return `setGenThemeCustom_${name}`;
},
removeTheme(theme) {
delete SettingsManager.allThemes[theme.name];
if (AppSettingsModel.instance.get('theme') === theme.name) {
AppSettingsModel.instance.set('theme', 'fb');
}
delete BaseLocale[this.getThemeLocaleKey(theme.name)];
},
uninstall() {
const manifest = this.get('manifest');
this.logger.info('Uninstalling plugin with resources', Object.keys(manifest.resources).join(', '));
@ -320,6 +338,9 @@ const Plugin = Backbone.Model.extend({
if (manifest.resources.loc) {
this.removeLoc(this.get('manifest').locale);
}
if (manifest.theme) {
this.removeTheme(manifest.theme);
}
return this.deleteResources().then(() => {
this.set('status', 'inactive');
this.logger.info('Uninstall complete', this.logger.ts(ts));

View File

@ -47,16 +47,6 @@ const SettingsGeneralView = Backbone.View.extend({
views: null,
allThemes: {
fb: 'setGenThemeFb',
db: 'setGenThemeDb',
sd: 'setGenThemeSd',
sl: 'setGenThemeSl',
wh: 'setGenThemeWh',
te: 'setGenThemeTe',
hc: 'setGenThemeHc'
},
initialize: function() {
this.views = {};
this.listenTo(UpdateModel.instance, 'change:status', this.render, this);
@ -69,7 +59,7 @@ const SettingsGeneralView = Backbone.View.extend({
const updateManual = UpdateModel.instance.get('updateManual');
const storageProviders = this.getStorageProviders();
this.renderTemplate({
themes: _.mapObject(this.allThemes, theme => Locale[theme]),
themes: _.mapObject(SettingsManager.allThemes, theme => Locale[theme]),
activeTheme: AppSettingsModel.instance.get('theme'),
locales: SettingsManager.allLocales,
activeLocale: SettingsManager.activeLocale,

View File

@ -11,7 +11,8 @@ const SettingsPluginsView = Backbone.View.extend({
events: {
'click .settings_plugins-install-btn': 'installClick',
'click .settings_plugins-uninstall-btn': 'uninstallClick',
'click .settings_plugins-use-locale-btn': 'useLocaleClick'
'click .settings_plugins-use-locale-btn': 'useLocaleClick',
'click .settings_plugins-use-theme-btn': 'useThemeClick'
},
initialize() {
@ -70,6 +71,11 @@ const SettingsPluginsView = Backbone.View.extend({
useLocaleClick(e) {
const locale = $(e.target).data('locale');
AppSettingsModel.instance.set('locale', locale);
},
useThemeClick(e) {
const theme = $(e.target).data('theme');
AppSettingsModel.instance.set('theme', theme);
}
});

View File

@ -19,9 +19,12 @@
</div>
<div class="settings__plugins-plugin-buttons">
<button class="settings_plugins-uninstall-btn btn-silent" data-plugin="{{plugin.id}}">{{res 'setPlUninstallBtn'}}</button>
{{#if plugin.manifest.resources.loc}}
{{#if plugin.manifest.locale}}
<button class="settings_plugins-use-locale-btn btn-silent" data-locale="{{plugin.manifest.locale.name}}">{{res 'setPlLocaleBtn'}}</button>
{{/if}}
{{#if plugin.manifest.theme}}
<button class="settings_plugins-use-theme-btn btn-silent" data-theme="{{plugin.manifest.theme.name}}">{{res 'setPlThemeBtn'}}</button>
{{/if}}
</div>
</div>
{{/each}}

View File

@ -11,7 +11,7 @@
"licence": "MIT",
"url": "https://keeweb.info",
"resources": {
"js": "AXUK3TetuHvs0wZU0BW4fHHKhxO+GB6ji2YxuAS8UF64hsF4FQXA9dxg4KSDkUyUSvs8DMucmUNSevOw3UOLGP86jvBmiaGrS0M+/EXD4LUEXMtDVhn2mZmlCaX34sA9AyPVbZuP1eI+6o6vcTyS/ugH8T38i6pLAR3Xzl6iC0Z16WkyX0+3zmQGhMEJwAxTQNVfe+RjUtvsXoBIeay/tIohCRgpkXKoB1bOVT/cETdVThaFHeEEPAweGcX0/b3QQ6AU+oqJGB3RoEJJGWFc/rv40OMAlvw310QHtlv9eE+jMLcewQiF/x1LtBOb/a8whp5vhn3HR6jlUhhXOHbwhg=="
"js": "GkZuvYFiRx6UZk1hvJjInhmunMxyFVuI3u4UpCB6rjho1hgfR9CtebwU6dyTYARfivzZAsD4kVxx8TnbsU+Wu4PuS0cvE9e7+C3I8yGwoTgpk8GOCnORsaQBXMRvi93Snb/B8TXwT7wpSVFraiNGsuf5VKGZqN7YB0DyZHmeAtZf8KXMeg5XrSiwUtTokdozFQKSAx9pyKpIBvEQ7c03wQfZu9L6xSYJsLTjNje2UbEH6TS7yVt5F1lqaitaHRUMAYGbVgZkAK75jboUitWKebXaJUJbF8VxWJJDp7cmYkq6Zc6Qy1uTElzAu8sR/jTxHsJ0UpgaUeXxqpMZjLEjYQ=="
},
"publicKey": "MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA1QB+yQofkqIHbHFVAtWhjEFjaxvNekyQx/aK7nEpZzqM8ReoVWbJGVA+7z7MhymwZanbL8uAUrSpNTp5eFWltDksxqHqmXT4UcFU+4reLjYfgwjIaA3c9Q+2JA1Iowqbv3NDcDKm6Ug+dROr04VDCfYE4WRYgGdTYHDbJs5svxUgQ25uc0KKUWAvhYbSKsw43AwmbPbKkHdfZHiS5ZST99HVEJWxn3Kd2zLY9Kk70nu9MzypMLDqxUqjKgdeRCIyZeAYzB75miH3B5vMKhFcdmA8+D6WU2N+6gzKsY5BfqF729uFKSTo4JUKQ5fMU0lKSDHG4qGrkgnURfAUuj9YMQIDAQAB"
}

View File

@ -5,7 +5,7 @@
*/
const Storage = require('storage/index');
const Locale = require('locales/base');
const BaseLocale = require('locales/base');
const StorageBase = require('storage/storage-base');
const FailStorage = StorageBase.extend({
@ -43,11 +43,11 @@ const FailStorage = StorageBase.extend({
}
});
Locale.failStorage = 'Fail';
BaseLocale.failStorage = 'Fail';
Storage.failStorage = new FailStorage();
module.exports.uninstall = function() {
delete Locale.failStorage;
delete BaseLocale.failStorage;
delete Storage.failStorage;
};

View File

@ -2,7 +2,7 @@
"version": "0.0.1",
"manifestVersion": "0.1.0",
"name": "psychodelic",
"description": "Crazy animations for KeeWeb",
"description": "Crazy animations",
"author": {
"name": "antelle",
"email": "antelle.net@gmail.com",
@ -15,4 +15,4 @@
"css": "P3qX1ccKLeHI/75sWC/46O/Qs8cq6UFyoW2qPYRn05q8dtAfXr7YKXEndt1BqSqaa+ZanaA6TDmb5FJ/GKQpG1KfuXy+ug92uwSvp6QUd7/hj++OR6RRY/bsL4hA9J2BwMB3jYc58lCPcK2jcu3HCYX5T+I1tFLmqOAKbTUGQxl+a4lc0w/zAq9sEFIvm7Nj66HhF7TMqVoPt6pUBz7oWdTYuKJ3rz46rLd9kzTeaeG6WxGorFc6Sk5tlvy+o9e5S2T0lHJwCHw24rMeOSgwV8rA/RXXnKowVc9Qbb3KwVh2TlKUWRtUuygIIgSsp4GmzT+w8+5hXke7iXDTGczp1Q=="
},
"publicKey": "MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA1QB+yQofkqIHbHFVAtWhjEFjaxvNekyQx/aK7nEpZzqM8ReoVWbJGVA+7z7MhymwZanbL8uAUrSpNTp5eFWltDksxqHqmXT4UcFU+4reLjYfgwjIaA3c9Q+2JA1Iowqbv3NDcDKm6Ug+dROr04VDCfYE4WRYgGdTYHDbJs5svxUgQ25uc0KKUWAvhYbSKsw43AwmbPbKkHdfZHiS5ZST99HVEJWxn3Kd2zLY9Kk70nu9MzypMLDqxUqjKgdeRCIyZeAYzB75miH3B5vMKhFcdmA8+D6WU2N+6gzKsY5BfqF729uFKSTo4JUKQ5fMU0lKSDHG4qGrkgnURfAUuj9YMQIDAQAB"
}
}

View File

@ -0,0 +1,3 @@
.DS_Store
*.log
*.pem

View File

@ -0,0 +1,21 @@
{
"version": "0.0.1",
"manifestVersion": "0.1.0",
"name": "rainbow-theme",
"description": "Rainbow theme",
"author": {
"name": "antelle",
"email": "antelle.net@gmail.com",
"url": "http://antelle.net"
},
"licence": "MIT",
"url": "https://keeweb.info",
"resources": {
"css": "VMBsTo36lliqTzhith4BqWOYW4n4nW5jt+Pj9LqnCJzUChZPtb2eQex1Al3YNC9gCxej1Dw0VNDr55HzBv/q/k4F1/zszaR1twtfRP2fiwGkxN5Cvso0IFjB1PUjr3VeMAnNMtkkkqAz9hHLaFkdIwVZf98wZ2WEIok+lAM2g9vSklZ34aikhvDbRojNZ0Waqovo41IA4Z3xhb0KQkud8WaH3oNxulitsiRdgIbigj43Gd5XlJYE+/JpAcnG033mC0W0XmXXrjEiD0CH8ZoEX/3vo7LVH+AfUuhJWl0zj49+VSjBe9X6+XiPIb2ZUEJEuSaD3vwg9GNSkjF49lB8gA=="
},
"publicKey": "MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA1QB+yQofkqIHbHFVAtWhjEFjaxvNekyQx/aK7nEpZzqM8ReoVWbJGVA+7z7MhymwZanbL8uAUrSpNTp5eFWltDksxqHqmXT4UcFU+4reLjYfgwjIaA3c9Q+2JA1Iowqbv3NDcDKm6Ug+dROr04VDCfYE4WRYgGdTYHDbJs5svxUgQ25uc0KKUWAvhYbSKsw43AwmbPbKkHdfZHiS5ZST99HVEJWxn3Kd2zLY9Kk70nu9MzypMLDqxUqjKgdeRCIyZeAYzB75miH3B5vMKhFcdmA8+D6WU2N+6gzKsY5BfqF729uFKSTo4JUKQ5fMU0lKSDHG4qGrkgnURfAUuj9YMQIDAQAB",
"theme": {
"name": "rainbow",
"title": "Rainbow"
}
}

View File

@ -0,0 +1,31 @@
.th-rainbow * {
animation: rainbow 5s linear 0s infinite;
}
.th-rainbow button {
animation: bgrainbow 5s linear 0s infinite;
border: 1px solid;
}
.th-rainbow input {
border: 1px solid;
}
*:nth-child(5n+1) { animation-delay: -1s; }
*:nth-child(5n+2) { animation-delay: -2s; }
*:nth-child(5n+3) { animation-delay: -3s; }
*:nth-child(5n+4) { animation-delay: -4s; }
*:nth-child(5n+5) { animation-delay: -5s; }
@keyframes rainbow {
0% { color: lightseagreen; }
20% { color: darkviolet; }
40% { color: gold; }
60% { color: hotpink; }
80% { color: palegoldenrod; }
100% { color: lightseagreen; }
}
@keyframes bgrainbow {
0% { color: darkviolet; background-color: lightseagreen; }
20% { color: gold; background-color: darkviolet; }
40% { color: hotpink; background-color: gold; }
60% { color: palegoldenrod; background-color: hotpink; }
80% { color: lightseagreen; background-color: palegoldenrod; }
100% { color: darkviolet; background-color: lightseagreen; }
}

View File

@ -2,7 +2,7 @@
"version": "0.0.1",
"manifestVersion": "0.1.0",
"name": "square-language",
"description": "KeeWeb language which replaces everything with squares",
"description": "Language which replaces everything with squares",
"author": {
"name": "antelle",
"email": "antelle.net@gmail.com",

View File

@ -133,7 +133,8 @@ function gatherPluginData(callback) {
'1: js only\n ' +
'2: js + css\n ' +
'3: css only\n ' +
'4: locale\n' +
'4: locale\n ' +
'5: theme\n' +
'Your plugin type is',
callback: res => {
const placeholder = `<resource signature will be here, please run 'kw-plugin-control sign ${data.name}'>`;
@ -149,6 +150,11 @@ function gatherPluginData(callback) {
break;
case '4':
data.resources = { loc: placeholder };
data.locale = {};
break;
case '5':
data.resources = { css: placeholder };
data.theme = {};
break;
default:
console.error('Please enter number from 1 to 4');
@ -158,18 +164,18 @@ function gatherPluginData(callback) {
}
}, {
text: 'Locale code (format: xx or xx-XX)',
if: () => data.resources.loc,
if: () => data.locale,
callback: loc => {
if (!/^[a-z]{2}(-[A-Z]{2})?$/.test(loc) || loc === 'en') {
console.error('Invalid locale');
return true;
}
data.locale = { name: loc };
data.locale.name = loc;
next();
}
}, {
text: 'Locale name (human-readable)',
if: () => data.resources.loc,
if: () => data.locale,
callback: loc => {
if (!loc || loc.toLowerCase() === 'english' || loc.toLowerCase() === 'default') {
console.error('Invalid locale');
@ -178,6 +184,24 @@ function gatherPluginData(callback) {
data.locale.title = loc;
next();
}
}, {
text: 'Theme class name (lowercase letters and dashes only)',
if: () => data.theme,
callback: loc => {
if (!/^[a-z\-]+$/.test(loc)) {
console.error('Invalid theme');
return true;
}
data.theme.name = loc;
next();
}
}, {
text: 'Theme name (human-readable)',
if: () => data.theme,
callback: loc => {
data.theme.title = loc;
next();
}
}];
next();

View File

@ -1,6 +1,6 @@
{
"name": "keeweb-plugin",
"version": "0.1.0",
"version": "0.1.1",
"description": "KeeWeb plugin utils",
"main": "keeweb-plugin.js",
"scripts": {