This commit is contained in:
2026-08-27 14:30:26 +08:00
parent c704032d66
commit a5a803046b
11 changed files with 178 additions and 66 deletions
+29 -31
View File
@@ -114,7 +114,7 @@
<button class="pick-btn pick-btn-partial" @tap="openPartial(item.id)">部分拣货</button>
<button class="pick-btn pick-btn-skip" @tap="openSkip(item.id)">跳拣</button>
</view>
<view v-else-if="!completedBoxes[currentBoxIndex]" class="pick-item-actions processed-actions">
<view v-else-if="pickingOperationReady" class="pick-item-actions processed-actions">
<button class="pick-btn pick-btn-undo" @tap="undoItem(item.id)">撤销</button>
</view>
</view>
@@ -124,15 +124,18 @@
<view v-if="activeStage === 'evidence'" class="loading-evidence-section">
<view class="section-heading-row">
<view><text class="section-title">装柜证据</text><text class="section-subtitle">空仓、半仓、满仓、锁仓及带锁码照</text></view>
<view><text class="section-title">装柜证据</text><text class="section-subtitle">每类至少 1 张,拍照后自动上传,可继续追加</text></view>
<text class="sync-state" :class="remoteSyncState.tone">{{ remoteSyncState.label }}</text>
</view>
<view class="evidence-grid">
<view v-for="slot in evidenceSlots" :key="slot.type" class="evidence-card" :class="{ filled: evidenceEntries(slot.type).length }">
<view v-for="(slot, slotIndex) in evidenceSlots" :key="slot.type" class="evidence-card" :class="{ filled: evidenceEntries(slot.type).length }">
<view class="evidence-card-header">
<view class="evidence-card-title">
<text class="evidence-label">{{ slot.label }}</text>
<text class="evidence-count" :class="{ complete: evidenceEntries(slot.type).length }">{{ evidenceEntries(slot.type).length ? evidenceEntries(slot.type).length + ' 张' : '待拍摄' }}</text>
<view class="evidence-card-main">
<text class="evidence-step" :class="{ complete: evidenceEntries(slot.type).length }">{{ evidenceEntries(slot.type).length ? '✓' : slotIndex + 1 }}</text>
<view class="evidence-card-title">
<text class="evidence-label">{{ slot.label }}</text>
<text class="evidence-count" :class="{ complete: evidenceEntries(slot.type).length }">{{ evidenceEntries(slot.type).length ? `已拍 ${evidenceEntries(slot.type).length} 张` : '待拍摄' }}</text>
</view>
</view>
<button class="evidence-btn evidence-add-btn" @tap="chooseEvidence(slot)">{{ evidenceUploadLabel(slot.type) }}</button>
</view>
@@ -144,7 +147,6 @@
<button v-if="photo.id && photo.status !== 'VOID' && photo.status !== 'VOIDED'" class="evidence-void-btn" @tap="voidEvidencePhoto(photo)">作废</button>
</view>
</view>
<text v-else class="evidence-empty-hint">现场拍摄后自动上传,可继续追加</text>
<text v-if="evidenceQueueEntry(slot.type)" class="evidence-upload-state" :class="evidenceQueueEntry(slot.type).status.toLowerCase()">
{{ evidenceUploadState(slot.type) }}
</text>
@@ -308,6 +310,10 @@
<PopupHeader title="拣货完成" @close="closeOverlay" />
<view class="complete-icon">✓</view>
<text class="complete-desc">集装箱号 {{ currentBox.currentContainerNo }} · 柜次号 {{ currentBox.cabinetNo }} · 订单 {{ currentBox.orderNo }}</text>
<view class="complete-evidence-status">
<text>装柜照片已拍 {{ evidenceCapturedTypeCount }}/{{ evidenceSlots.length }} 类</text>
<text>{{ sealNo ? '封签号已填写' : '封签号未填写' }}</text>
</view>
<view class="complete-stats">
<view class="complete-stat">
<text class="complete-stat-num green">{{ completionSummary.picked }}</text>
@@ -328,20 +334,11 @@
</view>
<view class="complete-btns">
<button class="complete-btn-back" @tap="closeOverlay">返回查看</button>
<button class="complete-btn-next" @tap="nextBox">{{ nextBoxButtonText }}</button>
<button class="complete-btn-next" @tap="continueToEvidence">{{ evidenceNextButtonText }}</button>
</view>
</view>
</uni-popup>
<uni-popup ref="allCompletePopup" type="center" :is-mask-click="true" @change="handleOverlayChange('allComplete', $event)">
<view class="complete-modal" role="dialog" aria-modal="true" aria-label="全部柜次已完成" @tap.stop>
<PopupHeader title="全部柜次已完成" @close="closeOverlay" />
<view class="complete-icon">✓</view>
<text class="complete-desc">本班次 {{ boxes.length }} 个柜次任务已全部处理</text>
<button class="all-complete-btn" @tap="leavePicking">返回工作台</button>
</view>
</uni-popup>
<view v-if="toast.visible" class="app-toast" :class="toast.type" role="status">{{ toast.message }}</view>
</view>
</template>
@@ -488,8 +485,13 @@
if (this.summary.pending > 0) return '提交时需选择原因'
return `已处理 ${this.summary.processed}/${this.summary.total}`
},
nextBoxButtonText() {
return this.completedCount === this.boxes.length ? '查看全部完成' : '下一箱'
evidenceCapturedTypeCount() {
return this.evidenceSlots.filter((slot) => this.evidenceEntries(slot.type).length > 0).length
},
evidenceNextButtonText() {
return this.evidenceCapturedTypeCount === this.evidenceSlots.length && Boolean(String(this.sealNo || '').trim())
? '查看装柜取证'
: '去拍照'
},
visibleBoxList() {
return this.boxes
@@ -513,17 +515,17 @@
},
onLoad(options = {}) {
if (!requireSession()) return
this.currentUser = session.currentUser
if (options.taskId) {
// A local completion marker belongs to the previously opened task. The
// canonical server detail decides whether this task is complete.
this.completedBoxes = {}
this.boxes = [{
boxNo: String(options.currentContainerNo || options.cabinetNo || '同步中'), cabinetNo: options.cabinetNo ? String(options.cabinetNo) : null, currentContainerNo: options.currentContainerNo ? String(options.currentContainerNo) : null, orderNo: String(options.orderNo || options.inboundCode || ''),
boxNo: '同步中', cabinetNo: null, currentContainerNo: null, orderNo: '',
taskId: String(options.taskId), loadingPlanId: null, containerBookingId: null,
inboundId: options.inboundId ? String(options.inboundId) : null,
inboundVersion: options.inboundVersion == null ? null : Number(options.inboundVersion),
inboundId: null, inboundVersion: null,
warehouseId: options.warehouseId ? String(options.warehouseId) : null,
tenantId: options.tenantId ? String(options.tenantId) : null, items: []
tenantId: null, items: []
}]
this.currentBoxIndex = 0
this.remoteTaskId = options.taskId ? String(options.taskId) : null
@@ -531,6 +533,7 @@
},
async onShow() {
if (!requireSession()) return
this.currentUser = session.currentUser
this.startHardwareScanner()
if (this.cameraPicking) {
this.debugEvidence('choose.resume', { evidenceIdentity: this.evidenceIdentity })
@@ -1645,15 +1648,10 @@
}
this.openOverlay('complete')
},
nextBox() {
continueToEvidence() {
this.closeOverlay(false)
const nextIndex = this.boxes.findIndex((box, index) => !this.completedBoxes[index])
if (nextIndex < 0) {
this.openOverlay('allComplete')
return
}
this.selectBox(nextIndex)
this.showToast('切换至下一箱', 'success')
this.activeStage = 'evidence'
this.scrollToTop()
},
resetOverlayState() {
this.activeOverlay = ''