| | |
| | | </el-tag> |
| | | </template> |
| | | </el-table-column> |
| | | <el-table-column label="审批中数量" width="120" align="center"> |
| | | <template #default="scope"> |
| | | <span>{{ scope.row.pendingApprovalQuantity || 0 }}</span> |
| | | </template> |
| | | </el-table-column> |
| | | <el-table-column |
| | | label="快递公司" |
| | | prop="expressCompany" |
| | |
| | | </template> |
| | | </el-table-column> |
| | | <el-table-column label="数量" prop="quantity" /> |
| | | <el-table-column label="退货数量" prop="returnQuantity" /> |
| | | <el-table-column label="待发货数量" prop="noQuantity" /> |
| | | <el-table-column label="税率(%)" prop="taxRate" /> |
| | | <el-table-column |
| | |
| | | show-overflow-tooltip |
| | | :formatter="formattedNumber" |
| | | /> |
| | | <!-- <el-table-column--> |
| | | <!-- label="实际合同金额(元)"--> |
| | | <!-- prop="netContractAmount"--> |
| | | <!-- width="220"--> |
| | | <!-- show-overflow-tooltip--> |
| | | <!-- :formatter="formattedNumber"--> |
| | | <!-- />--> |
| | | <el-table-column |
| | | label="录入人" |
| | | prop="entryPersonName" |
| | |
| | | align="right" |
| | | > |
| | | <template #default="scope"> |
| | | {{ Number(scope.row.totalAmount ?? 0).toFixed(2) }} |
| | | {{ Number(scope.row.totalAmount ?? 0).toFixed(6) }} |
| | | </template> |
| | | </el-table-column> |
| | | <el-table-column fixed="right" label="操作" width="120" align="center"> |
| | |
| | | :min="0" |
| | | v-model="productForm.taxInclusiveUnitPrice" |
| | | style="width: 100%" |
| | | :precision="2" |
| | | :precision="6" |
| | | placeholder="请输入" |
| | | clearable |
| | | @change="calculateFromUnitPrice" |
| | |
| | | v-model="productForm.quantity" |
| | | placeholder="请输入" |
| | | clearable |
| | | :precision="2" |
| | | :precision="6" |
| | | @change="calculateFromQuantity" |
| | | style="width: 100%" |
| | | /> |
| | |
| | | v-model="scope.row.deliveryQuantity" |
| | | :min="0" |
| | | :max="getDeliveryBatchDeliveryMax(scope.row)" |
| | | :precision="2" |
| | | :precision="6" |
| | | :step="0.01" |
| | | controls-position="right" |
| | | @change="handleDeliveryBatchQuantityChange(scope.row)" |
| | |
| | | }; |
| | | const formattedNumber = (row, column, cellValue) => { |
| | | if (cellValue === undefined || cellValue === null || cellValue === "") { |
| | | return "0.00"; |
| | | return "0.000000"; |
| | | } |
| | | return parseFloat(cellValue).toFixed(2); |
| | | return parseFloat(cellValue).toFixed(6); |
| | | }; |
| | | const findLedgerRecordByRow = (row) => { |
| | | if (!row) return null; |
| | |
| | | }; |
| | | // 主表合计方法 |
| | | const summarizeMainTable = (param) => { |
| | | return proxy.summarizeTable(param, [ |
| | | "contractAmount", |
| | | "taxInclusiveTotalPrice", |
| | | "taxExclusiveTotalPrice", |
| | | ]); |
| | | return proxy.summarizeTable( |
| | | param, |
| | | ["contractAmount", "taxInclusiveTotalPrice", "taxExclusiveTotalPrice"], |
| | | { |
| | | contractAmount: { decimalPlaces: 6 }, |
| | | taxInclusiveTotalPrice: { decimalPlaces: 6 }, |
| | | taxExclusiveTotalPrice: { decimalPlaces: 6 }, |
| | | } |
| | | ); |
| | | }; |
| | | // 子表合计方法 |
| | | const summarizeChildrenTable = (param, parentRow) => { |
| | |
| | | return ""; |
| | | }); |
| | | } |
| | | return proxy.summarizeTable(param, [ |
| | | "taxInclusiveUnitPrice", |
| | | "taxInclusiveTotalPrice", |
| | | "taxExclusiveTotalPrice", |
| | | ]); |
| | | return proxy.summarizeTable( |
| | | param, |
| | | [ |
| | | "taxInclusiveUnitPrice", |
| | | "taxInclusiveTotalPrice", |
| | | "taxExclusiveTotalPrice", |
| | | ], |
| | | { |
| | | taxInclusiveUnitPrice: { decimalPlaces: 6 }, |
| | | taxInclusiveTotalPrice: { decimalPlaces: 6 }, |
| | | taxExclusiveTotalPrice: { decimalPlaces: 6 }, |
| | | } |
| | | ); |
| | | }; |
| | | // 打开弹框 |
| | | const openForm = async (type, row) => { |
| | |
| | | // 签订日期默认为当天 |
| | | form.value.executionDate = getCurrentDate(); |
| | | // 创建时间默认为当天 |
| | | form.value.createTime = getCurrentDate(); |
| | | form.value.createTime = dayjs().format("YYYY-MM-DD HH:mm:ss"); |
| | | // 默认自动生成销售合同号 |
| | | form.value.autoGenerateContractNo = true; |
| | | } else { |
| | |
| | | const quantity = Number(p.quantity ?? 0) || 0; |
| | | const unitPrice = Number(p.unitPrice ?? 0) || 0; |
| | | const taxRate = "13"; // 默认 13%,便于直接提交(如需可在产品中自行修改) |
| | | const taxInclusiveTotalPrice = (unitPrice * quantity).toFixed(2); |
| | | const taxInclusiveTotalPrice = (unitPrice * quantity).toFixed(6); |
| | | const taxExclusiveTotalPrice = proxy.calculateTaxExclusiveTotalPrice( |
| | | taxInclusiveTotalPrice, |
| | | taxRate |
| | | taxRate, |
| | | 6 |
| | | ); |
| | | return { |
| | | // 台账字段 |
| | |
| | | unit: p.unit || "", |
| | | quantity: quantity, |
| | | taxRate: taxRate, |
| | | taxInclusiveUnitPrice: unitPrice.toFixed(2), |
| | | taxInclusiveUnitPrice: unitPrice.toFixed(6), |
| | | taxInclusiveTotalPrice: taxInclusiveTotalPrice, |
| | | taxExclusiveTotalPrice: taxExclusiveTotalPrice, |
| | | invoiceType: "增普票", |
| | |
| | | ); |
| | | if (shippedProducts.length > 0) { |
| | | proxy.$modal.msgWarning("已发货或审核通过的产品不能删除"); |
| | | return; |
| | | } |
| | | |
| | | // 检查是否只剩一条数据,销售台账至少保留一条产品 |
| | | if (productData.value.length <= 1) { |
| | | proxy.$modal.msgWarning("销售台账至少需要保留一条产品数据"); |
| | | return; |
| | | } |
| | | |
| | |
| | | }; |
| | | |
| | | // 打印功能 |
| | | const handlePrint = async () => { |
| | | const handlePrint = async () => { |
| | | if (selectedRows.value.length === 0) { |
| | | proxy.$modal.msgWarning("请选择要打印的数据"); |
| | | return; |
| | |
| | | // 格式化日期 |
| | | const formatDate = (dateString) => { |
| | | if (!dateString) return getCurrentDate(); |
| | | const date = new Date(dateString); |
| | | const year = date.getFullYear(); |
| | | const month = String(date.getMonth() + 1).padStart(2, "0"); |
| | | const day = String(date.getDate()).padStart(2, "0"); |
| | | return `${year}/${month}/${day}`; |
| | | return dayjs(dateString).format("YYYY/MM/DD HH:mm:ss"); |
| | | }; |
| | | // 格式化日期时间 |
| | | const formatDateTime = (date) => { |
| | |
| | | const total = products.reduce((sum, product) => { |
| | | return sum + (parseFloat(product.quantity) || 0); |
| | | }, 0); |
| | | return total.toFixed(2); |
| | | return total.toFixed(6); |
| | | }; |
| | | |
| | | // 计算产品总金额 |
| | |
| | | const total = products.reduce((sum, product) => { |
| | | return sum + (parseFloat(product.taxInclusiveTotalPrice) || 0); |
| | | }, 0); |
| | | return total.toFixed(2); |
| | | return total.toFixed(6); |
| | | }; |
| | | |
| | | // 用于打印的计算函数 |
| | |
| | | const total = products.reduce((sum, product) => { |
| | | return sum + (parseFloat(product.quantity) || 0); |
| | | }, 0); |
| | | return total.toFixed(2); |
| | | return total.toFixed(6); |
| | | }; |
| | | |
| | | const getTotalAmountForPrint = (products) => { |
| | |
| | | const total = products.reduce((sum, product) => { |
| | | return sum + (parseFloat(product.taxInclusiveTotalPrice) || 0); |
| | | }, 0); |
| | | return total.toFixed(2); |
| | | return total.toFixed(6); |
| | | }; |
| | | |
| | | const mathNum = () => { |
| | |
| | | productForm.value.taxInclusiveTotalPrice = |
| | | proxy.calculateTaxIncludeTotalPrice( |
| | | productForm.value.taxInclusiveUnitPrice, |
| | | productForm.value.quantity |
| | | productForm.value.quantity, |
| | | 6 |
| | | ); |
| | | if (productForm.value.taxRate) { |
| | | // 不含税总价计算 |
| | | productForm.value.taxExclusiveTotalPrice = |
| | | proxy.calculateTaxExclusiveTotalPrice( |
| | | productForm.value.taxInclusiveTotalPrice, |
| | | productForm.value.taxRate |
| | | productForm.value.taxRate, |
| | | 6 |
| | | ); |
| | | } |
| | | }; |
| | |
| | | isCalculating.value = true; |
| | | |
| | | // 计算含税单价 = 含税总价 / 数量 |
| | | productForm.value.taxInclusiveUnitPrice = (totalPrice / quantity).toFixed(2); |
| | | productForm.value.taxInclusiveUnitPrice = (totalPrice / quantity).toFixed(6); |
| | | |
| | | // 如果有税率,计算不含税总价 |
| | | if (productForm.value.taxRate) { |
| | | productForm.value.taxExclusiveTotalPrice = |
| | | proxy.calculateTaxExclusiveTotalPrice( |
| | | totalPrice, |
| | | productForm.value.taxRate |
| | | productForm.value.taxRate, |
| | | 6 |
| | | ); |
| | | } |
| | | |
| | |
| | | // 先计算含税总价 = 不含税总价 / (1 - 税率/100) |
| | | const taxRateDecimal = taxRate / 100; |
| | | const inclusiveTotalPrice = exclusiveTotalPrice / (1 - taxRateDecimal); |
| | | productForm.value.taxInclusiveTotalPrice = inclusiveTotalPrice.toFixed(2); |
| | | productForm.value.taxInclusiveTotalPrice = inclusiveTotalPrice.toFixed(6); |
| | | |
| | | // 计算含税单价 = 含税总价 / 数量 |
| | | productForm.value.taxInclusiveUnitPrice = ( |
| | | inclusiveTotalPrice / quantity |
| | | ).toFixed(2); |
| | | ).toFixed(6); |
| | | |
| | | isCalculating.value = false; |
| | | }; |
| | |
| | | isCalculating.value = true; |
| | | |
| | | // 计算含税总价 |
| | | productForm.value.taxInclusiveTotalPrice = (unitPrice * quantity).toFixed(2); |
| | | productForm.value.taxInclusiveTotalPrice = (unitPrice * quantity).toFixed(6); |
| | | |
| | | // 如果有税率,计算不含税总价 |
| | | if (productForm.value.taxRate) { |
| | | productForm.value.taxExclusiveTotalPrice = |
| | | proxy.calculateTaxExclusiveTotalPrice( |
| | | productForm.value.taxInclusiveTotalPrice, |
| | | productForm.value.taxRate |
| | | productForm.value.taxRate, |
| | | 6 |
| | | ); |
| | | } |
| | | |
| | |
| | | isCalculating.value = true; |
| | | |
| | | // 计算含税总价 |
| | | productForm.value.taxInclusiveTotalPrice = (unitPrice * quantity).toFixed(2); |
| | | productForm.value.taxInclusiveTotalPrice = (unitPrice * quantity).toFixed(6); |
| | | |
| | | // 如果有税率,计算不含税总价 |
| | | if (productForm.value.taxRate) { |
| | | productForm.value.taxExclusiveTotalPrice = |
| | | proxy.calculateTaxExclusiveTotalPrice( |
| | | productForm.value.taxInclusiveTotalPrice, |
| | | productForm.value.taxRate |
| | | productForm.value.taxRate, |
| | | 6 |
| | | ); |
| | | } |
| | | |
| | |
| | | |
| | | // 计算不含税总价 |
| | | productForm.value.taxExclusiveTotalPrice = |
| | | proxy.calculateTaxExclusiveTotalPrice(inclusiveTotalPrice, taxRate); |
| | | proxy.calculateTaxExclusiveTotalPrice(inclusiveTotalPrice, taxRate, 6); |
| | | |
| | | isCalculating.value = false; |
| | | }; |
| | |
| | | |
| | | /** |
| | | * 判断是否可以发货 |
| | | * 只有在产品状态是充足,发货状态是待发货和审核拒绝的时候才可以发货 |
| | | * 只有在产品状态是充足,发货状态是待发货、审批中、审核拒绝、部分发货的时候才可以发货 |
| | | * @param row 行数据 |
| | | */ |
| | | const canShip = (row) => { |
| | |
| | | // 获取发货状态 |
| | | const shippingStatus = row.shippingStatus; |
| | | |
| | | // 如果已发货(有发货日期或车牌号),不能再次发货 |
| | | // 如果已发货,不能再次发货 |
| | | if (shippingStatus === "已发货") { |
| | | return false; |
| | | } |
| | | |
| | | // 发货状态必须是"待发货"或"审核拒绝" |
| | | // 发货状态必须是"待发货"、"审批中"、"审核拒绝"或"部分发货" |
| | | const statusStr = shippingStatus ? String(shippingStatus).trim() : ""; |
| | | return ( |
| | | statusStr === "待发货" || |
| | | statusStr === "审批中" || |
| | | statusStr === "审核拒绝" || |
| | | statusStr === "部分发货" |
| | | ); |
| | |
| | | // 检查是否可以发货 |
| | | if (!canShip(row)) { |
| | | proxy.$modal.msgWarning( |
| | | "只有在产品状态是充足,发货状态是待发货或审核拒绝的时候才可以发货" |
| | | "只有在产品状态是充足,发货状态是待发货、审批中、审核拒绝或部分发货的时候才可以发货" |
| | | ); |
| | | return; |
| | | } |
| | | |
| | | // 审批中时提示用户已有待审批的发货记录 |
| | | const statusStr = row.shippingStatus ? String(row.shippingStatus).trim() : ""; |
| | | if (statusStr === "审批中") { |
| | | proxy.$modal.msgWarning("该产品存在待审批的发货记录,请注意避免重复提交"); |
| | | } |
| | | |
| | | currentDeliveryRow.value = row; |
| | | const batchNoList = await getDeliveryBatchNoList( |
| | | row.productModelId || row.modelId |