refactor(erp): 更新产品分类和单位选择逻辑

- 优化库存和采购相关页面布局
- 修复供应商和仓库选择功能
- 调整统计页面显示内容
- 优化表单验证逻辑
This commit is contained in:
郑彪辉
2025-04-29 23:41:03 +08:00
parent 907bc6c61d
commit 73b9a68605
19 changed files with 109 additions and 79 deletions

View File

@@ -20,6 +20,14 @@ export function getProductTypeSelect() {
export function getProductTypeInfo(id : number) {
return request.get(`erp/product/type/${id}`);
}
// /**
// * 根据分类id查询商品
// * @param type 商品分类id
// * @returns
// */
// export function getProductByTypeList(type : number) {
// return request.get(`erp/product/getListsByType/${type}`);
// }
/**
* 添加商品分类

View File

@@ -4,7 +4,7 @@
"name": "食材名称",
"namePlaceholder": "请输入食材名称",
"productTypeId": "食材类型",
"productTypeIdPlaceholder": "请输入食材类型",
"productTypeIdPlaceholder": "请选择食材类型",
"spec": "规格",
"specPlaceholder": "请输入规格",
"inventory": "食材库存",
@@ -18,7 +18,7 @@
"remark": "备注",
"remarkPlaceholder": "请输入备注",
"productUnitId": "单位",
"productUnitIdPlaceholder": "请输入单位",
"productUnitIdPlaceholder": "请选择单位",
"unit": "单位值",
"unitPlaceholder": "请输入单位值",
"image": "图片",

View File

@@ -4,7 +4,7 @@
"name":"食材名称",
"namePlaceholder":"请输入食材名称",
"productTypeId":"食材类型",
"productTypeIdPlaceholder":"请输入食材类型",
"productTypeIdPlaceholder":"请选择食材类型",
"spec":"食材规格",
"specPlaceholder":"请输入规格",
"inventory":"食材库存",
@@ -18,7 +18,7 @@
"remark":"备注",
"remarkPlaceholder":"请输入备注",
"productUnitId":"食材单位",
"productUnitIdPlaceholder":"请输入单位",
"productUnitIdPlaceholder":"请选择单位",
"unit":"单位值",
"unitPlaceholder":"请输入单位值",
"image":"图片",

View File

@@ -1,5 +1,5 @@
{
"dataSummary": "今日汇总",
"dataSummary": "汇总数据",
"updateTime": "更新时间",
"todayPurchaseCount": "今日入库订单数",
"purchaseCount": "采购订单总数",

View File

@@ -2,11 +2,11 @@
<view class="bg-[var(--page-bg-color)] min-h-[100vh] overflow-hidden form-edit" :style="themeColor()">
<u-form labelPosition="left" :model="formData" errorType='toast' :rules="rules" ref="formRef" labelWidth="180rpx">
<view class="sidebar-margin card-template mt-[var(--top-m)] py-[20rpx]">
<view>
<!-- <view>
<u-form-item :label="t('code')" prop="code" required borderBottom>
<u-input fontSize="28rpx" v-model.trim="formData.code" disabled clearable placeholderStyle="color: #888" :placeholder="t('codePlaceholderNew')"/>
</u-form-item>
</view>
</view> -->
<view class="mt-[16rpx]">
<u-form-item :label="t('name')" prop="name" required borderBottom>
<u-input fontSize="28rpx" v-model.trim="formData.name" clearable placeholderStyle="color: #888" :placeholder="t('namePlaceholder')"/>

View File

@@ -3,9 +3,9 @@
<view class="mx-[30rpx]">
<!-- 注意如果需要兼容微信小程序最好通过setRules方法设置rules规则 -->
<up-form labelPosition="left" :model="formData" labelWidth="160rpx" ref="formRef">
<up-form-item :label="t('code')" borderBottom>
<!-- <up-form-item :label="t('code')" borderBottom>
{{formData.code}}
</up-form-item>
</up-form-item> -->
<up-form-item :label="t('name')" borderBottom>
{{formData.name}}
</up-form-item>

View File

@@ -4,11 +4,11 @@
<u-form labelPosition="left" :model="formData" errorType='toast' :rules="rules" ref="formRef"
labelWidth="160rpx">
<view class="sidebar-margin card-template mt-[var(--top-m)] py-[20rpx]">
<view>
<!-- <view>
<u-form-item :label="t('code')" prop="code" borderBottom required>
<u-input fontSize="28rpx" v-model="formData.code" :placeholder="t('codePlaceholderNew')" disabled ></u-input>
</u-form-item>
</view>
</view> -->
<view class="mt-[16rpx]">
<u-form-item :label="t('name')" prop="name" borderBottom required>
<u-input fontSize="28rpx" v-model="formData.name" :placeholder="t('namePlaceholder')" ></u-input>

View File

@@ -3,9 +3,9 @@
<view class="mx-[30rpx]">
<!-- 注意如果需要兼容微信小程序最好通过setRules方法设置rules规则 -->
<up-form labelPosition="left" :model="formData" labelWidth="160rpx" ref="formRef">
<up-form-item :label="t('code')" borderBottom>
<!-- <up-form-item :label="t('code')" borderBottom>
{{formData.code}}
</up-form-item>
</up-form-item> -->
<up-form-item :label="t('name')" borderBottom>
{{formData.name}}
</up-form-item>

View File

@@ -3,9 +3,9 @@
<view class="mx-[30rpx]">
<!-- 注意如果需要兼容微信小程序最好通过setRules方法设置rules规则 -->
<up-form labelPosition="left" :model="formData" labelWidth="160rpx" ref="formRef">
<up-form-item :label="t('number')" borderBottom>
<!-- <up-form-item :label="t('number')" borderBottom>
{{formData.number}}
</up-form-item>
</up-form-item> -->
<up-form-item :label="t('name')" borderBottom>
{{formData.name}}
</up-form-item>

View File

@@ -80,7 +80,7 @@
</up-form-item>
</view>
<view class="mt-[16rpx]">
<u-form-item :label="t('inboundImage')" prop="inbound_image" borderBottom>
<u-form-item :label="t('inboundImage')" required prop="inbound_image" borderBottom>
<up-upload
:fileList="imageFileList"
@afterRead="afterRead"
@@ -343,9 +343,9 @@
*/
const canteenList = ref<any[]>([]);
const customeChange=(e: any) =>{
formData.value.customer_id = e.id
formData.value.contact = e.contact
formData.value.phone = e.phone
formData.value.customer_id = e.id
formData.value.contact = e?.contact ?? ''
formData.value.phone = e?.phone ?? ''
formData.value.address = e?.address ?? ''
getOutboundManualAllFn(e.id)
if (formRef.value) {
@@ -400,7 +400,10 @@
if (!formData.value.billing_time) {
uni.showToast({ icon: 'none', title: t('billingTimePlaceholder') })
return false;
}
}
if (imageFileList.value.length === 0) {
uni.showToast({ icon: 'none', title: '请上传图片' })
return false;
}
loading.value = true
formData.value.total_num = totalData.value.total_num;

View File

@@ -109,7 +109,7 @@
placeholder="请输入拒绝原因" />
</view>
</up-modal>
<view class="fixed bottom-4 right-4 z-2">
<view v-if="hasPermission('erp_inbound_return_add')" class="fixed bottom-4 right-4 z-2">
<up-button @click="redirect({ url: '/addon/erp/pages/canteen/return/add'})" type="primary" shape="circle"
:customStyle="{borderRadius: '50%',padding: 0,width: '50px',height: '50px'}">
<u-icon size="30" color="#fff" name="plus-circle-fill"></u-icon>

View File

@@ -92,13 +92,13 @@
</up-form-item>
</view>
<view class="mt-[16rpx]">
<up-form-item :label="t('inboundImage')" prop="inbound_image">
<up-form-item :label="t('inboundImage')" required prop="inbound_image">
<up-upload :fileList="inbinboundImageFileList" @afterRead="afterRead" @delete="imageDelete" multiple :maxCount="5"
accept="image" :capture="['camera']"></up-upload>
</up-form-item>
</view>
<view class="mt-[16rpx]">
<up-form-item :label="t('inspectionReportImage')" prop="inspection_report_image">
<up-form-item :label="t('inspectionReportImage')" required prop="inspection_report_image">
<up-upload :fileList="inspectionReportImageFileList" @afterRead="inspectionReportImageAfterRead" @delete="imageDelete2"
multiple :maxCount="5" accept="image" :capture="['camera']"></up-upload>
</up-form-item>
@@ -302,7 +302,7 @@
item.purchase_price = 0;
item.inbound_quantity = 1;
item.expiry_term = item.expiry_term || 0
item.unit = item.productUnit?.name
item.unit = item.productUnit?.name ?? ''
return item;
});
})
@@ -392,8 +392,8 @@
*/
const supplierList = ref<any[]>([]);
const supplierIdChange = (e : any) => {
formData.value.supplier_id = e.id;
formData.value.supplier_name = e.name;
formData.value.supplier_id = e?.id ?? '';
formData.value.supplier_name = e?.name ?? '';
if (formRef.value) {
formRef.value.validateField('supplier_id');
}
@@ -504,7 +504,14 @@
uni.showToast({ icon: 'none', title: t('batchNumberPlaceholder') })
return false;
}
if (inbinboundImageFileList.value.length === 0) {
uni.showToast({ icon: 'none', title: '请上传图片' })
return false;
}
if (inspectionReportImageFileList.value.length === 0) {
uni.showToast({ icon: 'none', title: '请上传检验图片' })
return false;
}
loading.value = true
formData.value.total_num = totalData.value.nums;
formData.value.total_amount = totalData.value.money;

