tocbot生成文章目录

news2025/1/23 7:08:41

学习链接

github上的tocbot
npmjs上的tocbot

效果图

在这里插入图片描述

使用步骤

1. 安装tocbot

npm install tocbot --save

2. vue组件中使用引入tocbot

只需要引入tocbot,然后调用tocbot.init(…),指定提取的文章内容所在的dom,以及要把生成的目录放到哪个dom里面,就可以生成目录了。

注意:tocbot要求原文章内容的h1-h6标签必须要有id才可以跳转的哦

<style lang="scss">
@import 'tocbot/src/scss/tocbot';
@import url('https://fonts.font.im/css?family=Roboto');

body {
    margin: 0;
}

/* 整个滚动条 */
::-webkit-scrollbar {
    width: 10px;
    height: 10px;
}

/* 滚动条上的滚动滑块,参考: 滚动条样式修改->https://blog.csdn.net/coder_jxd/article/details/124213962 */
::-webkit-scrollbar-thumb {
    background-color: #49b1f5;
    /* 关键代码 */
    background-image: -webkit-linear-gradient(45deg,
            rgba(255, 255, 255, 0.4) 25%,
            transparent 25%,
            transparent 50%,
            rgba(255, 255, 255, 0.4) 50%,
            rgba(255, 255, 255, 0.4) 75%,
            transparent 75%,
            transparent);
    border-radius: 32px;
}

/* 添加行号插件后,它默认把滚动条给覆盖了,所以将padding-left改成margin-left */
[class*=v-md-prism-] {
    margin-left: 72px !important;
    padding-left: 0 !important;
}

/* 滚动条样式,参考: */
/* 滚动条轨道 */
::-webkit-scrollbar-track {
    background-color: #dbeffd;
    border-radius: 32px;
}




/* 行号相关样式 */
pre {
    background-color: #282c34;
    border-radius: 6px;
    position: relative;

    .line-numbers {
        position: absolute;
        color: #e0e0e0;
        font-size: 16px;
        margin: 16px 0;
        padding-right: 10px;
        width: 30px;
        text-align: right;
        font-family: 'Roboto', sans-serif;
        border-right: 1px solid #c5c5c5;
    }
}

code {
    font-family: 'Roboto', sans-serif;
    border-radius: 6px;

    padding-left: 0 !important;
    margin-left: 3em !important;


}

ul,
li {
    margin: 0;
    padding: 0;
    list-style: none;
}

.article {
    width: 600px;
    display: flex;

    width: 1200px;
    margin: 0 auto;
    margin-top: 50px;

    .article-content {
        width: 725px;
        padding: 15px;
        // border: 1px solid red;
        border-radius: 5px;
        box-shadow: 0 2px 8px 0 rgba(0, 0, 0, 0.16);
        flex-basis: 75%;
    }

    /* 目录相关样式 */
    .right-container {

        color: #666261;
        padding-left:  15px;

        .toc-wrapper {
            position: sticky;
            top: 10px;
            flex-basis: 25%;
            box-shadow: 0 4px 8px 6px rgba(7, 17, 27, .06);
            padding: 20px;
            border-radius: 10px;

            .toc-header {
                display: flex;
                align-items: center;
                padding: 10px;
            }

            #toc-content {
                position: sticky;
                top: 20px;
                box-sizing: border-box;
                width: 300px;
                // border: 1px solid red;
                background-color: #fff;

                a {
                    transition: all 0.3s;
                    text-decoration: none;
                    display: block;
                    line-height: 1.6em;
                    padding-left: 10px;
                    border-left: 4px solid transparent;

                    &::before {
                        display: none;
                    }

                    &.is-active-link {
                        font-weight: normal;
                        color: #fff;
                        background-color: #00c4b6;
                        border-left-color: #009d92;
                    }
                }
            }
        }
    }

}
</style>

<template>
    <div class="article">
        <!-- <div style="height: 500px;"> </div> -->
        <div class="article-content" id="article-content" v-html="htmlContent"></div>
        <div class="right-container">
            <div class="toc-wrapper">
                <div class="toc-header">
                    <img src="@/assets/svg/menu.svg" style="margin-right: 8px;" width="16px" height="16px" alt="">
                    <span>目录</span>
                </div>
                <div id="toc-content"></div>
            </div>
        </div>
    </div>
</template>

<script>
import { getArticle } from '@/api/articleApi'

import hljs from 'highlight.js';
import 'highlight.js/styles/atom-one-dark.css'

console.log(hljs);

import tocbot from 'tocbot'
console.log('tocbot', tocbot);

