diff --git a/apps/web-antd/src/api/iot/product/product/index.ts b/apps/web-antd/src/api/iot/product/product/index.ts index 28b2f7b2e..bf5682d2d 100644 --- a/apps/web-antd/src/api/iot/product/product/index.ts +++ b/apps/web-antd/src/api/iot/product/product/index.ts @@ -48,6 +48,12 @@ export enum CodecTypeEnum { ALINK = 'Alink', // 阿里云 Alink 协议 } +/** IOT 产品状态枚举类 */ +export enum ProductStatusEnum { + UNPUBLISHED = 0, // 开发中 + PUBLISHED = 1, // 已发布 +} + /** 查询产品分页 */ export function getProductPage(params: PageParam) { return requestClient.get>( diff --git a/apps/web-antd/src/views/iot/device/group/index.vue b/apps/web-antd/src/views/iot/device/group/index.vue index d72341a6b..0d3f7b6ab 100644 --- a/apps/web-antd/src/views/iot/device/group/index.vue +++ b/apps/web-antd/src/views/iot/device/group/index.vue @@ -11,12 +11,12 @@ import { deleteDeviceGroup, getDeviceGroupPage } from '#/api/iot/device/group'; import { $t } from '#/locales'; import { useGridColumns, useGridFormSchema } from './data'; -import DeviceGroupForm from './modules/device-group-form.vue'; +import Form from './modules/form.vue'; defineOptions({ name: 'IoTDeviceGroup' }); const [FormModal, formModalApi] = useVbenModal({ - connectedComponent: DeviceGroupForm, + connectedComponent: Form, destroyOnClose: true, }); diff --git a/apps/web-antd/src/views/iot/device/group/modules/device-group-form.vue b/apps/web-antd/src/views/iot/device/group/modules/form.vue similarity index 64% rename from apps/web-antd/src/views/iot/device/group/modules/device-group-form.vue rename to apps/web-antd/src/views/iot/device/group/modules/form.vue index 90529de77..3e1a2d521 100644 --- a/apps/web-antd/src/views/iot/device/group/modules/device-group-form.vue +++ b/apps/web-antd/src/views/iot/device/group/modules/form.vue @@ -1,4 +1,4 @@ - diff --git a/apps/web-antd/src/views/iot/product/category/index.vue b/apps/web-antd/src/views/iot/product/category/index.vue index 05a56ee6d..3dc7201b7 100644 --- a/apps/web-antd/src/views/iot/product/category/index.vue +++ b/apps/web-antd/src/views/iot/product/category/index.vue @@ -14,12 +14,12 @@ import { import { $t } from '#/locales'; import { useGridColumns, useGridFormSchema } from './data'; -import ProductCategoryForm from './modules/product-category-form.vue'; +import Form from './modules/form.vue'; defineOptions({ name: 'IoTProductCategory' }); const [FormModal, formModalApi] = useVbenModal({ - connectedComponent: ProductCategoryForm, + connectedComponent: Form, destroyOnClose: true, }); diff --git a/apps/web-antd/src/views/iot/product/category/modules/product-category-form.vue b/apps/web-antd/src/views/iot/product/category/modules/form.vue similarity index 88% rename from apps/web-antd/src/views/iot/product/category/modules/product-category-form.vue rename to apps/web-antd/src/views/iot/product/category/modules/form.vue index 792c7ddac..df2290639 100644 --- a/apps/web-antd/src/views/iot/product/category/modules/product-category-form.vue +++ b/apps/web-antd/src/views/iot/product/category/modules/form.vue @@ -17,8 +17,6 @@ import { $t } from '#/locales'; import { useFormSchema } from '../data'; -// TODO @haohao:应该是 form.vue,不用前缀; - const emit = defineEmits(['success']); const formData = ref(); const getTitle = computed(() => { @@ -40,7 +38,6 @@ const [Form, formApi] = useVbenForm({ showDefaultActions: false, }); -// TODO @haohao:参考 apps/web-antd/src/views/system/dept/modules/form.vue 简化 useVbenModal 里的代码; const [Modal, modalApi] = useVbenModal({ async onConfirm() { const { valid } = await formApi.validate(); @@ -66,25 +63,19 @@ const [Modal, modalApi] = useVbenModal({ async onOpenChange(isOpen: boolean) { if (!isOpen) { formData.value = undefined; - formApi.resetForm(); return; } - - // 重置表单 - await formApi.resetForm(); - + // 加载数据 const data = modalApi.getData(); - // 如果没有数据或没有 id,表示是新增 if (!data || !data.id) { - formData.value = undefined; // 新增模式:设置默认值 + formData.value = undefined; await formApi.setValues({ sort: 0, status: 1, }); return; } - // 编辑模式:加载数据 modalApi.lock(); try { diff --git a/apps/web-antd/src/views/iot/product/product/data.ts b/apps/web-antd/src/views/iot/product/product/data.ts index 066cc1330..57d2c3818 100644 --- a/apps/web-antd/src/views/iot/product/product/data.ts +++ b/apps/web-antd/src/views/iot/product/product/data.ts @@ -1,7 +1,8 @@ import type { VbenFormSchema } from '#/adapter/form'; import type { VxeTableGridOptions } from '#/adapter/vxe-table'; +import type { IotProductCategoryApi } from '#/api/iot/product/category'; -import { h, ref } from 'vue'; +import { h } from 'vue'; import { DICT_TYPE } from '@vben/constants'; import { getDictOptions } from '@vben/hooks'; @@ -10,7 +11,17 @@ import { Button } from 'ant-design-vue'; import { z } from '#/adapter/form'; import { getSimpleProductCategoryList } from '#/api/iot/product/category'; -import { getProductPage } from '#/api/iot/product/product'; + +/** 产品分类列表缓存 */ +let categoryList: IotProductCategoryApi.ProductCategory[] = []; + +/** 加载产品分类数据 */ +async function loadCategoryData() { + categoryList = await getSimpleProductCategoryList(); +} + +// 初始化加载分类数据 +loadCategoryData(); /** 新增/修改产品的表单 */ export function useFormSchema(formApi?: any): VbenFormSchema[] { @@ -134,7 +145,7 @@ export function useFormSchema(formApi?: any): VbenFormSchema[] { label: '产品状态', component: 'RadioGroup', componentProps: { - options: getDictOptions(DICT_TYPE.COMMON_STATUS, 'number'), + options: getDictOptions(DICT_TYPE.IOT_PRODUCT_STATUS, 'number'), buttonStyle: 'solid', optionType: 'button', }, @@ -283,7 +294,7 @@ export function useBasicFormSchema(formApi?: any): VbenFormSchema[] { label: '产品状态', component: 'RadioGroup', componentProps: { - options: getDictOptions(DICT_TYPE.COMMON_STATUS, 'number'), + options: getDictOptions(DICT_TYPE.IOT_PRODUCT_STATUS, 'number'), buttonStyle: 'solid', optionType: 'button', }, @@ -308,11 +319,10 @@ export function useAdvancedFormSchema(): VbenFormSchema[] { { fieldName: 'icon', label: '产品图标', - component: 'IconPicker', // 用这个组件 产品卡片列表 可以根据这个显示 否则就显示默认的 + component: 'IconPicker', componentProps: { placeholder: '请选择产品图标', prefix: 'carbon', - autoFetchApi: false, }, }, { @@ -333,31 +343,6 @@ export function useAdvancedFormSchema(): VbenFormSchema[] { ]; } -/** 列表的搜索表单 */ -// TODO @haohao:貌似用不上? -export function useGridFormSchema(): VbenFormSchema[] { - return [ - { - fieldName: 'name', - label: '产品名称', - component: 'Input', - componentProps: { - placeholder: '请输入产品名称', - allowClear: true, - }, - }, - { - fieldName: 'productKey', - label: 'ProductKey', - component: 'Input', - componentProps: { - placeholder: '请输入产品标识', - allowClear: true, - }, - }, - ]; -} - /** 列表的字段 */ export function useGridColumns(): VxeTableGridOptions['columns'] { return [ @@ -375,7 +360,8 @@ export function useGridColumns(): VxeTableGridOptions['columns'] { field: 'categoryId', title: '品类', minWidth: 120, - slots: { default: 'category' }, + formatter: ({ cellValue }) => + categoryList.find((c) => c.id === cellValue)?.name || '未分类', }, { field: 'deviceType', @@ -390,13 +376,17 @@ export function useGridColumns(): VxeTableGridOptions['columns'] { field: 'icon', title: '产品图标', width: 100, - slots: { default: 'icon' }, + cellRender: { + name: 'CellImage', + }, }, { field: 'picUrl', title: '产品图片', width: 100, - slots: { default: 'picUrl' }, + cellRender: { + name: 'CellImage', + }, }, { field: 'createTime', @@ -413,35 +403,6 @@ export function useGridColumns(): VxeTableGridOptions['columns'] { ]; } -/** 查询产品列表 */ -// TODO @haohao:貌似可以删除? -export async function queryProductList({ page }: any, searchParams: any) { - return await getProductPage({ - pageNo: page.currentPage, - pageSize: page.pageSize, - ...searchParams, - }); -} - -/** 创建图片预览状态 */ -// TODO @haohao:可能不一定用的上; -export function useImagePreview() { - const previewVisible = ref(false); - const previewImage = ref(''); - - function handlePreviewImage(url: string) { - previewImage.value = url; - previewVisible.value = true; - } - - return { - previewVisible, - previewImage, - handlePreviewImage, - }; -} - -// TODO @haohao:放到对应的 form 里 /** 生成 ProductKey(包含大小写字母和数字) */ export function generateProductKey(): string { const chars = diff --git a/apps/web-antd/src/views/iot/product/product/index.vue b/apps/web-antd/src/views/iot/product/product/index.vue index 0e5dcef8c..3aa14191d 100644 --- a/apps/web-antd/src/views/iot/product/product/index.vue +++ b/apps/web-antd/src/views/iot/product/product/index.vue @@ -1,5 +1,7 @@ - - diff --git a/apps/web-antd/src/views/iot/product/product/modules/detail/index.vue b/apps/web-antd/src/views/iot/product/product/modules/detail/index.vue index f63389860..5fc1fc7bd 100644 --- a/apps/web-antd/src/views/iot/product/product/modules/detail/index.vue +++ b/apps/web-antd/src/views/iot/product/product/modules/detail/index.vue @@ -1,7 +1,6 @@ diff --git a/apps/web-antd/src/views/iot/product/product/modules/detail/product-details-info.vue b/apps/web-antd/src/views/iot/product/product/modules/detail/modules/info.vue similarity index 88% rename from apps/web-antd/src/views/iot/product/product/modules/detail/product-details-info.vue rename to apps/web-antd/src/views/iot/product/product/modules/detail/modules/info.vue index fbbd07246..2693fff49 100644 --- a/apps/web-antd/src/views/iot/product/product/modules/detail/product-details-info.vue +++ b/apps/web-antd/src/views/iot/product/product/modules/detail/modules/info.vue @@ -1,5 +1,4 @@ - + + diff --git a/apps/web-antd/src/views/iot/product/product/modules/product-form.vue b/apps/web-antd/src/views/iot/product/product/modules/product-form.vue deleted file mode 100644 index 48222bc93..000000000 --- a/apps/web-antd/src/views/iot/product/product/modules/product-form.vue +++ /dev/null @@ -1,172 +0,0 @@ - - -