文章或博客自动生成章节目录索引(支持三级)的实现代码


Posted in Javascript onMay 10, 2020

自动生成章节目录索引(只支持一级)

一个好的博文除了博文的质量要好以外,好的组织结构也能让读者阅读的更加舒服与方便,我看园子里面有一些园友的博文都是分章节的,并且在博文的前面都带有章节的目录索引,点击索引之后会跳转到相应的章节阅读,并且还可以回到目录顶端,其中 Fish Li 的博文就是这种组织,当然这种结构如果是在写博文的时候人工设置那是非常麻烦的,无疑是增加了写作人的工作量。如果能自动生成章节索引岂不是节省了一大堆工作量。本来想通过FireBug看看Fish Li源码是怎么实现的,但是好像js是加密过的。那我就自己动手了,其实也没多少代码,很简单。

<script language="javascript" type="text/javascript">
//生成目录索引列表
function GenerateContentList()
{
  var jquery_h3_list = $('#cnblogs_post_body h3');//如果你的章节标题不是h3,只需要将这里的h3换掉即可
  if(jquery_h3_list.length>0)
  {
    var content = '<a name="_labelTop"></a>';
    content  += '<div id="navCategory">';
    content  += '<p style="font-size:18px"><b>阅读目录</b></p>';
    content  += '<ul>';
    for(var i =0;i<jquery_h3_list.length;i++)
    {
      var go_to_top = '<div style="text-align: right"><a href="#_labelTop" rel="external nofollow" rel="external nofollow" >回到顶部</a><a name="_label' + i + '"></a></div>';
      $(jquery_h3_list[i]).before(go_to_top);
      var li_content = '<li><a href="#_label' + i + '" rel="external nofollow" rel="external nofollow" >' + $(jquery_h3_list[i]).text() + '</a></li>';
      content += li_content;
    }
    content  += '</ul>';
    content  += '</div>';
    if($('#cnblogs_post_body').length != 0 )
    {
      $($('#cnblogs_post_body')[0]).prepend(content);
    }
  }  
}
GenerateContentList();
</script>

使用方法:登录到博客园之后,打开博客园的后台管理,切换到“设置”选项卡,将上面的代码,粘贴到 “页脚HTML代码” 区保存即可。

注意:上述js代码中提取的h3作为章节的标题,如果你的标题不是h3请在代码注释的地方自行修改。该代码除了在文章的最开始生成目录索引之外,还会在每一个章节最后右下角(也就是下一个章节标题的右上角)会生成一个“回到顶部”的链接,以方便读者回到目录。本篇文章的目录结构就是自动生成的效果,如果你觉得有用,就赶快试用一下吧。

自动生成三级目录

<script language="javascript" type="text/javascript">
//生成目录索引列表
function GenerateContentList()
{
  var jquery_h1_list = $('#cnblogs_post_body h1');
  if (jquery_h1_list.length == 0) { return; }
  if ($('#cnblogs_post_body').length == 0) { return; }

  var content = '<a name="_labelTop"></a>';
  content  += '<div id="navCategory">';
  content  += '<p style="font-size:18px"><b>阅读目录(Content)</b></p>';
  // 一级目录 start
  content += '<ul class="first_class_ul">';

  for (var i = 0; i < jquery_h1_list.length; i++)
  {
    var go_to_top = '<div style="text-align: right"><a href="#_labelTop" rel="external nofollow" rel="external nofollow" >回到顶部(go to top)</a><a name="_label' + i + '"></a></div>';
    $(jquery_h1_list[i]).before(go_to_top);

    // 一级目录的一条
    var li_content = '<li><a href="#_label' + i + '" rel="external nofollow" rel="external nofollow" >' + $(jquery_h1_list[i]).text() + '</a></li>';

    var nextH1Index = i + 1;
    if (nextH1Index == jquery_h1_list.length) { nextH1Index = 0; }
    var jquery_h2_list = $(jquery_h1_list[i]).nextUntil(jquery_h1_list[nextH1Index], "h2");
    // 二级目录 start
    if (jquery_h2_list.length > 0)
    {
      //li_content +='<ul style="list-style-type:none; text-align: left; margin:2px 2px;">';
      li_content += '<ul class="second_class_ul">';
    }
    for (var j = 0; j < jquery_h2_list.length; j++)
    {
      var go_to_top2 = '<div style="text-align: right"><a name="_lab2_'+ i + '_' + j + '"></a></div>';
      $(jquery_h2_list[j]).before(go_to_top2);
      // 二级目录的一条
      li_content +='<li><a href="#_lab2_'+ i +'_' + j + '" rel="external nofollow" >' + $(jquery_h2_list[j]).text() + '</a></li>';

      var nextH2Index = j + 1;
      var next;
      if (nextH2Index == jquery_h2_list.length) 
      {
        if (i + 1 == jquery_h1_list.length)
        {
          next = jquery_h1_list[0];
        }
        else
        {
          next = jquery_h1_list[i + 1];
        }
      }
      else
      {
        next = jquery_h2_list[nextH2Index];
      }
      var jquery_h3_list = $(jquery_h2_list[j]).nextUntil(next, "h3");
      // 三级目录 start
      if (jquery_h3_list.length > 0)
      {
        li_content += '<ul class="third_class_ul">';
      }
      
      for (var k = 0; k < jquery_h3_list.length; k++)
      {
        var go_to_third_Content = '<div style="text-align: right"><a name="_label3_' + i + '_' + j + '_' + k + '"></a></div>';
        $(jquery_h3_list[k]).before(go_to_third_Content);
        // 三级目录的一条
        li_content += '<li><a href="#_label3_' + i + '_' + j + '_' + k + '" rel="external nofollow" >' + $(jquery_h3_list[k]).text() + '</a></li>';
      }
      
      if (jquery_h3_list.length > 0)
      {
        li_content += '</ul>';
      }
      li_content += '</li>';
      // 三级目录 end
    }
    if (jquery_h2_list.length > 0)
    {
      li_content +='</ul>';
    }
    li_content +='</li>';
    // 二级目录 end

    content += li_content;
  }
  // 一级目录 end
  content += '</ul>';
  content += '</div>';

  $($('#cnblogs_post_body')[0]).prepend(content);
}

