Repository navigation
Expand file tree
/
Copy pathmain.js
More file actions
124 lines (112 loc) · 5.19 KB
/
Copy pathmain.js
File metadata and controls
124 lines (112 loc) · 5.19 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
(function () {
const stored = localStorage.getItem('theme');
const prefersDark = window.matchMedia('(prefers-color-scheme: dark)').matches;
if (stored === 'dark' || (!stored && prefersDark)) document.documentElement.classList.add('dark');
})();
document.addEventListener('DOMContentLoaded', function () {
const themeToggleBtns = document.querySelectorAll('[data-theme-toggle]');
const hamburger = document.querySelector('[data-hamburger]');
const mobileNav = document.querySelector('[data-mobile-nav]');
const mobileClose = document.querySelector('[data-mobile-close]');
function updateThemeIcons() {
const isDark = document.documentElement.classList.contains('dark');
document.querySelectorAll('.icon-sun').forEach(function (element) {
element.style.display = isDark ? 'block' : 'none';
});
document.querySelectorAll('.icon-moon').forEach(function (element) {
element.style.display = isDark ? 'none' : 'block';
});
themeToggleBtns.forEach(function (button) {
button.setAttribute('aria-label', isDark ? 'Use light theme' : 'Use dark theme');
button.setAttribute('aria-pressed', String(isDark));
});
}
function closeMenu(restoreFocus) {
if (!mobileNav) return;
mobileNav.classList.remove('open');
mobileNav.setAttribute('aria-hidden', 'true');
document.body.style.overflow = '';
if (hamburger) hamburger.setAttribute('aria-expanded', 'false');
if (restoreFocus && hamburger) hamburger.focus();
}
themeToggleBtns.forEach(function (button) {
button.addEventListener('click', function () {
const isDark = document.documentElement.classList.toggle('dark');
localStorage.setItem('theme', isDark ? 'dark' : 'light');
updateThemeIcons();
});
});
updateThemeIcons();
if (hamburger && mobileNav) {
if (!mobileNav.id) mobileNav.id = 'mobile-navigation';
hamburger.setAttribute('aria-label', 'Open navigation menu');
hamburger.setAttribute('aria-controls', mobileNav.id);
hamburger.setAttribute('aria-expanded', 'false');
mobileNav.setAttribute('aria-hidden', 'true');
hamburger.addEventListener('click', function () {
mobileNav.classList.add('open');
mobileNav.setAttribute('aria-hidden', 'false');
hamburger.setAttribute('aria-expanded', 'true');
document.body.style.overflow = 'hidden';
const firstLink = mobileNav.querySelector('a');
if (firstLink) firstLink.focus();
});
}
if (mobileClose) {
mobileClose.setAttribute('aria-label', 'Close navigation menu');
mobileClose.addEventListener('click', function () { closeMenu(true); });
}
if (mobileNav) {
mobileNav.querySelectorAll('a').forEach(function (link) {
link.addEventListener('click', function () { closeMenu(false); });
});
}
document.addEventListener('keydown', function (event) {
if (event.key === 'Escape' && mobileNav && mobileNav.classList.contains('open')) closeMenu(true);
});
const scrollBtn = document.querySelector('.scroll-top-btn');
if (scrollBtn) {
scrollBtn.setAttribute('aria-label', 'Scroll to top');
window.addEventListener('scroll', function () {
scrollBtn.classList.toggle('visible', window.scrollY > 400);
});
scrollBtn.addEventListener('click', function () {
window.scrollTo({ top: 0, behavior: 'smooth' });
});
}
const currentPath = window.location.pathname.replace(/\/index\.html$/, '/');
document.querySelectorAll('.desktop-nav a, .mobile-nav-links a').forEach(function (link) {
const href = link.getAttribute('href') || '';
const page = href.split('/').filter(Boolean).pop() || '';
const pathPage = currentPath.split('/').filter(Boolean).pop() || '';
if ((href === 'index.html' && (currentPath === '/' || currentPath.endsWith('index.html'))) || (page && pathPage && page === pathPage)) link.classList.add('active');
});
const searchBox = document.querySelector('.search-box');
if (searchBox) {
if (!searchBox.getAttribute('aria-label')) searchBox.setAttribute('aria-label', 'Search posts');
searchBox.addEventListener('input', function () {
const query = searchBox.value.toLowerCase().trim();
document.querySelectorAll('.post-item[data-title]').forEach(function (item) {
const title = (item.getAttribute('data-title') || '').toLowerCase();
const tags = (item.getAttribute('data-tags') || '').toLowerCase();
const summary = (item.getAttribute('data-summary') || '').toLowerCase();
item.style.display = !query || title.includes(query) || tags.includes(query) || summary.includes(query) ? '' : 'none';
});
});
}
document.querySelectorAll('pre').forEach(function (pre) {
const button = document.createElement('button');
button.textContent = 'Copy';
button.setAttribute('aria-label', 'Copy code');
button.className = 'copy-code-btn';
pre.style.position = 'relative';
pre.appendChild(button);
button.addEventListener('click', function () {
const code = pre.querySelector('code') ? pre.querySelector('code').textContent : pre.textContent;
navigator.clipboard.writeText(code).then(function () {
button.textContent = 'Copied!';
setTimeout(function () { button.textContent = 'Copy'; }, 2000);
});
});
});
});