From 9e6d8ff3e935b6c2951ddd0ee0c164f5739912eb Mon Sep 17 00:00:00 2001 From: YunaiV Date: Tue, 30 Sep 2025 19:42:20 +0800 Subject: [PATCH] =?UTF-8?q?feat=EF=BC=9A=E3=80=90antd=E3=80=91=E3=80=90crm?= =?UTF-8?q?=E3=80=91=E8=B0=83=E6=95=B4=E6=93=8D=E4=BD=9C=E6=97=A5=E5=BF=97?= =?UTF-8?q?=E5=92=8C=E5=9B=A2=E9=98=9F=E6=88=90=E5=91=98=E7=9A=84=E6=A0=87?= =?UTF-8?q?=E7=AD=BE=E9=A1=BA=E5=BA=8F=EF=BC=8C=E4=BC=98=E5=8C=96=E8=A1=A8?= =?UTF-8?q?=E5=8D=95=E5=AD=97=E6=AE=B5=E7=9A=84=E8=A7=84=E5=88=99=E5=92=8C?= =?UTF-8?q?=E5=B1=9E=E6=80=A7?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- apps/web-antd/src/views/crm/business/data.ts | 2 +- .../src/views/crm/business/detail/index.vue | 8 +- apps/web-antd/src/views/crm/contact/data.ts | 36 ++++---- .../src/views/crm/contact/detail/data.ts | 13 +-- .../src/views/crm/contact/detail/index.vue | 10 +-- .../src/views/crm/contract/detail/index.vue | 4 +- .../src/views/crm/customer/detail/data.ts | 19 ++--- .../src/views/crm/customer/detail/index.vue | 2 +- .../src/views/crm/product/detail/data.ts | 2 +- .../web-antd/src/views/crm/receivable/data.ts | 26 +++--- .../src/views/crm/receivable/detail/data.ts | 31 ++++++- .../src/views/crm/receivable/detail/index.vue | 8 +- .../crm/receivable/detail/modules/info.vue | 5 +- .../views/crm/receivable/plan/detail/data.ts | 84 +++++++++++++++---- .../crm/receivable/plan/detail/index.vue | 8 +- .../receivable/plan/detail/modules/info.vue | 5 +- 16 files changed, 168 insertions(+), 95 deletions(-) diff --git a/apps/web-antd/src/views/crm/business/data.ts b/apps/web-antd/src/views/crm/business/data.ts index 8dce7f60..2f5f5cec 100644 --- a/apps/web-antd/src/views/crm/business/data.ts +++ b/apps/web-antd/src/views/crm/business/data.ts @@ -98,7 +98,6 @@ export function useFormSchema(): VbenFormSchema[] { fieldName: 'dealTime', label: '预计成交日期', component: 'DatePicker', - rules: 'required', componentProps: { showTime: false, format: 'YYYY-MM-DD HH:mm:ss', @@ -123,6 +122,7 @@ export function useFormSchema(): VbenFormSchema[] { componentProps: { min: 0, precision: 2, + disabled: true, placeholder: '请输入产品总金额', }, rules: z.number().min(0).optional().default(0), diff --git a/apps/web-antd/src/views/crm/business/detail/index.vue b/apps/web-antd/src/views/crm/business/detail/index.vue index 92ced523..193b4a03 100644 --- a/apps/web-antd/src/views/crm/business/detail/index.vue +++ b/apps/web-antd/src/views/crm/business/detail/index.vue @@ -165,7 +165,10 @@ onMounted(() => { :biz-type="BizTypeEnum.CRM_BUSINESS" /> - + + + + { @quit-team="handleBack" /> - - - diff --git a/apps/web-antd/src/views/crm/contact/data.ts b/apps/web-antd/src/views/crm/contact/data.ts index b3901de8..55b0494d 100644 --- a/apps/web-antd/src/views/crm/contact/data.ts +++ b/apps/web-antd/src/views/crm/contact/data.ts @@ -29,7 +29,7 @@ export function useFormSchema(): VbenFormSchema[] { rules: 'required', componentProps: { placeholder: '请输入联系人姓名', - }, + }, }, { fieldName: 'ownerUserId', @@ -66,7 +66,7 @@ export function useFormSchema(): VbenFormSchema[] { component: 'Input', componentProps: { placeholder: '请输入手机号', - }, + }, }, { fieldName: 'telephone', @@ -74,7 +74,7 @@ export function useFormSchema(): VbenFormSchema[] { component: 'Input', componentProps: { placeholder: '请输入电话', - }, + }, }, { fieldName: 'email', @@ -82,7 +82,7 @@ export function useFormSchema(): VbenFormSchema[] { component: 'Input', componentProps: { placeholder: '请输入邮箱', - }, + }, }, { fieldName: 'wechat', @@ -90,7 +90,7 @@ export function useFormSchema(): VbenFormSchema[] { component: 'Input', componentProps: { placeholder: '请输入微信', - }, + }, }, { fieldName: 'qq', @@ -98,7 +98,7 @@ export function useFormSchema(): VbenFormSchema[] { component: 'Input', componentProps: { placeholder: '请输入QQ', - }, + }, }, { fieldName: 'post', @@ -106,7 +106,7 @@ export function useFormSchema(): VbenFormSchema[] { component: 'Input', componentProps: { placeholder: '请输入职位', - }, + }, }, { fieldName: 'master', @@ -115,7 +115,7 @@ export function useFormSchema(): VbenFormSchema[] { componentProps: { options: getDictOptions(DICT_TYPE.INFRA_BOOLEAN_STRING, 'boolean'), placeholder: '请选择是否关键决策人', - buttonStyle: 'solid', + buttonStyle: 'solid', optionType: 'button', }, defaultValue: false, @@ -127,7 +127,7 @@ export function useFormSchema(): VbenFormSchema[] { componentProps: { options: getDictOptions(DICT_TYPE.SYSTEM_USER_SEX, 'number'), placeholder: '请选择性别', - }, + }, }, { fieldName: 'parentId', @@ -158,7 +158,7 @@ export function useFormSchema(): VbenFormSchema[] { component: 'Input', componentProps: { placeholder: '请输入详细地址', - }, + }, }, { fieldName: 'contactNextTime', @@ -169,7 +169,7 @@ export function useFormSchema(): VbenFormSchema[] { format: 'YYYY-MM-DD HH:mm:ss', valueFormat: 'x', placeholder: '请选择下次联系时间', - }, + }, }, { fieldName: 'remark', @@ -177,7 +177,7 @@ export function useFormSchema(): VbenFormSchema[] { component: 'Textarea', componentProps: { placeholder: '请输入备注', - }, + }, }, ]; } @@ -196,7 +196,7 @@ export function useGridFormSchema(): VbenFormSchema[] { value: 'id', }, placeholder: '请选择客户', - }, + }, }, { fieldName: 'name', @@ -205,7 +205,7 @@ export function useGridFormSchema(): VbenFormSchema[] { componentProps: { placeholder: '请输入联系人姓名', allowClear: true, - }, + }, }, { fieldName: 'mobile', @@ -214,7 +214,7 @@ export function useGridFormSchema(): VbenFormSchema[] { componentProps: { placeholder: '请输入手机号', allowClear: true, - }, + }, }, { fieldName: 'telephone', @@ -223,7 +223,7 @@ export function useGridFormSchema(): VbenFormSchema[] { componentProps: { placeholder: '请输入电话', allowClear: true, - }, + }, }, { fieldName: 'wechat', @@ -232,7 +232,7 @@ export function useGridFormSchema(): VbenFormSchema[] { componentProps: { placeholder: '请输入微信', allowClear: true, - }, + }, }, { fieldName: 'email', @@ -241,7 +241,7 @@ export function useGridFormSchema(): VbenFormSchema[] { componentProps: { placeholder: '请输入电子邮箱', allowClear: true, - }, + }, }, ]; } diff --git a/apps/web-antd/src/views/crm/contact/detail/data.ts b/apps/web-antd/src/views/crm/contact/detail/data.ts index a259c0d1..d510ba4d 100644 --- a/apps/web-antd/src/views/crm/contact/detail/data.ts +++ b/apps/web-antd/src/views/crm/contact/detail/data.ts @@ -11,7 +11,7 @@ import { DictTag } from '#/components/dict-tag'; export function useDetailSchema(): DescriptionItemSchema[] { return [ { - field: 'name', + field: 'customerName', label: '客户名称', }, { @@ -24,7 +24,7 @@ export function useDetailSchema(): DescriptionItemSchema[] { }, { field: 'createTime', - label: '下次联系时间', + label: '创建时间', content: (data) => formatDateTime(data?.createTime) as string, }, ]; @@ -64,10 +64,11 @@ export function useDetailBaseSchema(): DescriptionItemSchema[] { { field: 'areaName', label: '地址', - }, - { - field: 'detailAddress', - label: '详细地址', + content: (data) => { + const areaName = data?.areaName ?? ''; + const detailAddress = data?.detailAddress ?? ''; + return [areaName, detailAddress].filter(Boolean).join(' '); + }, }, { field: 'post', diff --git a/apps/web-antd/src/views/crm/contact/detail/index.vue b/apps/web-antd/src/views/crm/contact/detail/index.vue index 96c8cb36..b7ac6bf1 100644 --- a/apps/web-antd/src/views/crm/contact/detail/index.vue +++ b/apps/web-antd/src/views/crm/contact/detail/index.vue @@ -134,7 +134,10 @@ onMounted(() => { - + + + + { @quit-team="handleBack" /> - + { :customer-id="contact.customerId" /> - - - diff --git a/apps/web-antd/src/views/crm/contract/detail/index.vue b/apps/web-antd/src/views/crm/contract/detail/index.vue index b09bd7e4..0bd119ac 100644 --- a/apps/web-antd/src/views/crm/contract/detail/index.vue +++ b/apps/web-antd/src/views/crm/contract/detail/index.vue @@ -130,10 +130,10 @@ onMounted(() => { - + - + diff --git a/apps/web-antd/src/views/crm/customer/detail/data.ts b/apps/web-antd/src/views/crm/customer/detail/data.ts index 0f45ff4a..5540a93e 100644 --- a/apps/web-antd/src/views/crm/customer/detail/data.ts +++ b/apps/web-antd/src/views/crm/customer/detail/data.ts @@ -53,6 +53,10 @@ export function useDetailSchema(): DescriptionItemSchema[] { label: '成交状态', content: (data) => (data.dealStatus ? '已成交' : '未成交'), }, + { + field: 'ownerUserName', + label: '负责人', + }, { field: 'createTime', label: '创建时间', @@ -92,10 +96,11 @@ export function useDetailBaseSchema(): DescriptionItemSchema[] { { field: 'areaName', label: '地址', - }, - { - field: 'detailAddress', - label: '详细地址', + content: (data) => { + const areaName = data?.areaName ?? ''; + const detailAddress = data?.detailAddress ?? ''; + return [areaName, detailAddress].filter(Boolean).join(' '); + }, }, { field: 'qq', @@ -114,12 +119,6 @@ export function useDetailBaseSchema(): DescriptionItemSchema[] { value: data?.industryId, }), }, - { - field: 'level', - label: '客户级别', - content: (data) => - h(DictTag, { type: DICT_TYPE.CRM_CUSTOMER_LEVEL, value: data?.level }), - }, { field: 'contactNextTime', label: '下次联系时间', diff --git a/apps/web-antd/src/views/crm/customer/detail/index.vue b/apps/web-antd/src/views/crm/customer/detail/index.vue index b796c0c3..d93a2059 100644 --- a/apps/web-antd/src/views/crm/customer/detail/index.vue +++ b/apps/web-antd/src/views/crm/customer/detail/index.vue @@ -279,7 +279,7 @@ onMounted(() => { - + diff --git a/apps/web-antd/src/views/crm/product/detail/data.ts b/apps/web-antd/src/views/crm/product/detail/data.ts index a43312dd..dc9bb6e1 100644 --- a/apps/web-antd/src/views/crm/product/detail/data.ts +++ b/apps/web-antd/src/views/crm/product/detail/data.ts @@ -22,7 +22,7 @@ export function useDetailSchema(): DescriptionItemSchema[] { }, { field: 'price', - label: '产品价格', + label: '产品价格(元)', content: (data) => erpPriceInputFormatter(data.price), }, { diff --git a/apps/web-antd/src/views/crm/receivable/data.ts b/apps/web-antd/src/views/crm/receivable/data.ts index 7997ecf9..02462722 100644 --- a/apps/web-antd/src/views/crm/receivable/data.ts +++ b/apps/web-antd/src/views/crm/receivable/data.ts @@ -64,6 +64,7 @@ export function useFormSchema(): VbenFormSchema[] { placeholder: '请选择客户', }, }, + // TODO @AI:这里的合同名称不对; { fieldName: 'contractId', label: '合同名称', @@ -121,14 +122,12 @@ export function useFormSchema(): VbenFormSchema[] { }, }, { - fieldName: 'returnTime', - label: '回款日期', - component: 'DatePicker', + fieldName: 'returnType', + label: '回款方式', + component: 'Select', componentProps: { - placeholder: '请选择回款日期', - showTime: false, - valueFormat: 'x', - format: 'YYYY-MM-DD', + options: getDictOptions(DICT_TYPE.CRM_RECEIVABLE_RETURN_TYPE, 'number'), + placeholder: '请选择回款方式', }, }, { @@ -143,13 +142,15 @@ export function useFormSchema(): VbenFormSchema[] { }, }, { - fieldName: 'returnType', - label: '回款方式', - component: 'Select', + fieldName: 'returnTime', + label: '回款日期', + component: 'DatePicker', rules: 'required', componentProps: { - options: getDictOptions(DICT_TYPE.CRM_RECEIVABLE_RETURN_TYPE, 'number'), - placeholder: '请选择回款方式', + placeholder: '请选择回款日期', + showTime: false, + valueFormat: 'x', + format: 'YYYY-MM-DD', }, }, { @@ -160,6 +161,7 @@ export function useFormSchema(): VbenFormSchema[] { placeholder: '请输入备注', rows: 4, }, + formItemClass: 'md:col-span-2', }, ]; } diff --git a/apps/web-antd/src/views/crm/receivable/detail/data.ts b/apps/web-antd/src/views/crm/receivable/detail/data.ts index f78afcc2..8c79dd54 100644 --- a/apps/web-antd/src/views/crm/receivable/detail/data.ts +++ b/apps/web-antd/src/views/crm/receivable/detail/data.ts @@ -16,8 +16,9 @@ export function useDetailSchema(): DescriptionItemSchema[] { }, { field: 'totalPrice', - label: '合同金额', - content: (data) => erpPriceInputFormatter(data.totalPrice), + label: '合同金额(元)', + content: (data) => + erpPriceInputFormatter(data?.contract?.totalPrice ?? data.totalPrice), }, { field: 'returnTime', @@ -26,7 +27,7 @@ export function useDetailSchema(): DescriptionItemSchema[] { }, { field: 'price', - label: '回款金额', + label: '回款金额(元)', content: (data) => erpPriceInputFormatter(data.price), }, { @@ -77,3 +78,27 @@ export function useDetailBaseSchema(): DescriptionItemSchema[] { }, ]; } + +/** 系统信息字段 */ +export function useDetailSystemSchema(): DescriptionItemSchema[] { + return [ + { + field: 'ownerUserName', + label: '负责人', + }, + { + field: 'creatorName', + label: '创建人', + }, + { + field: 'createTime', + label: '创建时间', + content: (data) => formatDateTime(data?.createTime) as string, + }, + { + field: 'updateTime', + label: '更新时间', + content: (data) => formatDateTime(data?.updateTime) as string, + }, + ]; +} diff --git a/apps/web-antd/src/views/crm/receivable/detail/index.vue b/apps/web-antd/src/views/crm/receivable/detail/index.vue index 81c521e7..82de47fc 100644 --- a/apps/web-antd/src/views/crm/receivable/detail/index.vue +++ b/apps/web-antd/src/views/crm/receivable/detail/index.vue @@ -114,7 +114,10 @@ onMounted(() => { - + + + + { @quit-team="handleBack" /> - - - diff --git a/apps/web-antd/src/views/crm/receivable/detail/modules/info.vue b/apps/web-antd/src/views/crm/receivable/detail/modules/info.vue index fdf6261c..dfad21c8 100644 --- a/apps/web-antd/src/views/crm/receivable/detail/modules/info.vue +++ b/apps/web-antd/src/views/crm/receivable/detail/modules/info.vue @@ -4,9 +4,8 @@ import type { CrmReceivableApi } from '#/api/crm/receivable'; import { Divider } from 'ant-design-vue'; import { useDescription } from '#/components/description'; -import { useFollowUpDetailSchema } from '#/views/crm/followup/data'; -import { useDetailBaseSchema } from '../data'; +import { useDetailBaseSchema, useDetailSystemSchema } from '../data'; defineProps<{ receivable: CrmReceivableApi.Receivable; // 收款信息 @@ -29,7 +28,7 @@ const [SystemDescriptions] = useDescription({ column: 3, class: 'mx-4', }, - schema: useFollowUpDetailSchema(), + schema: useDetailSystemSchema(), }); diff --git a/apps/web-antd/src/views/crm/receivable/plan/detail/data.ts b/apps/web-antd/src/views/crm/receivable/plan/detail/data.ts index f78afcc2..70d07164 100644 --- a/apps/web-antd/src/views/crm/receivable/plan/detail/data.ts +++ b/apps/web-antd/src/views/crm/receivable/plan/detail/data.ts @@ -15,23 +15,24 @@ export function useDetailSchema(): DescriptionItemSchema[] { label: '客户名称', }, { - field: 'totalPrice', - label: '合同金额', - content: (data) => erpPriceInputFormatter(data.totalPrice), - }, - { - field: 'returnTime', - label: '回款日期', - content: (data) => formatDateTime(data?.returnTime) as string, + field: 'contractNo', + label: '合同编号', }, { field: 'price', - label: '回款金额', + label: '计划回款金额', content: (data) => erpPriceInputFormatter(data.price), }, { - field: 'ownerUserName', - label: '负责人', + field: 'returnTime', + label: '计划回款日期', + content: (data) => formatDateTime(data?.returnTime) as string, + }, + { + field: 'receivable', + label: '实际回款金额', + content: (data) => + erpPriceInputFormatter(data?.receivable?.price ?? 0), }, ]; } @@ -40,40 +41,87 @@ export function useDetailSchema(): DescriptionItemSchema[] { export function useDetailBaseSchema(): DescriptionItemSchema[] { return [ { - field: 'no', - label: '回款编号', + field: 'period', + label: '期数', }, { field: 'customerName', label: '客户名称', }, { - field: 'contract', + field: 'contractNo', label: '合同编号', - content: (data) => data?.contract?.no, }, { field: 'returnTime', - label: '回款日期', + label: '计划回款日期', content: (data) => formatDateTime(data?.returnTime) as string, }, { field: 'price', - label: '回款金额', + label: '计划回款金额', content: (data) => erpPriceInputFormatter(data.price), }, { field: 'returnType', - label: '回款方式', + label: '计划回款方式', content: (data) => h(DictTag, { type: DICT_TYPE.CRM_RECEIVABLE_RETURN_TYPE, value: data?.returnType, }), }, + { + field: 'remindDays', + label: '提前几天提醒', + }, + { + field: 'receivable', + label: '实际回款金额', + content: (data) => + erpPriceInputFormatter(data?.receivable?.price ?? 0), + }, + { + field: 'receivableRemain', + label: '未回款金额', + content: (data) => { + const paid = data?.receivable?.price ?? 0; + return erpPriceInputFormatter(Math.max(data.price - paid, 0)); + }, + }, + { + field: 'receivable.returnTime', + label: '实际回款日期', + content: (data) => + formatDateTime(data?.receivable?.returnTime) as string, + }, { field: 'remark', label: '备注', }, ]; } + +/** 系统信息字段 */ +export function useDetailSystemSchema(): DescriptionItemSchema[] { + return [ + { + field: 'ownerUserName', + label: '负责人', + }, + { + field: 'creatorName', + label: '创建人', + }, + { + field: 'createTime', + label: '创建时间', + content: (data) => formatDateTime(data?.createTime) as string, + }, + { + field: 'updateTime', + label: '更新时间', + content: (data) => formatDateTime(data?.updateTime) as string, + }, + ]; +} diff --git a/apps/web-antd/src/views/crm/receivable/plan/detail/index.vue b/apps/web-antd/src/views/crm/receivable/plan/detail/index.vue index 3b855edd..59ba9ae3 100644 --- a/apps/web-antd/src/views/crm/receivable/plan/detail/index.vue +++ b/apps/web-antd/src/views/crm/receivable/plan/detail/index.vue @@ -121,7 +121,10 @@ onMounted(() => { - + + + + { @quit-team="handleBack" /> - - - diff --git a/apps/web-antd/src/views/crm/receivable/plan/detail/modules/info.vue b/apps/web-antd/src/views/crm/receivable/plan/detail/modules/info.vue index 12128cb5..c7c6c642 100644 --- a/apps/web-antd/src/views/crm/receivable/plan/detail/modules/info.vue +++ b/apps/web-antd/src/views/crm/receivable/plan/detail/modules/info.vue @@ -4,9 +4,8 @@ import type { CrmReceivablePlanApi } from '#/api/crm/receivable/plan'; import { Divider } from 'ant-design-vue'; import { useDescription } from '#/components/description'; -import { useFollowUpDetailSchema } from '#/views/crm/followup/data'; -import { useDetailBaseSchema } from '../data'; +import { useDetailBaseSchema, useDetailSystemSchema } from '../data'; defineProps<{ receivablePlan: CrmReceivablePlanApi.Plan; // 收款计划信息 @@ -29,7 +28,7 @@ const [SystemDescriptions] = useDescription({ column: 3, class: 'mx-4', }, - schema: useFollowUpDetailSchema(), + schema: useDetailSystemSchema(), });