zen-gitsync 2.12.3 → 2.12.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (30) hide show
  1. package/LICENSE +190 -190
  2. package/package.json +17 -4
  3. package/scripts/README_COLOR_CONVERTER.md +196 -196
  4. package/scripts/README_FONTSIZE_CONVERTER.md +278 -278
  5. package/scripts/README_SPACING_CONVERTER.md +126 -126
  6. package/scripts/README_STYLE_VARS.md +180 -180
  7. package/src/ui/public/assets/EditorView-DDyMmxPI.js +0 -0
  8. package/src/ui/public/assets/EditorView-DK-Xgt7r.css +1 -0
  9. package/src/ui/public/assets/SourceMapView-DakscAmd.js +3 -0
  10. package/src/ui/public/assets/{css.worker-Wv5dxAWO.js → css.worker-CvXBzhp8.js} +1 -1
  11. package/src/ui/public/assets/{html.worker-CQP8QQsS.js → html.worker-BO6WuOEO.js} +1 -1
  12. package/src/ui/public/assets/index-CPUqt5Ue.js +73 -0
  13. package/src/ui/public/assets/index-a-r8YYZJ.css +1 -0
  14. package/src/ui/public/assets/{json.worker-DzV-CpCQ.js → json.worker-BkJRGcCJ.js} +1 -1
  15. package/src/ui/public/assets/{ts.worker-METxwbDZ.js → ts.worker-B0J26iPs.js} +31 -16
  16. package/src/ui/public/assets/{vendor-DITsiaGj.js → vendor-BMFU1ekz.js} +254 -234
  17. package/src/ui/public/assets/vendor-BPPhhD0O.css +1 -0
  18. package/src/ui/public/favicon.svg +75 -75
  19. package/src/ui/public/index.html +22 -22
  20. package/src/ui/public/logo.svg +74 -74
  21. package/src/ui/server/routes/config.js +46 -11
  22. package/src/ui/public/assets/EditorView-CbqSI9nw.css +0 -1
  23. package/src/ui/public/assets/EditorView-GS5cmh99.js +0 -21
  24. package/src/ui/public/assets/SourceMapView-_YRtzmZZ.js +0 -3
  25. package/src/ui/public/assets/index-ML5Y-5lO.css +0 -1
  26. package/src/ui/public/assets/index-yky0Sd13.js +0 -73
  27. package/src/ui/public/assets/vendor-q83wvJns.css +0 -1
  28. package/src/ui/server/.claude/codediff.txt +0 -6
  29. /package/src/ui/public/assets/{editor.worker-Bd9IXS8d.js → editor.worker-Cn2oRESe.js} +0 -0
  30. /package/src/ui/public/assets/{rolldown-runtime-BM3Ffeng.js → rolldown-runtime-CMxvf4Kt.js} +0 -0
