mypgs 1.1.5 → 1.3.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,25 @@
1
+ import { pgs } from "./_pgs.js";
2
+
3
+ import { PGS_accordion } from "./components/_accordion.js";
4
+ import { PGS_dropdown } from "./components/_dropdown.js";
5
+ import { PGS_menu } from "./components/_menu.js";
6
+ import { PGS_modal } from "./components/_modals.js";
7
+ import { PGS_notification } from "./components/_notifications.js";
8
+ import { PGS_slides } from "./components/_slides.js";
9
+ import { PGS_stepTabs } from "./components/_stepTabs.js";
10
+ import { PGS_steps } from "./components/_steps.js";
11
+ import { PGS_formValidate } from "./functions/_formValidate.js";
12
+ import { PGS_scrollHorizontal } from "./functions/_scrollY.js";
13
+
14
+ pgs.registerImport({
15
+ PGS_accordion,
16
+ PGS_dropdown,
17
+ PGS_menu,
18
+ PGS_modal,
19
+ PGS_notification,
20
+ PGS_slides,
21
+ PGS_stepTabs,
22
+ PGS_steps,
23
+ PGS_formValidate,
24
+ PGS_scrollHorizontal,
25
+ });
@@ -224,6 +224,42 @@ export function pgs(root) {
224
224
  return api;
225
225
  }
226
226
 
