Files
OMS/app/wap/statics/js/batch-consign.js
2026-01-04 19:08:31 +08:00

459 lines
12 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
/**
* Copyright 2012-2026 ShopeX (https://www.shopex.cn)
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
/**
* 批量发货管理器
* 基于批量打印功能实现,用于批量发货操作
*
* @author AI Assistant
* @date 2025-07-08
*/
class BatchConsignManager {
constructor() {
this.selectedOrders = new Set();
this.isActive = false;
this.apiUrl = '';
}
/**
* 初始化批量发货功能
* @param {string} apiUrl - 发货API地址
*/
init(apiUrl) {
this.apiUrl = apiUrl;
this.bindEvents();
}
/**
* 绑定事件
*/
bindEvents() {
// 注意按钮事件由主页面的onclick属性处理这里不重复绑定
}
/**
* 切换批量发货模式
*/
toggle() {
const batchConsignBtn = document.getElementById('batchConsignBtn');
if (this.isActive) {
// 取消批量发货模式
this.deactivate();
batchConsignBtn.classList.remove('active');
} else {
// 激活批量发货模式
this.activate();
batchConsignBtn.classList.add('active');
// 清除其他按钮的active状态
const otherBtns = document.querySelectorAll('.date-select-item:not(#batchConsignBtn)');
otherBtns.forEach(btn => btn.classList.remove('active'));
}
}
/**
* 激活批量发货模式
*/
activate() {
this.isActive = true;
this.applyBatchConsignSelection();
this.updateUI();
// 如果没有可选订单返回false表示激活失败
return this.selectedOrders.size > 0;
}
/**
* 激活批量发货模式(保持已选择状态但验证条件)
*/
activateWithoutAutoSelect() {
this.isActive = true;
// 不清空已有选择,保持当前状态
// this.selectedOrders.clear(); // 注释掉这行
this.enableBatchConsignCheckboxes();
this.updateUI();
console.log('BatchConsignManager: 激活批量发货模式,保持已有选择并验证条件');
}
/**
* 启用批量发货模式的复选框(保持已选择状态但验证条件)
*/
enableBatchConsignCheckboxes() {
const orderCheckboxes = document.querySelectorAll('.order-checkbox');
let validSelectedCount = 0;
let invalidSelectedCount = 0;
orderCheckboxes.forEach(checkbox => {
const listItem = checkbox.closest('.list-item');
const deliveryId = checkbox.value;
const wasSelected = checkbox.checked;
// 检查是否满足批量发货条件
if (this.canSelectForBatchConsign(listItem)) {
// 符合条件的订单
checkbox.disabled = false;
if (wasSelected) {
// 保持已选择状态
checkbox.checked = true;
this.selectedOrders.add(deliveryId);
validSelectedCount++;
} else {
// 未选择的订单保持未选择状态
checkbox.checked = false;
}
} else {
// 不符合条件的订单
checkbox.disabled = true;
if (wasSelected) {
// 如果之前选中但现在不符合条件,取消选择
checkbox.checked = false;
this.selectedOrders.delete(deliveryId);
invalidSelectedCount++;
} else {
checkbox.checked = false;
}
}
});
// 提示用户选择状态
if (invalidSelectedCount > 0) {
this.showToast(`已取消${invalidSelectedCount}个不符合条件的订单选择,请重新选择需要发货的订单`);
} else if (validSelectedCount > 0) {
this.showToast(`保持${validSelectedCount}个订单的选择状态,可继续选择其他订单`);
} else {
this.showToast('请选择需要发货的订单');
}
console.log('BatchConsignManager: 保持有效选择', validSelectedCount, '个,取消无效选择', invalidSelectedCount, '个');
}
/**
* 取消批量发货模式
*/
deactivate() {
this.isActive = false;
this.selectedOrders.clear();
this.resetOrderSelection();
this.hideActionButton();
// 注意不自动移除按钮的active状态由调用方决定是否移除
// 这样可以支持保持tab选中状态的需求
}
/**
* 应用批量发货的选择逻辑
*/
applyBatchConsignSelection() {
this.selectedOrders.clear();
const orderCheckboxes = document.querySelectorAll('.order-checkbox');
orderCheckboxes.forEach(checkbox => {
const listItem = checkbox.closest('.list-item');
if (this.canSelectForBatchConsign(listItem)) {
checkbox.checked = true;
checkbox.disabled = false;
this.selectedOrders.add(checkbox.value);
} else {
checkbox.checked = false;
checkbox.disabled = true;
}
});
console.log('BatchConsignManager: 应用批量发货选择逻辑,选中', this.selectedOrders.size, '个订单');
}
/**
* 检查订单是否可以进行批量发货
* @param {Element} listItem - 订单项DOM元素
* @returns {boolean}
*/
canSelectForBatchConsign(listItem) {
const checkbox = listItem.querySelector('.order-checkbox');
if (!checkbox) return false;
// 获取订单状态数据
const status = parseInt(checkbox.getAttribute('data-status'));
const hasLogiNo = parseInt(checkbox.getAttribute('data-has-logi-no'));
const print_status=parseInt(checkbox.getAttribute('data-print-status'))//
// 批量发货条件status == 0 && 有快递单号(已获取物流单号且未发货)
return status === 0 && print_status === 1;
}
/**
* 重置订单选择状态
*/
resetOrderSelection() {
const orderCheckboxes = document.querySelectorAll('.order-checkbox');
orderCheckboxes.forEach(checkbox => {
checkbox.disabled = false;
checkbox.checked = false;
});
}
/**
* 更新UI状态
*/
updateUI() {
this.updateSelectedCount();
if (this.selectedOrders.size > 0) {
this.showActionButton();
} else {
this.hideActionButton();
}
console.log('BatchConsignManager: 更新UI状态选中订单数:', this.selectedOrders.size);
}
/**
* 更新选中数量显示
*/
updateSelectedCount() {
// 调用主页面的updateSelectedCount函数确保状态同步
if (window.updateSelectedCount) {
window.updateSelectedCount();
} else {
// 降级处理直接更新DOM
const countElement = document.getElementById('selectedCount');
if (countElement) {
countElement.textContent = this.selectedOrders.size;
}
}
}
/**
* 显示操作按钮
*/
showActionButton() {
const footer = document.getElementById('batchActionFooter');
const consignBtn = document.getElementById('batchConsignNextBtn');
const deliveryBtn = document.getElementById('batchDeliveryBtn');
const printBtn = document.getElementById('batchPrintNextBtn');
if (footer && consignBtn) {
consignBtn.style.display = 'block';
if (deliveryBtn) deliveryBtn.style.display = 'none';
if (printBtn) printBtn.style.display = 'none';
footer.style.display = 'block';
}
}
/**
* 隐藏操作按钮
*/
hideActionButton() {
// 只隐藏下一步按钮,不退出批量模式
const footer = document.getElementById('batchActionFooter');
if (footer) {
footer.style.display = 'none';
}
}
/**
* 处理订单选择变化
* @param {Element} checkbox - 复选框元素
*/
handleOrderSelect(checkbox) {
if (!this.isActive) return;
const listItem = checkbox.closest('.list-item');
if (!this.canSelectForBatchConsign(listItem)) {
checkbox.checked = false;
this.showToast('该订单不满足批量发货条件');
return;
}
const deliveryId = checkbox.value;
if (checkbox.checked) {
this.selectedOrders.add(deliveryId);
} else {
this.selectedOrders.delete(deliveryId);
}
this.updateUI();
// 同步主页面的选中数量显示
if (window.updateSelectedCount) {
window.updateSelectedCount();
}
}
/**
* 执行批量发货
*/
goToBatchConsign() {
if (this.selectedOrders.size === 0) {
this.showToast('请选择需要发货的订单');
return;
}
const confirmMessage = `即将为 ${this.selectedOrders.size} 个订单执行发货操作。\n\n发货后订单状态将变更为"已发货",无法撤销。\n\n请确认是否继续?`;
if (confirm(confirmMessage)) {
this.startBatchConsign();
}
}
/**
* 开始批量发货
*/
async startBatchConsign() {
this.showProgress();
const deliveryIds = Array.from(this.selectedOrders);
const results = await this.processBatchConsign(deliveryIds);
this.hideProgress();
this.showResults(results);
}
/**
* 处理批量发货
* @param {Array} deliveryIds - 发货单ID数组
* @returns {Object} 处理结果
*/
async processBatchConsign(deliveryIds) {
const totalCount = deliveryIds.length;
let processedCount = 0;
let successCount = 0;
let failCount = 0;
const errorMessages = [];
for (let i = 0; i < deliveryIds.length; i++) {
const deliveryId = deliveryIds[i];
try {
this.updateProgress(deliveryId, processedCount, totalCount, `正在发货订单 ${deliveryId}...`);
const response = await this.callConsignAPI(deliveryId);
if (response.rsp === 'succ' || response.res === 'succ') {
successCount++;
} else if (response.res === 'error') {
failCount++;
errorMessages.push(`订单 ${deliveryId}: ${response.msg || '发货失败'}`);
} else {
// 处理其他可能的响应格式
failCount++;
errorMessages.push(`订单 ${deliveryId}: 未知响应格式`);
}
processedCount++;
await this.delay(500); // 延迟500ms避免请求过快
} catch (error) {
failCount++;
errorMessages.push(`订单 ${deliveryId}: 网络错误或系统异常`);
processedCount++;
}
}
return {
total: totalCount,
success: successCount,
fail: failCount,
errors: errorMessages
};
}
/**
* 调用发货API
* @param {string} deliveryId - 发货单ID
* @returns {Promise} API响应
*/
async callConsignAPI(deliveryId) {
return new Promise((resolve, reject) => {
$.post(this.apiUrl, {
'delivery_id': deliveryId
})
.done(response => {
try {
const result = JSON.parse(response);
resolve(result);
} catch (e) {
reject(new Error('响应解析失败'));
}
})
.fail(() => {
reject(new Error('网络请求失败'));
});
});
}
/**
* 延迟函数
* @param {number} ms - 延迟毫秒数
* @returns {Promise}
*/
delay(ms) {
return new Promise(resolve => setTimeout(resolve, ms));
}
/**
* 显示进度弹窗
*/
showProgress() {
// 进度弹窗的实现将在主文件中处理
if (window.showBatchConsignProgress) {
window.showBatchConsignProgress();
}
}
/**
* 隐藏进度弹窗
*/
hideProgress() {
if (window.hideBatchConsignProgress) {
window.hideBatchConsignProgress();
}
}
/**
* 更新进度
*/
updateProgress(currentOrder, processed, total, status) {
if (window.updateConsignProgress) {
window.updateConsignProgress(currentOrder, processed, total, status);
}
}
/**
* 显示结果
*/
showResults(results) {
if (window.showBatchConsignResult) {
window.showBatchConsignResult(results);
}
}
/**
* 显示提示消息
*/
showToast(message) {
if (window.showToast) {
window.showToast(message);
}
}
}
// 导出到全局
window.BatchConsignManager = BatchConsignManager;