代码块 CSS 代码 JS代码 迭代记录

🎨CSS 代码:

1. 🔄代码块 CSS 样式 - 2026年1月1日

/* ==========================================
   代码块 - 需置于 文章详情页 样式下
   ========================================== */
.article-content {
  --code-bg: #0f1724;
  --code-text: #e6eef8;
  --code-toolbar-bg: #151d27;
  --code-border: rgba(255, 255, 255, 0.08);
  --code-line-num: rgba(255, 255, 255, 0.28);
  --code-btn-text: rgba(255, 255, 255, 0.68);
  --code-btn-hover: rgba(255, 255, 255, 0.06);
  --inline-code-bg: #0f1724;
  --inline-code-text: #e6eef8;
  --inline-code-hover: #252f3e;
}

/* 注意:折叠高度计算依赖以下值:
   - 折叠时显示5行代码(由JS的CODE_CONFIG.COLLAPSE_LINES控制)
   - 上边距:48px (工具栏高度38px + 10px间隔)
   - 下边距:16px (--spacing-md)
   - 行高:1.6 * 字体大小
*/

/* 字体渲染通用设置 */
.article-content pre,
.article-content code {
  /* 字体栈:英文等宽 + 中文无衬线 */
  font-family: var(--font-mono), var(--font-mono-cjk);

  /* 字体平滑 */
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;

  /* 文本渲染质量 */
  text-rendering: optimizeLegibility;

  /* 禁用连字 */
  font-feature-settings: "liga" off;
  font-variant-ligatures: none;
}

/* 基础 pre 样式 */
.article-content pre {
  position: relative;
  background: var(--code-bg);
  color: var(--code-text);
  font-family: var(--font-mono);
  font-size: 15px;
  line-height: 1.6;
  padding: 48px var(--spacing-md) var(--spacing-md) 54px;
  border-radius: var(--radius-sm);
  border: 1px solid var(--code-border);
  margin: 1.2rem 0;
  overflow: hidden; /* 初始为折叠状态 */
  white-space: pre;
  transition: max-height var(--transition-normal);
  box-sizing: border-box;
}

/* 展开状态 */
.article-content pre.expanded {
  overflow: auto;
  max-height: none;
}

/* 折叠状态(由 JS 控制 maxHeight) */
.article-content pre.collapsed {
  overflow: hidden;
}

/* 左侧行号列 */
.article-content pre::before {
  content: attr(data-line-numbers);
  position: absolute;
  top: 48px;
  left: 0;
  width: 44px;
  padding-right: 8px;
  text-align: right;
  font-size: 15px;
  line-height: 1.6;
  font-family: var(--font-mono);
  color: var(--code-line-num);
  white-space: pre;
  user-select: none;
  border-right: 1px solid rgba(255, 255, 255, 0.06);
  box-sizing: border-box;
}

/* 顶部工具栏 */
.article-content pre .code-tools {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  height: 38px;
  padding: 0 var(--spacing-sm);
  background: var(--code-toolbar-bg);
  display: flex;
  align-items: center;
  justify-content: space-between;
  border-top-left-radius: var(--radius-md);
  border-top-right-radius: var(--radius-md);
  box-sizing: border-box;
}

/* CODE 标题 */
.article-content pre .code-title {
  font-size: 12px;
  font-weight: 700;
  color: rgba(255, 255, 255, 0.65);
  letter-spacing: 1px;
  user-select: none;
  font-family: var(--font-primary);
}

/* 按钮样式 */
.article-content pre .code-btn {
  background: transparent;
  border: none;
  color: var(--code-btn-text);
  font-size: 13px;
  cursor: pointer;
  padding: 6px 8px;
  border-radius: var(--radius-sm);
  transition: all var(--transition-fast);
  user-select: none;
  -webkit-user-select: none;
}

.article-content pre .code-btn:hover:not(:disabled) {
  color: var(--color-text-inverse);
  background: var(--code-btn-hover);
}

.article-content pre .code-btn:active:not(:disabled) {
  transform: scale(0.95);
}

.article-content pre .code-btn:disabled {
  cursor: not-allowed;
  opacity: 0.7;
  color: #4ade80;
  font-weight: bold;
}

/* 代码内容(code 元素) */
.article-content pre > code {
  background: none;
  border: none;
  padding: 0;
  margin: 0;
  font-family: inherit;
  font-size: inherit;
  line-height: inherit;
  display: block;
  word-break: break-word;
}

/* 折叠遮罩 */
.article-content pre.collapsed::after {
  content: "";
  position: absolute;
  left: 0;
  right: 0;
  bottom: 0;
  height: 48px; /* 匹配下边距,创建渐变过渡效果 */
  background: linear-gradient(to bottom, transparent, var(--code-bg));
  pointer-events: none;
}

/* ==========================================
   行内代码
   ========================================== */
.article-content code {
  font-family: var(--font-mono);
  background-color: var(--inline-code-bg);
  color: var(--inline-code-text);
  margin: 0 2px;
  padding: 2px 5px;
  border-radius: var(--radius-xs);
  font-size: 0.94em;
  transition: background-color var(--transition-fast);
}

2. ✅️代码块 CSS 样式 - AI风格 - 2026年1月12日

/* ==========================================
   代码块 - 需置于 文章详情页 样式下
   ========================================== */

/* CSS变量 - 响应式浅色/深色主题 */
:root {
  /* 浅色主题 */
  --itxgo-code-bg-light: var(--color-bg-light);
  --itxgo-code-text-light: #24292f;
  --itxgo-border-light: #d1d9e0;
  --itxgo-btn-text-light: #57606a;
  --itxgo-code-label-light: #6e7781;
  --itxgo-scrollbar-thumb-light: #afb8c1;
  
  /* 深色主题 */
  --itxgo-code-bg-dark: #30302e;
  --itxgo-code-text-dark: #e6edf3;
  --itxgo-border-dark: #30363d;
  --itxgo-btn-text-dark: #c9d1d9;
  --itxgo-code-label-dark: #8b949e;
  --itxgo-scrollbar-thumb-dark: #484f58;
  
  /* 默认使用浅色主题 */
  --itxgo-code-bg: var(--itxgo-code-bg-light);
  --itxgo-code-text: var(--itxgo-code-text-light);
  --itxgo-border: var(--itxgo-border-light);
  --itxgo-btn-text: var(--itxgo-btn-text-light);
  --itxgo-code-label: var(--itxgo-code-label-light);
  --itxgo-scrollbar-thumb: var(--itxgo-scrollbar-thumb-light);
}

/* 深色主题切换 */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) {
    --itxgo-code-bg: var(--itxgo-code-bg-dark);
    --itxgo-code-text: var(--itxgo-code-text-dark);
    --itxgo-border: var(--itxgo-border-dark);
    --itxgo-btn-text: var(--itxgo-btn-text-dark);
    --itxgo-code-label: var(--itxgo-code-label-dark);
    --itxgo-scrollbar-thumb: var(--itxgo-scrollbar-thumb-dark);
  }
}

[data-theme="dark"],
.dark-mode,
.dark {
  --itxgo-code-bg: var(--itxgo-code-bg-dark);
  --itxgo-code-text: var(--itxgo-code-text-dark);
  --itxgo-border: var(--itxgo-border-dark);
  --itxgo-btn-text: var(--itxgo-btn-text-dark);
  --itxgo-code-label: var(--itxgo-code-label-dark);
  --itxgo-scrollbar-thumb: var(--itxgo-scrollbar-thumb-dark);
}

/* 代码块容器 */
.article-content pre.itxgo-code-block {
  position: relative;
  background: var(--itxgo-code-bg);
  color: var(--itxgo-code-text);
  font-family: Cascadia Code;
  font-size: 14px;
  line-height: 1.4286;
  padding: 40px 16px 12px;
  border-radius: var(--radius-md);
  margin: 1rem 0;
  overflow: hidden;
  transition: max-height 0.3s ease-out, background-color 0.3s ease;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  border: 1px solid #6e7781;
}

.article-content pre.itxgo-code-block > code {
  font-family: inherit;
  background: none;
  border: none;
  padding: 0;
  margin: 0;
  display: block;
  word-break: break-word;
  white-space: pre-wrap;
  tab-size: 2;
}

/* 展开/折叠状态 */
.article-content pre.itxgo-expanded {
  overflow: auto;
  max-height: none;
}

.article-content pre.itxgo-collapsed {
  overflow: hidden;
  cursor: pointer;
}

.article-content pre.itxgo-collapsed::after {
  content: "︾";
  position: absolute;
  left: 0;
  right: 0;
  bottom: 0;
  height: 40px;
  background: linear-gradient(to bottom, transparent, var(--itxgo-code-bg) 70%);
  display: flex;
  align-items: flex-end;
  justify-content: center;
  padding-bottom: 6px;
  color: var(--itxgo-code-label);
  font-size: 18px;
  font-weight: normal;
  font-family: system-ui, -apple-system, sans-serif;
  pointer-events: none;
  border-radius: 6px;
}

/* 工具栏 */
.article-content pre .itxgo-code-tools {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  height: 38px;
  padding: 0 16px;
  background: var(--itxgo-code-bg);
  display: flex;
  align-items: center;
  justify-content: space-between;
  border-radius: 6px 6px 0 0;
  transition: background-color 0.3s ease;
  z-index: 10;
  cursor: default;
}

.article-content pre .itxgo-code-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  width: 100%;
  gap: 12px;
}

.article-content pre .itxgo-code-label {
  font-family: Cascadia Code;
  font-size: 12px;
  font-weight: 600;
  color: var(--itxgo-code-label);
  letter-spacing: 0.5px;
  user-select: none;
  text-transform: uppercase;
  transition: color 0.3s ease;
  cursor: default;
}

.article-content pre .itxgo-code-actions {
  display: flex;
  align-items: center;
  gap: 6px;
}

/* 按钮样式 */
.article-content pre .itxgo-code-btn {
  display: flex;
  align-items: center;
  gap: 6px;
  background: transparent;
  border: 1px solid transparent;
  color: var(--itxgo-btn-text);
  font-size: 12px;
  cursor: pointer;
  padding: 4px 10px;
  border-radius: 6px;
  transition: all 0.2s ease;
  user-select: none;
  font-family: Cascadia Code;
  font-weight: 500;
  height: 28px;
}

.article-content pre .itxgo-code-btn:disabled {
  cursor: not-allowed;
  opacity: 0.7;
}

.article-content pre .itxgo-copy .copy-icon {
  flex-shrink: 0;
  stroke-width: 2;
}

.article-content pre .itxgo-copy .copy-text {
  font-size: 12px;
}

.article-content pre .itxgo-toggle {
  width: 28px;
  min-width: 28px;
  padding: 0;
  justify-content: center;
  font-size: 12px;
}

/* 滚动条 */
.article-content pre.itxgo-code-block::-webkit-scrollbar {
  width: 8px;
  height: 8px;
}

.article-content pre.itxgo-code-block::-webkit-scrollbar-track {
  background: transparent;
  border-radius: 6px;
}

.article-content pre.itxgo-code-block::-webkit-scrollbar-thumb {
  background: var(--itxgo-scrollbar-thumb);
  border-radius: 4px;
}

.article-content pre.itxgo-code-block::-webkit-scrollbar-thumb:hover {
  background: color-mix(in srgb, var(--itxgo-scrollbar-thumb) 80%, var(--itxgo-code-text));
}

/* 行内代码 */
.article-content code:not(pre > code) {
  font-family: Cascadia Code;
  background-color: rgba(88, 166, 255, 0.1);
  color: #58a6ff;
  margin: 0 1px;
  padding: 2px 6px;
  border-radius: 4px;
  font-size: 0.88em;
  transition: all 0.2s ease;
}

.article-content code:not(pre > code):hover {
  background-color: rgba(88, 166, 255, 0.15);
}

/* 响应式 */
@media (max-width: 768px) {
  .article-content pre.itxgo-code-block {
    font-size: 13px;
    padding: 36px 12px 10px;
    margin: 0.8rem -8px;
    border-radius: 0;
  }
  
  .article-content pre .itxgo-code-tools {
    height: 34px;
    padding: 0 12px;
  }
  
  .article-content pre .itxgo-code-btn {
    padding: 3px 8px;
    font-size: 11px;
    height: 26px;
  }
  
  .article-content pre .itxgo-toggle {
    width: 26px;
    min-width: 26px;
  }
  
  .article-content pre .itxgo-code-label {
    font-size: 11px;
  }
}

3. ✅️代码块 CSS 样式 - AI风格 新增右下折叠按钮 - 2026年1月12日

/* ==========================================
   代码块 - 需置于 文章详情页 样式下
   ========================================== */

/* CSS变量 - 响应式浅色/深色主题 */
:root {
  /* 浅色主题 */
  --itxgo-code-bg-light: var(--color-bg-light);
  --itxgo-code-text-light: #24292f;
  --itxgo-border-light: #d1d9e0;
  --itxgo-btn-text-light: #57606a;
  --itxgo-code-label-light: #6e7781;
  --itxgo-scrollbar-thumb-light: #afb8c1;
  
  /* 深色主题 */
  --itxgo-code-bg-dark: #30302e;
  --itxgo-code-text-dark: #e6edf3;
  --itxgo-border-dark: #30363d;
  --itxgo-btn-text-dark: #c9d1d9;
  --itxgo-code-label-dark: #8b949e;
  --itxgo-scrollbar-thumb-dark: #484f58;
  
  /* 默认使用浅色主题 */
  --itxgo-code-bg: var(--itxgo-code-bg-light);
  --itxgo-code-text: var(--itxgo-code-text-light);
  --itxgo-border: var(--itxgo-border-light);
  --itxgo-btn-text: var(--itxgo-btn-text-light);
  --itxgo-code-label: var(--itxgo-code-label-light);
  --itxgo-scrollbar-thumb: var(--itxgo-scrollbar-thumb-light);
}

/* 深色主题切换 */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) {
    --itxgo-code-bg: var(--itxgo-code-bg-dark);
    --itxgo-code-text: var(--itxgo-code-text-dark);
    --itxgo-border: var(--itxgo-border-dark);
    --itxgo-btn-text: var(--itxgo-btn-text-dark);
    --itxgo-code-label: var(--itxgo-code-label-dark);
    --itxgo-scrollbar-thumb: var(--itxgo-scrollbar-thumb-dark);
  }
}

[data-theme="dark"],
.dark-mode,
.dark {
  --itxgo-code-bg: var(--itxgo-code-bg-dark);
  --itxgo-code-text: var(--itxgo-code-text-dark);
  --itxgo-border: var(--itxgo-border-dark);
  --itxgo-btn-text: var(--itxgo-btn-text-dark);
  --itxgo-code-label: var(--itxgo-code-label-dark);
  --itxgo-scrollbar-thumb: var(--itxgo-scrollbar-thumb-dark);
}

/* 代码块容器 */
.article-content pre.itxgo-code-block {
  position: relative;
  background: var(--itxgo-code-bg);
  color: var(--itxgo-code-text);
  font-family: Cascadia Code;
  font-size: 14px;
  line-height: 1.4286;
  padding: 40px 16px 12px;
  border-radius: var(--radius-md);
  margin: 1rem 0;
  overflow: hidden;
  transition: max-height 0.3s ease-out, background-color 0.3s ease;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  border: 1px solid #6e7781;
}

.article-content pre.itxgo-code-block > code {
  font-family: inherit;
  background: none;
  border: none;
  padding: 0;
  margin: 0;
  display: block;
  word-break: break-word;
  white-space: pre-wrap;
  tab-size: 2;
}

/* 展开/折叠状态 */
.article-content pre.itxgo-expanded {
  overflow: auto;
  max-height: none;
}

.article-content pre.itxgo-collapsed {
  overflow: hidden;
  cursor: pointer;
}

.article-content pre.itxgo-collapsed::after {
  content: "︾";
  position: absolute;
  left: 0;
  right: 0;
  bottom: 0;
  height: 40px;
  background: linear-gradient(to bottom, transparent, var(--itxgo-code-bg) 70%);
  display: flex;
  align-items: flex-end;
  justify-content: center;
  padding-bottom: 6px;
  color: var(--itxgo-code-label);
  font-size: 18px;
  font-weight: normal;
  font-family: system-ui, -apple-system, sans-serif;
  pointer-events: none;
  border-radius: 6px;
}

/* 工具栏 */
.article-content pre .itxgo-code-tools {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  height: 38px;
  padding: 0 16px;
  background: var(--itxgo-code-bg);
  display: flex;
  align-items: center;
  justify-content: space-between;
  border-radius: 6px 6px 0 0;
  transition: background-color 0.3s ease;
  z-index: 10;
  cursor: default;
}

.article-content pre .itxgo-code-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  width: 100%;
  gap: 12px;
}

.article-content pre .itxgo-code-label {
  font-family: Cascadia Code;
  font-size: 12px;
  font-weight: 600;
  color: var(--itxgo-code-label);
  letter-spacing: 0.5px;
  user-select: none;
  text-transform: uppercase;
  transition: color 0.3s ease;
  cursor: default;
}

.article-content pre .itxgo-code-actions {
  display: flex;
  align-items: center;
  gap: 6px;
}

/* 按钮样式 */
.article-content pre .itxgo-code-btn {
  display: flex;
  align-items: center;
  gap: 6px;
  background: transparent;
  border: 1px solid transparent;
  color: var(--itxgo-btn-text);
  font-size: 12px;
  cursor: pointer;
  padding: 4px 10px;
  border-radius: 6px;
  transition: all 0.2s ease;
  user-select: none;
  font-family: Cascadia Code;
  font-weight: 500;
  height: 28px;
}

.article-content pre .itxgo-code-btn:disabled {
  cursor: not-allowed;
  opacity: 0.7;
}

.article-content pre .itxgo-copy .copy-icon {
  flex-shrink: 0;
  stroke-width: 2;
}

.article-content pre .itxgo-copy .copy-text {
  font-size: 12px;
}

.article-content pre .itxgo-toggle {
  width: 28px;
  min-width: 28px;
  padding: 0;
  justify-content: center;
  font-size: 12px;
}

/* 右下角折叠按钮 */
.article-content pre .itxgo-collapse-corner-btn {
  display: none;
  position: absolute;
  bottom: 12px;
  right: 12px;
  z-index: 20;
  background: transparent;
  border: none;
  font-size: 18px;
  color: var(--itxgo-code-label);
  cursor: pointer;
}

/* 仅在展开状态显示 */
.article-content pre.itxgo-expanded .itxgo-collapse-corner-btn {
  display: block;
}

.article-content pre .itxgo-collapse-corner-btn:hover {
  opacity: 1;
}

/* 滚动条 */
.article-content pre.itxgo-code-block::-webkit-scrollbar {
  width: 8px;
  height: 8px;
}

.article-content pre.itxgo-code-block::-webkit-scrollbar-track {
  background: transparent;
  border-radius: 6px;
}

.article-content pre.itxgo-code-block::-webkit-scrollbar-thumb {
  background: var(--itxgo-scrollbar-thumb);
  border-radius: 4px;
}

.article-content pre.itxgo-code-block::-webkit-scrollbar-thumb:hover {
  background: color-mix(in srgb, var(--itxgo-scrollbar-thumb) 80%, var(--itxgo-code-text));
}

/* 行内代码 */
.article-content code:not(pre > code) {
  font-family: Cascadia Code;
  background-color: rgba(88, 166, 255, 0.1);
  color: #58a6ff;
  margin: 0 1px;
  padding: 2px 6px;
  border-radius: 4px;
  font-size: 0.88em;
  transition: all 0.2s ease;
}

.article-content code:not(pre > code):hover {
  background-color: rgba(88, 166, 255, 0.15);
}

/* 响应式 */
@media (max-width: 768px) {
  .article-content pre.itxgo-code-block {
    font-size: 13px;
    padding: 36px 12px 10px;
    margin: 0.8rem -8px;
    border-radius: 0;
  }
  
  .article-content pre .itxgo-code-tools {
    height: 34px;
    padding: 0 12px;
  }
  
  .article-content pre .itxgo-code-btn {
    padding: 3px 8px;
    font-size: 11px;
    height: 26px;
  }
  
  .article-content pre .itxgo-toggle {
    width: 26px;
    min-width: 26px;
  }
  
  .article-content pre .itxgo-code-label {
    font-size: 11px;
  }
}

4. ✅️代码块 CSS 样式 - AI风格 代码高亮版 - GitHub 配色 - 2026年1月13日

/* ==========================================
   代码块 - 需置于 文章详情页 样式下
   ========================================== */

