mirror of
https://github.com/bunkerity/bunkerized-nginx
synced 2023-12-13 21:30:18 +01:00
Update tsparticles in the UI + remove unused static files
This commit is contained in:
parent
685cb9809d
commit
1c71572f44
|
@ -10,5 +10,9 @@ CONTRIBUTING.md
|
|||
LICENSE.md
|
||||
README.md
|
||||
SECURITY.md
|
||||
src/ui/static
|
||||
examples/*
|
||||
tsparticles.bundle.min.js
|
||||
flatpickr.*
|
||||
src/ui/static/js/editor/*
|
||||
src/ui/templates/*
|
||||
datepicker-foundation.css
|
||||
examples/*
|
||||
|
|
|
@ -2590,15 +2590,34 @@ h6 {
|
|||
}
|
||||
|
||||
.transition {
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
transition-property:
|
||||
color,
|
||||
background-color,
|
||||
border-color,
|
||||
text-decoration-color,
|
||||
fill,
|
||||
stroke,
|
||||
opacity,
|
||||
box-shadow,
|
||||
transform,
|
||||
filter,
|
||||
-webkit-backdrop-filter;
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
backdrop-filter;
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
backdrop-filter, -webkit-backdrop-filter;
|
||||
transition-property:
|
||||
color,
|
||||
background-color,
|
||||
border-color,
|
||||
text-decoration-color,
|
||||
fill,
|
||||
stroke,
|
||||
opacity,
|
||||
box-shadow,
|
||||
transform,
|
||||
filter,
|
||||
backdrop-filter,
|
||||
-webkit-backdrop-filter;
|
||||
transition-timing-function: cubic-bezier(0.25, 0.1, 0.25, 1);
|
||||
transition-duration: 150ms;
|
||||
}
|
||||
|
@ -3310,15 +3329,34 @@ h6 {
|
|||
font-size: 0.875rem;
|
||||
line-height: 1.5rem;
|
||||
font-weight: 700;
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
transition-property:
|
||||
color,
|
||||
background-color,
|
||||
border-color,
|
||||
text-decoration-color,
|
||||
fill,
|
||||
stroke,
|
||||
opacity,
|
||||
box-shadow,
|
||||
transform,
|
||||
filter,
|
||||
-webkit-backdrop-filter;
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
backdrop-filter;
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
backdrop-filter, -webkit-backdrop-filter;
|
||||
transition-property:
|
||||
color,
|
||||
background-color,
|
||||
border-color,
|
||||
text-decoration-color,
|
||||
fill,
|
||||
stroke,
|
||||
opacity,
|
||||
box-shadow,
|
||||
transform,
|
||||
filter,
|
||||
backdrop-filter,
|
||||
-webkit-backdrop-filter;
|
||||
transition-timing-function: cubic-bezier(0.25, 0.1, 0.25, 1);
|
||||
transition-duration: 300ms;
|
||||
transition-timing-function: cubic-bezier(0.42, 0, 0.58, 1);
|
||||
|
@ -3343,15 +3381,34 @@ h6 {
|
|||
--tw-bg-opacity: 1;
|
||||
background-color: rgb(94 114 228 / var(--tw-bg-opacity));
|
||||
padding: 0.75rem;
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
transition-property:
|
||||
color,
|
||||
background-color,
|
||||
border-color,
|
||||
text-decoration-color,
|
||||
fill,
|
||||
stroke,
|
||||
opacity,
|
||||
box-shadow,
|
||||
transform,
|
||||
filter,
|
||||
-webkit-backdrop-filter;
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
backdrop-filter;
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
backdrop-filter, -webkit-backdrop-filter;
|
||||
transition-property:
|
||||
color,
|
||||
background-color,
|
||||
border-color,
|
||||
text-decoration-color,
|
||||
fill,
|
||||
stroke,
|
||||
opacity,
|
||||
box-shadow,
|
||||
transform,
|
||||
filter,
|
||||
backdrop-filter,
|
||||
-webkit-backdrop-filter;
|
||||
transition-timing-function: cubic-bezier(0.25, 0.1, 0.25, 1);
|
||||
transition-duration: 150ms;
|
||||
}
|
||||
|
@ -3370,15 +3427,34 @@ h6 {
|
|||
font-weight: 700;
|
||||
--tw-text-opacity: 1;
|
||||
color: rgb(255 255 255 / var(--tw-text-opacity));
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
transition-property:
|
||||
color,
|
||||
background-color,
|
||||
border-color,
|
||||
text-decoration-color,
|
||||
fill,
|
||||
stroke,
|
||||
opacity,
|
||||
box-shadow,
|
||||
transform,
|
||||
filter,
|
||||
-webkit-backdrop-filter;
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
backdrop-filter;
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
backdrop-filter, -webkit-backdrop-filter;
|
||||
transition-property:
|
||||
color,
|
||||
background-color,
|
||||
border-color,
|
||||
text-decoration-color,
|
||||
fill,
|
||||
stroke,
|
||||
opacity,
|
||||
box-shadow,
|
||||
transform,
|
||||
filter,
|
||||
backdrop-filter,
|
||||
-webkit-backdrop-filter;
|
||||
transition-timing-function: cubic-bezier(0.25, 0.1, 0.25, 1);
|
||||
transition-duration: 300ms;
|
||||
transition-timing-function: cubic-bezier(0.42, 0, 0.58, 1);
|
||||
|
@ -3539,15 +3615,34 @@ h6 {
|
|||
padding-right: 0.5rem;
|
||||
--tw-text-opacity: 1;
|
||||
color: rgb(8 85 119 / var(--tw-text-opacity));
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
transition-property:
|
||||
color,
|
||||
background-color,
|
||||
border-color,
|
||||
text-decoration-color,
|
||||
fill,
|
||||
stroke,
|
||||
opacity,
|
||||
box-shadow,
|
||||
transform,
|
||||
filter,
|
||||
-webkit-backdrop-filter;
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
backdrop-filter;
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
backdrop-filter, -webkit-backdrop-filter;
|
||||
transition-property:
|
||||
color,
|
||||
background-color,
|
||||
border-color,
|
||||
text-decoration-color,
|
||||
fill,
|
||||
stroke,
|
||||
opacity,
|
||||
box-shadow,
|
||||
transform,
|
||||
filter,
|
||||
backdrop-filter,
|
||||
-webkit-backdrop-filter;
|
||||
transition-timing-function: cubic-bezier(0.25, 0.1, 0.25, 1);
|
||||
transition-duration: 300ms;
|
||||
transition-timing-function: cubic-bezier(0.42, 0, 0.58, 1);
|
||||
|
@ -3569,15 +3664,34 @@ h6 {
|
|||
--tw-bg-opacity: 1;
|
||||
background-color: rgb(94 114 228 / var(--tw-bg-opacity));
|
||||
padding: 0.75rem;
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
transition-property:
|
||||
color,
|
||||
background-color,
|
||||
border-color,
|
||||
text-decoration-color,
|
||||
fill,
|
||||
stroke,
|
||||
opacity,
|
||||
box-shadow,
|
||||
transform,
|
||||
filter,
|
||||
-webkit-backdrop-filter;
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
backdrop-filter;
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
backdrop-filter, -webkit-backdrop-filter;
|
||||
transition-property:
|
||||
color,
|
||||
background-color,
|
||||
border-color,
|
||||
text-decoration-color,
|
||||
fill,
|
||||
stroke,
|
||||
opacity,
|
||||
box-shadow,
|
||||
transform,
|
||||
filter,
|
||||
backdrop-filter,
|
||||
-webkit-backdrop-filter;
|
||||
transition-timing-function: cubic-bezier(0.25, 0.1, 0.25, 1);
|
||||
transition-duration: 150ms;
|
||||
}
|
||||
|
@ -3666,15 +3780,34 @@ h6 {
|
|||
.settings-tabs-mobile-btn-text {
|
||||
--tw-text-opacity: 1;
|
||||
color: rgb(8 85 119 / var(--tw-text-opacity));
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
transition-property:
|
||||
color,
|
||||
background-color,
|
||||
border-color,
|
||||
text-decoration-color,
|
||||
fill,
|
||||
stroke,
|
||||
opacity,
|
||||
box-shadow,
|
||||
transform,
|
||||
filter,
|
||||
-webkit-backdrop-filter;
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
backdrop-filter;
|
||||
transition-property: color, background-color, border-color,
|
||||
text-decoration-color, fill, stroke, opacity, box-shadow, transform, filter,
|
||||
backdrop-filter, -webkit-backdrop-filter;
|
||||
transition-property:
|
||||
color,
|
||||
background-color,
|
||||
border-color,
|
||||
text-decoration-color,
|
||||
fill,
|
||||
stroke,
|
||||
opacity,
|
||||
box-shadow,
|
||||
transform,
|
||||
filter,
|
||||
backdrop-filter,
|
||||
-webkit-backdrop-filter;
|
||||
transition-timing-function: cubic-bezier(0.25, 0.1, 0.25, 1);
|
||||
transition-duration: 300ms;
|
||||
transition-timing-function: cubic-bezier(0.42, 0, 0.58, 1);
|
||||
|
|
|
@ -1 +0,0 @@
|
|||
.datepicker{display:none}.datepicker.active{display:block}.datepicker-dropdown{left:0;padding-top:4px;position:absolute;top:0;z-index:10}.datepicker-dropdown.datepicker-orient-top{padding-bottom:4px;padding-top:0}.datepicker-picker{background-color:#fefefe;border-radius:0;display:inline-block}.datepicker-dropdown .datepicker-picker{box-shadow:0 0 0 1px #cacaca}.datepicker-picker span{-webkit-touch-callout:none;border:0;border-radius:0;cursor:default;display:block;flex:1;text-align:center;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none}.datepicker-main{padding:2px}.datepicker-footer{background-color:#e6e6e6;box-shadow:inset 0 1px 1px hsla(0,0%,4%,.1)}.datepicker-controls,.datepicker-grid,.datepicker-view,.datepicker-view .days-of-week{display:flex}.datepicker-grid{flex-wrap:wrap}.datepicker-view .days .datepicker-cell,.datepicker-view .dow{flex-basis:14.2857142857%}.datepicker-view.datepicker-grid .datepicker-cell{flex-basis:25%}.datepicker-cell,.datepicker-view .week{height:2.25rem;line-height:2.25rem}.datepicker-title{background-color:#e6e6e6;box-shadow:inset 0 -1px 1px hsla(0,0%,4%,.1);font-weight:700;padding:.375rem .75rem;text-align:center}.datepicker-header .datepicker-controls{padding:2px 2px 0}.datepicker-controls .button{background-color:#fefefe;color:#0a0a0a;margin:0}.datepicker-controls .button:focus,.datepicker-controls .button:hover{background-color:#d8d8d8}.datepicker-controls .button:focus[disabled],.datepicker-controls .button:hover[disabled]{background-color:#fefefe;color:#0a0a0a;opacity:.25}.datepicker-header .datepicker-controls .button{border-color:transparent;font-weight:700}.datepicker-footer .datepicker-controls .button{border-radius:0;font-size:.75rem;margin:calc(.375rem - 1px) .375rem;width:100%}.datepicker-controls .view-switch{flex:auto}.datepicker-controls .next-btn,.datepicker-controls .prev-btn{padding-left:.375rem;padding-right:.375rem;width:2.25rem}.datepicker-controls .next-btn.disabled,.datepicker-controls .prev-btn.disabled{visibility:hidden}.datepicker-view .dow{font-size:.875rem;font-weight:700;height:1.5rem;line-height:1.5rem}.datepicker-view .week{color:#8a8a8a;font-size:.75rem;width:2.25rem}@media (max-width:22.5rem){.datepicker-view .week{width:1.96875rem}}.datepicker-grid{width:15.75rem}@media (max-width:22.5rem){.calendar-weeks+.days .datepicker-grid{width:13.78125rem}}.datepicker-cell:not(.disabled):hover{background-color:#f8f8f8;cursor:pointer}.datepicker-cell.focused:not(.selected){background-color:#f1f1f1}.datepicker-cell.selected,.datepicker-cell.selected:hover{background-color:#1779ba;color:#fefefe;font-weight:semibold}.datepicker-cell.disabled{color:#e6e6e6}.datepicker-cell.next:not(.disabled),.datepicker-cell.prev:not(.disabled){color:#cacaca}.datepicker-cell.next.selected,.datepicker-cell.prev.selected{color:#e5e5e5}.datepicker-cell.highlighted:not(.selected):not(.range):not(.today){background-color:#f7f7f7;border-radius:0}.datepicker-cell.highlighted:not(.selected):not(.range):not(.today).focused,.datepicker-cell.highlighted:not(.selected):not(.range):not(.today):not(.disabled):hover{background-color:#f1f1f1}.datepicker-cell.today:not(.selected){background-color:#d7ecfa}.datepicker-cell.today:not(.selected):not(.disabled){color:#8a8a8a}.datepicker-cell.today.focused:not(.selected){background-color:#cbe7f9}.datepicker-cell.range-end:not(.selected),.datepicker-cell.range-start:not(.selected){background-color:#767676;color:#fefefe}.datepicker-cell.range-end.focused:not(.selected),.datepicker-cell.range-start.focused:not(.selected){background-color:#707070}.datepicker-cell.range-end,.datepicker-cell.range-start{border-radius:0 0 0 0}.datepicker-cell.range{background-color:#e6e6e6;border-radius:0}.datepicker-cell.range:not(.disabled):not(.focused):not(.today):hover{background-color:#e0e0e0}.datepicker-cell.range.disabled{color:#cdcdcd}.datepicker-cell.range.focused{background-color:#d9d9d9}.datepicker-cell.range.today{background-color:#b3dbf6}.datepicker-view.datepicker-grid .datepicker-cell{height:4.5rem;line-height:4.5rem}.datepicker-input.in-edit{border-color:#a4a4a4}.datepicker-input.in-edit:active,.datepicker-input.in-edit:focus{box-shadow:0 0 .25em .25em hsla(0,0%,64%,.2)}
|
File diff suppressed because it is too large
Load diff
|
@ -16,7 +16,9 @@ class Download {
|
|||
this.listContainer.addEventListener("click", (e) => {
|
||||
try {
|
||||
if (
|
||||
e.target.closest("button").hasAttribute(`data-${this.prefix}-download`)
|
||||
e.target
|
||||
.closest("button")
|
||||
.hasAttribute(`data-${this.prefix}-download`)
|
||||
) {
|
||||
const btnEl = e.target.closest("button");
|
||||
const jobName = btnEl.getAttribute("data-cache-download");
|
||||
|
@ -31,8 +33,8 @@ class Download {
|
|||
window.open(
|
||||
`${location.href.replace(
|
||||
"cache",
|
||||
"jobs"
|
||||
)}/download?job_name=${jobName}&file_name=${fileName}`
|
||||
"jobs",
|
||||
)}/download?job_name=${jobName}&file_name=${fileName}`,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,11 +1,11 @@
|
|||
import {
|
||||
FolderNav,
|
||||
FolderEditor,
|
||||
FolderModal,
|
||||
FolderDropdown,
|
||||
} from "./utils/file.manager.js";
|
||||
|
||||
const setModal = new FolderModal("configs");
|
||||
const setEditor = new FolderEditor();
|
||||
const setFolderNav = new FolderNav("configs");
|
||||
const setDropdown = new FolderDropdown("configs");
|
||||
import {
|
||||
FolderNav,
|
||||
FolderEditor,
|
||||
FolderModal,
|
||||
FolderDropdown,
|
||||
} from "./utils/file.manager.js";
|
||||
|
||||
const setModal = new FolderModal("configs");
|
||||
const setEditor = new FolderEditor();
|
||||
const setFolderNav = new FolderNav("configs");
|
||||
const setDropdown = new FolderDropdown("configs");
|
||||
|
|
|
@ -1,317 +1,317 @@
|
|||
import { Checkbox, Select, Password, DisabledPop } from "./utils/form.js";
|
||||
|
||||
class Menu {
|
||||
constructor() {
|
||||
this.sidebarEl = document.querySelector("[data-sidebar-menu]");
|
||||
this.toggleBtn = document.querySelector("[data-sidebar-menu-toggle]");
|
||||
this.closeBtn = document.querySelector("[data-sidebar-menu-close]");
|
||||
|
||||
this.toggleBtn.addEventListener("click", this.toggle.bind(this));
|
||||
this.closeBtn.addEventListener("click", this.close.bind(this));
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
window.addEventListener("click", (e) => {
|
||||
try {
|
||||
if (
|
||||
e.target.closest("aside").hasAttribute("data-sidebar-menu") &&
|
||||
e.target.closest("button").getAttribute("role") === "tab"
|
||||
) {
|
||||
this.close();
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
|
||||
toggle() {
|
||||
this.sidebarEl.classList.toggle("-translate-x-full");
|
||||
}
|
||||
|
||||
close() {
|
||||
this.sidebarEl.classList.add("-translate-x-full");
|
||||
}
|
||||
}
|
||||
|
||||
class News {
|
||||
constructor() {
|
||||
this.BASE_URL = "https://www.bunkerweb.io/";
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
window.addEventListener("load", async () => {
|
||||
try {
|
||||
const res = await fetch("https://www.bunkerweb.io/api/posts/0/2", {
|
||||
headers: {
|
||||
method: "GET",
|
||||
},
|
||||
});
|
||||
return await this.render(res);
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
|
||||
render(lastNews) {
|
||||
const newsContainer = document.querySelector("[data-news-container]");
|
||||
//remove default message
|
||||
newsContainer.textContent = "";
|
||||
//render last news
|
||||
lastNews.forEach((news) => {
|
||||
//get info
|
||||
const slug = news.slug;
|
||||
const img = news.photo.url;
|
||||
const excerpt = news.excerpt;
|
||||
const tags = news.tags;
|
||||
const date = news.date;
|
||||
const lastUpdate = news.lastUpdate;
|
||||
//create html card from infos
|
||||
const cardHTML = this.template(
|
||||
slug,
|
||||
img,
|
||||
excerpt,
|
||||
tags,
|
||||
date,
|
||||
lastUpdate
|
||||
);
|
||||
//add to DOM
|
||||
document
|
||||
.querySelector("[data-news-container]")
|
||||
.insertAdjacentHTML("afterbegin", cardHTML);
|
||||
});
|
||||
}
|
||||
|
||||
template(slug, img, excerpt, tags, date, lastUpdate) {
|
||||
//loop on tags to get list
|
||||
let tagList = "";
|
||||
tags.forEach((tag) => {
|
||||
tagList += ` <a
|
||||
href="${this.BASE_URL}/blog/tag/${tag.slug}"
|
||||
class="my-0 mr-1 rounded bg-secondary hover:brightness-90 hover:-translate-y-0.4 text-white py-1 px-2 text-sm"
|
||||
>
|
||||
${tag.name}
|
||||
</a>`;
|
||||
});
|
||||
//create card
|
||||
const card = `
|
||||
<div
|
||||
class="min-h-[400px] w-full col-span-12 transition hover:-translate-y-2 bg-gray-100 dark:bg-slate-900 rounded px-6 py-4 m-2 flex flex-col justify-between"
|
||||
>
|
||||
<div>
|
||||
<img role="link"
|
||||
onclick="window.location.href='${this.BASE_URL}/blog/post/${slug}'"
|
||||
class="cursor-pointer rounded w-full h-40 m-0 object-cover"
|
||||
src="${img}"
|
||||
alt="image"
|
||||
/>
|
||||
<h3 role="link"
|
||||
onclick="window.location.href='${this.BASE_URL}/blog/post/${slug}'"
|
||||
class="cursor-pointer mt-3 mb-1 text-3xl dark:text-white tracking-wide">{{ post['title'] }}</h3>
|
||||
</div>
|
||||
<div>
|
||||
<div role="link"
|
||||
onclick="window.location.href='${this.BASE_URL}/blog/post/${slug}'"
|
||||
class="cursor-pointer min-h-[130px] mb-3 text-lg dark:text-gray-300 text-gray-600 pt-3">
|
||||
${excerpt}
|
||||
</div>
|
||||
<div class="min-h-[75px] mt-2 flex flex-wrap justify-start items-end align-bottom">
|
||||
${tagList}
|
||||
</div>
|
||||
|
||||
<div class="mt-2 flex flex-col justify-start items-start">
|
||||
<span class="text-xs dark:text-gray-300 text-gray-600"
|
||||
>Posted on : ${date}</span
|
||||
>
|
||||
{% if post["updatedAt"] %}
|
||||
<span class="text-xs dark:text-gray-300 text-gray-600"
|
||||
>Last update : ${lastUpdate}</span
|
||||
>
|
||||
{%endif%}
|
||||
</div>
|
||||
</div>
|
||||
</div> `;
|
||||
return card;
|
||||
}
|
||||
}
|
||||
|
||||
class Sidebar {
|
||||
constructor(elAtt, btnOpenAtt, btnCloseAtt) {
|
||||
this.sidebarEl = document.querySelector(elAtt);
|
||||
this.openBtn = document.querySelector(btnOpenAtt);
|
||||
this.closeBtn = document.querySelector(btnCloseAtt);
|
||||
this.openBtn.addEventListener("click", this.open.bind(this));
|
||||
this.closeBtn.addEventListener("click", this.close.bind(this));
|
||||
}
|
||||
|
||||
open() {
|
||||
this.sidebarEl.classList.add("translate-x-0");
|
||||
this.sidebarEl.classList.remove("translate-x-90");
|
||||
}
|
||||
|
||||
close() {
|
||||
this.sidebarEl.classList.add("translate-x-90");
|
||||
this.sidebarEl.classList.remove("translate-x-0");
|
||||
}
|
||||
}
|
||||
|
||||
class darkMode {
|
||||
constructor() {
|
||||
this.htmlEl = document.querySelector("html");
|
||||
this.darkToggleEl = document.querySelector("[data-dark-toggle]");
|
||||
this.darkToggleLabel = document.querySelector("[data-dark-toggle-label]");
|
||||
this.csrf = document.querySelector("input#csrf_token");
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
this.darkToggleEl.addEventListener("change", (e) => {
|
||||
this.toggle();
|
||||
this.saveMode();
|
||||
});
|
||||
}
|
||||
|
||||
toggle() {
|
||||
document.querySelector("html").classList.toggle("dark");
|
||||
this.darkToggleLabel.textContent = this.darkToggleEl.checked
|
||||
? "dark mode"
|
||||
: "light mode";
|
||||
}
|
||||
|
||||
async saveMode() {
|
||||
const isDark = this.darkToggleEl.checked ? "true" : "false";
|
||||
const data = {
|
||||
method: "POST",
|
||||
headers: {
|
||||
Accept: "application/json",
|
||||
"Content-Type": "application/json",
|
||||
"X-CSRF-Token": this.csrf.value,
|
||||
},
|
||||
body: JSON.stringify({ darkmode: isDark }),
|
||||
};
|
||||
const send = await fetch(
|
||||
`${location.href.split("/").slice(0, -1).join("/")}/darkmode`,
|
||||
data
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class FlashMsg {
|
||||
constructor() {
|
||||
this.openBtn = document.querySelector("[data-flash-sidebar-open]");
|
||||
this.flashCount = document.querySelector("[data-flash-count]");
|
||||
this.isMsgCheck = false;
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
//animate message button if message + never opened
|
||||
window.addEventListener("load", (e) => {
|
||||
if (Number(this.flashCount.textContent) > 0) this.animeBtn();
|
||||
});
|
||||
//stop animate if clicked once
|
||||
this.openBtn.addEventListener("click", (e) => {
|
||||
try {
|
||||
if (
|
||||
e.target.closest("button").hasAttribute("data-flash-sidebar-open")
|
||||
) {
|
||||
this.isMsgCheck = true;
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
//remove flash message and change count
|
||||
window.addEventListener("click", (e) => {
|
||||
try {
|
||||
if (
|
||||
e.target.closest("button").hasAttribute("data-close-flash-message")
|
||||
) {
|
||||
//remove logic
|
||||
const closeBtn = e.target.closest("button");
|
||||
const flashEl = closeBtn.closest("[data-flash-message]");
|
||||
flashEl.remove();
|
||||
//update count
|
||||
this.flashCount.textContent = document.querySelectorAll(
|
||||
"[data-flash-message]"
|
||||
).length;
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
|
||||
animeBtn() {
|
||||
this.openBtn.classList.add("rotate-12");
|
||||
|
||||
setTimeout(() => {
|
||||
this.openBtn.classList.remove("rotate-12");
|
||||
this.openBtn.classList.add("-rotate-12");
|
||||
}, 150);
|
||||
|
||||
setTimeout(() => {
|
||||
this.openBtn.classList.remove("-rotate-12");
|
||||
}, 300);
|
||||
|
||||
setTimeout(() => {
|
||||
if (!this.isMsgCheck) {
|
||||
this.animeBtn();
|
||||
}
|
||||
}, 1500);
|
||||
}
|
||||
}
|
||||
|
||||
class Loader {
|
||||
constructor() {
|
||||
this.menuContainer = document.querySelector("[data-menu-container]");
|
||||
this.logoContainer = document.querySelector("[data-loader]");
|
||||
this.logoEl = document.querySelector("[data-loader-img]");
|
||||
this.isLoading = true;
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
this.loading();
|
||||
window.addEventListener("load", (e) => {
|
||||
setTimeout(() => {
|
||||
this.logoContainer.classList.add("opacity-0");
|
||||
}, 350);
|
||||
|
||||
setTimeout(() => {
|
||||
this.isLoading = false;
|
||||
this.logoContainer.classList.add("hidden");
|
||||
}, 650);
|
||||
|
||||
setTimeout(() => {
|
||||
this.logoContainer.remove();
|
||||
}, 800);
|
||||
});
|
||||
}
|
||||
|
||||
loading() {
|
||||
if ((this.isLoading = true)) {
|
||||
setTimeout(() => {
|
||||
this.logoEl.classList.toggle("scale-105");
|
||||
this.loading();
|
||||
}, 300);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const setLoader = new Loader();
|
||||
const setMenu = new Menu();
|
||||
const setNewsSidebar = new Sidebar(
|
||||
"[data-sidebar-info]",
|
||||
"[data-sidebar-info-open]",
|
||||
"[data-sidebar-info-close]"
|
||||
);
|
||||
|
||||
const setCheckbox = new Checkbox();
|
||||
const setSelect = new Select();
|
||||
const setPassword = new Password();
|
||||
const setDisabledPop = new DisabledPop();
|
||||
|
||||
const setFlashSidebar = new Sidebar(
|
||||
"[data-flash-sidebar]",
|
||||
"[data-flash-sidebar-open]",
|
||||
"[data-flash-sidebar-close]"
|
||||
);
|
||||
const setNews = new News();
|
||||
const setDarkM = new darkMode();
|
||||
const setFlash = new FlashMsg();
|
||||
import { Checkbox, Select, Password, DisabledPop } from "./utils/form.js";
|
||||
|
||||
class Menu {
|
||||
constructor() {
|
||||
this.sidebarEl = document.querySelector("[data-sidebar-menu]");
|
||||
this.toggleBtn = document.querySelector("[data-sidebar-menu-toggle]");
|
||||
this.closeBtn = document.querySelector("[data-sidebar-menu-close]");
|
||||
|
||||
this.toggleBtn.addEventListener("click", this.toggle.bind(this));
|
||||
this.closeBtn.addEventListener("click", this.close.bind(this));
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
window.addEventListener("click", (e) => {
|
||||
try {
|
||||
if (
|
||||
e.target.closest("aside").hasAttribute("data-sidebar-menu") &&
|
||||
e.target.closest("button").getAttribute("role") === "tab"
|
||||
) {
|
||||
this.close();
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
|
||||
toggle() {
|
||||
this.sidebarEl.classList.toggle("-translate-x-full");
|
||||
}
|
||||
|
||||
close() {
|
||||
this.sidebarEl.classList.add("-translate-x-full");
|
||||
}
|
||||
}
|
||||
|
||||
class News {
|
||||
constructor() {
|
||||
this.BASE_URL = "https://www.bunkerweb.io/";
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
window.addEventListener("load", async () => {
|
||||
try {
|
||||
const res = await fetch("https://www.bunkerweb.io/api/posts/0/2", {
|
||||
headers: {
|
||||
method: "GET",
|
||||
},
|
||||
});
|
||||
return await this.render(res);
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
|
||||
render(lastNews) {
|
||||
const newsContainer = document.querySelector("[data-news-container]");
|
||||
//remove default message
|
||||
newsContainer.textContent = "";
|
||||
//render last news
|
||||
lastNews.forEach((news) => {
|
||||
//get info
|
||||
const slug = news.slug;
|
||||
const img = news.photo.url;
|
||||
const excerpt = news.excerpt;
|
||||
const tags = news.tags;
|
||||
const date = news.date;
|
||||
const lastUpdate = news.lastUpdate;
|
||||
//create html card from infos
|
||||
const cardHTML = this.template(
|
||||
slug,
|
||||
img,
|
||||
excerpt,
|
||||
tags,
|
||||
date,
|
||||
lastUpdate,
|
||||
);
|
||||
//add to DOM
|
||||
document
|
||||
.querySelector("[data-news-container]")
|
||||
.insertAdjacentHTML("afterbegin", cardHTML);
|
||||
});
|
||||
}
|
||||
|
||||
template(slug, img, excerpt, tags, date, lastUpdate) {
|
||||
//loop on tags to get list
|
||||
let tagList = "";
|
||||
tags.forEach((tag) => {
|
||||
tagList += ` <a
|
||||
href="${this.BASE_URL}/blog/tag/${tag.slug}"
|
||||
class="my-0 mr-1 rounded bg-secondary hover:brightness-90 hover:-translate-y-0.4 text-white py-1 px-2 text-sm"
|
||||
>
|
||||
${tag.name}
|
||||
</a>`;
|
||||
});
|
||||
//create card
|
||||
const card = `
|
||||
<div
|
||||
class="min-h-[400px] w-full col-span-12 transition hover:-translate-y-2 bg-gray-100 dark:bg-slate-900 rounded px-6 py-4 m-2 flex flex-col justify-between"
|
||||
>
|
||||
<div>
|
||||
<img role="link"
|
||||
onclick="window.location.href='${this.BASE_URL}/blog/post/${slug}'"
|
||||
class="cursor-pointer rounded w-full h-40 m-0 object-cover"
|
||||
src="${img}"
|
||||
alt="image"
|
||||
/>
|
||||
<h3 role="link"
|
||||
onclick="window.location.href='${this.BASE_URL}/blog/post/${slug}'"
|
||||
class="cursor-pointer mt-3 mb-1 text-3xl dark:text-white tracking-wide">{{ post['title'] }}</h3>
|
||||
</div>
|
||||
<div>
|
||||
<div role="link"
|
||||
onclick="window.location.href='${this.BASE_URL}/blog/post/${slug}'"
|
||||
class="cursor-pointer min-h-[130px] mb-3 text-lg dark:text-gray-300 text-gray-600 pt-3">
|
||||
${excerpt}
|
||||
</div>
|
||||
<div class="min-h-[75px] mt-2 flex flex-wrap justify-start items-end align-bottom">
|
||||
${tagList}
|
||||
</div>
|
||||
|
||||
<div class="mt-2 flex flex-col justify-start items-start">
|
||||
<span class="text-xs dark:text-gray-300 text-gray-600"
|
||||
>Posted on : ${date}</span
|
||||
>
|
||||
{% if post["updatedAt"] %}
|
||||
<span class="text-xs dark:text-gray-300 text-gray-600"
|
||||
>Last update : ${lastUpdate}</span
|
||||
>
|
||||
{%endif%}
|
||||
</div>
|
||||
</div>
|
||||
</div> `;
|
||||
return card;
|
||||
}
|
||||
}
|
||||
|
||||
class Sidebar {
|
||||
constructor(elAtt, btnOpenAtt, btnCloseAtt) {
|
||||
this.sidebarEl = document.querySelector(elAtt);
|
||||
this.openBtn = document.querySelector(btnOpenAtt);
|
||||
this.closeBtn = document.querySelector(btnCloseAtt);
|
||||
this.openBtn.addEventListener("click", this.open.bind(this));
|
||||
this.closeBtn.addEventListener("click", this.close.bind(this));
|
||||
}
|
||||
|
||||
open() {
|
||||
this.sidebarEl.classList.add("translate-x-0");
|
||||
this.sidebarEl.classList.remove("translate-x-90");
|
||||
}
|
||||
|
||||
close() {
|
||||
this.sidebarEl.classList.add("translate-x-90");
|
||||
this.sidebarEl.classList.remove("translate-x-0");
|
||||
}
|
||||
}
|
||||
|
||||
class darkMode {
|
||||
constructor() {
|
||||
this.htmlEl = document.querySelector("html");
|
||||
this.darkToggleEl = document.querySelector("[data-dark-toggle]");
|
||||
this.darkToggleLabel = document.querySelector("[data-dark-toggle-label]");
|
||||
this.csrf = document.querySelector("input#csrf_token");
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
this.darkToggleEl.addEventListener("change", (e) => {
|
||||
this.toggle();
|
||||
this.saveMode();
|
||||
});
|
||||
}
|
||||
|
||||
toggle() {
|
||||
document.querySelector("html").classList.toggle("dark");
|
||||
this.darkToggleLabel.textContent = this.darkToggleEl.checked
|
||||
? "dark mode"
|
||||
: "light mode";
|
||||
}
|
||||
|
||||
async saveMode() {
|
||||
const isDark = this.darkToggleEl.checked ? "true" : "false";
|
||||
const data = {
|
||||
method: "POST",
|
||||
headers: {
|
||||
Accept: "application/json",
|
||||
"Content-Type": "application/json",
|
||||
"X-CSRF-Token": this.csrf.value,
|
||||
},
|
||||
body: JSON.stringify({ darkmode: isDark }),
|
||||
};
|
||||
const send = await fetch(
|
||||
`${location.href.split("/").slice(0, -1).join("/")}/darkmode`,
|
||||
data,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class FlashMsg {
|
||||
constructor() {
|
||||
this.openBtn = document.querySelector("[data-flash-sidebar-open]");
|
||||
this.flashCount = document.querySelector("[data-flash-count]");
|
||||
this.isMsgCheck = false;
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
//animate message button if message + never opened
|
||||
window.addEventListener("load", (e) => {
|
||||
if (Number(this.flashCount.textContent) > 0) this.animeBtn();
|
||||
});
|
||||
//stop animate if clicked once
|
||||
this.openBtn.addEventListener("click", (e) => {
|
||||
try {
|
||||
if (
|
||||
e.target.closest("button").hasAttribute("data-flash-sidebar-open")
|
||||
) {
|
||||
this.isMsgCheck = true;
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
//remove flash message and change count
|
||||
window.addEventListener("click", (e) => {
|
||||
try {
|
||||
if (
|
||||
e.target.closest("button").hasAttribute("data-close-flash-message")
|
||||
) {
|
||||
//remove logic
|
||||
const closeBtn = e.target.closest("button");
|
||||
const flashEl = closeBtn.closest("[data-flash-message]");
|
||||
flashEl.remove();
|
||||
//update count
|
||||
this.flashCount.textContent = document.querySelectorAll(
|
||||
"[data-flash-message]",
|
||||
).length;
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
|
||||
animeBtn() {
|
||||
this.openBtn.classList.add("rotate-12");
|
||||
|
||||
setTimeout(() => {
|
||||
this.openBtn.classList.remove("rotate-12");
|
||||
this.openBtn.classList.add("-rotate-12");
|
||||
}, 150);
|
||||
|
||||
setTimeout(() => {
|
||||
this.openBtn.classList.remove("-rotate-12");
|
||||
}, 300);
|
||||
|
||||
setTimeout(() => {
|
||||
if (!this.isMsgCheck) {
|
||||
this.animeBtn();
|
||||
}
|
||||
}, 1500);
|
||||
}
|
||||
}
|
||||
|
||||
class Loader {
|
||||
constructor() {
|
||||
this.menuContainer = document.querySelector("[data-menu-container]");
|
||||
this.logoContainer = document.querySelector("[data-loader]");
|
||||
this.logoEl = document.querySelector("[data-loader-img]");
|
||||
this.isLoading = true;
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
this.loading();
|
||||
window.addEventListener("load", (e) => {
|
||||
setTimeout(() => {
|
||||
this.logoContainer.classList.add("opacity-0");
|
||||
}, 350);
|
||||
|
||||
setTimeout(() => {
|
||||
this.isLoading = false;
|
||||
this.logoContainer.classList.add("hidden");
|
||||
}, 650);
|
||||
|
||||
setTimeout(() => {
|
||||
this.logoContainer.remove();
|
||||
}, 800);
|
||||
});
|
||||
}
|
||||
|
||||
loading() {
|
||||
if ((this.isLoading = true)) {
|
||||
setTimeout(() => {
|
||||
this.logoEl.classList.toggle("scale-105");
|
||||
this.loading();
|
||||
}, 300);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const setLoader = new Loader();
|
||||
const setMenu = new Menu();
|
||||
const setNewsSidebar = new Sidebar(
|
||||
"[data-sidebar-info]",
|
||||
"[data-sidebar-info-open]",
|
||||
"[data-sidebar-info-close]",
|
||||
);
|
||||
|
||||
const setCheckbox = new Checkbox();
|
||||
const setSelect = new Select();
|
||||
const setPassword = new Password();
|
||||
const setDisabledPop = new DisabledPop();
|
||||
|
||||
const setFlashSidebar = new Sidebar(
|
||||
"[data-flash-sidebar]",
|
||||
"[data-flash-sidebar-open]",
|
||||
"[data-flash-sidebar-close]",
|
||||
);
|
||||
const setNews = new News();
|
||||
const setDarkM = new darkMode();
|
||||
const setFlash = new FlashMsg();
|
||||
|
|
|
@ -1,35 +1,35 @@
|
|||
import {
|
||||
Popover,
|
||||
Tabs,
|
||||
FormatValue,
|
||||
FilterSettings,
|
||||
} from "./utils/settings.js";
|
||||
|
||||
class Multiple {
|
||||
constructor(prefix) {
|
||||
this.prefix = prefix;
|
||||
this.init();
|
||||
}
|
||||
//hide multiples handler if no multiple setting on plugin
|
||||
init() {
|
||||
//hide multiple btn if no multiple exist on a plugin
|
||||
const multiples = document.querySelectorAll(
|
||||
`[data-${this.prefix}-settings-multiple]`
|
||||
);
|
||||
multiples.forEach((container) => {
|
||||
if (container.querySelectorAll(`[data-setting-container]`).length <= 0)
|
||||
container.parentElement
|
||||
.querySelector("[data-multiple-handler]")
|
||||
.classList.add("hidden");
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
const setPopover = new Popover("main", "global-config");
|
||||
const setTabs = new Tabs("[global-config-tabs]", "global-config");
|
||||
const format = new FormatValue();
|
||||
const setMultiple = new Multiple("global-config");
|
||||
const setFilterGlobal = new FilterSettings(
|
||||
"settings-filter",
|
||||
"[data-service-content='settings']"
|
||||
);
|
||||
import {
|
||||
Popover,
|
||||
Tabs,
|
||||
FormatValue,
|
||||
FilterSettings,
|
||||
} from "./utils/settings.js";
|
||||
|
||||
class Multiple {
|
||||
constructor(prefix) {
|
||||
this.prefix = prefix;
|
||||
this.init();
|
||||
}
|
||||
//hide multiples handler if no multiple setting on plugin
|
||||
init() {
|
||||
//hide multiple btn if no multiple exist on a plugin
|
||||
const multiples = document.querySelectorAll(
|
||||
`[data-${this.prefix}-settings-multiple]`,
|
||||
);
|
||||
multiples.forEach((container) => {
|
||||
if (container.querySelectorAll(`[data-setting-container]`).length <= 0)
|
||||
container.parentElement
|
||||
.querySelector("[data-multiple-handler]")
|
||||
.classList.add("hidden");
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
const setPopover = new Popover("main", "global-config");
|
||||
const setTabs = new Tabs("[global-config-tabs]", "global-config");
|
||||
const format = new FormatValue();
|
||||
const setMultiple = new Multiple("global-config");
|
||||
const setFilterGlobal = new FilterSettings(
|
||||
"settings-filter",
|
||||
"[data-service-content='settings']",
|
||||
);
|
||||
|
|
|
@ -37,7 +37,7 @@ class Dropdown {
|
|||
const btn = e.target.closest("button");
|
||||
const btnValue = btn.getAttribute("value");
|
||||
const btnSetting = btn.getAttribute(
|
||||
`data-${this.prefix}-setting-select-dropdown-btn`
|
||||
`data-${this.prefix}-setting-select-dropdown-btn`,
|
||||
);
|
||||
//stop if same value to avoid new fetching
|
||||
const isSameVal = this.isSameValue(btnSetting, btnValue);
|
||||
|
@ -61,7 +61,7 @@ class Dropdown {
|
|||
|
||||
closeAllDrop() {
|
||||
const drops = document.querySelectorAll(
|
||||
`[data-${this.prefix}-setting-select-dropdown]`
|
||||
`[data-${this.prefix}-setting-select-dropdown]`,
|
||||
);
|
||||
drops.forEach((drop) => {
|
||||
drop.classList.add("hidden");
|
||||
|
@ -69,8 +69,8 @@ class Dropdown {
|
|||
document
|
||||
.querySelector(
|
||||
`svg[data-${this.prefix}-setting-select="${drop.getAttribute(
|
||||
`data-${this.prefix}-setting-select-dropdown`
|
||||
)}"]`
|
||||
`data-${this.prefix}-setting-select-dropdown`,
|
||||
)}"]`,
|
||||
)
|
||||
.classList.remove("rotate-180");
|
||||
});
|
||||
|
@ -78,7 +78,7 @@ class Dropdown {
|
|||
|
||||
isSameValue(btnSetting, value) {
|
||||
const selectCustom = document.querySelector(
|
||||
`[data-${this.prefix}-setting-select-text="${btnSetting}"]`
|
||||
`[data-${this.prefix}-setting-select-text="${btnSetting}"]`,
|
||||
);
|
||||
const currVal = selectCustom.textContent;
|
||||
return currVal === value ? true : false;
|
||||
|
@ -86,30 +86,30 @@ class Dropdown {
|
|||
|
||||
setSelectNewValue(btnSetting, value) {
|
||||
const selectCustom = document.querySelector(
|
||||
`[data-${this.prefix}-setting-select="${btnSetting}"]`
|
||||
`[data-${this.prefix}-setting-select="${btnSetting}"]`,
|
||||
);
|
||||
selectCustom.querySelector(
|
||||
`[data-${this.prefix}-setting-select-text]`
|
||||
`[data-${this.prefix}-setting-select-text]`,
|
||||
).textContent = value;
|
||||
}
|
||||
|
||||
hideDropdown(btnSetting) {
|
||||
//hide dropdown
|
||||
const dropdownEl = document.querySelector(
|
||||
`[data-${this.prefix}-setting-select-dropdown="${btnSetting}"]`
|
||||
`[data-${this.prefix}-setting-select-dropdown="${btnSetting}"]`,
|
||||
);
|
||||
dropdownEl.classList.add("hidden");
|
||||
dropdownEl.classList.remove("flex");
|
||||
//svg effect
|
||||
const dropdownChevron = document.querySelector(
|
||||
`svg[data-${this.prefix}-setting-select="${btnSetting}"]`
|
||||
`svg[data-${this.prefix}-setting-select="${btnSetting}"]`,
|
||||
);
|
||||
dropdownChevron.classList.remove("rotate-180");
|
||||
}
|
||||
|
||||
changeDropBtnStyle(btnSetting, selectedBtn) {
|
||||
const dropdownEl = document.querySelector(
|
||||
`[data-${this.prefix}-setting-select-dropdown="${btnSetting}"]`
|
||||
`[data-${this.prefix}-setting-select-dropdown="${btnSetting}"]`,
|
||||
);
|
||||
//reset dropdown btns
|
||||
const btnEls = dropdownEl.querySelectorAll("button");
|
||||
|
@ -119,7 +119,7 @@ class Dropdown {
|
|||
"bg-primary",
|
||||
"dark:bg-primary",
|
||||
"text-gray-300",
|
||||
"text-gray-300"
|
||||
"text-gray-300",
|
||||
);
|
||||
btn.classList.add("bg-white", "dark:bg-slate-700", "text-gray-700");
|
||||
});
|
||||
|
@ -127,7 +127,7 @@ class Dropdown {
|
|||
selectedBtn.classList.remove(
|
||||
"bg-white",
|
||||
"dark:bg-slate-700",
|
||||
"text-gray-700"
|
||||
"text-gray-700",
|
||||
);
|
||||
selectedBtn.classList.add("dark:bg-primary", "bg-primary", "text-gray-300");
|
||||
}
|
||||
|
@ -138,10 +138,10 @@ class Dropdown {
|
|||
.getAttribute(`data-${this.prefix}-setting-select`);
|
||||
//toggle dropdown
|
||||
const dropdownEl = document.querySelector(
|
||||
`[data-${this.prefix}-setting-select-dropdown="${attribut}"]`
|
||||
`[data-${this.prefix}-setting-select-dropdown="${attribut}"]`,
|
||||
);
|
||||
const dropdownChevron = document.querySelector(
|
||||
`svg[data-${this.prefix}-setting-select="${attribut}"]`
|
||||
`svg[data-${this.prefix}-setting-select="${attribut}"]`,
|
||||
);
|
||||
dropdownEl.classList.toggle("hidden");
|
||||
dropdownEl.classList.toggle("flex");
|
||||
|
@ -197,7 +197,7 @@ class Filter {
|
|||
setTimeout(() => {
|
||||
const value = document
|
||||
.querySelector(
|
||||
`[data-${this.prefix}-setting-select-text="success"]`
|
||||
`[data-${this.prefix}-setting-select-text="success"]`,
|
||||
)
|
||||
.textContent.trim();
|
||||
|
||||
|
@ -220,7 +220,7 @@ class Filter {
|
|||
setTimeout(() => {
|
||||
const value = document
|
||||
.querySelector(
|
||||
`[data-${this.prefix}-setting-select-text="reload"]`
|
||||
`[data-${this.prefix}-setting-select-text="reload"]`,
|
||||
)
|
||||
.textContent.trim();
|
||||
|
||||
|
@ -329,7 +329,7 @@ class Download {
|
|||
|
||||
async sendFileToDL(jobName, fileName) {
|
||||
window.open(
|
||||
`${location.href}/download?job_name=${jobName}&file_name=${fileName}`
|
||||
`${location.href}/download?job_name=${jobName}&file_name=${fileName}`,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -37,7 +37,7 @@ class Dropdown {
|
|||
const btn = e.target.closest("button");
|
||||
const btnValue = btn.getAttribute("value");
|
||||
const btnSetting = btn.getAttribute(
|
||||
`data-${this.prefix}-setting-select-dropdown-btn`
|
||||
`data-${this.prefix}-setting-select-dropdown-btn`,
|
||||
);
|
||||
//stop if same value to avoid new fetching
|
||||
const isSameVal = this.isSameValue(btnSetting, btnValue);
|
||||
|
@ -58,7 +58,7 @@ class Dropdown {
|
|||
|
||||
closeAllDrop() {
|
||||
const drops = document.querySelectorAll(
|
||||
`[data-${this.prefix}-setting-select-dropdown]`
|
||||
`[data-${this.prefix}-setting-select-dropdown]`,
|
||||
);
|
||||
drops.forEach((drop) => {
|
||||
drop.classList.add("hidden");
|
||||
|
@ -66,8 +66,8 @@ class Dropdown {
|
|||
document
|
||||
.querySelector(
|
||||
`svg[data-${this.prefix}-setting-select="${drop.getAttribute(
|
||||
`data-${this.prefix}-setting-select-dropdown`
|
||||
)}"]`
|
||||
`data-${this.prefix}-setting-select-dropdown`,
|
||||
)}"]`,
|
||||
)
|
||||
.classList.remove("rotate-180");
|
||||
});
|
||||
|
@ -75,7 +75,7 @@ class Dropdown {
|
|||
|
||||
isSameValue(btnSetting, value) {
|
||||
const selectCustom = document.querySelector(
|
||||
`[data-${this.prefix}-setting-select-text="${btnSetting}"]`
|
||||
`[data-${this.prefix}-setting-select-text="${btnSetting}"]`,
|
||||
);
|
||||
const currVal = selectCustom.textContent;
|
||||
return currVal === value ? true : false;
|
||||
|
@ -83,30 +83,30 @@ class Dropdown {
|
|||
|
||||
setSelectNewValue(btnSetting, value) {
|
||||
const selectCustom = document.querySelector(
|
||||
`[data-${this.prefix}-setting-select="${btnSetting}"]`
|
||||
`[data-${this.prefix}-setting-select="${btnSetting}"]`,
|
||||
);
|
||||
selectCustom.querySelector(
|
||||
`[data-${this.prefix}-setting-select-text]`
|
||||
`[data-${this.prefix}-setting-select-text]`,
|
||||
).textContent = value;
|
||||
}
|
||||
|
||||
hideDropdown(btnSetting) {
|
||||
//hide dropdown
|
||||
const dropdownEl = document.querySelector(
|
||||
`[data-${this.prefix}-setting-select-dropdown="${btnSetting}"]`
|
||||
`[data-${this.prefix}-setting-select-dropdown="${btnSetting}"]`,
|
||||
);
|
||||
dropdownEl.classList.add("hidden");
|
||||
dropdownEl.classList.remove("flex");
|
||||
//svg effect
|
||||
const dropdownChevron = document.querySelector(
|
||||
`svg[data-${this.prefix}-setting-select="${btnSetting}"]`
|
||||
`svg[data-${this.prefix}-setting-select="${btnSetting}"]`,
|
||||
);
|
||||
dropdownChevron.classList.remove("rotate-180");
|
||||
}
|
||||
|
||||
changeDropBtnStyle(btnSetting, selectedBtn) {
|
||||
const dropdownEl = document.querySelector(
|
||||
`[data-${this.prefix}-setting-select-dropdown="${btnSetting}"]`
|
||||
`[data-${this.prefix}-setting-select-dropdown="${btnSetting}"]`,
|
||||
);
|
||||
//reset dropdown btns
|
||||
const btnEls = dropdownEl.querySelectorAll("button");
|
||||
|
@ -116,7 +116,7 @@ class Dropdown {
|
|||
"bg-primary",
|
||||
"dark:bg-primary",
|
||||
"text-gray-300",
|
||||
"text-gray-300"
|
||||
"text-gray-300",
|
||||
);
|
||||
btn.classList.add("bg-white", "dark:bg-slate-700", "text-gray-700");
|
||||
});
|
||||
|
@ -124,7 +124,7 @@ class Dropdown {
|
|||
selectedBtn.classList.remove(
|
||||
"bg-white",
|
||||
"dark:bg-slate-700",
|
||||
"text-gray-700"
|
||||
"text-gray-700",
|
||||
);
|
||||
selectedBtn.classList.add("dark:bg-primary", "bg-primary", "text-gray-300");
|
||||
}
|
||||
|
@ -135,10 +135,10 @@ class Dropdown {
|
|||
.getAttribute(`data-${this.prefix}-setting-select`);
|
||||
//toggle dropdown
|
||||
const dropdownEl = document.querySelector(
|
||||
`[data-${this.prefix}-setting-select-dropdown="${attribut}"]`
|
||||
`[data-${this.prefix}-setting-select-dropdown="${attribut}"]`,
|
||||
);
|
||||
const dropdownChevron = document.querySelector(
|
||||
`svg[data-${this.prefix}-setting-select="${attribut}"]`
|
||||
`svg[data-${this.prefix}-setting-select="${attribut}"]`,
|
||||
);
|
||||
dropdownEl.classList.toggle("hidden");
|
||||
dropdownEl.classList.toggle("flex");
|
||||
|
@ -173,7 +173,7 @@ class FetchLogs {
|
|||
constructor(prefix = "logs") {
|
||||
this.prefix = prefix;
|
||||
this.instance = document.querySelector(
|
||||
`[data-${this.prefix}-setting-select-text="instances"]`
|
||||
`[data-${this.prefix}-setting-select-text="instances"]`,
|
||||
);
|
||||
this.instanceName = "";
|
||||
this.updateInp = document.querySelector("input#update-date");
|
||||
|
@ -188,7 +188,7 @@ class FetchLogs {
|
|||
this.lastUpdate = Date.now() - 86400000;
|
||||
this.container = document.querySelector(`[data-${this.prefix}-settings]`);
|
||||
this.logListContainer = document.querySelector(
|
||||
`[data-${this.prefix}-list]`
|
||||
`[data-${this.prefix}-list]`,
|
||||
);
|
||||
this.submitDate = document.querySelector("button[data-submit-date]");
|
||||
this.submitLive = document.querySelector("button[data-submit-live]");
|
||||
|
@ -218,7 +218,7 @@ class FetchLogs {
|
|||
"data-submit-live",
|
||||
this.submitLive.getAttribute("data-submit-live") === "yes"
|
||||
? "no"
|
||||
: "yes"
|
||||
: "yes",
|
||||
);
|
||||
|
||||
if (this.submitLive.getAttribute("data-submit-live") === "yes") {
|
||||
|
@ -314,7 +314,7 @@ class FetchLogs {
|
|||
.querySelector(`[data-${this.prefix}-list]`)
|
||||
.scrollTo(
|
||||
0,
|
||||
document.querySelector(`[data-${this.prefix}-list]`).scrollHeight
|
||||
document.querySelector(`[data-${this.prefix}-list]`).scrollHeight,
|
||||
);
|
||||
}
|
||||
|
||||
|
@ -323,7 +323,7 @@ class FetchLogs {
|
|||
//case from date defined only
|
||||
if (this.toDate) {
|
||||
res = await fetch(
|
||||
`${location.href}/${this.instanceName}?from_date=${this.fromDate}&to_date=${this.toDate}`
|
||||
`${location.href}/${this.instanceName}?from_date=${this.fromDate}&to_date=${this.toDate}`,
|
||||
);
|
||||
const data = await res.json();
|
||||
return await this.showLogsDate(data);
|
||||
|
@ -331,7 +331,7 @@ class FetchLogs {
|
|||
//case from date and to date defined
|
||||
if (!this.toDate) {
|
||||
res = await fetch(
|
||||
`${location.href}/${this.instanceName}?from_date=${this.fromDate}`
|
||||
`${location.href}/${this.instanceName}?from_date=${this.fromDate}`,
|
||||
);
|
||||
const data = await res.json();
|
||||
return await this.showLogsDate(data);
|
||||
|
@ -341,7 +341,7 @@ class FetchLogs {
|
|||
async getLogsSinceLastUpdate() {
|
||||
const response = await fetch(
|
||||
`${location.href}/${this.instanceName}` +
|
||||
(this.lastUpdate ? `?last_update=${this.lastUpdate}` : "")
|
||||
(this.lastUpdate ? `?last_update=${this.lastUpdate}` : ""),
|
||||
);
|
||||
const data = await response.json();
|
||||
return await this.showLogsLive(data);
|
||||
|
@ -437,7 +437,7 @@ class Filter {
|
|||
const btn = e.target.closest("button");
|
||||
const btnValue = btn.getAttribute("value");
|
||||
const btnSetting = btn.getAttribute(
|
||||
`data-${this.prefix}-setting-select-dropdown-btn`
|
||||
`data-${this.prefix}-setting-select-dropdown-btn`,
|
||||
);
|
||||
|
||||
this.lastType = btnValue;
|
||||
|
|
|
@ -36,7 +36,7 @@ class Dropdown {
|
|||
const btn = e.target.closest("button");
|
||||
const btnValue = btn.getAttribute("value");
|
||||
const btnSetting = btn.getAttribute(
|
||||
`data-${this.prefix}-setting-select-dropdown-btn`
|
||||
`data-${this.prefix}-setting-select-dropdown-btn`,
|
||||
);
|
||||
//stop if same value to avoid new fetching
|
||||
const isSameVal = this.isSameValue(btnSetting, btnValue);
|
||||
|
@ -57,7 +57,7 @@ class Dropdown {
|
|||
|
||||
closeAllDrop() {
|
||||
const drops = document.querySelectorAll(
|
||||
`[data-${this.prefix}-setting-select-dropdown]`
|
||||
`[data-${this.prefix}-setting-select-dropdown]`,
|
||||
);
|
||||
drops.forEach((drop) => {
|
||||
drop.classList.add("hidden");
|
||||
|
@ -65,8 +65,8 @@ class Dropdown {
|
|||
document
|
||||
.querySelector(
|
||||
`svg[data-${this.prefix}-setting-select="${drop.getAttribute(
|
||||
`data-${this.prefix}-setting-select-dropdown`
|
||||
)}"]`
|
||||
`data-${this.prefix}-setting-select-dropdown`,
|
||||
)}"]`,
|
||||
)
|
||||
.classList.remove("rotate-180");
|
||||
});
|
||||
|
@ -74,7 +74,7 @@ class Dropdown {
|
|||
|
||||
isSameValue(btnSetting, value) {
|
||||
const selectCustom = document.querySelector(
|
||||
`[data-${this.prefix}-setting-select-text="${btnSetting}"]`
|
||||
`[data-${this.prefix}-setting-select-text="${btnSetting}"]`,
|
||||
);
|
||||
const currVal = selectCustom.textContent;
|
||||
return currVal === value ? true : false;
|
||||
|
@ -82,30 +82,30 @@ class Dropdown {
|
|||
|
||||
setSelectNewValue(btnSetting, value) {
|
||||
const selectCustom = document.querySelector(
|
||||
`[data-${this.prefix}-setting-select="${btnSetting}"]`
|
||||
`[data-${this.prefix}-setting-select="${btnSetting}"]`,
|
||||
);
|
||||
selectCustom.querySelector(
|
||||
`[data-${this.prefix}-setting-select-text]`
|
||||
`[data-${this.prefix}-setting-select-text]`,
|
||||
).textContent = value;
|
||||
}
|
||||
|
||||
hideDropdown(btnSetting) {
|
||||
//hide dropdown
|
||||
const dropdownEl = document.querySelector(
|
||||
`[data-${this.prefix}-setting-select-dropdown="${btnSetting}"]`
|
||||
`[data-${this.prefix}-setting-select-dropdown="${btnSetting}"]`,
|
||||
);
|
||||
dropdownEl.classList.add("hidden");
|
||||
dropdownEl.classList.remove("flex");
|
||||
//svg effect
|
||||
const dropdownChevron = document.querySelector(
|
||||
`svg[data-${this.prefix}-setting-select="${btnSetting}"]`
|
||||
`svg[data-${this.prefix}-setting-select="${btnSetting}"]`,
|
||||
);
|
||||
dropdownChevron.classList.remove("rotate-180");
|
||||
}
|
||||
|
||||
changeDropBtnStyle(btnSetting, selectedBtn) {
|
||||
const dropdownEl = document.querySelector(
|
||||
`[data-${this.prefix}-setting-select-dropdown="${btnSetting}"]`
|
||||
`[data-${this.prefix}-setting-select-dropdown="${btnSetting}"]`,
|
||||
);
|
||||
//reset dropdown btns
|
||||
const btnEls = dropdownEl.querySelectorAll("button");
|
||||
|
@ -116,7 +116,7 @@ class Dropdown {
|
|||
"bg-primary",
|
||||
"bg-primary",
|
||||
"text-gray-300",
|
||||
"text-gray-300"
|
||||
"text-gray-300",
|
||||
);
|
||||
btn.classList.add("bg-white", "dark:bg-slate-700", "text-gray-700");
|
||||
});
|
||||
|
@ -124,7 +124,7 @@ class Dropdown {
|
|||
selectedBtn.classList.remove(
|
||||
"bg-white",
|
||||
"dark:bg-slate-700",
|
||||
"text-gray-700"
|
||||
"text-gray-700",
|
||||
);
|
||||
selectedBtn.classList.add("dark:bg-primary", "bg-primary", "text-gray-300");
|
||||
}
|
||||
|
@ -135,10 +135,10 @@ class Dropdown {
|
|||
.getAttribute(`data-${this.prefix}-setting-select`);
|
||||
//toggle dropdown
|
||||
const dropdownEl = document.querySelector(
|
||||
`[data-${this.prefix}-setting-select-dropdown="${attribut}"]`
|
||||
`[data-${this.prefix}-setting-select-dropdown="${attribut}"]`,
|
||||
);
|
||||
const dropdownChevron = document.querySelector(
|
||||
`svg[data-${this.prefix}-setting-select="${attribut}"]`
|
||||
`svg[data-${this.prefix}-setting-select="${attribut}"]`,
|
||||
);
|
||||
dropdownEl.classList.toggle("hidden");
|
||||
dropdownEl.classList.toggle("flex");
|
||||
|
@ -286,7 +286,9 @@ class Upload {
|
|||
//close fail/success log
|
||||
this.container.addEventListener("click", (e) => {
|
||||
try {
|
||||
if (e.target.closest("button").hasAttribute("data-upload-message-delete")) {
|
||||
if (
|
||||
e.target.closest("button").hasAttribute("data-upload-message-delete")
|
||||
) {
|
||||
const message = e.target.closest("div[data-upload-message]");
|
||||
message.remove();
|
||||
}
|
||||
|
@ -298,7 +300,7 @@ class Upload {
|
|||
this.dropZoneElement.classList.remove(
|
||||
"border-solid",
|
||||
"bg-gray-100",
|
||||
"dark:bg-slate-700/50"
|
||||
"dark:bg-slate-700/50",
|
||||
);
|
||||
this.dropZoneElement.classList.add("border-dashed");
|
||||
}
|
||||
|
@ -307,7 +309,7 @@ class Upload {
|
|||
this.dropZoneElement.classList.add(
|
||||
"border-solid",
|
||||
"bg-gray-100",
|
||||
"dark:bg-slate-700/50"
|
||||
"dark:bg-slate-700/50",
|
||||
);
|
||||
this.dropZoneElement.classList.remove("border-dashed");
|
||||
}
|
||||
|
@ -343,13 +345,13 @@ class Upload {
|
|||
if (xhr.status == 201) {
|
||||
this.uploadedArea.insertAdjacentHTML(
|
||||
"afterbegin",
|
||||
this.fileSuccess(name, fileSize)
|
||||
this.fileSuccess(name, fileSize),
|
||||
);
|
||||
this.allowReload();
|
||||
} else {
|
||||
this.uploadedArea.insertAdjacentHTML(
|
||||
"afterbegin",
|
||||
this.fileFail(name, fileSize)
|
||||
this.fileFail(name, fileSize),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -445,8 +447,12 @@ class Modal {
|
|||
this.modalNameInp = this.modal.querySelector("input#name");
|
||||
this.modalExtInp = this.modal.querySelector("input#external");
|
||||
|
||||
this.modalTitle = this.modal.querySelector(`[data-${this.prefix}-modal-title]`);
|
||||
this.modalTxt = this.modal.querySelector(`[data-${this.prefix}-modal-text]`);
|
||||
this.modalTitle = this.modal.querySelector(
|
||||
`[data-${this.prefix}-modal-title]`,
|
||||
);
|
||||
this.modalTxt = this.modal.querySelector(
|
||||
`[data-${this.prefix}-modal-text]`,
|
||||
);
|
||||
this.init();
|
||||
}
|
||||
|
||||
|
@ -455,8 +461,9 @@ class Modal {
|
|||
//DELETE HANDLER
|
||||
try {
|
||||
if (
|
||||
e.target.closest("button").getAttribute(`data-${this.prefix}-action`) ===
|
||||
"delete"
|
||||
e.target
|
||||
.closest("button")
|
||||
.getAttribute(`data-${this.prefix}-action`) === "delete"
|
||||
) {
|
||||
const btnEl = e.target.closest("button");
|
||||
this.setModal(btnEl);
|
||||
|
@ -469,7 +476,9 @@ class Modal {
|
|||
//CLOSE MODAL HANDLER
|
||||
try {
|
||||
if (
|
||||
e.target.closest("button").hasAttribute(`data-${this.prefix}-modal-close`)
|
||||
e.target
|
||||
.closest("button")
|
||||
.hasAttribute(`data-${this.prefix}-modal-close`)
|
||||
) {
|
||||
this.hideModal();
|
||||
}
|
||||
|
|
File diff suppressed because it is too large
Load diff
4
src/ui/static/js/tsparticles.bundle.min.js
vendored
4
src/ui/static/js/tsparticles.bundle.min.js
vendored
File diff suppressed because one or more lines are too long
File diff suppressed because it is too large
Load diff
|
@ -1,262 +1,262 @@
|
|||
class Checkbox {
|
||||
constructor() {
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
window.addEventListener("click", (e) => {
|
||||
//prevent default checkbox behavior
|
||||
try {
|
||||
//case a related checkbox element is clicked and checkbox is enabled
|
||||
if (
|
||||
e.target.closest("div").hasAttribute("data-checkbox-handler") &&
|
||||
!e.target
|
||||
.closest("div")
|
||||
.querySelector('input[type="checkbox"]')
|
||||
.hasAttribute("disabled")
|
||||
) {
|
||||
//get related checkbox
|
||||
const checkboxEl = e.target
|
||||
.closest("div")
|
||||
.querySelector('input[type="checkbox"]');
|
||||
|
||||
const prevValue = checkboxEl.getAttribute("value");
|
||||
|
||||
//set attribute value for new state
|
||||
prevValue === "no"
|
||||
? checkboxEl.setAttribute("value", "yes")
|
||||
: checkboxEl.setAttribute("value", "no");
|
||||
|
||||
//set custom input hidden value
|
||||
const newValue = checkboxEl.getAttribute("value");
|
||||
newValue === "yes"
|
||||
? checkboxEl.setAttribute("aria-checked", "true")
|
||||
: checkboxEl.setAttribute("aria-checked", "false");
|
||||
|
||||
//force checked for submit
|
||||
checkboxEl.checked = true;
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
class Select {
|
||||
constructor() {
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
window.addEventListener("click", (e) => {
|
||||
//CASE NO BTN SELECT CLICKED
|
||||
try {
|
||||
if (!e.target.closest("button")) {
|
||||
const selectEls = document.querySelectorAll(
|
||||
"div[data-setting-select-dropdown]"
|
||||
);
|
||||
selectEls.forEach((select) => {
|
||||
select.classList.add("hidden");
|
||||
select.classList.remove("flex");
|
||||
});
|
||||
const btnEls = document.querySelectorAll(
|
||||
"button[data-setting-select]"
|
||||
);
|
||||
btnEls.forEach((btn) => {
|
||||
const dropdownChevron = btn.querySelector(
|
||||
`svg[data-setting-select]`
|
||||
);
|
||||
dropdownChevron.classList.remove("rotate-180");
|
||||
});
|
||||
}
|
||||
} catch (err) {}
|
||||
//SELECT BTN LOGIC
|
||||
try {
|
||||
if (
|
||||
e.target.closest("button").hasAttribute(`data-setting-select`) &&
|
||||
!e.target.closest("button").hasAttribute(`disabled`)
|
||||
) {
|
||||
const btnEl = e.target.closest("button");
|
||||
this.toggleSelectBtn(btnEl);
|
||||
}
|
||||
} catch (err) {}
|
||||
//SELECT DROPDOWN BTN LOGIC
|
||||
try {
|
||||
if (
|
||||
e.target
|
||||
.closest("button")
|
||||
.hasAttribute(`data-setting-select-dropdown-btn`)
|
||||
) {
|
||||
const btn = e.target.closest(
|
||||
`button[data-setting-select-dropdown-btn]`
|
||||
);
|
||||
const btnValue = btn.getAttribute("value");
|
||||
|
||||
//add new value to custom
|
||||
const selectCustom = btn
|
||||
.closest("div[data-select-container]")
|
||||
.querySelector(`button[data-setting-select]`);
|
||||
|
||||
selectCustom.querySelector(`[data-setting-select-text]`).textContent =
|
||||
btnValue;
|
||||
//add selected to new value
|
||||
|
||||
//change style
|
||||
const dropdownEl = btn.closest(`div[data-setting-select-dropdown]`);
|
||||
dropdownEl.classList.add("hidden");
|
||||
dropdownEl.classList.remove("flex");
|
||||
|
||||
//reset dropdown btns
|
||||
const btnEls = dropdownEl.querySelectorAll("button");
|
||||
|
||||
btnEls.forEach((btn) => {
|
||||
btn.classList.remove("active");
|
||||
});
|
||||
//highlight clicked btn
|
||||
btn.classList.add("active");
|
||||
|
||||
//close dropdown
|
||||
const dropdownChevron = selectCustom.querySelector(
|
||||
`svg[data-setting-select]`
|
||||
);
|
||||
dropdownChevron.classList.remove("rotate-180");
|
||||
|
||||
//update real select element
|
||||
const realSel = btn
|
||||
.closest("div[data-setting-container]")
|
||||
.querySelector("select");
|
||||
this.updateSelected(realSel, btnValue);
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
|
||||
updateSelected(selectEl, selectedValue) {
|
||||
const options = selectEl.querySelectorAll("option");
|
||||
//remove selected to all
|
||||
options.forEach((option) => {
|
||||
option.removeAttribute("selected");
|
||||
option.selected = false;
|
||||
});
|
||||
//select new one
|
||||
const newOption = selectEl.querySelector(
|
||||
`option[value="${selectedValue}"]`
|
||||
);
|
||||
newOption.selected = true;
|
||||
newOption.setAttribute("selected", "");
|
||||
}
|
||||
|
||||
toggleSelectBtn(btn) {
|
||||
//toggle dropdown
|
||||
const dropdownEl = btn
|
||||
.closest("div")
|
||||
.querySelector(`[data-setting-select-dropdown]`);
|
||||
const dropdownChevron = btn.querySelector(`svg[data-setting-select]`);
|
||||
dropdownEl.classList.toggle("hidden");
|
||||
dropdownEl.classList.toggle("flex");
|
||||
dropdownChevron.classList.toggle("rotate-180");
|
||||
}
|
||||
}
|
||||
|
||||
class Password {
|
||||
constructor() {
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
window.addEventListener("click", (e) => {
|
||||
try {
|
||||
if (e.target.closest("button").hasAttribute("data-setting-password")) {
|
||||
const btn = e.target.closest("button");
|
||||
const action = btn.getAttribute("data-setting-password");
|
||||
const inp = btn
|
||||
.closest("[data-setting-container]")
|
||||
.querySelector("input");
|
||||
this.setValDisplay(action, inp);
|
||||
this.hiddenBtns(btn);
|
||||
this.showOppositeBtn(btn, action);
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
|
||||
showOppositeBtn(btnEl, action) {
|
||||
const btnEls = this.getBtns(btnEl);
|
||||
const opposite = action === "visible" ? "invisible" : "visible";
|
||||
|
||||
btnEls.forEach((btn) => {
|
||||
const action = btn.getAttribute("data-setting-password");
|
||||
|
||||
if (action === opposite) {
|
||||
btn.classList.add("flex");
|
||||
btn.classList.remove("hidden");
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
setValDisplay(action, inp) {
|
||||
if (action === "visible") inp.setAttribute("type", "text");
|
||||
if (action === "invisible") inp.setAttribute("type", "password");
|
||||
}
|
||||
|
||||
hiddenBtns(btnEl) {
|
||||
const btnEls = this.getBtns(btnEl);
|
||||
|
||||
btnEls.forEach((btn) => {
|
||||
btn.classList.add("hidden");
|
||||
btn.classList.remove("flex");
|
||||
});
|
||||
}
|
||||
|
||||
getBtns(btnEl) {
|
||||
return btnEl
|
||||
.closest("[data-setting-container]")
|
||||
.querySelectorAll("button[data-setting-password]");
|
||||
}
|
||||
}
|
||||
|
||||
class DisabledPop {
|
||||
constructor() {
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
window.addEventListener("pointerover", (e) => {
|
||||
//for checkbox and regular inputs
|
||||
if (e.target.tagName === "INPUT") {
|
||||
const el = e.target;
|
||||
this.showPopup(el, "input");
|
||||
}
|
||||
//for select custom
|
||||
if (
|
||||
e.target.tagName === "BUTTON" &&
|
||||
e.target.hasAttribute("data-setting-select")
|
||||
) {
|
||||
const el = e.target;
|
||||
this.showPopup(el, "select");
|
||||
}
|
||||
});
|
||||
|
||||
window.addEventListener("pointerout", (e) => {
|
||||
try {
|
||||
const popupEl = e.target
|
||||
.closest("div")
|
||||
.querySelector("div[data-disabled-info]");
|
||||
popupEl.remove();
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
|
||||
showPopup(el, type = "input") {
|
||||
if (!el.hasAttribute("disabled")) return;
|
||||
const method = el.getAttribute("data-default-method");
|
||||
const popupHTML = `
|
||||
<div data-disabled-info class="${
|
||||
type === "select" ? "translate-y-2" : ""
|
||||
} bg-blue-500 absolute right-2 rounded-lg px-2 py-1 z-20 dark:brightness-90">
|
||||
<p class="m-0 text-xs text-white dark:text-gray-100">disabled by ${method}</p>
|
||||
</div>`;
|
||||
el.insertAdjacentHTML("beforebegin", popupHTML);
|
||||
}
|
||||
}
|
||||
|
||||
export { Checkbox, Select, Password, DisabledPop };
|
||||
class Checkbox {
|
||||
constructor() {
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
window.addEventListener("click", (e) => {
|
||||
//prevent default checkbox behavior
|
||||
try {
|
||||
//case a related checkbox element is clicked and checkbox is enabled
|
||||
if (
|
||||
e.target.closest("div").hasAttribute("data-checkbox-handler") &&
|
||||
!e.target
|
||||
.closest("div")
|
||||
.querySelector('input[type="checkbox"]')
|
||||
.hasAttribute("disabled")
|
||||
) {
|
||||
//get related checkbox
|
||||
const checkboxEl = e.target
|
||||
.closest("div")
|
||||
.querySelector('input[type="checkbox"]');
|
||||
|
||||
const prevValue = checkboxEl.getAttribute("value");
|
||||
|
||||
//set attribute value for new state
|
||||
prevValue === "no"
|
||||
? checkboxEl.setAttribute("value", "yes")
|
||||
: checkboxEl.setAttribute("value", "no");
|
||||
|
||||
//set custom input hidden value
|
||||
const newValue = checkboxEl.getAttribute("value");
|
||||
newValue === "yes"
|
||||
? checkboxEl.setAttribute("aria-checked", "true")
|
||||
: checkboxEl.setAttribute("aria-checked", "false");
|
||||
|
||||
//force checked for submit
|
||||
checkboxEl.checked = true;
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
class Select {
|
||||
constructor() {
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
window.addEventListener("click", (e) => {
|
||||
//CASE NO BTN SELECT CLICKED
|
||||
try {
|
||||
if (!e.target.closest("button")) {
|
||||
const selectEls = document.querySelectorAll(
|
||||
"div[data-setting-select-dropdown]",
|
||||
);
|
||||
selectEls.forEach((select) => {
|
||||
select.classList.add("hidden");
|
||||
select.classList.remove("flex");
|
||||
});
|
||||
const btnEls = document.querySelectorAll(
|
||||
"button[data-setting-select]",
|
||||
);
|
||||
btnEls.forEach((btn) => {
|
||||
const dropdownChevron = btn.querySelector(
|
||||
`svg[data-setting-select]`,
|
||||
);
|
||||
dropdownChevron.classList.remove("rotate-180");
|
||||
});
|
||||
}
|
||||
} catch (err) {}
|
||||
//SELECT BTN LOGIC
|
||||
try {
|
||||
if (
|
||||
e.target.closest("button").hasAttribute(`data-setting-select`) &&
|
||||
!e.target.closest("button").hasAttribute(`disabled`)
|
||||
) {
|
||||
const btnEl = e.target.closest("button");
|
||||
this.toggleSelectBtn(btnEl);
|
||||
}
|
||||
} catch (err) {}
|
||||
//SELECT DROPDOWN BTN LOGIC
|
||||
try {
|
||||
if (
|
||||
e.target
|
||||
.closest("button")
|
||||
.hasAttribute(`data-setting-select-dropdown-btn`)
|
||||
) {
|
||||
const btn = e.target.closest(
|
||||
`button[data-setting-select-dropdown-btn]`,
|
||||
);
|
||||
const btnValue = btn.getAttribute("value");
|
||||
|
||||
//add new value to custom
|
||||
const selectCustom = btn
|
||||
.closest("div[data-select-container]")
|
||||
.querySelector(`button[data-setting-select]`);
|
||||
|
||||
selectCustom.querySelector(`[data-setting-select-text]`).textContent =
|
||||
btnValue;
|
||||
//add selected to new value
|
||||
|
||||
//change style
|
||||
const dropdownEl = btn.closest(`div[data-setting-select-dropdown]`);
|
||||
dropdownEl.classList.add("hidden");
|
||||
dropdownEl.classList.remove("flex");
|
||||
|
||||
//reset dropdown btns
|
||||
const btnEls = dropdownEl.querySelectorAll("button");
|
||||
|
||||
btnEls.forEach((btn) => {
|
||||
btn.classList.remove("active");
|
||||
});
|
||||
//highlight clicked btn
|
||||
btn.classList.add("active");
|
||||
|
||||
//close dropdown
|
||||
const dropdownChevron = selectCustom.querySelector(
|
||||
`svg[data-setting-select]`,
|
||||
);
|
||||
dropdownChevron.classList.remove("rotate-180");
|
||||
|
||||
//update real select element
|
||||
const realSel = btn
|
||||
.closest("div[data-setting-container]")
|
||||
.querySelector("select");
|
||||
this.updateSelected(realSel, btnValue);
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
|
||||
updateSelected(selectEl, selectedValue) {
|
||||
const options = selectEl.querySelectorAll("option");
|
||||
//remove selected to all
|
||||
options.forEach((option) => {
|
||||
option.removeAttribute("selected");
|
||||
option.selected = false;
|
||||
});
|
||||
//select new one
|
||||
const newOption = selectEl.querySelector(
|
||||
`option[value="${selectedValue}"]`,
|
||||
);
|
||||
newOption.selected = true;
|
||||
newOption.setAttribute("selected", "");
|
||||
}
|
||||
|
||||
toggleSelectBtn(btn) {
|
||||
//toggle dropdown
|
||||
const dropdownEl = btn
|
||||
.closest("div")
|
||||
.querySelector(`[data-setting-select-dropdown]`);
|
||||
const dropdownChevron = btn.querySelector(`svg[data-setting-select]`);
|
||||
dropdownEl.classList.toggle("hidden");
|
||||
dropdownEl.classList.toggle("flex");
|
||||
dropdownChevron.classList.toggle("rotate-180");
|
||||
}
|
||||
}
|
||||
|
||||
class Password {
|
||||
constructor() {
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
window.addEventListener("click", (e) => {
|
||||
try {
|
||||
if (e.target.closest("button").hasAttribute("data-setting-password")) {
|
||||
const btn = e.target.closest("button");
|
||||
const action = btn.getAttribute("data-setting-password");
|
||||
const inp = btn
|
||||
.closest("[data-setting-container]")
|
||||
.querySelector("input");
|
||||
this.setValDisplay(action, inp);
|
||||
this.hiddenBtns(btn);
|
||||
this.showOppositeBtn(btn, action);
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
|
||||
showOppositeBtn(btnEl, action) {
|
||||
const btnEls = this.getBtns(btnEl);
|
||||
const opposite = action === "visible" ? "invisible" : "visible";
|
||||
|
||||
btnEls.forEach((btn) => {
|
||||
const action = btn.getAttribute("data-setting-password");
|
||||
|
||||
if (action === opposite) {
|
||||
btn.classList.add("flex");
|
||||
btn.classList.remove("hidden");
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
setValDisplay(action, inp) {
|
||||
if (action === "visible") inp.setAttribute("type", "text");
|
||||
if (action === "invisible") inp.setAttribute("type", "password");
|
||||
}
|
||||
|
||||
hiddenBtns(btnEl) {
|
||||
const btnEls = this.getBtns(btnEl);
|
||||
|
||||
btnEls.forEach((btn) => {
|
||||
btn.classList.add("hidden");
|
||||
btn.classList.remove("flex");
|
||||
});
|
||||
}
|
||||
|
||||
getBtns(btnEl) {
|
||||
return btnEl
|
||||
.closest("[data-setting-container]")
|
||||
.querySelectorAll("button[data-setting-password]");
|
||||
}
|
||||
}
|
||||
|
||||
class DisabledPop {
|
||||
constructor() {
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
window.addEventListener("pointerover", (e) => {
|
||||
//for checkbox and regular inputs
|
||||
if (e.target.tagName === "INPUT") {
|
||||
const el = e.target;
|
||||
this.showPopup(el, "input");
|
||||
}
|
||||
//for select custom
|
||||
if (
|
||||
e.target.tagName === "BUTTON" &&
|
||||
e.target.hasAttribute("data-setting-select")
|
||||
) {
|
||||
const el = e.target;
|
||||
this.showPopup(el, "select");
|
||||
}
|
||||
});
|
||||
|
||||
window.addEventListener("pointerout", (e) => {
|
||||
try {
|
||||
const popupEl = e.target
|
||||
.closest("div")
|
||||
.querySelector("div[data-disabled-info]");
|
||||
popupEl.remove();
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
|
||||
showPopup(el, type = "input") {
|
||||
if (!el.hasAttribute("disabled")) return;
|
||||
const method = el.getAttribute("data-default-method");
|
||||
const popupHTML = `
|
||||
<div data-disabled-info class="${
|
||||
type === "select" ? "translate-y-2" : ""
|
||||
} bg-blue-500 absolute right-2 rounded-lg px-2 py-1 z-20 dark:brightness-90">
|
||||
<p class="m-0 text-xs text-white dark:text-gray-100">disabled by ${method}</p>
|
||||
</div>`;
|
||||
el.insertAdjacentHTML("beforebegin", popupHTML);
|
||||
}
|
||||
}
|
||||
|
||||
export { Checkbox, Select, Password, DisabledPop };
|
||||
|
|
|
@ -1,239 +1,239 @@
|
|||
class Popover {
|
||||
constructor() {
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
window.addEventListener("pointerover", (e) => {
|
||||
//POPOVER LOGIC
|
||||
try {
|
||||
if (e.target.closest("svg").hasAttribute(`data-popover-btn`)) {
|
||||
this.showPopover(e.target);
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
|
||||
window.addEventListener("pointerout", (e) => {
|
||||
//POPOVER LOGIC
|
||||
try {
|
||||
if (e.target.closest("svg").hasAttribute(`data-popover-btn`)) {
|
||||
this.hidePopover(e.target);
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
|
||||
showPopover(el) {
|
||||
const btn = el.closest("svg");
|
||||
//toggle curr popover
|
||||
const popover = btn.parentElement.querySelector(`[data-popover-content]`);
|
||||
popover.classList.remove("hidden");
|
||||
}
|
||||
|
||||
hidePopover(el) {
|
||||
const btn = el.closest("svg");
|
||||
//toggle curr popover
|
||||
const popover = btn.parentElement.querySelector(`[data-popover-content]`);
|
||||
popover.classList.add("hidden");
|
||||
}
|
||||
}
|
||||
|
||||
class Tabs {
|
||||
constructor() {
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
window.addEventListener("click", (e) => {
|
||||
try {
|
||||
if (
|
||||
e.target.closest("button").hasAttribute("data-tab-handler") ||
|
||||
e.target.closest("button").hasAttribute("data-tab-handler-mobile")
|
||||
) {
|
||||
//get needed data
|
||||
const tab = e.target.closest("button");
|
||||
const tabAtt =
|
||||
tab.getAttribute("data-tab-handler") ||
|
||||
tab.getAttribute("data-tab-handler-mobile");
|
||||
const container = tab.closest("div[data-service-content]");
|
||||
// change style
|
||||
this.resetTabsStyle(container);
|
||||
this.highlightClicked(container, tabAtt);
|
||||
//show content
|
||||
this.hideAllSettings(container);
|
||||
this.showSettingClicked(container, tabAtt);
|
||||
//close dropdown and change btn textcontent on mobile
|
||||
this.setDropBtnText(container, tabAtt);
|
||||
this.closeDropdown(container);
|
||||
}
|
||||
} catch (err) {}
|
||||
|
||||
try {
|
||||
if (e.target.closest("button").hasAttribute("data-tab-dropdown-btn")) {
|
||||
const dropBtn = e.target.closest("button");
|
||||
const container = dropBtn.closest("div[data-service-content]");
|
||||
this.toggleDropdown(container);
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
|
||||
resetTabsStyle(container) {
|
||||
//reset desktop style
|
||||
const tabsDesktop = container.querySelectorAll("button[data-tab-handler]");
|
||||
tabsDesktop.forEach((tab) => {
|
||||
tab.classList.remove("active");
|
||||
});
|
||||
//reset mobile style
|
||||
const tabsMobile = container.querySelectorAll(
|
||||
"button[data-tab-handler-mobile]"
|
||||
);
|
||||
tabsMobile.forEach((tab) => {
|
||||
tab.classList.remove("active");
|
||||
});
|
||||
}
|
||||
|
||||
highlightClicked(container, tabAtt) {
|
||||
//desktop case
|
||||
const tabDesktop = container.querySelector(
|
||||
`button[data-tab-handler='${tabAtt}']`
|
||||
);
|
||||
tabDesktop.classList.add("active");
|
||||
|
||||
//mobile case
|
||||
const tabMobile = container.querySelector(
|
||||
`button[data-tab-handler-mobile='${tabAtt}']`
|
||||
);
|
||||
tabMobile.classList.add("active");
|
||||
}
|
||||
|
||||
hideAllSettings(container) {
|
||||
const plugins = container.querySelectorAll("[data-plugin-item]");
|
||||
plugins.forEach((plugin) => {
|
||||
plugin.classList.add("hidden");
|
||||
});
|
||||
}
|
||||
|
||||
showSettingClicked(container, tabAtt) {
|
||||
const plugin = container.querySelector(`[data-plugin-item='${tabAtt}']`);
|
||||
plugin.classList.remove("hidden");
|
||||
}
|
||||
|
||||
setDropBtnText(container, tabAtt) {
|
||||
const dropBtn = container.querySelector("[data-tab-dropdown-btn]");
|
||||
dropBtn.querySelector("span").textContent = tabAtt;
|
||||
}
|
||||
|
||||
closeDropdown(container) {
|
||||
const dropdown = container.querySelector("[data-tab-dropdown]");
|
||||
dropdown.classList.add("hidden");
|
||||
dropdown.classList.remove("flex");
|
||||
}
|
||||
|
||||
toggleDropdown(container) {
|
||||
const dropdown = container.querySelector("[data-tab-dropdown]");
|
||||
dropdown.classList.toggle("hidden");
|
||||
dropdown.classList.toggle("flex");
|
||||
}
|
||||
}
|
||||
|
||||
class FormatValue {
|
||||
constructor() {
|
||||
this.inputs = document.querySelectorAll("input");
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
this.inputs.forEach((inp) => {
|
||||
try {
|
||||
inp.setAttribute("value", inp.getAttribute("value").trim());
|
||||
inp.value = inp.value.trim();
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
class FilterSettings {
|
||||
constructor(inputID, container) {
|
||||
this.input = document.querySelector(`input#${inputID}`);
|
||||
//DESKTOP
|
||||
this.container = document.querySelector(container);
|
||||
this.deskTabs = this.container.querySelectorAll(`[data-tab-handler]`);
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
this.input.addEventListener("input", () => {
|
||||
this.resetFilter();
|
||||
//get inp format
|
||||
const inpValue = this.input.value.trim().toLowerCase();
|
||||
//loop all tabs
|
||||
this.deskTabs.forEach((tab) => {
|
||||
//get settings of tabs except multiples
|
||||
const settings = this.getSettingsFromTab(tab);
|
||||
|
||||
//compare total count to currCount to determine
|
||||
//if tabs need to be hidden
|
||||
const settingCount = settings.length;
|
||||
let hiddenCount = 0;
|
||||
settings.forEach((setting) => {
|
||||
try {
|
||||
const title = setting
|
||||
.querySelector("h5")
|
||||
.textContent.trim()
|
||||
.toLowerCase();
|
||||
if (!title.includes(inpValue)) {
|
||||
setting.classList.add("hidden");
|
||||
hiddenCount++;
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
//case no setting match, hidden tab and content
|
||||
if (settingCount === hiddenCount) {
|
||||
const tabName = tab.getAttribute(`data-tab-handler`);
|
||||
//hide mobile and desk tabs
|
||||
tab.classList.add("hidden");
|
||||
this.container
|
||||
.querySelector(`[data-tab-handler-mobile="${tabName}"]`)
|
||||
.classList.add("hidden");
|
||||
this.container
|
||||
.querySelector(`[data-plugin-item=${tabName}]`)
|
||||
.querySelector("[data-setting-header]")
|
||||
.classList.add("hidden");
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
resetFilter() {
|
||||
this.deskTabs.forEach((tab) => {
|
||||
const tabName = tab.getAttribute(`data-tab-handler`);
|
||||
//hide mobile and desk tabs
|
||||
tab.classList.remove("hidden");
|
||||
this.container
|
||||
.querySelector(`[data-tab-handler-mobile="${tabName}"]`)
|
||||
.classList.remove("hidden");
|
||||
this.container
|
||||
.querySelector(`[data-plugin-item=${tabName}]`)
|
||||
.querySelector("[data-setting-header]")
|
||||
.classList.remove("hidden");
|
||||
const settings = this.getSettingsFromTab(tab);
|
||||
settings.forEach((setting) => {
|
||||
setting.classList.remove("hidden");
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
getSettingsFromTab(tabEl) {
|
||||
const tabName = tabEl.getAttribute(`data-tab-handler`);
|
||||
const settingContainer = this.container
|
||||
.querySelector(`[data-plugin-item="${tabName}"]`)
|
||||
.querySelector(`[data-plugin-settings]`);
|
||||
const settings = settingContainer.querySelectorAll(
|
||||
"[data-setting-container]"
|
||||
);
|
||||
return settings;
|
||||
}
|
||||
}
|
||||
|
||||
export { Popover, Tabs, FormatValue, FilterSettings };
|
||||
class Popover {
|
||||
constructor() {
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
window.addEventListener("pointerover", (e) => {
|
||||
//POPOVER LOGIC
|
||||
try {
|
||||
if (e.target.closest("svg").hasAttribute(`data-popover-btn`)) {
|
||||
this.showPopover(e.target);
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
|
||||
window.addEventListener("pointerout", (e) => {
|
||||
//POPOVER LOGIC
|
||||
try {
|
||||
if (e.target.closest("svg").hasAttribute(`data-popover-btn`)) {
|
||||
this.hidePopover(e.target);
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
|
||||
showPopover(el) {
|
||||
const btn = el.closest("svg");
|
||||
//toggle curr popover
|
||||
const popover = btn.parentElement.querySelector(`[data-popover-content]`);
|
||||
popover.classList.remove("hidden");
|
||||
}
|
||||
|
||||
hidePopover(el) {
|
||||
const btn = el.closest("svg");
|
||||
//toggle curr popover
|
||||
const popover = btn.parentElement.querySelector(`[data-popover-content]`);
|
||||
popover.classList.add("hidden");
|
||||
}
|
||||
}
|
||||
|
||||
class Tabs {
|
||||
constructor() {
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
window.addEventListener("click", (e) => {
|
||||
try {
|
||||
if (
|
||||
e.target.closest("button").hasAttribute("data-tab-handler") ||
|
||||
e.target.closest("button").hasAttribute("data-tab-handler-mobile")
|
||||
) {
|
||||
//get needed data
|
||||
const tab = e.target.closest("button");
|
||||
const tabAtt =
|
||||
tab.getAttribute("data-tab-handler") ||
|
||||
tab.getAttribute("data-tab-handler-mobile");
|
||||
const container = tab.closest("div[data-service-content]");
|
||||
// change style
|
||||
this.resetTabsStyle(container);
|
||||
this.highlightClicked(container, tabAtt);
|
||||
//show content
|
||||
this.hideAllSettings(container);
|
||||
this.showSettingClicked(container, tabAtt);
|
||||
//close dropdown and change btn textcontent on mobile
|
||||
this.setDropBtnText(container, tabAtt);
|
||||
this.closeDropdown(container);
|
||||
}
|
||||
} catch (err) {}
|
||||
|
||||
try {
|
||||
if (e.target.closest("button").hasAttribute("data-tab-dropdown-btn")) {
|
||||
const dropBtn = e.target.closest("button");
|
||||
const container = dropBtn.closest("div[data-service-content]");
|
||||
this.toggleDropdown(container);
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
|
||||
resetTabsStyle(container) {
|
||||
//reset desktop style
|
||||
const tabsDesktop = container.querySelectorAll("button[data-tab-handler]");
|
||||
tabsDesktop.forEach((tab) => {
|
||||
tab.classList.remove("active");
|
||||
});
|
||||
//reset mobile style
|
||||
const tabsMobile = container.querySelectorAll(
|
||||
"button[data-tab-handler-mobile]",
|
||||
);
|
||||
tabsMobile.forEach((tab) => {
|
||||
tab.classList.remove("active");
|
||||
});
|
||||
}
|
||||
|
||||
highlightClicked(container, tabAtt) {
|
||||
//desktop case
|
||||
const tabDesktop = container.querySelector(
|
||||
`button[data-tab-handler='${tabAtt}']`,
|
||||
);
|
||||
tabDesktop.classList.add("active");
|
||||
|
||||
//mobile case
|
||||
const tabMobile = container.querySelector(
|
||||
`button[data-tab-handler-mobile='${tabAtt}']`,
|
||||
);
|
||||
tabMobile.classList.add("active");
|
||||
}
|
||||
|
||||
hideAllSettings(container) {
|
||||
const plugins = container.querySelectorAll("[data-plugin-item]");
|
||||
plugins.forEach((plugin) => {
|
||||
plugin.classList.add("hidden");
|
||||
});
|
||||
}
|
||||
|
||||
showSettingClicked(container, tabAtt) {
|
||||
const plugin = container.querySelector(`[data-plugin-item='${tabAtt}']`);
|
||||
plugin.classList.remove("hidden");
|
||||
}
|
||||
|
||||
setDropBtnText(container, tabAtt) {
|
||||
const dropBtn = container.querySelector("[data-tab-dropdown-btn]");
|
||||
dropBtn.querySelector("span").textContent = tabAtt;
|
||||
}
|
||||
|
||||
closeDropdown(container) {
|
||||
const dropdown = container.querySelector("[data-tab-dropdown]");
|
||||
dropdown.classList.add("hidden");
|
||||
dropdown.classList.remove("flex");
|
||||
}
|
||||
|
||||
toggleDropdown(container) {
|
||||
const dropdown = container.querySelector("[data-tab-dropdown]");
|
||||
dropdown.classList.toggle("hidden");
|
||||
dropdown.classList.toggle("flex");
|
||||
}
|
||||
}
|
||||
|
||||
class FormatValue {
|
||||
constructor() {
|
||||
this.inputs = document.querySelectorAll("input");
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
this.inputs.forEach((inp) => {
|
||||
try {
|
||||
inp.setAttribute("value", inp.getAttribute("value").trim());
|
||||
inp.value = inp.value.trim();
|
||||
} catch (err) {}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
class FilterSettings {
|
||||
constructor(inputID, container) {
|
||||
this.input = document.querySelector(`input#${inputID}`);
|
||||
//DESKTOP
|
||||
this.container = document.querySelector(container);
|
||||
this.deskTabs = this.container.querySelectorAll(`[data-tab-handler]`);
|
||||
this.init();
|
||||
}
|
||||
|
||||
init() {
|
||||
this.input.addEventListener("input", () => {
|
||||
this.resetFilter();
|
||||
//get inp format
|
||||
const inpValue = this.input.value.trim().toLowerCase();
|
||||
//loop all tabs
|
||||
this.deskTabs.forEach((tab) => {
|
||||
//get settings of tabs except multiples
|
||||
const settings = this.getSettingsFromTab(tab);
|
||||
|
||||
//compare total count to currCount to determine
|
||||
//if tabs need to be hidden
|
||||
const settingCount = settings.length;
|
||||
let hiddenCount = 0;
|
||||
settings.forEach((setting) => {
|
||||
try {
|
||||
const title = setting
|
||||
.querySelector("h5")
|
||||
.textContent.trim()
|
||||
.toLowerCase();
|
||||
if (!title.includes(inpValue)) {
|
||||
setting.classList.add("hidden");
|
||||
hiddenCount++;
|
||||
}
|
||||
} catch (err) {}
|
||||
});
|
||||
//case no setting match, hidden tab and content
|
||||
if (settingCount === hiddenCount) {
|
||||
const tabName = tab.getAttribute(`data-tab-handler`);
|
||||
//hide mobile and desk tabs
|
||||
tab.classList.add("hidden");
|
||||
this.container
|
||||
.querySelector(`[data-tab-handler-mobile="${tabName}"]`)
|
||||
.classList.add("hidden");
|
||||
this.container
|
||||
.querySelector(`[data-plugin-item=${tabName}]`)
|
||||
.querySelector("[data-setting-header]")
|
||||
.classList.add("hidden");
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
resetFilter() {
|
||||
this.deskTabs.forEach((tab) => {
|
||||
const tabName = tab.getAttribute(`data-tab-handler`);
|
||||
//hide mobile and desk tabs
|
||||
tab.classList.remove("hidden");
|
||||
this.container
|
||||
.querySelector(`[data-tab-handler-mobile="${tabName}"]`)
|
||||
.classList.remove("hidden");
|
||||
this.container
|
||||
.querySelector(`[data-plugin-item=${tabName}]`)
|
||||
.querySelector("[data-setting-header]")
|
||||
.classList.remove("hidden");
|
||||
const settings = this.getSettingsFromTab(tab);
|
||||
settings.forEach((setting) => {
|
||||
setting.classList.remove("hidden");
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
getSettingsFromTab(tabEl) {
|
||||
const tabName = tabEl.getAttribute(`data-tab-handler`);
|
||||
const settingContainer = this.container
|
||||
.querySelector(`[data-plugin-item="${tabName}"]`)
|
||||
.querySelector(`[data-plugin-settings]`);
|
||||
const settings = settingContainer.querySelectorAll(
|
||||
"[data-setting-container]",
|
||||
);
|
||||
return settings;
|
||||
}
|
||||
}
|
||||
|
||||
export { Popover, Tabs, FormatValue, FilterSettings };
|
||||
|
|
3
src/ui/static/webfonts/bootstrap-icons.css
vendored
3
src/ui/static/webfonts/bootstrap-icons.css
vendored
|
@ -1,6 +1,7 @@
|
|||
@font-face {
|
||||
font-family: "bootstrap-icons";
|
||||
src: url("./bootstrap-icons.woff2?524846017b983fc8ded9325d94ed40f3")
|
||||
src:
|
||||
url("./bootstrap-icons.woff2?524846017b983fc8ded9325d94ed40f3")
|
||||
format("woff2"),
|
||||
url("./bootstrap-icons.woff?524846017b983fc8ded9325d94ed40f3")
|
||||
format("woff");
|
||||
|
|
Loading…
Reference in a new issue