vome-core 0.1.82 → 0.1.83

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 (83) hide show
  1. package/dist/admin/components/ui/avatar/index.js +1 -1
  2. package/dist/admin/components/ui/badge/index.d.ts +1 -1
  3. package/dist/admin/components/ui/badge/index.js +1 -1
  4. package/dist/admin/components/ui/button/index.d.ts +1 -1
  5. package/dist/admin/components/ui/button/index.js +1 -1
  6. package/dist/admin/components/ui/checkbox/index.js +1 -1
  7. package/dist/admin/components/ui/dialog/index.js +1 -1
  8. package/dist/admin/components/ui/dropdown-menu/index.js +1 -1
  9. package/dist/admin/components/ui/input/index.js +1 -1
  10. package/dist/admin/components/ui/label/index.js +1 -1
  11. package/dist/admin/components/ui/scroll-area/index.js +1 -1
  12. package/dist/admin/components/ui/select/index.js +1 -1
  13. package/dist/admin/components/ui/separator/index.js +1 -1
  14. package/dist/admin/components/ui/sheet/index.js +1 -1
  15. package/dist/admin/components/ui/sonner/index.js +1 -1
  16. package/dist/admin/components/ui/table/index.js +1 -1
  17. package/dist/admin/components/ui/tabs/index.js +1 -1
  18. package/dist/admin/components/ui/tooltip/index.js +1 -1
  19. package/dist/admin/components/vm-role-picker.vue +10 -3
  20. package/dist/admin/crud/components/vm-richtext-extensions.js +1 -1
  21. package/dist/admin/crud/config.js +1 -1
  22. package/dist/admin/crud/confirm.js +1 -1
  23. package/dist/admin/crud/crud-page-request.js +1 -1
  24. package/dist/admin/crud/dict.js +1 -1
  25. package/dist/admin/crud/export-fetch.js +1 -1
  26. package/dist/admin/crud/key.js +1 -1
  27. package/dist/admin/crud/plugins.js +1 -1
  28. package/dist/admin/crud/span.js +1 -1
  29. package/dist/admin/crud/style.js +1 -1
  30. package/dist/admin/crud/validate.js +1 -1
  31. package/dist/admin/directives/perm.js +1 -1
  32. package/dist/admin/hooks/useUpload.js +1 -1
  33. package/dist/admin/index.d.ts +0 -5
  34. package/dist/admin/index.js +0 -4
  35. package/dist/admin/lib/browser.js +1 -1
  36. package/dist/admin/lib/cn.js +1 -1
  37. package/dist/admin/lib/dialog-float.js +1 -1
  38. package/dist/admin/lib/export-excel.js +1 -1
  39. package/dist/admin/lib/file-preview.js +6 -2
  40. package/dist/admin/lib/import-excel.js +1 -1
  41. package/dist/admin/lib/json.js +1 -1
  42. package/dist/admin/lib/menu.js +1 -1
  43. package/dist/admin/lib/micro-locale.js +1 -1
  44. package/dist/admin/lib/micro-theme.js +1 -1
  45. package/dist/admin/lib/setup-crud-defaults.js +1 -1
  46. package/dist/admin/lib/shell.js +1 -1
  47. package/dist/admin/lib/theme-color-options.js +1 -1
  48. package/dist/admin/lib/tree.js +1 -1
  49. package/dist/admin/lib/upload.js +1 -1
  50. package/dist/admin/lib/video-frame.js +1 -1
  51. package/dist/admin/router/create.js +1 -1
  52. package/dist/admin/router/guards.js +1 -1
  53. package/dist/admin/themes/dark.js +1 -1
  54. package/dist/admin/themes/index.js +1 -1
  55. package/dist/admin/themes/light.js +1 -1
  56. package/dist/ai/index.js +298 -9
  57. package/dist/client/configure.js +13 -4
  58. package/dist/client/vite-admin.d.ts +16 -1
  59. package/dist/client/vite-admin.js +33 -13
  60. package/dist/client/vite-auto-import.js +3 -3
  61. package/dist/client/vite-resolve.js +28 -4
  62. package/dist/index.js +1 -1
  63. package/dist/server/index.js +1 -1
  64. package/dist/shared/datetime-picker.js +1 -1
  65. package/dist/shared/excel.js +1 -1
  66. package/dist/shared/index.js +1 -1
  67. package/dist/shared/locale-json.js +1 -1
  68. package/dist/shared/tree.js +1 -1
  69. package/package.json +1 -1
  70. package/dist/admin/components/layout/vm-app-header.vue +0 -341
  71. package/dist/admin/components/layout/vm-app-sidebar.vue +0 -187
  72. package/dist/admin/components/layout/vm-sidebar-flyout.vue +0 -268
  73. package/dist/admin/components/layout/vm-sidebar-nav-item.vue +0 -490
  74. package/dist/admin/components/layout/vm-sidebar-nav.vue +0 -104
  75. package/dist/admin/components/layout/vm-tags-view.vue +0 -233
  76. package/dist/admin/lib/document-title.d.ts +0 -6
  77. package/dist/admin/lib/document-title.js +0 -1
  78. package/dist/admin/stores/dict.d.ts +0 -13
  79. package/dist/admin/stores/dict.js +0 -1
  80. package/dist/admin/stores/locale.d.ts +0 -3
  81. package/dist/admin/stores/locale.js +0 -1
  82. package/dist/admin/stores/theme.d.ts +0 -1
  83. package/dist/admin/stores/theme.js +0 -1
