2019-02-03 12:30:44 +01:00
|
|
|
jQuery(function($) {
|
|
|
|
|
|
|
|
'use strict';
|
|
|
|
|
|
|
|
var _Blog = window._Blog || {};
|
|
|
|
|
2019-08-11 19:36:19 +02:00
|
|
|
_Blog.toggleMobileMenu = function() {
|
2019-08-24 13:32:41 +02:00
|
|
|
$('#menu-toggle').on('click', () => {
|
|
|
|
$('#menu-toggle').toggleClass('active');
|
2020-02-13 18:30:33 +01:00
|
|
|
$('#menu-mobile').toggleClass('active');
|
2019-08-11 19:36:19 +02:00
|
|
|
});
|
|
|
|
};
|
|
|
|
|
2019-08-21 22:01:02 +02:00
|
|
|
_Blog.toggleTheme = function() {
|
2019-08-11 19:36:19 +02:00
|
|
|
$('.theme-switch').on('click', () => {
|
|
|
|
$('body').toggleClass('dark-theme');
|
2020-02-08 15:19:22 +01:00
|
|
|
window.isDark = !window.isDark;
|
|
|
|
window.localStorage && window.localStorage.setItem('theme', window.isDark ? 'dark' : 'light');
|
2019-08-21 22:01:02 +02:00
|
|
|
this.echarts();
|
2019-08-11 19:36:19 +02:00
|
|
|
});
|
|
|
|
};
|
|
|
|
|
|
|
|
_Blog.changeTitle = function() {
|
|
|
|
var currentTitle = document.title;
|
|
|
|
window.onblur = function() {
|
|
|
|
document.title = currentTitle;
|
|
|
|
};
|
|
|
|
window.onfocus = function() {
|
|
|
|
document.title = currentTitle;
|
|
|
|
};
|
|
|
|
};
|
|
|
|
|
2019-08-22 20:01:22 +02:00
|
|
|
_Blog.dynamicToTop = function() {
|
|
|
|
const min = 300;
|
|
|
|
var $toTop = $('#dynamic-to-top');
|
2019-11-23 18:10:17 +01:00
|
|
|
$(window).scroll(() => {
|
2019-08-24 13:32:41 +02:00
|
|
|
var scrollTop = $(window).scrollTop();
|
|
|
|
if (typeof document.body.style.maxHeight === 'undefined') {
|
|
|
|
$toTop.css({
|
|
|
|
'position': 'absolute',
|
|
|
|
'top': scrollTop + $(window).height() - 20,
|
|
|
|
});
|
|
|
|
}
|
|
|
|
if (scrollTop > min) {
|
|
|
|
(function fadeIn(el, display){
|
|
|
|
display = display || "block";
|
|
|
|
if (el.style.display !== display) {
|
|
|
|
el.style.opacity = 0;
|
|
|
|
el.style.display = display;
|
|
|
|
(function fade() {
|
|
|
|
var val = parseFloat(el.style.opacity);
|
|
|
|
if (!((val += .1) > 1)) {
|
|
|
|
el.style.opacity = val;
|
|
|
|
requestAnimationFrame(fade);
|
|
|
|
}
|
|
|
|
})();
|
|
|
|
}
|
|
|
|
})(document.getElementById('dynamic-to-top'));
|
|
|
|
} else {
|
|
|
|
(function fadeOut(el){
|
|
|
|
if (el.style.display !== "none") {
|
|
|
|
el.style.opacity = 1;
|
|
|
|
(function fade() {
|
|
|
|
if ((el.style.opacity -= .1) < 0) {
|
|
|
|
el.style.display = "none";
|
|
|
|
} else {
|
|
|
|
requestAnimationFrame(fade);
|
|
|
|
}
|
|
|
|
})();
|
|
|
|
}
|
|
|
|
})(document.getElementById('dynamic-to-top'));
|
|
|
|
}
|
|
|
|
});
|
2019-08-22 20:01:22 +02:00
|
|
|
};
|
|
|
|
|
2020-01-31 18:52:27 +01:00
|
|
|
_Blog.chroma = function () {
|
2019-08-11 19:36:19 +02:00
|
|
|
const blocks = document.querySelectorAll('.highlight > .chroma');
|
|
|
|
for (let i = 0; i < blocks.length; i++) {
|
|
|
|
const block = blocks[i];
|
2020-01-31 18:52:27 +01:00
|
|
|
const codes = block.querySelectorAll('pre.chroma > code');
|
|
|
|
const code = codes[codes.length - 1];
|
|
|
|
const lang = code ? code.className.toLowerCase() : '';
|
2019-08-11 19:36:19 +02:00
|
|
|
block.className += ' ' + lang;
|
|
|
|
}
|
2020-02-10 13:34:57 +01:00
|
|
|
|
|
|
|
const nolinenosBlocks = document.querySelectorAll('.highlight > pre.chroma');
|
|
|
|
for (let i = 0; i < nolinenosBlocks.length; i++) {
|
|
|
|
const block = nolinenosBlocks[i];
|
|
|
|
const chroma = document.createElement('div');
|
|
|
|
chroma.className = block.className;
|
|
|
|
const table = document.createElement('table');
|
|
|
|
chroma.appendChild(table);
|
|
|
|
const tbody = document.createElement('tbody');
|
|
|
|
table.appendChild(tbody);
|
|
|
|
const tr = document.createElement('tr');
|
|
|
|
tbody.appendChild(tr);
|
|
|
|
const td = document.createElement('td');
|
|
|
|
tr.appendChild(td);
|
|
|
|
block.parentElement.replaceChild(chroma, block);
|
|
|
|
td.appendChild(block);
|
|
|
|
}
|
2019-08-11 19:36:19 +02:00
|
|
|
};
|
|
|
|
|
2019-08-17 17:16:09 +02:00
|
|
|
_Blog.responsiveTable = function() {
|
2020-02-13 18:30:33 +01:00
|
|
|
const tables = document.querySelectorAll('.content table');
|
2019-08-17 17:16:09 +02:00
|
|
|
for (let i = 0; i < tables.length; i++) {
|
|
|
|
const table = tables[i];
|
|
|
|
const wrapper = document.createElement('div');
|
|
|
|
wrapper.className = 'table-wrapper';
|
|
|
|
table.parentElement.replaceChild(wrapper, table);
|
|
|
|
wrapper.appendChild(table);
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
2019-08-21 22:01:02 +02:00
|
|
|
_Blog._refactorToc = function(toc) {
|
|
|
|
// when headings do not start with `h1`
|
|
|
|
const oldTocList = toc.children[0];
|
|
|
|
let newTocList = oldTocList;
|
|
|
|
let temp;
|
|
|
|
while (newTocList.children.length === 1
|
|
|
|
&& (temp = newTocList.children[0].children[0]).tagName === 'UL') {
|
|
|
|
newTocList = temp;
|
|
|
|
}
|
|
|
|
if (newTocList !== oldTocList) toc.replaceChild(newTocList, oldTocList);
|
|
|
|
};
|
|
|
|
|
|
|
|
_Blog._linkToc = function() {
|
|
|
|
const links = document.querySelectorAll('#TableOfContents a:first-child');
|
|
|
|
for (let i = 0; i < links.length; i++) links[i].className += ' toc-link';
|
|
|
|
|
|
|
|
for (let num = 1; num <= 6; num++) {
|
2020-02-13 18:30:33 +01:00
|
|
|
const headers = document.querySelectorAll('.content>h' + num);
|
2019-08-21 22:01:02 +02:00
|
|
|
for (let i = 0; i < headers.length; i++) {
|
|
|
|
const header = headers[i];
|
2019-08-26 09:17:21 +02:00
|
|
|
header.innerHTML = `<a href="#${header.id}" class="headerlink"></a>${header.innerHTML}`;
|
2019-08-21 22:01:02 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
2019-08-17 17:16:09 +02:00
|
|
|
_Blog._initToc = function() {
|
2019-08-24 13:32:41 +02:00
|
|
|
const $toc = $('#post-toc');
|
2019-08-21 22:01:02 +02:00
|
|
|
if ($toc.length && $toc.css('display') !== 'none') {
|
2020-02-02 07:43:29 +01:00
|
|
|
const SPACING = 80;
|
2019-08-24 13:32:41 +02:00
|
|
|
const $footer = $('#post-footer');
|
2019-08-21 22:01:02 +02:00
|
|
|
const minTop = $toc.position().top;;
|
2019-08-18 19:36:52 +02:00
|
|
|
const mainTop = $('main').position().top;
|
|
|
|
const minScrollTop = minTop + mainTop - SPACING;
|
2019-08-19 15:14:15 +02:00
|
|
|
const changeTocState = function() {
|
2019-08-18 19:36:52 +02:00
|
|
|
const scrollTop = $(window).scrollTop();
|
|
|
|
const maxTop = $footer.position().top - $toc.height();
|
|
|
|
const maxScrollTop = maxTop + mainTop - SPACING;
|
|
|
|
|
|
|
|
const tocState = {
|
|
|
|
start: {
|
|
|
|
'position': 'absolute',
|
|
|
|
'top': minTop,
|
|
|
|
},
|
|
|
|
process: {
|
|
|
|
'position': 'fixed',
|
|
|
|
'top': SPACING,
|
|
|
|
},
|
|
|
|
end: {
|
|
|
|
'position': 'absolute',
|
|
|
|
'top': maxTop,
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
|
|
|
if (scrollTop < minScrollTop) {
|
|
|
|
$toc.css(tocState.start);
|
|
|
|
} else if (scrollTop > maxScrollTop) {
|
|
|
|
$toc.css(tocState.end);
|
|
|
|
} else {
|
|
|
|
$toc.css(tocState.process);
|
|
|
|
}
|
|
|
|
};
|
2019-08-19 15:14:15 +02:00
|
|
|
changeTocState();
|
|
|
|
|
|
|
|
const $toclink = $('.toc-link');
|
2020-02-09 03:27:30 +01:00
|
|
|
const $headerDummyLink = $('.post-dummy-target');
|
2019-08-19 15:14:15 +02:00
|
|
|
const $tocLinkLis = $('.post-toc-content li');
|
2020-01-31 11:46:28 +01:00
|
|
|
const activeIndex = function () {
|
2019-08-19 15:14:15 +02:00
|
|
|
const scrollTop = $(window).scrollTop();
|
2020-02-09 03:27:30 +01:00
|
|
|
const headerlinkTop = $.map($headerDummyLink, function(link) {
|
2019-08-19 15:14:15 +02:00
|
|
|
return $(link).offset().top;
|
|
|
|
});
|
|
|
|
const searchActiveTocIndex = function(array, target) {
|
|
|
|
for (let i = 0; i < array.length - 1; i++) {
|
2020-01-31 11:46:28 +01:00
|
|
|
if ( target < array[i + 1]) return i;
|
2019-08-19 15:14:15 +02:00
|
|
|
}
|
2020-01-31 11:46:28 +01:00
|
|
|
return array.length - 1;
|
2019-08-19 15:14:15 +02:00
|
|
|
};
|
2019-08-18 19:36:52 +02:00
|
|
|
|
2020-02-11 08:22:22 +01:00
|
|
|
const activeTocIndex = searchActiveTocIndex(headerlinkTop, scrollTop);
|
2019-08-17 17:16:09 +02:00
|
|
|
|
2019-08-19 15:14:15 +02:00
|
|
|
$($toclink).removeClass('active');
|
|
|
|
$($tocLinkLis).removeClass('has-active');
|
2019-08-17 17:16:09 +02:00
|
|
|
|
2019-08-19 15:14:15 +02:00
|
|
|
if (activeTocIndex !== -1) {
|
|
|
|
$($toclink[activeTocIndex]).addClass('active');
|
|
|
|
let ancestor = $toclink[activeTocIndex].parentNode;
|
|
|
|
while (ancestor.tagName !== 'NAV') {
|
|
|
|
$(ancestor).addClass('has-active');
|
|
|
|
ancestor = ancestor.parentNode.parentNode;
|
|
|
|
}
|
2019-08-17 17:16:09 +02:00
|
|
|
}
|
2019-08-19 15:14:15 +02:00
|
|
|
};
|
|
|
|
activeIndex();
|
2019-08-21 18:32:52 +02:00
|
|
|
if (!this._initTocOnce) {
|
|
|
|
$(window).scroll(changeTocState);
|
|
|
|
$(window).scroll(activeIndex);
|
|
|
|
this._initTocOnce = true;
|
|
|
|
}
|
2019-08-19 15:14:15 +02:00
|
|
|
}
|
2019-08-17 17:16:09 +02:00
|
|
|
};
|
|
|
|
|
|
|
|
_Blog.toc = function() {
|
|
|
|
const tocContainer = document.getElementById('post-toc');
|
|
|
|
if (tocContainer !== null) {
|
|
|
|
const toc = document.getElementById('TableOfContents');
|
|
|
|
if (toc === null) {
|
2019-08-21 18:32:52 +02:00
|
|
|
// toc = true, but there are no headings
|
|
|
|
tocContainer.parentNode.removeChild(tocContainer);
|
2019-08-17 17:16:09 +02:00
|
|
|
} else {
|
2019-08-21 18:32:52 +02:00
|
|
|
this._refactorToc(toc);
|
|
|
|
this._linkToc();
|
|
|
|
this._initToc();
|
|
|
|
// Listen for orientation changes
|
2019-08-22 20:54:26 +02:00
|
|
|
window.addEventListener("resize", function() {
|
2019-08-21 22:01:02 +02:00
|
|
|
this.setTimeout(_Blog._initToc, 0);
|
|
|
|
}, false);
|
2019-08-17 17:16:09 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
2019-11-23 18:10:17 +01:00
|
|
|
_Blog.mermaid = function() {
|
|
|
|
if (window.mermaidMap) {
|
|
|
|
const mermaidAPI = mermaid.mermaidAPI
|
|
|
|
Object.keys(mermaidMap).forEach((id) => {
|
|
|
|
const element = document.getElementById(id);
|
|
|
|
mermaidAPI.render("d" + id, mermaidMap[id], (svgCode) => {
|
|
|
|
element.innerHTML = svgCode;
|
|
|
|
const svg = element.firstChild;
|
|
|
|
svg.style.width = "100%"
|
|
|
|
}, element);
|
|
|
|
});
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-08-21 22:01:02 +02:00
|
|
|
_Blog.echarts = function() {
|
2019-08-17 17:16:09 +02:00
|
|
|
if (window.echartsMap) {
|
|
|
|
for (let i = 0; i < echartsArr.length; i++) {
|
|
|
|
echartsArr[i].dispose();
|
|
|
|
}
|
|
|
|
echartsArr = [];
|
2019-11-23 18:10:17 +01:00
|
|
|
Object.keys(echartsMap).forEach((id) => {
|
2019-08-24 13:32:41 +02:00
|
|
|
let myChart = echarts.init(document.getElementById(id), window.isDark ? 'dark' : 'macarons', {renderer: 'svg'});
|
2019-08-17 17:16:09 +02:00
|
|
|
myChart.setOption(echartsMap[id]);
|
|
|
|
echartsArr.push(myChart);
|
|
|
|
});
|
2019-08-24 13:32:41 +02:00
|
|
|
window.addEventListener("resize", function() {
|
2019-11-23 18:10:17 +01:00
|
|
|
this.setTimeout(() => {
|
2019-08-24 13:32:41 +02:00
|
|
|
for (let i = 0; i < echartsArr.length; i++) {
|
|
|
|
echartsArr[i].resize();
|
|
|
|
}
|
|
|
|
}, 0);
|
|
|
|
}, false);
|
2019-08-17 17:16:09 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-08-11 19:36:19 +02:00
|
|
|
_Blog.countdown = function() {
|
|
|
|
if (window.countdownMap) {
|
2019-08-16 21:40:34 +02:00
|
|
|
Object.keys(countdownMap).forEach(function(id) {
|
2019-08-24 13:32:41 +02:00
|
|
|
$(`#${id}`).countdown(countdownMap[id]['date'], {elapse: true})
|
|
|
|
.on('update.countdown', function(event) {
|
|
|
|
$(this).html(event.strftime(countdownMap[id]['pattern']));
|
|
|
|
});
|
|
|
|
});
|
2019-08-11 19:36:19 +02:00
|
|
|
}
|
|
|
|
};
|
|
|
|
|
2019-08-07 23:01:18 +02:00
|
|
|
_Blog.typeit = function() {
|
2019-08-16 21:40:34 +02:00
|
|
|
if (window.typeitArr) {
|
|
|
|
for (let i = 0; i < typeitArr.length; i++) {
|
|
|
|
const group = typeitArr[i];
|
2020-01-29 15:16:50 +01:00
|
|
|
(function typeone(i) {
|
|
|
|
const content = document.getElementById(`r${group[i]}`).innerHTML;
|
2019-08-16 21:40:34 +02:00
|
|
|
if (i === group.length - 1) {
|
|
|
|
new TypeIt(`#${group[i]}`, {
|
2020-01-29 15:16:50 +01:00
|
|
|
strings: content,
|
2019-08-10 21:26:03 +02:00
|
|
|
}).go();
|
2019-08-16 21:40:34 +02:00
|
|
|
return;
|
|
|
|
}
|
|
|
|
let instance = new TypeIt(`#${group[i]}`, {
|
2020-01-29 15:16:50 +01:00
|
|
|
strings: content,
|
2019-08-16 21:40:34 +02:00
|
|
|
afterComplete: () => {
|
|
|
|
instance.destroy();
|
|
|
|
typeone(i + 1);
|
|
|
|
},
|
2019-08-10 21:26:03 +02:00
|
|
|
}).go();
|
2019-08-16 21:40:34 +02:00
|
|
|
})(0);
|
2019-08-07 23:01:18 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
2019-11-23 18:10:17 +01:00
|
|
|
$(document).ready(() => {
|
2019-08-11 19:36:19 +02:00
|
|
|
_Blog.toggleMobileMenu();
|
2019-08-21 22:01:02 +02:00
|
|
|
_Blog.toggleTheme();
|
2019-08-09 15:25:13 +02:00
|
|
|
_Blog.changeTitle();
|
2019-08-22 20:01:22 +02:00
|
|
|
_Blog.dynamicToTop();
|
2019-08-11 19:36:19 +02:00
|
|
|
_Blog.chroma();
|
2019-08-17 17:16:09 +02:00
|
|
|
_Blog.responsiveTable();
|
2019-11-23 18:10:17 +01:00
|
|
|
_Blog.mermaid();
|
2019-08-21 22:01:02 +02:00
|
|
|
_Blog.echarts();
|
2019-08-11 19:36:19 +02:00
|
|
|
_Blog.countdown();
|
2019-08-09 15:25:13 +02:00
|
|
|
_Blog.typeit();
|
2019-08-18 19:36:52 +02:00
|
|
|
_Blog.toc();
|
2019-02-03 12:30:44 +01:00
|
|
|
});
|
2020-01-31 18:52:27 +01:00
|
|
|
});
|