@@ -1,75 +1,75 @@
1
- <svg width="200" height="200" viewBox="0 0 200 200" xmlns="http://www.w3.org/2000/svg">
2
- <defs>
3
- <radialGradient id="bgGrad" cx="38%" cy="32%" r="70%">
4
- <stop offset="0%" stop-color="#1e1b4b"/>
5
- <stop offset="100%" stop-color="#0d0b1e"/>
6
- </radialGradient>
7
- <linearGradient id="mainGrad" x1="0%" y1="0%" x2="0%" y2="100%">
8
- <stop offset="0%" stop-color="#c4b5fd"/>
9
- <stop offset="100%" stop-color="#7c3aed"/>
10
- </linearGradient>
11
- <linearGradient id="featGrad" x1="0%" y1="0%" x2="100%" y2="100%">
12
- <stop offset="0%" stop-color="#7dd3fc"/>
13
- <stop offset="100%" stop-color="#0284c7"/>
14
- </linearGradient>
15
- <filter id="glow" x="-40%" y="-40%" width="180%" height="180%">
16
- <feGaussianBlur in="SourceGraphic" stdDeviation="2.5" result="blur"/>
17
- <feMerge><feMergeNode in="blur"/><feMergeNode in="SourceGraphic"/></feMerge>
18
- </filter>
19
- <filter id="softGlow" x="-20%" y="-20%" width="140%" height="140%">
20
- <feGaussianBlur in="SourceGraphic" stdDeviation="1.5" result="blur"/>
21
- <feMerge><feMergeNode in="blur"/><feMergeNode in="SourceGraphic"/></feMerge>
22
- </filter>
23
- </defs>
24
-
25
- <!-- 背景圆 -->
26
- <circle cx="100" cy="100" r="96" fill="url(#bgGrad)"/>
27
-
28
- <!-- 同步外弧(上半,代表 sync 循环) -->
29
- <path d="M 100,20 A 80,80 0 1,1 36,153"
30
- stroke="rgba(167,139,250,0.18)" stroke-width="4.5" fill="none" stroke-linecap="round"/>
31
- <!-- 同步外弧(下半) -->
32
- <path d="M 36,153 A 80,80 0 0,1 164,153"
33
- stroke="rgba(56,189,248,0.18)" stroke-width="4.5" fill="none" stroke-linecap="round"/>
34
- <!-- 同步箭头(上) -->
35
- <path d="M 91,17 L 100,20 L 96,29"
36
- stroke="rgba(167,139,250,0.55)" stroke-width="2.5" fill="none"
37
- stroke-linecap="round" stroke-linejoin="round"/>
38
- <!-- 同步箭头(下) -->
39
- <path d="M 163,145 L 164,154 L 155,151"
40
- stroke="rgba(56,189,248,0.55)" stroke-width="2.5" fill="none"
41
- stroke-linecap="round" stroke-linejoin="round"/>
42
-
43
- <!-- 主分支竖线 -->
44
- <line x1="76" y1="44" x2="76" y2="156"
45
- stroke="url(#mainGrad)" stroke-width="5.5" stroke-linecap="round"
46
- filter="url(#softGlow)"/>
47
-
48
- <!-- 特性分支曲线(分出) -->
49
- <path d="M 76,80 C 98,80 130,96 130,120 L 130,140"
50
- stroke="url(#featGrad)" stroke-width="4.5" fill="none"
51
- stroke-linecap="round" filter="url(#softGlow)"/>
52
- <!-- 特性分支合并回主分支 -->
53
- <path d="M 130,140 C 130,156 105,159 76,155"
54
- stroke="url(#featGrad)" stroke-width="4.5" fill="none" stroke-linecap="round"/>
55
-
56
- <!-- 主分支节点 -->
57
- <circle cx="76" cy="48" r="11" fill="#13103a" stroke="#c4b5fd" stroke-width="3" filter="url(#glow)"/>
58
- <circle cx="76" cy="48" r="5" fill="#ddd6fe"/>
59
-
60
- <circle cx="76" cy="84" r="11" fill="#13103a" stroke="#a78bfa" stroke-width="3"/>
61
- <circle cx="76" cy="84" r="5" fill="#c4b5fd"/>
62
-
63
- <circle cx="76" cy="120" r="11" fill="#13103a" stroke="#8b5cf6" stroke-width="3"/>
64
- <circle cx="76" cy="120" r="5" fill="#a78bfa"/>
65
-
66
- <circle cx="76" cy="155" r="11" fill="#13103a" stroke="#7c3aed" stroke-width="3" filter="url(#glow)"/>
67
- <circle cx="76" cy="155" r="5" fill="#8b5cf6"/>
68
-
69
- <!-- 特性分支节点 -->
70
- <circle cx="130" cy="115" r="11" fill="#13103a" stroke="#38bdf8" stroke-width="3" filter="url(#glow)"/>
71
- <circle cx="130" cy="115" r="5" fill="#7dd3fc"/>
72
-
73
- <circle cx="130" cy="143" r="11" fill="#13103a" stroke="#0ea5e9" stroke-width="3" filter="url(#glow)"/>
74
- <circle cx="130" cy="143" r="5" fill="#38bdf8"/>
75
- </svg>
1
+ <svg width="200" height="200" viewBox="0 0 200 200" xmlns="http://www.w3.org/2000/svg">
2
+ <defs>
3
+ <radialGradient id="bgGrad" cx="38%" cy="32%" r="70%">
4
+ <stop offset="0%" stop-color="#1e1b4b"/>
5
+ <stop offset="100%" stop-color="#0d0b1e"/>
6
+ </radialGradient>
7
+ <linearGradient id="mainGrad" x1="0%" y1="0%" x2="0%" y2="100%">
8
+ <stop offset="0%" stop-color="#c4b5fd"/>
9
+ <stop offset="100%" stop-color="#7c3aed"/>
10
+ </linearGradient>
11
+ <linearGradient id="featGrad" x1="0%" y1="0%" x2="100%" y2="100%">
12
+ <stop offset="0%" stop-color="#7dd3fc"/>
13
+ <stop offset="100%" stop-color="#0284c7"/>
14
+ </linearGradient>
15
+ <filter id="glow" x="-40%" y="-40%" width="180%" height="180%">
16
+ <feGaussianBlur in="SourceGraphic" stdDeviation="2.5" result="blur"/>
17
+ <feMerge><feMergeNode in="blur"/><feMergeNode in="SourceGraphic"/></feMerge>
18
+ </filter>
19
+ <filter id="softGlow" x="-20%" y="-20%" width="140%" height="140%">
20
+ <feGaussianBlur in="SourceGraphic" stdDeviation="1.5" result="blur"/>
21
+ <feMerge><feMergeNode in="blur"/><feMergeNode in="SourceGraphic"/></feMerge>
22
+ </filter>
23
+ </defs>
24
+
25
+ <!-- 背景圆 -->
26
+ <circle cx="100" cy="100" r="96" fill="url(#bgGrad)"/>
27
+
28
+ <!-- 同步外弧(上半,代表 sync 循环) -->
29
+ <path d="M 100,20 A 80,80 0 1,1 36,153"
30
+ stroke="rgba(167,139,250,0.18)" stroke-width="4.5" fill="none" stroke-linecap="round"/>
31
+ <!-- 同步外弧(下半) -->
32
+ <path d="M 36,153 A 80,80 0 0,1 164,153"
33
+ stroke="rgba(56,189,248,0.18)" stroke-width="4.5" fill="none" stroke-linecap="round"/>
34
+ <!-- 同步箭头(上) -->
35
+ <path d="M 91,17 L 100,20 L 96,29"
36
+ stroke="rgba(167,139,250,0.55)" stroke-width="2.5" fill="none"
37
+ stroke-linecap="round" stroke-linejoin="round"/>
38
+ <!-- 同步箭头(下) -->
39
+ <path d="M 163,145 L 164,154 L 155,151"
40
+ stroke="rgba(56,189,248,0.55)" stroke-width="2.5" fill="none"
41
+ stroke-linecap="round" stroke-linejoin="round"/>
42
+
43
+ <!-- 主分支竖线 -->
44
+ <line x1="76" y1="44" x2="76" y2="156"
45
+ stroke="url(#mainGrad)" stroke-width="5.5" stroke-linecap="round"
46
+ filter="url(#softGlow)"/>
47
+
48
+ <!-- 特性分支曲线(分出) -->
49
+ <path d="M 76,80 C 98,80 130,96 130,120 L 130,140"
50
+ stroke="url(#featGrad)" stroke-width="4.5" fill="none"
51
+ stroke-linecap="round" filter="url(#softGlow)"/>
52
+ <!-- 特性分支合并回主分支 -->
53
+ <path d="M 130,140 C 130,156 105,159 76,155"
54
+ stroke="url(#featGrad)" stroke-width="4.5" fill="none" stroke-linecap="round"/>
55
+
56
+ <!-- 主分支节点 -->
57
+ <circle cx="76" cy="48" r="11" fill="#13103a" stroke="#c4b5fd" stroke-width="3" filter="url(#glow)"/>
58
+ <circle cx="76" cy="48" r="5" fill="#ddd6fe"/>
59
+
60
+ <circle cx="76" cy="84" r="11" fill="#13103a" stroke="#a78bfa" stroke-width="3"/>
61
+ <circle cx="76" cy="84" r="5" fill="#c4b5fd"/>
62
+
63
+ <circle cx="76" cy="120" r="11" fill="#13103a" stroke="#8b5cf6" stroke-width="3"/>
64
+ <circle cx="76" cy="120" r="5" fill="#a78bfa"/>
65
+
66
+ <circle cx="76" cy="155" r="11" fill="#13103a" stroke="#7c3aed" stroke-width="3" filter="url(#glow)"/>
67
+ <circle cx="76" cy="155" r="5" fill="#8b5cf6"/>
68
+
69
+ <!-- 特性分支节点 -->
70
+ <circle cx="130" cy="115" r="11" fill="#13103a" stroke="#38bdf8" stroke-width="3" filter="url(#glow)"/>
71
+ <circle cx="130" cy="115" r="5" fill="#7dd3fc"/>
72
+
73
+ <circle cx="130" cy="143" r="11" fill="#13103a" stroke="#0ea5e9" stroke-width="3" filter="url(#glow)"/>
74
+ <circle cx="130" cy="143" r="5" fill="#38bdf8"/>
75
+ </svg>
@@ -1,22 +1,22 @@
1
- <!doctype html>
2
- <html lang="zh-CN" translate="no">
3
- <head>
4
- <meta charset="UTF-8" />
5
- <meta name="google" content="notranslate" />
6
- <link rel="icon" type="image/svg+xml" href="/favicon.svg" />
7
- <meta name="viewport" content="width=device-width, initial-scale=1.0" />
8
- <title>Zen GitSync</title>
9
- <!-- Premium fonts: Plus Jakarta Sans (UI) + JetBrains Mono (code) -->
10
- <link rel="preconnect" href="https://fonts.googleapis.com" />
11
- <link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
12
- <link href="https://fonts.googleapis.com/css2?family=Plus+Jakarta+Sans:ital,wght@0,300;0,400;0,500;0,600;0,700;0,800;1,400&family=JetBrains+Mono:wght@400;500&display=swap" rel="stylesheet" />
13
- <script type="module" crossorigin src="/assets/index-yky0Sd13.js"></script>
14
- <link rel="modulepreload" crossorigin href="/assets/rolldown-runtime-BM3Ffeng.js">
15
- <link rel="modulepreload" crossorigin href="/assets/vendor-DITsiaGj.js">
16
- <link rel="stylesheet" crossorigin href="/assets/vendor-q83wvJns.css">
17
- <link rel="stylesheet" crossorigin href="/assets/index-ML5Y-5lO.css">
18
- </head>
19
- <body>
20
- <div id="app"></div>
21
- </body>
22
- </html>
1
+ <!doctype html>
2
+ <html lang="zh-CN" translate="no">
3
+ <head>
4
+ <meta charset="UTF-8" />
5
+ <meta name="google" content="notranslate" />
6
+ <link rel="icon" type="image/svg+xml" href="/favicon.svg" />
7
+ <meta name="viewport" content="width=device-width, initial-scale=1.0" />
8
+ <title>Zen GitSync</title>
9
+ <!-- Premium fonts: Plus Jakarta Sans (UI) + JetBrains Mono (code) -->
10
+ <link rel="preconnect" href="https://fonts.googleapis.com" />
11
+ <link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
12
+ <link href="https://fonts.googleapis.com/css2?family=Plus+Jakarta+Sans:ital,wght@0,300;0,400;0,500;0,600;0,700;0,800;1,400&family=JetBrains+Mono:wght@400;500&display=swap" rel="stylesheet" />
13
+ <script type="module" crossorigin src="/assets/index-CPUqt5Ue.js"></script>
14
+ <link rel="modulepreload" crossorigin href="/assets/rolldown-runtime-CMxvf4Kt.js">
15
+ <link rel="modulepreload" crossorigin href="/assets/vendor-BMFU1ekz.js">
16
+ <link rel="stylesheet" crossorigin href="/assets/vendor-BPPhhD0O.css">
17
+ <link rel="stylesheet" crossorigin href="/assets/index-a-r8YYZJ.css">
18
+ </head>
19
+ <body>
20
+ <div id="app"></div>
21
+ </body>
22
+ </html>
@@ -1,75 +1,75 @@
1
- <svg width="200" height="200" viewBox="0 0 200 200" xmlns="http://www.w3.org/2000/svg">
2
- <defs>
3
- <radialGradient id="bgGrad" cx="38%" cy="32%" r="70%">
4
- <stop offset="0%" stop-color="#1e1b4b"/>
5
- <stop offset="100%" stop-color="#0d0b1e"/>
6
- </radialGradient>
7
- <linearGradient id="mainGrad" x1="0%" y1="0%" x2="0%" y2="100%">
8
- <stop offset="0%" stop-color="#c4b5fd"/>
9
- <stop offset="100%" stop-color="#7c3aed"/>
10
- </linearGradient>
11
- <linearGradient id="featGrad" x1="0%" y1="0%" x2="100%" y2="100%">
12
- <stop offset="0%" stop-color="#7dd3fc"/>
13
- <stop offset="100%" stop-color="#0284c7"/>
14
- </linearGradient>
15
- <filter id="glow" x="-40%" y="-40%" width="180%" height="180%">
16
- <feGaussianBlur in="SourceGraphic" stdDeviation="2.5" result="blur"/>
17
- <feMerge><feMergeNode in="blur"/><feMergeNode in="SourceGraphic"/></feMerge>
18
- </filter>
19
- <filter id="softGlow" x="-20%" y="-20%" width="140%" height="140%">
20
- <feGaussianBlur in="SourceGraphic" stdDeviation="1.5" result="blur"/>
21
- <feMerge><feMergeNode in="blur"/><feMergeNode in="SourceGraphic"/></feMerge>
22
- </filter>
23
- </defs>
24
-
25
- <!-- 背景�?-->
26
- <circle cx="100" cy="100" r="96" fill="url(#bgGrad)"/>
27
-
28
- <!-- 同步外弧(上半,代表 sync 循环�?-->
29
- <path d="M 100,20 A 80,80 0 1,1 36,153"
30
- stroke="rgba(167,139,250,0.18)" stroke-width="4.5" fill="none" stroke-linecap="round"/>
31
- <!-- 同步外弧(下半) -->
32
- <path d="M 36,153 A 80,80 0 0,1 164,153"
33
- stroke="rgba(56,189,248,0.18)" stroke-width="4.5" fill="none" stroke-linecap="round"/>
34
- <!-- 同步箭头(上�?-->
35
- <path d="M 91,17 L 100,20 L 96,29"
36
- stroke="rgba(167,139,250,0.55)" stroke-width="2.5" fill="none"
37
- stroke-linecap="round" stroke-linejoin="round"/>
38
- <!-- 同步箭头(下�?-->
39
- <path d="M 163,145 L 164,154 L 155,151"
40
- stroke="rgba(56,189,248,0.55)" stroke-width="2.5" fill="none"
41
- stroke-linecap="round" stroke-linejoin="round"/>
42
-
43
- <!-- 主分支竖�?-->
44
- <line x1="76" y1="44" x2="76" y2="156"
45
- stroke="url(#mainGrad)" stroke-width="5.5" stroke-linecap="round"
46
- filter="url(#softGlow)"/>
47
-
48
- <!-- 特性分支曲线(分出�?-->
49
- <path d="M 76,80 C 98,80 130,96 130,120 L 130,140"
50
- stroke="url(#featGrad)" stroke-width="4.5" fill="none"
51
- stroke-linecap="round" filter="url(#softGlow)"/>
52
- <!-- 特性分支合并回主分�?-->
53
- <path d="M 130,140 C 130,156 105,159 76,155"
54
- stroke="url(#featGrad)" stroke-width="4.5" fill="none" stroke-linecap="round"/>
55
-
56
- <!-- 主分支节�?-->
57
- <circle cx="76" cy="48" r="11" fill="#13103a" stroke="#c4b5fd" stroke-width="3" filter="url(#glow)"/>
58
- <circle cx="76" cy="48" r="5" fill="#ddd6fe"/>
59
-
60
- <circle cx="76" cy="84" r="11" fill="#13103a" stroke="#a78bfa" stroke-width="3"/>
61
- <circle cx="76" cy="84" r="5" fill="#c4b5fd"/>
62
-
63
- <circle cx="76" cy="120" r="11" fill="#13103a" stroke="#8b5cf6" stroke-width="3"/>
64
- <circle cx="76" cy="120" r="5" fill="#a78bfa"/>
65
-
66
- <circle cx="76" cy="155" r="11" fill="#13103a" stroke="#7c3aed" stroke-width="3" filter="url(#glow)"/>
67
- <circle cx="76" cy="155" r="5" fill="#8b5cf6"/>
68
-
69
- <!-- 特性分支节�?-->
70
- <circle cx="130" cy="115" r="11" fill="#13103a" stroke="#38bdf8" stroke-width="3" filter="url(#glow)"/>
71
- <circle cx="130" cy="115" r="5" fill="#7dd3fc"/>
72
-
73
- <circle cx="130" cy="143" r="11" fill="#13103a" stroke="#0ea5e9" stroke-width="3" filter="url(#glow)"/>
74
- <circle cx="130" cy="143" r="5" fill="#38bdf8"/>
1
+ <svg width="200" height="200" viewBox="0 0 200 200" xmlns="http://www.w3.org/2000/svg">
2
+ <defs>
3
+ <radialGradient id="bgGrad" cx="38%" cy="32%" r="70%">
4
+ <stop offset="0%" stop-color="#1e1b4b"/>
5
+ <stop offset="100%" stop-color="#0d0b1e"/>
6
+ </radialGradient>
7
+ <linearGradient id="mainGrad" x1="0%" y1="0%" x2="0%" y2="100%">
8
+ <stop offset="0%" stop-color="#c4b5fd"/>
9
+ <stop offset="100%" stop-color="#7c3aed"/>
10
+ </linearGradient>
11
+ <linearGradient id="featGrad" x1="0%" y1="0%" x2="100%" y2="100%">
12
+ <stop offset="0%" stop-color="#7dd3fc"/>
13
+ <stop offset="100%" stop-color="#0284c7"/>
14
+ </linearGradient>
15
+ <filter id="glow" x="-40%" y="-40%" width="180%" height="180%">
16
+ <feGaussianBlur in="SourceGraphic" stdDeviation="2.5" result="blur"/>
17
+ <feMerge><feMergeNode in="blur"/><feMergeNode in="SourceGraphic"/></feMerge>
18
+ </filter>
19
+ <filter id="softGlow" x="-20%" y="-20%" width="140%" height="140%">
20
+ <feGaussianBlur in="SourceGraphic" stdDeviation="1.5" result="blur"/>
21
+ <feMerge><feMergeNode in="blur"/><feMergeNode in="SourceGraphic"/></feMerge>
22
+ </filter>
23
+ </defs>
24
+
25
+ <!-- 背景�?-->
26
+ <circle cx="100" cy="100" r="96" fill="url(#bgGrad)"/>
27
+
28
+ <!-- 同步外弧(上半,代表 sync 循环�?-->
29
+ <path d="M 100,20 A 80,80 0 1,1 36,153"
30
+ stroke="rgba(167,139,250,0.18)" stroke-width="4.5" fill="none" stroke-linecap="round"/>
31
+ <!-- 同步外弧(下半) -->
32
+ <path d="M 36,153 A 80,80 0 0,1 164,153"
33
+ stroke="rgba(56,189,248,0.18)" stroke-width="4.5" fill="none" stroke-linecap="round"/>
34
+ <!-- 同步箭头(上�?-->
35
+ <path d="M 91,17 L 100,20 L 96,29"
36
+ stroke="rgba(167,139,250,0.55)" stroke-width="2.5" fill="none"
37
+ stroke-linecap="round" stroke-linejoin="round"/>
38
+ <!-- 同步箭头(下�?-->
39
+ <path d="M 163,145 L 164,154 L 155,151"
40
+ stroke="rgba(56,189,248,0.55)" stroke-width="2.5" fill="none"
41
+ stroke-linecap="round" stroke-linejoin="round"/>
42
+
43
+ <!-- 主分支竖�?-->
44
+ <line x1="76" y1="44" x2="76" y2="156"
45
+ stroke="url(#mainGrad)" stroke-width="5.5" stroke-linecap="round"
46
+ filter="url(#softGlow)"/>
47
+
48
+ <!-- 特性分支曲线(分出�?-->
49
+ <path d="M 76,80 C 98,80 130,96 130,120 L 130,140"
50
+ stroke="url(#featGrad)" stroke-width="4.5" fill="none"
51
+ stroke-linecap="round" filter="url(#softGlow)"/>
52
+ <!-- 特性分支合并回主分�?-->
53
+ <path d="M 130,140 C 130,156 105,159 76,155"
54
+ stroke="url(#featGrad)" stroke-width="4.5" fill="none" stroke-linecap="round"/>
55
+
56
+ <!-- 主分支节�?-->
57
+ <circle cx="76" cy="48" r="11" fill="#13103a" stroke="#c4b5fd" stroke-width="3" filter="url(#glow)"/>
58
+ <circle cx="76" cy="48" r="5" fill="#ddd6fe"/>
59
+
60
+ <circle cx="76" cy="84" r="11" fill="#13103a" stroke="#a78bfa" stroke-width="3"/>
61
+ <circle cx="76" cy="84" r="5" fill="#c4b5fd"/>
62
+
63
+ <circle cx="76" cy="120" r="11" fill="#13103a" stroke="#8b5cf6" stroke-width="3"/>
64
+ <circle cx="76" cy="120" r="5" fill="#a78bfa"/>
65
+
66
+ <circle cx="76" cy="155" r="11" fill="#13103a" stroke="#7c3aed" stroke-width="3" filter="url(#glow)"/>
67
+ <circle cx="76" cy="155" r="5" fill="#8b5cf6"/>
68
+
69
+ <!-- 特性分支节�?-->
70
+ <circle cx="130" cy="115" r="11" fill="#13103a" stroke="#38bdf8" stroke-width="3" filter="url(#glow)"/>
71
+ <circle cx="130" cy="115" r="5" fill="#7dd3fc"/>
72
+
73
+ <circle cx="130" cy="143" r="11" fill="#13103a" stroke="#0ea5e9" stroke-width="3" filter="url(#glow)"/>
74
+ <circle cx="130" cy="143" r="5" fill="#38bdf8"/>
75
75
  </svg>
@@ -84,13 +84,19 @@ function parseDiffByFile(diffText) {
84
84
  // 关键: untracked 文件默认不会出现在 git diff --staged 输出里,
85
85
  // 所以先对所有 untracked 文件做 git add -N(intent to add),
86
86
  // 这样它们会以 "new file" 形式出现在 diff 里
87
- async function collectDiffForAi({ execGitCommand, getCurrentProjectPath }) {
87
+ // selectedPaths: 若给定且非空,则只收集这些路径的 diff,且 git add -N 也仅作用于所选 untracked,
88
+ // 避免污染整个 index
89
+ async function collectDiffForAi({ execGitCommand, getCurrentProjectPath, selectedPaths }) {
88
90
  if (typeof execGitCommand !== 'function') {
89
91
  return { diff: '', fileList: [] }
90
92
  }
91
93
  const projectPath = typeof getCurrentProjectPath === 'function' ? getCurrentProjectPath() : ''
92
94
  const cwdOpts = projectPath ? { cwd: projectPath, log: false } : { log: false }
93
95
 
96
+ const selectedSet = Array.isArray(selectedPaths) && selectedPaths.length > 0
97
+ ? new Set(selectedPaths.map(p => String(p).replace(/\\/g, '/')))
98
+ : null
99
+
94
100
  let fileList = []
95
101
  try {
96
102
  // 1. 拿到工作区状态,识别 untracked 文件
@@ -103,6 +109,8 @@ async function collectDiffForAi({ execGitCommand, getCurrentProjectPath }) {
103
109
  const x = line[0]
104
110
  const y = line[1]
105
111
  const path = line.slice(3)
112
+ // 选择模式: 只保留所选路径
113
+ if (selectedSet && !selectedSet.has(path.replace(/\\/g, '/'))) continue
106
114
  if (x === '?' && y === '?') {
107
115
  untracked.push(path)
108
116
  } else if (x !== ' ' || y !== ' ') {
@@ -113,6 +121,7 @@ async function collectDiffForAi({ execGitCommand, getCurrentProjectPath }) {
113
121
  fileList = [...trackedChanges, ...untracked.map(p => `? ${p}`)]
114
122
 
115
123
  // 2. 对 untracked 文件做 intent to add(只在内存中,不会真的暂存内容)
124
+ // 选择模式下 untracked 已被裁剪,只会对所选的做 -N,不污染整个 index
116
125
  if (untracked.length > 0) {
117
126
  // 加上 --force 以防某些文件已经在 index 中
118
127
  // 分批处理,避免命令行过长
@@ -131,9 +140,13 @@ async function collectDiffForAi({ execGitCommand, getCurrentProjectPath }) {
131
140
 
132
141
  // 3. 合并 staged + unstaged diff
133
142
  // 用 --no-color 避免 ANSI 干扰, --no-ext-diff 避免外接 diff 工具
143
+ // 选择模式下用 `-- <paths>` 限定,避免拉取无关 staged 改动
144
+ const pathArgs = selectedSet
145
+ ? ' -- ' + [...selectedSet].map(p => `"${p.replace(/"/g, '\\"')}"`).join(' ')
146
+ : ''
134
147
  const [stagedRes, unstagedRes] = await Promise.all([
135
- execGitCommand('git diff --staged --no-color --no-ext-diff', cwdOpts).catch(() => ({ stdout: '' })),
136
- execGitCommand('git diff --no-color --no-ext-diff', cwdOpts).catch(() => ({ stdout: '' }))
148
+ execGitCommand(`git diff --staged --no-color --no-ext-diff${pathArgs}`, cwdOpts).catch(() => ({ stdout: '' })),
149
+ execGitCommand(`git diff --no-color --no-ext-diff${pathArgs}`, cwdOpts).catch(() => ({ stdout: '' }))
137
150
  ])
138
151
  let combined = ''
139
152
  if (stagedRes?.stdout) combined += stagedRes.stdout.trim() + '\n'
@@ -1073,9 +1086,10 @@ export function registerConfigRoutes({
1073
1086
 
1074
1087
  // AI 生成提交信息
1075
1088
  app.post('/api/config/generate-commit-message', express.json(), async (req, res) => {
1076
- const { fileList } = req.body || {}
1089
+ const { selectedPaths, locale: reqLocale } = req.body || {}
1077
1090
  try {
1078
1091
  const rawConfig = await configManager.readRawConfigFile()
1092
+ const userLocale = reqLocale || rawConfig.locale || 'zh-CN'
1079
1093
  const models = Array.isArray(rawConfig.models) ? rawConfig.models : []
1080
1094
  const defaultModel = models.find(m => m.isDefault) || models[0]
1081
1095
  if (!defaultModel) {
@@ -1083,11 +1097,16 @@ export function registerConfigRoutes({
1083
1097
  }
1084
1098
 
1085
1099
  // 后端自己收集 diff,确保 untracked 文件也能进 prompt
1086
- const { diff: rawDiff, fileList: serverFileList } = await collectDiffForAi({ execGitCommand, getCurrentProjectPath })
1087
- const safeFileList = Array.isArray(fileList) && fileList.length > 0 ? fileList : serverFileList
1088
- const diffText = prepareDiffForPrompt(rawDiff, safeFileList)
1089
- const filesText = safeFileList.slice(0, 30).join('\n')
1090
- const prompt = `你是一个 Git 提交信息生成助手。根据以下 git diff 信息,生成一条符合 Conventional Commits 规范的提交信息。
1100
+ // 选择模式下传入 selectedPaths,后端在 git 层面就过滤,避免污染 index
1101
+ const { diff: rawDiff, fileList: serverFileList } = await collectDiffForAi({
1102
+ execGitCommand,
1103
+ getCurrentProjectPath,
1104
+ selectedPaths
1105
+ })
1106
+ const diffText = prepareDiffForPrompt(rawDiff, serverFileList)
1107
+ const filesText = serverFileList.slice(0, 30).join('\n')
1108
+
1109
+ const promptZh = `你是一个 Git 提交信息生成助手。根据以下 git diff 信息,生成一条符合 Conventional Commits 规范的提交信息。
1091
1110
 
1092
1111
  要求:
1093
1112
  1. type 只能是:feat/fix/docs/style/refactor/test/chore 之一
@@ -1101,10 +1120,26 @@ ${filesText}
1101
1120
  git diff --staged:
1102
1121
  ${diffText || '(无 staged 内容,请根据文件列表推断)'}`
1103
1122
 
1104
- console.log('[generate-commit] ===== PROMPT START (length: ' + prompt.length + ') =====')
1123
+ const promptEn = `You are a Git commit message generation assistant. Based on the following git diff, generate a commit message that follows the Conventional Commits specification.
1124
+
1125
+ Requirements:
1126
+ 1. type must be one of: feat/fix/docs/style/refactor/test/chore
1127
+ 2. scope is optional; use a short English word or short noun phrase to indicate the affected area. Leave empty if unclear.
1128
+ 3. description must be a concise English summary of the change (no more than 50 characters). Use the imperative mood (e.g. "add login button", not "added" or "adding").
1129
+ 4. Return ONLY a JSON object in the format: {"type":"feat","scope":"","description":"xxx"}
1130
+
1131
+ Changed files:
1132
+ ${filesText}
1133
+
1134
+ git diff --staged:
1135
+ ${diffText || '(no staged content, please infer from the file list)'}`
1136
+
1137
+ const prompt = userLocale.startsWith('en') ? promptEn : promptZh
1138
+
1139
+ console.log('[generate-commit] locale:', userLocale, '| prompt length:', prompt.length)
1140
+ console.log('[generate-commit] ===== PROMPT START =====')
1105
1141
  console.log(prompt)
1106
1142
  console.log('[generate-commit] ===== PROMPT END =====')
1107
-
1108
1143
  const { default: fetch } = await import('node-fetch').catch(() => ({ default: globalThis.fetch }))
1109
1144
  const url = `${defaultModel.baseURL.replace(/\/$/, '')}/chat/completions`
1110
1145
  const headers = { 'Content-Type': 'application/json' }
@@ -1 +0,0 @@
1
- .editor-view[data-v-bd5cc01f]{background:var(--bg-container);border:1px solid var(--border-color);width:100%;height:100%;box-shadow:var(--shadow-sm);border-radius:0;display:flex;overflow:hidden}.editor-sidebar[data-v-bd5cc01f]{border-right:1px solid var(--border-color);background:var(--bg-panel);flex-direction:column;flex-shrink:0;display:flex;overflow:hidden}.sidebar-header[data-v-bd5cc01f]{border-bottom:1px solid var(--border-color);flex-shrink:0;justify-content:space-between;align-items:center;padding:8px 10px 6px;display:flex}.sidebar-title[data-v-bd5cc01f]{letter-spacing:.08em;text-transform:uppercase;color:var(--text-secondary);-webkit-user-select:none;user-select:none;font-size:11px;font-weight:700}.sidebar-action-btn[data-v-bd5cc01f]{cursor:pointer;color:var(--text-tertiary);border-radius:var(--radius-base);background:0 0;border:none;align-items:center;padding:3px;display:flex}.sidebar-action-btn[data-v-bd5cc01f]:hover{color:var(--text-primary);background:var(--bg-hover)}.sidebar-tree[data-v-bd5cc01f]{flex:1;padding:4px 0;overflow:hidden auto}.tree-node[data-v-bd5cc01f]{cursor:pointer;-webkit-user-select:none;user-select:none;height:24px;color:var(--text-primary);white-space:nowrap;border-radius:4px;align-items:center;gap:4px;padding-right:8px;font-size:13px;transition:background .1s;display:flex;overflow:hidden}.tree-node[data-v-bd5cc01f]:hover{background:var(--bg-hover)}.tree-node--active[data-v-bd5cc01f]{color:var(--color-primary);background:#3b82f61f}.tree-node--selected[data-v-bd5cc01f]{outline-offset:-1px;background:#63b3ed26;outline:1px solid #63b3ed59}.tree-arrow[data-v-bd5cc01f]{color:var(--text-tertiary);flex-shrink:0;align-items:center;width:12px;transition:transform .15s;display:flex}.tree-arrow.expanded[data-v-bd5cc01f]{transform:rotate(90deg)}.tree-arrow-spacer[data-v-bd5cc01f]{flex-shrink:0;width:12px}.tree-icon[data-v-bd5cc01f]{flex-shrink:0;align-items:center;font-size:14px;line-height:1;display:flex}.tree-icon.mit-icon[data-v-bd5cc01f]{fill:currentColor;vertical-align:middle;width:14px;height:14px;display:inline-block}.tree-icon--dir[data-v-bd5cc01f]{color:#e8b84b}.tree-name[data-v-bd5cc01f]{text-overflow:ellipsis;flex:1;min-width:0;font-size:13px;overflow:hidden}.tree-loading[data-v-bd5cc01f]{border:1.5px solid var(--color-primary);border-top-color:#0000;border-radius:50%;flex-shrink:0;width:10px;height:10px;animation:.8s linear infinite spin-bd5cc01f;display:inline-block}.tree-empty[data-v-bd5cc01f]{color:var(--text-tertiary);text-align:center;padding:24px 12px;font-size:12px}.sidebar-loading[data-v-bd5cc01f]{flex:1;justify-content:center;align-items:center;display:flex}.spin-icon[data-v-bd5cc01f]{border:2px solid var(--color-primary);border-top-color:#0000;border-radius:50%;width:20px;height:20px;animation:.8s linear infinite spin-bd5cc01f;display:inline-block}@keyframes spin-bd5cc01f{to{transform:rotate(360deg)}}.editor-resizer[data-v-bd5cc01f]{cursor:col-resize;z-index:2;background:0 0;flex-shrink:0;width:6px;transition:background .15s;position:relative}.editor-resizer[data-v-bd5cc01f]:after{content:"";background:var(--color-gray-300);border-radius:2px;width:2px;height:32px;transition:background .15s,height .15s;position:absolute;top:50%;left:50%;transform:translate(-50%,-50%)}.editor-resizer[data-v-bd5cc01f]:hover{background:#3b82f60f}.editor-resizer[data-v-bd5cc01f]:hover:after{background:var(--color-primary);height:48px;box-shadow:0 0 8px #3b82f666}.editor-main[data-v-bd5cc01f]{flex-direction:column;flex:1;display:flex;overflow:hidden}.editor-tabs[data-v-bd5cc01f]{border-bottom:1px solid var(--border-color);background:var(--bg-panel);scrollbar-width:none;flex-shrink:0;display:flex;overflow:auto hidden}.editor-tabs[data-v-bd5cc01f]::-webkit-scrollbar{display:none}.editor-tab[data-v-bd5cc01f]{border-right:1px solid var(--border-color);cursor:pointer;height:34px;color:var(--text-secondary);-webkit-user-select:none;user-select:none;flex-shrink:0;align-items:center;gap:6px;min-width:80px;max-width:200px;padding:0 12px;font-size:12.5px;transition:background .1s,color .1s;display:flex}.editor-tab[data-v-bd5cc01f]:hover{background:var(--bg-hover);color:var(--text-primary)}.editor-tab.active[data-v-bd5cc01f]{background:var(--bg-container);color:var(--text-primary);border-bottom:2px solid var(--color-primary)}.tab-name[data-v-bd5cc01f]{text-overflow:ellipsis;white-space:nowrap;flex:1;overflow:hidden}.tab-dirty-dot[data-v-bd5cc01f]{background:var(--color-warning);border-radius:50%;flex-shrink:0;width:6px;height:6px}.tab-close[data-v-bd5cc01f]{cursor:pointer;color:var(--text-tertiary);opacity:0;background:0 0;border:none;border-radius:3px;flex-shrink:0;align-items:center;padding:2px;transition:opacity .1s,background .1s;display:flex}.editor-tab:hover .tab-close[data-v-bd5cc01f],.editor-tab.active .tab-close[data-v-bd5cc01f]{opacity:1}.tab-close[data-v-bd5cc01f]:hover{background:var(--bg-hover);color:var(--color-danger)}.editor-empty[data-v-bd5cc01f]{color:var(--text-tertiary);-webkit-user-select:none;user-select:none;flex-direction:column;flex:1;justify-content:center;align-items:center;gap:10px;font-size:13px;display:flex}.editor-empty p[data-v-bd5cc01f]{margin:0}.editor-empty-hint[data-v-bd5cc01f]{opacity:.6;font-size:11px}.monaco-container[data-v-bd5cc01f]{flex:1;min-width:0;overflow:hidden}.monaco-container.hidden[data-v-bd5cc01f]{display:none}.image-tab-placeholder[data-v-bd5cc01f]{justify-content:center;align-items:center;gap:var(--spacing-sm);color:var(--text-secondary);background:var(--bg-container);text-align:center;padding:var(--spacing-lg);flex-direction:column;flex:1;display:flex}.image-tab-placeholder-title[data-v-bd5cc01f]{font-size:var(--font-size-md);font-weight:var(--font-weight-medium);color:var(--text-primary);word-break:break-all;margin:0}.image-tab-placeholder-hint[data-v-bd5cc01f]{font-size:var(--font-size-sm);color:var(--text-tertiary);margin:0}.editor-body[data-v-bd5cc01f]{flex:1;min-height:0;display:flex;overflow:hidden}.preview-resizer[data-v-bd5cc01f]{cursor:col-resize;z-index:2;background:0 0;flex-shrink:0;order:99;width:6px;margin-left:auto;transition:background .15s;position:relative}.preview-resizer[data-v-bd5cc01f]:after{content:"";background:var(--color-gray-300);border-radius:2px;width:2px;height:32px;transition:background .15s,height .15s;position:absolute;top:50%;left:50%;transform:translate(-50%,-50%)}.preview-resizer[data-v-bd5cc01f]:hover{background:#3b82f60f}.preview-resizer[data-v-bd5cc01f]:hover:after{background:var(--color-primary);height:48px;box-shadow:0 0 8px #3b82f666}.preview-panel[data-v-bd5cc01f]{border-left:1px solid var(--border-color);background:var(--bg-panel);flex-direction:column;flex:1 1 0;min-width:200px;display:flex;overflow:hidden}.preview-header[data-v-bd5cc01f]{border-bottom:1px solid var(--border-color);background:var(--bg-panel);flex-shrink:0;align-items:center;gap:6px;height:34px;padding:0 10px;display:flex}.preview-title[data-v-bd5cc01f]{letter-spacing:.08em;text-transform:uppercase;color:var(--text-secondary);-webkit-user-select:none;user-select:none;font-size:11px;font-weight:700}.preview-ext-badge[data-v-bd5cc01f]{color:var(--color-primary);letter-spacing:.04em;background:#3b82f626;border-radius:3px;padding:1px 5px;font-size:10px;font-weight:600}.preview-header-spacer[data-v-bd5cc01f]{flex:1}.preview-close-btn[data-v-bd5cc01f]{cursor:pointer;color:var(--text-tertiary);border-radius:var(--radius-base);background:0 0;border:none;align-items:center;padding:3px;transition:color .1s,background .1s;display:flex}.preview-close-btn[data-v-bd5cc01f]:hover{color:var(--color-danger);background:var(--bg-hover)}.preview-body[data-v-bd5cc01f]{flex-direction:column;flex:1;display:flex;overflow:hidden}.preview-iframe[data-v-bd5cc01f]{background:0 0;border:none;flex:1;width:100%;height:100%}.preview-image-wrap[data-v-bd5cc01f]{background:var(--bg-container);flex:1;justify-content:center;align-items:center;padding:16px;display:flex;overflow:auto}.preview-image-wrap img[data-v-bd5cc01f]{object-fit:contain;border-radius:4px;max-width:100%;max-height:100%;box-shadow:0 2px 12px #0003}.editor-tabs-spacer[data-v-bd5cc01f]{flex:1}.preview-toggle-btn[data-v-bd5cc01f]{cursor:pointer;height:34px;color:var(--text-secondary);white-space:nowrap;border:none;border-left:1px solid var(--border-color);background:0 0;flex-shrink:0;align-items:center;gap:5px;padding:0 10px;font-size:12px;transition:background .1s,color .1s;display:flex}.preview-toggle-btn[data-v-bd5cc01f]:hover{background:var(--bg-hover);color:var(--text-primary)}.preview-toggle-btn.active[data-v-bd5cc01f]{color:var(--color-primary);background:#3b82f614}.sidebar-actions[data-v-bd5cc01f]{align-items:center;gap:2px;display:flex}.tree-inline-input-row[data-v-bd5cc01f]{cursor:default;background:var(--bg-hover)}.tree-inline-input[data-v-bd5cc01f]{background:var(--bg-container);border:1px solid var(--color-primary);min-width:0;height:20px;color:var(--text-primary);border-radius:3px;outline:none;flex:1;padding:0 5px;font-family:inherit;font-size:12.5px}.ctx-menu[data-v-bd5cc01f]{z-index:9999;background:var(--bg-panel);border:1px solid var(--border-color);-webkit-user-select:none;user-select:none;border-radius:6px;min-width:160px;padding:4px;position:fixed;box-shadow:0 8px 24px #00000040}.ctx-menu-item[data-v-bd5cc01f]{cursor:pointer;width:100%;color:var(--text-primary);text-align:left;background:0 0;border:none;border-radius:4px;align-items:center;gap:8px;padding:6px 10px;font-size:12.5px;transition:background .1s;display:flex}.ctx-menu-item[data-v-bd5cc01f]:hover{background:var(--bg-hover)}.ctx-menu-item--danger[data-v-bd5cc01f]{color:var(--color-danger)}.ctx-menu-item--danger[data-v-bd5cc01f]:hover{background:#ef44441a}.ctx-menu-sep[data-v-bd5cc01f]{background:var(--border-color);height:1px;margin:4px 2px}
@@ -1,21 +0,0 @@
1
- import"./rolldown-runtime-BM3Ffeng.js";import{$r as e,$t as t,Ai as n,Ci as r,Jr as i,Mi as a,Ni as o,Oi as s,Qr as c,Qt as ee,Ti as te,Un as l,Xt as ne,Zr as u,Zt as re,_i as d,_t as ie,ci as f,ei as p,en as ae,hi as m,ii as h,ji as g,ki as oe,mi as _,n as se,ni as ce,pi as v,ri as y,si as b,sn as x,ti as S,ui as le,vt as C,wi as ue,yi as de}from"./vendor-DITsiaGj.js";import{a as w,i as fe,n as pe,o as T,r as me,t as he}from"./index-yky0Sd13.js";function ge(e){return{ts:`typescript`,tsx:`typescript`,js:`javascript`,mjs:`javascript`,cjs:`javascript`,jsx:`javascript`,vue:`html`,html:`html`,htm:`html`,css:`css`,scss:`scss`,less:`less`,json:`json`,jsonc:`json`,md:`markdown`,markdown:`markdown`,yaml:`yaml`,yml:`yaml`,toml:`ini`,xml:`xml`,svg:`xml`,sh:`shell`,bash:`shell`,zsh:`shell`,fish:`shell`,ps1:`powershell`,py:`python`,go:`go`,rs:`rust`,java:`java`,kt:`kotlin`,rb:`ruby`,php:`php`,c:`c`,cpp:`cpp`,h:`cpp`,cs:`csharp`,sql:`sql`,graphql:`graphql`,gql:`graphql`,txt:`plaintext`,log:`plaintext`,ini:`ini`,env:`ini`,gitignore:`ini`,dockerfile:`dockerfile`}[e.toLowerCase()]??`plaintext`}var _e={class:`sidebar-header`},ve={class:`sidebar-title`},ye={class:`sidebar-actions`},be={key:0,class:`sidebar-tree`},xe={key:1,class:`tree-arrow-spacer`},Se={class:`tree-icon mit-icon`,"aria-hidden":`true`},Ce=[`xlink:href`],we=[`onClick`,`onContextmenu`],Te={key:1,class:`tree-arrow-spacer`},Ee={key:2,class:`tree-icon mit-icon`,"aria-hidden":`true`},De=[`xlink:href`],Oe={key:3,class:`tree-icon mit-icon`,"aria-hidden":`true`},ke=[`xlink:href`],Ae=[`title`],je={key:4,class:`tree-loading`},Me={key:0,viewBox:`0 0 24 24`,width:`13`,height:`13`,fill:`none`,stroke:`currentColor`,"stroke-width":`2`,"stroke-linecap":`round`,"stroke-linejoin":`round`,style:{"flex-shrink":`0`,color:`var(--color-warning)`}},Ne={key:1,viewBox:`0 0 24 24`,width:`13`,height:`13`,fill:`none`,stroke:`currentColor`,"stroke-width":`2`,"stroke-linecap":`round`,"stroke-linejoin":`round`,style:{"flex-shrink":`0`,color:`var(--text-tertiary)`}},Pe=[`placeholder`],Fe={key:0,class:`tree-node tree-inline-input-row`,style:{paddingLeft:`12px`}},Ie={key:0,viewBox:`0 0 24 24`,width:`13`,height:`13`,fill:`none`,stroke:`currentColor`,"stroke-width":`2`,"stroke-linecap":`round`,"stroke-linejoin":`round`,style:{"flex-shrink":`0`,color:`var(--color-warning)`}},Le={key:1,viewBox:`0 0 24 24`,width:`13`,height:`13`,fill:`none`,stroke:`currentColor`,"stroke-width":`2`,"stroke-linecap":`round`,"stroke-linejoin":`round`,style:{"flex-shrink":`0`,color:`var(--text-tertiary)`}},Re=[`placeholder`],ze={key:1,class:`tree-empty`},Be={key:1,class:`sidebar-loading`},Ve={class:`editor-main`},He={key:0,class:`editor-tabs`},Ue=[`onClick`,`title`],We={class:`tab-name`},Ge={key:0,class:`tab-dirty-dot`},Ke=[`onClick`],qe=[`title`],Je={key:1,class:`editor-empty`},Ye={viewBox:`0 0 24 24`,width:`48`,height:`48`,fill:`none`,stroke:`currentColor`,"stroke-width":`1.2`,"stroke-linecap":`round`,"stroke-linejoin":`round`,style:{opacity:`.3`}},Xe={class:`editor-empty-hint`},Ze={class:`editor-body`},Qe={key:0,class:`image-tab-placeholder`},$e={viewBox:`0 0 24 24`,width:`56`,height:`56`,fill:`none`,stroke:`currentColor`,"stroke-width":`1.2`,"stroke-linecap":`round`,"stroke-linejoin":`round`,style:{opacity:`.35`}},et={class:`image-tab-placeholder-title`},tt={class:`image-tab-placeholder-hint`},nt={class:`preview-header`},rt={class:`preview-title`},it={class:`preview-ext-badge`},at=[`title`],ot={class:`preview-body`},st=[`srcdoc`],E=w(le({__name:`EditorView`,setup(le){self.MonacoEnvironment={getWorker(e,n){return n===`json`?new t:n===`css`||n===`scss`||n===`less`?new ee:n===`html`||n===`handlebars`||n===`razor`?new re:n===`typescript`||n===`javascript`?new ne:new ae}};let w=fe(),E=s([]),D=s(!1);async function O(e,t=0){let n=await(await fetch(`/api/browse_directory?path=${encodeURIComponent(e)}`)).json();return n.success?n.items.map(e=>({...e,depth:t,expanded:!1,loading:!1,children:(e.type,void 0)})):[]}async function ct(){let e=w.currentDirectory;if(e){D.value=!0;try{E.value=await O(e,0)}finally{D.value=!1}}}function lt(e,t=new Set){for(let n of e)n.type===`directory`&&n.expanded&&(t.add(n.path),n.children&&lt(n.children,t));return t}async function ut(e,t){for(let n of e)n.type===`directory`&&t.has(n.path)&&(n.children||=await O(n.path,n.depth+1),n.expanded=!0,await ut(n.children,t))}async function k(){let e=w.currentDirectory;if(!e)return;let t=lt(E.value);D.value=!0;try{E.value=await O(e,0),t.size>0&&await ut(E.value,t)}finally{D.value=!1}}async function A(e){if(e.type===`directory`)if(e.expanded)e.expanded=!1;else{if(!e.children){e.loading=!0;try{e.children=await O(e.path,e.depth+1)}finally{e.loading=!1}}e.expanded=!0}}function dt(e){let t=[];for(let n of e)t.push(n),n.type===`directory`&&n.expanded&&n.children&&t.push(...dt(n.children));return t}let j=s([]),M=s(null),N=s(null);async function ft(e){if(N.value=e,e.type!==`file`){A(e);return}if(j.value.find(t=>t.path===e.path)){M.value=e.path;return}let t=e.name.split(`.`).pop()||``;if(Y.has(t.toLowerCase())){let t={path:e.path,name:e.name,content:``,originalContent:``,isDirty:!1,language:`plaintext`};j.value.push(t),M.value=e.path,X.value=!0;return}try{let n=await(await fetch(`/api/editor/file?path=${encodeURIComponent(e.path)}`)).json();if(!n.success){x.error(`${T(`@EDITOR:打开文件失败: `)}${n.error}`);return}let r=ge(t),i={path:e.path,name:e.name,content:n.content,originalContent:n.content,isDirty:!1,language:r};j.value.push(i),M.value=e.path}catch(e){x.error(`${T(`@EDITOR:打开文件失败: `)}${e.message}`)}}function pt(e,t){t.stopPropagation();let n=j.value.findIndex(t=>t.path===e);n!==-1&&(j.value[n].isDirty&&!confirm(T(`@EDITOR:文件未保存,确认关闭?`))||(j.value.splice(n,1),M.value===e&&(M.value=j.value[Math.min(n,j.value.length-1)]?.path??null)))}let P=()=>j.value.find(e=>e.path===M.value)??null,F=s(null),I=oe(null),L=new Map;function mt(e){let t=L.get(e.path);return(!t||t.isDisposed())&&(t=C.createModel(e.content,e.language,ie.file(e.path)),L.set(e.path,t)),t}function ht(){if(!F.value)return;let e=document.documentElement.getAttribute(`data-theme`)===`dark`;I.value=C.create(F.value,{theme:e?`vs-dark`:`vs`,fontSize:13,lineHeight:20,fontFamily:`'JetBrains Mono', 'Fira Code', 'Cascadia Code', Consolas, monospace`,minimap:{enabled:!0},scrollBeyondLastLine:!1,renderWhitespace:`selection`,automaticLayout:!0,tabSize:2,wordWrap:`off`,smoothScrolling:!0,cursorBlinking:`smooth`,padding:{top:8,bottom:8}}),I.value.onDidChangeModelContent(()=>{let e=P();if(!e)return;let t=I.value.getValue();e.content=t,e.isDirty=t!==e.originalContent}),I.value.onDidBlurEditorText(()=>{w.ui.editorAutoSave&&P()?.isDirty&&_t(!1)})}r(M,e=>{if(!I.value||!e)return;let t=j.value.find(t=>t.path===e);if(!t)return;let n=mt(t);I.value.setModel(n)});let gt=new MutationObserver(()=>{let e=document.documentElement.getAttribute(`data-theme`)===`dark`;C.setTheme(e?`vs-dark`:`vs`)});m(async()=>{ht(),await ct(),gt.observe(document.documentElement,{attributes:!0,attributeFilter:[`data-theme`]})}),_(()=>{gt.disconnect(),I.value?.dispose(),L.forEach(e=>e.dispose()),L.clear()});async function _t(e=!1){let t=P();if(t)try{let n=await(await fetch(`/api/editor/file`,{method:`PUT`,headers:{"Content-Type":`application/json`},body:JSON.stringify({path:t.path,content:t.content})})).json();if(!n.success){x.error(`${T(`@EDITOR:保存失败: `)}${n.error}`);return}t.originalContent=t.content,t.isDirty=!1,e||x.success(T(`@EDITOR:已保存`))}catch(e){x.error(`${T(`@EDITOR:保存失败: `)}${e.message}`)}}function vt(e){(e.ctrlKey||e.metaKey)&&e.key===`s`&&(e.preventDefault(),_t())}m(()=>window.addEventListener(`keydown`,vt)),_(()=>window.removeEventListener(`keydown`,vt));let yt=s(null),R=s(220),z=!1,bt=0,xt=0;function St(e){z=!0,bt=e.clientX,xt=R.value,document.addEventListener(`mousemove`,Ct),document.addEventListener(`mouseup`,wt),e.preventDefault()}function Ct(e){if(!z)return;let t=e.clientX-bt;R.value=Math.max(140,Math.min(400,xt+t))}function wt(){z=!1,document.removeEventListener(`mousemove`,Ct),document.removeEventListener(`mouseup`,wt)}function B(e){return e.type===`directory`?me(e.name):pe(e.name)}let V=s(null),H=s(null),U=s(null),W=s(null);function G(){let e=N.value;return e?e.type===`directory`?{parentPath:e.path,afterNode:e,depth:e.depth+1}:{parentPath:e.path.includes(`/`)||e.path.includes(`\\`)?e.path.replace(/[\\/][^\\/]+$/,``):w.currentDirectory??``,afterNode:e,depth:e.depth}:{parentPath:w.currentDirectory??``,afterNode:null,depth:0}}async function Tt(){let e=G();N.value?.type===`directory`&&!N.value.expanded&&await A(N.value),V.value={...e,kind:`file`,value:``},await v(),U.value?.focus()}async function Et(){let e=G();N.value?.type===`directory`&&!N.value.expanded&&await A(N.value),V.value={...e,kind:`directory`,value:``},await v(),U.value?.focus()}function K(){V.value=null}async function Dt(){let e=V.value;if(!e||!e.value.trim()){V.value=null;return}let t=e.value.trim(),n=e.parentPath.replace(/[/\\]$/,``)+`/`+t;if(e.kind===`file`){let e=await(await fetch(`/api/editor/file`,{method:`POST`,headers:{"Content-Type":`application/json`},body:JSON.stringify({path:n})})).json();if(!e.success){x.error(e.error);return}x.success(T(`@EDITOR:创建成功`))}else{let e=await(await fetch(`/api/editor/directory`,{method:`POST`,headers:{"Content-Type":`application/json`},body:JSON.stringify({path:n})})).json();if(!e.success){x.error(e.error);return}x.success(T(`@EDITOR:创建成功`))}V.value=null,await k()}function Ot(e){e.key===`Enter`&&(e.preventDefault(),Dt()),e.key===`Escape`&&(e.preventDefault(),K())}let q=s(null),kt=s(null);function At(e,t){e.preventDefault(),q.value={x:e.clientX,y:e.clientY,node:t}}function J(){q.value=null}async function jt(){let e=q.value?.node;J(),e&&(N.value=e),e?.type===`directory`&&!e.expanded&&await A(e),V.value={...G(),kind:`file`,value:``},await v(),U.value?.focus()}async function Mt(){let e=q.value?.node;J(),e&&(N.value=e),e?.type===`directory`&&!e.expanded&&await A(e),V.value={...G(),kind:`directory`,value:``},await v(),U.value?.focus()}async function Nt(){let e=q.value?.node;J(),e&&(H.value={node:e,value:e.name},await v(),W.value?.focus(),W.value?.select())}async function Pt(){let e=H.value;if(!e||!e.value.trim()||e.value.trim()===e.node.name){H.value=null;return}let t=e.value.trim(),n=e.node.path.replace(/[\\/][^\\/]+$/,``).replace(/[/\\]$/,``)+`/`+t,r=await(await fetch(`/api/editor/rename`,{method:`PUT`,headers:{"Content-Type":`application/json`},body:JSON.stringify({oldPath:e.node.path,newPath:n})})).json();if(!r.success){x.error(r.error);return}let i=j.value.find(t=>t.path===e.node.path);i&&(i.path=n,i.name=t,M.value===e.node.path&&(M.value=n)),H.value=null,await k()}function Ft(e){e.key===`Enter`&&(e.preventDefault(),Pt()),e.key===`Escape`&&(e.preventDefault(),H.value=null)}async function It(){let e=q.value?.node;if(J(),!e)return;let t=e.type===`directory`?T(`@EDITOR:文件夹`):T(`@EDITOR:文件`);if(!confirm(`${T(`@EDITOR:确认删除`)} ${t} "${e.name}"?`))return;let n=await(await fetch(`/api/editor/entry?path=${encodeURIComponent(e.path)}`,{method:`DELETE`})).json();if(!n.success){x.error(n.error);return}let r=j.value.findIndex(t=>t.path===e.path);r!==-1&&(j.value.splice(r,1),M.value===e.path&&(M.value=j.value[Math.max(0,r-1)]?.path??null)),x.success(T(`@EDITOR:已删除`)),await k()}async function Lt(){let e=q.value?.node;if(J(),e)try{let t=await(await fetch(`/api/editor/reveal`,{method:`POST`,headers:{"Content-Type":`application/json`},body:JSON.stringify({path:e.path})})).json();t.success||x.error(t.error)}catch(e){x.error(e?.message||String(e))}}m(()=>document.addEventListener(`click`,J)),_(()=>document.removeEventListener(`click`,J));let Rt=new Set([`md`,`html`,`htm`,`svg`]),Y=new Set([`png`,`jpg`,`jpeg`,`gif`,`webp`,`ico`,`bmp`]),X=s(!1),Z=s(0),Q=p(()=>j.value.find(e=>e.path===M.value)??null),zt=p(()=>Q.value?.language===`plaintext`&&Q.value?.content===``),$=p(()=>(Q.value?.name??``).split(`.`).pop()?.toLowerCase()??``),Bt=p(()=>Rt.has($.value)||Y.has($.value));r(M,()=>{X.value&&!Bt.value&&(X.value=!1)});function Vt(){Bt.value&&(X.value=!X.value)}let Ht=p(()=>{let e=Q.value;if(!e)return``;let t=$.value,n=document.documentElement.getAttribute(`data-theme`)!==`light`,r=n?`#0d1117`:`#ffffff`,i=n?`#c9d1d9`:`#1f2328`,a=n?`#30363d`:`#d0d7de`,o=n?`#161b22`:`#f6f8fa`,s=`
2
- html, body { margin: 0; padding: 0; background: ${r}; color: ${i}; }
3
- body { font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif; font-size: 14px; line-height: 1.6; padding: 20px 24px; }
4
- * { box-sizing: border-box; }
5
- h1, h2, h3, h4, h5, h6 { border-bottom: 1px solid ${a}; padding-bottom: .3em; margin-top: 24px; margin-bottom: 16px; }
6
- h1 { font-size: 2em; } h2 { font-size: 1.5em; } h3 { font-size: 1.25em; }
7
- p { margin: 0 0 16px; }
8
- code { background: ${o}; padding: 2px 5px; border-radius: 4px; font-family: 'JetBrains Mono', 'Fira Code', Consolas, monospace; font-size: 87%; }
9
- pre { background: ${o}; padding: 14px 16px; border-radius: 6px; overflow: auto; margin: 0 0 16px; }
10
- pre code { background: none; padding: 0; font-size: 100%; }
11
- a { color: ${n?`#58a6ff`:`#0969da`}; }
12
- blockquote { border-left: 3px solid ${a}; margin: 0 0 16px; padding: 0 16px; color: ${n?`#8b949e`:`#656d76`}; }
13
- img { max-width: 100%; border-radius: 4px; }
14
- hr { border: none; border-top: 1px solid ${a}; margin: 24px 0; }
15
- table { border-collapse: collapse; width: 100%; margin-bottom: 16px; }
16
- th, td { border: 1px solid ${a}; padding: 6px 13px; }
17
- thead tr { background: ${o}; }
18
- tbody tr:nth-child(even) { background: ${o}; }
19
- ul, ol { padding-left: 2em; margin-bottom: 16px; }
20
- li { margin: 4px 0; }
21
- `;return t===`md`?`<!DOCTYPE html><html><head><meta charset="utf-8"><style>${s}</style></head><body>${se.parse(e.content)}</body></html>`:t===`html`||t===`htm`?e.content:t===`svg`?`<!DOCTYPE html><html><head><meta charset="utf-8"><style>html,body{margin:0;padding:0;background:${r};display:flex;align-items:center;justify-content:center;min-height:100vh;}svg{max-width:100%;max-height:90vh;}</style></head><body>${e.content}</body></html>`:``}),Ut=!1,Wt=0,Gt=0;function Kt(e){Ut=!0,Wt=e.clientX,Gt=Z.value,document.addEventListener(`mousemove`,qt),document.addEventListener(`mouseup`,Jt),e.preventDefault()}function qt(e){if(!Ut)return;let t=e.clientX-Wt;Z.value=Math.max(200,Math.min(900,Gt+t))}function Jt(){Ut=!1,document.removeEventListener(`mousemove`,qt),document.removeEventListener(`mouseup`,Jt)}return(t,r)=>(d(),h(c,null,[S(`div`,{class:`editor-view`,ref_key:`containerRef`,ref:yt},[S(`div`,{class:`editor-sidebar`,style:a({width:R.value+`px`})},[S(`div`,_e,[S(`span`,ve,o(n(T)(`@EDITOR:资源管理器`)),1),S(`div`,ye,[f(n(l),{content:n(T)(`@EDITOR:新建文件`),placement:`bottom`,"show-after":300},{default:ue(()=>[S(`button`,{class:`sidebar-action-btn`,onClick:Tt},r[8]||=[S(`svg`,{viewBox:`0 0 24 24`,width:`14`,height:`14`,fill:`none`,stroke:`currentColor`,"stroke-width":`2`,"stroke-linecap":`round`,"stroke-linejoin":`round`},[S(`path`,{d:`M14.5 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V7.5L14.5 2z`}),S(`polyline`,{points:`14 2 14 8 20 8`}),S(`line`,{x1:`12`,y1:`13`,x2:`12`,y2:`19`}),S(`line`,{x1:`9`,y1:`16`,x2:`15`,y2:`16`})],-1)])]),_:1},8,[`content`]),f(n(l),{content:n(T)(`@EDITOR:新建文件夹`),placement:`bottom`,"show-after":300},{default:ue(()=>[S(`button`,{class:`sidebar-action-btn`,onClick:Et},r[9]||=[S(`svg`,{viewBox:`0 0 24 24`,width:`14`,height:`14`,fill:`none`,stroke:`currentColor`,"stroke-width":`2`,"stroke-linecap":`round`,"stroke-linejoin":`round`},[S(`path`,{d:`M22 19a2 2 0 0 1-2 2H4a2 2 0 0 1-2-2V5a2 2 0 0 1 2-2h5l2 3h9a2 2 0 0 1 2 2z`}),S(`line`,{x1:`12`,y1:`11`,x2:`12`,y2:`17`}),S(`line`,{x1:`9`,y1:`14`,x2:`15`,y2:`14`})],-1)])]),_:1},8,[`content`]),f(n(l),{content:n(T)(`@EDITOR:刷新`),placement:`bottom`,"show-after":300},{default:ue(()=>[S(`button`,{class:`sidebar-action-btn`,onClick:ct},r[10]||=[S(`svg`,{viewBox:`0 0 24 24`,width:`14`,height:`14`,fill:`none`,stroke:`currentColor`,"stroke-width":`2`,"stroke-linecap":`round`,"stroke-linejoin":`round`},[S(`polyline`,{points:`1 4 1 10 7 10`}),S(`polyline`,{points:`23 20 23 14 17 14`}),S(`path`,{d:`M20.49 9A9 9 0 0 0 5.64 5.64L1 10m22 4l-4.64 4.36A9 9 0 0 1 3.51 15`})],-1)])]),_:1},8,[`content`])])]),D.value?(d(),h(`div`,Be,r[19]||=[S(`span`,{class:`spin-icon`},null,-1)])):(d(),h(`div`,be,[(d(!0),h(c,null,de(dt(E.value),e=>(d(),h(c,{key:e.path},[H.value&&H.value.node.path===e.path?(d(),h(`div`,{key:0,class:`tree-node tree-inline-input-row`,style:a({paddingLeft:12+e.depth*14+`px`})},[e.type===`directory`?(d(),h(`span`,{key:0,class:g([`tree-arrow`,{expanded:e.expanded}])},r[11]||=[S(`svg`,{viewBox:`0 0 24 24`,width:`10`,height:`10`,fill:`none`,stroke:`currentColor`,"stroke-width":`2.5`,"stroke-linecap":`round`,"stroke-linejoin":`round`},[S(`polyline`,{points:`9 18 15 12 9 6`})],-1)],2)):(d(),h(`span`,xe)),(d(),h(`svg`,Se,[S(`use`,{"xlink:href":`#${B(e)}`},null,8,Ce)])),te(S(`input`,{ref_for:!0,ref_key:`renameInputRef`,ref:W,"onUpdate:modelValue":r[0]||=e=>H.value.value=e,onKeydown:Ft,onBlur:Pt,onClick:r[1]||=u(()=>{},[`stop`])},null,544),[[i,H.value.value]])],4)):(d(),h(`div`,{key:1,class:g([`tree-node`,{"tree-node--dir":e.type===`directory`,"tree-node--file":e.type===`file`,"tree-node--active":M.value===e.path,"tree-node--selected":N.value?.path===e.path&&M.value!==e.path}]),style:a({paddingLeft:12+e.depth*14+`px`}),onClick:t=>ft(e),onContextmenu:t=>At(t,e)},[e.type===`directory`?(d(),h(`span`,{key:0,class:g([`tree-arrow`,{expanded:e.expanded}])},r[12]||=[S(`svg`,{viewBox:`0 0 24 24`,width:`10`,height:`10`,fill:`none`,stroke:`currentColor`,"stroke-width":`2.5`,"stroke-linecap":`round`,"stroke-linejoin":`round`},[S(`polyline`,{points:`9 18 15 12 9 6`})],-1)],2)):(d(),h(`span`,Te)),e.type===`directory`?(d(),h(`svg`,Ee,[S(`use`,{"xlink:href":`#${B(e)}`},null,8,De)])):(d(),h(`svg`,Oe,[S(`use`,{"xlink:href":`#${B(e)}`},null,8,ke)])),S(`span`,{class:`tree-name`,title:e.path},o(e.name),9,Ae),e.loading?(d(),h(`span`,je)):y(``,!0)],46,we)),V.value&&V.value.afterNode?.path===e.path?(d(),h(`div`,{key:2,class:`tree-node tree-inline-input-row`,style:a({paddingLeft:12+V.value.depth*14+`px`})},[r[15]||=S(`span`,{class:`tree-arrow-spacer`},null,-1),V.value.kind===`directory`?(d(),h(`svg`,Me,r[13]||=[S(`path`,{d:`M22 19a2 2 0 0 1-2 2H4a2 2 0 0 1-2-2V5a2 2 0 0 1 2-2h5l2 3h9a2 2 0 0 1 2 2z`},null,-1)])):(d(),h(`svg`,Ne,r[14]||=[S(`path`,{d:`M14.5 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V7.5L14.5 2z`},null,-1),S(`polyline`,{points:`14 2 14 8 20 8`},null,-1)])),te(S(`input`,{ref_for:!0,ref_key:`inlineInputRef`,ref:U,class:`tree-inline-input`,"onUpdate:modelValue":r[2]||=e=>V.value.value=e,placeholder:V.value.kind===`file`?n(T)(`@EDITOR:输入文件名`):n(T)(`@EDITOR:输入文件夹名`),onKeydown:Ot,onBlur:K,onClick:r[3]||=u(()=>{},[`stop`])},null,40,Pe),[[i,V.value.value]])],4)):y(``,!0)],64))),128)),V.value&&V.value.afterNode===null?(d(),h(`div`,Fe,[r[18]||=S(`span`,{class:`tree-arrow-spacer`},null,-1),V.value.kind===`directory`?(d(),h(`svg`,Ie,r[16]||=[S(`path`,{d:`M22 19a2 2 0 0 1-2 2H4a2 2 0 0 1-2-2V5a2 2 0 0 1 2-2h5l2 3h9a2 2 0 0 1 2 2z`},null,-1)])):(d(),h(`svg`,Le,r[17]||=[S(`path`,{d:`M14.5 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V7.5L14.5 2z`},null,-1),S(`polyline`,{points:`14 2 14 8 20 8`},null,-1)])),te(S(`input`,{ref_key:`inlineInputRef`,ref:U,class:`tree-inline-input`,"onUpdate:modelValue":r[4]||=e=>V.value.value=e,placeholder:V.value.kind===`file`?n(T)(`@EDITOR:输入文件名`):n(T)(`@EDITOR:输入文件夹名`),onKeydown:Ot,onBlur:K,onClick:r[5]||=u(()=>{},[`stop`])},null,40,Re),[[i,V.value.value]])])):y(``,!0),E.value.length===0&&!V.value?(d(),h(`div`,ze,o(n(T)(`@EDITOR:暂无文件`)),1)):y(``,!0)]))],4),S(`div`,{class:`editor-resizer`,onMousedown:St},null,32),S(`div`,Ve,[j.value.length>0?(d(),h(`div`,He,[(d(!0),h(c,null,de(j.value,e=>(d(),h(`div`,{key:e.path,class:g([`editor-tab`,{active:M.value===e.path,dirty:e.isDirty}]),onClick:t=>M.value=e.path,title:e.path},[S(`span`,We,o(e.name),1),e.isDirty?(d(),h(`span`,Ge)):y(``,!0),S(`button`,{class:`tab-close`,onClick:t=>pt(e.path,t)},r[20]||=[S(`svg`,{viewBox:`0 0 24 24`,width:`12`,height:`12`,fill:`none`,stroke:`currentColor`,"stroke-width":`2.5`,"stroke-linecap":`round`},[S(`line`,{x1:`18`,y1:`6`,x2:`6`,y2:`18`}),S(`line`,{x1:`6`,y1:`6`,x2:`18`,y2:`18`})],-1)],8,Ke)],10,Ue))),128)),r[22]||=S(`div`,{class:`editor-tabs-spacer`},null,-1),Bt.value?(d(),h(`button`,{key:0,class:g([`preview-toggle-btn`,{active:X.value}]),title:X.value?n(T)(`@EDITOR:关闭预览`):n(T)(`@EDITOR:打开预览`),onClick:Vt},[r[21]||=S(`svg`,{viewBox:`0 0 24 24`,width:`14`,height:`14`,fill:`none`,stroke:`currentColor`,"stroke-width":`2`,"stroke-linecap":`round`,"stroke-linejoin":`round`},[S(`path`,{d:`M1 12s4-8 11-8 11 8 11 8-4 8-11 8-11-8-11-8z`}),S(`circle`,{cx:`12`,cy:`12`,r:`3`})],-1),S(`span`,null,o(n(T)(`@EDITOR:预览`)),1)],10,qe)):y(``,!0)])):y(``,!0),j.value.length===0?(d(),h(`div`,Je,[(d(),h(`svg`,Ye,r[23]||=[S(`path`,{d:`M14.5 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V7.5L14.5 2z`},null,-1),S(`polyline`,{points:`14 2 14 8 20 8`},null,-1)])),S(`p`,null,o(n(T)(`@EDITOR:从左侧选择文件打开`)),1),S(`p`,Xe,o(n(T)(`@EDITOR:Ctrl+S 保存`)),1)])):y(``,!0),S(`div`,Ze,[S(`div`,{class:g([`monaco-container`,{hidden:j.value.length===0||zt.value}]),ref_key:`editorContainerRef`,ref:F},null,2),zt.value&&j.value.length>0&&!X.value?(d(),h(`div`,Qe,[(d(),h(`svg`,$e,r[24]||=[S(`rect`,{x:`3`,y:`3`,width:`18`,height:`18`,rx:`2`},null,-1),S(`circle`,{cx:`9`,cy:`9`,r:`2`},null,-1),S(`path`,{d:`m21 15-5-5L5 21`},null,-1)])),S(`p`,et,o(Q.value?.name),1),S(`p`,tt,o(n(T)(`@EDITOR:这是图片文件,已在右侧预览面板中打开`)),1)])):y(``,!0),X.value&&j.value.length>0?(d(),h(`div`,{key:1,class:`preview-resizer`,onMousedown:Kt},null,32)):y(``,!0),X.value&&j.value.length>0?(d(),h(`div`,{key:2,class:`preview-panel`,style:a({flexBasis:Z.value+`px`})},[S(`div`,nt,[S(`span`,rt,o(n(T)(`@EDITOR:预览`)),1),S(`span`,it,o($.value.toUpperCase()),1),r[26]||=S(`div`,{class:`preview-header-spacer`},null,-1),S(`button`,{class:`preview-close-btn`,title:n(T)(`@EDITOR:关闭预览`),onClick:r[6]||=e=>X.value=!1},r[25]||=[S(`svg`,{viewBox:`0 0 24 24`,width:`13`,height:`13`,fill:`none`,stroke:`currentColor`,"stroke-width":`2.5`,"stroke-linecap":`round`},[S(`line`,{x1:`18`,y1:`6`,x2:`6`,y2:`18`}),S(`line`,{x1:`6`,y1:`6`,x2:`18`,y2:`18`})],-1)],8,at)]),S(`div`,ot,[[`md`,`html`,`htm`,`svg`].includes($.value)?(d(),h(`iframe`,{key:0,class:`preview-iframe`,sandbox:`allow-same-origin`,srcdoc:Ht.value},null,8,st)):n(Y).has($.value)&&Q.value?(d(),ce(he,{key:1,"file-path":Q.value.path,"file-name":Q.value.name},null,8,[`file-path`,`file-name`])):y(``,!0)])],4)):y(``,!0)])])],512),(d(),ce(e,{to:`body`},[q.value?(d(),h(`div`,{key:0,ref_key:`ctxMenuRef`,ref:kt,class:`ctx-menu`,style:a({left:q.value.x+`px`,top:q.value.y+`px`}),onClick:r[7]||=u(()=>{},[`stop`])},[S(`button`,{class:`ctx-menu-item`,onClick:jt},[r[27]||=S(`svg`,{viewBox:`0 0 24 24`,width:`13`,height:`13`,fill:`none`,stroke:`currentColor`,"stroke-width":`2`,"stroke-linecap":`round`,"stroke-linejoin":`round`},[S(`path`,{d:`M14.5 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V7.5L14.5 2z`}),S(`polyline`,{points:`14 2 14 8 20 8`}),S(`line`,{x1:`12`,y1:`13`,x2:`12`,y2:`19`}),S(`line`,{x1:`9`,y1:`16`,x2:`15`,y2:`16`})],-1),b(` `+o(n(T)(`@EDITOR:新建文件`)),1)]),S(`button`,{class:`ctx-menu-item`,onClick:Mt},[r[28]||=S(`svg`,{viewBox:`0 0 24 24`,width:`13`,height:`13`,fill:`none`,stroke:`currentColor`,"stroke-width":`2`,"stroke-linecap":`round`,"stroke-linejoin":`round`},[S(`path`,{d:`M22 19a2 2 0 0 1-2 2H4a2 2 0 0 1-2-2V5a2 2 0 0 1 2-2h5l2 3h9a2 2 0 0 1 2 2z`}),S(`line`,{x1:`12`,y1:`11`,x2:`12`,y2:`17`}),S(`line`,{x1:`9`,y1:`14`,x2:`15`,y2:`14`})],-1),b(` `+o(n(T)(`@EDITOR:新建文件夹`)),1)]),r[32]||=S(`div`,{class:`ctx-menu-sep`},null,-1),S(`button`,{class:`ctx-menu-item`,onClick:Lt},[r[29]||=S(`svg`,{viewBox:`0 0 24 24`,width:`13`,height:`13`,fill:`none`,stroke:`currentColor`,"stroke-width":`2`,"stroke-linecap":`round`,"stroke-linejoin":`round`},[S(`path`,{d:`M3 7a2 2 0 0 1 2-2h4l2 2h8a2 2 0 0 1 2 2v8a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2z`}),S(`path`,{d:`M3 7v10a2 2 0 0 0 2 2h14a2 2 0 0 0 2-2V9a2 2 0 0 0-2-2`})],-1),b(` `+o(n(T)(`@EDITOR:在资源管理器中打开`)),1)]),S(`button`,{class:`ctx-menu-item`,onClick:Nt},[r[30]||=S(`svg`,{viewBox:`0 0 24 24`,width:`13`,height:`13`,fill:`none`,stroke:`currentColor`,"stroke-width":`2`,"stroke-linecap":`round`,"stroke-linejoin":`round`},[S(`path`,{d:`M11 4H4a2 2 0 0 0-2 2v14a2 2 0 0 0 2 2h14a2 2 0 0 0 2-2v-7`}),S(`path`,{d:`M18.5 2.5a2.121 2.121 0 0 1 3 3L12 15l-4 1 1-4 9.5-9.5z`})],-1),b(` `+o(n(T)(`@EDITOR:重命名`)),1)]),S(`button`,{class:`ctx-menu-item ctx-menu-item--danger`,onClick:It},[r[31]||=S(`svg`,{viewBox:`0 0 24 24`,width:`13`,height:`13`,fill:`none`,stroke:`currentColor`,"stroke-width":`2`,"stroke-linecap":`round`,"stroke-linejoin":`round`},[S(`polyline`,{points:`3 6 5 6 21 6`}),S(`path`,{d:`M19 6l-1 14a2 2 0 0 1-2 2H8a2 2 0 0 1-2-2L5 6`}),S(`path`,{d:`M10 11v6`}),S(`path`,{d:`M14 11v6`}),S(`path`,{d:`M9 6V4a1 1 0 0 1 1-1h4a1 1 0 0 1 1 1v2`})],-1),b(` `+o(n(T)(`@EDITOR:删除`)),1)])],4)):y(``,!0)]))],64))}}),[[`__scopeId`,`data-v-bd5cc01f`]]);export{E as default};