From 096cc1da942a00dec212720402228be3c6cb7068 Mon Sep 17 00:00:00 2001 From: landaiqing Date: Fri, 21 Nov 2025 23:35:42 +0800 Subject: [PATCH] :art: Optimize hyperlink extension --- frontend/src/assets/styles/index.css | 3 +- frontend/src/assets/styles/styles.css | 3 ++ .../editor/extensions/hyperlink/index.ts | 52 +++++-------------- 3 files changed, 18 insertions(+), 40 deletions(-) create mode 100644 frontend/src/assets/styles/styles.css diff --git a/frontend/src/assets/styles/index.css b/frontend/src/assets/styles/index.css index 7dc7327..d13ca2b 100644 --- a/frontend/src/assets/styles/index.css +++ b/frontend/src/assets/styles/index.css @@ -5,4 +5,5 @@ @import 'opensans_fonts.css'; @import "monocraft_fonts.css"; @import 'variables.css'; -@import 'scrollbar.css'; \ No newline at end of file +@import 'scrollbar.css'; +@import 'styles.css'; \ No newline at end of file diff --git a/frontend/src/assets/styles/styles.css b/frontend/src/assets/styles/styles.css new file mode 100644 index 0000000..398461f --- /dev/null +++ b/frontend/src/assets/styles/styles.css @@ -0,0 +1,3 @@ +body { + background-color: var(--bg-primary); +} \ No newline at end of file diff --git a/frontend/src/views/editor/extensions/hyperlink/index.ts b/frontend/src/views/editor/extensions/hyperlink/index.ts index 3d7fdba..2806888 100644 --- a/frontend/src/views/editor/extensions/hyperlink/index.ts +++ b/frontend/src/views/editor/extensions/hyperlink/index.ts @@ -9,9 +9,8 @@ import { } from '@codemirror/view'; import { Extension, Range } from '@codemirror/state'; import * as runtime from "@wailsio/runtime"; -import { getNoteBlockFromPos } from '../codeblock/state'; const pathStr = ``; -const defaultRegexp = /\b((?:https?|ftp):\/\/[^\s/$.?#].[^\s]*)\b/gi; +const defaultRegexp = /\b(([a-zA-Z][\w+\-.]*):\/\/[^\s/$.?#].[^\s]*)\b/gi; export interface HyperLinkState { at: number; @@ -54,18 +53,8 @@ function hyperLinkDecorations(view: EditorView, anchor?: HyperLinkExtensionOptio const from = match.index; const to = from + match[0].length; - // 检查当前位置是否在 HTTP 代码块中 - const block = getNoteBlockFromPos(view.state, from); - if (block && block.language.name === 'http') { - // 如果在 HTTP 代码块中,跳过超链接装饰 - continue; - } - const linkMark = Decoration.mark({ - class: 'cm-hyper-link-text', - attributes: { - 'data-url': match[0] - } + class: 'cm-hyper-link-text' }); widgets.push(linkMark.range(from, to)); @@ -91,14 +80,7 @@ const linkDecorator = ( ) => new MatchDecorator({ regexp: regexp || defaultRegexp, - decorate: (add, from, to, match, view) => { - // 检查当前位置是否在 HTTP 代码块中 - const block = getNoteBlockFromPos(view.state, from); - if (block && block.language.name === 'http') { - // 如果在 HTTP 代码块中,跳过超链接装饰 - return; - } - + decorate: (add, from, to, match, _view) => { const url = match[0]; let urlStr = matchFn && typeof matchFn === 'function' ? matchFn(url, match.input, from, to) : url; if (matchData && matchData[url]) { @@ -109,10 +91,7 @@ const linkDecorator = ( const linkIcon = new HyperLinkIcon({ at: start, url: urlStr, anchor }); add(from, to, Decoration.mark({ - class: 'cm-hyper-link-text cm-hyper-link-underline', - attributes: { - 'data-url': urlStr - } + class: 'cm-hyper-link-text cm-hyper-link-underline' })); add(start, end, Decoration.widget({ widget: linkIcon, side: 1 })); }, @@ -158,7 +137,7 @@ export function hyperLinkExtension({ regexp, match, handle, anchor, showIcon = t export const hyperLinkStyle = EditorView.baseTheme({ '.cm-hyper-link-text': { color: '#0969da', - cursor: 'pointer', + cursor: 'text', transition: 'color 0.2s ease', textDecoration: 'underline', textDecorationColor: '#0969da', @@ -216,24 +195,19 @@ export const hyperLinkStyle = EditorView.baseTheme({ }); export const hyperLinkClickHandler = EditorView.domEventHandlers({ - click: (event, view) => { - const target = event.target as HTMLElement; - let urlElement = target; - - while (urlElement && !urlElement.hasAttribute('data-url')) { - urlElement = urlElement.parentElement as HTMLElement; - if (!urlElement || urlElement === document.body) break; - } - - if (urlElement && urlElement.hasAttribute('data-url')) { - const url = urlElement.getAttribute('data-url'); + click: (event) => { + const target = event.target as HTMLElement | null; + const iconElement = target?.closest?.('.cm-hyper-link-icon') as (HTMLElement | null); + + if (iconElement && iconElement.hasAttribute('data-url')) { + const url = iconElement.getAttribute('data-url'); if (url) { runtime.Browser.OpenURL(url); event.preventDefault(); return true; } } - + return false; } }); @@ -242,4 +216,4 @@ export const hyperLink: Extension = [ hyperLinkExtension(), hyperLinkStyle, hyperLinkClickHandler -]; \ No newline at end of file +];