refactor(order): 优化订单处理逻辑和界面显示
- 修复经销商信息显示逻辑,正确处理名称和瓜品等级的显示 - 移除PDF自动保存功能,仅保留下载成功提示 - 更新按钮样式为外框样式,改善视觉效果 - 优化箱重计算精度,添加小数位处理 - 移除货币格式化,直接显示数值 - 添加供应商银行名称字段并优化验证逻辑 - 改进供应商信息表单的空值处理 - 优化车次号获取逻辑,支持强制重新获取 - 实现包装信息表格的可编辑功能,支持销售单价修改 - 修复表格渲染逻辑,正确处理合计行显示 - 更新应用版本号至v0.0.61 - 优化PDF模板中经销商和目的地信息的显示逻辑 - 修复订单转换器中的价格计算逻辑 - 调整发货单转换器中的包装分组逻辑
This commit is contained in:
parent
438e17f093
commit
4b9d0002d7
@ -65,25 +65,11 @@ export default function Step3Success(props: Step3SuccessProps) {
|
|||||||
|
|
||||||
if (downloadRes.tempFilePath) {
|
if (downloadRes.tempFilePath) {
|
||||||
setTempFilePath(downloadRes.tempFilePath);
|
setTempFilePath(downloadRes.tempFilePath);
|
||||||
|
Taro.showToast({
|
||||||
// 保存PDF到手机
|
title: "PDF下载成功",
|
||||||
if (Taro.saveFile) {
|
icon: "success",
|
||||||
await Taro.saveFile({
|
duration: 2000,
|
||||||
tempFilePath: downloadRes.tempFilePath,
|
});
|
||||||
});
|
|
||||||
|
|
||||||
Taro.showToast({
|
|
||||||
title: "PDF下载成功",
|
|
||||||
icon: "success",
|
|
||||||
duration: 2000,
|
|
||||||
});
|
|
||||||
} else {
|
|
||||||
// 如果不支持saveFile,直接提示下载完成
|
|
||||||
Taro.openDocument({
|
|
||||||
filePath: downloadRes.tempFilePath,
|
|
||||||
showMenu: true,
|
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error("下载PDF失败:", error);
|
console.error("下载PDF失败:", error);
|
||||||
@ -173,8 +159,9 @@ export default function Step3Success(props: Step3SuccessProps) {
|
|||||||
{tempFilePath && (
|
{tempFilePath && (
|
||||||
<View className="flex-1">
|
<View className="flex-1">
|
||||||
<Button
|
<Button
|
||||||
icon={<Icon name="eye" size={16} color={"white"} />}
|
icon={<Icon name="eye" size={16} />}
|
||||||
type="default"
|
type="primary"
|
||||||
|
fill={"outline"}
|
||||||
size={"large"}
|
size={"large"}
|
||||||
block
|
block
|
||||||
onClick={handleViewPDF}
|
onClick={handleViewPDF}
|
||||||
|
|||||||
@ -11,17 +11,17 @@ export default function DealerInfo(props: { module: any }) {
|
|||||||
<View className="col-span-1"></View>
|
<View className="col-span-1"></View>
|
||||||
{config.showDealerName || config.showWatermelonGrade ? (
|
{config.showDealerName || config.showWatermelonGrade ? (
|
||||||
<View className="col-span-3 flex items-end justify-center border-b border-black">
|
<View className="col-span-3 flex items-end justify-center border-b border-black">
|
||||||
{config.showWatermelonGrade
|
{config.showDealerName ? config.dealerName : ""}
|
||||||
? `${config.dealerName}-${config.watermelonGrade}`
|
{config.showDealerName && config.showWatermelonGrade ? "- " : ""}
|
||||||
: config.dealerName}
|
{config.showWatermelonGrade ? config.watermelonGrade : ""}
|
||||||
</View>
|
</View>
|
||||||
) : (
|
) : (
|
||||||
<View className="col-span-3"></View>
|
<View className="col-span-3"></View>
|
||||||
)}
|
)}
|
||||||
{config.showDestination || config.showVehicleNumber ? (
|
{config.showDestination || config.showVehicleNumber ? (
|
||||||
<View className="col-span-3 flex items-end justify-center border-b border-black">
|
<View className="col-span-3 flex items-end justify-center border-b border-black">
|
||||||
{config.destination}
|
{config.showDestination ? config.destination : ""}
|
||||||
{config.vehicleNumber}
|
{config.showVehicleNumber ? config.vehicleNumber : ""}
|
||||||
</View>
|
</View>
|
||||||
) : (
|
) : (
|
||||||
<View className="col-span-3"></View>
|
<View className="col-span-3"></View>
|
||||||
|
|||||||
@ -544,6 +544,7 @@ export default function MadePreview(props: IPurchasePreviewProps) {
|
|||||||
sum +
|
sum +
|
||||||
new Decimal(item.boxProductWeight || 0)
|
new Decimal(item.boxProductWeight || 0)
|
||||||
.mul(new Decimal(item.boxCount || 0))
|
.mul(new Decimal(item.boxCount || 0))
|
||||||
|
.toDecimalPlaces(0)
|
||||||
.toNumber(),
|
.toNumber(),
|
||||||
0,
|
0,
|
||||||
);
|
);
|
||||||
@ -594,7 +595,7 @@ export default function MadePreview(props: IPurchasePreviewProps) {
|
|||||||
<View className="text-gray-600">
|
<View className="text-gray-600">
|
||||||
<View className="text-xs">箱重</View>
|
<View className="text-xs">箱重</View>
|
||||||
<View className="font-semibold text-gray-900">
|
<View className="font-semibold text-gray-900">
|
||||||
{formatCurrency(brandBoxWeight)} 斤
|
{brandBoxWeight} 斤
|
||||||
</View>
|
</View>
|
||||||
</View>
|
</View>
|
||||||
</View>
|
</View>
|
||||||
@ -647,6 +648,7 @@ export default function MadePreview(props: IPurchasePreviewProps) {
|
|||||||
sum +
|
sum +
|
||||||
new Decimal(item.boxProductWeight || 0)
|
new Decimal(item.boxProductWeight || 0)
|
||||||
.mul(new Decimal(item.boxCount || 0))
|
.mul(new Decimal(item.boxCount || 0))
|
||||||
|
.toDecimalPlaces(0)
|
||||||
.toNumber(),
|
.toNumber(),
|
||||||
0,
|
0,
|
||||||
);
|
);
|
||||||
@ -697,7 +699,7 @@ export default function MadePreview(props: IPurchasePreviewProps) {
|
|||||||
<View className="text-gray-600">
|
<View className="text-gray-600">
|
||||||
<View className="text-xs">箱重</View>
|
<View className="text-xs">箱重</View>
|
||||||
<View className="font-semibold text-gray-900">
|
<View className="font-semibold text-gray-900">
|
||||||
{formatCurrency(brandBoxWeight)} 斤
|
{brandBoxWeight} 斤
|
||||||
</View>
|
</View>
|
||||||
</View>
|
</View>
|
||||||
</View>
|
</View>
|
||||||
|
|||||||
@ -471,6 +471,7 @@ export default function MarketPreview(props: IMarketPreviewProps) {
|
|||||||
sum +
|
sum +
|
||||||
new Decimal(item.boxProductWeight || 0)
|
new Decimal(item.boxProductWeight || 0)
|
||||||
.mul(new Decimal(item.boxCount || 0))
|
.mul(new Decimal(item.boxCount || 0))
|
||||||
|
.toDecimalPlaces(0)
|
||||||
.toNumber(),
|
.toNumber(),
|
||||||
0,
|
0,
|
||||||
);
|
);
|
||||||
@ -521,7 +522,7 @@ export default function MarketPreview(props: IMarketPreviewProps) {
|
|||||||
<View className="text-gray-600">
|
<View className="text-gray-600">
|
||||||
<View className="text-xs">箱重</View>
|
<View className="text-xs">箱重</View>
|
||||||
<View className="font-semibold text-gray-900">
|
<View className="font-semibold text-gray-900">
|
||||||
{formatCurrency(brandBoxWeight)} 斤
|
{brandBoxWeight} 斤
|
||||||
</View>
|
</View>
|
||||||
</View>
|
</View>
|
||||||
</View>
|
</View>
|
||||||
@ -574,6 +575,7 @@ export default function MarketPreview(props: IMarketPreviewProps) {
|
|||||||
sum +
|
sum +
|
||||||
new Decimal(item.boxProductWeight || 0)
|
new Decimal(item.boxProductWeight || 0)
|
||||||
.mul(new Decimal(item.boxCount || 0))
|
.mul(new Decimal(item.boxCount || 0))
|
||||||
|
.toDecimalPlaces(0)
|
||||||
.toNumber(),
|
.toNumber(),
|
||||||
0,
|
0,
|
||||||
);
|
);
|
||||||
@ -624,7 +626,7 @@ export default function MarketPreview(props: IMarketPreviewProps) {
|
|||||||
<View className="text-gray-600">
|
<View className="text-gray-600">
|
||||||
<View className="text-xs">箱重</View>
|
<View className="text-xs">箱重</View>
|
||||||
<View className="font-semibold text-gray-900">
|
<View className="font-semibold text-gray-900">
|
||||||
{formatCurrency(brandBoxWeight)} 斤
|
{brandBoxWeight} 斤
|
||||||
</View>
|
</View>
|
||||||
</View>
|
</View>
|
||||||
</View>
|
</View>
|
||||||
|
|||||||
@ -29,6 +29,7 @@ export default forwardRef<SupplierInfoRef, ISupplierInfoProps>(
|
|||||||
name: "瓜农1",
|
name: "瓜农1",
|
||||||
payeeName: "",
|
payeeName: "",
|
||||||
idCard: "",
|
idCard: "",
|
||||||
|
bankName: "",
|
||||||
bankCard: "",
|
bankCard: "",
|
||||||
phone: "",
|
phone: "",
|
||||||
selected: true,
|
selected: true,
|
||||||
@ -201,7 +202,7 @@ export default forwardRef<SupplierInfoRef, ISupplierInfoProps>(
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
// 银行名称至少2个字符
|
// 银行名称至少2个字符
|
||||||
return bankName.length >= 2;
|
return bankName?.length >= 2;
|
||||||
};
|
};
|
||||||
|
|
||||||
// 校验手机号函数 (使用项目中已有的规则)
|
// 校验手机号函数 (使用项目中已有的规则)
|
||||||
@ -895,7 +896,7 @@ export default forwardRef<SupplierInfoRef, ISupplierInfoProps>(
|
|||||||
clearable
|
clearable
|
||||||
type="idcard"
|
type="idcard"
|
||||||
placeholder="请输入身份证号"
|
placeholder="请输入身份证号"
|
||||||
value={supplierVO.idCard}
|
value={supplierVO.idCard || ""}
|
||||||
onChange={(value) => handleIdCardChange(value, supplierVO)}
|
onChange={(value) => handleIdCardChange(value, supplierVO)}
|
||||||
onBlur={() =>
|
onBlur={() =>
|
||||||
handleIdCardBlur(
|
handleIdCardBlur(
|
||||||
@ -920,7 +921,7 @@ export default forwardRef<SupplierInfoRef, ISupplierInfoProps>(
|
|||||||
clearable
|
clearable
|
||||||
type="text"
|
type="text"
|
||||||
placeholder="请输入银行名称"
|
placeholder="请输入银行名称"
|
||||||
value={supplierVO.bankName}
|
value={supplierVO.bankName || ""}
|
||||||
onChange={(value) => handleBankNameChange(value, supplierVO)}
|
onChange={(value) => handleBankNameChange(value, supplierVO)}
|
||||||
onBlur={() =>
|
onBlur={() =>
|
||||||
handleBankNameBlur(
|
handleBankNameBlur(
|
||||||
@ -933,7 +934,7 @@ export default forwardRef<SupplierInfoRef, ISupplierInfoProps>(
|
|||||||
</View>
|
</View>
|
||||||
{bankNameError[supplierVO.orderSupplierId] && (
|
{bankNameError[supplierVO.orderSupplierId] && (
|
||||||
<View className="text-xs text-red-500">
|
<View className="text-xs text-red-500">
|
||||||
{`银行名称"${supplierVO.bankName}"至少2个字符`}
|
{`银行名称"${supplierVO.bankName || ""}"至少2个字符`}
|
||||||
</View>
|
</View>
|
||||||
)}
|
)}
|
||||||
<View className="block text-sm font-normal text-[#000000]">
|
<View className="block text-sm font-normal text-[#000000]">
|
||||||
@ -952,7 +953,7 @@ export default forwardRef<SupplierInfoRef, ISupplierInfoProps>(
|
|||||||
clearable
|
clearable
|
||||||
type="digit"
|
type="digit"
|
||||||
placeholder="请输入银行卡号"
|
placeholder="请输入银行卡号"
|
||||||
value={supplierVO.bankCard}
|
value={supplierVO.bankCard || ""}
|
||||||
onChange={(value) => handleBankCardChange(value, supplierVO)}
|
onChange={(value) => handleBankCardChange(value, supplierVO)}
|
||||||
onBlur={() =>
|
onBlur={() =>
|
||||||
handleBankCardBlur(
|
handleBankCardBlur(
|
||||||
|
|||||||
@ -89,15 +89,23 @@ export default function BasicInfoSection(props: {
|
|||||||
// 获取上一车次号
|
// 获取上一车次号
|
||||||
const fetchLastVehicleNo = async (
|
const fetchLastVehicleNo = async (
|
||||||
dealerId: BusinessAPI.DealerVO["dealerId"],
|
dealerId: BusinessAPI.DealerVO["dealerId"],
|
||||||
|
// 强制重新获取
|
||||||
|
force: boolean = false,
|
||||||
) => {
|
) => {
|
||||||
// 如果已经有车次号,则不需要获取上一车次号
|
if (!force) {
|
||||||
if (orderVehicle?.vehicleNo || !dealerId) {
|
// 如果已经有车次号,则不需要获取上一车次号
|
||||||
return;
|
if (orderVehicle?.vehicleNo || !dealerId) {
|
||||||
}
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
// 避免重复请求
|
// 避免重复请求
|
||||||
if (loadingLastVehicleNo || lastVehicleNo) {
|
if (loadingLastVehicleNo || lastVehicleNo) {
|
||||||
return;
|
return;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (loadingLastVehicleNo || !dealerId) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
setLoadingLastVehicleNo(true);
|
setLoadingLastVehicleNo(true);
|
||||||
@ -133,7 +141,7 @@ export default function BasicInfoSection(props: {
|
|||||||
|
|
||||||
// 组件加载时获取上一车次号
|
// 组件加载时获取上一车次号
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
fetchLastVehicleNo(orderVO.orderDealer.dealerId);
|
fetchLastVehicleNo(orderVO.orderDealer.dealerId, true);
|
||||||
}, [orderVO.orderDealer.dealerId]);
|
}, [orderVO.orderDealer.dealerId]);
|
||||||
|
|
||||||
// 打开基础信息弹窗
|
// 打开基础信息弹窗
|
||||||
|
|||||||
@ -1,8 +1,7 @@
|
|||||||
import { formatCurrency } from "@/utils";
|
import { useMemo, useRef, useState } from "react";
|
||||||
import { useEffect, useState } from "react";
|
|
||||||
import { Table } from "@nutui/nutui-react-taro";
|
import { Table } from "@nutui/nutui-react-taro";
|
||||||
import { Icon } from "@/components";
|
import { Icon } from "@/components";
|
||||||
import { View } from "@tarojs/components";
|
import { Input, View } from "@tarojs/components";
|
||||||
import { Decimal } from "decimal.js";
|
import { Decimal } from "decimal.js";
|
||||||
|
|
||||||
export default function PackageInfoSection(props: {
|
export default function PackageInfoSection(props: {
|
||||||
@ -10,87 +9,193 @@ export default function PackageInfoSection(props: {
|
|||||||
onChange?: (orderVO: BusinessAPI.OrderVO) => void;
|
onChange?: (orderVO: BusinessAPI.OrderVO) => void;
|
||||||
readOnly?: boolean;
|
readOnly?: boolean;
|
||||||
}) {
|
}) {
|
||||||
const { orderVO, readOnly } = props;
|
const { orderVO, readOnly, onChange } = props;
|
||||||
|
|
||||||
const defaultColumns = [
|
const inputRefs = useRef<Record<string, any>>({});
|
||||||
{
|
|
||||||
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 (
|
// 管理编辑状态: key 为分组键,值为输入值
|
||||||
<View
|
const [editingStates, setEditingStates] = useState<
|
||||||
className="flex w-full items-center justify-between"
|
Record<string, { isEditing: boolean; inputValue: string }>
|
||||||
onClick={(e) => {
|
>({});
|
||||||
if (!readOnly) {
|
// 开始编辑
|
||||||
e.stopPropagation();
|
const startEdit = (key: string, currentValue: number) => {
|
||||||
}
|
const inputValue = currentValue === 0 ? "" : currentValue.toString();
|
||||||
}}
|
setEditingStates((prev) => ({
|
||||||
>
|
...prev,
|
||||||
<View className={!readOnly ? "cursor-pointer underline" : ""}>
|
[key]: { isEditing: true, inputValue },
|
||||||
{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) {
|
setTimeout(() => {
|
||||||
setColumns([...defaultColumns]);
|
if (inputRefs.current[key]) {
|
||||||
|
inputRefs.current[key].focus();
|
||||||
|
}
|
||||||
|
}, 0);
|
||||||
|
};
|
||||||
|
|
||||||
|
// 处理输入变化
|
||||||
|
const handleInputChange = (key: string, e: any) => {
|
||||||
|
const val = e.detail?.value || e.target?.value || "";
|
||||||
|
// 只允许数字和小数点
|
||||||
|
if (/^\d*\.?\d*$/.test(val) || val === "") {
|
||||||
|
setEditingStates((prev) => ({
|
||||||
|
...prev,
|
||||||
|
[key]: { ...prev[key], inputValue: val },
|
||||||
|
}));
|
||||||
}
|
}
|
||||||
}, [readOnly]);
|
};
|
||||||
|
|
||||||
|
// 保存编辑
|
||||||
|
const saveEdit = (key: string) => {
|
||||||
|
const state = editingStates[key];
|
||||||
|
if (!state) return;
|
||||||
|
|
||||||
|
let newValue = 0;
|
||||||
|
if (state.inputValue !== "" && !Number.isNaN(Number(state.inputValue))) {
|
||||||
|
newValue = Number(state.inputValue);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 更新 orderVO 中的数据
|
||||||
|
const updatedOrderVO = { ...orderVO };
|
||||||
|
updatedOrderVO.orderSupplierList?.forEach((supplier) => {
|
||||||
|
supplier.orderPackageList?.forEach((pkg) => {
|
||||||
|
const pkgKey = `${pkg.boxBrandId}-${pkg.boxProductId}-${pkg.boxSpecId}`;
|
||||||
|
if (pkgKey === key) {
|
||||||
|
pkg.boxSalePrice = newValue;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
// 触发 onChange 回调
|
||||||
|
onChange?.(updatedOrderVO);
|
||||||
|
|
||||||
|
// 退出编辑状态
|
||||||
|
setEditingStates((prev) => {
|
||||||
|
const newState = { ...prev };
|
||||||
|
delete newState[key];
|
||||||
|
return newState;
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
// 取消编辑
|
||||||
|
const cancelEdit = (key: string) => {
|
||||||
|
setEditingStates((prev) => {
|
||||||
|
const newState = { ...prev };
|
||||||
|
delete newState[key];
|
||||||
|
return newState;
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const columns = useMemo(() => {
|
||||||
|
return [
|
||||||
|
{
|
||||||
|
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 value.boxSalePrice as number;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 生成分组键
|
||||||
|
const key = `${value.boxBrandId}-${value.boxProductId}-${value.boxSpecId}`;
|
||||||
|
const editingState = editingStates[key];
|
||||||
|
const isEditing = editingState?.isEditing || false;
|
||||||
|
|
||||||
|
if (isEditing) {
|
||||||
|
return (
|
||||||
|
<View className="flex items-center">
|
||||||
|
<Input
|
||||||
|
ref={(el: any) => {
|
||||||
|
inputRefs.current[key] = el;
|
||||||
|
}}
|
||||||
|
type="digit"
|
||||||
|
value={editingState.inputValue}
|
||||||
|
onInput={(e) => handleInputChange(key, e)}
|
||||||
|
onBlur={() => saveEdit(key)}
|
||||||
|
className="flex-1 border-b border-blue-500 px-1"
|
||||||
|
style={{ minWidth: "80px" }}
|
||||||
|
onClick={(e) => e.stopPropagation()}
|
||||||
|
/>
|
||||||
|
<View
|
||||||
|
className="ml-1 cursor-pointer"
|
||||||
|
onClick={(e) => {
|
||||||
|
e.stopPropagation();
|
||||||
|
cancelEdit(key);
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<Icon name="circle-xmark" size={16} color={"#ef4444"} />
|
||||||
|
</View>
|
||||||
|
</View>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
return (
|
||||||
|
<View
|
||||||
|
className="flex items-center justify-between"
|
||||||
|
onClick={(e) => {
|
||||||
|
if (!readOnly) {
|
||||||
|
e.stopPropagation();
|
||||||
|
startEdit(key, value.boxSalePrice as number);
|
||||||
|
}
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<View
|
||||||
|
className={!readOnly ? "cursor-pointer underline" : ""}
|
||||||
|
>
|
||||||
|
{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;
|
||||||
|
},
|
||||||
|
) => value.boxProductWeight,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "品牌",
|
||||||
|
key: "boxBrandName",
|
||||||
|
},
|
||||||
|
];
|
||||||
|
}, [readOnly, editingStates]);
|
||||||
|
|
||||||
// 将所有包装信息合并并按品牌、型号、规格分组
|
// 将所有包装信息合并并按品牌、型号、规格分组
|
||||||
const groupedPackageData = orderVO.orderSupplierList?.reduce(
|
const groupedPackageData = orderVO.orderSupplierList?.reduce(
|
||||||
@ -99,7 +204,7 @@ export default function PackageInfoSection(props: {
|
|||||||
?.filter((pkg) => pkg.boxType === "USED")
|
?.filter((pkg) => pkg.boxType === "USED")
|
||||||
?.forEach((pkg) => {
|
?.forEach((pkg) => {
|
||||||
// 生成分组键
|
// 生成分组键
|
||||||
const key = `${pkg.boxBrandName}-${pkg.boxProductName}-${pkg.boxSpecId}`;
|
const key = `${pkg.boxBrandId}-${pkg.boxProductId}-${pkg.boxSpecId}`;
|
||||||
|
|
||||||
// 转换规格字段
|
// 转换规格字段
|
||||||
const boxSpecId = pkg.boxSpecId;
|
const boxSpecId = pkg.boxSpecId;
|
||||||
@ -208,11 +313,11 @@ export default function PackageInfoSection(props: {
|
|||||||
if (rowData.isTotalRow) {
|
if (rowData.isTotalRow) {
|
||||||
return (
|
return (
|
||||||
<span style={{ fontWeight: "bold" }}>
|
<span style={{ fontWeight: "bold" }}>
|
||||||
{formatCurrency(rowData.boxSalePrice as number)}
|
{rowData.boxSalePrice as number}
|
||||||
</span>
|
</span>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
return column.render(rowData, rowData);
|
return column?.render?.(rowData);
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
} else if (column.key === "boxSalePayment") {
|
} else if (column.key === "boxSalePayment") {
|
||||||
@ -223,7 +328,7 @@ export default function PackageInfoSection(props: {
|
|||||||
if (rowData.isTotalRow) {
|
if (rowData.isTotalRow) {
|
||||||
return (
|
return (
|
||||||
<span style={{ fontWeight: "bold" }}>
|
<span style={{ fontWeight: "bold" }}>
|
||||||
{formatCurrency(rowData.boxSalePayment)}
|
{rowData.boxSalePayment}
|
||||||
</span>
|
</span>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -241,11 +346,11 @@ export default function PackageInfoSection(props: {
|
|||||||
if (rowData.isTotalRow) {
|
if (rowData.isTotalRow) {
|
||||||
return (
|
return (
|
||||||
<span style={{ fontWeight: "bold" }}>
|
<span style={{ fontWeight: "bold" }}>
|
||||||
{formatCurrency(rowData.boxProductWeight)}
|
{rowData.boxProductWeight}
|
||||||
</span>
|
</span>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
return column.render(rowData, rowData);
|
return column?.render?.(rowData);
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
@ -257,7 +362,7 @@ export default function PackageInfoSection(props: {
|
|||||||
return (
|
return (
|
||||||
<Table
|
<Table
|
||||||
className={"table-sum"}
|
className={"table-sum"}
|
||||||
columns={columnsWithTotalsRender}
|
columns={columnsWithTotalsRender as any}
|
||||||
data={dataWithTotals}
|
data={dataWithTotals}
|
||||||
striped
|
striped
|
||||||
/>
|
/>
|
||||||
|
|||||||
@ -1,2 +1,2 @@
|
|||||||
// App 相关常量
|
// App 相关常量
|
||||||
export const APP_VERSION = "v0.0.59";
|
export const APP_VERSION = "v0.0.61";
|
||||||
|
|||||||
@ -35,11 +35,9 @@ export class PdfTemplate {
|
|||||||
if (config.showDealerName || config.showWatermelonGrade) {
|
if (config.showDealerName || config.showWatermelonGrade) {
|
||||||
htmlString += `
|
htmlString += `
|
||||||
<div class="col-span-3 flex items-end justify-center border-b border-black">
|
<div class="col-span-3 flex items-end justify-center border-b border-black">
|
||||||
${
|
${config.showDealerName ? config.dealerName : ""}
|
||||||
config.showWatermelonGrade
|
${config.showDealerName && config.showWatermelonGrade ? "- " : ""}
|
||||||
? `${config.dealerName || ""}-${config.watermelonGrade || ""}`
|
${config.showWatermelonGrade ? config.watermelonGrade : ""}
|
||||||
: config.dealerName || ""
|
|
||||||
}
|
|
||||||
</div>
|
</div>
|
||||||
`;
|
`;
|
||||||
} else {
|
} else {
|
||||||
@ -49,7 +47,8 @@ export class PdfTemplate {
|
|||||||
if (config.showDestination || config.showVehicleNumber) {
|
if (config.showDestination || config.showVehicleNumber) {
|
||||||
htmlString += `
|
htmlString += `
|
||||||
<div class="col-span-3 flex items-end justify-center border-b border-black">
|
<div class="col-span-3 flex items-end justify-center border-b border-black">
|
||||||
${config.destination || ""} ${config.vehicleNumber || ""}
|
${config.showDestination ? config.destination : ""}
|
||||||
|
${config.showVehicleNumber ? config.vehicleNumber : ""}
|
||||||
</div>
|
</div>
|
||||||
`;
|
`;
|
||||||
} else {
|
} else {
|
||||||
|
|||||||
@ -33,7 +33,7 @@ export const convertOrderToOrderShip = (
|
|||||||
// 转换供应商列表为发货单项列表,根据 purchasePrice 分组
|
// 转换供应商列表为发货单项列表,根据 purchasePrice 分组
|
||||||
const suppliersByPrice = groupBy(
|
const suppliersByPrice = groupBy(
|
||||||
orderVO.orderSupplierList || [],
|
orderVO.orderSupplierList || [],
|
||||||
(supplier) => String(supplier.purchasePrice),
|
(supplier) => String(supplier.salePrice || "0"),
|
||||||
);
|
);
|
||||||
|
|
||||||
const orderShipId = oldOrderShip?.orderShipId || generateShortId();
|
const orderShipId = oldOrderShip?.orderShipId || generateShortId();
|
||||||
@ -57,10 +57,15 @@ export const convertOrderToOrderShip = (
|
|||||||
);
|
);
|
||||||
|
|
||||||
const totalAmount = DecimalUtils.toDecimalPlaces(
|
const totalAmount = DecimalUtils.toDecimalPlaces(
|
||||||
suppliers.reduce(
|
suppliers.reduce((sum, supplier) => {
|
||||||
(sum, supplier) => DecimalUtils.add(sum, supplier.invoiceAmount || 0),
|
const amount = DecimalUtils.multiply(
|
||||||
0,
|
orderVO.pricingMethod === "BY_GROSS_WEIGHT"
|
||||||
),
|
? supplier.grossWeight
|
||||||
|
: supplier.netWeight,
|
||||||
|
supplier.salePrice || 0,
|
||||||
|
);
|
||||||
|
return DecimalUtils.add(sum, amount || 0);
|
||||||
|
}, 0),
|
||||||
);
|
);
|
||||||
|
|
||||||
const totalBoxCount = DecimalUtils.toDecimalPlaces(
|
const totalBoxCount = DecimalUtils.toDecimalPlaces(
|
||||||
@ -89,7 +94,7 @@ export const convertOrderToOrderShip = (
|
|||||||
grossWeight: totalGrossWeight,
|
grossWeight: totalGrossWeight,
|
||||||
boxWeight: totalGrossWeight - totalNetWeight,
|
boxWeight: totalGrossWeight - totalNetWeight,
|
||||||
netWeight: totalNetWeight,
|
netWeight: totalNetWeight,
|
||||||
unitPrice: parseFloat(price),
|
unitPrice: price ? parseFloat(price) : 0,
|
||||||
totalAmount: totalAmount,
|
totalAmount: totalAmount,
|
||||||
watermelonGrade: oldOrderShipItem?.watermelonGrade || "", // 需要手动填写
|
watermelonGrade: oldOrderShipItem?.watermelonGrade || "", // 需要手动填写
|
||||||
};
|
};
|
||||||
|
|||||||
@ -42,7 +42,10 @@ export const convertOrderShipVOToExamplesFormat = (
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
const packagesBySpec = groupBy(allPackages, (pkg) => pkg.boxSpecId);
|
const packagesBySpec = groupBy(
|
||||||
|
allPackages,
|
||||||
|
(pkg) => pkg.boxSpecName + pkg.boxProductName,
|
||||||
|
);
|
||||||
|
|
||||||
const orderShipPackageList = Object.entries(packagesBySpec).map(
|
const orderShipPackageList = Object.entries(packagesBySpec).map(
|
||||||
([specId, packages]) => {
|
([specId, packages]) => {
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user