GenerateContentList();
</script>
levels of contents

如何使用(How to Use)

把上述JS代码复制到“页脚Html代码”里。

文章或博客自动生成章节目录索引(支持三级)的实现代码

在写博客的时候,给每个章节的标题设置“标题1”或“标题2”或“标题3”格式。

文章或博客自动生成章节目录索引(支持三级)的实现代码

然后一切就绪,欣赏效果吧。

示例(Demo)

三水点靠木小编注:为了seo考虑,不建议大量用h1,一个页面可以存在多个h2,h3,h4,所以三水点靠木网站采用的是h2,h3,h4实现三级目录。

补充:

三水点靠木小编从别的地方看到的相关文章可以当个参考

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <style>
    * {
      margin: 0;
      padding: 0;
      word-break: break-all;
    }
    #toc {
      width: 200px;
      position: fixed;
      left: 0;
      top: 0;
    }
    #toc a.active {
      color: red;
    }
    #content {
      margin-left: 200px;
    }
  </style>
  <script src="https://cdn.bootcss.com/jquery/3.2.1/jquery.min.js"></script>
  <script>
    $(document).ready(function () {
      for (var i = 0; i < 50; ++i) {
        $(".seg-content").append("<p>一个段落而已</p>")
      }

      (function () {
        var segs = [];
        $(".seg-begin").each(function (idx, node) {
          segs.push(node)

          var link = $("<a></a>").attr("href", "#" + $(node).attr("name")).html($(node).children("h1").html())
          if (!idx) {
            link.addClass("active")
          }
          var row = $("<li></li>").append(link)
          $("#toc ul").append(row)
        })

        $(window).bind("scroll", function() {
          var scrollTop = $(this).scrollTop()

          var topSeg = null
          for (var idx in segs) {
            var seg = segs[idx]
            if (seg.offsetTop > scrollTop) {
              continue
            }
            if (!topSeg) {
              topSeg = seg
            } else if (seg.offsetTop >= topSeg.offsetTop) {
              topSeg = seg
            }
          }
          if (topSeg) {
            $("#toc a").removeClass("active")

            var link = "#" + $(topSeg).attr("name")
            console.log('#toc a[href="' + link + '" rel="external nofollow" rel="external nofollow" ]')
            $('#toc a[href="' + link + '" rel="external nofollow" rel="external nofollow" ]').addClass("active")
            // console.log($(topSeg).children("h1").text())
          }
        })
      })()
    })
  </script>
</head>
<body>
  <div id="toc">
    <ul>

    </ul>
  </div>
  <div id="content">
    <a name="seg-1" class="seg-begin"><h1>第1章节</h1></a>
    <div class="seg-content"></div>
    <a name="seg-2" class="seg-begin"><h1>第2章节</h1></a>
    <div class="seg-content"></div>
    <a name="seg-3" class="seg-begin"><h1>第3章节</h1></a>
    <div class="seg-content"></div>
    <a name="seg-4" class="seg-begin"><h1>第4章节</h1></a>
    <div class="seg-content"></div>
  </div>