View File

@@ -170,8 +170,8 @@
// 获取状态
const getTypeAllFn = () => {
getCheckTypeList().then((res) => {
const data= Object.values(res.data);
typeList.value =data.map((item:any)=>{
const data = Object.values(res.data);
typeList.value = data.map((item:any)=>{
return {name:item}
})
});
@@ -183,7 +183,7 @@
*/
const warehouseList = ref<any[]>([]);
const updateSexWarehouse = (e : any) => {
formData.value.warehouse_id = e.id;
formData.value.warehouse_id = e?.id ?? '';
formData.value.inventory_id = ''
formData.value.product_id = ''
formData.value.surface_num = ''
@@ -213,17 +213,17 @@
// 食材
const productList = ref<any[]>([]);
const productIdChange = (e : any) => {
formData.value.product_id = e.product_id;
formData.value.product_id = e?.product_id ?? '';
handleProductIdChange(e.product_id);
}
// 批次号
const inventoryIdChange = (e : any) => {
formData.value.inventory_id = e.inventory_id;
formData.value.inventory_id = e?.inventory_id ?? '';
}
// 盘点结果
const typeChange = (e : any) => {
formData.value.type = e.name;
formData.value.type = e?.name ?? '';
}
// 食材选择事件
@@ -231,8 +231,8 @@
const product = productList.value.find((item) => item.product_id === val);
batchNumberList.value = productList.value.filter((item) => item.product_id === val)
if (product) {
formData.value.surface_num = product.surface_num;
formData.value.freeze = product.freeze
formData.value.surface_num = product?.surface_num ?? '';
formData.value.freeze = product?.freeze ?? ''
}
};

View File

@@ -39,17 +39,17 @@
placeholderStyle="color: #888" :placeholder="'请输入详细地址'" />
</up-form-item>
</view>
<view class="mt-[16rpx]">
<up-form-item :label="'供应商'" prop="supplier_id" borderBottom>
<!-- <view class="mssst-[16rpx]"> -->
<!-- <up-form-item :label="'供应商'" prop="supplier_id" borderBottom> -->
<!-- #ifdef H5 -->
<zxz-uni-data-select v-model="formData.supplier_id" :localdata="supplierList" dataKey="name" dataValue="id"
:clear="false" placeholder="请选择供应商" @change="supplierIdChange"/>
<!-- <zxz-uni-data-select v-model="formData.supplier_id" :localdata="supplierList" dataKey="name" dataValue="id"
:clear="false" placeholder="请选择供应商" @change="supplierIdChange"/> -->
<!-- #endif -->
<!-- #ifdef MP-WEIXIN -->
<wht-select v-model="formData.supplier_id" :options="supplierList" dataKey="name" dataValue="id" placeholder="请选择供应商" :height="38" @change="supplierIdChange"/>
<!-- <wht-select v-model="formData.supplier_id" :options="supplierList" dataKey="name" dataValue="id" placeholder="请选择供应商" :height="38" @change="supplierIdChange"/> -->
<!-- #endif -->
</up-form-item>
</view>
<!-- </up-form-item> -->
<!-- </view> -->
<view class="mt-[16rpx]">
<up-form-item :label="'交货方式'" prop="type" required borderBottom>
<!-- #ifdef H5 -->
@@ -363,8 +363,8 @@
* 供应商
*/
const supplierList = ref<any[]>([]);
const supplierIdChange = (e : any) => {
formData.value.supplier_id = e.id;
const supplierIdChange = (e : any) => {
formData.value.supplier_id = e?.id ?? '';
formData.value.supplier_name = e?.name ?? '';
if (formRef.value) {
formRef.value.validateField('supplier_id');

View File

@@ -4,14 +4,14 @@
labelWidth="180rpx">
<view class="sidebar-margin card-template mt-[var(--top-m)] py-[20rpx]">
<view>
<u-form-item :label="t('productTypeId')" prop="name" required borderBottom>
<view class="flex w-full items-center h-[52rpx]" @click="pidSheetShow = true">
<view v-if="!formData.product_type_id" class="text-[#888] text-[28rpx] flex-1">
{{ t('productTypeIdPlaceholder') }}
</view>
<view v-else class="text-[28rpx] flex-1 leading-[1.4]">{{ formData.product_type_name }}
</view>
</view>
<u-form-item :label="t('productTypeId')" prop="product_type_id" required borderBottom>
<!-- #ifdef H5 -->
<zxz-uni-data-select v-model="formData.product_type_id" :localdata="pidList" dataKey="name" dataValue="id"
:clear="false" placeholder="请选择食材类型" @change="updateSex"/>
<!-- #endif -->
<!-- #ifdef MP-WEIXIN -->
<wht-select v-model="formData.product_type_id" :options="pidList" dataKey="name" dataValue="id" :defaultVal="formData.product_type_id" placeholder="请选择食材类型" :height="38" @change="updateSex"/>
<!-- #endif -->
</u-form-item>
</view>
<view class="mt-[16rpx]">
@@ -28,13 +28,13 @@
</view>
<view class="mt-[16rpx]">
<u-form-item :label="t('productUnitId')" required prop="product_unit_id" borderBottom>
<view class="flex w-full items-center h-[52rpx]" @click="unitSheetShow = true">
<view v-if="!formData.product_unit_id" class="text-[#888] text-[28rpx] flex-1">
{{ t('productUnitIdPlaceholder') }}
</view>
<view v-else class="text-[28rpx] flex-1 leading-[1.4]">{{ formData.product_unit_name }}
</view>
</view>
<!-- #ifdef H5 -->
<zxz-uni-data-select v-model="formData.product_unit_id" :localdata="unitList" dataKey="name" dataValue="id"
:clear="false" placeholder="请选择单位" @change="updateSexUnit"/>
<!-- #endif -->
<!-- #ifdef MP-WEIXIN -->
<wht-select v-model="formData.product_unit_id" :options="unitList" dataKey="name" dataValue="id" :defaultVal="formData.product_type_id" placeholder="请选择单位" :height="38" @change="updateSexUnit"/>
<!-- #endif -->
</u-form-item>
</view>
<view class="mt-[16rpx]">
@@ -91,15 +91,6 @@
</view>
</u-form>
<!-- 食材分类 -->
<u-action-sheet class="" :actions="pidList" :show="pidSheetShow" :closeOnClickOverlay="true"
:safeAreaInsetBottom="true" @close="pidSheetShow = false" @select="updateSex"></u-action-sheet>
<!-- 食材单位 -->
<u-action-sheet class="" :actions="unitList" :show="unitSheetShow" :closeOnClickOverlay="true"
:safeAreaInsetBottom="true" @close="unitSheetShow = false" @select="updateSexUnit"></u-action-sheet>
<view v-if="hasPermission('erp_product_add')" class="w-full footer">
<view
class="py-[var(--top-m)] px-[var(--sidebar-m)] footer w-full fixed bottom-0 left-0 right-0 box-border">
@@ -141,7 +132,7 @@
type: 'string',
required: true,
message: t('productTypeIdPlaceholder'),
trigger: ['blur', 'change'],
trigger: ['change'],
},
'name': {
type: 'string',
@@ -186,7 +177,6 @@
/**
* 分类
*/
const pidSheetShow = ref(false)
const pidList = ref<any[]>([]);
const updateSex = (e : any) => {
formData.value.product_type_id = e.id;
@@ -207,7 +197,6 @@
/**
* 单位
*/
const unitSheetShow = ref(false)
const unitList = ref<any[]>([]);
const updateSexUnit = (e : any) => {
formData.value.product_unit_id = e.id;

View File

@@ -80,8 +80,6 @@
queryType.value = option.type ? option.type : '';
warehouse_id.value = option.warehouse_id ? option.warehouse_id : undefined
})
const mescrollTop = "20rpx"
const productList = ref<Array<any>>([]),

View File

@@ -51,7 +51,7 @@
</up-form-item>
</view>
<view class="mt-[16rpx]">
<u-form-item :label="t('image')" prop="image" borderBottom>
<u-form-item :label="t('image')" required prop="image" borderBottom>
<up-upload
:fileList="imageFileList"
@afterRead="afterRead"
@@ -340,7 +340,7 @@
*/
const warehouseList = ref<any[]>([]);
const warehouseIdChange = (e : any) => {
formData.value.warehouse_id = e.id;
formData.value.warehouse_id = e?.id ?? '';
if (formRef.value) {
formRef.value.validateField('warehouse_id');
}
@@ -400,6 +400,10 @@
uni.showToast({ icon: 'none', title: t('billingTimePlaceholder') })
return false;
}
if (imageFileList.value.length === 0) {
uni.showToast({ icon: 'none', title: '请上传图片' })
return false;
}
loading.value = true
formData.value.total_num = totalData.value.nums;
formData.value.total_amount = totalData.value.money;
@@ -407,7 +411,7 @@
if(imageFileList.value.length > 0){
const imgUrls=imageFileList.value.map((item:any)=>{
return `upload${item.url.split('upload')[1]}`
})
})|| []
formData.value.outbound_image=imgUrls.join(',')
}

View File

@@ -26,9 +26,30 @@
class="text-center color-[#909399] text-[28rpx] pt-[20rpx] pb-[20rpx]">{{t('todaySellSale')}}</text>
<up-count-to :startVal="0" :endVal="baseInfo.sell_price.today" color="#007aff"></up-count-to>
</up-grid-item>
<up-grid-item class="pt-[20rpx]">
<text
class="text-center color-[#909399] text-[28rpx] pt-[20rpx] pb-[20rpx]">入库订单总数</text>
<up-count-to :startVal="0" :endVal="baseInfo.purchase_count.total" color="#007aff"></up-count-to>
</up-grid-item>
<up-grid-item class="pt-[20rpx]">
<text
class="text-center color-[#909399] text-[28rpx] pt-[20rpx] pb-[20rpx]">入库总额()</text>
<up-count-to :startVal="0" :endVal="baseInfo.purchase_price.total" color="#007aff"></up-count-to>
</up-grid-item>
<up-grid-item class="pt-[20rpx]">
<text
class="text-center color-[#909399] text-[28rpx] pt-[20rpx] pb-[20rpx]">出库订单总数</text>
<up-count-to :startVal="0" :endVal="baseInfo.sell_count.total" color="#007aff"></up-count-to>
</up-grid-item>
<up-grid-item class="pt-[20rpx]">
<text
class="text-center color-[#909399] text-[28rpx] pt-[20rpx] pb-[20rpx]">出库总额()</text>
<up-count-to :startVal="0" :endVal="baseInfo.sell_price.total" color="#007aff"></up-count-to>
</up-grid-item>
</up-grid>
</view>
<view class="statistics-title" >待办事项</view>
<view class="sidebar-margin mt-[20rpx] bg-[#ffffff] br-gg">
<up-grid :border="true" col="2" align="center">
<up-grid-item class="pt-[20rpx]">

View File

@@ -1,6 +1,6 @@
{
"name" : "食堂溯源系统",
"appid" : "__UNI__3023471",
"appid" : "__UNI__E8719AF",
"description" : "",
"versionName" : "1.0.0",
"versionCode" : "100",