Einstellungen angefangen

This commit is contained in:
silas
2018-09-19 12:22:42 +02:00
parent d7494e3622
commit f729bd487a
18 changed files with 712 additions and 272 deletions

View File

@@ -2850,6 +2850,21 @@ class MyDb {
});
}
removeAll(objectStore){
return new Promise((resolve) => {
this.openStore(objectStore, "readwrite", (store) => {
let req = store.clear();
req.onerror = (e) => {
throw {
"type":"indexed-db-index-error",
"event": e
}
};
req.onsuccess = resolve;
});
})
}
upgrade(db) {
};
}
@@ -3621,6 +3636,66 @@ class SettingsManager {
SettingsManager._instance = null;
class LocalStorageSettingsFragment extends Fragment {
onFirstStart() {
let res = super.onFirstStart();
let settings = this.findBy(".setting", true);
const settingsManager = SettingsManager.getInstance();
for (let i = 0; i < settings.length; i++) {
let setting = settings[i];
const name = setting.name;
let value = settingsManager.getSetting(name);
let isCheckable = false;
if (setting instanceof HTMLInputElement && (setting.type === 'checkbox' || setting.type === 'radio')) {
isCheckable = true;
}
if (!settingsManager.hasSetting(name) && Helper.isNotNull(settings[i]["dataset"]["default"])) {
value = setting["dataset"]["default"];
if (Helper.isNotNull(setting["dataset"]["defaultTranslateable"])) {
setting["dataset"]["translation"] = "";
setting["dataset"]["translationValue"] = value;
value = Translator.translate(value);
}
}
if (Helper.isNotNull(value)) {
if (isCheckable) {
setting.checked = (value === setting.value);
}
else {
setting.value = value;
}
if (value !== "") {
setting.classList.add("notEmpty");
}
}
setting.addEventListener("change", function () {
let value = this.value;
if (isCheckable) {
if (this.checked)
{
settingsManager.setSetting(name, value);
}
else
{
settingsManager.setSetting(name, null);
}
}
else {
settingsManager.setSetting(name, value);
}
delete setting["dataset"]["translationValue"];
delete setting["dataset"]["translation"];
});
}
return res;
}
}
class SmartColumn{
constructor(name, label, translateable){
this._name = name;
@@ -3889,7 +3964,7 @@ class ListHelper {
class SettingsSite extends AbstractSite {
constructor(siteManager) {
super(siteManager, 'core/html/settings.html', "settings");
super(siteManager, SettingsSite.template, "settings");
for (let k in SettingsSite.settingsFragments) {
this.addSettingsFragment(k, new SettingsSite.settingsFragments[k](this));
}
@@ -3958,139 +4033,33 @@ class SettingsSite extends AbstractSite {
static setAddSettingsSite(addLink) {
SettingsSite.shouldAddSettingsSite = addLink;
}
static setTemplate(template) {
SettingsSite.template = template;
}
}
SettingsSite.template = 'core/html/settings.html';
SettingsSite.settingsFragments = {};
SettingsSite.shouldAddSettingsSite = true;
SettingsSite.settingsAction = null;
SettingsSite.shouldAddSettingsAction = true;
InitPromise.addPromise(function (app) {
if (SettingsSite.shouldAddSettingsSite) {
app.addDeepLink("settings", SettingsSite);
let settingsAction = new MenuAction("settings", function () {
app.startSite(SettingsSite);
}, MenuAction.SHOW_FOR_LARGE, 10000);
settingsAction.setIcon("img/settings.png");
app.addDefaultAction(settingsAction);
}
});
class ScaleHelper {
scaleTo(scale, fontElement, container, ignoreHeight, ignoreWidth, margin, fontWeight, addListener) {
margin = Helper.nonNull(margin, 10);
ignoreHeight = Helper.nonNull(ignoreHeight, false);
ignoreWidth = Helper.nonNull(ignoreWidth, false);
fontWeight = Helper.nonNull(fontWeight, fontElement.innerHTML.length);
addListener = Helper.nonNull(addListener, true);
let hasNoTransitionClass = container.classList.contains("no-transition");
container.classList.add("no-transition");
let currentFontSize = 1;
let diff = 0;
let widthDiff = 0;
let heightDiff = 0;
let containerWidth = 0;
let containerHeight = 0;
do {
currentFontSize += diff / (fontWeight + 1);
fontElement.style.fontSize = currentFontSize + 'px';
let containerStyle = window.getComputedStyle(container);
containerWidth = containerStyle.getPropertyValue("width").replace('px', '');
containerHeight = containerStyle.getPropertyValue("height").replace('px', '');
widthDiff = containerWidth - fontElement.offsetWidth;
heightDiff = containerHeight - fontElement.offsetHeight;
let newDiff = (ignoreWidth ? heightDiff : (ignoreHeight ? widthDiff : Math.min(widthDiff, heightDiff)));
if (newDiff === diff) {
break;
}
diff = newDiff;
} while ((widthDiff > (1 - scale) * containerWidth || ignoreWidth) && (heightDiff > (1 - scale) * containerHeight || ignoreHeight));
fontElement.style.fontSize = (currentFontSize - margin) + 'px';
if (!hasNoTransitionClass) {
container.classList.remove("no-transition");
if (Helper.isNull(SettingsSite.settingsAction)) {
let settingsAction = new MenuAction("settings", function () {
app.startSite(SettingsSite);
}, MenuAction.SHOW_FOR_LARGE, 10000);
settingsAction.setIcon("img/settings.png");
SettingsSite.settingsAction = settingsAction;
}
let self = this;
let listener = function () {
setTimeout(() => {
self.scaleTo(scale, fontElement, container, ignoreHeight, ignoreWidth, margin, fontWeight, false);
}, 255);
};
if (addListener) {
window.addEventListener("resize", listener);
}
return listener;
}
scaleToFull(fontElement, container, ignoreHeight, ignoreWidth, margin, fontWeight) {
return this.scaleTo(1, fontElement, container, ignoreHeight, ignoreWidth, margin, fontWeight);
}
}
class Code {
constructor(args) {
if (typeof args === "string") {
args = {
"code": args
};
}
this.args = args;
this.isCacheable = false;
}
setIsCacheable(isCacheable) {
this.isCacheable = isCacheable;
}
getIsCacheable() {
return this.isCacheable;
}
activate() {
return DataManager.send("c/code", this.args);
}
}
class CodeSite extends AbstractSite {
constructor(siteManager) {
super(siteManager, "core/html/load.html", "code");
}
onConstruct(args) {
super.onConstruct(args);
console.log(args);
let resPromise = Promise.resolve();
if (Helper.isNotNull(args["code"])) {
let code = args["code"];
let isCachable = Helper.nonNull(args["cachable"], false);
let codeObject = new Code(code);
codeObject.setIsCacheable(isCachable);
let self = this;
resPromise = codeObject.activate().then(function (res) {
if (!res["success"]) {
FlashMessenger.addMessage(FlashMessenger.MESSAGE_TYPE_SUCCESS, Translator.translate(res["errors"][0]));
}
else {
FlashMessenger.addMessage(FlashMessenger.MESSAGE_TYPE_SUCCESS, Translator.translate(Helper.nonNull(res["result"]["successMessage"], "code-activated")));
}
self.finish();
});
if (SettingsSite.shouldAddSettingsAction) {
app.addDefaultAction(SettingsSite.settingsAction);
}
}
}
InitPromise.addPromise(function (app) {
app.addDeepLink("code", CodeSite);
});
class UserManager {
@@ -4499,34 +4468,51 @@ InitPromise.addPromise(function(app){
app.addDeepLink("forgotPassword", ForgotPasswordSite);
});
class LoginSite extends UserSite{
class LoginSite extends UserSite {
constructor(siteManager) {
super(siteManager, 'userManagement/html/login.html', "login", "offline");
}
onFirstStart() {
let self = this;
(new LoginForm(document.getElementById("login-form"), "u/login", "post")).onSubmit(function(res){
(new LoginForm(document.getElementById("login-form"), "u/login", "post")).onSubmit(function (res) {
UserManager.setData(res);
self.startStartsite();
FlashMessenger.addMessage(FlashMessenger.MESSAGE_TYPE_SUCCESS, Translator.translate("login-success"));
self.finish();
});
this.findBy("#forgot-password-link").addEventListener("click", function(){
this.findBy("#forgot-password-link").addEventListener("click", function () {
self.startSite(ForgotPasswordSite);
self.finish();
});
}
}
InitPromise.addPromise(function(app){
LoginSite.loginAction = null;
LoginSite.logoutAction = null;
LoginSite.addLoginAction = true;
LoginSite.addLogoutAction = true;
InitPromise.addPromise(function (app) {
app.addDeepLink("login", LoginSite);
app.addDefaultAction(new UserAction('login', function(){
app.startSite(LoginSite);
}, Menu.SHOW_NEVER, 1100, "offline"));
app.addDefaultAction(new UserAction('logout', function(){
UserManager.logOut();
}, Menu.SHOW_NEVER, 1100, "online"));
if (Helper.isNull(LoginSite.loginAction)) {
LoginSite.loginAction = new UserAction('login', function () {
app.startSite(LoginSite);
}, Menu.SHOW_NEVER, 1100, "offline");
}
if (Helper.isNull(LoginSite.logoutAction)) {
LoginSite.logoutAction = new UserAction('logout', function () {
UserManager.logOut();
}, Menu.SHOW_NEVER, 1100, "online");
}
if (LoginSite.addLoginAction){
app.addDefaultAction(LoginSite.loginAction);
}
if (LoginSite.addLogoutAction){
app.addDefaultAction(LoginSite.logoutAction);
}
});
class RegistrationSite extends UserSite {
@@ -4535,17 +4521,26 @@ class RegistrationSite extends UserSite {
}
onFirstStart() {
(new RegistrationForm(document.getElementById("registration-form"), "u/registration", "post")).onSubmit(function(res){
(new RegistrationForm(document.getElementById("registration-form"), "u/registration", "post")).onSubmit(function (res) {
FlashMessenger.addMessage(FlashMessenger.MESSAGE_TYPE_SUCCESS, Translator.translate("registration-success"));
});
}
}
RegistrationSite.action = null;
RegistrationSite.addAction = true;
InitPromise.addPromise(function (app) {
app.addDeepLink("registration", RegistrationSite);
app.addDefaultAction(new UserAction('registration', function(){
app.startSite(RegistrationSite);
}, null, 1100, "offline"));
if (Helper.isNull(RegistrationSite.action)) {
RegistrationSite.action = new UserAction('registration', function () {
app.startSite(RegistrationSite);
}, null, 1100, "offline");
}
if (RegistrationSite.addAction) {
app.addDefaultAction(RegistrationSite.action);
}
});
class SetNewPasswordSite extends UserSite {
@@ -4574,15 +4569,193 @@ InitPromise.addPromise(function(app){
app.addDeepLink("newPassword", SetNewPasswordSite);
});
let basePath = "/pwa/wordRotator/public/";
if (window.location.pathname.endsWith("publicTest/"))
{
basePath = "/pwa/wordRotator/publicTest/";
class ScaleHelper {
scaleTo(scale, fontElement, container, ignoreHeight, ignoreWidth, margin, fontWeight, addListener) {
margin = Helper.nonNull(margin, 10);
ignoreHeight = Helper.nonNull(ignoreHeight, false);
ignoreWidth = Helper.nonNull(ignoreWidth, false);
fontWeight = Helper.nonNull(fontWeight, fontElement.innerHTML.length);
addListener = Helper.nonNull(addListener, true);
let hasNoTransitionClass = container.classList.contains("no-transition");
container.classList.add("no-transition");
let currentFontSize = 1;
let diff = 0;
let widthDiff = 0;
let heightDiff = 0;
let containerWidth = 0;
let containerHeight = 0;
do {
currentFontSize += diff / (fontWeight + 1);
fontElement.style.fontSize = currentFontSize + 'px';
let containerStyle = window.getComputedStyle(container);
containerWidth = containerStyle.getPropertyValue("width").replace('px', '');
containerHeight = containerStyle.getPropertyValue("height").replace('px', '');
widthDiff = containerWidth - fontElement.offsetWidth;
heightDiff = containerHeight - fontElement.offsetHeight;
let newDiff = (ignoreWidth ? heightDiff : (ignoreHeight ? widthDiff : Math.min(widthDiff, heightDiff)));
if (newDiff === diff) {
break;
}
diff = newDiff;
} while ((widthDiff > (1 - scale) * containerWidth || ignoreWidth) && (heightDiff > (1 - scale) * containerHeight || ignoreHeight));
fontElement.style.fontSize = (currentFontSize - margin) + 'px';
if (!hasNoTransitionClass) {
container.classList.remove("no-transition");
}
let self = this;
let listener = function () {
setTimeout(() => {
self.scaleTo(scale, fontElement, container, ignoreHeight, ignoreWidth, margin, fontWeight, false);
}, 255);
};
if (addListener) {
window.addEventListener("resize", listener);
}
return listener;
}
scaleToFull(fontElement, container, ignoreHeight, ignoreWidth, margin, fontWeight) {
return this.scaleTo(1, fontElement, container, ignoreHeight, ignoreWidth, margin, fontWeight);
}
}
SystemSettings.setBasePath(basePath);
Translator.supportedLanguages = ["de", "en"];
Translator.markTranslations = false;
class Code {
constructor(args) {
if (typeof args === "string") {
args = {
"code": args
};
}
this.args = args;
this.isCacheable = false;
}
setIsCacheable(isCacheable) {
this.isCacheable = isCacheable;
}
getIsCacheable() {
return this.isCacheable;
}
activate() {
return DataManager.send("c/code", this.args);
}
}
class CodeSite extends AbstractSite {
constructor(siteManager) {
super(siteManager, "core/html/load.html", "code");
}
onConstruct(args) {
super.onConstruct(args);
console.log(args);
let resPromise = Promise.resolve();
if (Helper.isNotNull(args["code"])) {
let code = args["code"];
let isCachable = Helper.nonNull(args["cachable"], false);
let codeObject = new Code(code);
codeObject.setIsCacheable(isCachable);
let self = this;
resPromise = codeObject.activate().then(function (res) {
if (!res["success"]) {
FlashMessenger.addMessage(FlashMessenger.MESSAGE_TYPE_SUCCESS, Translator.translate(res["errors"][0]));
}
else {
FlashMessenger.addMessage(FlashMessenger.MESSAGE_TYPE_SUCCESS, Translator.translate(Helper.nonNull(res["result"]["successMessage"], "code-activated")));
}
self.finish();
});
}
}
}
InitPromise.addPromise(function (app) {
app.addDeepLink("code", CodeSite);
});
class WordRotatorDb extends MyDb {
static getInstance() {
if (Helper.isNull(WordRotatorDb.instance)) {
WordRotatorDb.instance = new WordRotatorDb();
}
return WordRotatorDb.instance;
}
constructor() {
super("wordRotator", 3);
}
upgrade(db, oldVersion, newVersion, e) {
if (Helper.isNull(oldVersion) || oldVersion < 1 && newVersion >= 1) {
let levelObjectStore = db.createObjectStore(WordRotatorDb.OBJECT_STORE.LEVEL, {"keyPath": "id"});
}
if (Helper.isNull(oldVersion) || oldVersion < 2 && newVersion >= 2) {
let levelObjectStore = e.target.transaction.objectStore(WordRotatorDb.OBJECT_STORE.LEVEL);
levelObjectStore.createIndex("played", ["deleted", "played", "difficulty", "id"], {"unique": false});
}
if (Helper.isNull(oldVersion) || oldVersion < 3 && newVersion >= 3) {
let levelObjectStore = e.target.transaction.objectStore(WordRotatorDb.OBJECT_STORE.LEVEL);
levelObjectStore.createIndex("difficulty", "difficulty", {"unique": false});
}
};
async saveManyLevels(levels) {
return this.saveMany(levels, WordRotatorDb.OBJECT_STORE.LEVEL);
}
async loadLevel(levelId) {
return this.load(levelId, WordRotatorDb.OBJECT_STORE.LEVEL);
}
async loadNextLevel(rendererTypes) {
const levels = await this.loadMany("difficulty", IDBKeyRange.lowerBound(0), WordRotatorDb.OBJECT_STORE.LEVEL);
let wrongLevels = [];
let newLevels = [];
let difficulty = -1;
for (let i = 0, n = levels.length; i < n; i++) {
if ((difficulty < 0 || difficulty === levels[i]["difficulty"]) && !levels[i]["deleted"] && !levels[i]["played"] && rendererTypes.indexOf(levels[i]["rendererType"]) !== -1) {
newLevels.push(levels[i]);
difficulty = levels[i]["difficulty"];
}
else if (levels[i]["difficulty"] !== 0 && !levels[i]["deleted"] && !levels[i]["played"] ) {
wrongLevels.push(levels[i]);
}
}
if (newLevels.length === 0) {
return null;
}
return newLevels[Math.round(Math.random() * newLevels.length) % newLevels.length];
}
async saveLevelPlayed(levelId) {
const level = await this.loadLevel(levelId);
level.played = true;
return await this.saveObj(level, WordRotatorDb.OBJECT_STORE.LEVEL);
}
}
WordRotatorDb.OBJECT_STORE = {
LEVEL: "level",
};
WordRotatorDb.instance = null;
class Segment{
constructor(element){
@@ -5299,88 +5472,18 @@ LevelHelper.types = {
160: FourWordsLevel12,
};
class WordRotatorDb extends MyDb {
static getInstance() {
if (Helper.isNull(WordRotatorDb.instance)) {
WordRotatorDb.instance = new WordRotatorDb();
}
return WordRotatorDb.instance;
}
constructor() {
super("wordRotator", 3);
}
upgrade(db, oldVersion, newVersion, e) {
if (Helper.isNull(oldVersion) || oldVersion < 1 && newVersion >= 1) {
let levelObjectStore = db.createObjectStore(WordRotatorDb.OBJECT_STORE.LEVEL, {"keyPath": "id"});
}
if (Helper.isNull(oldVersion) || oldVersion < 2 && newVersion >= 2) {
let levelObjectStore = e.target.transaction.objectStore(WordRotatorDb.OBJECT_STORE.LEVEL);
levelObjectStore.createIndex("played", ["deleted", "played", "difficulty", "id"], {"unique": false});
}
if (Helper.isNull(oldVersion) || oldVersion < 3 && newVersion >= 3) {
let levelObjectStore = e.target.transaction.objectStore(WordRotatorDb.OBJECT_STORE.LEVEL);
levelObjectStore.createIndex("difficulty", "difficulty", {"unique": false});
}
};
async saveManyLevels(levels) {
return this.saveMany(levels, WordRotatorDb.OBJECT_STORE.LEVEL);
}
async loadLevel(levelId) {
return this.load(levelId, WordRotatorDb.OBJECT_STORE.LEVEL);
}
async loadNextLevel(rendererTypes) {
const levels = await this.loadMany("difficulty", IDBKeyRange.lowerBound(0), WordRotatorDb.OBJECT_STORE.LEVEL);
let wrongLevels = [];
let newLevels = [];
let difficulty = -1;
for (let i = 0, n = levels.length; i < n; i++) {
if ((difficulty < 0 || difficulty === levels[i]["difficulty"]) && !levels[i]["deleted"] && !levels[i]["played"] && rendererTypes.indexOf(levels[i]["rendererType"]) !== -1) {
newLevels.push(levels[i]);
difficulty = levels[i]["difficulty"];
}
else if (levels[i]["difficulty"] !== 0 && !levels[i]["deleted"] && !levels[i]["played"] ) {
wrongLevels.push(levels[i]);
}
}
if (newLevels.length === 0) {
return null;
}
return newLevels[Math.round(Math.random() * newLevels.length) % newLevels.length];
}
async saveLevelPlayed(levelId) {
const level = await this.loadLevel(levelId);
level.played = true;
return await this.saveObj(level, WordRotatorDb.OBJECT_STORE.LEVEL);
}
}
WordRotatorDb.OBJECT_STORE = {
LEVEL: "level",
};
WordRotatorDb.instance = null;
class WordRotatorBaseSite extends AbstractSite {
createActionBarMenu(menu) {
menu = super.createActionBarMenu(menu);
let actions = menu.actions;
for (let i = 0; i < actions.length; i++) {
if (actions[i].title === "login" || actions[i].title === "registration"){
actions[i].setVisible(false);
}
}
return menu;
}
// createActionBarMenu(menu) {
// menu = super.createActionBarMenu(menu);
// // menu.addAction(SettingsSite.settingsAction.copy());
// // let actions = menu.actions;
// // for (let i = 0; i < actions.length; i++) {
// // if (actions[i].title === "login" || actions[i].title === "registration"){
// // actions[i].setVisible(false);
// // }
// // }
// return menu;
// }
}
class EndSite extends WordRotatorBaseSite{
@@ -5392,6 +5495,7 @@ class EndSite extends WordRotatorBaseSite{
class LevelSite extends WordRotatorBaseSite {
constructor(siteManager) {
super(siteManager, "html/application/level.html");
this.levelScaler = ()=>{};
}
onConstruct(args) {
@@ -5468,7 +5572,7 @@ class LevelSite extends WordRotatorBaseSite {
let levelSegment = this.findBy("#level");
levelSegment.removeAllChildren().appendChild(level.getRootSegment().getElement());
let scaleHelper = new ScaleHelper();
scaleHelper.scaleToFull(levelSegment, levelSegment.parentElement, false, false, 2, level.words[0].length * 2);
this.levelScaler = scaleHelper.scaleToFull(levelSegment, levelSegment.parentElement, false, false, 2, level.words[0].length * 2);
this.level = level;
return;
@@ -5505,7 +5609,7 @@ class LevelSite extends WordRotatorBaseSite {
let levelSegment = this.findBy("#level");
levelSegment.removeAllChildren().appendChild(level.getRootSegment().getElement());
let scaleHelper = new ScaleHelper();
scaleHelper.scaleToFull(levelSegment, levelSegment.parentElement, false, false, 2, level.words[0].length * 2);
this.levelScaler = scaleHelper.scaleToFull(levelSegment, levelSegment.parentElement, false, false, 2, level.words[0].length * 2);
this.level = level;
this.levelCounterAction.innerText = this.levelCounter;
@@ -5518,8 +5622,10 @@ class LevelSite extends WordRotatorBaseSite {
onStart(args) {
let res = super.onStart(args);
this.levelCounterAction.innerText = this.levelCounter;
this.levelCounterActionContainer.classList.add("visible");
this.levelScaler();
return res;
}
@@ -5601,6 +5707,60 @@ class SynchronizeSite extends WordRotatorBaseSite {
}
}
class WordRotatorSettingFragment extends LocalStorageSettingsFragment {
constructor(site) {
super(site, "html/application/fragment/settings.html");
}
onFirstStart() {
let themeTemplate = this.findBy("#theme-radio-template");
delete themeTemplate["id"];
let themeTemplateContainer = themeTemplate.parentNode;
themeTemplateContainer.removeAllChildren();
for (let i = 0; i < ThemeManager.themes.length; i++) {
let themeElem = Helper.cloneNode(themeTemplate);
let theme = ThemeManager.themes[i];
themeElem.appendChild(Translator.makePersistentTranslation(theme._name));
let inputElem = themeElem.querySelector("input");
inputElem.value = theme._className;
inputElem.addEventListener("change", function() {
if (this.checked){
ThemeManager.changeCurrentTheme(theme);
}
});
themeTemplateContainer.appendChild(themeElem);
}
SettingsManager.getInstance().setSetting("theme", ThemeManager.currentTheme._name);
this.findBy("#reset-levels").addEventListener("click", () => {
localStorage.removeItem("currentLevel");
localStorage.removeItem("date-last-sync");
localStorage.removeItem("levelCounter");
WordRotatorDb.getInstance().removeAll(WordRotatorDb.OBJECT_STORE.LEVEL);
});
return super.onFirstStart();
}
}
InitPromise.addPromise(function () {
SettingsSite.addSettingsFragment("settings", WordRotatorSettingFragment);
});
let basePath = "/pwa/wordRotator/public/";
if (window.location.pathname.endsWith("publicTest/"))
{
basePath = "/pwa/wordRotator/publicTest/";
}
SystemSettings.setBasePath(basePath);
Translator.supportedLanguages = ["de", "en"];
Translator.markTranslations = false;
applyPolyfills();
ThemeManager.addTheme(new Theme('red', ''));
@@ -5627,7 +5787,15 @@ window["app"]["refreshCurrentSite"] = app.refreshCurrentSite;
window["Translator"] = Translator;
window["Translator"]["setLanguage"] = Translator.setLanguage;
SettingsSite.setTemplate("html/application/setting-template.html");
// SettingsSite.shouldAddSettingsAction = false;
RegistrationSite.addAction = false;
LoginSite.addLoginAction = false;
InitPromise.resolve(app).then(function(){
SettingsSite.settingsAction.showFor = MenuAction.SHOW_ALWAYS;
app.start(SynchronizeSite);
Translator.setLanguage("de");
});