export default {
    name: 'Article',
    data() {
        return {
            htmlContent: ''
        }
    },
    created() {
        getArticle(this.$route.params.articleId).then(data => {
            this.htmlContent = data.htmlContent
            this.$nextTick(() => {
                // console.log('$nextTick...');
                let articleContent = document.querySelector('#article-content')
                let headingTag = ['h1', 'h2', 'h3']
                let children = Array.from(articleContent.children)
                for (let i = 0; i < children.length; i++) {
                    const e = children[i];
                    e.id = `h-${i}`
                }

                hljs.highlightAll()

                let codes = document.querySelectorAll('code')

                console.log(codes);
                for (let i = 0; i < codes.length; i++) {

                    const codeBlock = codes[i];
                    // console.log(codeBlock.innerHTML);
                    let lineTotal = codeBlock.innerHTML.split('\n').length
                    let ul = document.createElement('ul')
                    ul.classList.add('line-numbers')
                    for (let i = 1; i <= lineTotal; i++) {
                        let li = document.createElement('li')
                        let lineNum = document.createTextNode(i)
                        li.appendChild(lineNum)
                        ul.appendChild(li)
                    }
                    codeBlock.parentNode.prepend(ul)
                }


                tocbot.init({
                    // Where to render the table of contents.
                    tocSelector: '#toc-content',
                    // Where to grab the headings to build the table of contents.
                    contentSelector: '#article-content',
                    // Which headings to grab inside of the contentSelector element.
                    headingSelector: 'h1, h2, h3, h4, h5, h6',
                    // For headings inside relative or absolute positioned containers within content.
                    hasInnerContainers: true,
                });
            })
        })
    },
    mounted() {
        // console.log('mounted');

    },
    components: {
    }
}
</script>

tocbot生成的目录结构

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/413946.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

4月第1周榜单丨飞瓜数据B站UP主排行榜(哔哩哔哩平台)发布!

飞瓜轻数发布2023年4月3日-4月9日飞瓜数据UP主排行榜&#xff08;B站平台&#xff09;&#xff0c;通过充电数、涨粉数、成长指数三个维度来体现UP主账号成长的情况&#xff0c;为用户提供B站号综合价值的数据参考&#xff0c;根据UP主成长情况用户能够快速找到运营能力强的B站…

Flink (十一) --------- Table API 和 SQL

目录一、快速上手1. 需要引入的依赖2. 一个简单示例二、基本 API1. 程序架构2. 创建表环境3. 创建表4. 表的查询5. 输出表6. 表和流的转换三、流处理中的表1. 动态表和持续查询2. 将流转换成动态表3. 用 SQL 持续查询3. 将动态表转换为流四、时间属性和窗口1. 事件时间2. 处理时…

PDF怎么转换成word格式?这三个方法转换效率很高

在日常办公生活中&#xff0c;我们经常需要对文件进行格式转换&#xff0c;尤其是将PDF文件转换为可编辑的Word文件。虽然在Office软件中将Word文件转换为PDF很容易&#xff0c;但是将PDF文件转换为Word文件却需要一些技巧。在保证安全性能的前提下&#xff0c;如何将PDF文件转…

回溯算法编程题集合(leetcode)

给定一个整数数组 nums 和一个正整数 k&#xff0c;找出是否有可能把这个数组分成 k 个非空子集&#xff0c;其总和都相等。 示例 1&#xff1a; 输入&#xff1a; nums [4, 3, 2, 3, 5, 2, 1], k 4 输出&#xff1a; True 说明&#xff1a; 有可能将其分成 4 个子集&#x…

【springboot】ApplicationListener用法及源码

用法 方法一&#xff1a;继承ApplicationListener 传递事件 继承于ApplicationEvent public class ForDebuggerEvent extends ApplicationEvent {public ForDebuggerEvent(Object source) {super(source);}public void executeEvent() {System.out.println("ForDebugge…

第四章 网络层

网络层服务 网络层需要实现的两项重要功能&#xff1a; 转发&#xff1b;当通过一条输入链路接收到一个分组后&#xff0c;路由器需要决策通过哪条输出链路将分组发送出去&#xff0c;并将分组从输入接口转移到输出接口路由选择&#xff1b;当分组从源主机流向目的主机时&…

24.SSM-SpringMVC延续--拦截器

目录 一、拦截器。 &#xff08;1&#xff09;拦截器的作用。 &#xff08;2&#xff09;拦截器与过滤器的区别。 &#xff08;3&#xff09;拦截器的方法。 &#xff08;4&#xff09;拦截器的快速入门。 &#xff08;5&#xff09;多拦截器。 &#xff08;5.1&#xf…

libui的简单使用

libui是一个 C 中简单且可移植&#xff08;但并非不灵活&#xff09;的 GUI 库&#xff0c;它使用每个平台原生的GUI技术进行绘制。 官网地址&#xff1a;链接 相关文件&#xff1a;链接 一、配置说明 1. 所需链接的库 在使用libui的过程中至少需要链接以下库 user32.lib ke…

NumPy 秘籍中文第二版:一、使用 IPython

