love-on-the-route
Version:
842 lines (841 loc) • 28.8 kB
JavaScript
var S = Object.defineProperty;
var b = (o, e, t) => e in o ? S(o, e, { enumerable: !0, configurable: !0, writable: !0, value: t }) : o[e] = t;
var m = (o, e, t) => b(o, typeof e != "symbol" ? e + "" : e, t);
class N {
constructor(e) {
m(this, "routes", []);
m(this, "contentElement");
m(this, "defaultLanguage");
m(this, "supportedLanguages");
this.rootElement = e, this.contentElement = document.createElement("main"), this.contentElement.id = "content", this.rootElement.appendChild(this.contentElement), window.addEventListener("popstate", this.render.bind(this)), this.setupNavigationListener();
}
addRoute(e, t, r, n) {
if (!e || !t || !r) {
console.error("Router: Invalid route parameters", {
path: e,
handler: !!t,
title: r
});
return;
}
const a = { path: e, handler: t, title: r };
if (n) {
const l = this.findRoute(n);
l && (l.children || (l.children = []), l.children.push(a));
} else
this.routes.push(a);
}
autoGenerateRoutes(e) {
Object.entries(e).forEach(([t, r]) => {
const n = `/${t.toLowerCase()}`, a = t.replace(/([A-Z])/g, " $1").trim();
this.addRoute(n, r.default, a);
});
}
findRoute(e) {
return this.routes.find((r) => r.path === e);
}
navigate(e) {
if (!e || typeof e != "string") {
console.error("Router: Invalid path for navigation", e);
return;
}
window.history.pushState({}, "", e), this.render();
}
render() {
const e = window.location.pathname;
if (!this.contentElement) {
console.error("Router: Content element not found");
return;
}
if (this.handleMultilingualRedirect(e))
return;
const t = this.findRoute(e);
this.contentElement.innerHTML = "", t ? t.handler() : this.contentElement.innerHTML = "<h1>404 - Page Not Found</h1>", window.dispatchEvent(
new CustomEvent("routeChanged", {
detail: { path: e }
})
);
}
setupNavigationListener() {
document.body.addEventListener("click", (e) => {
if (e.target instanceof HTMLAnchorElement) {
const t = e.target.getAttribute("href");
if (t && ([
"http://",
"https://",
"mailto:",
"tel:",
"javascript:",
"ftp:",
"file:"
].some((n) => t.startsWith(n)) || t.startsWith("#")))
return;
e.preventDefault(), this.navigate(e.target.pathname);
}
});
}
// Méthode pour configurer le mode multilingue
setMultilingualConfig(e, t) {
if (!e || !Array.isArray(e) || e.length === 0) {
console.error(
"[Love On The Route] Router: Valid supported languages array is required"
);
return;
}
this.supportedLanguages = e, this.defaultLanguage = t || e[0];
}
// Méthode pour détecter si une redirection multilingue est nécessaire
handleMultilingualRedirect(e) {
return !this.supportedLanguages || !this.defaultLanguage ? !1 : e === "/" && this.routes.some(
(r) => this.supportedLanguages.some(
(n) => r.path.startsWith(`/${n}`)
)
) ? (this.navigate(`/${this.defaultLanguage}`), !0) : !1;
}
// Méthode utilitaire pour obtenir les routes (pour génération de nav externe)
getRoutes() {
return this.routes;
}
}
function A(o) {
return new N(o);
}
function w(o, e, t = "") {
if (!o) {
console.error(
"[Love On The Route] generateRoutes: Router instance is required"
);
return;
}
if (!e || !Array.isArray(e)) {
console.error(
"[Love On The Route] generateRoutes: Valid route configs array is required"
);
return;
}
if (e.length === 0) {
console.warn("[Love On The Route] generateRoutes: No routes provided");
return;
}
e.forEach((r) => {
if (!r || typeof r != "object") {
console.error(
"[Love On The Route] generateRoutes: Invalid route config",
r
);
return;
}
if (!r.path || typeof r.path != "string") {
console.error(
"[Love On The Route] generateRoutes: Route config must have a valid path",
r
);
return;
}
if (!r.component || typeof r.component != "function") {
console.error(
"[Love On The Route] generateRoutes: Route config must have a valid component function",
r
);
return;
}
const n = t + r.path;
o.addRoute(
n,
() => {
try {
const a = r.component();
if (!a || !(a instanceof HTMLElement)) {
console.error(
"[Love On The Route] Component must return a valid HTMLElement",
r.path
);
return;
}
const l = document.getElementById("content");
l ? l.appendChild(a) : console.error(
"[Love On The Route] Content element '#content' not found in DOM"
);
} catch (a) {
console.error(
"[Love On The Route] Error executing component for route",
r.path,
a
);
}
},
r.title,
t || void 0
), r.children && w(o, r.children, n);
}), P(o, e);
}
function P(o, e) {
try {
const t = /* @__PURE__ */ new Set();
if (e.forEach((r) => {
r.language && t.add(r.language);
const n = r.path.match(/^\/([a-z]{2})(?:\/|$)/);
n && t.add(n[1]);
}), t.size > 0) {
const r = Array.from(t).sort(), n = r[0];
typeof o.setMultilingualConfig == "function" && o.setMultilingualConfig(
r,
n
);
}
} catch (t) {
console.error(
"[Love On The Route] Error auto-configuring multilingual mode",
t
);
}
}
function E(o) {
if (!o || typeof o != "object")
return console.error(
"[Love On The Route] autoDiscoverPages: Components object is required"
), [];
if (Object.keys(o).length === 0)
return console.warn("[Love On The Route] autoDiscoverPages: No components found"), [];
const e = ["index.ts", "PanicHeader.ts"];
return Object.entries(o).filter(([r]) => {
const n = r.split("/").pop() || "";
return !e.includes(n);
}).map(([r, n]) => {
var u;
const a = r.split("/"), l = ((u = a.pop()) == null ? void 0 : u.replace(".ts", "")) || "", s = a[a.length - 1];
let i;
return l.toLowerCase() === "home" ? i = "/" : i = s && s !== "pages" ? `/${s.toLowerCase()}` : `/${l.toLowerCase()}`, {
path: i,
component: n.default,
title: l.replace(/([A-Z])/g, " $1").trim()
};
}).sort((r, n) => r.path === "/" ? -1 : n.path === "/" ? 1 : r.title.localeCompare(n.title));
}
function q(o, e = ["en", "fr"]) {
const t = ["index.ts", "PanicHeader.ts"], r = /* @__PURE__ */ new Set();
return {
routes: Object.entries(o).filter(([l]) => {
const s = l.split("/").pop() || "";
return !t.includes(s);
}).map(([l, s]) => {
var f;
const i = l.split("/"), u = ((f = i.pop()) == null ? void 0 : f.replace(".ts", "")) || "";
let c = null, g = [];
for (let d = i.length - 1; d >= 0; d--) {
const C = i[d];
if (e.includes(C)) {
c = C, g = i.slice(d + 1);
break;
}
}
c || (c = e[0]), r.add(c);
let h;
if (u.toLowerCase() === "home")
h = `/${c}`;
else {
const d = g.length > 0 ? g.join("/").toLowerCase() : u.toLowerCase();
h = `/${c}/${d}`;
}
return {
path: h,
component: s.default,
title: u.replace(/([A-Z])/g, " $1").trim(),
language: c
};
}).sort((l, s) => {
if (l.language !== s.language)
return l.language.localeCompare(s.language);
const i = l.path === `/${l.language}`, u = s.path === `/${s.language}`;
return i && !u ? -1 : !i && u ? 1 : l.title.localeCompare(s.title);
}),
languages: Array.from(r).sort()
};
}
function U(o, e = ["en", "fr"]) {
if (Object.keys(o).some((n) => n.split("/").some((l) => e.includes(l)))) {
const { routes: n, languages: a } = q(
o,
e
);
return { routes: n, languages: a, isMultilingual: !0 };
} else
return { routes: E(o), isMultilingual: !1 };
}
function F(o, e = {}) {
const {
homeNames: t = ["home", "index", "accueil", "main"],
supportedLanguages: r = ["en", "fr"]
} = e;
if (Object.keys(o).some((l) => l.split("/").some((i) => r.includes(i)))) {
const l = /* @__PURE__ */ new Set();
return {
routes: Object.entries(o).map(([i, u]) => {
var C;
const c = i.split("/"), g = ((C = c.pop()) == null ? void 0 : C.replace(".ts", "")) || "";
let h = null, f = [];
for (let v = c.length - 1; v >= 0; v--) {
const O = c[v];
if (r.includes(O)) {
h = O, f = c.slice(v + 1);
break;
}
}
h || (h = r[0]), l.add(h);
let d;
if (t.some((v) => g.toLowerCase() === v.toLowerCase()))
d = `/${h}`;
else {
const v = f.length > 0 ? f.join("/").toLowerCase() : g.toLowerCase();
d = `/${h}/${v}`;
}
return {
path: d,
component: u.default,
title: g.replace(/([A-Z])/g, " $1").trim(),
language: h
};
}).sort((i, u) => {
if (i.language !== u.language)
return i.language.localeCompare(u.language);
const c = i.path === `/${i.language}`, g = u.path === `/${u.language}`;
return c && !g ? -1 : !c && g ? 1 : i.title.localeCompare(u.title);
}),
languages: Array.from(l).sort(),
isMultilingual: !0
};
} else
return {
routes: Object.entries(o).map(([s, i]) => {
var f;
const u = s.split("/"), c = ((f = u.pop()) == null ? void 0 : f.replace(".ts", "")) || "", g = u[u.length - 1];
let h;
return t.some((d) => c.toLowerCase() === d.toLowerCase()) ? h = "/" : h = g && g !== "pages" ? `/${g.toLowerCase()}` : `/${c.toLowerCase()}`, {
path: h,
component: i.default,
title: c.replace(/([A-Z])/g, " $1").trim()
};
}).sort((s, i) => s.path === "/" ? -1 : i.path === "/" ? 1 : s.title.localeCompare(i.title)),
isMultilingual: !1
};
}
class H {
constructor(e, t = {}) {
m(this, "element");
m(this, "logoConfig");
this.routes = e, this.options = t, (!e || !Array.isArray(e)) && (console.error("[Love On The Route] LoveNav: Routes array is required"), this.routes = []), (!t || typeof t != "object") && (console.error("[Love On The Route] LoveNav: Options should be an object"), this.options = {}), this.logoConfig = this.options.logo, this.logoConfig && console.log(
"[Love On The Route] DEBUG: LoveNav initialisé avec logo:",
this.logoConfig
);
try {
this.element = document.createElement(this.options.tagName || "nav"), this.options.containerClass && (this.element.className = this.options.containerClass), this.updateContent(), this.setupActiveStateListener();
} catch (r) {
console.error(
"[Love On The Route] LoveNav: Error during initialization",
r
), this.element = document.createElement("nav");
}
}
updateContent() {
var e;
try {
if (!this.routes || this.routes.length === 0) {
console.warn(
"[Love On The Route] LoveNav: No routes provided for navigation"
), this.element.innerHTML = "";
return;
}
let t = "";
if (this.logoConfig && !this.options.separateLogoFromNav) {
const a = this.logoConfig.href || "/", l = this.logoConfig.linkClass || "logo-link", s = this.logoConfig.containerClass || "";
console.log("[Love On The Route] DEBUG: Ajout du logo intégré:", {
logoHref: a,
logoClass: l,
logoContainerClass: s,
replacesHome: this.logoConfig.replacesHome
}), t += `<div class="${s}">
<a href="${a}" class="${l}" data-route="${a}" data-logo="true">
${this.logoConfig.html}
</a>
</div>`;
}
let r = this.routes;
(e = this.logoConfig) != null && e.replacesHome && (console.log(
"[Love On The Route] DEBUG: Logo replacesHome activé, routes avant filtrage:",
this.routes
), r = this.routes.filter((a) => {
const l = a.path.toLowerCase(), s = a.title.toLowerCase(), i = l === "/" || l.match(/^\/[a-z]{2}$/) || // /en, /fr, etc.
s === "home" || s === "accueil";
return i && console.log("[Love On The Route] DEBUG: Route home exclue:", a), !i;
}), console.log(
"[Love On The Route] DEBUG: Routes après filtrage:",
r
));
const n = r.filter((a) => a && a.path && a.title).map((a) => {
const l = this.options.linkClass || "", s = a.path.replace(/"/g, """), i = a.title.replace(/</g, "<").replace(/>/g, ">");
return `<a href="${s}" class="${l}" data-route="${s}">${i}</a>`;
}).join("");
t += n, this.element.innerHTML = t, this.setupClickHandlers();
} catch (t) {
console.error(
"[Love On The Route] LoveNav: Error updating content",
t
), this.element.innerHTML = "";
}
}
setupClickHandlers() {
const e = this.element.querySelectorAll("a");
console.log(
"[Love On The Route] DEBUG: Configuration des clics pour",
e.length,
"liens"
), e.forEach((t, r) => {
const n = t.getAttribute("data-route"), a = t.getAttribute("data-logo") === "true";
console.log(`[Love On The Route] DEBUG: Lien ${r}:`, {
routePath: n,
isLogo: a,
innerHTML: t.innerHTML.substring(0, 50)
}), n ? t.addEventListener("click", (l) => {
l.preventDefault(), console.log(
"[Love On The Route] DEBUG: Clic sur",
a ? "logo" : "lien",
"vers:",
n
), window.history.pushState(null, "", n), window.dispatchEvent(new PopStateEvent("popstate")), console.log(
"[Love On The Route] DEBUG: Navigation déclenchée vers:",
n
);
}) : console.error("[Love On The Route] ERROR: Lien sans data-route:", t);
});
}
setupActiveStateListener() {
const e = () => {
const t = window.location.pathname;
this.element.querySelectorAll("a").forEach((n) => {
var s;
const a = n.getAttribute("data-route"), l = n.getAttribute("data-logo") === "true";
this.options.activeClass && (l ? t === "/" || t === a || ((s = this.logoConfig) == null ? void 0 : s.href) && t === this.logoConfig.href ? n.classList.add(this.options.activeClass) : n.classList.remove(this.options.activeClass) : a === t ? n.classList.add(this.options.activeClass) : n.classList.remove(this.options.activeClass));
});
};
window.addEventListener("popstate", e), window.addEventListener("routeChanged", e), e();
}
render() {
return this.element;
}
renderSeparate() {
if (!this.logoConfig || !this.options.separateLogoFromNav)
return { nav: this.element };
const e = document.createElement("div");
e.className = this.logoConfig.containerClass || "logo-container";
const t = this.logoConfig.href || "/", r = this.logoConfig.linkClass || "logo-link";
e.innerHTML = `
<a href="${t}" class="${r}" data-route="${t}" data-logo="true">
${this.logoConfig.html}
</a>
`;
const n = e.querySelector("a");
return n ? (console.log(
"[Love On The Route] DEBUG: Configuration du clic logo séparé vers:",
t
), n.addEventListener("click", (a) => {
a.preventDefault(), console.log(
"[Love On The Route] DEBUG: Clic sur logo séparé vers:",
t
), window.history.pushState(null, "", t), window.dispatchEvent(new PopStateEvent("popstate")), console.log(
"[Love On The Route] DEBUG: Navigation logo séparé déclenchée vers:",
t
);
})) : console.error(
"[Love On The Route] ERROR: Logo séparé créé mais lien non trouvé"
), { logo: e, nav: this.element };
}
updateRoutes(e) {
if (!e || !Array.isArray(e)) {
console.error(
"[Love On The Route] LoveNav: updateRoutes requires a valid routes array"
);
return;
}
try {
this.routes = e, this.updateContent();
} catch (t) {
console.error(
"[Love On The Route] LoveNav: Error updating routes",
t
);
}
}
updateLogo(e) {
this.logoConfig = e, this.updateContent();
}
}
function T(o) {
if (!o || typeof o != "object") {
console.error(
"[Love On The Route] updateSEO: Configuration object is required"
);
return;
}
try {
o.title && (document.title = o.title, p("og:title", o.title), p("twitter:title", o.title)), o.description && (p("description", o.description), p("og:description", o.description), p("twitter:description", o.description)), o.url && (p("og:url", o.url), M(o.url)), o.image && (p("og:image", o.image), p("twitter:image", o.image)), o.siteName && p("og:site_name", o.siteName), o.type && p("og:type", o.type), o.keywords && o.keywords.length > 0 && p("keywords", o.keywords.join(", "));
} catch (e) {
console.error(
"[Love On The Route] updateSEO: Error updating SEO tags",
e
);
}
}
function p(o, e) {
if (!o || typeof o != "string") {
console.error("[Love On The Route] updateMetaTag: Valid name is required");
return;
}
if (e == null) {
console.error("[Love On The Route] updateMetaTag: Content is required");
return;
}
try {
let t = document.querySelector(
`meta[name="${o}"]`
);
t || (t = document.querySelector(
`meta[property="${o}"]`
)), t || (t = document.createElement("meta"), o.startsWith("og:") || o.startsWith("twitter:") ? t.setAttribute("property", o) : t.setAttribute("name", o), document.head.appendChild(t)), t.setAttribute("content", e);
} catch (t) {
console.error(
"[Love On The Route] updateMetaTag: Error updating meta tag",
o,
t
);
}
}
function M(o) {
if (!o || typeof o != "string") {
console.error(
"[Love On The Route] updateCanonicalLink: Valid URL is required"
);
return;
}
try {
let e = document.querySelector(
'link[rel="canonical"]'
);
e || (e = document.createElement("link"), e.rel = "canonical", document.head.appendChild(e)), e.href = o;
} catch (e) {
console.error(
"[Love On The Route] updateCanonicalLink: Error updating canonical link",
e
);
}
}
function G() {
try {
const o = document.querySelectorAll("meta[name], meta[property]"), e = document.querySelector('link[rel="canonical"]');
o.forEach((t) => {
const r = t.getAttribute("name") || t.getAttribute("property");
r && (r.startsWith("og:") || r.startsWith("twitter:") || ["description", "keywords"].includes(r)) && t.remove();
}), e && e.remove();
} catch (o) {
console.error(
"[Love On The Route] resetSEO: Error resetting SEO tags",
o
);
}
}
function j(o = ["en", "fr"]) {
if (!o || !Array.isArray(o) || o.length === 0)
return console.error(
"[Love On The Route] detectCurrentLanguage: Valid supported languages array is required"
), "en";
try {
const t = window.location.pathname.split("/").filter(Boolean);
if (t.length > 0) {
const r = t[0];
if (o.includes(r))
return r;
}
return o[0] || "en";
} catch (e) {
return console.error(
"[Love On The Route] detectCurrentLanguage: Error detecting language",
e
), "en";
}
}
function $() {
try {
const e = window.location.pathname.split("/").filter(Boolean);
if (e.length > 0) {
const t = e[0];
if (t.length === 2 || t.length === 3)
return t;
}
return "en";
} catch (o) {
return console.error(
"[Love On The Route] getCurrentLanguage: Error detecting language",
o
), "en";
}
}
let L = [], y = "";
function x(o) {
return !o || typeof o != "function" ? (console.error(
"[Love On The Route] watchLanguageChanges: Valid callback function is required"
), () => {
}) : (L.push(o), L.length === 1 && k(), () => {
const e = L.indexOf(o);
e > -1 && L.splice(e, 1), L.length === 0 && D();
});
}
function k() {
y = $(), window.addEventListener("popstate", R);
const o = history.pushState, e = history.replaceState;
history.pushState = function(...t) {
o.apply(history, t), setTimeout(R, 0);
}, history.replaceState = function(...t) {
e.apply(history, t), setTimeout(R, 0);
};
}
function D() {
window.removeEventListener("popstate", R);
}
function R() {
const o = $();
o !== y && (y = o, L.forEach((e) => {
try {
e(o);
} catch (t) {
console.error(
"[Love On The Route] Error in language change callback:",
t
);
}
}));
}
function W(o, e) {
if (!o || !Array.isArray(o))
return console.error(
"[Love On The Route] filterRoutesByCurrentLanguage: Valid routes array is required"
), [];
if (!e || e.length === 0)
return o;
try {
const t = j(e);
return o.filter((r) => r.language ? r.language === t : !0);
} catch (t) {
return console.error(
"[Love On The Route] filterRoutesByCurrentLanguage: Error filtering routes",
t
), o;
}
}
function I(o) {
var l;
if (!o || typeof o != "object")
throw console.error(
"[Love On The Route] loveOnTheRoute: Configuration object is required"
), new Error("Configuration object is required");
if (!o.container)
throw console.error("[Love On The Route] loveOnTheRoute: Container is required"), new Error("Container is required");
const e = typeof o.container == "string" ? document.querySelector(o.container) : o.container;
if (!e)
throw console.error(
"[Love On The Route] loveOnTheRoute: Container not found",
o.container
), new Error(`Container not found: ${o.container}`);
const t = A(e);
if (!o.pages)
throw console.error("[Love On The Route] loveOnTheRoute: Pages are required"), new Error(
"Pages are required. Use import.meta.glob('./pages/**/*.ts', { eager: true }) and pass the result to loveOnTheRoute({ pages: ... })"
);
if (typeof o.pages != "object" || Object.keys(o.pages).length === 0)
throw console.error(
"[Love On The Route] loveOnTheRoute: Pages object is empty or invalid",
o.pages
), new Error("Pages object must contain at least one page component");
const r = E(o.pages), n = r.map((s) => ({
...s,
component: () => {
try {
o.seoDefaults && T({
title: `${o.seoDefaults.siteName || ""} | ${s.title}`.trim(),
url: window.location.href,
type: o.seoDefaults.type || "website",
image: o.seoDefaults.image,
siteName: o.seoDefaults.siteName
});
const i = s.component();
return !i || !(i instanceof HTMLElement) ? (console.error(
"[Love On The Route] Component must return a valid HTMLElement",
s.path
), document.createElement("div")) : i;
} catch (i) {
console.error(
"[Love On The Route] Error in route component",
s.path,
i
);
const u = document.createElement("div");
return u.innerHTML = `<h1>Error loading page</h1><p>Route: ${s.path}</p>`, u;
}
}
}));
w(t, n);
let a;
if (o.generateNav)
try {
const s = r.map((i) => ({
path: i.path,
title: i.title
}));
if (a = new H(s, o.navOptions || {}), (l = o.navOptions) != null && l.insertBefore) {
const i = typeof o.navOptions.insertBefore == "string" ? document.querySelector(o.navOptions.insertBefore) : o.navOptions.insertBefore;
i && i.parentNode ? i.parentNode.insertBefore(a.render(), i) : (console.warn(
"[Love On The Route] insertBefore target not found, inserting before container instead"
), e.parentNode && e.parentNode.insertBefore(a.render(), e));
} else
e.parentNode ? e.parentNode.insertBefore(a.render(), e) : console.warn(
"[Love On The Route] Container has no parent, navigation cannot be inserted"
);
} catch (s) {
console.error("[Love On The Route] Error creating navigation", s), a = void 0;
}
try {
t.render(), window.location.pathname === "/" && t.navigate("/");
} catch (s) {
throw console.error(
"[Love On The Route] Error during router initialization",
s
), s;
}
return {
router: t,
nav: a,
updateSEO: T
};
}
class V {
// Default value
constructor(e, t = {}) {
m(this, "element");
m(this, "currentLang", "en");
this.languages = e, this.options = t, (!e || !Array.isArray(e) || e.length === 0) && (console.error(
"[Love On The Route] LangSelector: Languages array is required and cannot be empty"
), this.languages = [{ code: "en", label: "English" }]), (!t || typeof t != "object") && (console.error(
"[Love On The Route] LangSelector: Options should be an object"
), this.options = {});
try {
this.currentLang = this.detectCurrentLanguage(), this.element = document.createElement(this.options.tagName || "div"), this.options.containerClass && (this.element.className = this.options.containerClass), this.updateContent(), this.setupLanguageListener();
} catch (r) {
console.error(
"[Love On The Route] LangSelector: Error during initialization",
r
), this.element = document.createElement("div");
}
}
detectCurrentLanguage() {
var e;
try {
const r = window.location.pathname.split("/").filter(Boolean);
if (r.length > 0) {
const n = r[0];
if (this.languages.some((a) => a.code === n))
return n;
}
return ((e = this.languages[0]) == null ? void 0 : e.code) || "en";
} catch (t) {
return console.error(
"[Love On The Route] LangSelector: Error detecting current language",
t
), "en";
}
}
updateContent() {
const e = this.languages.map((t) => {
const r = this.options.linkClass || "", n = t.code === this.currentLang && this.options.activeClass || "", a = `${r} ${n}`.trim(), s = `${this.options.showFlags && t.flag ? t.flag + " " : ""}${t.label}`;
return `<a href="/${t.code}" class="${a}" data-lang="${t.code}">${s}</a>`;
}).join("");
this.element.innerHTML = e;
}
setupLanguageListener() {
const e = () => {
this.currentLang = this.detectCurrentLanguage(), this.updateContent();
};
window.addEventListener("popstate", e), window.addEventListener("routeChanged", e), this.element.addEventListener("click", (t) => {
if (t.target instanceof HTMLAnchorElement) {
const r = t.target.getAttribute("data-lang");
r && (t.preventDefault(), this.switchLanguage(r));
}
});
}
switchLanguage(e) {
if (!e || typeof e != "string") {
console.error(
"[Love On The Route] LangSelector: Valid language code is required"
);
return;
}
if (!this.languages.some((t) => t.code === e)) {
console.error(
"[Love On The Route] LangSelector: Language code not found in supported languages",
e
);
return;
}
try {
const r = window.location.pathname.split("/").filter(Boolean);
r.length > 0 && this.languages.some((a) => a.code === r[0]) && r.shift();
const n = `/${e}${r.length > 0 ? "/" + r.join("/") : ""}`;
window.history.pushState({}, "", n), window.dispatchEvent(
new CustomEvent("routeChanged", {
detail: { path: n, lang: e }
})
);
} catch (t) {
console.error(
"[Love On The Route] LangSelector: Error switching language",
t
);
}
}
render() {
return this.element;
}
getCurrentLanguage() {
return this.currentLang;
}
updateLanguages(e) {
if (!e || !Array.isArray(e) || e.length === 0) {
console.error(
"[Love On The Route] LangSelector: updateLanguages requires a valid, non-empty languages array"
);
return;
}
try {
this.languages = e, this.updateContent();
} catch (t) {
console.error(
"[Love On The Route] LangSelector: Error updating languages",
t
);
}
}
}
export {
V as LangSelector,
H as LoveNav,
q as autoDiscoverMultilingualPages,
E as autoDiscoverPages,
F as autoDiscoverPagesFlexible,
U as autoDiscoverPagesIntelligent,
A as createRouter,
j as detectCurrentLanguage,
W as filterRoutesByCurrentLanguage,
w as generateRoutes,
$ as getCurrentLanguage,
I as loveOnTheRoute,
G as resetSEO,
T as updateSEO,
x as watchLanguageChanges
};