feat: add code block copy feature

This commit is contained in:
XPoet 2020-04-18 17:26:29 +08:00
parent cf5b9e0e32
commit b46e1edb90
7 changed files with 68 additions and 6 deletions

View File

@ -15,7 +15,7 @@ menu:
# RSS # RSS
rss: rss:
enable: false enable: true
# favicon # favicon
favicon: images/favicon.png favicon: images/favicon.png
@ -66,4 +66,10 @@ local_search:
# Unescape html strings to the readable one. # Unescape html strings to the readable one.
unescape: false unescape: false
# Preload the search data when the page loads. # Preload the search data when the page loads.
preload: false preload: false
# Code Block
codeblock:
style: flat # Available values: default | flat | mac
copy_button:
enable: true

View File

@ -1 +1,9 @@
<%- js(['js/main.js', 'js/header-shrink.js', 'js/toggle-mode.js', 'js/scroll-to-top.js']) %> <%- js([
'js/main.js',
'js/header-shrink.js',
'js/toggle-mode.js',
'js/scroll-to-top.js'
]) %>
<% if (theme.codeblock.copy_button.enable) { %>
<%- js('js/code-copy.js') %>
<% } %>

View File

@ -15,7 +15,7 @@ $code-block {
} }
&::-webkit-scrollbar-thumb { &::-webkit-scrollbar-thumb {
border-radius: 5px; border-radius: 1px;
background: rgba(0, 0, 0, 0.3) background: rgba(0, 0, 0, 0.3)
} }
@ -60,6 +60,7 @@ pre {
padding: 10px 0; padding: 10px 0;
} }
table { table {
margin: 0; margin: 0;
width: auto; width: auto;
@ -67,6 +68,7 @@ pre {
border-spacing: unset; border-spacing: unset;
} }
td { td {
border: none; border: none;
padding: 0; padding: 0;

View File

@ -25,7 +25,7 @@ $z-index-6 = 1006;
// color // color
// =============================== // ===============================
// normal mode color // normal mode color
$primary-color = #f04c12; // $primary-color = #1b65ea; //
$background-color = #fdfdfd; // $background-color = #fdfdfd; //
$normal-text-color = #44424e; // $normal-text-color = #44424e; //
$first-text-color = darken($normal-text-color, 15%); // $first-text-color = darken($normal-text-color, 15%); //

View File

@ -16,4 +16,5 @@
@import "layout/category-content.styl" @import "layout/category-content.styl"
@import "layout/tag-content.styl" @import "layout/tag-content.styl"
@import "layout/common/markdown.styl" @import "layout/common/markdown.styl"
@import "layout/common/highlight/highlight.styl" @import "layout/common/codeblock/highlight.styl"
@import "layout/common/codeblock/copy-code.styl"

45
source/js/code-copy.js Normal file
View File

@ -0,0 +1,45 @@
HTMLElement.prototype.wrap = function (wrapper) {
this.parentNode.insertBefore(wrapper, this);
this.parentNode.removeChild(this);
wrapper.appendChild(this);
};
window.addEventListener('DOMContentLoaded', () => {
document.querySelectorAll('figure.highlight').forEach(element => {
const box = document.createElement('div');
element.wrap(box);
box.classList.add('highlight-container');
box.insertAdjacentHTML('beforeend', '<div class="copy-btn"><i class="fa fa-clipboard"></i></div>');
var button = element.parentNode.querySelector('.copy-btn');
button.addEventListener('click', event => {
var target = event.currentTarget;
var code = [...target.parentNode.querySelectorAll('.code .line')].map(line => line.innerText).join('\n');
var ta = document.createElement('textarea');
ta.style.top = window.scrollY + 'px'; // Prevent page scrolling
ta.style.position = 'absolute';
ta.style.opacity = '0';
ta.readOnly = true;
ta.value = code;
document.body.append(ta);
const selection = document.getSelection();
const selected = selection.rangeCount > 0 ? selection.getRangeAt(0) : false;
ta.select();
ta.setSelectionRange(0, code.length);
ta.readOnly = false;
var result = document.execCommand('copy');
target.querySelector('i').className = result ? 'fa fa-check' : 'fa fa-times';
ta.blur(); // For iOS
target.blur();
if (selected) {
selection.removeAllRanges();
selection.addRange(selected);
}
document.body.removeChild(ta);
});
button.addEventListener('mouseleave', event => {
setTimeout(() => {
event.target.querySelector('i').className = 'fa fa-clipboard';
}, 300);
});
});
});