jquery.autoMenu.js 6.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166
  1. /*
  2. 这段代码按H2、H3格式生成两级菜单
  3. 写博客按H2、H3格式写,不然生成不了
  4. Markdown写作按##、###两级目录写
  5. 当然你也可以改写代码成三级菜单
  6. 参考:孤傲苍狼 zhang_derek
  7. 洪卫 2018-5-18
  8. */
  9. let BlogDirectory = {
  10. /* 获取元素位置,距浏览器左边界的距离(left)和距浏览器上边界的距离(top)*/
  11. getElementPosition: function (ele) {
  12. let topPosition = 0;
  13. let leftPosition = 0;
  14. while (ele) {
  15. topPosition += ele.offsetTop;
  16. leftPosition += ele.offsetLeft;
  17. ele = ele.offsetParent;
  18. }
  19. return {top: topPosition, left: leftPosition};
  20. },
  21. /*获取滚动条当前位置 */
  22. getScrollBarPosition: function () {
  23. let scrollBarPosition = document.body.scrollTop || document.documentElement.scrollTop;
  24. return scrollBarPosition;
  25. },
  26. /* 移动滚动条,finalPos 为目的位置,internal 为移动速度 */
  27. moveScrollBar: function (finalpos, interval) {
  28. //若不支持此方法,则退出
  29. if (!window.scrollTo) {
  30. return false;
  31. }
  32. //窗体滚动时,禁用鼠标滚轮
  33. window.onmousewheel = function () {
  34. return false;
  35. };
  36. //清除计时
  37. if (document.body.movement) {
  38. clearTimeout(document.body.movement);
  39. }
  40. //获取滚动条当前位置
  41. let currentpos = BlogDirectory.getScrollBarPosition();
  42. let dist = 0;
  43. //到达预定位置,则解禁鼠标滚轮,并退出
  44. if (currentpos == finalpos) {
  45. window.onmousewheel = function () {
  46. return true;
  47. }
  48. return true;
  49. }
  50. //未到达,则计算下一步所要移动的距离
  51. if (currentpos < finalpos) {
  52. dist = Math.ceil((finalpos - currentpos) / 10);
  53. currentpos += dist;
  54. }
  55. if (currentpos > finalpos) {
  56. dist = Math.ceil((currentpos - finalpos) / 10);
  57. currentpos -= dist;
  58. }
  59. let scrTop = BlogDirectory.getScrollBarPosition();//获取滚动条当前位置
  60. window.scrollTo(0, currentpos);//移动窗口
  61. if (BlogDirectory.getScrollBarPosition() == scrTop)//若已到底部,则解禁鼠标滚轮,并退出
  62. {
  63. window.onmousewheel = function () {
  64. return true;
  65. }
  66. return true;
  67. }
  68. //进行下一步移动
  69. let repeat = "BlogDirectory.moveScrollBar(" + finalpos + "," + interval + ")";
  70. document.body.movement = setTimeout(repeat, interval);
  71. },
  72. htmlDecode: function (text) {
  73. let temp = document.createElement("div");
  74. temp.innerHTML = text;
  75. let output = temp.innerText || temp.textContent;
  76. temp = null;
  77. return output;
  78. },
  79. /*
  80. 创建博客目录,id表示包含博文正文的 div 容器的 id,
  81. mt 和 st 分别表示主标题和次级标题的标签名称(如 H2、H3,大写或小写都可以!),
  82. interval 表示移动的速度
  83. */
  84. createBlogDirectory: function (selector, mt, st, interval) {
  85. //获取博文正文div容器
  86. let elem = document.querySelector(selector);
  87. if (!elem) return false;
  88. //获取div中所有元素结点
  89. let nodes = elem.getElementsByTagName("*");
  90. //创建博客目录的div容器
  91. let divSideBar = document.createElement('DIV');
  92. divSideBar.className = 'uprightsideBar';
  93. divSideBar.setAttribute('id', 'uprightsideBar');
  94. let divSideBarTab = document.createElement('DIV');
  95. divSideBarTab.setAttribute('id', 'sideBarTab');
  96. divSideBar.appendChild(divSideBarTab);
  97. let h2 = document.createElement('DIV');
  98. divSideBarTab.appendChild(h2);
  99. let txt = document.createTextNode('目录导航');
  100. h2.appendChild(txt);
  101. let divSideBarContents = document.createElement('DIV');
  102. divSideBarContents.style.display = 'none';
  103. divSideBarContents.setAttribute('id', 'sideBarContents');
  104. divSideBar.appendChild(divSideBarContents);
  105. //创建自定义列表
  106. let dlist = document.createElement("dl");
  107. divSideBarContents.appendChild(dlist);
  108. let num = 0;//统计找到的mt和st
  109. mt = mt.toUpperCase();//转化成大写
  110. st = st.toUpperCase();//转化成大写
  111. //遍历所有元素结点
  112. for (let i = 0; i < nodes.length; i++) {
  113. if (nodes[i].nodeName == mt || nodes[i].nodeName == st) {
  114. //获取标题文本
  115. let nodetext = nodes[i].innerHTML.replace(/<\/?[^>]+>/g, "");//innerHTML里面的内容可能有HTML标签,所以用正则表达式去除HTML的标签
  116. nodetext = nodetext.replace(/ /ig, "");//替换掉所有的
  117. nodetext = BlogDirectory.htmlDecode(nodetext);
  118. //插入锚
  119. nodes[i].setAttribute("id", "blogTitle" + num);
  120. let item;
  121. switch (nodes[i].nodeName) {
  122. case mt: //若为主标题
  123. item = document.createElement("dt");
  124. break;
  125. case st: //若为子标题
  126. item = document.createElement("dd");
  127. break;
  128. }
  129. //创建锚链接
  130. let itemtext = document.createTextNode(nodetext);
  131. item.appendChild(itemtext);
  132. item.setAttribute("name", num);
  133. //添加鼠标点击触发函数
  134. item.onclick = function () {
  135. let pos = BlogDirectory.getElementPosition(document.getElementById("blogTitle" + this.getAttribute("name")));
  136. if (!BlogDirectory.moveScrollBar(pos.top, interval)) return false;
  137. };
  138. //将自定义表项加入自定义列表中
  139. dlist.appendChild(item);
  140. num++;
  141. }
  142. }
  143. if (num == 0) return false;
  144. /* 鼠标进入时的事件处理 */
  145. divSideBarTab.onmouseenter = function () {
  146. divSideBarContents.style.display = 'block';
  147. }
  148. /* 鼠标离开时的事件处理 */
  149. divSideBar.onmouseleave = function () {
  150. divSideBarContents.style.display = 'none';
  151. }
  152. document.body.appendChild(divSideBar);
  153. }
  154. };