Files
mindflux/src/main/resources/static/js/theme.js
T
AliceDarkest 548a90f15e
mindflux-ci / build (push) Successful in 22s
Accessibility in Kopfzeilen integrieren und Kategorien angleichen
2026-07-12 23:51:46 +02:00

108 lines
4.7 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
/* Mindflux Theme – Dark/Light-Umschaltung, zentral.
Im <head> einbinden (ohne defer), dann setzt es das Theme vor dem Rendern (kein Flash).
Jeder Button mit Klasse .mf-theme wird automatisch zum Umschalter. */
(function () {
var KEY = 'mf-theme';
function read() { try { return localStorage.getItem(KEY) || 'dark'; } catch (e) { return 'dark'; } }
function apply(mode) { document.documentElement.setAttribute('data-theme', mode); }
apply(read()); // früh -> kein Aufblitzen
// Globale, rein clientseitige Komfortfunktionen. FluxTimer bleibt auf öffentlichen
// Seiten inaktiv, läuft bei aktivierter Einstellung aber über Seitennavigationen weiter.
if (!document.querySelector('link[data-fluxtimer]')) {
var timerCss = document.createElement('link');
timerCss.rel = 'stylesheet';
timerCss.href = '/css/fluxtimer.css?v=3';
timerCss.setAttribute('data-fluxtimer', '');
document.head.appendChild(timerCss);
}
if (!document.querySelector('script[data-fluxtimer]')) {
var timerScript = document.createElement('script');
timerScript.src = '/js/fluxtimer.js?v=1';
timerScript.defer = true;
timerScript.setAttribute('data-fluxtimer', '');
document.head.appendChild(timerScript);
}
if (!document.querySelector('link[data-accessibility]')) {
var accessibilityCss = document.createElement('link');
accessibilityCss.rel = 'stylesheet';
accessibilityCss.href = '/css/accessibility.css?v=3';
accessibilityCss.setAttribute('data-accessibility', '');
document.head.appendChild(accessibilityCss);
var accessibilityPlacementCss = document.createElement('link');
accessibilityPlacementCss.rel = 'stylesheet';
accessibilityPlacementCss.href = '/css/accessibility-placement.css?v=1';
accessibilityPlacementCss.setAttribute('data-accessibility', '');
document.head.appendChild(accessibilityPlacementCss);
}
if (!document.querySelector('script[data-accessibility]')) {
var accessibilityScript = document.createElement('script');
accessibilityScript.src = '/js/accessibility.js?v=4';
accessibilityScript.defer = true;
accessibilityScript.setAttribute('data-accessibility', '');
document.head.appendChild(accessibilityScript);
}
var SUN = '<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2"><circle cx="12" cy="12" r="4"/><path d="M12 2v2M12 20v2M4.9 4.9l1.4 1.4M17.7 17.7l1.4 1.4M2 12h2M20 12h2M4.9 19.1l1.4-1.4M17.7 6.3l1.4-1.4"/></svg>';
var MOON = '<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2"><path d="M21 12.8A9 9 0 1 1 11.2 3a7 7 0 0 0 9.8 9.8z"/></svg>';
function paint() {
var dark = document.documentElement.getAttribute('data-theme') === 'dark';
document.querySelectorAll('.mf-theme').forEach(function (b) { b.innerHTML = dark ? SUN : MOON; });
}
function toggle() {
var next = document.documentElement.getAttribute('data-theme') === 'dark' ? 'light' : 'dark';
apply(next);
try { localStorage.setItem(KEY, next); } catch (e) {}
paint();
}
function set(mode) {
var next = mode === 'light' ? 'light' : 'dark';
apply(next);
try { localStorage.setItem(KEY, next); } catch (e) {}
paint();
}
window.MindfluxTheme = {
toggle: toggle,
apply: apply,
set: set,
current: function () { return document.documentElement.getAttribute('data-theme'); }
};
// Mobile-Nav: Off-Canvas-Drawer für Seiten mit App-Sidebar (.mf-shell)
function initMobileNav() {
var sidebar = document.querySelector('.mf-sidebar');
if (!sidebar || document.querySelector('.mf-burger')) return;
var burger = document.createElement('button');
burger.className = 'mf-burger';
burger.setAttribute('aria-label', 'Menü öffnen');
burger.innerHTML = '<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2"><path d="M3 6h18M3 12h18M3 18h18"/></svg>';
var backdrop = document.createElement('div');
backdrop.className = 'mf-nav-backdrop';
function close() { document.body.classList.remove('mf-nav-open'); }
function toggleNav() { document.body.classList.toggle('mf-nav-open'); }
burger.addEventListener('click', toggleNav);
backdrop.addEventListener('click', close);
sidebar.querySelectorAll('a').forEach(function (a) { a.addEventListener('click', close); });
window.addEventListener('keydown', function (e) { if (e.key === 'Escape') close(); });
document.body.appendChild(backdrop);
document.body.appendChild(burger);
}
document.addEventListener('DOMContentLoaded', function () {
document.querySelectorAll('.mf-theme').forEach(function (b) {
b.setAttribute('role', 'button');
b.setAttribute('aria-label', 'Theme umschalten');
b.addEventListener('click', toggle);
});
paint();
initMobileNav();
});
})();