diff --git a/static/css/main.css b/static/css/main.css index 39d502f7..b0a5e07f 100644 --- a/static/css/main.css +++ b/static/css/main.css @@ -963,3 +963,34 @@ h4.see-also { overflow-x: auto; overflow-y: hidden; } + + + .highlight { + box-sizing: border-box; + padding: 10px; + position: relative; + } + + .copyCodeButton { + background-color: #f5f5f5; + border: 1px solid #ccc; + color: black; + cursor: pointer; + display: none; + font-size: 14px; + padding: 5px 10px; + position: absolute; + right: 10px; + top: 10px; + transition: background-color 0.3s ease; + z-index: 10; + } + + .highlight:hover .copyCodeButton { + display: block; + } + + .copyCodeButton:hover { + background-color: #e0e0e0; + } + diff --git a/static/js/main.js b/static/js/main.js index 99200c7d..0129c5c2 100644 --- a/static/js/main.js +++ b/static/js/main.js @@ -179,4 +179,50 @@ var main = { // 2fc73a3a967e97599c9763d05e564189 -document.addEventListener('DOMContentLoaded', main.init); \ No newline at end of file +document.addEventListener('DOMContentLoaded', main.init); +/** + * Add copy button to code block + */ +document.addEventListener('DOMContentLoaded', () => { + const highlights = document.querySelectorAll('.row div.highlight'); + const copyText = '📋'; + const copiedText = '✔️'; + + highlights.forEach((highlight) => { + const copyButton = document.createElement('button'); + copyButton.innerHTML = copyText; + copyButton.classList.add('copyCodeButton'); + highlight.appendChild(copyButton); + + const codeBlock = highlight.querySelector('code[data-lang]'); + if (!codeBlock) return; + + copyButton.addEventListener('click', () => { + // Create a deep clone of the code block + const codeBlockClone = codeBlock.cloneNode(true); + + // Remove line number elements from the clone + const lineNumbers = codeBlockClone.querySelectorAll('.ln'); + lineNumbers.forEach(ln => ln.remove()); + + // Get the text content, splitting by lines, trimming each line, and joining back + const codeText = codeBlockClone.textContent + .split('\n') // Split into lines + .map(line => line.trim()) // Trim each line + .join('\n'); // Join lines back with newline + + navigator.clipboard.writeText(codeText) + .then(() => { + copyButton.textContent = copiedText; + + setTimeout(() => { + copyButton.textContent = copyText; + }, 1000); + }) + .catch((err) => { + alert('Failed to copy text'); + console.error('Something went wrong', err); + }); + }); + }); +});