/* CSS变量 - 响应式浅色/深色主题 */
:root {
  /* 浅色主题 */
  --itxgo-code-bg-light: var(--color-bg-light);
  --itxgo-code-text-light: #24292f;
  --itxgo-border-light: #d1d9e0;
  --itxgo-btn-text-light: #57606a;
  --itxgo-code-label-light: #6e7781;
  --itxgo-scrollbar-thumb-light: #afb8c1;
  
  /* 深色主题 */
  --itxgo-code-bg-dark: #30302e;
  --itxgo-code-text-dark: #e6edf3;
  --itxgo-border-dark: #30363d;
  --itxgo-btn-text-dark: #c9d1d9;
  --itxgo-code-label-dark: #8b949e;
  --itxgo-scrollbar-thumb-dark: #484f58;
  
  /* 默认使用浅色主题 */
  --itxgo-code-bg: var(--itxgo-code-bg-light);
  --itxgo-code-text: var(--itxgo-code-text-light);
  --itxgo-border: var(--itxgo-border-light);
  --itxgo-btn-text: var(--itxgo-btn-text-light);
  --itxgo-code-label: var(--itxgo-code-label-light);
  --itxgo-scrollbar-thumb: var(--itxgo-scrollbar-thumb-light);
}

/* 深色主题切换 */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) {
    --itxgo-code-bg: var(--itxgo-code-bg-dark);
    --itxgo-code-text: var(--itxgo-code-text-dark);
    --itxgo-border: var(--itxgo-border-dark);
    --itxgo-btn-text: var(--itxgo-btn-text-dark);
    --itxgo-code-label: var(--itxgo-code-label-dark);
    --itxgo-scrollbar-thumb: var(--itxgo-scrollbar-thumb-dark);
  }
}

[data-theme="dark"],
.dark-mode,
.dark {
  --itxgo-code-bg: var(--itxgo-code-bg-dark);
  --itxgo-code-text: var(--itxgo-code-text-dark);
  --itxgo-border: var(--itxgo-border-dark);
  --itxgo-btn-text: var(--itxgo-btn-text-dark);
  --itxgo-code-label: var(--itxgo-code-label-dark);
  --itxgo-scrollbar-thumb: var(--itxgo-scrollbar-thumb-dark);
}

/* 代码块容器 */
.article-content pre.itxgo-code-block {
  position: relative;
  background: var(--itxgo-code-bg);
  color: var(--itxgo-code-text);
  font-family: Cascadia Code;
  font-size: 14px;
  line-height: 1.4286;
  padding: 40px 16px 12px;
  border-radius: var(--radius-md);
  margin: 1rem 0;
  overflow: hidden;
  transition: max-height 0.3s ease-out, background-color 0.3s ease;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  border: 1px solid #6e7781;
}

.article-content pre.itxgo-code-block > code {
  font-family: inherit;
  background: none;
  border: none;
  padding: 0;
  margin: 0;
  display: block;
  word-break: break-word;
  white-space: pre-wrap;
  tab-size: 2;
}

/* ==========================================
   Prism.js 语法高亮样式 - 浅色主题
   ========================================== */
.article-content pre.itxgo-code-block code[class*="language-"] .token.comment,
.article-content pre.itxgo-code-block code[class*="language-"] .token.prolog,
.article-content pre.itxgo-code-block code[class*="language-"] .token.doctype,
.article-content pre.itxgo-code-block code[class*="language-"] .token.cdata {
  color: #6a737d;
  font-style: italic;
}

.article-content pre.itxgo-code-block code[class*="language-"] .token.punctuation {
  color: #24292f;
}

.article-content pre.itxgo-code-block code[class*="language-"] .token.property,
.article-content pre.itxgo-code-block code[class*="language-"] .token.tag,
.article-content pre.itxgo-code-block code[class*="language-"] .token.boolean,
.article-content pre.itxgo-code-block code[class*="language-"] .token.number,
.article-content pre.itxgo-code-block code[class*="language-"] .token.constant,
.article-content pre.itxgo-code-block code[class*="language-"] .token.symbol,
.article-content pre.itxgo-code-block code[class*="language-"] .token.deleted {
  color: #005cc5;
}

.article-content pre.itxgo-code-block code[class*="language-"] .token.selector,
.article-content pre.itxgo-code-block code[class*="language-"] .token.attr-name,
.article-content pre.itxgo-code-block code[class*="language-"] .token.string,
.article-content pre.itxgo-code-block code[class*="language-"] .token.char,
.article-content pre.itxgo-code-block code[class*="language-"] .token.builtin,
.article-content pre.itxgo-code-block code[class*="language-"] .token.inserted {
  color: #032f62;
}

.article-content pre.itxgo-code-block code[class*="language-"] .token.operator,
.article-content pre.itxgo-code-block code[class*="language-"] .token.entity,
.article-content pre.itxgo-code-block code[class*="language-"] .token.url,
.article-content pre.itxgo-code-block code[class*="language-"] .language-css .token.string,
.article-content pre.itxgo-code-block code[class*="language-"] .style .token.string {
  color: #d73a49;
}

.article-content pre.itxgo-code-block code[class*="language-"] .token.atrule,
.article-content pre.itxgo-code-block code[class*="language-"] .token.attr-value,
.article-content pre.itxgo-code-block code[class*="language-"] .token.keyword {
  color: #d73a49;
}

.article-content pre.itxgo-code-block code[class*="language-"] .token.function,
.article-content pre.itxgo-code-block code[class*="language-"] .token.class-name {
  color: #6f42c1;
}

.article-content pre.itxgo-code-block code[class*="language-"] .token.regex,
.article-content pre.itxgo-code-block code[class*="language-"] .token.important,
.article-content pre.itxgo-code-block code[class*="language-"] .token.variable {
  color: #e36209;
}

/* ==========================================
   Prism.js 语法高亮样式 - 深色主题
   ========================================== */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.comment,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.prolog,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.doctype,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.cdata {
    color: #8b949e;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.punctuation {
    color: #c9d1d9;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.property,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.tag,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.boolean,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.number,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.constant,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.symbol,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.deleted {
    color: #79c0ff;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.selector,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-name,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.string,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.char,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.builtin,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.inserted {
    color: #a5d6ff;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.operator,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.entity,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.url,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .language-css .token.string,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .style .token.string {
    color: #ff7b72;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.atrule,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-value,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.keyword {
    color: #ff7b72;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.function,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.class-name {
    color: #d2a8ff;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.regex,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.important,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.variable {
    color: #ffa657;
  }
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.comment,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.prolog,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.doctype,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.cdata,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.comment,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.prolog,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.doctype,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.cdata,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.comment,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.prolog,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.doctype,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.cdata {
  color: #8b949e;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.punctuation,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.punctuation,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.punctuation {
  color: #c9d1d9;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.property,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.tag,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.boolean,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.number,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.constant,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.symbol,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.deleted,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.property,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.tag,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.boolean,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.number,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.constant,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.symbol,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.deleted,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.property,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.tag,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.boolean,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.number,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.constant,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.symbol,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.deleted {
  color: #79c0ff;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.selector,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-name,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.string,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.char,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.builtin,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.inserted,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.selector,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-name,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.string,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.char,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.builtin,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.inserted,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.selector,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-name,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.string,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.char,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.builtin,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.inserted {
  color: #a5d6ff;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.operator,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.entity,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.url,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .language-css .token.string,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .style .token.string,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.operator,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.entity,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.url,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .language-css .token.string,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .style .token.string,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.operator,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.entity,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.url,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .language-css .token.string,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .style .token.string {
  color: #ff7b72;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.atrule,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-value,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.keyword,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.atrule,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-value,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.keyword,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.atrule,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-value,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.keyword {
  color: #ff7b72;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.function,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.class-name,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.function,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.class-name,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.function,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.class-name {
  color: #d2a8ff;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.regex,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.important,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.variable,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.regex,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.important,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.variable,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.regex,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.important,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.variable {
  color: #ffa657;
}

/* 展开/折叠状态 */
.article-content pre.itxgo-expanded {
  overflow: auto;
  max-height: none;
}

.article-content pre.itxgo-collapsed {
  overflow: hidden;
  cursor: pointer;
}

.article-content pre.itxgo-collapsed::after {
  content: "︾";
  position: absolute;
  left: 0;
  right: 0;
  bottom: 0;
  height: 40px;
  background: linear-gradient(to bottom, transparent, var(--itxgo-code-bg) 70%);
  display: flex;
  align-items: flex-end;
  justify-content: center;
  padding-bottom: 6px;
  color: var(--itxgo-code-label);
  font-size: 18px;
  font-weight: normal;
  font-family: system-ui, -apple-system, sans-serif;
  pointer-events: none;
  border-radius: 6px;
}

/* 工具栏 */
.article-content pre .itxgo-code-tools {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  height: 38px;
  padding: 0 16px;
  background: var(--itxgo-code-bg);
  display: flex;
  align-items: center;
  justify-content: space-between;
  border-radius: 6px 6px 0 0;
  transition: background-color 0.3s ease;
  z-index: 10;
  cursor: default;
}

.article-content pre .itxgo-code-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  width: 100%;
  gap: 12px;
}

.article-content pre .itxgo-code-label {
  font-family: Cascadia Code;
  font-size: 12px;
  font-weight: 600;
  color: var(--itxgo-code-label);
  letter-spacing: 0.5px;
  user-select: none;
  text-transform: uppercase;
  transition: color 0.3s ease;
  cursor: default;
}

.article-content pre .itxgo-code-actions {
  display: flex;
  align-items: center;
  gap: 6px;
}

/* 按钮样式 */
.article-content pre .itxgo-code-btn {
  display: flex;
  align-items: center;
  gap: 6px;
  background: transparent;
  border: 1px solid transparent;
  color: var(--itxgo-btn-text);
  font-size: 12px;
  cursor: pointer;
  padding: 4px 10px;
  border-radius: 6px;
  transition: all 0.2s ease;
  user-select: none;
  font-family: Cascadia Code;
  font-weight: 500;
  height: 28px;
}

.article-content pre .itxgo-code-btn:disabled {
  cursor: not-allowed;
  opacity: 0.7;
}

.article-content pre .itxgo-copy .copy-icon {
  flex-shrink: 0;
  stroke-width: 2;
}

.article-content pre .itxgo-copy .copy-text {
  font-size: 12px;
}

.article-content pre .itxgo-toggle {
  width: 28px;
  min-width: 28px;
  padding: 0;
  justify-content: center;
  font-size: 12px;
}

/* 右下角折叠按钮 */
.article-content pre .itxgo-collapse-corner-btn {
  display: none;
  position: absolute;
  bottom: 12px;
  right: 12px;
  z-index: 20;
  background: transparent;
  border: none;
  font-size: 18px;
  color: var(--itxgo-code-label);
  cursor: pointer;
}

/* 仅在展开状态显示 */
.article-content pre.itxgo-expanded .itxgo-collapse-corner-btn {
  display: block;
}

.article-content pre .itxgo-collapse-corner-btn:hover {
  opacity: 1;
}

/* 滚动条 */
.article-content pre.itxgo-code-block::-webkit-scrollbar {
  width: 8px;
  height: 8px;
}

.article-content pre.itxgo-code-block::-webkit-scrollbar-track {
  background: transparent;
  border-radius: 6px;
}

.article-content pre.itxgo-code-block::-webkit-scrollbar-thumb {
  background: var(--itxgo-scrollbar-thumb);
  border-radius: 4px;
}

.article-content pre.itxgo-code-block::-webkit-scrollbar-thumb:hover {
  background: color-mix(in srgb, var(--itxgo-scrollbar-thumb) 80%, var(--itxgo-code-text));
}

/* 重置代码块内部元素样式 */
.article-content pre.itxgo-code-block code,
.article-content pre.itxgo-code-block code * {
  background: transparent;
  padding: 0;
  margin: 0;
  border: none;
  border-radius: 0;
}

/* 行内代码 */
.article-content code:not(pre > code) {
  font-family: Cascadia Code;
  background-color: rgba(88, 166, 255, 0.1);
  color: #58a6ff;
  margin: 0 1px;
  padding: 2px 6px;
  border-radius: 4px;
  font-size: 0.88em;
  transition: all 0.2s ease;
}

.article-content code:not(pre > code):hover {
  background-color: rgba(88, 166, 255, 0.15);
}

/* 响应式 */
@media (max-width: 768px) {
  .article-content pre.itxgo-code-block {
    font-size: 13px;
    padding: 36px 12px 10px;
    margin: 0.8rem -8px;
    border-radius: 0;
  }
  
  .article-content pre .itxgo-code-tools {
    height: 34px;
    padding: 0 12px;
  }
  
  .article-content pre .itxgo-code-btn {
    padding: 3px 8px;
    font-size: 11px;
    height: 26px;
  }
  
  .article-content pre .itxgo-toggle {
    width: 26px;
    min-width: 26px;
  }
  
  .article-content pre .itxgo-code-label {
    font-size: 11px;
  }
}

4-1. ✅️代码块 CSS 样式 - AI风格 代码高亮版 - DeepSeek 配色 - 2026年1月13日

/* ==========================================
   代码块 - 需置于 文章详情页 样式下
   ========================================== */

/* CSS变量 - 响应式浅色/深色主题 */
:root {
  /* 浅色主题 */
  --itxgo-code-bg-light: var(--color-bg-light);
  --itxgo-code-text-light: #24292f;
  --itxgo-border-light: #d1d9e0;
  --itxgo-btn-text-light: #57606a;
  --itxgo-code-label-light: #6e7781;
  --itxgo-scrollbar-thumb-light: #afb8c1;
  
  /* 深色主题 */
  --itxgo-code-bg-dark: #30302e;
  --itxgo-code-text-dark: #e6edf3;
  --itxgo-border-dark: #30363d;
  --itxgo-btn-text-dark: #c9d1d9;
  --itxgo-code-label-dark: #8b949e;
  --itxgo-scrollbar-thumb-dark: #484f58;
  
  /* 默认使用浅色主题 */
  --itxgo-code-bg: var(--itxgo-code-bg-light);
  --itxgo-code-text: var(--itxgo-code-text-light);
  --itxgo-border: var(--itxgo-border-light);
  --itxgo-btn-text: var(--itxgo-btn-text-light);
  --itxgo-code-label: var(--itxgo-code-label-light);
  --itxgo-scrollbar-thumb: var(--itxgo-scrollbar-thumb-light);
}

/* 深色主题切换 */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) {
    --itxgo-code-bg: var(--itxgo-code-bg-dark);
    --itxgo-code-text: var(--itxgo-code-text-dark);
    --itxgo-border: var(--itxgo-border-dark);
    --itxgo-btn-text: var(--itxgo-btn-text-dark);
    --itxgo-code-label: var(--itxgo-code-label-dark);
    --itxgo-scrollbar-thumb: var(--itxgo-scrollbar-thumb-dark);
  }
}

[data-theme="dark"],
.dark-mode,
.dark {
  --itxgo-code-bg: var(--itxgo-code-bg-dark);
  --itxgo-code-text: var(--itxgo-code-text-dark);
  --itxgo-border: var(--itxgo-border-dark);
  --itxgo-btn-text: var(--itxgo-btn-text-dark);
  --itxgo-code-label: var(--itxgo-code-label-dark);
  --itxgo-scrollbar-thumb: var(--itxgo-scrollbar-thumb-dark);
}

/* 未初始化的代码块使用 display:none 完全隐藏 */
.article-content pre:not(.itxgo-initialized):not(.itxgo-code-block) {
  display: none;
}

/* 代码块容器 */
.article-content pre.itxgo-code-block {
  position: relative;
  background: var(--itxgo-code-bg);
  color: var(--itxgo-code-text);
  font-family: Cascadia Code;
  font-size: 14px;
  line-height: 1.4286;
  padding: 40px 16px 12px;
  border-radius: var(--radius-md);
  margin: 1rem 0;
  overflow: hidden;
  transition: max-height 0.3s ease-out, background-color 0.3s ease;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  border: 1px solid #6e7781;
}

.article-content pre.itxgo-code-block > code {
  font-family: inherit;
  background: none;
  border: none;
  padding: 0;
  margin: 0;
  display: block;
  word-break: break-word;
  white-space: pre-wrap;
  tab-size: 2;
}

/* ==========================================
   Prism.js 语法高亮样式 - DeepSeek 配色
   ========================================== */

/* 浅色主题 */
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.comment,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.prolog,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.doctype,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.cdata {
  color: #6b7280;
  font-style: italic;
}

:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.punctuation {
  color: #374151;
}

:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.property,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.tag,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.boolean,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.number,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.constant,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.symbol,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.deleted {
  color: #0284c7;
}

:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.selector,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-name,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.string,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.char,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.builtin,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.inserted {
  color: #059669;
}

:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.operator,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.entity,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.url,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .language-css .token.string,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .style .token.string {
  color: #dc2626;
}

:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.atrule,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-value,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.keyword {
  color: #7c3aed;
}

:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.function,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.class-name {
  color: #2563eb;
}

:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.regex,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.important,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.variable {
  color: #ea580c;
}

/* 深色主题 - 媒体查询 */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.comment,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.prolog,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.doctype,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.cdata {
    color: #94a3b8;
    font-style: italic;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.punctuation {
    color: #e2e8f0;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.property,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.tag,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.boolean,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.number,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.constant,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.symbol,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.deleted {
    color: #38bdf8;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.selector,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-name,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.string,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.char,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.builtin,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.inserted {
    color: #4ade80;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.operator,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.entity,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.url,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .language-css .token.string,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .style .token.string {
    color: #f87171;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.atrule,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-value,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.keyword {
    color: #a78bfa;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.function,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.class-name {
    color: #60a5fa;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.regex,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.important,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.variable {
    color: #fb923c;
  }
}

/* 深色主题 - 显式指定 */
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.comment,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.prolog,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.doctype,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.cdata,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.comment,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.prolog,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.doctype,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.cdata,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.comment,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.prolog,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.doctype,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.cdata {
  color: #94a3b8;
  font-style: italic;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.punctuation,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.punctuation,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.punctuation {
  color: #e2e8f0;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.property,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.tag,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.boolean,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.number,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.constant,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.symbol,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.deleted,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.property,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.tag,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.boolean,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.number,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.constant,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.symbol,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.deleted,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.property,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.tag,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.boolean,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.number,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.constant,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.symbol,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.deleted {
  color: #38bdf8;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.selector,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-name,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.string,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.char,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.builtin,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.inserted,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.selector,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-name,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.string,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.char,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.builtin,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.inserted,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.selector,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-name,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.string,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.char,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.builtin,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.inserted {
  color: #4ade80;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.operator,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.entity,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.url,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .language-css .token.string,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .style .token.string,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.operator,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.entity,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.url,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .language-css .token.string,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .style .token.string,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.operator,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.entity,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.url,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .language-css .token.string,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .style .token.string {
  color: #f87171;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.atrule,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-value,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.keyword,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.atrule,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-value,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.keyword,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.atrule,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-value,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.keyword {
  color: #a78bfa;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.function,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.class-name,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.function,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.class-name,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.function,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.class-name {
  color: #60a5fa;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.regex,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.important,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.variable,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.regex,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.important,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.variable,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.regex,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.important,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.variable {
  color: #fb923c;
}

/* 展开/折叠状态 */
.article-content pre.itxgo-expanded {
  overflow: auto;
  max-height: none;
}

.article-content pre.itxgo-collapsed {
  overflow: hidden;
  cursor: pointer;
}

.article-content pre.itxgo-collapsed::after {
  content: "︾";
  position: absolute;
  left: 0;
  right: 0;
  bottom: 0;
  height: 40px;
  background: linear-gradient(to bottom, transparent, var(--itxgo-code-bg) 70%);
  display: flex;
  align-items: flex-end;
  justify-content: center;
  padding-bottom: 6px;
  color: var(--itxgo-code-label);
  font-size: 18px;
  font-weight: normal;
  font-family: system-ui, -apple-system, sans-serif;
  pointer-events: none;
  border-radius: 6px;
}

/* 工具栏 */
.article-content pre .itxgo-code-tools {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  height: 38px;
  padding: 0 16px;
  background: var(--itxgo-code-bg);
  display: flex;
  align-items: center;
  justify-content: space-between;
  border-radius: 6px 6px 0 0;
  transition: background-color 0.3s ease;
  z-index: 10;
  cursor: default;
}

.article-content pre .itxgo-code-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  width: 100%;
  gap: 12px;
}

.article-content pre .itxgo-code-label {
  font-family: Cascadia Code;
  font-size: 12px;
  font-weight: 600;
  color: var(--itxgo-code-label);
  letter-spacing: 0.5px;
  user-select: none;
  text-transform: uppercase;
  transition: color 0.3s ease;
  cursor: default;
}

.article-content pre .itxgo-code-actions {
  display: flex;
  align-items: center;
  gap: 6px;
}

/* 按钮样式 */
.article-content pre .itxgo-code-btn {
  display: flex;
  align-items: center;
  gap: 6px;
  background: transparent;
  border: 1px solid transparent;
  color: var(--itxgo-btn-text);
  font-size: 12px;
  cursor: pointer;
  padding: 4px 0 4px 4px;
  border-radius: 6px;
  transition: all 0.2s ease;
  user-select: none;
  font-family: Cascadia Code;
  font-weight: 500;
  height: 28px;
}