227
- globalThis.pgs ??= pgs;
227
+ const PGS_IMPORTS = {};
228
+
229
+ function registerImportModule(name, module) {
230
+ const key = String(name || "").trim().replace(/^pgs[_-\s]*/i, "").toLowerCase();
228
231
 
232
+ if (!key) throw new TypeError("pgs.registerImport(...modules): ogni modulo deve avere name o PGS_name");
233
+
234
+ PGS_IMPORTS[key] = {
235
+ name,
236
+ module
237
+ };
238
+ }
239
+
240
+ pgs.registerImport = function (...modules) {
241
+ modules.flat().forEach(item => {
242
+ if (item && typeof item === "object" && !item.PGS_name && !item.name) {
243
+ Object.entries(item).forEach(([name, module]) => registerImportModule(name, module));
244
+ return;
245
+ }
229
246
 
247
+ registerImportModule(item?.PGS_name || item?.name, item);
248
+ });
249
+
250
+ return pgs;
251
+ };
252
+
253
+ pgs.import = function (...names) {
254
+ return names.flat().reduce((imports, name) => {
255
+ const key = String(name || "").trim().replace(/^pgs[_-\s]*/i, "").toLowerCase();
256
+ const item = PGS_IMPORTS[key];
257
+
258
+ if (!item) throw new Error(`pgs.import(): modulo "${name}" non registrato`);
259
+
260
+ imports[item.name] = item.module;
261
+ return imports;
262
+ }, {});
263
+ };
264
+
265
+ globalThis.pgs ??= pgs;
@@ -1,77 +1,116 @@
1
- //= ACCORDION
2
- const allAccordion = pgs(document).querySelectorAll("accordion")
3
-
4
- allAccordion.forEach((accordion, index) => {
5
-
6
- const BUTTON = pgs(accordion).querySelector("accordion-button");
7
- const CONTENT = pgs(accordion).querySelector("accordion-content");
8
-
9
- //== ID univoci per aria-controls / aria-labelledby
10
- const ID = index + 1;
11
- const btnId = `acc-btn-${ID}`;
12
- const panelId = `acc-panel-${ID}`;
13
-
14
- //== Stato iniziale
15
- const isOpenInit = pgs(accordion).state.contains("open");
16
-
17
- //== Accessibilità (setup una volta)
18
- BUTTON.setAttribute("role", "button");
19
- BUTTON.setAttribute("tabindex", "0");
20
- BUTTON.setAttribute("id", btnId);
21
- BUTTON.setAttribute("aria-controls", panelId);
22
-
23
- CONTENT.setAttribute("id", panelId);
24
- CONTENT.setAttribute("role", "region");
25
- CONTENT.setAttribute("aria-labelledby", btnId);
26
-
27
- //+ Accessibility (applica stato aperto/chiuso)
28
- function accordionAccessibility(isOpen, button, content) {
29
- const text = (button?.textContent || "").trim().replace(/\s+/g, " ");
30
- button.setAttribute("aria-label", `${isOpen ? "Chiudi" : "Apri"} ${text || "sezione"}`);
31
- button.setAttribute("aria-expanded", String(isOpen));
32
- content.hidden = !isOpen;
33
- }
34
-
35
- //+ Chiudi tutti gli altri
36
- function closeOltherAccordion() {
37
- for (const otherLi of allAccordion) {
38
- if (otherLi === accordion) continue;
39
-
40
- const otherBtn = pgs(otherLi).querySelector("accordion-button");
41
- const otherContent = pgs(otherLi).querySelector("accordion-content");
42
- if (!otherBtn || !otherContent) continue;
43
-
44
- pgs(otherLi).state().remove("open");
45
- accordionAccessibility(false, otherBtn, otherContent);
1
+ //= ACCORDION
2
+ const API = new WeakMap();
3
+
4
+ export function PGS_accordion_init(root = document) {
5
+ pgs(root).querySelectorAll("accordion").forEach((accordion, index) => {
6
+ if (API.has(accordion)) return;
7
+
8
+ const BUTTON = pgs(accordion).querySelector("accordion-button");
9
+ const CONTENT = pgs(accordion).querySelector("accordion-content");
10
+ if (!BUTTON || !CONTENT) return;
11
+
12
+ //== ID univoci per aria-controls / aria-labelledby
13
+ const ID = index + 1;
14
+ const btnId = `acc-btn-${ID}`;
15
+ const panelId = `acc-panel-${ID}`;
16
+
17
+ //== Stato iniziale
18
+ const isOpenInit = pgs(accordion).state.contains("open");
19
+
20
+ //== Accessibilità (setup una volta)
21
+ BUTTON.setAttribute("role", "button");
22
+ BUTTON.setAttribute("tabindex", "0");
23
+ BUTTON.setAttribute("id", btnId);
24
+ BUTTON.setAttribute("aria-controls", panelId);
25
+
26
+ CONTENT.setAttribute("id", panelId);
27
+ CONTENT.setAttribute("role", "region");
28
+ CONTENT.setAttribute("aria-labelledby", btnId);
29
+
30
+ //+ Accessibility (applica stato aperto/chiuso)
31
+ function accordionAccessibility(isOpen, button, content) {
32
+ const text = (button?.textContent || "").trim().replace(/\s+/g, " ");
33
+ button.setAttribute("aria-label", `${isOpen ? "Chiudi" : "Apri"} ${text || "sezione"}`);
34
+ button.setAttribute("aria-expanded", String(isOpen));
35
+ content.hidden = !isOpen;
46
36
  }
47
- }
48
37
 
49
- //+ FN ACCORDION
50
- function accordionFunction() {
51
- const isOpen = pgs(accordion).state.contains("open");
52
- const nowOpen = !isOpen;
38
+ //+ Chiudi tutti gli altri
39
+ function closeOltherAccordion() {
40
+ for (const otherLi of pgs(document).querySelectorAll("accordion")) {
41
+ if (otherLi === accordion) continue;
53
42
 
54
- pgs(accordion).state.toggle("open", nowOpen);
55
- accordionAccessibility(nowOpen, BUTTON, CONTENT);
43
+ const otherBtn = pgs(otherLi).querySelector("accordion-button");
44
+ const otherContent = pgs(otherLi).querySelector("accordion-content");
45
+ if (!otherBtn || !otherContent) continue;
56
46
 
57
- closeOltherAccordion();
47
+ pgs(otherLi).state().remove("open");
48
+ accordionAccessibility(false, otherBtn, otherContent);
49
+ }
50
+ }
51
+
52
+ //+ FN ACCORDION
53
+ function accordionFunction() {
54
+ const isOpen = pgs(accordion).state.contains("open");
55
+ const nowOpen = !isOpen;
58
56
 
59
- //== scroll to view
60
- if (nowOpen) setTimeout(() => accordion.scrollIntoView({ block: "nearest", inline: "nearest" }), 100);
61
- }
57
+ pgs(accordion).state.toggle("open", nowOpen);
58
+ accordionAccessibility(nowOpen, BUTTON, CONTENT);
62
59
 
63
- // applica stato iniziale
64
- accordionAccessibility(isOpenInit, BUTTON, CONTENT);
60
+ closeOltherAccordion();
61
+
62
+ //== scroll to view
63
+ if (nowOpen) setTimeout(() => accordion.scrollIntoView({ block: "nearest", inline: "nearest" }), 100);
64
+ }
65
65
 
66
- //- Eventi
67
- BUTTON.addEventListener("click", accordionFunction);
66
+ function open() {
67
+ if (!pgs(accordion).state.contains("open")) accordionFunction();
68
+ }
68
69
 
69
- //- Tastiera: Enter / Space
70
- BUTTON.addEventListener("keydown", (e) => {
71
- if (e.key === "Enter" || e.key === " ") {
72
- e.preventDefault();
73
- accordionFunction();
70
+ function close() {
71
+ if (pgs(accordion).state.contains("open")) accordionFunction();
74
72
  }
73
+
74
+ // applica stato iniziale
75
+ accordionAccessibility(isOpenInit, BUTTON, CONTENT);
76
+
77
+ //- Eventi
78
+ BUTTON.addEventListener("click", accordionFunction);
79
+
80
+ //- Tastiera: Enter / Space
81
+ BUTTON.addEventListener("keydown", (e) => {
82
+ if (e.key === "Enter" || e.key === " ") {
83
+ e.preventDefault();
84
+ accordionFunction();
85
+ }
86
+ });
87
+
88
+ API.set(accordion, {
89
+ element: accordion,
90
+ button: BUTTON,
91
+ content: CONTENT,
92
+ open,
93
+ close,
94
+ toggle: accordionFunction,
95
+ refresh: () => {
96
+ PGS_accordion_init(accordion.parentNode || document);
97
+ return API.get(accordion);
98
+ },
99
+ isOpen: () => pgs(accordion).state.contains("open"),
100
+ });
75
101
  });
102
+ }
103
+
104
+ //# INIT
105
+ PGS_accordion_init();
106
+
107
+ //# API
108
+ export function PGS_accordion_api(selector) {
109
+ return API.get(selector);
110
+ }
76
111
 
77
- });
112
+ export const PGS_accordion = {
113
+ PGS_name: "PGS_accordion",
114
+ init: PGS_accordion_init,
115
+ api: PGS_accordion_api
116
+ };
@@ -1,6 +1,10 @@
1
1
  // + dropdown (Popover API)
2
- export function pgs_dropdown() {
3
- pgs(document).querySelectorAll("dropdown").forEach((DROPDOWN, index) => {
2
+ const API = new WeakMap();
3
+
4
+ export function PGS_dropdown_init(root = document) {
5
+ pgs(root).querySelectorAll("dropdown").forEach((DROPDOWN, index) => {
6
+ if (API.has(DROPDOWN)) return;
7
+
4
8
  const BUTTON = pgs(DROPDOWN).querySelector("dropdown-button");
5
9
  const CONTENT = pgs(DROPDOWN).querySelector("dropdown-content");
6
10
 
@@ -101,8 +105,49 @@ export function pgs_dropdown() {
101
105
  window.addEventListener("scroll", () => {
102
106
  if (CONTENT.matches(":popover-open")) updatePopoverPosition();
103
107
  }, true);
108
+
109
+ function open() {
110
+ if (CONTENT.matches(":popover-open")) return;
111
+ updatePopoverPosition();
112
+ CONTENT.showPopover();
113
+ }
114
+
115
+ function close() {
116
+ if (!CONTENT.matches(":popover-open")) return;
117
+ CONTENT.hidePopover();
118
+ }
119
+
120
+ function toggle() {
121
+ CONTENT.matches(":popover-open") ? close() : open();
122
+ }
123
+
124
+ API.set(DROPDOWN, {
125
+ element: DROPDOWN,
126
+ button: BUTTON,
127
+ content: CONTENT,
128
+ open,
129
+ close,
130
+ toggle,
131
+ updatePosition: updatePopoverPosition,
132
+ refresh: () => {
133
+ PGS_dropdown_init(DROPDOWN.parentNode || document);
134
+ return API.get(DROPDOWN);
135
+ },
136
+ isOpen: () => CONTENT.matches(":popover-open"),
137
+ });
104
138
  });
105
139
  }
106
140
 
107
141
  // # INIT
108
- pgs_dropdown();
142
+ PGS_dropdown_init();
143
+
144
+ // # API
145
+ export function PGS_dropdown_api(selector) {
146
+ return API.get(selector);
147
+ }
148
+
149
+ export const PGS_dropdown = {
150
+ PGS_name: "PGS_dropdown",
151
+ init: PGS_dropdown_init,
152
+ api: PGS_dropdown_api
153
+ };
@@ -1,13 +1,17 @@
1
- import { pgs_dropdown } from "./_dropdown";
1
+ import { PGS_dropdown_init, PGS_dropdown_api } from "./_dropdown";
2
+
3
+ const API = new WeakMap();
2
4
 
3
5
  //= DROP DOWN MENU
4
- export function PGS_menu() {
6
+ export function PGS_menu_init(root = document) {
5
7
 
6
- pgs(document).querySelectorAll('menu-horizontal').forEach(MENU => {
8
+ pgs(root).querySelectorAll('menu-horizontal').forEach(MENU => {
9
+ if (API.has(MENU)) return;
7
10
 
8
11
  MENU.querySelectorAll('nav > ul > li.menu-item-has-children').forEach(li => {
9
12
  if (li.querySelector("ul")) {
10
13
  const ul = li.querySelector("ul");
14
+ if (pgs(li).querySelector("dropdown-button")) return;
11
15
 
12
16
  const button = document.createElement("button");
13
17
  button.className = "icon-down";
@@ -22,14 +26,28 @@ export function PGS_menu() {
22
26
  pgs(ul).add("menu-vertical")
23
27
  }
24
28
  });
29
+
30
+ API.set(MENU, {
31
+ element: MENU,
32
+ type: "horizontal",
33
+ items: () => Array.from(MENU.querySelectorAll('nav > ul > li')),
34
+ submenus: () => Array.from(MENU.querySelectorAll('.menu-item-has-children > ul')),
35
+ dropdowns: () => Array.from(MENU.querySelectorAll('.menu-item-has-children')).map(PGS_dropdown_api).filter(Boolean),
36
+ refresh: () => {
37
+ PGS_menu_init(MENU.parentNode || document);
38
+ return API.get(MENU);
39
+ },
40
+ });
25
41
  });
26
42
 
27
- pgs(document).querySelectorAll('menu-vertical').forEach(MENU => {
43
+ pgs(root).querySelectorAll('menu-vertical').forEach(MENU => {
44
+ if (API.has(MENU)) return;
28
45
 
29
46
  MENU.querySelectorAll('.menu-item-has-children').forEach((li, index) => {
30
47
  const ul = li.querySelector("ul");
31
48
 
32
49
  if (!ul) return
50
+ if (li.querySelector(":scope > button")) return;
33
51
 
34
52
  const button = document.createElement("button");
35
53
  button.className = "icon-down buttonIcon";
@@ -64,6 +82,42 @@ export function PGS_menu() {
64
82
  });
65
83
  });
66
84
 
85
+ function submenu(index) {
86
+ return MENU.querySelectorAll('.menu-item-has-children > ul')[index];
87
+ }
88
+
89
+ function setSubmenu(index, open) {
90
+ const ul = submenu(index);
91
+ const button = ul?.parentElement?.querySelector(":scope > button");
92
+ if (!ul || !button) return;
93
+
94
+ pgs(ul).state.toggle("open", open);
95
+ button.setAttribute("aria-expanded", String(open));
96
+ button.setAttribute("aria-label", open ? "Chiudi sottomenu" : "Apri sottomenu");
97
+ }
98
+
99
+ API.set(MENU, {
100
+ element: MENU,
101
+ type: "vertical",
102
+ items: () => Array.from(MENU.querySelectorAll(':scope > li')),
103
+ submenus: () => Array.from(MENU.querySelectorAll('.menu-item-has-children > ul')),
104
+ openSubmenu: (index) => setSubmenu(index, true),
105
+ closeSubmenu: (index) => setSubmenu(index, false),
106
+ toggleSubmenu: (index) => {
107
+ const ul = submenu(index);
108
+ if (!ul) return;
109
+ setSubmenu(index, !pgs(ul).state.contains("open"));
110
+ },
111
+ isSubmenuOpen: (index) => {
112
+ const ul = submenu(index);
113
+ return ul ? pgs(ul).state.contains("open") : false;
114
+ },
115
+ refresh: () => {
116
+ PGS_menu_init(MENU.parentNode || document);
117
+ return API.get(MENU);
118
+ },
119
+ });
120
+
67
121
  // pgs(document).querySelectorAll('menu-vertical').forEach(MENU => {
68
122
 
69
123
  // MENU.querySelectorAll('.menu-item-has-children').forEach(li => {
@@ -85,8 +139,19 @@ export function PGS_menu() {
85
139
  // });
86
140
  // });
87
141
  });
88
- pgs_dropdown()
142
+ PGS_dropdown_init()
89
143
  }
90
144
 
91
145
  //# INIT PGS_menu
92
- PGS_menu()
146
+ PGS_menu_init()
147
+
148
+ //# API
149
+ export function PGS_menu_api(selector) {
150
+ return API.get(selector);
151
+ }
152
+
153
+ export const PGS_menu = {
154
+ PGS_name: "PGS_menu",
155
+ init: PGS_menu_init,
156
+ api: PGS_menu_api
157
+ };
@@ -1,7 +1,9 @@
1
1
  //# MODAL
2
- PGS_modal()
3
- export function PGS_modal(selector = "modal") {
2
+ const API = new WeakMap();
3
+
4
+ export function PGS_modal_init(selector = "modal") {
4
5
  pgs(document).querySelectorAll(selector).forEach(MODAL => {
6
+ if (API.has(MODAL)) return;
5
7
 
6
8
  const BUTTON_OPEN = pgs(MODAL).querySelector("modal-button");
7
9
  const DIALOG = MODAL.querySelector("dialog");
@@ -54,9 +56,14 @@ export function PGS_modal(selector = "modal") {
54
56
  //+ FN OPEN
55
57
  function openModal(e) {
56
58
  e?.stopImmediatePropagation();
59
+ if (DIALOG.open) {
60
+ closeModal(e);
61
+ return;
62
+ }
63
+
57
64
  if (!DIALOG.open) document.querySelectorAll("dialog[open]").forEach((dlg) => dlg.close());
58
65
  statusModal(true);
59
- DIALOG.open ? closeModal(e) : topLevel ? DIALOG.showModal() : DIALOG.show();
66
+ topLevel ? DIALOG.showModal() : DIALOG.show();
60
67
  // modalCustomEvents('modal:open', { event: e });
61
68
  MODAL.dispatchEvent(new CustomEvent('modal:open'));
62
69
  DIALOG.dispatchEvent(new CustomEvent('modal:open'));
@@ -72,6 +79,14 @@ export function PGS_modal(selector = "modal") {
72
79
  DIALOG.dispatchEvent(new CustomEvent('modal:close'));
73
80
  }
74
81
 
82
+ function forceOpen(e) {
83
+ if (!DIALOG.open) openModal(e);
84
+ }
85
+
86
+ function forceClose(e) {
87
+ if (DIALOG.open) closeModal(e);
88
+ }
89
+
75
90
  //+ fn OPEN ON HISTORY
76
91
  function openModalOnHistory() {
77
92
  const params = new URLSearchParams(window.location.search);
@@ -117,7 +132,34 @@ export function PGS_modal(selector = "modal") {
117
132
  } catch (_) { }
118
133
  });
119
134
  }
135
+
136
+ API.set(MODAL, {
137
+ element: MODAL,
138
+ button: BUTTON_OPEN,
139
+ dialog: DIALOG,
140
+ closeButton: BUTTON_CLOSE,
141
+ open: forceOpen,
142
+ close: forceClose,
143
+ toggle: openModal,
144
+ refresh: () => {
145
+ PGS_modal_init(selector);
146
+ return API.get(MODAL);
147
+ },
148
+ isOpen: () => DIALOG.open,
149
+ });
120
150
  });
121
151
  }
122
152
 
123
153
  //# INIT PGS_modal
154
+ PGS_modal_init()
155
+
156
+ //# API
157
+ export function PGS_modal_api(selector) {
158
+ return API.get(selector);
159
+ }
160
+
161
+ export const PGS_modal = {
162
+ PGS_name: "PGS_modal",
163
+ init: PGS_modal_init,
164
+ api: PGS_modal_api
165
+ };
@@ -0,0 +1,163 @@
1
+ //= PGS_notification
2
+ const fn_notification = {
3
+ _escapeHtml(value) {
4
+ return String(value ?? "");
5
+ },
6
+
7
+ _getDuration(notification) {
8
+ const rawDuration = notification.duration;
9
+ const duration = Number.parseInt(rawDuration, 10);
10
+
11
+ return Number.isNaN(duration) ? 5000 : duration;
12
+ },
13
+
14
+ _getApi(notification) {
15
+ const element = String(notification.element || "notification").trim();
16
+
17
+ return element === "toast" ? PGS_notification.toast : PGS_notification.alert;
18
+ },
19
+
20
+ _getType(notification, api) {
21
+ const type = String(notification.type || "info").trim();
22
+
23
+ return typeof api[type] === "function" ? type : "info";
24
+ },
25
+
26
+ _getData(root) {
27
+ try {
28
+ return JSON.parse(root.dataset.notification || "{}");
29
+ } catch (error) {
30
+ console.warn("PGS notification: dati non validi", error);
31
+ return {};
32
+ }
33
+ },
34
+
35
+ _getContent(title, content) {
36
+ const safeContent = this._escapeHtml(content);
37
+ const safeTitle = this._escapeHtml(title);
38
+
39
+ if (!safeTitle) return safeContent;
40
+ if (!safeContent) return `<span pgs="notification-element-title">${safeTitle}</span>`;
41
+
42
+ return `
43
+ <span pgs="notification-element-title">${safeTitle}</span>
44
+ <br>
45
+ <span pgs="notification-element-content">${safeContent}</span>
46
+ `;
47
+ },
48
+
49
+ initNotification(type, containerToken, icon, text, timeout, methodDelete = "replace", link = null) {
50
+ let containerNotification = pgs(document).querySelector(containerToken);
51
+
52
+ //== Create Container
53
+ if (!containerNotification) {
54
+ const newContainer = document.createElement("div");
55
+ pgs(newContainer).add(containerToken);
56
+ newContainer.setAttribute("aria-live", "polite");
57
+ newContainer.setAttribute("aria-relevant", "additions");
58
+ document.body.appendChild(newContainer);
59
+ containerNotification = newContainer;
60
+ }
61
+
62
+ //== Create Notification
63
+ const notification = document.createElement(link ? "a" : "div");
64
+ if (methodDelete == "replace") containerNotification.innerHTML = "";
65
+ if (link) notification.href = link;
66
+ if (timeout > 0) notification.style.setProperty("--notification-timeout", timeout + "ms");
67
+ pgs(notification).state.add(type);
68
+ pgs(notification).add("notification-element");
69
+ notification.setAttribute("role", type == "error" ? "alert" : "status")
70
+ notification.innerHTML = `${icon} <p>${text}</p>`;
71
+ containerNotification.appendChild(notification);
72
+
73
+
74
+ //+ Animation delete
75
+ function deleteNotification() {
76
+ methodDelete == "stack" ? notification.style.translate = "120%" : notification.style.opacity = "0";
77
+ setTimeout(() => notification.remove(), 300);
78
+ }
79
+
80
+ //== Timeout delete
81
+ if (timeout > 0) setTimeout(() => { deleteNotification() }, timeout);
82
+
83
+ //== button delete
84
+ const btnDelete = document.createElement("button");
85
+ btnDelete.type = "button";
86
+ btnDelete.ariaLabel = "Rimuovi notifica";
87
+ btnDelete.innerHTML = '<i class="fa-solid fa-xmark"></i>';
88
+ btnDelete.setAttribute("pgs", "buttonClose");
89
+ notification.insertAdjacentElement("afterbegin", btnDelete);
90
+
91
+ //== event
92
+
93
+ btnDelete.addEventListener("click", function (e) {
94
+ e.preventDefault();
95
+ e.stopPropagation();
96
+ e.stopImmediatePropagation()
97
+ deleteNotification(e); // Esegue la tua funzione
98
+ });
99
+ },
100
+
101
+ deleteAll(containerToken) {
102
+ let containerNotification = pgs(document).querySelector(containerToken);
103
+ if (containerNotification) containerNotification.innerHTML = "";
104
+ },
105
+
106
+ trigger(root = document) {
107
+ pgs(root).querySelectorAll("notificationTrigger").forEach(element => {
108
+ if (!element || element.dataset.initialize === "true") return;
109
+
110
+ element.dataset.initialize = "true";
111
+
112
+ const notification = this._getData(element);
113
+ const title = String(notification.title || "").trim();
114
+ const content = String(notification.message || "").trim();
115
+
116
+ if (!title && !content) {
117
+ element.remove();
118
+ return;
119
+ }
120
+
121
+ const link = notification.link || null;
122
+ const icon = notification.icon || undefined;
123
+ const duration = this._getDuration(notification);
124
+ const api = this._getApi(notification);
125
+ const type = this._getType(notification, api);
126
+ const formattedContent = this._getContent(title, content);
127
+
128
+ if (api === PGS_notification.toast) api[type](formattedContent, duration, icon);
129
+ else api[type](formattedContent, link, duration, icon);
130
+
131
+ element.remove();
132
+ });
133
+ }
134
+ };
135
+
136
+ //# EXPORT
137
+ export function PGS_notificationTrigger_init(root = document) {
138
+ return fn_notification.trigger(root);
139
+ }
140
+
141
+ export const PGS_notification = {
142
+ PGS_name: "PGS_notification",
143
+ trigger: PGS_notificationTrigger_init,
144
+ alert: {
145
+ error: (text = "Errore", link = null, timeout = 0, icon = '<i class="fa-solid fa-octagon-xmark"></i>') => fn_notification.initNotification("error", "notification", icon, text, timeout, "stack", link),
146
+ success: (text = "Aggiornato", link = null, timeout = 0, icon = '<i class="fa-solid fa-check"></i>') => fn_notification.initNotification("success", "notification", icon, text, timeout, "stack", link),
147
+ info: (text = "Aggiornamento", link = null, timeout = 0, icon = '<i class="fa-solid fa-circle-info"></i>',) => fn_notification.initNotification("info", "notification", icon, text, timeout, "stack", link),
148
+ warning: (text = "Attenzione", link = null, timeout = 0, icon = '<i class="fa-solid fa-triangle-exclamation"></i>') => fn_notification.initNotification("warning", "notification", icon, text, timeout, "stack", link),
149
+ deleteAll: () => fn_notification.deleteAll("notification")
150
+ },
151
+ toast: {
152
+ error: (text = "Errore", timeout = 4000, icon = '<i class="fa-solid fa-octagon-xmark"></i>',) => fn_notification.initNotification("error", "toast", icon, text, timeout),
153
+ success: (text = "Aggiornato", timeout = 4000, icon = '<i class="fa-solid fa-check"></i>',) => fn_notification.initNotification("success", "toast", icon, text, timeout),
154
+ info: (text = "Aggiornamento", timeout = 0, icon = '<i class="fa-solid fa-circle-info"></i>',) => fn_notification.initNotification("info", "toast", icon, text, timeout),
155
+ warning: (text = "Attenzione", timeout = 4000, icon = '<i class="fa-solid fa-triangle-exclamation"></i>',) => fn_notification.initNotification("warning", "toast", icon, text, timeout),
156
+ deleteAll: () => fn_notification.deleteAll("toast")
157
+ }
158
+ };
159
+
160
+
161
+ //= EXECUTE
162
+ if (document.readyState === "loading") document.addEventListener("DOMContentLoaded", () => PGS_notificationTrigger_init());
163
+ else PGS_notificationTrigger_init();