diff --git a/templates/manual.js b/templates/manual.js index a08db05..c8d0719 100644 --- a/templates/manual.js +++ b/templates/manual.js @@ -26,11 +26,11 @@ function afterFonts() { try { - buildTOC(); renderAnnotations(); setupChapterString(); ensureAnchors(); ensureImagePaths(); + buildTOC(); } catch (err) { console.error('[manual.js] Error preparando el manual:', err); } @@ -39,6 +39,14 @@ /* --------------------------------------------------------- 1. Índice automático --------------------------------------------------------- */ + function slugify(text) { + return (text || '') + .toLowerCase() + .normalize('NFD').replace(/[\u0300-\u036f]/g, '') + .replace(/[^a-z0-9]+/g, '-') + .replace(/(^-|-$)/g, ''); + } + function buildTOC() { const out = document.querySelector('[data-toc-output]'); if (!out) return; @@ -59,14 +67,14 @@ const li = document.createElement('li'); li.className = 'toc-h1'; - li.appendChild(tocRow(romanize(chapterIndex) + '. ' + title.textContent.trim())); + li.appendChild(tocRow(romanize(chapterIndex) + '. ' + title.textContent.trim(), title.id)); frag.appendChild(li); const subsections = chapter.querySelectorAll('h2'); subsections.forEach((sub) => { const row = document.createElement('li'); row.className = 'toc-h2'; - row.appendChild(tocRow(' ' + (sub.dataset.tocLabel || sub.textContent.trim()))); + row.appendChild(tocRow((sub.dataset.tocLabel || sub.textContent.trim()), sub.id)); frag.appendChild(row); }); @@ -74,7 +82,7 @@ subsub.forEach((sub) => { const row = document.createElement('li'); row.className = 'toc-h3'; - row.appendChild(tocRow(' ' + (sub.dataset.tocLabel || sub.textContent.trim()))); + row.appendChild(tocRow((sub.dataset.tocLabel || sub.textContent.trim()), sub.id)); frag.appendChild(row); }); }); @@ -83,21 +91,25 @@ out.appendChild(frag); } - function tocRow(label) { - const span = document.createElement('span'); - span.className = 'toc-row'; - const text = document.createElement('span'); - text.className = 'toc-text'; - text.textContent = label; + function tocRow(label, anchorId) { + const row = document.createElement('span'); + row.className = 'toc-row'; + + const link = document.createElement('a'); + link.className = 'toc-text'; + link.textContent = label; + if (anchorId) { + link.href = '#' + anchorId; + link.setAttribute('aria-label', 'Ir a ' + label.trim()); + } + row.appendChild(link); + const dots = document.createElement('span'); dots.className = 'toc-dots'; - const num = document.createElement('span'); - num.className = 'toc-page-num'; - num.textContent = '—'; - span.appendChild(text); - span.appendChild(dots); - span.appendChild(num); - return span; + dots.setAttribute('aria-hidden', 'true'); + row.appendChild(dots); + + return row; } function romanize(num) { @@ -170,12 +182,7 @@ const headings = document.querySelectorAll('[data-chapter] h1, [data-chapter] h2, [data-chapter] h3, [data-chapter] h4'); headings.forEach((h) => { if (!h.id) { - const slug = (h.textContent || '') - .toLowerCase() - .normalize('NFD').replace(/[\u0300-\u036f]/g, '') - .replace(/[^a-z0-9]+/g, '-') - .replace(/(^-|-$)/g, ''); - h.id = slug || 'h-' + Math.random().toString(36).slice(2, 8); + h.id = slugify(h.textContent) || 'h-' + Math.random().toString(36).slice(2, 8); } }); }