.article-content pre .itxgo-code-btn:disabled {
  cursor: not-allowed;
  opacity: 0.7;
}

.article-content pre .itxgo-copy .copy-icon {
  flex-shrink: 0;
  stroke-width: 2;
}

.article-content pre .itxgo-copy .copy-text {
  font-size: 12px;
}

.article-content pre .itxgo-toggle {
  width: 28px;
  min-width: 28px;
  padding: 0;
  justify-content: center;
  font-size: 12px;
}

/* 右下角折叠按钮 */
.article-content pre .itxgo-collapse-corner-btn {
  display: none;
  position: absolute;
  bottom: 12px;
  right: 12px;
  z-index: 20;
  background: transparent;
  border: none;
  font-size: 18px;
  color: var(--itxgo-code-label);
  cursor: pointer;
}

/* 仅在展开状态显示 */
.article-content pre.itxgo-expanded .itxgo-collapse-corner-btn {
  display: block;
}

.article-content pre .itxgo-collapse-corner-btn:hover {
  opacity: 1;
}

/* 滚动条 */
.article-content pre.itxgo-code-block::-webkit-scrollbar {
  width: 8px;
  height: 8px;
}

.article-content pre.itxgo-code-block::-webkit-scrollbar-track {
  background: transparent;
  border-radius: 6px;
}

.article-content pre.itxgo-code-block::-webkit-scrollbar-thumb {
  background: var(--itxgo-scrollbar-thumb);
  border-radius: 4px;
}

.article-content pre.itxgo-code-block::-webkit-scrollbar-thumb:hover {
  background: color-mix(in srgb, var(--itxgo-scrollbar-thumb) 80%, var(--itxgo-code-text));
}

/* 重置代码块内部元素样式 */
.article-content pre.itxgo-code-block code,
.article-content pre.itxgo-code-block code * {
  background: transparent;
  padding: 0;
  margin: 0;
  border: none;
  border-radius: 0;
}

/* 行内代码 */
.article-content code:not(pre > code) {
  font-family: Cascadia Code;
  background-color: rgba(88, 166, 255, 0.1);
  color: #58a6ff;
  margin: 0 1px;
  padding: 2px 6px;
  border-radius: 4px;
  font-size: 0.88em;
  transition: all 0.2s ease;
}

.article-content code:not(pre > code):hover {
  background-color: rgba(88, 166, 255, 0.15);
}

/* 响应式 */
@media (max-width: 768px) {
  .article-content pre.itxgo-code-block {
    font-size: 13px;
    padding: 36px 12px 10px;
    margin: 0.8rem -8px;
    border-radius: 0;
  }
  
  .article-content pre .itxgo-code-tools {
    height: 34px;
    padding: 0 12px;
  }
  
  .article-content pre .itxgo-code-btn {
    padding: 3px 8px;
    font-size: 11px;
    height: 26px;
  }
  
  .article-content pre .itxgo-toggle {
    width: 26px;
    min-width: 26px;
  }
  
  .article-content pre .itxgo-code-label {
    font-size: 11px;
  }
}

5 ✅️代码块 CSS 样式 - 终版 - 2026年1月15日

:root {
  /* 代码块 浅色主题 */
  --itxgo-code-bg-light: var(--color-bg-light);
  --itxgo-code-text-light: #24292f;
  --itxgo-border-light: #d1d9e0;
  --itxgo-btn-text-light: #57606a;
  --itxgo-code-label-light: #6e7781;
  --itxgo-scrollbar-thumb-light: #afb8c1;
  
  /* 代码块 深色主题 */
  --itxgo-code-bg-dark: #30302e;
  --itxgo-code-text-dark: #e6edf3;
  --itxgo-border-dark: #30363d;
  --itxgo-btn-text-dark: #c9d1d9;
  --itxgo-code-label-dark: #8b949e;
  --itxgo-scrollbar-thumb-dark: #484f58;
  
  /* 代码块 默认使用浅色主题 */
  --itxgo-code-bg: var(--itxgo-code-bg-light);
  --itxgo-code-text: var(--itxgo-code-text-light);
  --itxgo-border: var(--itxgo-border-light);
  --itxgo-btn-text: var(--itxgo-btn-text-light);
  --itxgo-code-label: var(--itxgo-code-label-light);
  --itxgo-scrollbar-thumb: var(--itxgo-scrollbar-thumb-light);
}

/* ==========================================
   代码块 - 需置于 文章详情页 样式下
   ========================================== */

/* 深色主题切换 */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) {
    --itxgo-code-bg: var(--itxgo-code-bg-dark);
    --itxgo-code-text: var(--itxgo-code-text-dark);
    --itxgo-border: var(--itxgo-border-dark);
    --itxgo-btn-text: var(--itxgo-btn-text-dark);
    --itxgo-code-label: var(--itxgo-code-label-dark);
    --itxgo-scrollbar-thumb: var(--itxgo-scrollbar-thumb-dark);
  }
}

[data-theme="dark"],
.dark-mode,
.dark {
  --itxgo-code-bg: var(--itxgo-code-bg-dark);
  --itxgo-code-text: var(--itxgo-code-text-dark);
  --itxgo-border: var(--itxgo-border-dark);
  --itxgo-btn-text: var(--itxgo-btn-text-dark);
  --itxgo-code-label: var(--itxgo-code-label-dark);
  --itxgo-scrollbar-thumb: var(--itxgo-scrollbar-thumb-dark);
}

/* 防止页面加载瞬间出现横向滚动条 对 pre 标签生效 */
.article-content pre {
  max-width: 100%;
  width: 100%;
  box-sizing: border-box;
  white-space: pre-wrap;
  overflow-wrap: break-word;
  word-break: break-word;
  visibility: hidden;
  opacity: 0;
  position: relative;
  z-index: 0;
}

.article-content pre > code {
  display: block;
  width: 100%;
  white-space: pre-wrap;
  word-break: break-word;
}

/* 初始化完成后的淡入动画 */
@keyframes itxgo-fade-in {
  from { opacity: 0; }
  to { opacity: 1; }
}

.article-content pre.itxgo-initialized {
  visibility: visible;
  animation: itxgo-fade-in 0.4s ease-out forwards;
}

/* 代码块容器 */
.article-content pre.itxgo-code-block {
  position: relative;
  background: var(--itxgo-code-bg);
  color: var(--itxgo-code-text);
  font-family: Cascadia Code;
  font-size: 14px;
  line-height: 1.4286;
  padding: 40px 16px 12px;
  border-radius: var(--radius-md);
  margin: 1rem 0;
  overflow: hidden;
  transition: max-height 0.3s ease-out, background-color 0.3s ease;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  border: 1px solid #e9ecef;
}

.article-content pre.itxgo-code-block > code {
  font-family: inherit;
  background: none;
  border: none;
  padding: 0;
  margin: 0;
  tab-size: 2;
}

/* ==========================================
   Prism.js 语法高亮样式 - DeepSeek 配色
   ========================================== */

/* 浅色主题 */
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.comment,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.prolog,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.doctype,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.cdata {
  color: #6b7280;
  font-style: italic;
}

:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.punctuation {
  color: #374151;
}

:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.property,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.tag,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.boolean,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.number,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.constant,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.symbol,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.deleted {
  color: #0284c7;
}

:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.selector,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-name,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.string,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.char,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.builtin,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.inserted {
  color: #059669;
}

:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.operator,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.entity,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.url,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .language-css .token.string,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .style .token.string {
  color: #dc2626;
}

:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.atrule,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-value,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.keyword {
  color: #7c3aed;
}

:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.function,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.class-name {
  color: #2563eb;
}

:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.regex,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.important,
:root:not([data-theme="dark"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.variable {
  color: #ea580c;
}

/* 深色主题 - 媒体查询 */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.comment,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.prolog,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.doctype,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.cdata {
    color: #94a3b8;
    font-style: italic;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.punctuation {
    color: #e2e8f0;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.property,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.tag,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.boolean,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.number,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.constant,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.symbol,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.deleted {
    color: #38bdf8;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.selector,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-name,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.string,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.char,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.builtin,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.inserted {
    color: #4ade80;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.operator,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.entity,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.url,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .language-css .token.string,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .style .token.string {
    color: #f87171;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.atrule,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-value,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.keyword {
    color: #a78bfa;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.function,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.class-name {
    color: #60a5fa;
  }

  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.regex,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.important,
  :root:not([data-theme="light"]) .article-content pre.itxgo-code-block code[class*="language-"] .token.variable {
    color: #fb923c;
  }
}

/* 深色主题 - 显式指定 */
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.comment,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.prolog,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.doctype,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.cdata,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.comment,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.prolog,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.doctype,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.cdata,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.comment,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.prolog,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.doctype,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.cdata {
  color: #94a3b8;
  font-style: italic;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.punctuation,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.punctuation,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.punctuation {
  color: #e2e8f0;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.property,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.tag,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.boolean,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.number,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.constant,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.symbol,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.deleted,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.property,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.tag,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.boolean,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.number,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.constant,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.symbol,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.deleted,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.property,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.tag,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.boolean,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.number,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.constant,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.symbol,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.deleted {
  color: #38bdf8;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.selector,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-name,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.string,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.char,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.builtin,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.inserted,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.selector,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-name,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.string,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.char,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.builtin,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.inserted,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.selector,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-name,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.string,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.char,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.builtin,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.inserted {
  color: #4ade80;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.operator,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.entity,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.url,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .language-css .token.string,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .style .token.string,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.operator,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.entity,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.url,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .language-css .token.string,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .style .token.string,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.operator,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.entity,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.url,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .language-css .token.string,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .style .token.string {
  color: #f87171;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.atrule,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-value,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.keyword,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.atrule,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-value,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.keyword,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.atrule,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.attr-value,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.keyword {
  color: #a78bfa;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.function,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.class-name,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.function,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.class-name,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.function,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.class-name {
  color: #60a5fa;
}

[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.regex,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.important,
[data-theme="dark"] .article-content pre.itxgo-code-block code[class*="language-"] .token.variable,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.regex,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.important,
.dark-mode .article-content pre.itxgo-code-block code[class*="language-"] .token.variable,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.regex,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.important,
.dark .article-content pre.itxgo-code-block code[class*="language-"] .token.variable {
  color: #fb923c;
}

/* 展开/折叠状态 */
.article-content pre.itxgo-expanded {
  overflow: auto;
  max-height: none;
}

.article-content pre.itxgo-collapsed {
  overflow: hidden;
  cursor: pointer;
}

.article-content pre.itxgo-collapsed::after {
  content: "︾";
  position: absolute;
  left: 0;
  right: 0;
  bottom: 0;
  height: 40px;
  background: linear-gradient(to bottom, transparent, var(--itxgo-code-bg) 70%);
  display: flex;
  align-items: flex-end;
  justify-content: center;
  padding-bottom: 6px;
  color: var(--itxgo-code-label);
  font-size: 18px;
  font-weight: normal;
  font-family: system-ui, -apple-system, sans-serif;
  pointer-events: none;
  border-radius: 6px;
}

/* 工具栏 */
.article-content pre .itxgo-code-tools {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  height: 38px;
  padding: 0 16px;
  background: var(--itxgo-code-bg);
  display: flex;
  align-items: center;
  justify-content: space-between;
  border-radius: 6px 6px 0 0;
  transition: background-color 0.3s ease;
  z-index: 10;
  cursor: default;
}

.article-content pre .itxgo-code-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  width: 100%;
  gap: 12px;
}

.article-content pre .itxgo-code-label {
  font-family: Cascadia Code;
  font-size: 12px;
  font-weight: 600;
  color: var(--itxgo-code-label);
  letter-spacing: 0.5px;
  user-select: none;
  text-transform: uppercase;
  transition: color 0.3s ease;
  cursor: default;
}

.article-content pre .itxgo-code-actions {
  display: flex;
  align-items: center;
  gap: 6px;
}

/* 按钮样式 */
.article-content pre .itxgo-code-btn {
  display: flex;
  align-items: center;
  gap: 6px;
  background: transparent;
  border: 1px solid transparent;
  color: var(--itxgo-btn-text);
  font-size: 12px;
  cursor: pointer;
  padding: 4px 0 4px 4px;
  border-radius: 6px;
  transition: all 0.2s ease;
  user-select: none;
  font-family: Cascadia Code;
  font-weight: 500;
  height: 28px;
}

.article-content pre .itxgo-code-btn:disabled {
  cursor: not-allowed;
  opacity: 0.7;
}

.article-content pre .itxgo-copy .copy-icon {
  flex-shrink: 0;
  stroke-width: 2;
}

.article-content pre .itxgo-copy .copy-text {
  font-size: 12px;
}

.article-content pre .itxgo-toggle {
  width: 28px;
  min-width: 28px;
  padding: 0;
  justify-content: center;
  font-size: 12px;
}

/* 右下角折叠按钮 */
.article-content pre .itxgo-collapse-corner-btn {
  display: none;
  position: absolute;
  bottom: 12px;
  right: 12px;
  z-index: 20;
  background: transparent;
  border: none;
  font-size: 18px;
  color: var(--itxgo-code-label);
  cursor: pointer;
}

/* 仅在展开状态显示 */
.article-content pre.itxgo-expanded .itxgo-collapse-corner-btn {
  display: block;
}

.article-content pre .itxgo-collapse-corner-btn:hover {
  opacity: 1;
}

/* 滚动条 */
.article-content pre.itxgo-code-block::-webkit-scrollbar {
  width: 8px;
  height: 8px;
}

.article-content pre.itxgo-code-block::-webkit-scrollbar-track {
  background: transparent;
  border-radius: 6px;
}

.article-content pre.itxgo-code-block::-webkit-scrollbar-thumb {
  background: var(--itxgo-scrollbar-thumb);
  border-radius: 4px;
}

.article-content pre.itxgo-code-block::-webkit-scrollbar-thumb:hover {
  background: color-mix(in srgb, var(--itxgo-scrollbar-thumb) 80%, var(--itxgo-code-text));
}

/* 重置代码块内部元素样式 */
.article-content pre.itxgo-code-block code,
.article-content pre.itxgo-code-block code * {
  background: transparent;
  padding: 0;
  margin: 0;
  border: none;
  border-radius: 0;
}

/* 行内代码 */
.article-content code:not(pre > code) {
  font-family: Cascadia Code;
  background-color: rgba(88, 166, 255, 0.1);
  color: #58a6ff;
  margin: 0 1px;
  padding: 2px 6px;
  border-radius: 4px;
  font-size: 0.88em;
  transition: all 0.2s ease;
}

.article-content code:not(pre > code):hover {
  background-color: rgba(88, 166, 255, 0.15);
}

/* 响应式 */
@media (max-width: 768px) {
  .article-content pre.itxgo-code-block {
    font-size: 13px;
    padding: 36px 12px 10px;
    margin: 0.8rem -16px; 
    max-width: 100vw;
    border-radius: 0;
  }
  
  .article-content pre .itxgo-code-tools {
    height: 34px;
    padding: 0 12px;
  }
  
  .article-content pre .itxgo-code-btn {
    padding: 3px 8px;
    font-size: 11px;
    height: 26px;
  }
  
  .article-content pre .itxgo-toggle {
    width: 26px;
    min-width: 26px;
  }
  
  .article-content pre .itxgo-code-label {
    font-size: 11px;
  }
}

6 ✅️代码块 CSS 样式 - 终版简化版 - 2026年1月17日

:root {
  /* 代码块 UI 变量 - 浅色 */
  --itxgo-code-bg-light: var(--color-bg-light);
  --itxgo-code-text-light: #24292f;
  --itxgo-border-light: #e9ecef; 
  --itxgo-btn-text-light: #57606a;
  --itxgo-code-label-light: #6e7781;
  --itxgo-scrollbar-thumb-light: #afb8c1;

  /* 代码块 UI 变量 - 深色 */
  --itxgo-code-bg-dark: #30302e;
  --itxgo-code-text-dark: #e6edf3;
  --itxgo-border-dark: #30363d;
  --itxgo-btn-text-dark: #c9d1d9;
  --itxgo-code-label-dark: #8b949e;
  --itxgo-scrollbar-thumb-dark: #484f58;

  /* 语法高亮颜色变量 - 浅色 */
  --token-comment: #6b7280;
  --token-punctuation: #374151;
  --token-property: #0284c7;
  --token-selector: #059669;
  --token-operator: #dc2626;
  --token-keyword: #7c3aed;
  --token-function: #2563eb;
  --token-variable: #ea580c;

  /* 默认应用浅色变量 */
  --itxgo-code-bg: var(--itxgo-code-bg-light);
  --itxgo-code-text: var(--itxgo-code-text-light);
  --itxgo-border: var(--itxgo-border-light);
  --itxgo-btn-text: var(--itxgo-btn-text-light);
  --itxgo-code-label: var(--itxgo-code-label-light);
  --itxgo-scrollbar-thumb: var(--itxgo-scrollbar-thumb-light);
}

/* ==========================================
   代码块 - 需置于 文章详情页 样式下
   ========================================== */

/* 深色主题 - 媒体查询 */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) {
    /* UI 变量覆盖 */
    --itxgo-code-bg: var(--itxgo-code-bg-dark);
    --itxgo-code-text: var(--itxgo-code-text-dark);
    --itxgo-border: var(--itxgo-border-dark);
    --itxgo-btn-text: var(--itxgo-btn-text-dark);
    --itxgo-code-label: var(--itxgo-code-label-dark);
    --itxgo-scrollbar-thumb: var(--itxgo-scrollbar-thumb-dark);
    
    /* 语法变量覆盖 - 深色配色 */
    --token-comment: #94a3b8;
    --token-punctuation: #e2e8f0;
    --token-property: #38bdf8;
    --token-selector: #4ade80;
    --token-operator: #f87171;
    --token-keyword: #a78bfa;
    --token-function: #60a5fa;
    --token-variable: #fb923c;
  }
}

/* 深色主题 - 显式指定类名/属性 */
[data-theme="dark"],
.dark-mode,
.dark {
  /* UI 变量覆盖 */
  --itxgo-code-bg: var(--itxgo-code-bg-dark);
  --itxgo-code-text: var(--itxgo-code-text-dark);
  --itxgo-border: var(--itxgo-border-dark);
  --itxgo-btn-text: var(--itxgo-btn-text-dark);
  --itxgo-code-label: var(--itxgo-code-label-dark);
  --itxgo-scrollbar-thumb: var(--itxgo-scrollbar-thumb-dark);

  /* 语法变量覆盖 - 深色配色 */
  --token-comment: #94a3b8;
  --token-punctuation: #e2e8f0;
  --token-property: #38bdf8;
  --token-selector: #4ade80;
  --token-operator: #f87171;
  --token-keyword: #a78bfa;
  --token-function: #60a5fa;
  --token-variable: #fb923c;
}

/* ===== 基础布局与容器 ===== */

/* 防止页面加载瞬间出现横向滚动条 */
.article-content pre {
  max-width: 100%;
  width: 100%;
  box-sizing: border-box;
  white-space: pre-wrap;
  overflow-wrap: break-word;
  word-break: break-word;
  visibility: hidden;
  opacity: 0;
  position: relative;
  z-index: 0;
}

.article-content pre > code {
  display: block;
  width: 100%;
  white-space: pre-wrap;
  word-break: break-word;
}

/* 初始化完成后的淡入动画 */
@keyframes itxgo-fade-in {
  from { opacity: 0; }
  to { opacity: 1; }
}

.article-content pre.itxgo-initialized {
  visibility: visible;
  animation: itxgo-fade-in 0.4s ease-out forwards;
}

/* 代码块容器 */
.article-content pre.itxgo-code-block {
  position: relative;
  background: var(--itxgo-code-bg);
  color: var(--itxgo-code-text);
  font-family: Cascadia Code;
  font-size: 14px;
  line-height: 1.4286;
  padding: 40px 16px 12px;
  border-radius: var(--radius-md);
  margin: 1rem 0;
  overflow: hidden;
  transition: max-height 0.3s ease-out, background-color 0.3s ease;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  /* 使用变量边框,确保深色模式下正确 */
  border: 1px solid var(--itxgo-border);
}

.article-content pre.itxgo-code-block > code {
  font-family: inherit;
  background: none;
  border: none;
  padding: 0;
  margin: 0;
  tab-size: 2;
}

/* ===== Prism.js 语法高亮 ===== */
.article-content pre.itxgo-code-block .token.comment,
.article-content pre.itxgo-code-block .token.prolog,
.article-content pre.itxgo-code-block .token.doctype,
.article-content pre.itxgo-code-block .token.cdata {
  color: var(--token-comment);
  font-style: italic;
}

.article-content pre.itxgo-code-block .token.punctuation {
  color: var(--token-punctuation);
}

.article-content pre.itxgo-code-block .token.property,
.article-content pre.itxgo-code-block .token.tag,
.article-content pre.itxgo-code-block .token.boolean,
.article-content pre.itxgo-code-block .token.number,
.article-content pre.itxgo-code-block .token.constant,
.article-content pre.itxgo-code-block .token.symbol,
.article-content pre.itxgo-code-block .token.deleted {
  color: var(--token-property);
}

.article-content pre.itxgo-code-block .token.selector,
.article-content pre.itxgo-code-block .token.attr-name,
.article-content pre.itxgo-code-block .token.string,
.article-content pre.itxgo-code-block .token.char,
.article-content pre.itxgo-code-block .token.builtin,
.article-content pre.itxgo-code-block .token.inserted {
  color: var(--token-selector);
}

.article-content pre.itxgo-code-block .token.operator,
.article-content pre.itxgo-code-block .token.entity,
.article-content pre.itxgo-code-block .token.url,
.article-content pre.itxgo-code-block .language-css .token.string,
.article-content pre.itxgo-code-block .style .token.string {
  color: var(--token-operator);
}

.article-content pre.itxgo-code-block .token.atrule,
.article-content pre.itxgo-code-block .token.attr-value,
.article-content pre.itxgo-code-block .token.keyword {
  color: var(--token-keyword);
}

.article-content pre.itxgo-code-block .token.function,
.article-content pre.itxgo-code-block .token.class-name {
  color: var(--token-function);
}

.article-content pre.itxgo-code-block .token.regex,
.article-content pre.itxgo-code-block .token.important,
.article-content pre.itxgo-code-block .token.variable {
  color: var(--token-variable);
}

/* ===== 交互组件 (Toolbar, 展开/折叠, 滚动条) ===== */

/* 展开/折叠状态 */
.article-content pre.itxgo-expanded {
  overflow: auto;
  max-height: none;
}

.article-content pre.itxgo-collapsed {
  overflow: hidden;
  cursor: pointer;
}

.article-content pre.itxgo-collapsed::after {
  content: "︾";
  position: absolute;
  left: 0;
  right: 0;
  bottom: 0;
  height: 40px;
  background: linear-gradient(to bottom, transparent, var(--itxgo-code-bg) 70%);
  display: flex;
  align-items: flex-end;
  justify-content: center;
  padding-bottom: 6px;
  color: var(--itxgo-code-label);
  font-size: 18px;
  font-weight: normal;
  font-family: system-ui, -apple-system, sans-serif;
  pointer-events: none;
  border-radius: 6px;
}

/* 工具栏 */
.article-content pre .itxgo-code-tools {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  height: 38px;
  padding: 0 16px;
  background: var(--itxgo-code-bg);
  display: flex;
  align-items: center;
  justify-content: space-between;
  border-radius: 6px 6px 0 0;
  transition: background-color 0.3s ease;
  z-index: 10;
  cursor: default;
}

.article-content pre .itxgo-code-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  width: 100%;
  gap: 12px;
}