@@ -1,187 +0,0 @@
1
- <template>
2
- <aside v-if="!browser.isMini" class="vm-sidebar" :class="{ 'is-collapsed': collapsed }">
3
- <div class="vm-sidebar__brand">
4
- <img :src="logoSrc" alt="" class="vm-sidebar__logo" />
5
- <span v-if="!collapsed" class="vm-sidebar__title">{{ appName }}</span>
6
- </div>
7
- <vm-sidebar-nav :menus="user.navMenus" :collapsed="collapsed" />
8
- </aside>
9
-
10
- <!-- 移动端抽屉:Sheet 传送到 body,样式用下方非 scoped 全局类 -->
11
- <Sheet :open="app.mobileOpen" @update:open="app.setMobileOpen">
12
- <SheetContent side="left" class="vm-sidebar-sheet">
13
- <SheetHeader class="vm-sidebar-sheet__head">
14
- <img :src="logoSrc" alt="" class="vm-sidebar-sheet__logo" />
15
- <SheetTitle class="vm-sidebar-sheet__title">{{ appName }}</SheetTitle>
16
- </SheetHeader>
17
- <div class="vm-sidebar-sheet__nav">
18
- <vm-sidebar-nav :menus="user.navMenus" mobile />
19
- </div>
20
- </SheetContent>
21
- </Sheet>
22
- </template>
23
-
24
- <script setup lang="ts">
25
- import { getAdminShellBranding } from '../../lib/shell'
26
-
27
- defineOptions({ name: 'vm-app-sidebar' })
28
-
29
- const app = useAppStore()
30
- const user = useUserStore()
31
- const route = useRoute()
32
- const { browser } = useBrowser()
33
-
34
- const collapsed = computed(() => !browser.isMini && app.sidebarFold)
35
- const shell = getAdminShellBranding()
36
- /** 彩底侧栏始终用浅色 logo */
37
- const logoSrc = shell.logoLight
38
- const appName = computed(() => shell.appName)
39
-
40
- // 回到桌面断点时关掉抽屉;勿在 isMini 下监听 screen 变化强关(开抽屉去滚动条会触发断点抖动)
41
- watch(
42
- () => browser.isMini,
43
- (mini) => {
44
- if (!mini) app.setMobileOpen(false)
45
- },
46
- )
47
-
48
- watch(
49
- () => route.path,
50
- () => {
51
- if (browser.isMini) app.setMobileOpen(false)
52
- },
53
- )
54
- </script>
55
-
56
- <style lang="scss" scoped>
57
- .vm-sidebar {
58
- position: relative;
59
- z-index: 20;
60
- display: flex;
61
- width: 268px;
62
- height: 100%;
63
- flex-shrink: 0;
64
- flex-direction: column;
65
- overflow: visible;
66
- background: var(--sidebar);
67
- color: var(--sidebar-foreground);
68
- transition: width 0.2s ease;
69
-
70
- &.is-collapsed {
71
- width: 80px;
72
- overflow: visible;
73
-
74
- .vm-sidebar__logo {
75
- height: 28px;
76
- }
77
- }
78
- }
79
-
80
- .vm-sidebar__brand {
81
- display: flex;
82
- height: 84px;
83
- flex-shrink: 0;
84
- align-items: center;
85
- gap: 12px;
86
- padding: 0 14px;
87
-
88
- .is-collapsed & {
89
- justify-content: center;
90
- padding: 0;
91
- }
92
- }
93
-
94
- .vm-sidebar__logo {
95
- height: 24px;
96
- object-fit: contain;
97
- flex-shrink: 0;
98
- }
99
-
100
- .vm-sidebar__title {
101
- display: flex;
102
- height: 60px;
103
- align-items: center;
104
- overflow: hidden;
105
- text-overflow: ellipsis;
106
- white-space: nowrap;
107
- /* 与 60px logo 视觉同高(大写字面接近 logo) */
108
- font-size: 28px !important;
109
- font-weight: 1000 !important;
110
- line-height: 1 !important;
111
- letter-spacing: -0.04em;
112
- color: #fff !important;
113
- }
114
- </style>
115
-
116
- <!-- Sheet 经 Portal 挂到 body,scoped 无法稳定命中,必须用全局类 -->
117
- <style lang="scss">
118
- .vm-sidebar-sheet {
119
- width: min(280px, 85vw) !important;
120
- max-width: 85vw !important;
121
- height: 100% !important;
122
- padding: 0 !important;
123
- gap: 0 !important;
124
- border: none !important;
125
- background: var(--sidebar) !important;
126
- color: #fff !important;
127
- box-shadow: 8px 0 32px rgba(0, 0, 0, 0.18) !important;
128
-
129
- /* 关闭按钮:蓝底上用白 */
130
- > button {
131
- color: rgba(255, 255, 255, 0.92) !important;
132
- opacity: 1;
133
-
134
- &:hover {
135
- opacity: 0.85;
136
- background: rgba(255, 255, 255, 0.12);
137
- }
138
- }
139
- }
140
-
141
- .vm-sidebar-sheet__head {
142
- display: flex !important;
143
- height: 64px;
144
- flex-shrink: 0;
145
- flex-direction: row !important;
146
- align-items: center;
147
- gap: 10px;
148
- padding: 0 44px 0 16px;
149
- margin: 0 !important;
150
- text-align: left !important;
151
- border-bottom: 1px solid rgba(255, 255, 255, 0.12);
152
- }
153
-
154
- .vm-sidebar-sheet__logo {
155
- height: 28px;
156
- flex-shrink: 0;
157
- object-fit: contain;
158
- }
159
-
160
- .vm-sidebar-sheet__title {
161
- display: flex !important;
162
- height: auto !important;
163
- align-items: center;
164
- overflow: hidden;
165
- font-size: 22px !important;
166
- font-weight: 1000 !important;
167
- line-height: 1 !important;
168
- letter-spacing: -0.04em;
169
- text-transform: uppercase;
170
- white-space: nowrap;
171
- text-overflow: ellipsis;
172
- color: #fff !important;
173
- }
174
-
175
- .vm-sidebar-sheet__nav {
176
- flex: 1;
177
- min-height: 0;
178
- overflow: auto;
179
- /* 深色侧栏滚动条用 token 覆盖全局色 */
180
- --scrollbar-thumb: rgba(255, 255, 255, 0.35);
181
- --scrollbar-thumb-hover: rgba(255, 255, 255, 0.55);
182
-
183
- .vm-nav {
184
- height: 100%;
185
- }
186
- }
187
- </style>
@@ -1,268 +0,0 @@
1
- <template>
2
- <div
3
- class="vm-flyout"
4
- :class="{ 'is-nested': nested }"
5
- :style="panelStyle"
6
- @mouseenter="emit('enter')"
7
- @mouseleave="emit('leave')"
8
- >
9
- <div
10
- v-for="node in items"
11
- :key="node.id"
12
- class="vm-flyout__row"
13
- :class="{
14
- 'is-active': isActiveLeaf(node) || containsActive(node),
15
- 'is-open': openId === node.id,
16
- }"
17
- @mouseenter="onRowEnter(node)"
18
- @mouseleave="onRowLeave(node)"
19
- >
20
- <RouterLink
21
- v-if="isLeaf(node) && node.router"
22
- :to="node.router"
23
- class="vm-flyout__link"
24
- @click="onLeafClick(node)"
25
- >
26
- <vm-ri-icon v-if="hasIcon(node)" :name="iconOf(node)" class="vm-flyout__icon" />
27
- <span class="vm-flyout__label">{{ menuLabelOf(node) }}</span>
28
- </RouterLink>
29
-
30
- <button v-else type="button" class="vm-flyout__link">
31
- <vm-ri-icon v-if="hasIcon(node)" :name="iconOf(node)" class="vm-flyout__icon" />
32
- <span class="vm-flyout__label">{{ menuLabelOf(node) }}</span>
33
- <i class="ri-arrow-right-s-line vm-flyout__chevron" />
34
- </button>
35
-
36
- <vm-sidebar-flyout
37
- v-if="isDir(node) && openId === node.id"
38
- nested
39
- :items="kids(node)"
40
- :parent-id="node.id"
41
- @enter="clearLeaveTimer"
42
- @leave="scheduleCloseRow"
43
- @navigate="emit('navigate')"
44
- />
45
- </div>
46
- </div>
47
- </template>
48
-
49
- <script setup lang="ts">
50
- import { useLocaleStore } from '../../stores/locale'
51
-
52
- defineOptions({ name: 'vm-sidebar-flyout' })
53
-
54
- const props = defineProps<{
55
- items: MenuTreeNode[]
56
- /** 浮窗相对视口定位(根级);嵌套级不传 */
57
- anchor?: { top: number; left: number }
58
- nested?: boolean
59
- parentId?: number | null
60
- }>()
61
-
62
- const emit = defineEmits<{
63
- enter: []
64
- leave: []
65
- navigate: []
66
- }>()
67
-
68
- const locale = useLocaleStore()
69
- function menuLabelOf(node: MenuTreeNode) {
70
- return locale.tMenu(node)
71
- }
72
-
73
- const route = useRoute()
74
-
75
- const PENDING_KEY = 'sidebar-pending-leaf'
76
- const DEEP_KEY = 'sidebar-deep-focus'
77
- const pendingLeafId = inject<Ref<number | null>>(PENDING_KEY)!
78
- const deepFocusId = inject<Ref<number | null>>(DEEP_KEY)!
79
- if (!pendingLeafId || !deepFocusId) {
80
- throw new Error('[vm-sidebar-flyout] 缺少 sidebar provide')
81
- }
82
-
83
- const openId = ref<number | null>(null)
84
- let leaveTimer: ReturnType<typeof setTimeout> | null = null
85
-
86
- const panelStyle = computed(() => {
87
- if (props.nested || !props.anchor) return undefined
88
- return {
89
- top: `${props.anchor.top}px`,
90
- left: `${props.anchor.left}px`,
91
- } as Record<string, string>
92
- })
93
-
94
- function kids(item: MenuTreeNode) {
95
- return (item.children ?? []).filter(
96
- (c) => c.isShow !== false && Number(c.type) !== 2,
97
- )
98
- }
99
-
100
- function isDir(item: MenuTreeNode) {
101
- return Number(item.type) === 0 || kids(item).length > 0
102
- }
103
-
104
- function isLeaf(item: MenuTreeNode) {
105
- return Number(item.type) === 1 && Boolean(item.router)
106
- }
107
-
108
- /** 仅配置了 icon 才展示,不占空白位 */
109
- function hasIcon(item: MenuTreeNode) {
110
- return Boolean(item.icon && String(item.icon).trim())
111
- }
112
-
113
- function iconOf(item: MenuTreeNode) {
114
- const raw = String(item.icon || '').trim()
115
- return raw.startsWith('ri-') ? raw : `ri-${raw}`
116
- }
117
-
118
- function isActiveLeaf(item: MenuTreeNode) {
119
- if (!item.router) return false
120
- return route.path === item.router || route.path.startsWith(`${item.router}/`)
121
- }
122
-
123
- function containsActive(item: MenuTreeNode): boolean {
124
- if (isActiveLeaf(item)) return true
125
- return kids(item).some((c) => containsActive(c))
126
- }
127
-
128
- function clearLeaveTimer() {
129
- if (leaveTimer) {
130
- clearTimeout(leaveTimer)
131
- leaveTimer = null
132
- }
133
- }
134
-
135
- function onRowEnter(node: MenuTreeNode) {
136
- clearLeaveTimer()
137
- if (isDir(node)) openId.value = node.id
138
- else openId.value = null
139
- }
140
-
141
- function onRowLeave(node: MenuTreeNode) {
142
- if (!isDir(node)) return
143
- leaveTimer = setTimeout(() => {
144
- if (openId.value === node.id) openId.value = null
145
- }, 120)
146
- }
147
-
148
- function scheduleCloseRow() {
149
- leaveTimer = setTimeout(() => {
150
- openId.value = null
151
- }, 120)
152
- }
153
-
154
- function onLeafClick(node: MenuTreeNode) {
155
- pendingLeafId.value = node.id
156
- deepFocusId.value = props.parentId ?? null
157
- emit('navigate')
158
- }
159
-
160
- onBeforeUnmount(() => clearLeaveTimer())
161
- </script>
162
-
163
- <style lang="scss" scoped>
164
- .vm-flyout {
165
- position: fixed;
166
- z-index: 80;
167
- box-sizing: border-box;
168
- min-width: 168px;
169
- max-width: 240px;
170
- padding: 6px;
171
- border-radius: 12px;
172
- background: #fff;
173
- box-shadow: 0 10px 30px rgba(40, 50, 120, 0.14);
174
-
175
- /* 嵌套级:相对当前行右侧展开,级间留缝 */
176
- &.is-nested {
177
- position: absolute;
178
- top: -6px;
179
- left: calc(100% + 10px);
180
- margin: 0;
181
-
182
- /* 透明桥:盖住级间空隙,鼠标移动不中断 */
183
- &::before {
184
- content: '';
185
- position: absolute;
186
- top: 0;
187
- bottom: 0;
188
- left: -10px;
189
- width: 10px;
190
- }
191
- }
192
- }
193
-
194
- :global(.dark) .vm-flyout {
195
- background: var(--card);
196
- box-shadow: 0 10px 30px rgba(0, 0, 0, 0.4);
197
- }
198
-
199
- .vm-flyout__row {
200
- position: relative;
201
- }
202
-
203
- .vm-flyout__link {
204
- display: flex;
205
- width: 100%;
206
- height: 38px;
207
- align-items: center;
208
- gap: 8px;
209
- box-sizing: border-box;
210
- padding: 0 10px;
211
- border: none;
212
- border-radius: 10px;
213
- background: transparent;
214
- color: var(--foreground);
215
- font-size: 13px;
216
- font-weight: 600;
217
- line-height: 1;
218
- text-decoration: none;
219
- cursor: pointer;
220
- transition: background 0.12s ease;
221
-
222
- &:hover,
223
- .vm-flyout__row.is-open > & {
224
- background: var(--muted);
225
- }
226
-
227
- .vm-flyout__row.is-active > & {
228
- color: var(--brand);
229
- background: var(--brand-soft);
230
- }
231
- }
232
-
233
- .vm-flyout__icon {
234
- display: inline-flex;
235
- flex-shrink: 0;
236
- width: 16px;
237
- height: 16px;
238
- align-items: center;
239
- justify-content: center;
240
- font-size: 16px;
241
- line-height: 1;
242
- }
243
-
244
- .vm-flyout__label {
245
- display: inline-flex;
246
- flex: 1;
247
- min-width: 0;
248
- align-items: center;
249
- overflow: hidden;
250
- text-overflow: ellipsis;
251
- white-space: nowrap;
252
- line-height: 1;
253
- text-align: left;
254
- }
255
-
256
- .vm-flyout__chevron {
257
- display: inline-flex;
258
- flex-shrink: 0;
259
- width: 16px;
260
- height: 16px;
261
- align-items: center;
262
- justify-content: center;
263
- margin-left: 4px;
264
- font-size: 16px;
265
- line-height: 1;
266
- opacity: 0.45;
267
- }
268
- </style>