- Fix link resolution with proper relative/absolute path handling - Improve link styling with underline decoration - Hide leaf nodes from tree, only show directories - Fix log file path for packaged app
57 lines
2.8 KiB
Markdown
57 lines
2.8 KiB
Markdown
# 修复文档内链接跳转白屏问题计划
|
||
|
||
## 1. 问题分析
|
||
用户反馈“点击链接直接白屏了”。这是因为在 Markdown 文档内容中,部分相对链接(例如 `[Some Doc](SomeDoc.md)`)没有以 `./` 或 `../` 开头。
|
||
目前的 `DocContent.tsx` 组件在渲染 `<a>` 标签时,仅拦截了以 `./` 或 `../` 开头的链接。对于其他格式的本地链接,它会渲染为原生的 `<a href="SomeDoc.md">` 标签。
|
||
在 Electron 或单页应用(SPA)中,点击原生链接会触发浏览器的默认导航行为,试图跳转到该文件路径,从而导致 React 应用被卸载(变成白屏或显示 404/纯文本)。
|
||
|
||
以前用户可以通过左侧树直接点击叶子节点查看文档,但在我们隐藏了叶子节点后,用户必须依赖文档内的链接进行导航,导致这个原本就存在的链接跳转问题暴露了出来。
|
||
|
||
## 2. 修改方案
|
||
|
||
### 修改文件: `src/components/DocContent.tsx`
|
||
调整 Markdown 中 `<a>` 标签的渲染逻辑,拦截所有本地链接,阻止默认的页面跳转行为,并将其交给内部的 `onReferenceClick` 处理:
|
||
|
||
1. **识别内部链接**:
|
||
判断 `href` 是否存在,且**不以** `http://`、`https://`、`mailto:` 或 `#` 开头。满足此条件的都视为内部文档链接。
|
||
|
||
2. **阻止默认行为并触发内部跳转**:
|
||
对于内部链接,渲染为 `<a>` 标签,但在 `onClick` 事件中调用 `e.preventDefault()` 阻止白屏跳转,随后调用 `onReferenceClick(href)`。
|
||
|
||
```typescript
|
||
a: ({ href, children }) => {
|
||
// 判断是否是内部链接:非 http/https,非邮箱,非页内锚点
|
||
const isInternal = href && !href.startsWith('http') && !href.startsWith('mailto:') && !href.startsWith('#');
|
||
|
||
if (isInternal) {
|
||
return (
|
||
<a
|
||
href={href}
|
||
onClick={(e) => {
|
||
e.preventDefault();
|
||
onReferenceClick(href);
|
||
}}
|
||
className="text-blue-500 hover:text-blue-400 transition-colors cursor-pointer"
|
||
>
|
||
{children}
|
||
</a>
|
||
)
|
||
}
|
||
|
||
// 外部链接保留默认行为,但新窗口打开更安全
|
||
return (
|
||
<a
|
||
href={href}
|
||
target="_blank"
|
||
rel="noopener noreferrer"
|
||
className="text-blue-500 hover:text-blue-400 transition-colors"
|
||
>
|
||
{children}
|
||
</a>
|
||
)
|
||
},
|
||
```
|
||
|
||
## 3. 影响与验证
|
||
- **影响**:所有的内部 Markdown 链接现在都会通过 React 状态更新右侧内容,而不会触发导致白屏的浏览器原生导航。
|
||
- **验证**:保存修改后,点击文档内部的普通文件名链接(如 `SomeDoc.md`),页面将平滑切换到目标文档内容,不再出现白屏崩溃现象。 |