.article-content pre .itxgo-code-label {
  font-family: Cascadia Code;
  font-size: 12px;
  font-weight: 600;
  color: var(--itxgo-code-label);
  letter-spacing: 0.5px;
  user-select: none;
  text-transform: uppercase;
  transition: color 0.3s ease;
  cursor: default;
}

.article-content pre .itxgo-code-actions {
  display: flex;
  align-items: center;
  gap: 6px;
}

/* 按钮样式 */
.article-content pre .itxgo-code-btn {
  display: flex;
  align-items: center;
  gap: 6px;
  background: transparent;
  border: 1px solid transparent;
  color: var(--itxgo-btn-text);
  font-size: 12px;
  cursor: pointer;
  padding: 4px 0 4px 4px;
  border-radius: 6px;
  transition: all 0.2s ease;
  user-select: none;
  font-family: Cascadia Code;
  font-weight: 500;
  height: 28px;
}

.article-content pre .itxgo-code-btn:disabled {
  cursor: not-allowed;
  opacity: 0.7;
}

.article-content pre .itxgo-copy .copy-icon { flex-shrink: 0; stroke-width: 2; }
.article-content pre .itxgo-copy .copy-text { font-size: 12px; }

.article-content pre .itxgo-toggle {
  width: 28px;
  min-width: 28px;
  padding: 0;
  justify-content: center;
  font-size: 12px;
}

/* 右下角折叠按钮 */
.article-content pre .itxgo-collapse-corner-btn {
  display: none;
  position: absolute;
  bottom: 12px;
  right: 12px;
  z-index: 20;
  background: transparent;
  border: none;
  font-size: 18px;
  color: var(--itxgo-code-label);
  cursor: pointer;
}

.article-content pre.itxgo-expanded .itxgo-collapse-corner-btn { display: block; }
.article-content pre .itxgo-collapse-corner-btn:hover { opacity: 1; }

/* 滚动条 */
.article-content pre.itxgo-code-block::-webkit-scrollbar { width: 8px; height: 8px; }
.article-content pre.itxgo-code-block::-webkit-scrollbar-track { background: transparent; border-radius: 6px; }
.article-content pre.itxgo-code-block::-webkit-scrollbar-thumb {
  background: var(--itxgo-scrollbar-thumb);
  border-radius: 4px;
}
.article-content pre.itxgo-code-block::-webkit-scrollbar-thumb:hover {
  background: color-mix(in srgb, var(--itxgo-scrollbar-thumb) 80%, var(--itxgo-code-text));
}

/* 重置代码块内部元素样式 */
.article-content pre.itxgo-code-block code,
.article-content pre.itxgo-code-block code * {
  background: transparent; padding: 0; margin: 0; border: none; border-radius: 0;
}

/* 行内代码 */
.article-content code:not(pre > code) {
  font-family: Cascadia Code;
  background-color: rgba(88, 166, 255, 0.1);
  color: #58a6ff;
  margin: 0 1px;
  padding: 2px 6px;
  border-radius: 4px;
  font-size: 0.88em;
  transition: all 0.2s ease;
}

.article-content code:not(pre > code):hover { background-color: rgba(88, 166, 255, 0.15); }

/* 响应式 */
@media (max-width: 768px) {
  .article-content pre.itxgo-code-block {
    font-size: 13px;
    padding: 36px 12px 10px;
    margin: 0.8rem -16px; 
    max-width: 100vw;
    border-radius: 0;
  }
  .article-content pre .itxgo-code-tools { height: 34px; padding: 0 12px; }
  .article-content pre .itxgo-code-btn { padding: 3px 8px; font-size: 11px; height: 26px; }
  .article-content pre .itxgo-toggle { width: 26px; min-width: 26px; }
  .article-content pre .itxgo-code-label { font-size: 11px; }
}

⚡️JS 代码:

1. 🔄代码块 JS 函数代码 - 2026年1月1日

// =============================
// 7. 代码块功能
// =============================
const CODE_CONFIG = {
  COLLAPSE_LINE_THRESHOLD: 5,
  COLLAPSE_LINES: 5,
  COPY_FEEDBACK_DURATION: 1200,
  RESIZE_DEBOUNCE_DELAY: 150,
};

async function initCodeBlocks() {
  requestAnimationFrame(async () => {
    if (document.fonts && document.fonts.ready) {
      try {
        await document.fonts.ready;
      } catch (e) {
        console.warn("Fonts ready failed", e);
      }
    }

    const blocks = document.querySelectorAll(".article-content pre");
    if (blocks.length === 0) return;

    for (let i = 0; i < blocks.length; i++) {
      await processBlock(blocks[i], i);
    }
  });

  // Resize 处理
  let resizeTimer = null;
  window.addEventListener(
    "resize",
    () => {
      clearTimeout(resizeTimer);
      resizeTimer = setTimeout(() => {
        document
          .querySelectorAll(".article-content pre.collapsed")
          .forEach((pre) => {
            const codeEl = pre.querySelector("code") || pre;
            const cs = getComputedStyle(codeEl);
            const fs = parseFloat(cs.fontSize) || 15;
            const lh = parseFloat(cs.lineHeight) || fs * 1.6;
            const ps = getComputedStyle(pre);
            const pt = parseFloat(ps.paddingTop) || 48;
            const pb = parseFloat(ps.paddingBottom) || 16;
            const newHeight = Math.ceil(
              pt + lh * CODE_CONFIG.COLLAPSE_LINES + pb
            );
            pre._collapsedHeight = newHeight;
            pre.style.maxHeight = newHeight + "px";
          });
      }, CODE_CONFIG.RESIZE_DEBOUNCE_DELAY);
    },
    { passive: true }
  );
}

// 代码块处理逻辑分离
async function processBlock(pre, index) {
  // 分片处理,避免在主线程阻塞太久(Safari 尤其敏感)
  if (index > 0 && index % 5 === 0) {
    await new Promise((resolve) => setTimeout(resolve, 0));
  }

  const codeEl = pre.querySelector("code") || pre;
  // 使用 textContent 避免 innerText 触发重排
  let raw = (codeEl.textContent || "")
    .replace(/^\n+|\n+$/g, "")
    .replace(/\r\n/g, "\n");
  const lines = raw ? raw.split("\n") : [];

  // ==================== 生成行号 ====================
  if (!pre.hasAttribute("data-line-numbers")) {
    const lineNumbersText = lines.map((_, i) => i + 1).join("\n");
    pre.setAttribute("data-line-numbers", lineNumbersText);
  }

  // ==================== 工具栏 ====================
  if (!pre.querySelector(".code-tools")) {
    const shouldCollapse = lines.length > CODE_CONFIG.COLLAPSE_LINE_THRESHOLD;
    const toggleBtnHTML = shouldCollapse
      ? '<button class="code-btn code-toggle" type="button">展开</button>'
      : "";

    const tools = document.createElement("div");
    tools.className = "code-tools";
    tools.innerHTML = `
            <span class="code-title">CODE - iTxGo™️</span>
            <div style="display:flex; gap:8px; align-items:center;">
                ${toggleBtnHTML}
                <button class="code-btn code-copy" type="button" style="width:43px; min-width:43px; text-align:center;">复制</button>
            </div>
        `;
    pre.insertBefore(tools, pre.firstChild);
  }

  // ==================== 复制功能 ====================
  const copyBtn = pre.querySelector(".code-copy");
  if (copyBtn && !copyBtn.hasListener) {
    copyBtn.hasListener = true;
    // Safari 下使用 touchstart 或确保 click 有效
    copyBtn.addEventListener("click", async () => {
      try {
        await navigator.clipboard.writeText(raw);
        showCopyFeedback(copyBtn);
      } catch (e) {
        // 降级处理
        if (copyWithFallback(raw)) showCopyFeedback(copyBtn);
        else showCopyError(copyBtn, "复制失败");
      }
    });
  }

  // ==================== 折叠功能 ====================
  const shouldCollapse = lines.length > CODE_CONFIG.COLLAPSE_LINE_THRESHOLD;
  if (!shouldCollapse) {
    pre.classList.add("expanded");
    pre.classList.remove("collapsed");
    return;
  }

  // 计算折叠高度
  const cs = getComputedStyle(codeEl);
  const fontSize = parseFloat(cs.fontSize) || 15;
  const lineHeight = parseFloat(cs.lineHeight) || fontSize * 1.6;

  const ps = getComputedStyle(pre);
  const paddingTop = parseFloat(ps.paddingTop) || 48;
  const paddingBottom = parseFloat(ps.paddingBottom) || 16;
  const collapsedHeight = Math.ceil(
    paddingTop + lineHeight * CODE_CONFIG.COLLAPSE_LINES + paddingBottom
  );

  pre._collapsedHeight = collapsedHeight;
  pre.style.maxHeight = collapsedHeight + "px";
  pre.classList.add("collapsed");
  pre.classList.remove("expanded");

  // ==================== 折叠按钮事件 ====================
  const toggleBtn = pre.querySelector(".code-toggle");
  if (toggleBtn && !toggleBtn.hasListener) {
    toggleBtn.hasListener = true;
    toggleBtn.addEventListener("click", () => {
      const isCollapsed = pre.classList.contains("collapsed");
      if (isCollapsed) {
        pre.classList.replace("collapsed", "expanded");
        pre.style.maxHeight = "none";
        toggleBtn.textContent = "折叠";
      } else {
        pre.classList.replace("expanded", "collapsed");
        pre.style.maxHeight = pre._collapsedHeight + "px";
        toggleBtn.textContent = "展开";
      }
    });
  }
}

function copyWithFallback(text) {
  try {
    const textarea = document.createElement("textarea");
    textarea.value = text;
    // 防止 iOS 缩放和滚动
    textarea.style.position = "fixed";
    textarea.style.left = "-9999px";
    textarea.style.top = "0";
    document.body.appendChild(textarea);
    textarea.select();
    textarea.setSelectionRange(0, 99999); // 移动端兼容
    const success = document.execCommand("copy");
    document.body.removeChild(textarea);
    return success;
  } catch (err) {
    return false;
  }
}

function showCopyFeedback(btn) {
  const originalText = btn.textContent;
  btn.textContent = "✓";
  btn.disabled = true;
  btn.style.color = "#4ade80";
  setTimeout(() => {
    btn.textContent = originalText;
    btn.disabled = false;
    btn.style.color = "";
  }, CODE_CONFIG.COPY_FEEDBACK_DURATION);
}

function showCopyError(btn, message) {
  const originalText = btn.textContent;
  btn.textContent = "失败";
  btn.disabled = true;
  btn.style.color = "#ef4444";
  setTimeout(() => {
    btn.textContent = originalText;
    btn.disabled = false;
    btn.style.color = "";
  }, CODE_CONFIG.COPY_FEEDBACK_DURATION);
}

2. ✅️代码块 JS 函数代码 - AI风格 - 2026年1月12日

// =============================
// 7. 代码块功能
// =============================
const ITXGO_CODE_CONFIG = {
  COLLAPSE_LINE_THRESHOLD: 10,
  COLLAPSE_LINES: 10,
  COPY_FEEDBACK_DURATION: 1200,
  RESIZE_DEBOUNCE_DELAY: 150,
};

async function initItxgoCodeBlocks() {
  // 观察DOM变化
  const observer = new MutationObserver((mutations) => {
    mutations.forEach((mutation) => {
      mutation.addedNodes.forEach((node) => {
        if (node.nodeType === 1) {
          const newBlocks = node.querySelectorAll?.(".article-content pre:not(.itxgo-initialized)") || [];
          newBlocks.forEach((block, index) => setTimeout(() => processItxgoBlock(block), index * 10));
        }
      });
    });
  });

  observer.observe(document.body, { childList: true, subtree: true });

  // 处理现有代码块
  requestAnimationFrame(async () => {
    if (document.fonts?.ready) {
      try { await document.fonts.ready; } catch (e) {}
    }

    const blocks = document.querySelectorAll(".article-content pre:not(.itxgo-initialized)");
    for (let i = 0; i < blocks.length; i++) {
      await processItxgoBlock(blocks[i]);
    }
  });

  // Resize 处理
  let resizeTimer;
  window.addEventListener("resize", () => {
    clearTimeout(resizeTimer);
    resizeTimer = setTimeout(() => {
      document.querySelectorAll(".article-content pre.itxgo-collapsed").forEach((pre) => {
        const codeEl = pre.querySelector("code") || pre;
        const cs = getComputedStyle(codeEl);
        const fs = parseFloat(cs.fontSize) || 14;
        const lh = parseFloat(cs.lineHeight) || fs * 1.4286;
        const ps = getComputedStyle(pre);
        const pt = parseFloat(ps.paddingTop) || 40;
        const pb = parseFloat(ps.paddingBottom) || 12;
        const newHeight = Math.ceil(pt + lh * ITXGO_CODE_CONFIG.COLLAPSE_LINES + pb);
        pre._itxgoCollapsedHeight = newHeight;
        pre.style.maxHeight = newHeight + "px";
      });
    }, ITXGO_CODE_CONFIG.RESIZE_DEBOUNCE_DELAY);
  }, { passive: true });
}

async function processItxgoBlock(pre) {
  if (pre.classList.contains('itxgo-initialized')) return;
  pre.classList.add('itxgo-initialized', 'itxgo-code-block');

  const codeEl = pre.querySelector("code") || pre;
  const raw = (codeEl.textContent || "").replace(/^\n+|\n+$/g, "").replace(/\r\n/g, "\n");
  const lines = raw.split("\n");
  const shouldCollapse = lines.length > ITXGO_CODE_CONFIG.COLLAPSE_LINE_THRESHOLD;

  // 添加工具栏
  if (!pre.querySelector(".itxgo-code-tools")) {
    const tools = document.createElement("div");
    tools.className = "itxgo-code-tools";
    tools.innerHTML = `
      <div class="itxgo-code-header">
        <span class="itxgo-code-label">CODE</span>
        <div class="itxgo-code-actions">
          ${shouldCollapse ? '<button class="itxgo-code-btn itxgo-toggle" type="button" aria-label="展开代码">展开</button>' : ''}
          <button class="itxgo-code-btn itxgo-copy" type="button" aria-label="复制代码">
            <svg class="copy-icon" width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2">
              <rect x="9" y="9" width="13" height="13" rx="2" ry="2"></rect>
              <path d="M5 15H4a2 2 0 0 1-2-2V4a2 2 0 0 1 2-2h9a2 2 0 0 1 2 2v1"></path>
            </svg>
            <span class="copy-text">复制</span>
          </button>
        </div>
      </div>
    `;
    pre.insertBefore(tools, pre.firstChild);

    // 复制功能
    const copyBtn = tools.querySelector(".itxgo-copy");
    copyBtn.addEventListener("click", async (e) => {
      e.stopPropagation();
      try {
        await navigator.clipboard.writeText(raw);
        showFeedback(copyBtn, true);
      } catch (e) {
        showFeedback(copyBtn, copyWithFallback(raw));
      }
    });

    // 折叠功能
    if (shouldCollapse) {
      const toggleBtn = tools.querySelector(".itxgo-toggle");
      const cs = getComputedStyle(codeEl);
      const fontSize = parseFloat(cs.fontSize) || 14;
      const lineHeight = parseFloat(cs.lineHeight) || fontSize * 1.4286;
      const ps = getComputedStyle(pre);
      const paddingTop = parseFloat(ps.paddingTop) || 40;
      const paddingBottom = parseFloat(ps.paddingBottom) || 12;
      const collapsedHeight = Math.ceil(paddingTop + lineHeight * ITXGO_CODE_CONFIG.COLLAPSE_LINES + paddingBottom);

      pre._itxgoCollapsedHeight = collapsedHeight;
      pre.style.maxHeight = collapsedHeight + "px";
      pre.classList.add("itxgo-collapsed");

      const toggle = () => {
        const isCollapsed = pre.classList.contains("itxgo-collapsed");
        if (isCollapsed) {
          pre.classList.replace("itxgo-collapsed", "itxgo-expanded");
          pre.style.maxHeight = "none";
          toggleBtn.textContent = '折叠';
          toggleBtn.setAttribute('aria-label', '折叠代码');
        } else {
          pre.classList.replace("itxgo-expanded", "itxgo-collapsed");
          pre.style.maxHeight = collapsedHeight + "px";
          toggleBtn.textContent = '展开';
          toggleBtn.setAttribute('aria-label', '展开代码');
        }
      };

      toggleBtn.addEventListener("click", (e) => {
        e.stopPropagation();
        toggle();
      });

      pre.addEventListener('click', (e) => {
        if (!e.target.closest('.itxgo-code-tools') && pre.classList.contains('itxgo-collapsed')) {
          toggle();
        }
      });
    } else {
      pre.classList.add("itxgo-expanded");
    }
  }
}

function showFeedback(btn, success) {
  const copyText = btn.querySelector('.copy-text');
  const svgIcon = btn.querySelector('.copy-icon');
  const originalText = copyText.textContent;
  const originalSVG = svgIcon.innerHTML;
  
  if (success) {
    copyText.textContent = '复制';
    svgIcon.innerHTML = '<path d="M20 6L9 17l-5-5" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/>';
  } else {
    copyText.textContent = '复制失败';
  }
  
  setTimeout(() => {
    copyText.textContent = originalText;
    svgIcon.innerHTML = originalSVG;
  }, ITXGO_CODE_CONFIG.COPY_FEEDBACK_DURATION);
}

function copyWithFallback(text) {
  try {
    const textarea = document.createElement("textarea");
    textarea.value = text;
    textarea.style.cssText = "position:fixed;left:-9999px;top:0";
    document.body.appendChild(textarea);
    textarea.select();
    textarea.setSelectionRange(0, 99999);
    const success = document.execCommand("copy");
    document.body.removeChild(textarea);
    return success;
  } catch {
    return false;
  }
}

