@tnotesjs/core 0.1.21 → 0.1.23

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 (122) hide show
  1. package/README.md +87 -87
  2. package/dist/{chunk-4MO7F7Q4.js → chunk-BSTQOJVE.js} +1 -1
  3. package/dist/{chunk-SQVHJR2Z.js → chunk-O4DCXHOV.js} +0 -3
  4. package/dist/cli/index.js +2 -2
  5. package/dist/index.js +1 -1
  6. package/dist/vitepress/config/index.js +2 -2
  7. package/package.json +3 -4
  8. package/types/config.ts +60 -61
  9. package/types/index.ts +11 -11
  10. package/types/note.ts +33 -33
  11. package/vitepress/assets/icons/icon__check.svg +3 -3
  12. package/vitepress/assets/icons/icon__clipboard.svg +7 -7
  13. package/vitepress/assets/icons/icon__close.svg +1 -1
  14. package/vitepress/assets/icons/icon__collapse.svg +1 -1
  15. package/vitepress/assets/icons/icon__confirm.svg +1 -1
  16. package/vitepress/assets/icons/icon__copy.svg +4 -4
  17. package/vitepress/assets/icons/icon__focus.svg +1 -1
  18. package/vitepress/assets/icons/icon__fold.svg +3 -3
  19. package/vitepress/assets/icons/icon__folder.svg +1 -1
  20. package/vitepress/assets/icons/icon__fullscreen.svg +1 -1
  21. package/vitepress/assets/icons/icon__fullscreen_exit.svg +1 -1
  22. package/vitepress/assets/icons/icon__github.svg +3 -3
  23. package/vitepress/assets/icons/icon__mindmap.svg +1 -1
  24. package/vitepress/assets/icons/icon__next.svg +1 -1
  25. package/vitepress/assets/icons/icon__number_gray.svg +1 -1
  26. package/vitepress/assets/icons/icon__number_purple.svg +1 -1
  27. package/vitepress/assets/icons/icon__prev.svg +1 -1
  28. package/vitepress/assets/icons/icon__restore.svg +1 -1
  29. package/vitepress/assets/icons/icon__rotate.svg +4 -4
  30. package/vitepress/assets/icons/icon__search.svg +1 -1
  31. package/vitepress/assets/icons/icon__sidebar_collapsed.svg +1 -1
  32. package/vitepress/assets/icons/icon__sidebar_opened.svg +1 -1
  33. package/vitepress/assets/icons/icon__totop.svg +5 -5
  34. package/vitepress/assets/icons/icon__vscode.svg +5 -5
  35. package/vitepress/assets/icons/icon__zoom_fit.svg +1 -1
  36. package/vitepress/assets/icons/icon__zoom_in.svg +1 -1
  37. package/vitepress/assets/icons/icon__zoom_out.svg +1 -1
  38. package/vitepress/assets/icons/icon__zoom_reset.svg +1 -1
  39. package/vitepress/assets/icons/index.ts +39 -39
  40. package/vitepress/components/BilibiliOutsidePlayer/BilibiliOutsidePlayer.vue +20 -20
  41. package/vitepress/components/CodeBlockFullscreen/CodeBlockFullscreen.vue +369 -369
  42. package/vitepress/components/CodeBlockFullscreen/index.ts +209 -213
  43. package/vitepress/components/CodeBlockFullscreen/styles.css +126 -126
  44. package/vitepress/components/Discussions/Discussions.vue +244 -211
  45. package/vitepress/components/EnWordList/EnWordList.vue +663 -543
  46. package/vitepress/components/EnWordList/RightClickMenu.vue +89 -66
  47. package/vitepress/components/Footprints/Footprints.vue +472 -377
  48. package/vitepress/components/Layout/AboutModal.vue +331 -105
  49. package/vitepress/components/Layout/AboutPanel.vue +484 -270
  50. package/vitepress/components/Layout/ContentCollapse.vue +590 -603
  51. package/vitepress/components/Layout/CustomSidebar.vue +817 -817
  52. package/vitepress/components/Layout/DocBeforeControls.vue +351 -149
  53. package/vitepress/components/Layout/DocFooter.vue +233 -233
  54. package/vitepress/components/Layout/ImagePreview.vue +484 -281
  55. package/vitepress/components/Layout/Layout.vue +744 -621
  56. package/vitepress/components/Layout/NavBarSettingsTrigger.vue +0 -2
  57. package/vitepress/components/Layout/NoteStatus.vue +140 -140
  58. package/vitepress/components/Layout/SidebarItems.vue +1083 -1083
  59. package/vitepress/components/Layout/SidebarNavBefore.vue +170 -171
  60. package/vitepress/components/Layout/SidebarResizeHandle.vue +311 -319
  61. package/vitepress/components/Layout/Swiper.vue +167 -167
  62. package/vitepress/components/Layout/ToggleFullContent.vue +47 -35
  63. package/vitepress/components/Layout/ToggleSidebar.vue +37 -26
  64. package/vitepress/components/Layout/composables/useCollapseControl.ts +88 -88
  65. package/vitepress/components/Layout/composables/useNoteConfig.ts +119 -119
  66. package/vitepress/components/Layout/composables/useNoteSave.ts +178 -178
  67. package/vitepress/components/Layout/composables/useNoteValidation.ts +85 -85
  68. package/vitepress/components/Layout/composables/useRedirect.ts +113 -113
  69. package/vitepress/components/Layout/composables/useSidebarLayout.ts +122 -122
  70. package/vitepress/components/Layout/composables/useVSCodeIntegration.ts +85 -85
  71. package/vitepress/components/Layout/homeReadme.data.ts +124 -124
  72. package/vitepress/components/LoadingPage/LoadingPage.vue +1 -6
  73. package/vitepress/components/MarkMap/MarkMap.vue +564 -405
  74. package/vitepress/components/Mermaid/Mermaid.vue +643 -365
  75. package/vitepress/components/NotesTable/NotesTable.vue +174 -98
  76. package/vitepress/components/NotesTable/README.md +67 -67
  77. package/vitepress/components/Settings/Settings.vue +711 -334
  78. package/vitepress/components/Settings/SettingsDialog.vue +1 -11
  79. package/vitepress/components/SidebarCard/MindMapView.vue +484 -484
  80. package/vitepress/components/SidebarCard/NotesTrendChart.vue +108 -108
  81. package/vitepress/components/SidebarCard/SidebarCard.vue +945 -946
  82. package/vitepress/components/Tooltip/Tooltip.vue +70 -70
  83. package/vitepress/components/constants.ts +109 -109
  84. package/vitepress/components/notesConfig.data.ts +73 -73
  85. package/vitepress/components/sidebar.data.ts +59 -59
  86. package/vitepress/components/tnotes-config.data.ts +21 -21
  87. package/vitepress/components/utils.ts +26 -26
  88. package/vitepress/config/index.ts +169 -169
  89. package/vitepress/configs/constants.ts +26 -26
  90. package/vitepress/configs/head.config.ts +25 -25
  91. package/vitepress/configs/index.ts +9 -9
  92. package/vitepress/configs/markdown-it.d.ts +23 -23
  93. package/vitepress/configs/markdown.config.ts +368 -367
  94. package/vitepress/configs/theme.config.ts +108 -108
  95. package/vitepress/plugins/buildProgressPlugin.ts +434 -434
  96. package/vitepress/plugins/getNoteByConfigIdPlugin.ts +107 -107
  97. package/vitepress/plugins/renameNotePlugin.ts +68 -68
  98. package/vitepress/plugins/sidebarStructurePlugin.ts +260 -260
  99. package/vitepress/plugins/updateConfigPlugin.ts +63 -63
  100. package/vitepress/theme/index.ts +137 -137
  101. package/vitepress/theme/styles/base.scss +66 -64
  102. package/vitepress/theme/styles/components/404.scss +31 -31
  103. package/vitepress/theme/styles/components/collapse.scss +172 -172
  104. package/vitepress/theme/styles/components/markmap.scss +101 -101
  105. package/vitepress/theme/styles/components/swiper.scss +255 -255
  106. package/vitepress/theme/styles/index.scss +25 -25
  107. package/vitepress/theme/styles/layout.scss +78 -78
  108. package/vitepress/theme/styles/utilities.scss +39 -39
  109. package/vitepress/theme/styles/vitepress-override.scss +25 -25
  110. package/vitepress/components/Discussions/Discussions.module.scss +0 -32
  111. package/vitepress/components/EnWordList/EnWordList.module.scss +0 -124
  112. package/vitepress/components/EnWordList/RightClickMenu.module.scss +0 -22
  113. package/vitepress/components/Footprints/Footprints.module.scss +0 -93
  114. package/vitepress/components/Layout/AboutModal.module.scss +0 -233
  115. package/vitepress/components/Layout/ImagePreview.module.scss +0 -201
  116. package/vitepress/components/Layout/Layout.module.scss +0 -661
  117. package/vitepress/components/Layout/ToggleFullContent.module.scss +0 -11
  118. package/vitepress/components/Layout/ToggleSidebar.module.scss +0 -11
  119. package/vitepress/components/MarkMap/MarkMap.module.scss +0 -159
  120. package/vitepress/components/Mermaid/Mermaid.module.scss +0 -275
  121. package/vitepress/components/NotesTable/NotesTable.module.scss +0 -77
  122. package/vitepress/components/Settings/Settings.module.scss +0 -375
