diff --git a/README.md b/README.md index c3f0506..aa58235 100644 --- a/README.md +++ b/README.md @@ -165,8 +165,10 @@ darkmode: true # ClickLove clickLove: false -# ClickBoom +# ClickBoom style 1 clickBoom: false +# ClickBoom style 2 +clickBoom2: false # articleWidth and sidebarWidth layout: diff --git a/_config.yml b/_config.yml index f5c82a3..63a2e40 100644 --- a/_config.yml +++ b/_config.yml @@ -98,8 +98,10 @@ darkmode: true # 页面点击小红心(开启请设置为true) clickLove: false -# 页面点击烟花效果(开启请设置为true) +# 页面点击-粒子烟花效果(开启请设置为true) clickBoom: false +# 页面点击-爆炸烟花效果(开启请设置为true) +clickBoom2: false # 页面宽度自定义(不建议修改,可能造成布局混乱),article_width文章宽度,sidebar_width侧边栏宽度 layout: @@ -131,20 +133,6 @@ gitalk: owner: # GitHub ID admin: # GitHub ID -# 3、MiniValine -# See: https://github.com/MiniValine/MiniValine -minivaline: - enable: false - placeholder: Write a Comment # Comment box placeholder - adminEmailMd5: # The MD5 of Admin Email to show Admin Flag. - math: true # Support MathJax. - md: true # Support Markdown. - # MiniValine's display language depends on user's browser or system environment - # If you want everyone visiting your site to see a uniform language, you can set a force language value - # Available values: en | zh-CN | (and many more) - # More i18n info: https://github.com/MiniValine/minivaline-i18n - lang: - # GitHub Ribbons-封面右上角的forkme,换样式直接在source/images目录下替换forkme图片 github: # (关闭请设置为false) diff --git a/layout/_partial/after-footer.ejs b/layout/_partial/after-footer.ejs index 7a8d47b..0620102 100644 --- a/layout/_partial/after-footer.ejs +++ b/layout/_partial/after-footer.ejs @@ -67,6 +67,11 @@ <% if (theme.clickBoom){ %> <%- js('/js/clickBoom') %> <% } %> + +<% if (theme.clickBoom2){ %> + +<%- js('/js/clickBoom2') %> +<% } %> <% if (theme.copy_btn == true) { %> <%- css('/css/clipboard') %> diff --git a/layout/layout.ejs b/layout/layout.ejs index 2ba1906..98e395c 100644 --- a/layout/layout.ejs +++ b/layout/layout.ejs @@ -2,7 +2,20 @@ <% if (theme.clickBoom){ %> - + + <% } %> + <% if (theme.clickBoom2){ %> + + <% } %>
diff --git a/source/js/clickBoom2.js b/source/js/clickBoom2.js new file mode 100644 index 0000000..69b899b --- /dev/null +++ b/source/js/clickBoom2.js @@ -0,0 +1,152 @@ +const numberOfParticules = 20; + +const minOrbitRadius = 50; +const maxOrbitRadius = 100; + +const minCircleRadius = 10; +const maxCircleRadius = 20; + +const minAnimeDuration = 900; +const maxAnimeDuration = 1500; + +const minDiffuseRadius = 50; +const maxDiffuseRadius = 100; + +let canvasEl = document.querySelector(".fireworks"); +let ctx = canvasEl.getContext("2d"); +let pointerX = 0; +let pointerY = 0; + +let tap = + "ontouchstart" in window || navigator.msMaxTouchPoints + ? "touchstart" + : "mousedown"; + +// sea blue +let colors = ["127, 180, 226", "157, 209, 243", "204, 229, 255"]; + +function setCanvasSize() { + canvasEl.width = window.innerWidth; + canvasEl.height = window.innerHeight; + canvasEl.style.width = window.innerWidth + "px"; + canvasEl.style.height = window.innerHeight + "px"; +} + +function updateCoords(e) { + pointerX = e.clientX || e.touches[0].clientX; + pointerY = e.clientY || e.touches[0].clientY; +} + +function setParticuleDirection(p) { + let angle = (anime.random(0, 360) * Math.PI) / 180; + let value = anime.random(minDiffuseRadius, maxDiffuseRadius); + let radius = [-1, 1][anime.random(0, 1)] * value; + return { + x: p.x + radius * Math.cos(angle), + y: p.y + radius * Math.sin(angle) + }; +} + +function createParticule(x, y) { + let p = {}; + p.x = x; + p.y = y; + p.color = + "rgba(" + + colors[anime.random(0, colors.length - 1)] + + "," + + anime.random(0.2, 0.8) + + ")"; + p.radius = anime.random(minCircleRadius, maxCircleRadius); + p.endPos = setParticuleDirection(p); + p.draw = function () { + ctx.beginPath(); + ctx.arc(p.x, p.y, p.radius, 0, 2 * Math.PI, true); + ctx.fillStyle = p.color; + ctx.fill(); + }; + return p; +} + +function createCircle(x, y) { + let p = {}; + p.x = x; + p.y = y; + p.color = "#000"; + p.radius = 0.1; + p.alpha = 0.5; + p.lineWidth = 6; + p.draw = function () { + ctx.globalAlpha = p.alpha; + ctx.beginPath(); + ctx.arc(p.x, p.y, p.radius, 0, 2 * Math.PI, true); + ctx.lineWidth = p.lineWidth; + ctx.strokeStyle = p.color; + ctx.stroke(); + ctx.globalAlpha = 1; + }; + return p; +} + +function renderParticule(anim) { + for (let i = 0; i < anim.animatables.length; i++) { + anim.animatables[i].target.draw(); + } +} + +function animateParticules(x, y) { + let circle = createCircle(x, y); + let particules = []; + for (let i = 0; i < numberOfParticules; i++) { + particules.push(createParticule(x, y)); + } + anime + .timeline() + .add({ + targets: particules, + x: function (p) { + return p.endPos.x; + }, + y: function (p) { + return p.endPos.y; + }, + radius: 0.1, + duration: anime.random(minAnimeDuration, maxAnimeDuration), + easing: "easeOutExpo", + update: renderParticule + }) + .add({ + targets: circle, + radius: anime.random(minOrbitRadius, maxOrbitRadius), + lineWidth: 0, + alpha: { + value: 0, + easing: "linear", + duration: anime.random(600, 800) + }, + duration: anime.random(1200, 1800), + easing: "easeOutExpo", + update: renderParticule, + offset: 0 + }); +} + +let render = anime({ + duration: Infinity, + update: function () { + ctx.clearRect(0, 0, canvasEl.width, canvasEl.height); + } +}); + +document.addEventListener( + tap, + function (e) { + render.play(); + updateCoords(e); + animateParticules(pointerX, pointerY); + }, + false +); + +setCanvasSize(); +window.addEventListener("resize", setCanvasSize, false);