// 初始化
function initCodeBlocks() {
  initItxgoCodeBlocks();
}

3. ✅️代码块 JS 函数代码 - AI风格 新增右下折叠按钮 - 2026年1月12日

// =============================
// 7. 代码块功能
// =============================
const ITXGO_CODE_CONFIG = {
  COLLAPSE_LINE_THRESHOLD: 10,
  COLLAPSE_LINES: 10,
  COPY_FEEDBACK_DURATION: 1200,
  RESIZE_DEBOUNCE_DELAY: 150,
};
async function initItxgoCodeBlocks() {
  // 观察DOM变化
  const observer = new MutationObserver((mutations) => {
    mutations.forEach((mutation) => {
      mutation.addedNodes.forEach((node) => {
        if (node.nodeType === 1) {
          const newBlocks = node.querySelectorAll?.(".article-content pre:not(.itxgo-initialized)") || [];
          newBlocks.forEach((block, index) => setTimeout(() => processItxgoBlock(block), index * 10));
        }
      });
    });
  });
  observer.observe(document.body, { childList: true, subtree: true });
  // 处理现有代码块
  requestAnimationFrame(async () => {
    if (document.fonts?.ready) {
      try { await document.fonts.ready; } catch (e) {}
    }
    const blocks = document.querySelectorAll(".article-content pre:not(.itxgo-initialized)");
    for (let i = 0; i < blocks.length; i++) {
      await processItxgoBlock(blocks[i]);
    }
  });
  // Resize 处理
  let resizeTimer;
  window.addEventListener("resize", () => {
    clearTimeout(resizeTimer);
    resizeTimer = setTimeout(() => {
      document.querySelectorAll(".article-content pre.itxgo-collapsed").forEach((pre) => {
        const codeEl = pre.querySelector("code") || pre;
        const cs = getComputedStyle(codeEl);
        const fs = parseFloat(cs.fontSize) || 14;
        const lh = parseFloat(cs.lineHeight) || fs * 1.4286;
        const ps = getComputedStyle(pre);
        const pt = parseFloat(ps.paddingTop) || 40;
        const pb = parseFloat(ps.paddingBottom) || 12;
        const newHeight = Math.ceil(pt + lh * ITXGO_CODE_CONFIG.COLLAPSE_LINES + pb);
        pre._itxgoCollapsedHeight = newHeight;
        pre.style.maxHeight = newHeight + "px";
      });
    }, ITXGO_CODE_CONFIG.RESIZE_DEBOUNCE_DELAY);
  }, { passive: true });
}
async function processItxgoBlock(pre) {
  if (pre.classList.contains('itxgo-initialized')) return;
  pre.classList.add('itxgo-initialized', 'itxgo-code-block');
  const codeEl = pre.querySelector("code") || pre;
  const raw = (codeEl.textContent || "").replace(/^\n+|\n+$/g, "").replace(/\r\n/g, "\n");
  const lines = raw.split("\n");
  const shouldCollapse = lines.length > ITXGO_CODE_CONFIG.COLLAPSE_LINE_THRESHOLD;
  // 添加工具栏
  if (!pre.querySelector(".itxgo-code-tools")) {
    const tools = document.createElement("div");
    tools.className = "itxgo-code-tools";
    tools.innerHTML = `
      <div class="itxgo-code-header">
        <span class="itxgo-code-label">CODE</span>
        <div class="itxgo-code-actions">
          ${shouldCollapse ? '<button class="itxgo-code-btn itxgo-toggle" type="button" aria-label="展开代码">展开</button>' : ''}
          <button class="itxgo-code-btn itxgo-copy" type="button" aria-label="复制代码">
            <svg class="copy-icon" width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2">
              <rect x="9" y="9" width="13" height="13" rx="2" ry="2"></rect>
              <path d="M5 15H4a2 2 0 0 1-2-2V4a2 2 0 0 1 2-2h9a2 2 0 0 1 2 2v1"></path>
            </svg>
            <span class="copy-text">复制</span>
          </button>
        </div>
      </div>
    `;
    pre.insertBefore(tools, pre.firstChild);
    // 复制功能
    const copyBtn = tools.querySelector(".itxgo-copy");
    copyBtn.addEventListener("click", async (e) => {
      e.stopPropagation();
      try {
        await navigator.clipboard.writeText(raw);
        showFeedback(copyBtn, true);
      } catch (e) {
        showFeedback(copyBtn, copyWithFallback(raw));
      }
    });
    // 折叠功能
    if (shouldCollapse) {
      const toggleBtn = tools.querySelector(".itxgo-toggle");
      // 右下角折叠按钮
      const cornerBtn = document.createElement("button");
      cornerBtn.className = "itxgo-collapse-corner-btn";
      cornerBtn.type = "button";
      cornerBtn.innerHTML = "︽";
      cornerBtn.setAttribute('aria-label', '折叠代码');
      // 仅用于折叠 展开由原有toggleBtn或点击pre处理
      cornerBtn.addEventListener("click", (e) => {
        e.stopPropagation();
        // 只有在展开状态下才有效
        if (!pre.classList.contains("itxgo-collapsed")) {
            pre.classList.replace("itxgo-expanded", "itxgo-collapsed");
            pre.style.maxHeight = pre._itxgoCollapsedHeight + "px";
            // 同步更新原有工具栏按钮状态
            if(toggleBtn) {
                toggleBtn.textContent = '展开';
                toggleBtn.setAttribute('aria-label', '展开代码');
            }
        }
      });
      pre.appendChild(cornerBtn);
      // 计算折叠高度
      const cs = getComputedStyle(codeEl);
      const fontSize = parseFloat(cs.fontSize) || 14;
      const lineHeight = parseFloat(cs.lineHeight) || fontSize * 1.4286;
      const ps = getComputedStyle(pre);
      const paddingTop = parseFloat(ps.paddingTop) || 40;
      const paddingBottom = parseFloat(ps.paddingBottom) || 12;
      const collapsedHeight = Math.ceil(paddingTop + lineHeight * ITXGO_CODE_CONFIG.COLLAPSE_LINES + paddingBottom);
      pre._itxgoCollapsedHeight = collapsedHeight;
      pre.style.maxHeight = collapsedHeight + "px";
      pre.classList.add("itxgo-collapsed");
      const toggle = () => {
        const isCollapsed = pre.classList.contains("itxgo-collapsed");
        if (isCollapsed) {
          pre.classList.replace("itxgo-collapsed", "itxgo-expanded");
          pre.style.maxHeight = "none";
          toggleBtn.textContent = '折叠';
          toggleBtn.setAttribute('aria-label', '折叠代码');
        } else {
          pre.classList.replace("itxgo-expanded", "itxgo-collapsed");
          pre.style.maxHeight = collapsedHeight + "px";
          toggleBtn.textContent = '展开';
          toggleBtn.setAttribute('aria-label', '展开代码');
        }
      };
      // 工具栏按钮点击事件
      toggleBtn.addEventListener("click", (e) => {
        e.stopPropagation();
        toggle();
      });
      // 点击代码块空白处展开事件
      pre.addEventListener('click', (e) => {
        if (!e.target.closest('.itxgo-code-tools') && pre.classList.contains('itxgo-collapsed')) {
          toggle();
        }
      });
    } else {
      pre.classList.add("itxgo-expanded");
    }
  }
}
function showFeedback(btn, success) {
  const copyText = btn.querySelector('.copy-text');
  const svgIcon = btn.querySelector('.copy-icon');
  const originalText = copyText.textContent;
  const originalSVG = svgIcon.innerHTML;
  if (success) {
    copyText.textContent = '复制';
    svgIcon.innerHTML = '<path d="M20 6L9 17l-5-5" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/>';
  } else {
    copyText.textContent = '复制失败';
  }
  setTimeout(() => {
    copyText.textContent = originalText;
    svgIcon.innerHTML = originalSVG;
  }, ITXGO_CODE_CONFIG.COPY_FEEDBACK_DURATION);
}
function copyWithFallback(text) {
  try {
    const textarea = document.createElement("textarea");
    textarea.value = text;
    textarea.style.cssText = "position:fixed;left:-9999px;top:0";
    document.body.appendChild(textarea);
    textarea.select();
    textarea.setSelectionRange(0, 99999);
    const success = document.execCommand("copy");
    document.body.removeChild(textarea);
    return success;
  } catch {
    return false;
  }
}
// 初始化
function initCodeBlocks() {
  initItxgoCodeBlocks();
}

4. ✅️代码块 JS 函数代码 - AI风格 代码高亮版 - 2026年1月13日

// =============================
// 代码块功能(含自动语法高亮识别)
// =============================

const ITXGO_CODE_CONFIG = {
  COLLAPSE_LINE_THRESHOLD: 10,
  COLLAPSE_LINES: 10,
  COPY_FEEDBACK_DURATION: 1200,
  RESIZE_DEBOUNCE_DELAY: 150,
  PRISM_CDN: 'https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/prism.min.js',
  // 常用语言组件映射
  LANGUAGE_COMPONENTS: {
    'javascript': 'prism-javascript',
    'js': 'prism-javascript',
    'typescript': 'prism-typescript',
    'ts': 'prism-typescript',
    'python': 'prism-python',
    'py': 'prism-python',
    'java': 'prism-java',
    'cpp': 'prism-cpp',
    'c': 'prism-c',
    'csharp': 'prism-csharp',
    'cs': 'prism-csharp',
    'php': 'prism-php',
    'ruby': 'prism-ruby',
    'go': 'prism-go',
    'rust': 'prism-rust',
    'sql': 'prism-sql',
    'bash': 'prism-bash',
    'shell': 'prism-bash',
    'json': 'prism-json',
    'yaml': 'prism-yaml',
    'xml': 'prism-markup',
    'html': 'prism-markup',
    'css': 'prism-css',
    'scss': 'prism-scss',
    'markdown': 'prism-markdown',
    'md': 'prism-markdown'
  }
};

// 加载 Prism.js 及语言组件
let prismLoaded = false;
let prismLoading = false;
const loadedLanguages = new Set(['markup', 'css', 'clike', 'javascript']); // Prism 核心包含的语言

async function loadPrism() {
  if (prismLoaded) return true;
  if (prismLoading) {
    return new Promise((resolve) => {
      const check = setInterval(() => {
        if (prismLoaded) {
          clearInterval(check);
          resolve(true);
        }
      }, 100);
    });
  }

  prismLoading = true;
  
  return new Promise((resolve, reject) => {
    const script = document.createElement('script');
    script.src = ITXGO_CODE_CONFIG.PRISM_CDN;
    script.onload = () => {
      prismLoaded = true;
      prismLoading = false;
      if (window.Prism) {
        window.Prism.manual = true;
      }
      resolve(true);
    };
    script.onerror = () => {
      prismLoading = false;
      console.error('Failed to load Prism.js');
      reject(false);
    };
    document.head.appendChild(script);
  });
}

// 加载特定语言的组件
async function loadLanguageComponent(language) {
  if (!language || loadedLanguages.has(language)) return true;
  
  const componentName = ITXGO_CODE_CONFIG.LANGUAGE_COMPONENTS[language.toLowerCase()];
  if (!componentName) return true;
  
  return new Promise((resolve) => {
    const script = document.createElement('script');
    script.src = `https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/components/${componentName}.min.js`;
    script.onload = () => {
      loadedLanguages.add(language);
      resolve(true);
    };
    script.onerror = () => {
      console.warn(`Failed to load Prism component: ${componentName}`);
      resolve(false);
    };
    document.head.appendChild(script);
  });
}

