c-admin-kit 1.0.0

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 (56) hide show
  1. package/README.md +232 -0
  2. package/dist/c-admin-kit.css +1 -0
  3. package/dist/c-admin-kit.js +2482 -0
  4. package/dist/c-admin-kit.umd.cjs +10 -0
  5. package/dist/components/AsyncButton/index.vue.d.ts +48 -0
  6. package/dist/components/CollapsibleContainer/index.vue.d.ts +73 -0
  7. package/dist/components/CustomDrawer/index.vue.d.ts +149 -0
  8. package/dist/components/ImagePreview/index.vue.d.ts +34 -0
  9. package/dist/components/SearchBox/index.vue.d.ts +122 -0
  10. package/dist/components/SelectWithAll/index.vue.d.ts +169 -0
  11. package/dist/components/SelectWithPage/index.vue.d.ts +78 -0
  12. package/dist/components/SimpleTable/index.vue.d.ts +337 -0
  13. package/dist/components/SimpleTable/useTableColumnConfig.d.ts +5 -0
  14. package/dist/components/diff/index.vue.d.ts +33 -0
  15. package/dist/components/index.d.ts +12 -0
  16. package/dist/composables/index.d.ts +6 -0
  17. package/dist/composables/useConfirmAction.d.ts +5 -0
  18. package/dist/composables/useConfirmSubmit.d.ts +5 -0
  19. package/dist/composables/useDialog.d.ts +5 -0
  20. package/dist/composables/useDownload.d.ts +5 -0
  21. package/dist/composables/useForm.d.ts +5 -0
  22. package/dist/composables/useListPage.d.ts +5 -0
  23. package/dist/index.d.ts +9 -0
  24. package/dist/types.d.ts +282 -0
  25. package/dist/utils/index.d.ts +4 -0
  26. package/dist/utils/scroll-to.d.ts +7 -0
  27. package/dist/utils/searchFieldFactory.d.ts +34 -0
  28. package/dist/utils/treeManager.d.ts +64 -0
  29. package/dist/utils/validate.d.ts +30 -0
  30. package/package.json +86 -0
  31. package/src/components/AsyncButton/index.vue +58 -0
  32. package/src/components/CollapsibleContainer/index.vue +240 -0
  33. package/src/components/CustomDrawer/index.vue +167 -0
  34. package/src/components/ImagePreview/index.vue +88 -0
  35. package/src/components/SearchBox/index.vue +582 -0
  36. package/src/components/SelectWithAll/index.vue +281 -0
  37. package/src/components/SelectWithPage/index.vue +204 -0
  38. package/src/components/SimpleTable/index.vue +781 -0
  39. package/src/components/SimpleTable/useTableColumnConfig.ts +139 -0
  40. package/src/components/diff/index.vue +265 -0
  41. package/src/components/index.ts +35 -0
  42. package/src/composables/index.ts +6 -0
  43. package/src/composables/useConfirmAction.ts +62 -0
  44. package/src/composables/useConfirmSubmit.ts +68 -0
  45. package/src/composables/useDialog.ts +48 -0
  46. package/src/composables/useDownload.ts +83 -0
  47. package/src/composables/useForm.ts +114 -0
  48. package/src/composables/useListPage.ts +243 -0
  49. package/src/env.d.ts +7 -0
  50. package/src/index.ts +44 -0
  51. package/src/types.ts +344 -0
  52. package/src/utils/index.ts +4 -0
  53. package/src/utils/scroll-to.ts +60 -0
  54. package/src/utils/searchFieldFactory.ts +302 -0
  55. package/src/utils/treeManager.ts +218 -0
  56. package/src/utils/validate.ts +64 -0
