重构博客主题时(Compass V2.0 Rebirth)写的一段代码,记录一下...
效果如下:
/** * Compass Theme For Journey * * @abstract * @version 2.0 * @date 2020/01/03 16:47 * @author Wildlife <admin@lanseyujie.com> * @link https://www.lanseyujie.com * @copyright Copyright(c) 2014-2021, lanseyujie.com */ function buildToc(contentId, listId) { let content = document.getElementById(contentId); if (!content) { return } let tree = content.querySelectorAll('*'), ele = document.getElementById(listId), tags = ['h1', 'h2', 'h3', 'h4', 'h5', 'h6'], lastLevel = 1, // 初始化一个有序列表 rootList = document.createElement('ol'), // 当前的根列表 list = rootList; rootList.setAttribute('class', 'toc-list'); ele.append(rootList); tree.forEach(function (node, index) { // 当前 nodeName 存在于 H 标签列表;H 标签是否存在有效标题 if (tags.indexOf(node.nodeName.toLowerCase()) !== -1 && node.textContent.length > 0) { // 标记该标题的 id hash 以便跳转 node.setAttribute('id', 'toc-' + index); // 获取 H 标签的级别 let level = node.nodeName.slice(1), // 为该 H 标题创建索引 <li level=1><a href="#toc-1">title</a></li> li = document.createElement('li'), a = document.createElement('a'); // 标记索引级别 li.setAttribute('data-level', level); a.setAttribute('href', '#toc-' + index); a.setAttribute('title', node.textContent) a.textContent = node.textContent; li.appendChild(a); if (index === 0 || lastLevel === level) { // 将大标题插入根列表 list.appendChild(li); } else if (lastLevel < level) { if (list.hasChildNodes()) { // 当前较上一标题为小标题则创建子列表,并插入索引 let ol = document.createElement('ol'); ol.setAttribute('class', 'toc-list'); ol.appendChild(li); list.appendChild(ol); // 更新当前的根列表 list = ol; } else { // 上层根列表不存在索引则直接插入 list.appendChild(li); } } else if (lastLevel > level) { // 当前较上一标题为大标题则创建子列表,则获取差几级 let diff = lastLevel - level; if (diff < 6) { // 以当前根列表为基准,向父层遍历到所属层级根列表 let tmpList = list; for (let i = 1; i < 6; i++) { if (tmpList.parentNode) { tmpList = tmpList.parentNode; // 判断是否与该列表内索引层级一致 253,242如果返回 if (tmpList.firstElementChild.getAttribute('data-level') === level || i === diff) { break; } } } tmpList.appendChild(li); list = tmpList; } else { // 增强校错 rootList.appendChild(li); list = rootList; } } lastLevel = level; } }); if (rootList.hasChildNodes()) { ele.parentElement.classList.remove('hidden') } }
本文标题:js 生成标题目录树
版权声明:本文使用「署名-非商业性使用-相同方式共享」创作共享协议,转载或使用请遵守署名协议。
上一篇:Kubuntu 高分屏缩放