@@ -1,319 +1,311 @@
1
- <template>
2
- <div
3
- class="sidebar-resize-handle"
4
- :class="{
5
- 'is-hidden': hidden,
6
- 'is-dragging': isDragging,
7
- 'is-fullscreen': isContentFullscreen,
8
- }"
9
- >
10
- <div
11
- v-if="!hidden"
12
- class="resize-hotspot"
13
- :aria-label="`拖动调整侧边栏宽度,当前 ${width}px`"
14
- role="separator"
15
- aria-orientation="vertical"
16
- :aria-valuemin="minWidth"
17
- :aria-valuemax="maxWidth"
18
- :aria-valuenow="width"
19
- @mousedown.prevent="startResize"
20
- ></div>
21
-
22
- <div v-if="!hidden" class="resize-indicator" aria-hidden="true"></div>
23
-
24
- <button
25
- class="sidebar-edge-toggle"
26
- type="button"
27
- :aria-label="toggleTitle"
28
- :aria-pressed="hidden"
29
- @click.stop="toggleSidebar"
30
- >
31
- <img :src="toggleIcon" alt="" />
32
- <span class="sidebar-edge-tooltip" role="tooltip">
33
- <span>{{ toggleActionText }}</span>
34
- <kbd>{{ shortcutText }}</kbd>
35
- </span>
36
- </button>
37
- </div>
38
- </template>
39
-
40
- <script setup lang="ts">
41
- import { computed, onBeforeUnmount, onMounted, ref } from 'vue'
42
-
43
- import { useSidebarLayout } from './composables/useSidebarLayout'
44
- import { icon__next, icon__prev } from '../../assets/icons'
45
-
46
- const {
47
- hidden,
48
- width,
49
- minWidth,
50
- maxWidth,
51
- initSidebarLayout,
52
- toggleSidebar,
53
- setSidebarWidth,
54
- saveSidebarWidth,
55
- } = useSidebarLayout()
56
-
57
- const isDragging = ref(false)
58
- const isContentFullscreen = ref(false)
59
- const shortcutText = ref('Ctrl + Alt + ,')
60
- let fullscreenObserver: MutationObserver | null = null
61
-
62
- const toggleIcon = computed(() => (hidden.value ? icon__next : icon__prev))
63
- const toggleActionText = computed(() =>
64
- hidden.value ? '展开侧边栏' : '收起侧边栏',
65
- )
66
- const toggleTitle = computed(
67
- () => `${toggleActionText.value}\n${shortcutText.value}`,
68
- )
69
-
70
- onMounted(() => {
71
- initSidebarLayout()
72
- shortcutText.value = getShortcutText()
73
- updateContentFullscreen()
74
- fullscreenObserver = new MutationObserver(updateContentFullscreen)
75
- fullscreenObserver.observe(document.documentElement, {
76
- attributes: true,
77
- attributeFilter: ['class'],
78
- })
79
- window.addEventListener('keydown', handleShortcut)
80
- })
81
-
82
- onBeforeUnmount(() => {
83
- window.removeEventListener('keydown', handleShortcut)
84
- fullscreenObserver?.disconnect()
85
- fullscreenObserver = null
86
- stopResize()
87
- })
88
-
89
- function startResize(event: MouseEvent) {
90
- if (hidden.value || event.button !== 0) return
91
-
92
- isDragging.value = true
93
- document.body.classList.add('is-sidebar-resizing')
94
- window.addEventListener('mousemove', resize)
95
- window.addEventListener('mouseup', stopResize)
96
- setSidebarWidth(event.clientX)
97
- }
98
-
99
- function resize(event: MouseEvent) {
100
- if (!isDragging.value) return
101
-
102
- setSidebarWidth(event.clientX)
103
- }
104
-
105
- function stopResize() {
106
- if (!isDragging.value) return
107
-
108
- isDragging.value = false
109
- document.body.classList.remove('is-sidebar-resizing')
110
- window.removeEventListener('mousemove', resize)
111
- window.removeEventListener('mouseup', stopResize)
112
- saveSidebarWidth()
113
- }
114
-
115
- function handleShortcut(event: KeyboardEvent) {
116
- if (!isToggleShortcut(event) || isEditableTarget(event.target)) return
117
-
118
- event.preventDefault()
119
- toggleSidebar()
120
- }
121
-
122
- function updateContentFullscreen() {
123
- isContentFullscreen.value =
124
- document.documentElement.classList.contains('content-fullscreen')
125
- }
126
-
127
- function isToggleShortcut(event: KeyboardEvent): boolean {
128
- return (
129
- (event.ctrlKey || event.metaKey) && event.altKey && event.code === 'Comma'
130
- )
131
- }
132
-
133
- function getShortcutText(): string {
134
- return isMacPlatform() ? 'Cmd + Option + ,' : 'Ctrl + Alt + ,'
135
- }
136
-
137
- function isMacPlatform(): boolean {
138
- if (typeof navigator === 'undefined') return false
139
-
140
- return /Mac|iPhone|iPad|iPod/i.test(navigator.platform)
141
- }
142
-
143
- function isEditableTarget(target: EventTarget | null): boolean {
144
- if (!(target instanceof HTMLElement)) return false
145
-
146
- const tagName = target.tagName.toLowerCase()
147
- if (tagName === 'input' || tagName === 'textarea' || tagName === 'select') {
148
- return true
149
- }
150
-
151
- return target.isContentEditable || !!target.closest('[contenteditable="true"]')
152
- }
153
- </script>
154
-
155
- <style scoped>
156
- .sidebar-resize-handle {
157
- position: fixed;
158
- top: 0;
159
- bottom: 0;
160
- left: calc(var(--tn-sidebar-width, 260px) - 5px);
161
- z-index: 30;
162
- width: 10px;
163
- cursor: col-resize;
164
- }
165
-
166
- .sidebar-resize-handle::before {
167
- position: absolute;
168
- top: var(--vp-nav-height);
169
- bottom: 0;
170
- left: 4px;
171
- width: 2px;
172
- background: var(--vp-c-brand-1);
173
- border-radius: 999px;
174
- box-shadow: 0 0 0 1px var(--vp-c-brand-soft);
175
- content: '';
176
- opacity: 0;
177
- pointer-events: none;
178
- transition: opacity 0.18s ease;
179
- }
180
-
181
- .resize-hotspot {
182
- position: absolute;
183
- top: var(--vp-nav-height);
184
- right: 0;
185
- bottom: 0;
186
- left: 0;
187
- }
188
-
189
- .resize-indicator {
190
- position: absolute;
191
- top: 50%;
192
- left: 50%;
193
- width: 4px;
194
- height: 28px;
195
- border-right: 1px solid var(--vp-c-brand-1);
196
- border-left: 1px solid var(--vp-c-brand-1);
197
- opacity: 0;
198
- pointer-events: none;
199
- transform: translate(-50%, -50%);
200
- transition: opacity 0.18s ease;
201
- }
202
-
203
- .sidebar-edge-toggle {
204
- position: absolute;
205
- top: 220px;
206
- left: -2px;
207
- display: inline-flex;
208
- align-items: center;
209
- justify-content: center;
210
- width: 14px;
211
- height: 44px;
212
- padding: 0;
213
- color: var(--vp-c-text-2);
214
- background: var(--vp-c-bg);
215
- border: 1px solid var(--vp-c-divider);
216
- border-radius: 7px;
217
- box-shadow: var(--vp-shadow-2);
218
- cursor: pointer;
219
- opacity: 0;
220
- pointer-events: none;
221
- transition:
222
- opacity 0.18s ease,
223
- border-color 0.18s ease,
224
- background-color 0.18s ease;
225
- }
226
-
227
- .sidebar-edge-toggle img {
228
- width: 10px;
229
- height: 10px;
230
- }
231
-
232
- .sidebar-edge-tooltip {
233
- position: absolute;
234
- top: 50%;
235
- left: calc(100% + 8px);
236
- display: flex;
237
- flex-direction: column;
238
- gap: 2px;
239
- min-width: 128px;
240
- padding: 7px 9px;
241
- color: var(--vp-c-text-1);
242
- background: var(--vp-c-bg-elv);
243
- border: 1px solid var(--vp-c-divider);
244
- border-radius: 6px;
245
- box-shadow: var(--vp-shadow-2);
246
- font-size: 12px;
247
- line-height: 18px;
248
- opacity: 0;
249
- pointer-events: none;
250
- text-align: left;
251
- transform: translate(2px, -50%);
252
- transition:
253
- opacity 0.16s ease,
254
- transform 0.16s ease;
255
- white-space: nowrap;
256
- }
257
-
258
- .sidebar-edge-tooltip kbd {
259
- color: var(--vp-c-text-2);
260
- font-family: var(--vp-font-family-mono);
261
- font-size: 11px;
262
- }
263
-
264
- .sidebar-edge-toggle:hover .sidebar-edge-tooltip,
265
- .sidebar-edge-toggle:focus-visible .sidebar-edge-tooltip {
266
- opacity: 1;
267
- transform: translate(0, -50%);
268
- }
269
-
270
- .sidebar-resize-handle:hover::before,
271
- .sidebar-resize-handle.is-dragging::before,
272
- .sidebar-resize-handle:hover .resize-indicator,
273
- .sidebar-resize-handle.is-dragging .resize-indicator,
274
- .sidebar-resize-handle:hover .sidebar-edge-toggle,
275
- .sidebar-resize-handle.is-dragging .sidebar-edge-toggle,
276
- .sidebar-resize-handle.is-hidden .sidebar-edge-toggle {
277
- opacity: 1;
278
- pointer-events: auto;
279
- }
280
-
281
- .sidebar-edge-toggle:hover {
282
- color: var(--vp-c-brand-1);
283
- background: var(--vp-c-bg-soft);
284
- border-color: var(--vp-c-brand-1);
285
- }
286
-
287
- .sidebar-resize-handle.is-hidden {
288
- left: 0;
289
- width: 14px;
290
- cursor: default;
291
- }
292
-
293
- .sidebar-resize-handle.is-hidden::before,
294
- .sidebar-resize-handle.is-hidden .resize-indicator {
295
- display: none;
296
- }
297
-
298
- .sidebar-resize-handle.is-hidden .sidebar-edge-toggle {
299
- left: 0;
300
- border-left-color: var(--vp-c-divider);
301
- border-radius: 0 7px 7px 0;
302
- }
303
-
304
- :global(body.is-sidebar-resizing),
305
- :global(body.is-sidebar-resizing *) {
306
- cursor: col-resize !important;
307
- user-select: none !important;
308
- }
309
-
310
- .sidebar-resize-handle.is-fullscreen {
311
- display: none;
312
- }
313
-
314
- @media (max-width: 959px) {
315
- .sidebar-resize-handle {
316
- display: none;
317
- }
318
- }
319
- </style>
1
+ <template>
2
+ <div
3
+ class="sidebar-resize-handle"
4
+ :class="{
5
+ 'is-hidden': hidden,
6
+ 'is-dragging': isDragging,
7
+ 'is-fullscreen': isContentFullscreen,
8
+ }"
9
+ >
10
+ <div
11
+ v-if="!hidden"
12
+ class="resize-hotspot"
13
+ @mousedown.prevent="startResize"
14
+ ></div>
15
+
16
+ <div v-if="!hidden" class="resize-indicator"></div>
17
+
18
+ <button
19
+ class="sidebar-edge-toggle"
20
+ type="button"
21
+ @click.stop="toggleSidebar"
22
+ >
23
+ <img :src="toggleIcon" alt="" />
24
+ <span class="sidebar-edge-tooltip">
25
+ <span>{{ toggleActionText }}</span>
26
+ <kbd>{{ shortcutText }}</kbd>
27
+ </span>
28
+ </button>
29
+ </div>
30
+ </template>
31
+
32
+ <script setup lang="ts">
33
+ import { computed, onBeforeUnmount, onMounted, ref } from 'vue'
34
+
35
+ import { useSidebarLayout } from './composables/useSidebarLayout'
36
+ import { icon__next, icon__prev } from '../../assets/icons'
37
+
38
+ const {
39
+ hidden,
40
+ width,
41
+ minWidth,
42
+ maxWidth,
43
+ initSidebarLayout,
44
+ toggleSidebar,
45
+ setSidebarWidth,
46
+ saveSidebarWidth,
47
+ } = useSidebarLayout()
48
+
49
+ const isDragging = ref(false)
50
+ const isContentFullscreen = ref(false)
51
+ const shortcutText = ref('Ctrl + Alt + ,')
52
+ let fullscreenObserver: MutationObserver | null = null
53
+
54
+ const toggleIcon = computed(() => (hidden.value ? icon__next : icon__prev))
55
+ const toggleActionText = computed(() =>
56
+ hidden.value ? '展开侧边栏' : '收起侧边栏',
57
+ )
58
+ const toggleTitle = computed(
59
+ () => `${toggleActionText.value}\n${shortcutText.value}`,
60
+ )
61
+
62
+ onMounted(() => {
63
+ initSidebarLayout()
64
+ shortcutText.value = getShortcutText()
65
+ updateContentFullscreen()
66
+ fullscreenObserver = new MutationObserver(updateContentFullscreen)
67
+ fullscreenObserver.observe(document.documentElement, {
68
+ attributes: true,
69
+ attributeFilter: ['class'],
70
+ })
71
+ window.addEventListener('keydown', handleShortcut)
72
+ })
73
+
74
+ onBeforeUnmount(() => {
75
+ window.removeEventListener('keydown', handleShortcut)
76
+ fullscreenObserver?.disconnect()
77
+ fullscreenObserver = null
78
+ stopResize()
79
+ })
80
+
81
+ function startResize(event: MouseEvent) {
82
+ if (hidden.value || event.button !== 0) return
83
+
84
+ isDragging.value = true
85
+ document.body.classList.add('is-sidebar-resizing')
86
+ window.addEventListener('mousemove', resize)
87
+ window.addEventListener('mouseup', stopResize)
88
+ setSidebarWidth(event.clientX)
89
+ }
90
+
91
+ function resize(event: MouseEvent) {
92
+ if (!isDragging.value) return
93
+
94
+ setSidebarWidth(event.clientX)
95
+ }
96
+
97
+ function stopResize() {
98
+ if (!isDragging.value) return
99
+
100
+ isDragging.value = false
101
+ document.body.classList.remove('is-sidebar-resizing')
102
+ window.removeEventListener('mousemove', resize)
103
+ window.removeEventListener('mouseup', stopResize)
104
+ saveSidebarWidth()
105
+ }
106
+
107
+ function handleShortcut(event: KeyboardEvent) {
108
+ if (!isToggleShortcut(event) || isEditableTarget(event.target)) return
109
+
110
+ event.preventDefault()
111
+ toggleSidebar()
112
+ }
113
+
114
+ function updateContentFullscreen() {
115
+ isContentFullscreen.value =
116
+ document.documentElement.classList.contains('content-fullscreen')
117
+ }
118
+
119
+ function isToggleShortcut(event: KeyboardEvent): boolean {
120
+ return (
121
+ (event.ctrlKey || event.metaKey) && event.altKey && event.code === 'Comma'
122
+ )
123
+ }
124
+
125
+ function getShortcutText(): string {
126
+ return isMacPlatform() ? 'Cmd + Option + ,' : 'Ctrl + Alt + ,'
127
+ }
128
+
129
+ function isMacPlatform(): boolean {
130
+ if (typeof navigator === 'undefined') return false
131
+
132
+ return /Mac|iPhone|iPad|iPod/i.test(navigator.platform)
133
+ }
134
+
135
+ function isEditableTarget(target: EventTarget | null): boolean {
136
+ if (!(target instanceof HTMLElement)) return false
137
+
138
+ const tagName = target.tagName.toLowerCase()
139
+ if (tagName === 'input' || tagName === 'textarea' || tagName === 'select') {
140
+ return true
141
+ }
142
+
143
+ return target.isContentEditable || !!target.closest('[contenteditable="true"]')
144
+ }
145
+ </script>
146
+
147
+ <style scoped>
148
+ .sidebar-resize-handle {
149
+ position: fixed;
150
+ top: 0;
151
+ bottom: 0;
152
+ left: calc(var(--tn-sidebar-width, 260px) - 5px);
153
+ z-index: 30;
154
+ width: 10px;
155
+ cursor: col-resize;
156
+ }
157
+
158
+ .sidebar-resize-handle::before {
159
+ position: absolute;
160
+ top: var(--vp-nav-height);
161
+ bottom: 0;
162
+ left: 4px;
163
+ width: 2px;
164
+ background: var(--vp-c-brand-1);
165
+ border-radius: 999px;
166
+ box-shadow: 0 0 0 1px var(--vp-c-brand-soft);
167
+ content: '';
168
+ opacity: 0;
169
+ pointer-events: none;
170
+ transition: opacity 0.18s ease;
171
+ }
172
+
173
+ .resize-hotspot {
174
+ position: absolute;
175
+ top: var(--vp-nav-height);
176
+ right: 0;
177
+ bottom: 0;
178
+ left: 0;
179
+ }
180
+
181
+ .resize-indicator {
182
+ position: absolute;
183
+ top: 50%;
184
+ left: 50%;
185
+ width: 4px;
186
+ height: 28px;
187
+ border-right: 1px solid var(--vp-c-brand-1);
188
+ border-left: 1px solid var(--vp-c-brand-1);
189
+ opacity: 0;
190
+ pointer-events: none;
191
+ transform: translate(-50%, -50%);
192
+ transition: opacity 0.18s ease;
193
+ }
194
+
195
+ .sidebar-edge-toggle {
196
+ position: absolute;
197
+ top: 220px;
198
+ left: -2px;
199
+ display: inline-flex;
200
+ align-items: center;
201
+ justify-content: center;
202
+ width: 14px;
203
+ height: 44px;
204
+ padding: 0;
205
+ color: var(--vp-c-text-2);
206
+ background: var(--vp-c-bg);
207
+ border: 1px solid var(--vp-c-divider);
208
+ border-radius: 7px;
209
+ box-shadow: var(--vp-shadow-2);
210
+ cursor: pointer;
211
+ opacity: 0;
212
+ pointer-events: none;
213
+ transition:
214
+ opacity 0.18s ease,
215
+ border-color 0.18s ease,
216
+ background-color 0.18s ease;
217
+ }
218
+
219
+ .sidebar-edge-toggle img {
220
+ width: 10px;
221
+ height: 10px;
222
+ }
223
+
224
+ .sidebar-edge-tooltip {
225
+ position: absolute;
226
+ top: 50%;
227
+ left: calc(100% + 8px);
228
+ display: flex;
229
+ flex-direction: column;
230
+ gap: 2px;
231
+ min-width: 128px;
232
+ padding: 7px 9px;
233
+ color: var(--vp-c-text-1);
234
+ background: var(--vp-c-bg-elv);
235
+ border: 1px solid var(--vp-c-divider);
236
+ border-radius: 6px;
237
+ box-shadow: var(--vp-shadow-2);
238
+ font-size: 12px;
239
+ line-height: 18px;
240
+ opacity: 0;
241
+ pointer-events: none;
242
+ text-align: left;
243
+ transform: translate(2px, -50%);
244
+ transition:
245
+ opacity 0.16s ease,
246
+ transform 0.16s ease;
247
+ white-space: nowrap;
248
+ }
249
+
250
+ .sidebar-edge-tooltip kbd {
251
+ color: var(--vp-c-text-2);
252
+ font-family: var(--vp-font-family-mono);
253
+ font-size: 11px;
254
+ }
255
+
256
+ .sidebar-edge-toggle:hover .sidebar-edge-tooltip,
257
+ .sidebar-edge-toggle:focus-visible .sidebar-edge-tooltip {
258
+ opacity: 1;
259
+ transform: translate(0, -50%);
260
+ }
261
+
262
+ .sidebar-resize-handle:hover::before,
263
+ .sidebar-resize-handle.is-dragging::before,
264
+ .sidebar-resize-handle:hover .resize-indicator,
265
+ .sidebar-resize-handle.is-dragging .resize-indicator,
266
+ .sidebar-resize-handle:hover .sidebar-edge-toggle,
267
+ .sidebar-resize-handle.is-dragging .sidebar-edge-toggle,
268
+ .sidebar-resize-handle.is-hidden .sidebar-edge-toggle {
269
+ opacity: 1;
270
+ pointer-events: auto;
271
+ }
272
+
273
+ .sidebar-edge-toggle:hover {
274
+ color: var(--vp-c-brand-1);
275
+ background: var(--vp-c-bg-soft);
276
+ border-color: var(--vp-c-brand-1);
277
+ }
278
+
279
+ .sidebar-resize-handle.is-hidden {
280
+ left: 0;
281
+ width: 14px;
282
+ cursor: default;
283
+ }
284
+
285
+ .sidebar-resize-handle.is-hidden::before,
286
+ .sidebar-resize-handle.is-hidden .resize-indicator {
287
+ display: none;
288
+ }
289
+
290
+ .sidebar-resize-handle.is-hidden .sidebar-edge-toggle {
291
+ left: 0;
292
+ border-left-color: var(--vp-c-divider);
293
+ border-radius: 0 7px 7px 0;
294
+ }
295
+
296
+ :global(body.is-sidebar-resizing),
297
+ :global(body.is-sidebar-resizing *) {
298
+ cursor: col-resize !important;
299
+ user-select: none !important;
300
+ }
301
+
302
+ .sidebar-resize-handle.is-fullscreen {
303
+ display: none;
304
+ }
305
+
306
+ @media (max-width: 959px) {
307
+ .sidebar-resize-handle {
308
+ display: none;
309
+ }
310
+ }
311
+ </style>