// 自动检测代码语言
function autoDetectLanguage(code) {
  const trimmed = code.trim();
  
  // JavaScript/TypeScript 特征
  if (/^(import|export|const|let|var|function|class)\s/.test(trimmed) ||
      /=>\s*{/.test(trimmed) ||
      /\bconsole\.(log|error|warn)/.test(trimmed) ||
      /(async|await)\s/.test(trimmed)) {
    if (/:\s*(string|number|boolean|any)\s*[;=)]/.test(trimmed) || /interface\s+\w+/.test(trimmed)) {
      return 'typescript';
    }
    return 'javascript';
  }
  
  // Python 特征
  if (/^(def|class|import|from|if __name__|print\()\s/.test(trimmed) ||
      /:\s*$/.test(trimmed.split('\n')[0]) ||
      /\bself\.\w+/.test(trimmed)) {
    return 'python';
  }
  
  // HTML 特征
  if (/^<!DOCTYPE html>|^<html|^<\!--/.test(trimmed) ||
      /<(div|span|p|h[1-6]|body|head|meta|link)[\s>]/.test(trimmed)) {
    return 'html';
  }
  
  // CSS 特征
  if (/^[.#]?[\w-]+\s*{/.test(trimmed) ||
      /@(media|keyframes|import)\s/.test(trimmed) ||
      /:\s*[^;]+;/.test(trimmed.split('\n')[0])) {
    return 'css';
  }
  
  // Java 特征
  if (/^(public|private|protected|class|interface)\s/.test(trimmed) ||
      /System\.(out|err)\.print/.test(trimmed) ||
      /\bpublic static void main\(/.test(trimmed)) {
    return 'java';
  }
  
  // PHP 特征
  if (/^<\?php/.test(trimmed) || /\$\w+\s*=/.test(trimmed)) {
    return 'php';
  }
  
  // C/C++ 特征
  if (/#include\s*</.test(trimmed) ||
      /^(int|void|char|float|double)\s+\w+\s*\(/.test(trimmed)) {
    if (/std::|iostream|vector|string/.test(trimmed)) {
      return 'cpp';
    }
    return 'c';
  }
  
  // JSON 特征
  if (/^\s*[{\[]/.test(trimmed) && /[}\]]\s*$/.test(trimmed)) {
    try {
      JSON.parse(trimmed);
      return 'json';
    } catch (e) {
      // 不是有效的JSON
    }
  }
  
  // SQL 特征
  if (/^(SELECT|INSERT|UPDATE|DELETE|CREATE|ALTER|DROP)\s+/i.test(trimmed)) {
    return 'sql';
  }
  
  // Bash/Shell 特征
  if (/^#!\/bin\/(bash|sh)/.test(trimmed) ||
      /^(echo|cd|ls|mkdir|rm|cp|mv|grep|cat)\s/.test(trimmed) ||
      /\$\{?\w+\}?/.test(trimmed)) {
    return 'bash';
  }
  
  // YAML 特征
  if (/^\w+:\s*$/.test(trimmed.split('\n')[0]) && !/[{}]/.test(trimmed)) {
    return 'yaml';
  }
  
  return null; // 无法识别
}

// 检测代码块语言(优先使用标记的语言)
function detectLanguage(codeElement) {
  // 从 class 中检测 language-xxx
  const classes = codeElement.className.split(' ');
  for (const cls of classes) {
    if (cls.startsWith('language-')) {
      return cls.replace('language-', '');
    }
  }
  
  // 从父元素 pre 检测
  const pre = codeElement.closest('pre');
  if (pre) {
    const preClasses = pre.className.split(' ');
    for (const cls of preClasses) {
      if (cls.startsWith('language-')) {
        return cls.replace('language-', '');
      }
    }
  }
  
  // 如果没有标记,尝试自动检测
  const code = codeElement.textContent || '';
  return autoDetectLanguage(code);
}

// 应用语法高亮
async function applyHighlight(codeElement, language) {
  if (!window.Prism || !language) return false;
  
  try {
    await loadLanguageComponent(language);
    
    if (!codeElement.classList.contains(`language-${language}`)) {
      codeElement.classList.add(`language-${language}`);
    }
    
    window.Prism.highlightElement(codeElement);
    return true;
  } catch (e) {
    console.error('Highlight error:', e);
    return false;
  }
}

async function initItxgoCodeBlocks() {
  // 预加载 Prism.js
  loadPrism().catch(() => {
    console.warn('Prism.js not available, syntax highlighting disabled');
  });

  // 观察DOM变化
  const observer = new MutationObserver((mutations) => {
    mutations.forEach((mutation) => {
      mutation.addedNodes.forEach((node) => {
        if (node.nodeType === 1) {
          const newBlocks = node.querySelectorAll?.(".article-content pre:not(.itxgo-initialized)") || [];
          newBlocks.forEach((block, index) => setTimeout(() => processItxgoBlock(block), index * 10));
        }
      });
    });
  });

  observer.observe(document.body, { childList: true, subtree: true });

  // 处理现有代码块
  requestAnimationFrame(async () => {
    if (document.fonts?.ready) {
      try { await document.fonts.ready; } catch (e) {}
    }

    const blocks = document.querySelectorAll(".article-content pre:not(.itxgo-initialized)");
    for (let i = 0; i < blocks.length; i++) {
      await processItxgoBlock(blocks[i]);
    }
  });

  // Resize 处理
  let resizeTimer;
  window.addEventListener("resize", () => {
    clearTimeout(resizeTimer);
    resizeTimer = setTimeout(() => {
      document.querySelectorAll(".article-content pre.itxgo-collapsed").forEach((pre) => {
        const codeEl = pre.querySelector("code") || pre;
        const cs = getComputedStyle(codeEl);
        const fs = parseFloat(cs.fontSize) || 14;
        const lh = parseFloat(cs.lineHeight) || fs * 1.4286;
        const ps = getComputedStyle(pre);
        const pt = parseFloat(ps.paddingTop) || 40;
        const pb = parseFloat(ps.paddingBottom) || 12;
        const newHeight = Math.ceil(pt + lh * ITXGO_CODE_CONFIG.COLLAPSE_LINES + pb);
        pre._itxgoCollapsedHeight = newHeight;
        pre.style.maxHeight = newHeight + "px";
      });
    }, ITXGO_CODE_CONFIG.RESIZE_DEBOUNCE_DELAY);
  }, { passive: true });
}

async function processItxgoBlock(pre) {
  if (pre.classList.contains('itxgo-initialized')) return;
  pre.classList.add('itxgo-initialized', 'itxgo-code-block');

  const codeEl = pre.querySelector("code") || pre;
  const raw = (codeEl.textContent || "").replace(/^\n+|\n+$/g, "").replace(/\r\n/g, "\n");
  const lines = raw.split("\n");
  const shouldCollapse = lines.length > ITXGO_CODE_CONFIG.COLLAPSE_LINE_THRESHOLD;

  // 检测语言并应用高亮
  const language = detectLanguage(codeEl);
  if (prismLoaded && language) {
    await applyHighlight(codeEl, language);
  } else if (!prismLoaded && language) {
    loadPrism().then(() => {
      applyHighlight(codeEl, language);
    });
  }

  // 更新工具栏语言标签
  const languageLabel = language ? language.toUpperCase() : 'CODE';

  // 添加工具栏
  if (!pre.querySelector(".itxgo-code-tools")) {
    const tools = document.createElement("div");
    tools.className = "itxgo-code-tools";
    tools.innerHTML = `
      <div class="itxgo-code-header">
        <span class="itxgo-code-label">${languageLabel}</span>
        <div class="itxgo-code-actions">
          ${shouldCollapse ? '<button class="itxgo-code-btn itxgo-toggle" type="button" aria-label="展开代码">展开</button>' : ''}
          <button class="itxgo-code-btn itxgo-copy" type="button" aria-label="复制代码">
            <svg class="copy-icon" width="15" height="15" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg"><path fill="currentColor" d="M6.149 4.02c.963 0 1.73-.002 2.347.055.626.057 1.163.176 1.646.456.58.334 1.06.815 1.395 1.394.279.484.398 1.02.455 1.646.056.616.055 1.384.055 2.346 0 .963.002 1.73-.055 2.347-.057.626-.176 1.163-.456 1.646-.334.58-.815 1.06-1.394 1.395-.484.279-1.02.398-1.646.455-.616.056-1.384.055-2.347.055-.962 0-1.73.002-2.346-.055-.626-.057-1.163-.176-1.646-.456-.58-.334-1.06-.815-1.394-1.394-.28-.484-.4-1.02-.456-1.646-.056-.616-.056-1.384-.056-2.347 0-.962-.002-1.73.055-2.346.057-.626.177-1.163.456-1.646.335-.58.816-1.06 1.395-1.394.484-.28 1.02-.4 1.646-.456.616-.056 1.384-.056 2.347-.056Zm0 1.358c-.987 0-1.683.002-2.224.049-.53.048-.846.139-1.089.279-.373.215-.682.525-.898.897-.14.243-.231.559-.279 1.09-.049.54-.049 1.236-.049 2.224 0 .987-.002 1.683.049 2.224.048.53.139.846.279 1.089.215.372.525.682.897.897.243.14.559.231 1.09.279.54.049 1.236.049 2.224.049.987 0 1.683-.002 2.224-.049.53-.048.846-.139 1.089-.279.372-.215.682-.525.897-.897.14-.243.231-.559.279-1.09.049-.54.049-1.236.049-2.224 0-.987.002-1.683-.049-2.224-.048-.53-.139-.846-.279-1.089-.215-.373-.525-.682-.897-.897-.243-.14-.559-.231-1.09-.279-.54-.049-1.236-.049-2.224-.049Zm3.652-5.01c.963 0 1.73-.002 2.346.056.625.057 1.162.175 1.646.455.578.334 1.059.815 1.393 1.394.28.484.4 1.02.456 1.646.056.616.055 1.384.055 2.346v1.566c0 .462.002.76-.032 1.018-.199 1.504-1.265 2.725-2.682 3.15V11c.714-.356 1.227-1.05 1.336-1.875.019-.148.021-.336.021-.842V6.264c0-.987-.002-1.683-.049-2.224-.048-.53-.139-.846-.279-1.089-.215-.372-.525-.682-.897-.897-.243-.14-.559-.231-1.09-.279-.54-.049-1.236-.049-2.224-.049H7.715c-.959.002-1.788.553-2.192 1.355H4.07c.472-1.568 1.923-2.71 3.645-2.711h2.087Z"/></svg>
            <span class="copy-text">复制</span>
          </button>
        </div>
      </div>
    `;
    pre.insertBefore(tools, pre.firstChild);

    // 复制功能
    const copyBtn = tools.querySelector(".itxgo-copy");
    copyBtn.addEventListener("click", async (e) => {
      e.stopPropagation();
      try {
        await navigator.clipboard.writeText(raw);
        showFeedback(copyBtn, true);
      } catch (e) {
        showFeedback(copyBtn, copyWithFallback(raw));
      }
    });

    // 折叠功能
    if (shouldCollapse) {
      const toggleBtn = tools.querySelector(".itxgo-toggle");
      
      const cornerBtn = document.createElement("button");
      cornerBtn.className = "itxgo-collapse-corner-btn";
      cornerBtn.type = "button";
      cornerBtn.innerHTML = `<svg viewBox="0 0 1024 1024" xmlns="http://www.w3.org/2000/svg" width="18" height="18" fill="currentColor"><g stroke="currentColor" stroke-width="20" stroke-linecap="round" stroke-linejoin="round"><path d="M125.3 176.1h742.4c15.8 0 28.7-10.6 28.7-23.6s-12.9-23.6-28.7-23.6H125.3c-15.8 0-28.7 10.6-28.7 23.6 0 13 12.9 23.6 28.7 23.6z"/><path d="M492.5 385.2H125.3c-15.4 0-28.1 10.6-28.1 23.6 0 12.9 12.7 23.6 28.1 23.6h367.2c15.4 0 28.1-10.7 28.1-23.6 0-12.9-12.7-23.6-28.1-23.6z"/><path d="M492.5 594.3H125.3c-15.4 0-28.1 10.6-28.1 23.6 0 13.1 12.7 23.6 28.1 23.6h367.2c15.4 0 28.1-10.7 28.1-23.6 0-13.1-12.7-23.6-28.1-23.6z"/><path d="M492.1 803.4H126c-15.8 0-28.7 10.6-28.7 23.6 0 13.1 12.7 23.6 28.7 23.6h366.2c15.8 0 28.7-10.7 28.7-23.6 0-13.1-12.9-23.6-28.7-23.6z"/><path d="M926.31 502.17c1.02-2.25-0.2-9.22-7.78-18.64L819.2 359.42c-8.19-10.24-18.64-15.77-29.49-15.77-10.85 0-21.5 5.53-29.49 15.77L661.09 483.33c-7.78 9.63-9.01 16.59-7.99 18.64 1.43 2.66 8.19 6.35 22.53 6.35h90.52v306.38c0 15.36 10.44 28.06 23.55 28.06s23.55-12.7 23.55-28.06V508.31h90.52c14.34 0 21.5-3.69 22.53-6.14z"/></g></svg>`;
      cornerBtn.setAttribute('aria-label', '折叠代码');
      cornerBtn.title = "折叠";
      cornerBtn.addEventListener("click", (e) => {
        e.stopPropagation();
        if (!pre.classList.contains("itxgo-collapsed")) {
          pre.classList.replace("itxgo-expanded", "itxgo-collapsed");
          pre.style.maxHeight = pre._itxgoCollapsedHeight + "px";
          if(toggleBtn) {
            toggleBtn.textContent = '展开';
            toggleBtn.setAttribute('aria-label', '展开代码');
          }
        }
      });
      pre.appendChild(cornerBtn);

      const cs = getComputedStyle(codeEl);
      const fontSize = parseFloat(cs.fontSize) || 14;
      const lineHeight = parseFloat(cs.lineHeight) || fontSize * 1.4286;
      const ps = getComputedStyle(pre);
      const paddingTop = parseFloat(ps.paddingTop) || 40;
      const paddingBottom = parseFloat(ps.paddingBottom) || 12;
      const collapsedHeight = Math.ceil(paddingTop + lineHeight * ITXGO_CODE_CONFIG.COLLAPSE_LINES + paddingBottom);

      pre._itxgoCollapsedHeight = collapsedHeight;
      pre.style.maxHeight = collapsedHeight + "px";
      pre.classList.add("itxgo-collapsed");

      const toggle = () => {
        const isCollapsed = pre.classList.contains("itxgo-collapsed");
        if (isCollapsed) {
          pre.classList.replace("itxgo-collapsed", "itxgo-expanded");
          pre.style.maxHeight = "none";
          toggleBtn.textContent = '折叠';
          toggleBtn.setAttribute('aria-label', '折叠代码');
        } else {
          pre.classList.replace("itxgo-expanded", "itxgo-collapsed");
          pre.style.maxHeight = collapsedHeight + "px";
          toggleBtn.textContent = '展开';
          toggleBtn.setAttribute('aria-label', '展开代码');
        }
      };

      toggleBtn.addEventListener("click", (e) => {
        e.stopPropagation();
        toggle();
      });

      pre.addEventListener('click', (e) => {
        if (!e.target.closest('.itxgo-code-tools') && pre.classList.contains('itxgo-collapsed')) {
          toggle();
        }
      });
      
    } else {
      pre.classList.add("itxgo-expanded");
    }
  }
}

function showFeedback(btn, success) {
  const copyText = btn.querySelector('.copy-text');
  const svgIcon = btn.querySelector('.copy-icon');
  const originalText = copyText.textContent;
  const originalSVG = svgIcon.innerHTML;
  
  if (success) {
    copyText.textContent = '复制';
    svgIcon.innerHTML = '<path d="M3 8.5L6 11.5L12 5.5" stroke="currentColor" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round"/>';
  } else {
    copyText.textContent = '复制失败';
  }
  
  setTimeout(() => {
    copyText.textContent = originalText;
    svgIcon.innerHTML = originalSVG;
  }, ITXGO_CODE_CONFIG.COPY_FEEDBACK_DURATION);
}

function copyWithFallback(text) {
  try {
    const textarea = document.createElement("textarea");
    textarea.value = text;
    textarea.style.cssText = "position:fixed;left:-9999px;top:0";
    document.body.appendChild(textarea);
    textarea.select();
    textarea.setSelectionRange(0, 99999);
    const success = document.execCommand("copy");
    document.body.removeChild(textarea);
    return success;
  } catch {
    return false;
  }
}

// 初始化
function initCodeBlocks() {
  initItxgoCodeBlocks();
}

5. ✅️代码块 JS 函数代码 - 终版 - 2026年1月15日

// =============================
// 7. 代码块功能 - chat.z.ai
// =============================

const ITXGO_CODE_CONFIG = {
  COLLAPSE_LINES: 10,
  THRESHOLD: 10,
  COPY_DURATION: 1000,
  RESIZE_DELAY: 150,
  BASE_CDN: 'https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/',
  CHUNK_SIZE: 2
};

// 常量管理
const ICONS = {
  COPY: `<svg class="copy-icon" width="15" height="15" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg"><path fill="currentColor" d="M6.149 4.02c.963 0 1.73-.002 2.347.055.626.057 1.163.176 1.646.456.58.334 1.06.815 1.395 1.394.279.484.398 1.02.455 1.646.056.616.055 1.384.055 2.346 0 .963.002 1.73-.055 2.347-.057.626-.176 1.163-.456 1.646-.334.58-.815 1.06-1.394 1.395-.484.279-1.02.398-1.646.455-.616.056-1.384.055-2.347.055-.962 0-1.73.002-2.346-.055-.626-.057-1.163-.176-1.646-.456-.58-.334-1.06-.815-1.394-1.394-.28-.484-.4-1.02-.456-1.646-.056-.616-.056-1.384-.056-2.347 0-.962-.002-1.73.055-2.346.057-.626.177-1.163.456-1.646.335-.58.816-1.06 1.395-1.394.484-.28 1.02-.4 1.646-.456.616-.056 1.384-.056 2.347-.056Zm0 1.358c-.987 0-1.683.002-2.224.049-.53.048-.846.139-1.089.279-.373.215-.682.525-.898.897-.14.243-.231.559-.279 1.09-.049.54-.049 1.236-.049 2.224 0 .987-.002 1.683.049 2.224.048.53.139.846.279 1.089.215.372.525.682.897.897.243.14.559.231 1.09.279.54.049 1.236.049 2.224.049.987 0 1.683-.002 2.224-.049.53-.048.846-.139 1.089-.279.372-.215.682-.525.897-.897.14-.243.231-.559.279-1.09.049-.54.049-1.236.049-2.224 0-.987.002-1.683-.049-2.224-.048-.53-.139-.846-.279-1.089-.215-.373-.525-.682-.897-.897-.243-.14-.559-.231-1.09-.279-.54-.049-1.236-.049-2.224-.049Zm3.652-5.01c.963 0 1.73-.002 2.346.056.625.057 1.162.175 1.646.455.578.334 1.059.815 1.393 1.394.28.484.4 1.02.456 1.646.056.616.055 1.384.055 2.346v1.566c0 .462.002.76-.032 1.018-.199 1.504-1.265 2.725-2.682 3.15V11c.714-.356 1.227-1.05 1.336-1.875.019-.148.021-.336.021-.842V6.264c0-.987-.002-1.683-.049-2.224-.048-.53-.139-.846-.279-1.089-.215-.372-.525-.682-.897-.897-.243-.14-.559-.231-1.09-.279-.54-.049-1.236-.049-2.224-.049H7.715c-.959.002-1.788.553-2.192 1.355H4.07c.472-1.568 1.923-2.71 3.645-2.711h2.087Z"/></svg>`,
  COLLAPSE: `<svg viewBox="0 0 1024 1024" xmlns="http://www.w3.org/2000/svg" width="18" height="18" fill="currentColor"><g stroke="currentColor" stroke-width="20" stroke-linecap="round" stroke-linejoin="round"><path d="M125.3 176.1h742.4c15.8 0 28.7-10.6 28.7-23.6s-12.9-23.6-28.7-23.6H125.3c-15.8 0-28.7 10.6-28.7 23.6 0 13 12.9 23.6 28.7 23.6z"/><path d="M492.5 385.2H125.3c-15.4 0-28.1 10.6-28.1 23.6 0 12.9 12.7 23.6 28.1 23.6h367.2c15.4 0 28.1-10.7 28.1-23.6 0-12.9-12.7-23.6-28.1-23.6z"/><path d="M492.5 594.3H125.3c-15.4 0-28.1 10.6-28.1 23.6 0 13.1 12.7 23.6 28.1 23.6h367.2c15.4 0 28.1-10.7 28.1-23.6 0-13.1-12.7-23.6-28.1-23.6z"/><path d="M492.1 803.4H126c-15.8 0-28.7 10.6-28.7 23.6 0 13.1 12.7 23.6 28.7 23.6h366.2c15.8 0 28.7-10.7 28.7-23.6 0-13.1-12.9-23.6-28.7-23.6z"/><path d="M926.31 502.17c1.02-2.25-0.2-9.22-7.78-18.64L819.2 359.42c-8.19-10.24-18.64-15.77-29.49-15.77-10.85 0-21.5 5.53-29.49 15.77L661.09 483.33c-7.78 9.63-9.01 16.59-7.99 18.64 1.43 2.66 8.19 6.35 22.53 6.35h90.52v306.38c0 15.36 10.44 28.06 23.55 28.06s23.55-12.7 23.55-28.06V508.31h90.52c14.34 0 21.5-3.69 22.53-6.14z"/></g></svg>`
};

let prismLoaded = false, prismLoading = false;
const loadedLanguages = new Set(['markup', 'css', 'clike', 'javascript']);
const LANG_MAP = { js: 'javascript', ts: 'typescript', py: 'python', rb: 'ruby', cs: 'csharp', sh: 'bash', md: 'markdown', yaml: 'yaml' };

// ===== 异步加载 =====

function loadScript(src) {
  return new Promise((resolve, reject) => {
    const s = document.createElement('script');
    s.src = src; s.onload = resolve; s.onerror = reject;
    document.head.appendChild(s);
  });
}

async function loadPrism() {
  if (prismLoaded) return true;
  if (prismLoading) return new Promise(r => setTimeout(r, 50)); // 异步等待 不阻塞
  prismLoading = true;
  try {
    await loadScript(ITXGO_CODE_CONFIG.BASE_CDN + 'prism.min.js');
    prismLoaded = true;
    if (window.Prism) Prism.manual = true;
  } catch (e) { console.warn('Prism load failed'); }
  finally { prismLoading = false; }
  return prismLoaded;
}

async function loadLangComp(lang) {
  if (lang === 'html' || lang === 'markup') {
    if (loadedLanguages.has('markup')) return true;
    loadedLanguages.add('markup');
    return true;
  }
  if (!lang || loadedLanguages.has(lang)) return true;
  
  const key = LANG_MAP[lang] || lang;
  if (!key) return true;
  if (key === 'markup') {
    loadedLanguages.add('markup');
    return true;
  }

  return new Promise(resolve => {
    const s = document.createElement('script');
    s.src = `${ITXGO_CODE_CONFIG.BASE_CDN}components/prism-${key}.min.js`;
    s.onload = () => { 
      loadedLanguages.add(lang); 
      resolve(true); 
    };
    s.onerror = () => { 
      resolve(false); 
    };
    document.head.appendChild(s);
  });
}

async function runInChunks(items, processFn) {
  const { CHUNK_SIZE } = ITXGO_CODE_CONFIG;
  for (let i = 0; i < items.length; i += CHUNK_SIZE) {
    const chunk = items.slice(i, i + CHUNK_SIZE);
    chunk.forEach(processFn);
    applyCollapseHeights(chunk);
    // 标记代码块准备就绪,触发淡入动画
    chunk.forEach(pre => {
      if (!pre.classList.contains('itxgo-ready')) {
        pre.classList.add('itxgo-ready');
      }
    });
    if (i + CHUNK_SIZE < items.length) await new Promise(r => requestAnimationFrame(r));
  }
}

// ===== 代码语言判断核心逻辑 =====

function getLanguage(el) {
  const classMatch = (e) => e && (e.className || '').match(/language-(\w+)/);
  let m = classMatch(el) || classMatch(el.closest('pre'));
  if (m) return m[1];

  const text = (el.textContent || '').trim();
  const sample = text.slice(0, 500);

  const RULES = {
    css: {
      threshold: 15,
      score: [
        [/--[\w-]+\s*:/, 10],
        [/@media|@keyframes|@import|@font-face|:root|@supports/, 10],
        [/([.#]?[\w-]+\s*,?\s*[{])/, 5],
        [/(display|color|background|margin|padding|border|font-size|position)\s*:\s*[^;]+;/, 5],
      ],
    },
    javascript: {
      threshold: 10,
      score: [
        [/\b(const|let|async|await|import|export)\b/, 10],
        [/\bvar\s+[a-zA-Z_$]/, 10],
        [/\b(function|class)\s+[a-zA-Z_$][\w$]*\s*\(/, 10],
        [/=>\s*[{(]/, 8],
        [/\b(console|document|window|JSON)\./, 8],
        [/\.then\(|\.catch\(|new Promise\(/, 8],
      ],
      postDetect: (s) =>
        /\b(interface|type|enum|implements|: string|: number|: any)\b/.test(s)
          ? 'typescript'
          : null,
    },
    html: {
      threshold: 10,
      score: [
        [/^<!DOCTYPE|<html|<head|<body|<div|<span|<p\s/i, 15],
        [/<\/[\w]+>/, 10],
      ],
      result: 'markup',
    },
  };

  // 统一打分
  const scores = {};
  for (const lang in RULES) {
    let total = 0;
    for (const [regex, weight] of RULES[lang].score) {
      if (regex.test(sample)) total += weight;
    }
    scores[lang] = total;
  }

  // 选择最高得分
  let winner = null;
  let maxScore = 0;

  for (const lang in scores) {
    if (scores[lang] > maxScore) {
      maxScore = scores[lang];
      winner = lang;
    }
  }

  if (winner && maxScore >= RULES[winner].threshold) {
    const rule = RULES[winner];
    if (rule.postDetect) {
      const refined = rule.postDetect(sample);
      if (refined) return refined;
    }
    return rule.result || winner;
  }

  // --- 特殊语言判定(确定性规则) ---
  
  // JSON (需要完整的 text)
  try {
    if (/^\s*[{[]/.test(text) && /[}\]]\s*$/.test(text)) {
      JSON.parse(text);
      return 'json';
    }
  } catch (e) {}

  // Python (使用 /m 修饰符以支持多行检测)
  if (/^(def |class |import |from |if __name__|print\(|self\.|try:|except:)/m.test(sample)) return 'python';

  if (/^(public|private|protected|class|interface|enum|package)\s|System\.out\.print|@Override/m.test(sample)) return 'java';

  if (/^<\?php|\$\w+\s*=|namespace\s+|use\s+[\w\\]+;/m.test(sample)) return 'php';

  if (/#include <|(int|void|char|float|double|bool)\s+\w+\s*[\(\{]|std::|cout|cin|endl/.test(sample))
    return /std::|vector|namespace|class\s+\w+/.test(sample) ? 'cpp' : 'c';

  if (/^(SELECT|INSERT|UPDATE|DELETE|CREATE|ALTER|DROP|TRUNCATE|GRANT|REVOKE)\s+/i.test(sample)) return 'sql';

  if (/^#!\/(bin\/bash|bin\/sh|usr\/bin\/env)|^(echo|cd|ls|mkdir|rm|cp|mv|grep|sudo|npm|git|docker|curl|wget)\b/m.test(sample))
    return 'bash';

  if (/^package\s+main|func\s+\w+\(|go\s+func|import\s+\(/.test(sample)) return 'go';

  if (/^require\s|def\s+\w+|end$|puts\s|class\s+\w+/m.test(sample)) return 'ruby';

  if (/^fn\s+main|let\s+mut\b|use\s+std::|impl\s+\w+/.test(sample)) return 'rust';

  if (/^import\s+(Foundation|UIKit|Swift)|func\s+\w+|@IBOutlet/.test(sample)) return 'swift';

  if (/^fun\s+|val\s+\w+|class\s+\w+:/m.test(sample)) return 'kotlin';

  if (/^[\w-]+:\s*\n|^\s+-\s+/.test(sample)) return 'yaml';
  if (/^#{1,6}\s|^\*{3,}$|^\-{3,}$|^\[.*\]\(.*\)|^\d+\.\s|^\>\s/.test(sample)) return 'markdown';

  // --- 最终兜底 ---
  if (/[{}]\s*;/.test(sample) && (scores.javascript || 0) < 5) return 'css';

  return 'plaintext';
}

async function applyHighlight(el, lang) {
  if (!window.Prism || !lang) return;
  await loadLangComp(lang);
  el.classList.add(`language-${lang}`);
  Prism.highlightElement(el); // 同步执行 在 processBlock 中未 await 故不阻塞主线程
}

// ===== UI 与 交互 =====

function processBlock(pre) {
  if (pre.classList.contains('itxgo-initialized')) return;
  pre.classList.add('itxgo-initialized', 'itxgo-code-block');
  const codeEl = pre.querySelector('code') || pre;
  const raw = codeEl.textContent.replace(/^\n+|\n+$/g, '').replace(/\r\n/g, '\n');
  const lang = getLanguage(codeEl);
  const shouldCollapse = raw.split('\n').length > ITXGO_CODE_CONFIG.THRESHOLD;

  // 不使用 await 允许高亮在后台异步进行 避免长任务
  if (prismLoaded) applyHighlight(codeEl, lang);
  else loadPrism().then(() => applyHighlight(codeEl, lang));

  buildUI(pre, lang, shouldCollapse, raw);
}

function buildUI(pre, lang, shouldCollapse, raw) {
  const tools = document.createElement('div');
  tools.className = 'itxgo-code-tools';
  tools.innerHTML = `
    <div class="itxgo-code-header">
      <span class="itxgo-code-label">${lang.toUpperCase()}</span>
      <div class="itxgo-code-actions">
        ${shouldCollapse ? '<button class="itxgo-code-btn itxgo-toggle" type="button">展开</button>' : ''}
        <button class="itxgo-code-btn itxgo-copy" type="button">
          ${ICONS.COPY}<span class="copy-text">复制</span>
        </button>
      </div>
    </div>`;
  pre.insertBefore(tools, pre.firstChild);

  const copyBtn = tools.querySelector('.itxgo-copy');
  copyBtn.onclick = async (e) => {
    e.stopPropagation();
    let ok = false;
    try { await navigator.clipboard.writeText(raw); ok = true; } 
    catch { 
      const t = document.createElement('textarea'); 
      t.value = raw; t.style.cssText = "position:fixed;left:-9999px"; 
      document.body.appendChild(t); t.select(); 
      ok = document.execCommand('copy'); 
      document.body.removeChild(t); 
    }
    const icon = copyBtn.querySelector('.copy-icon'), txt = copyBtn.querySelector('.copy-text');
    const oldH = icon.innerHTML, oldT = txt.textContent;
    icon.innerHTML = '<path d="M3 8.5L6 11.5L12 5.5" stroke="currentColor" stroke-width="2" stroke-linecap="round"/>';
    txt.textContent = ok ? '复制' : '失败';
    setTimeout(() => { icon.innerHTML = oldH; txt.textContent = oldT; }, ITXGO_CODE_CONFIG.COPY_DURATION);
  };

  if (shouldCollapse) {
    const toggleBtn = tools.querySelector('.itxgo-toggle');
    const cornerBtn = document.createElement('button');
    cornerBtn.className = 'itxgo-collapse-corner-btn';
    cornerBtn.title = "折叠"; 
    cornerBtn.setAttribute('aria-label', '折叠');
    cornerBtn.innerHTML = ICONS.COLLAPSE;
    Object.assign(cornerBtn.style, { opacity: 0, pointerEvents: 'none', transition: 'opacity 0.2s' });
    
    const toggle = (forceState) => {
      const isCollapsed = pre.classList.contains('itxgo-collapsed');
      const shouldExpand = forceState !== undefined ? forceState : isCollapsed;
      if (shouldExpand) {
        pre.classList.replace('itxgo-collapsed', 'itxgo-expanded');
        pre.style.maxHeight = 'none';
        toggleBtn.textContent = '折叠';
        cornerBtn.style.opacity = 1; cornerBtn.style.pointerEvents = 'auto';
      } else {
        pre.classList.replace('itxgo-expanded', 'itxgo-collapsed');
        pre.style.maxHeight = pre._itxgoCollapsedHeight + 'px';
        toggleBtn.textContent = '展开';
        cornerBtn.style.opacity = 0; cornerBtn.style.pointerEvents = 'none';
      }
    };

    toggleBtn.onclick = (e) => { e.stopPropagation(); toggle(); };
    pre.onclick = (e) => { 
      if (pre.classList.contains('itxgo-collapsed') && !e.target.closest('.itxgo-code-tools')) toggle(true); 
    };
    cornerBtn.onclick = (e) => {
      e.stopPropagation();
      const preRect = pre.getBoundingClientRect();
      const offset = 170;
      window.scrollTo(0, Math.max(0, window.scrollY + preRect.top - offset));
      toggle(false);
    };
    pre.appendChild(cornerBtn);
  }
}

// ===== 性能关键:批量高度计算 =====

function applyCollapseHeights(pres) {
  const targets = Array.from(pres).filter(pre => {
    if (pre.classList.contains('itxgo-expanded')) return false;
    if (pre._itxgoCollapsedHeight) return false;
    return pre.querySelector('.itxgo-toggle');
  });
  if (targets.length === 0) return;

  // Batch Read & Write
  const metrics = targets.map(pre => {
    const code = pre.querySelector('code') || pre;
    const cs = getComputedStyle(code), ps = getComputedStyle(pre);
    const fs = parseFloat(cs.fontSize) || 14;
    const lh = parseFloat(cs.lineHeight); 
    const pt = parseFloat(ps.paddingTop) || 40;
    const pb = parseFloat(ps.paddingBottom) || 12;
    return { pre, height: Math.ceil(pt + lh * ITXGO_CODE_CONFIG.COLLAPSE_LINES + pb) };
  });

  metrics.forEach(({ pre, height }) => {
    pre._itxgoCollapsedHeight = height;
    pre.style.maxHeight = height + 'px';
    pre.classList.add('itxgo-collapsed');
  });
}

// ===== 初始化 =====

function initCodeBlocks() {
  loadPrism();

  const processObserverBlocks = async (blocks) => {
    if (!blocks.length) return;
    if (document.fonts) await document.fonts.ready; // 增加字体等待 防止计算抖动
    runInChunks(Array.from(blocks), processBlock);
  };

  if (document.readyState === 'loading') {
    document.addEventListener('DOMContentLoaded', () => processObserverBlocks(document.querySelectorAll(".article-content pre:not(.itxgo-initialized)")));
  } else {
    // 保持延迟 确保环境就绪
    setTimeout(() => processObserverBlocks(document.querySelectorAll(".article-content pre:not(.itxgo-initialized)")), 350);
  }

  const observer = new MutationObserver(mutations => {
    const newBlocks = [];
    mutations.forEach(m => m.addedNodes.forEach(n => {
      if (n.nodeType === 1) {
        if (n.matches && n.matches(".article-content pre:not(.itxgo-initialized)")) newBlocks.push(n);
        const found = n.querySelectorAll?.(".article-content pre:not(.itxgo-initialized)");
        if (found) newBlocks.push(...found);
      }
    }));
    if (newBlocks.length) runInChunks(newBlocks, processBlock);
  });
  observer.observe(document.body, { childList: true, subtree: true });

  let resizeTimer;
  window.addEventListener("resize", () => {
    clearTimeout(resizeTimer);
    resizeTimer = setTimeout(() => {
      applyCollapseHeights(document.querySelectorAll('.article-content pre.itxgo-collapsed'));
    }, ITXGO_CODE_CONFIG.RESIZE_DELAY);
  }, { passive: true });
}

6. ✅️代码块 JS 函数代码 - 终版语言判断简化版 - 2026年1月17日

// =============================
// 7. 代码块功能 - chat.z.ai
// =============================

const ITXGO_CODE_CONFIG = {
  COLLAPSE_LINES: 10,
  THRESHOLD: 10,
  COPY_DURATION: 1000,
  RESIZE_DELAY: 150,
  BASE_CDN: 'https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/',
  CHUNK_SIZE: 2
};

// 常量管理
const ICONS = {
  COPY: `<svg class="copy-icon" width="15" height="15" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg"><path fill="currentColor" d="M6.149 4.02c.963 0 1.73-.002 2.347.055.626.057 1.163.176 1.646.456.58.334 1.06.815 1.395 1.394.279.484.398 1.02.455 1.646.056.616.055 1.384.055 2.346 0 .963.002 1.73-.055 2.347-.057.626-.176 1.163-.456 1.646-.334.58-.815 1.06-1.394 1.395-.484.279-1.02.398-1.646.455-.616.056-1.384.055-2.347.055-.962 0-1.73.002-2.346-.055-.626-.057-1.163-.176-1.646-.456-.58-.334-1.06-.815-1.394-1.394-.28-.484-.4-1.02-.456-1.646-.056-.616-.056-1.384-.056-2.347 0-.962-.002-1.73.055-2.346.057-.626.177-1.163.456-1.646.335-.58.816-1.06 1.395-1.394.484-.28 1.02-.4 1.646-.456.616-.056 1.384-.056 2.347-.056Zm0 1.358c-.987 0-1.683.002-2.224.049-.53.048-.846.139-1.089.279-.373.215-.682.525-.898.897-.14.243-.231.559-.279 1.09-.049.54-.049 1.236-.049 2.224 0 .987-.002 1.683.049 2.224.048.53.139.846.279 1.089.215.372.525.682.897.897.243.14.559.231 1.09.279.54.049 1.236.049 2.224.049.987 0 1.683-.002 2.224-.049.53-.048.846-.139 1.089-.279.372-.215.682-.525.897-.897.14-.243.231-.559.279-1.09.049-.54.049-1.236.049-2.224 0-.987.002-1.683-.049-2.224-.048-.53-.139-.846-.279-1.089-.215-.373-.525-.682-.897-.897-.243-.14-.559-.231-1.09-.279-.54-.049-1.236-.049-2.224-.049Zm3.652-5.01c.963 0 1.73-.002 2.346.056.625.057 1.162.175 1.646.455.578.334 1.059.815 1.393 1.394.28.484.4 1.02.456 1.646.056.616.055 1.384.055 2.346v1.566c0 .462.002.76-.032 1.018-.199 1.504-1.265 2.725-2.682 3.15V11c.714-.356 1.227-1.05 1.336-1.875.019-.148.021-.336.021-.842V6.264c0-.987-.002-1.683-.049-2.224-.048-.53-.139-.846-.279-1.089-.215-.372-.525-.682-.897-.897-.243-.14-.559-.231-1.09-.279-.54-.049-1.236-.049-2.224-.049H7.715c-.959.002-1.788.553-2.192 1.355H4.07c.472-1.568 1.923-2.71 3.645-2.711h2.087Z"/></svg>`,
  COLLAPSE: `<svg viewBox="0 0 1024 1024" xmlns="http://www.w3.org/2000/svg" width="18" height="18" fill="currentColor"><g stroke="currentColor" stroke-width="20" stroke-linecap="round" stroke-linejoin="round"><path d="M125.3 176.1h742.4c15.8 0 28.7-10.6 28.7-23.6s-12.9-23.6-28.7-23.6H125.3c-15.8 0-28.7 10.6-28.7 23.6 0 13 12.9 23.6 28.7 23.6z"/><path d="M492.5 385.2H125.3c-15.4 0-28.1 10.6-28.1 23.6 0 12.9 12.7 23.6 28.1 23.6h367.2c15.4 0 28.1-10.7 28.1-23.6 0-12.9-12.7-23.6-28.1-23.6z"/><path d="M492.5 594.3H125.3c-15.4 0-28.1 10.6-28.1 23.6 0 13.1 12.7 23.6 28.1 23.6h367.2c15.4 0 28.1-10.7 28.1-23.6 0-13.1-12.7-23.6-28.1-23.6z"/><path d="M492.1 803.4H126c-15.8 0-28.7 10.6-28.7 23.6 0 13.1 12.7 23.6 28.7 23.6h366.2c15.8 0 28.7-10.7 28.7-23.6 0-13.1-12.9-23.6-28.7-23.6z"/><path d="M926.31 502.17c1.02-2.25-0.2-9.22-7.78-18.64L819.2 359.42c-8.19-10.24-18.64-15.77-29.49-15.77-10.85 0-21.5 5.53-29.49 15.77L661.09 483.33c-7.78 9.63-9.01 16.59-7.99 18.64 1.43 2.66 8.19 6.35 22.53 6.35h90.52v306.38c0 15.36 10.44 28.06 23.55 28.06s23.55-12.7 23.55-28.06V508.31h90.52c14.34 0 21.5-3.69 22.53-6.14z"/></g></svg>`
};

let prismLoaded = false, prismLoading = false;
const loadedLanguages = new Set(['markup', 'css', 'clike', 'javascript']);
const LANG_MAP = { js: 'javascript', ts: 'typescript', py: 'python', rb: 'ruby', cs: 'csharp', sh: 'bash', md: 'markdown', yaml: 'yaml' };

// ===== 异步加载 =====

function loadScript(src) {
  return new Promise((resolve, reject) => {
    const s = document.createElement('script');
    s.src = src; s.onload = resolve; s.onerror = reject;
    document.head.appendChild(s);
  });
}

async function loadPrism() {
  if (prismLoaded) return true;
  if (prismLoading) return new Promise(r => setTimeout(r, 50)); // 异步等待 不阻塞
  prismLoading = true;
  try {
    await loadScript(ITXGO_CODE_CONFIG.BASE_CDN + 'prism.min.js');
    prismLoaded = true;
    if (window.Prism) Prism.manual = true;
  } catch (e) { console.warn('Prism load failed'); }
  finally { prismLoading = false; }
  return prismLoaded;
}

async function loadLangComp(lang) {
  if (lang === 'html' || lang === 'markup') {
    if (loadedLanguages.has('markup')) return true;
    loadedLanguages.add('markup');
    return true;
  }
  if (!lang || loadedLanguages.has(lang)) return true;
  
  const key = LANG_MAP[lang] || lang;
  if (!key) return true;
  if (key === 'markup') {
    loadedLanguages.add('markup');
    return true;
  }

  return new Promise(resolve => {
    const s = document.createElement('script');
    s.src = `${ITXGO_CODE_CONFIG.BASE_CDN}components/prism-${key}.min.js`;
    s.onload = () => { 
      loadedLanguages.add(lang); 
      resolve(true); 
    };
    s.onerror = () => { 
      resolve(false); 
    };
    document.head.appendChild(s);
  });
}

async function runInChunks(items, processFn) {
  const { CHUNK_SIZE } = ITXGO_CODE_CONFIG;
  for (let i = 0; i < items.length; i += CHUNK_SIZE) {
    const chunk = items.slice(i, i + CHUNK_SIZE);
    chunk.forEach(processFn);
    applyCollapseHeights(chunk);
    // 标记代码块准备就绪,触发淡入动画
    chunk.forEach(pre => {
      if (!pre.classList.contains('itxgo-ready')) {
        pre.classList.add('itxgo-ready');
      }
    });
    if (i + CHUNK_SIZE < items.length) await new Promise(r => requestAnimationFrame(r));
  }
}

// ===== 代码语言判断核心逻辑 =====

function getLanguage(el) {
  // 第 1 层:上帝视角
  const findClass = (e) => {
    if (!e) return null;
    const match = e.className && e.className.match(/(?:^|\s)language-(\w+)(?:\s|$)/);
    return match ? match[1] : null;
  };
  
  const lang = findClass(el) || findClass(el.closest('pre'));
  if (lang) return lang;

  const text = (el.textContent || '').trim();
  const sample = text.slice(0, 300);

  // 第 2 层:硬核结构解析

  // 1. JSON
  try {
    if (/^[\[{]/.test(text) && /[\]}]$/.test(text)) {
      JSON.parse(text);
      return 'json';
    }
  } catch (e) {}

  // 2. HTML
  if (/<([a-zA-Z][a-zA-Z0-9]*)[^>]*>.*<\/\1>|<!DOCTYPE|<xml/i.test(sample)) {
    return 'markup';
  }

  // 第 3 层:JS/TS
  if (
    /=>|const\s+\w+\s*=|let\s+\w+\s*=|var\s+\w+\s*=/.test(sample) ||
    /function\s+\(|async\s+function|console\.log\|document\.|window\./i.test(sample) ||
    /import\s+.*from\s+|export\s+|interface\s+\w+/.test(sample)
  ) {
    return 'javascript'; 
  }

  // 4. SQL
  if (/\b(SELECT|UPDATE|INSERT|CREATE|ALTER|DELETE)\b.*\b(FROM|INTO|TABLE|SET)\b/i.test(sample)) {
    return 'sql';
  }

  // 5. PHP
  if (/<\?php|<\?(?!xml)|\$[a-zA-Z_]\w+\s*=/i.test(sample)) {
    return 'php';
  }

  // 6. C / C++
  if (/#include\s*<[^>]+>|#define\s+\w+/i.test(sample)) {
    return 'cpp';
  }

  // 7. Java
  if (/\b(System\.out\.println|package\s+\w+|public\s+static\s+void\s+main)\b/i.test(sample)) {
    return 'java';
  }

  // 8. Python
  if (/def\s+\w+\s*\(|import\s+\w+|print\s*\(/i.test(sample) && !/{/.test(sample.slice(0, 500))) {
    return 'python';
  }

  // 第 4 层:CSS
  const hasSelector = /(\.[\w-]+\s*\{|#[\w-]+\s*\{|:\w+\s*\{|@\w+[^\{]*\{)/i;
  const hasCssStyle = /(px|em|rem|%|vh|deg|s|ms)\s*;|!important|url\s*\(|rgba?\s*\(|var\s*\(|calc\s*\(:root/i;
  if (hasSelector.test(sample) && hasCssStyle.test(sample)) {
    return 'css';
  }

  // 第 5 层:兜底
  if (/\b(fn\s+|use\s+std\s*::)\b/i.test(sample)) return 'rust';
  if (/\b(package\s+main|func\s+\(|import\s*\()\b/i.test(sample)) return 'go';
  if (/(^#|^!\/bin\/bash|\-eq|\-ne|echo\s+\$\w+)/m.test(sample)) return 'bash';

  return 'plaintext';
}

async function applyHighlight(el, lang) {
  if (!window.Prism || !lang) return;
  await loadLangComp(lang);
  el.classList.add(`language-${lang}`);
  Prism.highlightElement(el); // 同步执行 在 processBlock 中未 await 故不阻塞主线程
}

// ===== UI 与 交互 =====

function processBlock(pre) {
  if (pre.classList.contains('itxgo-initialized')) return;
  pre.classList.add('itxgo-initialized', 'itxgo-code-block');
  const codeEl = pre.querySelector('code') || pre;
  const raw = codeEl.textContent.replace(/^\n+|\n+$/g, '').replace(/\r\n/g, '\n');
  const lang = getLanguage(codeEl);
  const shouldCollapse = raw.split('\n').length > ITXGO_CODE_CONFIG.THRESHOLD;

  // 不使用 await 允许高亮在后台异步进行 避免长任务
  if (prismLoaded) applyHighlight(codeEl, lang);
  else loadPrism().then(() => applyHighlight(codeEl, lang));

  buildUI(pre, lang, shouldCollapse, raw);
}

function buildUI(pre, lang, shouldCollapse, raw) {
  const tools = document.createElement('div');
  tools.className = 'itxgo-code-tools';
  tools.innerHTML = `
    <div class="itxgo-code-header">
      <span class="itxgo-code-label">${lang.toUpperCase()}</span>
      <div class="itxgo-code-actions">
        ${shouldCollapse ? '<button class="itxgo-code-btn itxgo-toggle" type="button">展开</button>' : ''}
        <button class="itxgo-code-btn itxgo-copy" type="button">
          ${ICONS.COPY}<span class="copy-text">复制</span>
        </button>
      </div>
    </div>`;
  pre.insertBefore(tools, pre.firstChild);

  const copyBtn = tools.querySelector('.itxgo-copy');
  copyBtn.onclick = async (e) => {
    e.stopPropagation();
    let ok = false;
    try { await navigator.clipboard.writeText(raw); ok = true; } 
    catch { 
      const t = document.createElement('textarea'); 
      t.value = raw; t.style.cssText = "position:fixed;left:-9999px"; 
      document.body.appendChild(t); t.select(); 
      ok = document.execCommand('copy'); 
      document.body.removeChild(t); 
    }
    const icon = copyBtn.querySelector('.copy-icon'), txt = copyBtn.querySelector('.copy-text');
    const oldH = icon.innerHTML, oldT = txt.textContent;
    icon.innerHTML = '<path d="M3 8.5L6 11.5L12 5.5" stroke="currentColor" stroke-width="2" stroke-linecap="round"/>';
    txt.textContent = ok ? '复制' : '失败';
    setTimeout(() => { icon.innerHTML = oldH; txt.textContent = oldT; }, ITXGO_CODE_CONFIG.COPY_DURATION);
  };

  if (shouldCollapse) {
    const toggleBtn = tools.querySelector('.itxgo-toggle');
    const cornerBtn = document.createElement('button');
    cornerBtn.className = 'itxgo-collapse-corner-btn';
    cornerBtn.title = "折叠"; 
    cornerBtn.setAttribute('aria-label', '折叠');
    cornerBtn.innerHTML = ICONS.COLLAPSE;
    Object.assign(cornerBtn.style, { opacity: 0, pointerEvents: 'none', transition: 'opacity 0.2s' });
    
    const toggle = (forceState) => {
      const isCollapsed = pre.classList.contains('itxgo-collapsed');
      const shouldExpand = forceState !== undefined ? forceState : isCollapsed;
      if (shouldExpand) {
        pre.classList.replace('itxgo-collapsed', 'itxgo-expanded');
        pre.style.maxHeight = 'none';
        toggleBtn.textContent = '折叠';
        cornerBtn.style.opacity = 1; cornerBtn.style.pointerEvents = 'auto';
      } else {
        pre.classList.replace('itxgo-expanded', 'itxgo-collapsed');
        pre.style.maxHeight = pre._itxgoCollapsedHeight + 'px';
        toggleBtn.textContent = '展开';
        cornerBtn.style.opacity = 0; cornerBtn.style.pointerEvents = 'none';
      }
    };

    toggleBtn.onclick = (e) => { e.stopPropagation(); toggle(); };
    pre.onclick = (e) => { 
      if (pre.classList.contains('itxgo-collapsed') && !e.target.closest('.itxgo-code-tools')) toggle(true); 
    };
    cornerBtn.onclick = (e) => {
      e.stopPropagation();
      const preRect = pre.getBoundingClientRect();
      const offset = 170;
      window.scrollTo(0, Math.max(0, window.scrollY + preRect.top - offset));
      toggle(false);
    };
    pre.appendChild(cornerBtn);
  }
}

// ===== 性能关键:批量高度计算 =====

function applyCollapseHeights(pres) {
  const targets = Array.from(pres).filter(pre => {
    if (pre.classList.contains('itxgo-expanded')) return false;
    if (pre._itxgoCollapsedHeight) return false;
    return pre.querySelector('.itxgo-toggle');
  });
  if (targets.length === 0) return;

  // Batch Read & Write
  const metrics = targets.map(pre => {
    const code = pre.querySelector('code') || pre;
    const cs = getComputedStyle(code), ps = getComputedStyle(pre);
    const fs = parseFloat(cs.fontSize) || 14;
    const lh = parseFloat(cs.lineHeight); 
    const pt = parseFloat(ps.paddingTop) || 40;
    const pb = parseFloat(ps.paddingBottom) || 12;
    return { pre, height: Math.ceil(pt + lh * ITXGO_CODE_CONFIG.COLLAPSE_LINES + pb) };
  });

  metrics.forEach(({ pre, height }) => {
    pre._itxgoCollapsedHeight = height;
    pre.style.maxHeight = height + 'px';
    pre.classList.add('itxgo-collapsed');
  });
}

// ===== 初始化 =====

function initCodeBlocks() {
  loadPrism();

  const processObserverBlocks = async (blocks) => {
    if (!blocks.length) return;
    if (document.fonts) await document.fonts.ready; // 增加字体等待 防止计算抖动
    runInChunks(Array.from(blocks), processBlock);
  };

  if (document.readyState === 'loading') {
    document.addEventListener('DOMContentLoaded', () => processObserverBlocks(document.querySelectorAll(".article-content pre:not(.itxgo-initialized)")));
  } else {
    // 保持延迟 确保环境就绪
    setTimeout(() => processObserverBlocks(document.querySelectorAll(".article-content pre:not(.itxgo-initialized)")), 350);
  }

  const observer = new MutationObserver(mutations => {
    const newBlocks = [];
    mutations.forEach(m => m.addedNodes.forEach(n => {
      if (n.nodeType === 1) {
        if (n.matches && n.matches(".article-content pre:not(.itxgo-initialized)")) newBlocks.push(n);
        const found = n.querySelectorAll?.(".article-content pre:not(.itxgo-initialized)");
        if (found) newBlocks.push(...found);
      }
    }));
    if (newBlocks.length) runInChunks(newBlocks, processBlock);
  });
  observer.observe(document.body, { childList: true, subtree: true });

  let resizeTimer;
  window.addEventListener("resize", () => {
    clearTimeout(resizeTimer);
    resizeTimer = setTimeout(() => {
      applyCollapseHeights(document.querySelectorAll('.article-content pre.itxgo-collapsed'));
    }, ITXGO_CODE_CONFIG.RESIZE_DELAY);
  }, { passive: true });
}

6-1. ✅️代码块 JS 函数代码 - 终版语言判断简化版 - 2026年1月17日

// =============================
// 7. 代码块功能 - claude.ai
// =============================

const ITXGO_CODE_CONFIG = {
  COLLAPSE_LINES: 10,
  THRESHOLD: 10,
  COPY_DURATION: 1000,
  RESIZE_DELAY: 150,
  BASE_CDN: 'https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/',
  CHUNK_SIZE: 2
};

// 常量管理
const ICONS = {
  COPY: `<svg class="copy-icon" width="15" height="15" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg"><path fill="currentColor" d="M6.149 4.02c.963 0 1.73-.002 2.347.055.626.057 1.163.176 1.646.456.58.334 1.06.815 1.395 1.394.279.484.398 1.02.455 1.646.056.616.055 1.384.055 2.346 0 .963.002 1.73-.055 2.347-.057.626-.176 1.163-.456 1.646-.334.58-.815 1.06-1.394 1.395-.484.279-1.02.398-1.646.455-.616.056-1.384.055-2.347.055-.962 0-1.73.002-2.346-.055-.626-.057-1.163-.176-1.646-.456-.58-.334-1.06-.815-1.394-1.394-.28-.484-.4-1.02-.456-1.646-.056-.616-.056-1.384-.056-2.347 0-.962-.002-1.73.055-2.346.057-.626.177-1.163.456-1.646.335-.58.816-1.06 1.395-1.394.484-.28 1.02-.4 1.646-.456.616-.056 1.384-.056 2.347-.056Zm0 1.358c-.987 0-1.683.002-2.224.049-.53.048-.846.139-1.089.279-.373.215-.682.525-.898.897-.14.243-.231.559-.279 1.09-.049.54-.049 1.236-.049 2.224 0 .987-.002 1.683.049 2.224.048.53.139.846.279 1.089.215.372.525.682.897.897.243.14.559.231 1.09.279.54.049 1.236.049 2.224.049.987 0 1.683-.002 2.224-.049.53-.048.846-.139 1.089-.279.372-.215.682-.525.897-.897.14-.243.231-.559.279-1.09.049-.54.049-1.236.049-2.224 0-.987.002-1.683-.049-2.224-.048-.53-.139-.846-.279-1.089-.215-.373-.525-.682-.897-.897-.243-.14-.559-.231-1.09-.279-.54-.049-1.236-.049-2.224-.049Zm3.652-5.01c.963 0 1.73-.002 2.346.056.625.057 1.162.175 1.646.455.578.334 1.059.815 1.393 1.394.28.484.4 1.02.456 1.646.056.616.055 1.384.055 2.346v1.566c0 .462.002.76-.032 1.018-.199 1.504-1.265 2.725-2.682 3.15V11c.714-.356 1.227-1.05 1.336-1.875.019-.148.021-.336.021-.842V6.264c0-.987-.002-1.683-.049-2.224-.048-.53-.139-.846-.279-1.089-.215-.372-.525-.682-.897-.897-.243-.14-.559-.231-1.09-.279-.54-.049-1.236-.049-2.224-.049H7.715c-.959.002-1.788.553-2.192 1.355H4.07c.472-1.568 1.923-2.71 3.645-2.711h2.087Z"/></svg>`,
  COLLAPSE: `<svg viewBox="0 0 1024 1024" xmlns="http://www.w3.org/2000/svg" width="18" height="18" fill="currentColor"><g stroke="currentColor" stroke-width="20" stroke-linecap="round" stroke-linejoin="round"><path d="M125.3 176.1h742.4c15.8 0 28.7-10.6 28.7-23.6s-12.9-23.6-28.7-23.6H125.3c-15.8 0-28.7 10.6-28.7 23.6 0 13 12.9 23.6 28.7 23.6z"/><path d="M492.5 385.2H125.3c-15.4 0-28.1 10.6-28.1 23.6 0 12.9 12.7 23.6 28.1 23.6h367.2c15.4 0 28.1-10.7 28.1-23.6 0-12.9-12.7-23.6-28.1-23.6z"/><path d="M492.5 594.3H125.3c-15.4 0-28.1 10.6-28.1 23.6 0 13.1 12.7 23.6 28.1 23.6h367.2c15.4 0 28.1-10.7 28.1-23.6 0-13.1-12.7-23.6-28.1-23.6z"/><path d="M492.1 803.4H126c-15.8 0-28.7 10.6-28.7 23.6 0 13.1 12.7 23.6 28.7 23.6h366.2c15.8 0 28.7-10.7 28.7-23.6 0-13.1-12.9-23.6-28.7-23.6z"/><path d="M926.31 502.17c1.02-2.25-0.2-9.22-7.78-18.64L819.2 359.42c-8.19-10.24-18.64-15.77-29.49-15.77-10.85 0-21.5 5.53-29.49 15.77L661.09 483.33c-7.78 9.63-9.01 16.59-7.99 18.64 1.43 2.66 8.19 6.35 22.53 6.35h90.52v306.38c0 15.36 10.44 28.06 23.55 28.06s23.55-12.7 23.55-28.06V508.31h90.52c14.34 0 21.5-3.69 22.53-6.14z"/></g></svg>`
};

let prismLoaded = false, prismLoading = false;
const loadedLanguages = new Set(['markup', 'css', 'clike', 'javascript']);
const LANG_MAP = { js: 'javascript', ts: 'typescript', py: 'python', rb: 'ruby', cs: 'csharp', sh: 'bash', md: 'markdown', yaml: 'yaml' };

// ===== 异步加载 =====

function loadScript(src) {
  return new Promise((resolve, reject) => {
    const s = document.createElement('script');
    s.src = src; s.onload = resolve; s.onerror = reject;
    document.head.appendChild(s);
  });
}

async function loadPrism() {
  if (prismLoaded) return true;
  if (prismLoading) return new Promise(r => setTimeout(r, 50)); // 异步等待 不阻塞
  prismLoading = true;
  try {
    await loadScript(ITXGO_CODE_CONFIG.BASE_CDN + 'prism.min.js');
    prismLoaded = true;
    if (window.Prism) Prism.manual = true;
  } catch (e) { console.warn('Prism load failed'); }
  finally { prismLoading = false; }
  return prismLoaded;
}

async function loadLangComp(lang) {
  if (lang === 'html' || lang === 'markup') {
    if (loadedLanguages.has('markup')) return true;
    loadedLanguages.add('markup');
    return true;
  }
  if (!lang || loadedLanguages.has(lang)) return true;
  
  const key = LANG_MAP[lang] || lang;
  if (!key) return true;
  if (key === 'markup') {
    loadedLanguages.add('markup');
    return true;
  }

  return new Promise(resolve => {
    const s = document.createElement('script');
    s.src = `${ITXGO_CODE_CONFIG.BASE_CDN}components/prism-${key}.min.js`;
    s.onload = () => { 
      loadedLanguages.add(lang); 
      resolve(true); 
    };
    s.onerror = () => { 
      resolve(false); 
    };
    document.head.appendChild(s);
  });
}

async function runInChunks(items, processFn) {
  const { CHUNK_SIZE } = ITXGO_CODE_CONFIG;
  for (let i = 0; i < items.length; i += CHUNK_SIZE) {
    const chunk = items.slice(i, i + CHUNK_SIZE);
    chunk.forEach(processFn);
    applyCollapseHeights(chunk);
    // 标记代码块准备就绪,触发淡入动画
    chunk.forEach(pre => {
      if (!pre.classList.contains('itxgo-ready')) {
        pre.classList.add('itxgo-ready');
      }
    });
    if (i + CHUNK_SIZE < items.length) await new Promise(r => requestAnimationFrame(r));
  }
}

// ===== 代码语言判断核心逻辑 =====

function getLanguage(el) {
  // 1. 优先级最高:显式标记
  const cls = el.className || el.closest('pre')?.className || '';
  const match = cls.match(/(?:^|\s)language-(\w+)/);
  if (match) return match[1];

  const text = (el.textContent || '').trim();
  const head = text.slice(0, 500); // 只检测前 500 字符

  // 2. 结构性语言
  if (/^[\[{][\s\S]*[\]}]$/.test(text)) {
    try { JSON.parse(text); return 'json'; } catch {}
  }

  // HTML/XML
  if (/<([a-z][\w-]*)[^>]*>[\s\S]*<\/\1>|<!DOCTYPE|<\?xml/i.test(head)) {
    return 'markup';
  }

  // 3. 编程语言特征
  // JavaScript/TypeScript
  if (
    /\bconst\s+\w+\s*=|let\s+\w+\s*=|var\s+\w+/.test(head) ||
    /\bfunction\s*\(|=>\s*[{(]|console\.(log|error)|export\s+(default|const)/.test(head) ||
    /import\s+.+from\s+['"]|interface\s+\w+\s*\{/.test(head)
  ) {
    return 'javascript';
  }

  // Python
  if (
    /\b(def|class)\s+\w+\s*[(:]|import\s+\w+|print\s*\(/.test(head) &&
    !/\bfunction\s*\(|=>\s*/.test(head)
  ) {
    return 'python';
  }

  // SQL
  if (/\b(SELECT|INSERT|UPDATE|DELETE|CREATE)\s+.+\b(FROM|INTO|TABLE|SET)\b/i.test(head)) {
    return 'sql';
  }

  // PHP
  if (/<\?php|<\?=|\$\w+\s*=/.test(head)) return 'php';

  // C/C++
  if (/#include\s*<|#define\s+\w+|int\s+main\s*\(/.test(head)) return 'cpp';

  // Java
  if (/\b(public\s+class|System\.out|package\s+[\w.]+)/.test(head)) return 'java';

  // 4. CSS
  if (
    /[.#][\w-]+\s*\{|@\w+[^{]*\{|:\w+\s*\{/.test(head) &&
    /(px|em|rem|%|vh|vw|deg|ms|s)\s*;|:\s*#[\da-f]{3,8}|rgba?\(|url\(/.test(head)
  ) {
    return 'css';
  }

  // 5. 其他语言
  if (/\bfn\s+\w+|use\s+std::/.test(head)) return 'rust';
  if (/\bpackage\s+main|func\s+\w+\s*\(/.test(head)) return 'go';
  if (/^#!/m.test(head) || /\becho\s+\$|\[\s*-[a-z]\s/.test(head)) return 'bash';

  return 'plaintext';
}

async function applyHighlight(el, lang) {
  if (!window.Prism || !lang) return;
  await loadLangComp(lang);
  el.classList.add(`language-${lang}`);
  Prism.highlightElement(el); // 同步执行 在 processBlock 中未 await 故不阻塞主线程
}

// ===== UI 与 交互 =====

function processBlock(pre) {
  if (pre.classList.contains('itxgo-initialized')) return;
  pre.classList.add('itxgo-initialized', 'itxgo-code-block');
  const codeEl = pre.querySelector('code') || pre;
  const raw = codeEl.textContent.replace(/^\n+|\n+$/g, '').replace(/\r\n/g, '\n');
  const lang = getLanguage(codeEl);
  const shouldCollapse = raw.split('\n').length > ITXGO_CODE_CONFIG.THRESHOLD;

  // 不使用 await 允许高亮在后台异步进行 避免长任务
  if (prismLoaded) applyHighlight(codeEl, lang);
  else loadPrism().then(() => applyHighlight(codeEl, lang));

  buildUI(pre, lang, shouldCollapse, raw);
}

function buildUI(pre, lang, shouldCollapse, raw) {
  const tools = document.createElement('div');
  tools.className = 'itxgo-code-tools';
  tools.innerHTML = `
    <div class="itxgo-code-header">
      <span class="itxgo-code-label">${lang.toUpperCase()}</span>
      <div class="itxgo-code-actions">
        ${shouldCollapse ? '<button class="itxgo-code-btn itxgo-toggle" type="button">展开</button>' : ''}
        <button class="itxgo-code-btn itxgo-copy" type="button">
          ${ICONS.COPY}<span class="copy-text">复制</span>
        </button>
      </div>
    </div>`;
  pre.insertBefore(tools, pre.firstChild);

  const copyBtn = tools.querySelector('.itxgo-copy');
  copyBtn.onclick = async (e) => {
    e.stopPropagation();
    let ok = false;
    try { await navigator.clipboard.writeText(raw); ok = true; } 
    catch { 
      const t = document.createElement('textarea'); 
      t.value = raw; t.style.cssText = "position:fixed;left:-9999px"; 
      document.body.appendChild(t); t.select(); 
      ok = document.execCommand('copy'); 
      document.body.removeChild(t); 
    }
    const icon = copyBtn.querySelector('.copy-icon'), txt = copyBtn.querySelector('.copy-text');
    const oldH = icon.innerHTML, oldT = txt.textContent;
    icon.innerHTML = '<path d="M3 8.5L6 11.5L12 5.5" stroke="currentColor" stroke-width="2" stroke-linecap="round"/>';
    txt.textContent = ok ? '复制' : '失败';
    setTimeout(() => { icon.innerHTML = oldH; txt.textContent = oldT; }, ITXGO_CODE_CONFIG.COPY_DURATION);
  };

  if (shouldCollapse) {
    const toggleBtn = tools.querySelector('.itxgo-toggle');
    const cornerBtn = document.createElement('button');
    cornerBtn.className = 'itxgo-collapse-corner-btn';
    cornerBtn.title = "折叠"; 
    cornerBtn.setAttribute('aria-label', '折叠');
    cornerBtn.innerHTML = ICONS.COLLAPSE;
    Object.assign(cornerBtn.style, { opacity: 0, pointerEvents: 'none', transition: 'opacity 0.2s' });
    
    const toggle = (forceState) => {
      const isCollapsed = pre.classList.contains('itxgo-collapsed');
      const shouldExpand = forceState !== undefined ? forceState : isCollapsed;
      if (shouldExpand) {
        pre.classList.replace('itxgo-collapsed', 'itxgo-expanded');
        pre.style.maxHeight = 'none';
        toggleBtn.textContent = '折叠';
        cornerBtn.style.opacity = 1; cornerBtn.style.pointerEvents = 'auto';
      } else {
        pre.classList.replace('itxgo-expanded', 'itxgo-collapsed');
        pre.style.maxHeight = pre._itxgoCollapsedHeight + 'px';
        toggleBtn.textContent = '展开';
        cornerBtn.style.opacity = 0; cornerBtn.style.pointerEvents = 'none';
      }
    };

    toggleBtn.onclick = (e) => { e.stopPropagation(); toggle(); };
    pre.onclick = (e) => { 
      if (pre.classList.contains('itxgo-collapsed') && !e.target.closest('.itxgo-code-tools')) toggle(true); 
    };
    cornerBtn.onclick = (e) => {
      e.stopPropagation();
      const preRect = pre.getBoundingClientRect();
      const offset = 170;
      window.scrollTo(0, Math.max(0, window.scrollY + preRect.top - offset));
      toggle(false);
    };
    pre.appendChild(cornerBtn);
  }
}

// ===== 性能关键:批量高度计算 =====

function applyCollapseHeights(pres) {
  const targets = Array.from(pres).filter(pre => {
    if (pre.classList.contains('itxgo-expanded')) return false;
    if (pre._itxgoCollapsedHeight) return false;
    return pre.querySelector('.itxgo-toggle');
  });
  if (targets.length === 0) return;

  // Batch Read & Write
  const metrics = targets.map(pre => {
    const code = pre.querySelector('code') || pre;
    const cs = getComputedStyle(code), ps = getComputedStyle(pre);
    const fs = parseFloat(cs.fontSize) || 14;
    const lh = parseFloat(cs.lineHeight); 
    const pt = parseFloat(ps.paddingTop) || 40;
    const pb = parseFloat(ps.paddingBottom) || 12;
    return { pre, height: Math.ceil(pt + lh * ITXGO_CODE_CONFIG.COLLAPSE_LINES + pb) };
  });

  metrics.forEach(({ pre, height }) => {
    pre._itxgoCollapsedHeight = height;
    pre.style.maxHeight = height + 'px';
    pre.classList.add('itxgo-collapsed');
  });
}

// ===== 初始化 =====

function initCodeBlocks() {
  loadPrism();

  const processObserverBlocks = async (blocks) => {
    if (!blocks.length) return;
    if (document.fonts) await document.fonts.ready; // 增加字体等待 防止计算抖动
    runInChunks(Array.from(blocks), processBlock);
  };

  if (document.readyState === 'loading') {
    document.addEventListener('DOMContentLoaded', () => processObserverBlocks(document.querySelectorAll(".article-content pre:not(.itxgo-initialized)")));
  } else {
    // 保持延迟 确保环境就绪
    setTimeout(() => processObserverBlocks(document.querySelectorAll(".article-content pre:not(.itxgo-initialized)")), 350);
  }

  const observer = new MutationObserver(mutations => {
    const newBlocks = [];
    mutations.forEach(m => m.addedNodes.forEach(n => {
      if (n.nodeType === 1) {
        if (n.matches && n.matches(".article-content pre:not(.itxgo-initialized)")) newBlocks.push(n);
        const found = n.querySelectorAll?.(".article-content pre:not(.itxgo-initialized)");
        if (found) newBlocks.push(...found);
      }
    }));
    if (newBlocks.length) runInChunks(newBlocks, processBlock);
  });
  observer.observe(document.body, { childList: true, subtree: true });

  let resizeTimer;
  window.addEventListener("resize", () => {
    clearTimeout(resizeTimer);
    resizeTimer = setTimeout(() => {
      applyCollapseHeights(document.querySelectorAll('.article-content pre.itxgo-collapsed'));
    }, ITXGO_CODE_CONFIG.RESIZE_DELAY);
  }, { passive: true });
}