- 移除CostSummarySection中formatCurrency调用,保持数值类型 - 根据订单类型动态显示PackageInfoSection销售单价列 - 为ProductionLossSection和TaxProvisionSection添加calculator参数 - 为TaxSubsidySection添加calculator参数支持 - 优化审计页面提交逻辑,添加calculator计算回填 - 简化组件onChange回调处理 - 改进CostCalculator中空值判断逻辑
266 lines
7.4 KiB
TypeScript
266 lines
7.4 KiB
TypeScript
import { formatCurrency } from "@/utils";
|
|
import { useEffect, useState } from "react";
|
|
import { Table } from "@nutui/nutui-react-taro";
|
|
import { Icon } from "@/components";
|
|
import { View } from "@tarojs/components";
|
|
import { Decimal } from "decimal.js";
|
|
|
|
export default function PackageInfoSection(props: {
|
|
orderVO: BusinessAPI.OrderVO;
|
|
onChange?: (orderVO: BusinessAPI.OrderVO) => void;
|
|
readOnly?: boolean;
|
|
}) {
|
|
const { orderVO, readOnly } = props;
|
|
|
|
const defaultColumns = [
|
|
{
|
|
title: "纸箱型号",
|
|
key: "boxProductName",
|
|
fixed: "left",
|
|
},
|
|
{
|
|
title: "个数",
|
|
key: "boxProductCount",
|
|
},
|
|
...(orderVO.type === "PRODUCTION_PURCHASE"
|
|
? [
|
|
{
|
|
title: "销售单价(元/斤)",
|
|
key: "boxSalePrice",
|
|
render: (
|
|
value: BusinessAPI.OrderPackage & {
|
|
orderPackageId?: string;
|
|
isTotalRow?: boolean;
|
|
},
|
|
) => {
|
|
// 合计行不显示编辑按钮
|
|
if (value.isTotalRow) {
|
|
return formatCurrency(value.boxSalePrice as number);
|
|
}
|
|
|
|
return (
|
|
<View
|
|
className="flex w-full items-center justify-between"
|
|
onClick={(e) => {
|
|
if (!readOnly) {
|
|
e.stopPropagation();
|
|
}
|
|
}}
|
|
>
|
|
<View className={!readOnly ? "cursor-pointer underline" : ""}>
|
|
{formatCurrency(value.boxSalePrice as number)}
|
|
</View>
|
|
{!readOnly && (
|
|
<View className="-m-2 ml-2 flex items-center justify-center p-2">
|
|
<Icon
|
|
name={"pen-to-square"}
|
|
size={16}
|
|
color={"#1a73e8"}
|
|
/>
|
|
</View>
|
|
)}
|
|
</View>
|
|
);
|
|
},
|
|
},
|
|
{
|
|
title: "销售金额(元)",
|
|
key: "boxSalePayment",
|
|
},
|
|
]
|
|
: []),
|
|
{
|
|
title: "箱重(斤)",
|
|
key: "boxProductWeight",
|
|
render: (
|
|
value: BusinessAPI.OrderPackage & {
|
|
orderPackageId?: string;
|
|
isTotalRow?: boolean;
|
|
},
|
|
) => formatCurrency(value.boxProductWeight),
|
|
},
|
|
{
|
|
title: "品牌",
|
|
key: "boxBrandName",
|
|
},
|
|
];
|
|
const [columns, setColumns] = useState<any[]>(defaultColumns);
|
|
|
|
useEffect(() => {
|
|
if (!readOnly) {
|
|
setColumns([...defaultColumns]);
|
|
}
|
|
}, [readOnly]);
|
|
|
|
// 将所有包装信息合并并按品牌、型号、规格分组
|
|
const groupedPackageData = orderVO.orderSupplierList?.reduce(
|
|
(acc, supplier) => {
|
|
supplier.orderPackageList
|
|
?.filter((pkg) => pkg.boxType === "USED")
|
|
?.forEach((pkg) => {
|
|
// 生成分组键
|
|
const key = `${pkg.boxBrandName}-${pkg.boxProductName}-${pkg.boxSpecId}`;
|
|
|
|
// 转换规格字段
|
|
const boxSpecId = pkg.boxSpecId;
|
|
const boxSpecName = pkg.boxSpecName;
|
|
|
|
if (!acc[key]) {
|
|
acc[key] = {
|
|
...pkg,
|
|
boxSpecId,
|
|
boxSpecName,
|
|
boxProductCount: 0,
|
|
};
|
|
}
|
|
|
|
// 累加数量
|
|
acc[key].boxProductCount += pkg.boxCount || 0;
|
|
});
|
|
|
|
return acc;
|
|
},
|
|
{} as Record<string, any>,
|
|
);
|
|
|
|
// 转换为数组格式
|
|
const packageData = Object.values(groupedPackageData || {});
|
|
|
|
// 计算合计数据
|
|
const calculateTotals = () => {
|
|
if (!packageData || packageData.length === 0) {
|
|
return {};
|
|
}
|
|
|
|
// 计算各项合计
|
|
let totalBoxProductCount = new Decimal(0);
|
|
let totalBoxSalePayment = new Decimal(0);
|
|
let totalBoxProductWeight = new Decimal(0);
|
|
|
|
packageData.forEach((pkg: any) => {
|
|
totalBoxProductCount = totalBoxProductCount.add(pkg.boxProductCount || 0);
|
|
totalBoxSalePayment = totalBoxSalePayment.add(
|
|
new Decimal(pkg?.boxSalePrice || 0)
|
|
.mul(pkg.boxProductCount || 0)
|
|
.toDecimalPlaces(0, Decimal.ROUND_HALF_UP),
|
|
);
|
|
totalBoxProductWeight = totalBoxProductWeight.add(
|
|
new Decimal(pkg?.boxProductWeight || 0)
|
|
.mul(pkg.boxProductCount || 0)
|
|
.toDecimalPlaces(0, Decimal.ROUND_HALF_UP),
|
|
);
|
|
});
|
|
|
|
return {
|
|
boxProductName: "合计",
|
|
boxProductCount: totalBoxProductCount.toNumber(),
|
|
boxSalePayment: totalBoxSalePayment.toNumber(),
|
|
boxProductWeight: totalBoxProductWeight.toNumber(),
|
|
isTotalRow: true, // 标记这是合计行
|
|
};
|
|
};
|
|
|
|
const totalsData = calculateTotals();
|
|
|
|
// 创建包含合计行的数据
|
|
const dataWithTotals = [...packageData];
|
|
if (Object.keys(totalsData).length > 0) {
|
|
dataWithTotals.push(totalsData);
|
|
}
|
|
|
|
// 自定义列配置,对合计行特殊处理
|
|
const columnsWithTotalsRender = columns.map((column) => {
|
|
if (column.key === "boxProductName") {
|
|
// 品牌列显示"合计"
|
|
return {
|
|
...column,
|
|
render: (rowData: any) => {
|
|
if (rowData.isTotalRow) {
|
|
return (
|
|
<span style={{ fontWeight: "bold" }}>
|
|
{rowData.boxProductName}
|
|
</span>
|
|
);
|
|
}
|
|
return rowData.boxProductName;
|
|
},
|
|
};
|
|
} else if (column.key === "boxProductCount") {
|
|
// 个数列显示合计
|
|
return {
|
|
...column,
|
|
render: (rowData: any) => {
|
|
if (rowData.isTotalRow) {
|
|
return (
|
|
<span style={{ fontWeight: "bold" }}>
|
|
{rowData.boxProductCount}
|
|
</span>
|
|
);
|
|
}
|
|
return rowData.boxProductCount;
|
|
},
|
|
};
|
|
} else if (column.key === "boxSalePrice") {
|
|
// 销售单价列合计行处理
|
|
return {
|
|
...column,
|
|
render: (rowData: any) => {
|
|
if (rowData.isTotalRow) {
|
|
return (
|
|
<span style={{ fontWeight: "bold" }}>
|
|
{formatCurrency(rowData.boxSalePrice as number)}
|
|
</span>
|
|
);
|
|
}
|
|
return column.render(rowData, rowData);
|
|
},
|
|
};
|
|
} else if (column.key === "boxSalePayment") {
|
|
// 销售金额列显示合计
|
|
return {
|
|
...column,
|
|
render: (rowData: any) => {
|
|
if (rowData.isTotalRow) {
|
|
return (
|
|
<span style={{ fontWeight: "bold" }}>
|
|
{formatCurrency(rowData.boxSalePayment)}
|
|
</span>
|
|
);
|
|
}
|
|
return new Decimal(rowData?.boxSalePrice || 0)
|
|
.mul(rowData.boxProductCount)
|
|
.toDecimalPlaces(0, Decimal.ROUND_HALF_UP)
|
|
.toNumber();
|
|
},
|
|
};
|
|
} else if (column.key === "boxProductWeight") {
|
|
// 重量列合计行处理
|
|
return {
|
|
...column,
|
|
render: (rowData: any) => {
|
|
if (rowData.isTotalRow) {
|
|
return (
|
|
<span style={{ fontWeight: "bold" }}>
|
|
{formatCurrency(rowData.boxProductWeight)}
|
|
</span>
|
|
);
|
|
}
|
|
return column.render(rowData, rowData);
|
|
},
|
|
};
|
|
}
|
|
|
|
// 其他列保持原有render函数或者默认显示
|
|
return column;
|
|
});
|
|
|
|
return (
|
|
<Table
|
|
className={"table-sum"}
|
|
columns={columnsWithTotalsRender}
|
|
data={dataWithTotals}
|
|
striped
|
|
/>
|
|
);
|
|
}
|