package/README.md ADDED
@@ -0,0 +1,232 @@
1
+ # C-Admin-Kit (企业级中后台组件与通用工具套件)
2
+
3
+ `c-admin-kit` 是一套基于 **Vue 3 + Element Plus** 深度解耦的中后台高阶通用组件、配置工厂与 Hooks 工具套件。
4
+
5
+ > 📌 **团队命名规范**:为了彻底杜绝多项目复用时的全局组件同名冲突,所有组件**统一且固定强制使用 `c-` / `C` 前缀**(例如 `<c-simple-table>`, `<c-search-box>`),不支持自定义配置,保持团队代码规范高度统一。
6
+
7
+ ---
8
+
9
+ ## 📦 目录结构
10
+
11
+ ```text
12
+ packages/admin-kit/
13
+ ├── src/
14
+ │ ├── components/ # UI 通用组件 (CSimpleTable, CSearchBox 等)
15
+ │ ├── composables/ # 通用 Hooks (useListPage, useForm 等)
16
+ │ ├── utils/ # 工具函数 (SearchFieldFactory, treeManager 等)
17
+ │ └── index.js # 统一主入口
18
+ ├── package.json
19
+ ├── vite.config.js
20
+ └── README.md
21
+ ```
22
+
23
+ ---
24
+
25
+ ## 🚀 快速上手
26
+
27
+ ### 1. 全局完整引入 (main.js)
28
+
29
+ ```javascript
30
+ import { createApp } from 'vue'
31
+ import ElementPlus from 'element-plus'
32
+ import 'element-plus/dist/index.css'
33
+ import App from './App.vue'
34
+
35
+ // 引入 c-admin-kit
36
+ import CAdminKit from 'c-admin-kit'
37
+ // 如已打包,可引入样式
38
+ // import 'c-admin-kit/dist/style.css'
39
+
40
+ const app = createApp(App)
41
+ app.use(ElementPlus)
42
+ app.use(CAdminKit) // 自动注册所有 c- 开头组件
43
+ app.mount('#app')
44
+ ```
45
+
46
+ ### 2. 局部按需引入 (推荐)
47
+
48
+ ```vue
49
+ <template>
50
+ <c-search-box :fields="searchFields" @search="handleSearch" />
51
+ <c-simple-table ref="tableRef" :api="apiList" :columns="columns" />
52
+ </template>
53
+
54
+ <script setup>
55
+ import { CSearchBox, CSimpleTable } from 'c-admin-kit'
56
+ import { SearchFieldFactory } from 'c-admin-kit'
57
+ import { useListPage } from 'c-admin-kit'
58
+
59
+ // 或细粒度引入:
60
+ // import { CSimpleTable } from 'c-admin-kit/components'
61
+ // import { useListPage } from 'c-admin-kit/hooks'
62
+ // import { SearchFieldFactory } from 'c-admin-kit/utils'
63
+ </script>
64
+ ```
65
+
66
+ ---
67
+
68
+ ## 🧩 组件清单与模板标签规范
69
+
70
+ | 组件名 (PascalCase) | 模板标签 (kebab-case) | 功能描述 |
71
+ | :--- | :--- | :--- |
72
+ | **`CSimpleTable`** | `<c-simple-table>` | 800+ 行高级配置化表格:支持拖拽排序、列自定义显隐(本地缓存/API持久化)、动态自适应全屏高度、分页联动。 |
73
+ | **`CSearchBox`** | `<c-search-box>` | 高阶配置化多条件表单搜索栏:支持响应式栅格、展开/收起两行、级联依赖、回车搜索。 |
74
+ | **`CAsyncButton`** | `<c-async-button>` | 异步按钮:自动识别 Promise 并开启 loading,防止重复点击。 |
75
+ | **`CSelectWithAll`** | `<c-select-with-all>` | 支持全选/半选/反选与防抖远程搜索的增强下拉框。 |
76
+ | **`CSelectWithPage`**| `<c-select-with-page>`| 支持分页数据源、参数化键值对(`labelKey`/`valueKey`)与远程搜索的下拉框。 |
77
+ | **`CCollapsibleContainer`** | `<c-collapsible-container>` | 左右双栏布局容器:支持鼠标按住分隔线拖拽缩放宽度、一键收起折叠。 |
78
+ | **`CCustomDrawer`** | `<c-custom-drawer>` | 二次封装 el-drawer,标准化底部取消/确定按钮与事件流。 |
79
+ | **`CDiff`** | `<c-diff>` | 纯前端字符级与行级文本/代码 Diff 对比可视化组件。 |
80
+ | **`CImagePreview`** | `<c-image-preview>` | 缩略图展示与大图预览包装组件。 |
81
+
82
+ ---
83
+
84
+ ## 🌟 黄金组合:10行代码搞定企业级增删改查页
85
+
86
+ 结合 `SearchFieldFactory`、`useListPage` 与 `CSearchBox`、`CSimpleTable`:
87
+
88
+ ```vue
89
+ <template>
90
+ <div class="page-container">
91
+ <!-- 1. 搜索表单 -->
92
+ <c-search-box
93
+ :fields="searchFields"
94
+ @search="handleSearch"
95
+ @reset="handleReset"
96
+ />
97
+
98
+ <!-- 2. 数据表格 -->
99
+ <c-simple-table
100
+ ref="tableRef"
101
+ :api="getUserListApi"
102
+ :columns="columns"
103
+ table-key="user_list_table"
104
+ auto-height
105
+ >
106
+ <template #headerLeft>
107
+ <el-button type="primary" @click="handleAdd">新增用户</el-button>
108
+ </template>
109
+
110
+ <!-- 操作列插槽 -->
111
+ <template #actions="{ row }">
112
+ <el-button link type="primary" @click="handleEdit(row)">编辑</el-button>
113
+ <el-button link type="danger" @click="handleDelete(row)">删除</el-button>
114
+ </template>
115
+ </c-simple-table>
116
+ </div>
117
+ </template>
118
+
119
+ <script setup>
120
+ import { computed } from 'vue'
121
+ import {
122
+ CSearchBox,
123
+ CSimpleTable,
124
+ SearchFieldFactory,
125
+ useListPage
126
+ } from 'c-admin-kit'
127
+ import { getUserListApi, deleteUserApi, changeUserStatusApi } from '@/api/user'
128
+
129
+ // 标准 CRUD 流控制
130
+ const {
131
+ tableRef,
132
+ handleSearch,
133
+ handleReset,
134
+ handleDelete,
135
+ handleAdd,
136
+ handleEdit
137
+ } = useListPage({
138
+ apiList: getUserListApi,
139
+ apiDelete: deleteUserApi,
140
+ apiChangeState: changeUserStatusApi,
141
+ addPath: '/user/add',
142
+ editPath: '/user/edit'
143
+ })
144
+
145
+ // 搜索字段快速定义 (SearchFieldFactory)
146
+ const searchFields = computed(() => [
147
+ SearchFieldFactory.input({ prop: 'username', label: '用户名' }),
148
+ SearchFieldFactory.select({
149
+ prop: 'status',
150
+ label: '状态',
151
+ options: [
152
+ { label: '正常', value: 1 },
153
+ { label: '停用', value: 0 }
154
+ ]
155
+ }),
156
+ SearchFieldFactory.dateRange({ prop: 'createTime', label: '创建时间' })
157
+ ])
158
+
159
+ // 列配置
160
+ const columns = [
161
+ { type: 'selection' },
162
+ { type: 'index', label: '序号' },
163
+ { prop: 'username', label: '用户名' },
164
+ { prop: 'status', label: '状态', type: 'status' },
165
+ { prop: 'createTime', label: '创建时间' },
166
+ { label: '操作', slot: 'actions', width: 160, fixed: 'right' }
167
+ ]
168
+ </script>
169
+ ```
170
+
171
+ ---
172
+
173
+ ## 🛠️ 组合式函数 (Hooks) 说明
174
+
175
+ ### 1. `useForm`
176
+ 管理表单数据与验证提交:
177
+ ```javascript
178
+ const { formRef, formData, loading, submit, reset } = useForm({
179
+ initFormData: { name: '', email: '' }
180
+ })
181
+
182
+ // 提交自动开启 loading 并执行表单校验
183
+ await submit(async (data) => await saveApi(data), '保存成功')
184
+ ```
185
+
186
+ ### 2. `useConfirmSubmit` & `useConfirmAction`
187
+ 操作二次确认弹窗:
188
+ ```javascript
189
+ const handleDelete = useConfirmSubmit(
190
+ async (id) => await deleteApi(id),
191
+ () => tableRef.value.refresh(),
192
+ { message: '确定要永久删除该项吗?' }
193
+ )
194
+ ```
195
+
196
+ ### 3. `useDownload`
197
+ 安全下载导出文件(支持 Blob 异常解析):
198
+ ```javascript
199
+ const { download } = useDownload(exportApi, { filename: '用户数据导出' })
200
+ await download({ keyword: 'test' })
201
+ ```
202
+
203
+ ---
204
+
205
+ ## 🚀 独立成 Git 仓库指南
206
+
207
+ 若需要将 `packages/admin-kit` 作为一个独立的 Git 仓库推送到公司代码托管平台(如 GitLab/Gitee/GitHub):
208
+
209
+ ```bash
210
+ # 1. 进入包目录
211
+ cd packages/admin-kit
212
+
213
+ # 2. 初始化独立 git 仓库
214
+ git init
215
+ git add .
216
+ git commit -m "feat: init c-admin-kit package"
217
+
218
+ # 3. 关联远程仓库并推送
219
+ git remote add origin https://your-git-server.com/frontend/c-admin-kit.git
220
+ git branch -M main
221
+ git push -u origin main
222
+ ```
223
+
224
+ 其他项目可通过 Git 依赖直接安装使用:
225
+ ```json
226
+ {
227
+ "dependencies": {
228
+ "c-admin-kit": "git+https://your-git-server.com/frontend/c-admin-kit.git"
229
+ }
230
+ }
231
+ ```
232
+ 或在公司内部私有 NPM 源执行 `npm publish` 即可!
@@ -0,0 +1 @@
1
+ .select-all-option[data-v-904634e0]{border-bottom:1px solid #e4e7ed;font-weight:600}[data-v-904634e0] .el-checkbox{width:100%}.empty-text[data-v-904634e0]{padding:10px 0;margin:0;text-align:center;color:#999;font-size:14px}.remote-select-wrapper[data-v-dea4bdcf]{width:100%}.loading-text[data-v-dea4bdcf]{display:flex;align-items:center;justify-content:center;gap:8px;color:#909399;font-size:14px;padding:10px}.no-data-text[data-v-dea4bdcf]{text-align:center;color:#c0c4cc;font-size:14px;padding:10px}.search-box[data-v-760b27aa]{border-radius:4px;margin-bottom:16px;padding-bottom:12px}.search-form[data-v-760b27aa],.search-fields[data-v-760b27aa]{width:100%}.field-col[data-v-760b27aa]{margin-bottom:12px}.action-col[data-v-760b27aa]{display:flex;justify-content:flex-end;align-items:center}.search-form[data-v-760b27aa] .el-form-item{margin-bottom:0;display:flex;align-items:center;width:100%}.search-form[data-v-760b27aa] .el-form-item__label{flex-shrink:0;font-weight:500;color:#606266;line-height:32px;min-width:var(--v7dbee7c4);width:var(--v7dbee7c4);padding-right:12px;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.search-form[data-v-760b27aa] .el-form-item__content{flex:1;line-height:32px;min-width:0;width:100%}.is-required[data-v-760b27aa] .el-form-item__label:before{content:"*";color:#f56c6c;margin-right:4px}.button-group[data-v-760b27aa]{display:flex;gap:8px;align-items:center;flex-wrap:wrap}.toggle-btn[data-v-760b27aa]{padding:8px 15px;color:#409eff;display:inline-flex;align-items:center;gap:4px}.toggle-btn[data-v-760b27aa]:hover{color:#66b1ff}.toggle-icon[data-v-760b27aa]{font-size:12px;transition:transform .3s}.search-form[data-v-760b27aa] .el-input,.search-form[data-v-760b27aa] .el-select,.search-form[data-v-760b27aa] .el-date-editor,.search-form[data-v-760b27aa] .el-input-number,.search-form[data-v-760b27aa] .el-cascader{width:100%;flex:1}@media(max-width:768px){.search-box[data-v-760b27aa]{padding:16px}.search-form[data-v-760b27aa] .el-form-item{flex-direction:column;align-items:flex-start}.search-form[data-v-760b27aa] .el-form-item__label{line-height:20px;margin-bottom:8px;width:100%;min-width:auto;white-space:normal}.action-col[data-v-760b27aa]{justify-content:flex-start}.button-group[data-v-760b27aa]{width:100%;flex-direction:column}.button-group .el-button[data-v-760b27aa]{width:100%}.toggle-btn[data-v-760b27aa]{width:100%;justify-content:center}}.collapsible-container[data-v-d7447c42]{display:grid;grid-template-columns:var(--v5dad642c);height:var(--v1c2deffa);width:100%;background:#f5f7fa;overflow:hidden}.left-panel[data-v-d7447c42]{background:#fff;border-right:1px solid #e4e7ed;display:flex;flex-direction:column;overflow:hidden;max-width:var(--v72e9676c);min-width:var(--v72e9676c);position:relative;will-change:max-width,min-width}.left-panel[data-v-d7447c42]:not(.resizing){transition:all .3s ease-in-out}.left-content[data-v-d7447c42]{height:100%;padding:16px;overflow-y:auto;min-width:0;transition:opacity .2s ease-in-out;opacity:1}.left-panel.collapsed .left-content[data-v-d7447c42]{opacity:0}.right-panel[data-v-d7447c42]{background:#fff;transition:all .3s ease-in-out;max-width:100%;overflow:hidden}.toggle-btn[data-v-d7447c42]{width:48px;height:48px;display:flex;align-items:center;justify-content:center;cursor:pointer;flex-shrink:0;transition:transform .3s ease-in-out}.toggle-btn[data-v-d7447c42]:hover{background-color:#f5f7fa}.right-content[data-v-d7447c42]{height:100%;padding:16px;overflow-y:auto;max-width:100%;box-sizing:border-box}.resize-handle[data-v-d7447c42]{position:absolute;right:0;top:0;width:4px;height:100%;cursor:col-resize;background:transparent;transition:background .2s ease;z-index:10;will-change:background;padding:0 4px;margin:0 -4px}.resize-handle[data-v-d7447c42]:hover{background:#409eff}.resize-handle[data-v-d7447c42]:active{background:#337ecc}.collapsible-container[data-v-d7447c42]:has(.resize-handle:active){transition:none}.left-panel[data-v-d7447c42]:has(.resize-handle:active){transition:none}.drawer-content[data-v-4f318c2b]{height:100%}.drawer-footer[data-v-4f318c2b]{display:flex;justify-content:flex-end;gap:12px}.c-simple-table[data-v-c7177925]{width:100%}.table-header[data-v-c7177925]{display:flex;justify-content:space-between;align-items:center;margin-bottom:8px;min-height:32px}.header-left[data-v-c7177925]{flex:1;display:flex;align-items:center;gap:12px}.header-right[data-v-c7177925]{display:flex;align-items:center;gap:12px}.table-pagination[data-v-c7177925]{margin-top:16px;display:flex;justify-content:flex-end}.drag-handle[data-v-c7177925]{display:inline-flex;align-items:center;justify-content:center;cursor:move;padding:4px;transition:all .2s}.drag-handle[data-v-c7177925]:hover{transform:scale(1.1)}[data-v-c7177925] .sortable-ghost{opacity:.4;background:#f5f7fa}[data-v-c7177925] .sortable-chosen{background:#ecf5ff}[data-v-c7177925] .sortable-drag{opacity:.8;background:#fff;box-shadow:0 2px 12px #0000001a}[data-v-c7177925] .el-table__body-wrapper{overflow-y:auto!important}.c-diff-container[data-v-29510e70]{font-family:monospace;font-size:14px;line-height:1.6;white-space:pre-wrap;word-break:break-word;color:#333}.diff-removed[data-v-29510e70]{background-color:#fee2e2;color:#991b1b;text-decoration:line-through;text-decoration-color:#dc2626;text-decoration-thickness:2px}.diff-added[data-v-29510e70]{background-color:#dcfce7;color:#166534;font-weight:600}.el-image[data-v-cd23dea8]{border-radius:5px;background-color:#ebeef5;box-shadow:0 0 5px 1px #ccc}[data-v-cd23dea8] .el-image__inner{transition:all .3s;cursor:pointer}[data-v-cd23dea8] .el-image__inner:hover{transform:scale(1.08)}[data-v-cd23dea8] .image-slot{display:flex;justify-content:center;align-items:center;width:100%;height:100%;color:#909399;font-size:24px}