</body>
</html>

具体的使用可以参考下面的文章。

Javascript 相关文章推荐
jQuery 图像裁剪插件Jcrop的简单使用
May 22 Javascript
JQuery中根据属性或属性值获得元素(6种情况获取方法)
Jan 17 Javascript
javascipt匹配单行和多行注释的正则表达式
Nov 20 Javascript
Javascript:为input设置readOnly属性(示例讲解)
Dec 25 Javascript
JS使用replace()方法和正则表达式进行字符串的搜索与替换实例
Apr 10 Javascript
javascript实现的图片切割多块效果实例
May 07 Javascript
js代码验证手机号码和电话号码是否合法
Jul 30 Javascript
javascript设计简单的秒表计时器
Sep 05 Javascript
es6 字符串String的扩展(实例讲解)
Aug 03 Javascript
jQuery 开发之EasyUI 添加数据的实例
Sep 26 jQuery
微信小程序 checkbox使用实例解析
Sep 09 Javascript
JavaScript实现淘宝商品图切换效果
Apr 29 Javascript
vue滑动吸顶及锚点定位的示例代码
May 10 #Javascript
webpack+vue.js构建前端工程化的详细教程
May 10 #Javascript
JS实现单张或多张图片持续无缝滚动的示例代码
May 10 #Javascript
Layer UI表格列日期格式化及取消自动填充日期的实现方法
May 10 #Javascript
angula中使用iframe点击后不执行变更检测的问题
May 10 #Javascript
JavaScript 装逼指南(js另类写法)
May 10 #Javascript
js中!和!!的区别与用法
May 09 #Javascript
You might like
PHP4实际应用经验篇(8)
2006/10/09 PHP
CodeIgniter模板引擎使用实例
2014/07/15 PHP
详解Yii实现分页的两种方法
2017/01/14 PHP
PHP基于ICU扩展intl快速实现汉字转拼音及按拼音首字母分组排序的方法
2017/05/03 PHP
PHP PDO数据库操作预处理与注意事项
2019/03/16 PHP
动态加载图片路径 保持JavaScript控件的相对独立性
2010/09/03 Javascript
jQuery新闻滚动插件 jquery.roller.js
2011/06/27 Javascript
jquery中ajax学习笔记一
2011/10/16 Javascript
Javascript事件实例详解
2013/11/06 Javascript
js控制浏览器全屏示例代码
2014/02/20 Javascript
JavaScript中的Repaint和Reflow用法详解
2015/07/27 Javascript
Jquery AJAX POST与GET之间的区别详细介绍
2016/10/17 Javascript
微信小程序 页面跳转传值实现代码
2017/07/27 Javascript
JS温故而知新之变量提升和时间死区
2019/01/27 Javascript
javascript中join方法实例讲解
2019/02/21 Javascript
使用RxJS更优雅地进行定时请求详析
2019/06/02 Javascript
谈谈我在vue-cli3中用预渲染遇到的坑
2020/04/22 Javascript
vuex中store存储store.commit和store.dispatch的用法
2020/07/24 Javascript
WebStorm中如何将自己的代码上传到github示例详解
2020/10/28 Javascript
在Python中操作字典之setdefault()方法的使用
2015/05/21 Python
在Django的form中使用CSS进行设计的方法
2015/07/18 Python
利用python获取Ping结果示例代码
2017/07/06 Python
Python读取properties配置文件操作示例
2018/03/29 Python
详解pandas.DataFrame中删除包涵特定字符串所在的行
2019/04/04 Python
python全局变量引用与修改过程解析
2020/01/07 Python
Python如何访问字符串中的值
2020/02/09 Python
python属于哪种语言
2020/08/16 Python
解决virtualenv -p python3 venv报错的问题
2021/02/05 Python
定义css设备类型-Media Queries图表简介及使用方法
2013/01/21 HTML / CSS
idealfit英国:世界领先的女性健身用品和运动衣物品牌
2017/11/25 全球购物
Coggles美国/加拿大:高级国际时装零售商
2018/10/23 全球购物
公司聘任书模板
2014/03/29 职场文书
汽车转让协议书范本
2014/12/07 职场文书
2015年幼儿园大班工作总结
2015/04/25 职场文书
小学五年级班主任工作经验交流材料
2015/11/02 职场文书
2016大学生入党积极分子心得体会
2016/01/06 职场文书