# 页面视图开发 :::tip 说明 页面视图位于 `src/views/` 目录,每个业务模块遵循 `index.vue`(列表页)+ `edit.vue`(编辑弹窗)+ `detail.vue`(详情弹窗)的标准模式,辅以 `columns.ts`(列定义)和 `querySchemas.ts`(搜索表单)配置文件。 ::: ## 目录结构 ``` src/views/ ├── tool/ │ ├── example/ │ │ ├── index.vue # 案例列表页 │ │ ├── edit.vue # 案例编辑弹窗 │ │ ├── detail.vue # 案例详情弹窗 │ │ ├── columns.ts # 表格列定义 │ │ └── querySchemas.ts # 搜索表单定义 │ └── ... └── ... ``` ## 文件职责 | 文件 | 职责 | 说明 | |------|------|------| | `index.vue` | 列表页 | 搜索表单 + 工具栏 + BasicTable + 编辑弹窗引用 | | `edit.vue` | 编辑弹窗 | n-dialog + n-form,懒加载 | | `detail.vue` | 详情弹窗 | n-dialog 展示详情,懒加载 | | `columns.ts` | 表格列定义 | 定义列 key、title、render 函数等 | | `querySchemas.ts` | 搜索表单定义 | FormSchema 数组,定义搜索字段 | ## index.vue 列表页 以案例管理为例,完整结构如下: ```vue ``` ## columns.ts ```typescript import { h } from 'vue'; import { NTag, NAvatar, NImage } from 'naive-ui'; /** * 表格列配置 * 定义表格显示的列 */ export const columns = [ { type: 'selection', // 多选框列 width: 50, fixed: 'left', }, { title: 'ID', key: 'id', fixed: 'left', width: 50, }, { title: '案例名称', key: 'name', width: 150, // 普通文本渲染(无需额外配置) ellipsis: { tooltip: true, }, }, { title: '案例图片', key: 'avatar', width: 150, // 图片渲染 render(record) { return record.avatar ? h(NAvatar, { src: record.avatar, size: 48, shape: 'square', fit: 'cover', style: { borderRadius: '4px', }, }) : h('span', '-'); }, }, { title: '案例类型', key: 'type', width: 100, // 选项标签渲染 render(record) { const statusMap = { 1: { text: '类型1', type: 'success' }, 2: { text: '类型2', type: 'error' }, 3: { text: '类型3', type: 'warning' }, 4: { text: '类型4', type: 'info' }, }; const status = statusMap[record.type]; return h( NTag, { bordered: false, type: status?.type || 'info', }, { default: () => status?.text || record.type, }, ); }, }, { title: '案例状态', key: 'status', width: 100, // 选项标签渲染 render(record) { const statusMap = { 1: { text: '正常', type: 'success' }, 2: { text: '禁用', type: 'error' }, }; const status = statusMap[record.status]; return h( NTag, { bordered: false, type: status?.type || 'info', }, { default: () => status?.text || record.status, }, ); }, }, { title: '排序', key: 'sort', width: 100, // 普通文本渲染(无需额外配置) ellipsis: { tooltip: true, }, }, { title: '创建人', key: 'createUser', width: 100, }, { title: '创建时间', key: 'createTime', width: 180, }, ]; ``` ## querySchemas.ts ```typescript import { FormSchema } from '@/components/Form/index'; /** * 查询表单配置 * 定义搜索区域的表单项 */ export const schemas: FormSchema[] = [ { field: 'name', component: 'NInput', label: '案例名称', componentProps: { placeholder: '请输入案例名称', clearable: true, filterable: false, }, }, { field: 'type', component: 'NSelect', label: '案例类型', componentProps: { placeholder: '请输入案例类型', clearable: true, filterable: true, options: [ { label: '类型1', value: 1, }, { label: '类型2', value: 2, }, { label: '类型3', value: 3, }, { label: '类型4', value: 4, }, ], }, }, { field: 'status', component: 'NSelect', label: '案例状态', componentProps: { placeholder: '请输入案例状态', clearable: true, filterable: true, options: [ { label: '正常', value: 1, }, { label: '禁用', value: 2, }, ], }, }, ]; ``` ## 数据流 ``` 页面加载 → BasicForm 注册 → BasicTable request 触发 → loadDataTable → API → 渲染表格 用户搜索 → handleSubmit → 更新 formParams → reloadTable → 重新请求 用户新增 → handleAdd → currentId=0 → editVisible=true → edit.vue 加载 → 表单填写 → 提交 用户编辑 → handleEdit → currentId=id → editVisible=true → edit.vue 加载详情 → 修改 → 提交 用户删除 → dialog.warning → 确认 → API → reloadTable ``` :::tip 温馨提示 `columns.ts` 和 `querySchemas.ts` 独立为配置文件,便于维护和复用。`columns` 中的 `render` 函数使用 Vue 的 `h()` 创建虚拟 DOM,可实现任意复杂的自定义渲染。`querySchemas` 中的 `options` 硬编码或通过字典 API 动态获取。 ::: ## 总结 页面视图遵循 `index.vue` + `edit.vue` + `detail.vue` + `columns.ts` + `querySchemas.ts` 标准模式。列表页使用 `BasicForm` 搜索 + `BasicTable` 展示数据 + `TableAction` 操作按钮,编辑弹窗使用 `import` 直接导入 + `useLockFn` 防重复提交。消息提示使用 NaiveUI 的 `useMessage()`,确认对话框使用 `useDialog()`。