added 代码折叠 修复bug
This commit is contained in:
1 parent
c115c7c0fb
commit
33a6ce2d85
4 files changed
+199
-22
No files matched your search
@@ -88,27 +88,38 @@ async function processFiles(dir) {
|
|||||||
window.artalk.on('list-loaded', function() {
|
window.artalk.on('list-loaded', function() {
|
||||||
// 检查是否有 AI 评论数据
|
// 检查是否有 AI 评论数据
|
||||||
if (window.artalkConfig.aiComment && !document.querySelector('.atk-ai-comment')) {
|
if (window.artalkConfig.aiComment && !document.querySelector('.atk-ai-comment')) {
|
||||||
|
var listBody = document.querySelector('.atk-list-body') || document.querySelector('.atk-list');
|
||||||
|
|
||||||
|
if (listBody) {
|
||||||
|
// 避免同时出现“此时无声胜有声”
|
||||||
|
var noComment = document.querySelector('.atk-list-no-comment');
|
||||||
|
if (noComment) noComment.style.display = 'none';
|
||||||
|
|
||||||
// 创建 DOM 结构
|
// 创建 DOM 结构
|
||||||
var aiDiv = document.createElement('div');
|
var aiDiv = document.createElement('div');
|
||||||
aiDiv.className = 'atk-comment atk-ai-comment';
|
aiDiv.className = 'atk-comment atk-ai-comment';
|
||||||
aiDiv.innerHTML = `...`; // 填充 HTML
|
aiDiv.innerHTML = `...`; // 填充 HTML
|
||||||
|
|
||||||
// 插入到列表头部
|
// 插入到列表头部
|
||||||
var listBody = document.querySelector('.atk-list-body');
|
listBody.prepend(aiDiv);
|
||||||
if (listBody) listBody.prepend(aiDiv);
|
|
||||||
|
|
||||||
// 简单的打字机效果
|
// ... (打字机效果)
|
||||||
const contentEl = aiDiv.querySelector('.ai-content-text');
|
|
||||||
const text = window.artalkConfig.aiComment.content;
|
|
||||||
let i = 0;
|
|
||||||
function type() {
|
|
||||||
if (i < text.length) {
|
|
||||||
contentEl.textContent += text.charAt(i);
|
|
||||||
i++;
|
|
||||||
setTimeout(type, Math.random() * 30 + 20);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
setTimeout(type, 500);
|
});
|
||||||
|
```
|
||||||
|
|
||||||
|
## 4. 适配 PJAX
|
||||||
|
|
||||||
|
由于博客使用了 PJAX,页面切换时需要重新初始化 Artalk。我们将初始化逻辑封装在 `initArtalk` 函数中,并在 `pjax:complete` 事件中调用。
|
||||||
|
|
||||||
|
```javascript
|
||||||
|
// mypjax.js
|
||||||
|
document.addEventListener("pjax:complete", function () {
|
||||||
|
// ...
|
||||||
|
// 重载评论
|
||||||
|
if (typeof window.initArtalk === 'function') {
|
||||||
|
window.initArtalk();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
```
|
```
|
||||||
|
|||||||
@@ -196,8 +196,102 @@ code {
|
|||||||
background-color: #f6f8fa; /* Day Mode */
|
background-color: #f6f8fa; /* Day Mode */
|
||||||
color: #24292e;
|
color: #24292e;
|
||||||
border: 1px solid #d0d7de;
|
border: 1px solid #d0d7de;
|
||||||
|
/* Hide scrollbar but allow scrolling */
|
||||||
|
scrollbar-width: none; /* Firefox */
|
||||||
|
-ms-overflow-style: none; /* IE 10+ */
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pre::-webkit-scrollbar,
|
||||||
|
code::-webkit-scrollbar {
|
||||||
|
display: none; /* Chrome/Safari/Webkit */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Code Folding */
|
||||||
|
.code-fold-container {
|
||||||
|
position: relative;
|
||||||
|
margin-bottom: 1rem;
|
||||||
|
border-radius: 4px; /* Optional: match highlight radius */
|
||||||
|
}
|
||||||
|
|
||||||
|
.code-fold-container.collapsed {
|
||||||
|
max-height: 360px;
|
||||||
|
overflow: hidden;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Ensure inner code blocks don't have bottom margin when wrapped */
|
||||||
|
.code-fold-container .highlight,
|
||||||
|
.code-fold-container pre {
|
||||||
|
margin-bottom: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
.code-expand-btn {
|
||||||
|
display: none;
|
||||||
|
position: absolute;
|
||||||
|
bottom: -7px;
|
||||||
|
left: -146px;
|
||||||
|
width: 100%;
|
||||||
|
height: 80px;
|
||||||
|
text-align: center;
|
||||||
|
/* Gradient Background for Fade Effect */
|
||||||
|
background: linear-gradient(180deg, rgba(246, 248, 250, 0) 0%, rgba(246, 248, 250, 0.9) 50%, rgba(246, 248, 250, 1) 100%);
|
||||||
|
border: none;
|
||||||
|
color: #586069;
|
||||||
|
cursor: pointer;
|
||||||
|
z-index: 10;
|
||||||
|
font-size: 13px;
|
||||||
|
transition: all 0.2s;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
padding-top: 20px;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Show button when collapsed */
|
||||||
|
.code-fold-container.collapsed .code-expand-btn {
|
||||||
|
display: flex;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Button Pill Style */
|
||||||
|
.code-expand-btn span {
|
||||||
|
background: rgba(255, 255, 255, 0.9);
|
||||||
|
padding: 6px 16px;
|
||||||
|
border-radius: 20px;
|
||||||
|
box-shadow: 0 2px 8px rgba(0,0,0,0.08);
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
border: 1px solid rgba(0,0,0,0.05);
|
||||||
|
transition: all 0.2s ease;
|
||||||
|
}
|
||||||
|
|
||||||
|
.code-expand-btn:hover span {
|
||||||
|
background: #fff;
|
||||||
|
transform: translateY(-2px);
|
||||||
|
box-shadow: 0 4px 12px rgba(0,0,0,0.12);
|
||||||
|
color: #0366d6;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Dark Mode Support */
|
||||||
|
[data-theme="dark"] .code-expand-btn {
|
||||||
|
background: linear-gradient(180deg, rgba(40, 42, 54, 0) 0%, rgba(40, 42, 54, 0.9) 50%, rgba(40, 42, 54, 1) 100%);
|
||||||
|
color: #f8f8f2;
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-theme="dark"] .code-expand-btn span {
|
||||||
|
background: rgba(68, 71, 90, 0.8);
|
||||||
|
border-color: rgba(255,255,255,0.05);
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-theme="dark"] .code-expand-btn:hover span {
|
||||||
|
background: #44475a;
|
||||||
|
color: #8be9fd;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Artalk AI Comment Integration */
|
||||||
|
.atk-list.has-ai-comment .atk-list-no-comment {
|
||||||
|
display: none !important;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
[data-theme="dark"] pre,
|
[data-theme="dark"] pre,
|
||||||
[data-theme="dark"] code {
|
[data-theme="dark"] code {
|
||||||
background-color: #282a36; /* Night Mode */
|
background-color: #282a36; /* Night Mode */
|
||||||
|
|||||||
@@ -114,7 +114,14 @@ window.initArtalk = function() {
|
|||||||
|
|
||||||
// Inject AI Comment
|
// Inject AI Comment
|
||||||
window.artalk.on('list-loaded', function() {
|
window.artalk.on('list-loaded', function() {
|
||||||
if (window.artalkConfig.aiComment && !document.querySelector('.atk-ai-comment')) {
|
if (window.artalkConfig.aiComment) {
|
||||||
|
// Force hide "No comments" message via CSS class
|
||||||
|
var list = document.querySelector('.atk-list');
|
||||||
|
if (list) {
|
||||||
|
list.classList.add('has-ai-comment');
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!document.querySelector('.atk-ai-comment')) {
|
||||||
var listBody = document.querySelector('.atk-list-body') || document.querySelector('.atk-list');
|
var listBody = document.querySelector('.atk-list-body') || document.querySelector('.atk-list');
|
||||||
if (listBody) {
|
if (listBody) {
|
||||||
var aiData = window.artalkConfig.aiComment;
|
var aiData = window.artalkConfig.aiComment;
|
||||||
@@ -158,6 +165,7 @@ window.initArtalk = function() {
|
|||||||
setTimeout(type, 500);
|
setTimeout(type, 500);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
// Artalk 初始化完成后,再加载弹幕 (If available)
|
// Artalk 初始化完成后,再加载弹幕 (If available)
|
||||||
@@ -190,7 +198,7 @@ function initCodeCopy() {
|
|||||||
|
|
||||||
const copyBtn = document.createElement('button');
|
const copyBtn = document.createElement('button');
|
||||||
copyBtn.className = 'copy-code-btn';
|
copyBtn.className = 'copy-code-btn';
|
||||||
copyBtn.innerHTML = '<i class="fa fa-copy"></i>'; // 使用 FontAwesome 图标
|
copyBtn.innerHTML = '<i class="ri-file-copy-2-line"></i>'; // 使用 RemixIcon
|
||||||
copyBtn.title = '复制代码';
|
copyBtn.title = '复制代码';
|
||||||
|
|
||||||
// 样式 (建议放到 CSS 文件中)
|
// 样式 (建议放到 CSS 文件中)
|
||||||
@@ -218,15 +226,15 @@ function initCodeCopy() {
|
|||||||
copyBtn.addEventListener('click', () => {
|
copyBtn.addEventListener('click', () => {
|
||||||
const code = codeBlock.innerText;
|
const code = codeBlock.innerText;
|
||||||
navigator.clipboard.writeText(code).then(() => {
|
navigator.clipboard.writeText(code).then(() => {
|
||||||
copyBtn.innerHTML = '<i class="fa fa-check"></i>';
|
copyBtn.innerHTML = '<i class="ri-check-line"></i>';
|
||||||
setTimeout(() => {
|
setTimeout(() => {
|
||||||
copyBtn.innerHTML = '<i class="fa fa-copy"></i>';
|
copyBtn.innerHTML = '<i class="ri-file-copy-2-line"></i>';
|
||||||
}, 2000);
|
}, 2000);
|
||||||
|
|
||||||
Qmsg.success("代码复制成功");
|
Qmsg.success("代码复制成功");
|
||||||
}).catch(err => {
|
}).catch(err => {
|
||||||
console.error('复制失败:', err);
|
console.error('复制失败:', err);
|
||||||
copyBtn.innerHTML = '<i class="fa fa-times"></i>';
|
copyBtn.innerHTML = '<i class="ri-close-line"></i>';
|
||||||
Qmsg.error("复制失败");
|
Qmsg.error("复制失败");
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
@@ -235,11 +243,73 @@ function initCodeCopy() {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
// 页面加载完成后初始化 (Merged into main DOMContentLoaded listener)
|
// 代码折叠功能
|
||||||
// document.addEventListener('DOMContentLoaded', function() {
|
function initCodeFold() {
|
||||||
// initCodeCopy();
|
const threshold = 360;
|
||||||
// initDescriptionHitokoto();
|
|
||||||
// });
|
// Helper to wrap element
|
||||||
|
const wrap = (el, wrapper) => {
|
||||||
|
el.parentNode.insertBefore(wrapper, el);
|
||||||
|
wrapper.appendChild(el);
|
||||||
|
};
|
||||||
|
|
||||||
|
// 1. Process .highlight blocks (Hugo generated)
|
||||||
|
document.querySelectorAll('.highlight').forEach(hl => {
|
||||||
|
if (hl.closest('.code-fold-container')) return; // Avoid double processing
|
||||||
|
|
||||||
|
// Check height
|
||||||
|
if (hl.scrollHeight > threshold) {
|
||||||
|
const wrapper = document.createElement('div');
|
||||||
|
wrapper.className = 'code-fold-container collapsed';
|
||||||
|
|
||||||
|
// Wrap the highlight block
|
||||||
|
wrap(hl, wrapper);
|
||||||
|
|
||||||
|
const btn = document.createElement('button');
|
||||||
|
btn.className = 'code-expand-btn';
|
||||||
|
// Use FontAwesome for reliability
|
||||||
|
btn.innerHTML = '<span><i class="fa fa-chevron-down" style="margin-right: 4px;"></i> 展开代码</span>';
|
||||||
|
|
||||||
|
btn.addEventListener('click', () => {
|
||||||
|
wrapper.classList.remove('collapsed');
|
||||||
|
btn.remove();
|
||||||
|
});
|
||||||
|
|
||||||
|
wrapper.appendChild(btn);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// 2. Process bare pre blocks (Fallback)
|
||||||
|
document.querySelectorAll('.post-content > pre').forEach(pre => {
|
||||||
|
if (pre.parentNode.classList.contains('highlight')) return;
|
||||||
|
if (pre.closest('.code-fold-container')) return;
|
||||||
|
if (pre.closest('.code-wrapper')) return; // Old wrapper check
|
||||||
|
|
||||||
|
if (pre.scrollHeight > threshold) {
|
||||||
|
const wrapper = document.createElement('div');
|
||||||
|
wrapper.className = 'code-fold-container collapsed';
|
||||||
|
|
||||||
|
wrap(pre, wrapper);
|
||||||
|
|
||||||
|
const btn = document.createElement('button');
|
||||||
|
btn.className = 'code-expand-btn';
|
||||||
|
btn.innerHTML = '<span><i class="fa fa-chevron-down" style="margin-right: 4px;"></i> 展开代码</span>';
|
||||||
|
|
||||||
|
btn.addEventListener('click', () => {
|
||||||
|
wrapper.classList.remove('collapsed');
|
||||||
|
btn.remove();
|
||||||
|
});
|
||||||
|
wrapper.appendChild(btn);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
// 页面加载完成后初始化
|
||||||
|
document.addEventListener('DOMContentLoaded', function() {
|
||||||
|
initCodeCopy();
|
||||||
|
initCodeFold();
|
||||||
|
initDescriptionHitokoto();
|
||||||
|
});
|
||||||
|
|
||||||
// 初始化个人描述一言切换
|
// 初始化个人描述一言切换
|
||||||
function initDescriptionHitokoto() {
|
function initDescriptionHitokoto() {
|
||||||
|
|||||||
@@ -175,6 +175,8 @@ document.addEventListener("pjax:complete", function () {
|
|||||||
pjax_reload()
|
pjax_reload()
|
||||||
// 初始化代码复制
|
// 初始化代码复制
|
||||||
initCodeCopy()
|
initCodeCopy()
|
||||||
|
// 初始化代码折叠
|
||||||
|
initCodeFold()
|
||||||
// 重载评论
|
// 重载评论
|
||||||
if (typeof window.initArtalk === 'function') {
|
if (typeof window.initArtalk === 'function') {
|
||||||
window.initArtalk();
|
window.initArtalk();
|
||||||
|
|||||||
Reference in new issue
Block a user