@@ -4031,7 +4031,7 @@
剩余数量:{{
- formatDispatchQuantity(dispatchItemHintRemainingQuantity(dispatchItemForm))
+ formatDispatchQuantity(dispatchItemDisplayRemainingQuantity(dispatchItemForm))
}}
{{ dispatchItemForm.quantityUnit || '吨' }}
@@ -5740,6 +5740,8 @@ export default {
dispatchItemIndex: -1,
dispatchItemForm: defaultDispatchRow(),
dispatchItemCargoRows: [],
+ // 本次数量变更版本号:驱动同表其他行「剩余数量」同步重算
+ dispatchCargoQuantityVersion: 0,
dispatchItemAttachmentRows: [],
selectedDispatchItemAttachmentRows: [],
attachmentRows: [],
@@ -12776,18 +12778,23 @@ export default {
row.cargoName = '';
row.specification = '';
row.model = '';
+ this.dispatchCargoQuantityVersion += 1;
},
handleDispatchConfiguredCargoNameChange(row, value) {
const option = this.getDispatchConfiguredCargoNameOptions(row).find(
item => String(item.value) === String(value || '')
);
row.cargoName = option?.value || '';
- if (!option) return;
+ if (!option) {
+ this.dispatchCargoQuantityVersion += 1;
+ return;
+ }
row.cargoType = option.cargoTypeLabel || row.cargoType || '';
row.cargoTypeCode = option.cargoTypeCode || row.cargoTypeCode || '';
row.cargoTypePath = option.cargoTypePath || row.cargoTypePath || [];
row.specification = option.specification || row.specification || '';
row.model = option.model || row.model || '';
+ this.dispatchCargoQuantityVersion += 1;
},
openDispatchItemDialog(index = -1, row = defaultDispatchRow()) {
const defaultSummaryItem =
@@ -13119,6 +13126,7 @@ export default {
const parts = text.split('.');
row.quantity =
parts.length > 1 ? `${parts[0]}.${parts.slice(1).join('').slice(0, 3)}` : parts[0];
+ this.dispatchCargoQuantityVersion += 1;
},
handleDispatchCargoNumberInput(row, prop, value) {
this.handleTaskFullFreightNumberInput(row, prop, value);
@@ -13138,12 +13146,14 @@ export default {
const nextRow = this.normalizeTransportCargoRow({ priceUnit: '元/吨' });
if (index > -1) this.dispatchItemCargoRows.splice(index + 1, 0, nextRow);
else this.dispatchItemCargoRows.push(nextRow);
+ this.dispatchCargoQuantityVersion += 1;
},
removeDispatchCargoRow(index) {
this.dispatchItemCargoRows.splice(index, 1);
if (!this.dispatchItemCargoRows.length) {
this.dispatchItemCargoRows.push(this.normalizeTransportCargoRow());
}
+ this.dispatchCargoQuantityVersion += 1;
},
dispatchCargoFreightAmount(cargo = {}) {
const quantity = Number(cargo.quantity || 0);
@@ -13217,11 +13227,52 @@ export default {
}, 0)
);
},
- /** 精简录入提示:可调度余量扣减当前本次数量后的剩余 */
- dispatchItemHintRemainingQuantity(row = {}) {
+ /**
+ * 当前编辑表单中,与指定行同货物(有身份)或同单位(无身份)已占用的本次数量合计。
+ * 用于剩余数量展示联动,不参与提交校验(校验仍按整单合计对比计划余量)。
+ */
+ getDispatchFormOccupiedQuantity(row = {}) {
+ const goodsRows =
+ this.dispatchItemForm?.taskEntryMode === 'full'
+ ? this.dispatchItemCargoRows || []
+ : [this.dispatchItemForm || row];
+ const hasCargoIdentity = Boolean(
+ String(row.cargoName || row.goodsName || row.name || '').trim() ||
+ String(
+ row.cargoType || row.secondCargoTypeName || row.goodsType || row.type || ''
+ ).trim()
+ );
+ const unit = this.getDispatchQuantityUnit(row);
+ const cargoKey = this.getDispatchCargoIdentity(row);
+ return goodsRows.reduce((sum, goods) => {
+ if (!goods) return sum;
+ if (hasCargoIdentity) {
+ const goodsHasIdentity = Boolean(
+ String(goods.cargoName || goods.goodsName || goods.name || '').trim() ||
+ String(
+ goods.cargoType || goods.secondCargoTypeName || goods.goodsType || goods.type || ''
+ ).trim()
+ );
+ if (!goodsHasIdentity || this.getDispatchCargoIdentity(goods) !== cargoKey) {
+ return sum;
+ }
+ } else if (this.getDispatchQuantityUnit(goods) !== unit) {
+ return sum;
+ }
+ return sum + this.parseDispatchQuantity(goods.quantity);
+ }, 0);
+ },
+ /** 展示用剩余数量:计划可调度余量扣减本单已填本次数量(含当前行) */
+ dispatchItemDisplayRemainingQuantity(row = {}) {
+ // 依赖版本号,确保一行本次数量变化后其他行剩余数量一并刷新
+ void this.dispatchCargoQuantityVersion;
const available = this.dispatchItemRemainingQuantity(row);
- const current = this.parseDispatchQuantity(row.quantity);
- return Math.max(available - current, 0);
+ const occupied = this.getDispatchFormOccupiedQuantity(row);
+ return Math.max(available - occupied, 0);
+ },
+ /** 精简录入提示:与完整录入剩余数量展示规则一致 */
+ dispatchItemHintRemainingQuantity(row = {}) {
+ return this.dispatchItemDisplayRemainingQuantity(row);
},
pruneDispatchPendingRows(rows = []) {
const planQuantities = new Map();
diff --git a/src/views/business/components/transport-plan-page.vue b/src/views/business/components/transport-plan-page.vue
index e4af27c..1eccc90 100644
--- a/src/views/business/components/transport-plan-page.vue
+++ b/src/views/business/components/transport-plan-page.vue
@@ -1677,7 +1677,7 @@
{{
isDispatchPlanQuantityUnlimited(row)
? '-'
- : formatDispatchQuantity(dispatchItemRemainingQuantity(row))
+ : formatDispatchQuantity(dispatchItemDisplayRemainingQuantity(row))
}}
@@ -1861,7 +1861,7 @@
/>
-