原文&#xff1a;NumPy Cookbook - Second Edition 协议&#xff1a;CC BY-NC-SA 4.0 译者&#xff1a;飞龙 在本章中&#xff0c;我们将介绍以下秘籍&#xff1a; 安装 IPython使用 IPython 作为 Shell阅读手册页安装 matplotlib运行 IPython 笔记本导出 IPython 笔记本导入网…

分享:如何给 DBA 减负?

欢迎访问 OceanBase 官网获取更多信息&#xff1a;https://www.oceanbase.com/ 本文来自OceanBase社区分享&#xff0c;仅限交流探讨。原作者肖杨&#xff0c;OceanBase 软件开发工程师。 研发、数据分析师及运维内部人员有数据查询、数据订正等需求&#xff0c;若无管控平台&…

vscode推送文件至github步骤

@目录 1、步骤: 提交到本地仓库从本地仓库再提交到远程仓库2、具体操作: 2.1 准备工作 设置提交代码时的用户信息 开始前我们需要先设置提交的用户信息,包括用户名和邮箱: git config --global user.name "runoob" git config --global user.email "tes…

【mysql性能调优 • 二】mysql的启动关闭原理和实战,及常见的错误排查

前言 MySQL是一个关系型数据库管理系统&#xff0c;由瑞典MySQL AB 公司开发&#xff0c;属于 Oracle 旗下产品。MySQL是最流行的关系型数据库管理系统之一&#xff0c;在 WEB 应用方面&#xff0c;MySQL是最好的 RDBMS (Relational Database Management System&#xff0c;关系…

【CSS】定位 ⑥ ( 使用绝对定位在父容器任意位置显示子容器 | 代码示例 )

文章目录一、需求分析及核心开发要点二、完整代码示例一、需求分析及核心开发要点 要实现如下功能 , 下图 粉色 部分是 整体 父容器 , 紫色元素 是 中心的核心位置 , 蓝色是左上角的浮标 , 红色是右下角的浮标 ; 首先分析父容器元素 ; 由于 子元素 需要使用 绝对定位 , 此处的…

【权限维持】Windows自启动映像劫持粘滞键辅助屏保后门WinLogon

文章目录权限维持-域环境&单机版-自启动权限维持-域环境&单机版-粘滞键权限维持-域环境&单机版-映像劫持权限维持-域环境&单机版-屏保&登录权限维持-域环境&单机版-自启动 1、自启动路径加载 C:\Users\Administrator\AppData\Roaming\Microsoft\Wind…

家装产业的数字化,正在成为越来越多人的新共识

一场数字化的浪潮&#xff0c;正在各行各业上演着。家装行业&#xff0c;亦不例外。可以说&#xff0c;家装产业的数字化&#xff0c;正在成为越来越多人的新共识。如何借助数字化的手段改造家装行业&#xff0c;如何乘着数字化的东风实现家装行业的全面转型升级&#xff0c;正…

uni-app--》如何实现网上购物小程序(中下)?

&#x1f3cd;️作者简介&#xff1a;大家好&#xff0c;我是亦世凡华、渴望知识储备自己的一名在校大学生 &#x1f6f5;个人主页&#xff1a;亦世凡华、 &#x1f6fa;系列专栏&#xff1a;uni-app &#x1f6b2;座右铭&#xff1a;人生亦可燃烧&#xff0c;亦可腐败&#xf…

STM32 W25QXX芯片

W25QXX芯片介绍 W25QXX芯片是华邦公司推出的大容量SPI FLASH产品&#xff0c;该系列有W25Q16/32/62/128等。本例程使用W25Q64&#xff0c;W25Q64容量为64Mbits&#xff08;8M字节&#xff09;&#xff1a;8MB的容量分为128个块(Block)&#xff08;块大小为64KB&#xff09;&…

Python每日一练(20230413)

目录 1. 最后一个单词的长度 ※ 2. 全排列 &#x1f31f;&#x1f31f; 3. 计数质数 ※ &#x1f31f; 每日一练刷题专栏 &#x1f31f; Golang每日一练 专栏 Python每日一练 专栏 C/C每日一练 专栏 Java每日一练 专栏 1. 最后一个单词的长度 给你一个字符串 s&…

clickhouse布隆过滤器跳数索引最佳实践

背景 本文来聊一下clickhouse的这个列式存储数据库的布隆过滤器的跳数索引类型,来了解它的数据结构&#xff0c;它可以为那些查询类型提供查询优化。 跳数索引-布隆过滤器 首先布隆过滤器家族的跳数索引分成三种类型&#xff1a; ngrambf_v1,tokenbf_v1,bloom_filter其原理是…

Visual Studio 2022如何安装和使用MSDN

我是荔园微风&#xff0c;作为一名在IT界整整25年的老兵&#xff0c;在后台收到提问&#xff0c;问我Visual Studio 2022如何安装和使用MSDN&#xff0c;这个我之前也没有在这个版本上装过MSDN&#xff0c;我之前是在Visual Studio 2017版上装过MSDN&#xff0c;那既然有人问了…