基本配置修改 优化
This commit is contained in:
parent
62b6cf70fb
commit
ae396e22df
|
|
@ -0,0 +1,20 @@
|
|||
import request from '@/utils/request'
|
||||
|
||||
// 查询列表
|
||||
export function checkInventoryPageApi(query) {
|
||||
return request({
|
||||
url: '/smart-canteen/drpcheckinventory/page',
|
||||
method: 'post',
|
||||
data: query,
|
||||
})
|
||||
}
|
||||
|
||||
export function getCheckInventoryInfoApi(query) {
|
||||
return request({
|
||||
url: '/smart-canteen/drpcheckinventory/detail',
|
||||
method: 'post',
|
||||
data: query,
|
||||
})
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -0,0 +1,707 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<!-- 查询条件 -->
|
||||
<el-form :model="queryParams" ref="queryForm" size="small" :inline="true" label-width="80px">
|
||||
<el-form-item label="日期时间">
|
||||
<el-date-picker
|
||||
v-model="dateRange"
|
||||
type="daterange"
|
||||
align="right"
|
||||
unlink-panels
|
||||
range-separator="至"
|
||||
start-placeholder="开始日期"
|
||||
end-placeholder="结束日期"
|
||||
format="yyyy-MM-dd"
|
||||
style="width: 340px"
|
||||
:default-time="['00:00:00', '23:59:59']"
|
||||
:picker-options="pickerOptions"
|
||||
>
|
||||
</el-date-picker>
|
||||
</el-form-item>
|
||||
|
||||
<el-form-item label="消费地">
|
||||
<el-cascader
|
||||
v-model="selectedOrg"
|
||||
:options="orgOptions"
|
||||
:show-all-levels="false"
|
||||
clearable
|
||||
filterable
|
||||
placeholder="请选择消费地"
|
||||
:props="cascaderProps"
|
||||
collapse-tags
|
||||
collapse-tags-tooltip
|
||||
style="width: 200px"
|
||||
@change="handleOrgChange"
|
||||
>
|
||||
</el-cascader>
|
||||
</el-form-item>
|
||||
|
||||
<el-form-item label="工作地">
|
||||
<el-cascader
|
||||
v-model="gzselectedOrg"
|
||||
:options="gzorgOptions"
|
||||
:show-all-levels="false"
|
||||
clearable
|
||||
filterable
|
||||
placeholder="请选择工作地"
|
||||
:props="cascaderProps"
|
||||
collapse-tags
|
||||
collapse-tags-tooltip
|
||||
style="width: 200px"
|
||||
@change="handleGzOrgChange"
|
||||
>
|
||||
</el-cascader>
|
||||
</el-form-item>
|
||||
|
||||
<el-form-item>
|
||||
<el-button type="primary" icon="el-icon-search" size="mini" @click="handleQuery">查询</el-button>
|
||||
<el-button icon="el-icon-refresh" size="mini" @click="resetQuery">重置</el-button>
|
||||
<el-button type="success" size="mini" @click="newexportExcel">导出列表</el-button>
|
||||
<el-button type="warning" size="mini" @click="printTable">打印</el-button>
|
||||
</el-form-item>
|
||||
</el-form>
|
||||
|
||||
<!-- 数据表格 -->
|
||||
<div class="table-container">
|
||||
<el-table
|
||||
v-loading="loading"
|
||||
:data="tableListData"
|
||||
style="margin-top: 20px;"
|
||||
show-summary
|
||||
:summary-method="getSummaries"
|
||||
border
|
||||
stripe
|
||||
:height="tableHeight"
|
||||
>
|
||||
<el-table-column label="序号" align="center" width="80" fixed="left">
|
||||
<template #default="scope">
|
||||
{{ (queryParams.pageNum - 1) * queryParams.pageSize + scope.$index + 1 }}
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column label="交易次数" align="center" prop="tradeNum" width="120">
|
||||
<template #default="scope">{{ scope.row.tradeNum || 0 }}</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column label="交易金额" align="center" prop="payableAmount" width="120">
|
||||
<template #default="scope">{{ formatAmount(scope.row.payableAmount) }}</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column label="消费地" align="center" prop="areaName" min-width="150" />
|
||||
<el-table-column label="工作地" align="center" prop="workAreaName" min-width="150" />
|
||||
</el-table>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { getTreeArea, getplaceListhz } from "@/api/canteen/canteenRecord";
|
||||
import ExcelJS from "exceljs";
|
||||
import { saveAs } from "file-saver";
|
||||
|
||||
export default {
|
||||
name: "ConsumeReport",
|
||||
data() {
|
||||
return {
|
||||
orgOptions: [],
|
||||
selectedOrg: [],
|
||||
gzorgOptions: [],
|
||||
gzselectedOrg: [],
|
||||
loading: false,
|
||||
tableListData: [],
|
||||
total: 0,
|
||||
dateRange: this.defaultDateRange(),
|
||||
queryParams: {
|
||||
pageNum: 1,
|
||||
pageSize: 10,
|
||||
selectedOrg: [],
|
||||
gzselectedOrg: [],
|
||||
startTime: '',
|
||||
endTime: ''
|
||||
},
|
||||
pickerOptions: {
|
||||
shortcuts: [
|
||||
{
|
||||
text: '最近一周',
|
||||
onClick(picker) {
|
||||
const end = new Date();
|
||||
const start = new Date();
|
||||
start.setDate(start.getDate() - 7);
|
||||
picker.$emit('pick', [start, end]);
|
||||
}
|
||||
},
|
||||
{
|
||||
text: '最近一个月',
|
||||
onClick(picker) {
|
||||
const end = new Date();
|
||||
const start = new Date();
|
||||
start.setMonth(start.getMonth() - 1);
|
||||
picker.$emit('pick', [start, end]);
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
cascaderProps: {
|
||||
multiple: true,
|
||||
checkStrictly: true,
|
||||
expandTrigger: 'hover',
|
||||
value: 'orgId',
|
||||
label: 'orgName',
|
||||
children: 'children'
|
||||
},
|
||||
tableHeight: 500
|
||||
};
|
||||
},
|
||||
created() {
|
||||
// 严格按你需求:先加载树 => 默认选择第一个(消费地 & 工作地)=> 再首次请求列表
|
||||
this.getTree()
|
||||
.then(() => {
|
||||
this.setDefaultBothOrg();
|
||||
this.getplaceList();
|
||||
})
|
||||
.catch(() => {
|
||||
// 即便获取树失败,也尝试请求列表(保持和你原逻辑行为一致)
|
||||
this.getplaceList();
|
||||
});
|
||||
|
||||
this.calculateTableHeight();
|
||||
window.addEventListener('resize', this.calculateTableHeight);
|
||||
},
|
||||
beforeDestroy() {
|
||||
window.removeEventListener('resize', this.calculateTableHeight);
|
||||
},
|
||||
methods: {
|
||||
// 计算表格高度
|
||||
calculateTableHeight() {
|
||||
const windowHeight = window.innerHeight;
|
||||
this.tableHeight = Math.max(400, windowHeight - 350);
|
||||
},
|
||||
|
||||
// 格式化金额
|
||||
formatAmount(amount) {
|
||||
if (!amount) return '0.00';
|
||||
return (Number(amount) / 100).toFixed(2);
|
||||
},
|
||||
|
||||
defaultDateRange() {
|
||||
const today = new Date();
|
||||
return [today, today];
|
||||
},
|
||||
|
||||
// getTree 保持原样,但返回 Promise 以便在 created 中链式调用
|
||||
getTree() {
|
||||
getTreeArea().then(res => {
|
||||
this.orgOptions = res;
|
||||
this.gzorgOptions = JSON.parse(JSON.stringify(res));
|
||||
|
||||
if (res && res.length > 0) {
|
||||
// ---------- 消费地 ----------
|
||||
let defaultConsume = res[0];
|
||||
if (defaultConsume.children && defaultConsume.children.length > 0) {
|
||||
// 默认选择二级节点
|
||||
this.selectedOrg = [[defaultConsume.orgId, defaultConsume.children[0].orgId]];
|
||||
} else {
|
||||
// 没有子节点则选一级
|
||||
this.selectedOrg = [[defaultConsume.orgId]];
|
||||
}
|
||||
|
||||
// ---------- 工作地 ----------
|
||||
let defaultWork = res[0];
|
||||
if (defaultWork.children && defaultWork.children.length > 0) {
|
||||
this.gzselectedOrg = [[defaultWork.orgId, defaultWork.children[0].orgId]];
|
||||
} else {
|
||||
this.gzselectedOrg = [[defaultWork.orgId]];
|
||||
}
|
||||
|
||||
// 默认加载数据
|
||||
this.getplaceList();
|
||||
}
|
||||
});
|
||||
},
|
||||
|
||||
/** 严格要求:页面打开默认选择第一个(消费地 + 工作地)——仅在首次加载时设置 */
|
||||
setDefaultBothOrg() {
|
||||
if (this.orgOptions && this.orgOptions.length > 0) {
|
||||
const first = this.orgOptions[0];
|
||||
// 和你原来 cascader 数据结构兼容(使用数组路径)
|
||||
this.selectedOrg = [[first.orgId]];
|
||||
}
|
||||
if (this.gzorgOptions && this.gzorgOptions.length > 0) {
|
||||
const firstGz = this.gzorgOptions[0];
|
||||
this.gzselectedOrg = [[firstGz.orgId]];
|
||||
}
|
||||
},
|
||||
|
||||
// 获取所有子节点ID
|
||||
getAllChildIds(node) {
|
||||
let ids = [node.orgId];
|
||||
if (node.children && node.children.length > 0) {
|
||||
node.children.forEach(child => {
|
||||
ids = ids.concat(this.getAllChildIds(child));
|
||||
});
|
||||
}
|
||||
return ids;
|
||||
},
|
||||
|
||||
// 处理消费地选择变化
|
||||
handleOrgChange(value) {
|
||||
console.log('消费地选择变化:', value);
|
||||
this.selectedOrg = value || [];
|
||||
},
|
||||
|
||||
// 处理工作地选择变化
|
||||
handleGzOrgChange(value) {
|
||||
console.log('工作地选择变化:', value);
|
||||
this.gzselectedOrg = value || [];
|
||||
},
|
||||
|
||||
// 获取选中的消费地ID列表
|
||||
getSelectedOrgIds() {
|
||||
if (!this.selectedOrg || this.selectedOrg.length === 0) {
|
||||
return [];
|
||||
}
|
||||
|
||||
let ids = [];
|
||||
this.selectedOrg.forEach(path => {
|
||||
if (Array.isArray(path) && path.length > 0) {
|
||||
const lastId = path[path.length - 1];
|
||||
const node = this.findNodeById(this.orgOptions, lastId);
|
||||
if (node) {
|
||||
ids = ids.concat(this.getAllChildIds(node));
|
||||
} else {
|
||||
ids.push(lastId);
|
||||
}
|
||||
} else if (typeof path === 'string' || typeof path === 'number') {
|
||||
const node = this.findNodeById(this.orgOptions, path);
|
||||
if (node) {
|
||||
ids = ids.concat(this.getAllChildIds(node));
|
||||
} else {
|
||||
ids.push(path);
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
return [...new Set(ids)];
|
||||
},
|
||||
|
||||
// 获取选中的工作地ID列表
|
||||
getGzSelectedOrgIds() {
|
||||
if (!this.gzselectedOrg || this.gzselectedOrg.length === 0) {
|
||||
return [];
|
||||
}
|
||||
|
||||
let ids = [];
|
||||
this.gzselectedOrg.forEach(path => {
|
||||
if (Array.isArray(path) && path.length > 0) {
|
||||
const lastId = path[path.length - 1];
|
||||
const node = this.findNodeById(this.gzorgOptions, lastId);
|
||||
if (node) {
|
||||
ids = ids.concat(this.getAllChildIds(node));
|
||||
} else {
|
||||
ids.push(lastId);
|
||||
}
|
||||
} else if (typeof path === 'string' || typeof path === 'number') {
|
||||
const node = this.findNodeById(this.gzorgOptions, path);
|
||||
if (node) {
|
||||
ids = ids.concat(this.getAllChildIds(node));
|
||||
} else {
|
||||
ids.push(path);
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
return [...new Set(ids)];
|
||||
},
|
||||
|
||||
// 根据ID查找节点
|
||||
findNodeById(nodes, id) {
|
||||
if (!nodes || !Array.isArray(nodes)) return null;
|
||||
|
||||
for (const node of nodes) {
|
||||
if (node.orgId === id) {
|
||||
return node;
|
||||
}
|
||||
if (node.children && node.children.length > 0) {
|
||||
const found = this.findNodeById(node.children, id);
|
||||
if (found) return found;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
},
|
||||
|
||||
// 严格校验:查询时消费地和工作地都不能为空(提示风格保持原样)
|
||||
handleQuery() {
|
||||
if (!this.selectedOrg || this.selectedOrg.length === 0) {
|
||||
this.$message.warning('请选择消费地');
|
||||
return;
|
||||
}
|
||||
if (!this.gzselectedOrg || this.gzselectedOrg.length === 0) {
|
||||
this.$message.warning('请选择工作地');
|
||||
return;
|
||||
}
|
||||
|
||||
this.queryParams.pageNum = 1;
|
||||
this.getplaceList();
|
||||
},
|
||||
|
||||
resetQuery() {
|
||||
this.dateRange = this.defaultDateRange();
|
||||
this.selectedOrg = [];
|
||||
this.gzselectedOrg = [];
|
||||
this.queryParams = {
|
||||
pageNum: 1,
|
||||
pageSize: 10,
|
||||
selectedOrg: [],
|
||||
gzselectedOrg: [],
|
||||
startTime: '',
|
||||
endTime: ''
|
||||
};
|
||||
this.getplaceList();
|
||||
},
|
||||
|
||||
getplaceList() {
|
||||
this.loading = true;
|
||||
|
||||
// 处理日期范围
|
||||
if (this.dateRange && this.dateRange.length === 2) {
|
||||
const [start, end] = this.dateRange;
|
||||
this.queryParams.startTime = this.formatDate(start) + ' 00:00:00';
|
||||
this.queryParams.endTime = this.formatDate(end) + ' 23:59:59';
|
||||
} else {
|
||||
this.queryParams.startTime = '';
|
||||
this.queryParams.endTime = '';
|
||||
}
|
||||
|
||||
// 获取选中的组织ID
|
||||
this.queryParams.selectedOrg = this.getSelectedOrgIds();
|
||||
this.queryParams.gzselectedOrg = this.getGzSelectedOrgIds();
|
||||
|
||||
// 调试信息
|
||||
console.log('查询参数:', {
|
||||
...this.queryParams,
|
||||
selectedOrgRaw: this.selectedOrg,
|
||||
gzselectedOrgRaw: this.gzselectedOrg
|
||||
});
|
||||
|
||||
getplaceListhz(this.queryParams)
|
||||
.then(res => {
|
||||
console.log('接口返回数据:', res);
|
||||
this.tableListData = res.rows || [];
|
||||
this.total = Number(res.total) || 0;
|
||||
this.loading = false;
|
||||
})
|
||||
.catch(err => {
|
||||
console.error('查询失败:', err);
|
||||
this.$message.error('查询数据失败');
|
||||
this.loading = false;
|
||||
});
|
||||
},
|
||||
|
||||
handleSizeChange(val) {
|
||||
this.queryParams.pageSize = val;
|
||||
this.getplaceList();
|
||||
},
|
||||
|
||||
handleCurrentChange(val) {
|
||||
this.queryParams.pageNum = val;
|
||||
this.getplaceList();
|
||||
},
|
||||
|
||||
/** 统计方法:用于 el-table 底部合计行 */
|
||||
getSummaries(param) {
|
||||
const { columns, data } = param;
|
||||
const sums = [];
|
||||
|
||||
columns.forEach((column, index) => {
|
||||
if (index === 0) {
|
||||
sums[index] = '合计';
|
||||
return;
|
||||
}
|
||||
|
||||
if (column.property === 'tradeNum') {
|
||||
const values = data.map(item => Number(item.tradeNum) || 0);
|
||||
sums[index] = values.reduce((prev, curr) => prev + curr, 0);
|
||||
} else if (column.property === 'payableAmount') {
|
||||
const values = data.map(item => Number(item.payableAmount) || 0);
|
||||
const total = values.reduce((prev, curr) => prev + curr, 0);
|
||||
sums[index] = this.formatAmount(total);
|
||||
} else {
|
||||
sums[index] = '';
|
||||
}
|
||||
});
|
||||
|
||||
return sums;
|
||||
},
|
||||
|
||||
/** 导出 Excel */
|
||||
async newexportExcel() {
|
||||
if (!this.tableListData.length) {
|
||||
this.$message.warning("暂无数据可导出");
|
||||
return;
|
||||
}
|
||||
|
||||
try {
|
||||
const workbook = new ExcelJS.Workbook();
|
||||
const sheet = workbook.addWorksheet("消费地汇总");
|
||||
|
||||
// 表头
|
||||
const header = ["序号", "交易次数", "交易金额(元)", "消费地", "工作地"];
|
||||
sheet.addRow(header);
|
||||
|
||||
// 数据行
|
||||
this.tableListData.forEach((item, index) => {
|
||||
sheet.addRow([
|
||||
index + 1,
|
||||
item.tradeNum || 0,
|
||||
this.formatAmount(item.payableAmount),
|
||||
item.areaName || "-",
|
||||
item.workAreaName || "-"
|
||||
]);
|
||||
});
|
||||
|
||||
// 计算合计
|
||||
const totalTradeNum = this.tableListData.reduce((acc, r) => acc + (Number(r.tradeNum) || 0), 0);
|
||||
const totalPayable = this.tableListData.reduce((acc, r) => acc + (Number(r.payableAmount) || 0), 0);
|
||||
|
||||
// 添加合计行
|
||||
sheet.addRow([
|
||||
"合计",
|
||||
totalTradeNum,
|
||||
this.formatAmount(totalPayable),
|
||||
"",
|
||||
""
|
||||
]);
|
||||
|
||||
// 设置列宽
|
||||
sheet.columns = [
|
||||
{ width: 8 },
|
||||
{ width: 12 },
|
||||
{ width: 15 },
|
||||
{ width: 20 },
|
||||
{ width: 20 }
|
||||
];
|
||||
|
||||
// 表头样式
|
||||
sheet.getRow(1).eachCell(cell => {
|
||||
cell.font = { bold: true, size: 12, color: { argb: "FF000000" } };
|
||||
cell.alignment = { horizontal: "center", vertical: "middle" };
|
||||
cell.fill = {
|
||||
type: "pattern",
|
||||
pattern: "solid",
|
||||
fgColor: { argb: "FFEAEAEA" }
|
||||
};
|
||||
cell.border = {
|
||||
top: { style: "thin" },
|
||||
bottom: { style: "thin" },
|
||||
left: { style: "thin" },
|
||||
right: { style: "thin" }
|
||||
};
|
||||
});
|
||||
|
||||
// 数据行样式
|
||||
sheet.eachRow((row, rowNumber) => {
|
||||
if (rowNumber === sheet.rowCount) {
|
||||
row.eachCell(cell => {
|
||||
cell.font = { bold: true };
|
||||
cell.alignment = { horizontal: "center", vertical: "middle" };
|
||||
cell.border = {
|
||||
top: { style: "thin", color: { argb: "FFCCCCCC" } },
|
||||
bottom: { style: "thin", color: { argb: "FFCCCCCC" } },
|
||||
left: { style: "thin", color: { argb: "FFCCCCCC" } },
|
||||
right: { style: "thin", color: { argb: "FFCCCCCC" } }
|
||||
};
|
||||
cell.fill = {
|
||||
type: "pattern",
|
||||
pattern: "solid",
|
||||
fgColor: { argb: "FFF5F5F5" }
|
||||
};
|
||||
});
|
||||
return;
|
||||
}
|
||||
|
||||
if (rowNumber === 1) return;
|
||||
|
||||
row.eachCell(cell => {
|
||||
cell.alignment = { horizontal: "center", vertical: "middle" };
|
||||
cell.border = {
|
||||
top: { style: "thin", color: { argb: "FFCCCCCC" } },
|
||||
bottom: { style: "thin", color: { argb: "FFCCCCCC" } },
|
||||
left: { style: "thin", color: { argb: "FFCCCCCC" } },
|
||||
right: { style: "thin", color: { argb: "FFCCCCCC" } }
|
||||
};
|
||||
});
|
||||
});
|
||||
|
||||
// 导出文件
|
||||
const buffer = await workbook.xlsx.writeBuffer();
|
||||
const fileName = `消费地汇总_${this.formatDate(new Date())}.xlsx`;
|
||||
saveAs(new Blob([buffer], { type: "application/octet-stream" }), fileName);
|
||||
|
||||
this.$message.success("导出成功");
|
||||
} catch (error) {
|
||||
console.error('导出失败:', error);
|
||||
this.$message.error("导出失败");
|
||||
}
|
||||
},
|
||||
|
||||
/** 打印表格 */
|
||||
printTable() {
|
||||
const printContent = `
|
||||
<html>
|
||||
<head>
|
||||
<title>消费地汇总报表</title>
|
||||
<style>
|
||||
body { font-family: "Microsoft YaHei", Arial, sans-serif; padding: 20px; color: #333; }
|
||||
.print-header { text-align: center; margin-bottom: 20px; border-bottom: 2px solid #409EFF; padding-bottom: 10px; }
|
||||
.print-header h2 { margin: 0; color: #409EFF; }
|
||||
.print-table { width: 100%; border-collapse: collapse; margin-top: 10px; }
|
||||
.print-table th, .print-table td { border: 1px solid #ddd; padding: 8px 12px; text-align: center; }
|
||||
.print-table th { background-color: #f5f7fa; font-weight: bold; }
|
||||
.print-table tr:nth-child(even) { background-color: #f9f9f9; }
|
||||
.print-summary { font-weight: bold; background-color: #f0f9ff !important; }
|
||||
.print-footer { margin-top: 20px; text-align: right; font-size: 12px; color: #666; }
|
||||
@media print {
|
||||
body { margin: 0; padding: 15px; }
|
||||
.no-print { display: none; }
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<div class="print-header">
|
||||
<h2>消费地汇总报表</h2>
|
||||
<div>日期范围: ${this.dateRange[0] ? this.formatDate(this.dateRange[0]) : ''} 至 ${this.dateRange[1] ? this.formatDate(this.dateRange[1]) : ''}</div>
|
||||
</div>
|
||||
|
||||
<table class="print-table">
|
||||
<thead>
|
||||
<tr>
|
||||
<th>序号</th>
|
||||
<th>交易次数</th>
|
||||
<th>交易金额(元)</th>
|
||||
<th>消费地</th>
|
||||
<th>工作地</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
${this.tableListData.map((item, index) => `
|
||||
<tr>
|
||||
<td>${index + 1}</td>
|
||||
<td>${item.tradeNum || 0}</td>
|
||||
<td>${this.formatAmount(item.payableAmount)}</td>
|
||||
<td>${item.areaName || '-'}</td>
|
||||
<td>${item.workAreaName || '-'}</td>
|
||||
</tr>
|
||||
`).join('')}
|
||||
</tbody>
|
||||
<tfoot>
|
||||
<tr class="print-summary">
|
||||
<td>合计</td>
|
||||
<td>${this.tableListData.reduce((acc, item) => acc + (Number(item.tradeNum) || 0), 0)}</td>
|
||||
<td>${this.formatAmount(this.tableListData.reduce((acc, item) => acc + (Number(item.payableAmount) || 0), 0))}</td>
|
||||
<td></td>
|
||||
<td></td>
|
||||
</tr>
|
||||
</tfoot>
|
||||
</table>
|
||||
|
||||
<div class="print-footer">
|
||||
打印时间: ${new Date().toLocaleString()}
|
||||
</div>
|
||||
</body>
|
||||
</html>
|
||||
`;
|
||||
|
||||
const printWindow = window.open('', '_blank', 'width=1000,height=800');
|
||||
printWindow.document.write(printContent);
|
||||
printWindow.document.close();
|
||||
|
||||
printWindow.onload = function() {
|
||||
printWindow.focus();
|
||||
printWindow.print();
|
||||
};
|
||||
},
|
||||
|
||||
formatDate(date) {
|
||||
if (!date) return '';
|
||||
const y = date.getFullYear();
|
||||
const m = String(date.getMonth() + 1).padStart(2, '0');
|
||||
const d = String(date.getDate()).padStart(2, '0');
|
||||
return `${y}-${m}-${d}`;
|
||||
}
|
||||
}
|
||||
};
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
.app-container {
|
||||
padding: 20px;
|
||||
}
|
||||
|
||||
.table-container {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.el-table ::v-deep .el-table__body-wrapper td {
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
/* 合计行样式 - 确保始终可见 */
|
||||
.el-table ::v-deep .el-table__footer-wrapper {
|
||||
position: sticky !important;
|
||||
bottom: 0 !important;
|
||||
z-index: 10 !important;
|
||||
background-color: #f0f9ff !important;
|
||||
}
|
||||
|
||||
.el-table ::v-deep .el-table__footer .el-table__cell {
|
||||
background-color: #f0f9ff !important;
|
||||
font-weight: bold !important;
|
||||
color: #409eff !important;
|
||||
position: sticky !important;
|
||||
bottom: 0 !important;
|
||||
z-index: 10 !important;
|
||||
}
|
||||
|
||||
.el-table ::v-deep .el-table__footer td {
|
||||
background-color: #f0f9ff !important;
|
||||
font-weight: bold !important;
|
||||
border-bottom: 1px solid #ebeef5 !important;
|
||||
position: sticky !important;
|
||||
bottom: 0 !important;
|
||||
z-index: 10 !important;
|
||||
}
|
||||
|
||||
/* 表格主体区域 */
|
||||
.el-table ::v-deep .el-table__body-wrapper {
|
||||
max-height: calc(100vh - 300px) !important;
|
||||
overflow-y: auto !important;
|
||||
}
|
||||
|
||||
/* 分页样式 */
|
||||
.el-pagination {
|
||||
margin-top: 15px;
|
||||
text-align: right;
|
||||
}
|
||||
|
||||
/* 级联选择器样式优化 */
|
||||
.el-cascader {
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
/* 响应式设计 */
|
||||
@media (max-width: 768px) {
|
||||
.app-container {
|
||||
padding: 10px;
|
||||
}
|
||||
|
||||
.el-form--inline .el-form-item {
|
||||
display: block;
|
||||
margin-right: 0;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.el-form--inline .el-form-item__content {
|
||||
width: 100%;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
|
@ -0,0 +1,451 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<el-form :model="queryParams" ref="queryForm" size="small" :inline="true" v-show="showSearch" label-width="90px">
|
||||
<el-form-item label="盘点时间">
|
||||
<el-date-picker
|
||||
v-model="dateRange"
|
||||
type="datetimerange"
|
||||
align="right"
|
||||
unlink-panels
|
||||
range-separator="至"
|
||||
start-placeholder="开始日期"
|
||||
end-placeholder="结束日期"
|
||||
format="yyyy-MM-dd HH:mm:ss" style="width: 400px"
|
||||
:default-time="['00:00:00', '23:59:59']"
|
||||
:picker-options="pickerOptions" >
|
||||
</el-date-picker>
|
||||
</el-form-item>
|
||||
<el-form-item label="盘点单号" prop="checkId">
|
||||
<el-input v-model="queryParams.checkId" placeholder="请输入盘点单号" maxlength="20" clearable style="width: 240px"/>
|
||||
</el-form-item>
|
||||
<el-form-item label="所属区域">
|
||||
<el-cascader
|
||||
v-model="selectedOrg"
|
||||
:options="orgOptions"
|
||||
:show-all-levels="false"
|
||||
clearable
|
||||
filterable
|
||||
placeholder="请选择所属区域"
|
||||
:props="{
|
||||
checkStrictly: true,
|
||||
expandTrigger: 'hover',
|
||||
value: 'orgId',
|
||||
label: 'orgName',
|
||||
children: 'children'
|
||||
}"
|
||||
style="width: 200px;"
|
||||
>
|
||||
</el-cascader>
|
||||
</el-form-item>
|
||||
<el-form-item>
|
||||
<el-button type="primary" icon="el-icon-search" size="mini" @click="handleQuery">搜索</el-button>
|
||||
<el-button icon="el-icon-refresh" size="mini" @click="resetQuery">重置</el-button>
|
||||
</el-form-item>
|
||||
</el-form>
|
||||
|
||||
<el-row :gutter="10" class="mb8">
|
||||
<!-- <el-col :span="1.5">
|
||||
<el-button
|
||||
type="primary"
|
||||
plain
|
||||
icon="el-icon-plus"
|
||||
size="mini"
|
||||
@click="handleAdd"
|
||||
>新增</el-button>
|
||||
</el-col> -->
|
||||
<right-toolbar :showSearch.sync="showSearch" @queryTable="getList"></right-toolbar>
|
||||
</el-row>
|
||||
|
||||
<el-table v-loading="loading" :data="tableListData">
|
||||
<el-table-column label="序号" align="center" width="50" type="index">
|
||||
<template slot-scope="scope">
|
||||
<span>{{(queryParams.pageNum - 1) * queryParams.pageSize + scope.$index + 1}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column label="盘点单号" align="center" width="180" prop="checkId" />
|
||||
<el-table-column label="所属区域" align="center" prop="areaName" :show-overflow-tooltip="true"/>
|
||||
<el-table-column label="货品仓库" align="center" prop="warehouseName" :show-overflow-tooltip="true" />
|
||||
<el-table-column label="审批状态" align="center" prop="dealWithStatus">
|
||||
<template slot-scope="{ row }">
|
||||
<el-tag
|
||||
v-if="row.dealWithStatus == 1"
|
||||
effect="plain"
|
||||
class="status-tag status-gray"
|
||||
>
|
||||
⏳ 待审批
|
||||
</el-tag>
|
||||
|
||||
<el-tag
|
||||
v-else-if="row.dealWithStatus == 2"
|
||||
effect="light"
|
||||
class="status-tag status-blue"
|
||||
>
|
||||
🔄 审批中
|
||||
</el-tag>
|
||||
<el-tag
|
||||
v-else-if="row.dealWithStatus == 3"
|
||||
effect="light"
|
||||
class="status-tag status-red"
|
||||
>
|
||||
❌ 审批拒绝
|
||||
</el-tag>
|
||||
<el-tag
|
||||
v-else-if="row.dealWithStatus == 4"
|
||||
effect="plain"
|
||||
class="status-tag status-orange"
|
||||
>
|
||||
待平仓
|
||||
</el-tag>
|
||||
<el-tag
|
||||
v-else-if="row.dealWithStatus == 5"
|
||||
type="success"
|
||||
effect="light"
|
||||
class="status-tag status-success"
|
||||
>
|
||||
已平仓
|
||||
</el-tag>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column label="盘点状态" align="center" prop="status">
|
||||
<template slot-scope="{ row }">
|
||||
<el-tag
|
||||
v-if="row.status == 2"
|
||||
type="success"
|
||||
effect="light"
|
||||
class="status-tag status-success"
|
||||
>
|
||||
已盘点
|
||||
</el-tag>
|
||||
<el-tag
|
||||
v-else-if="row.status == 1"
|
||||
effect="plain"
|
||||
class="status-tag status-gray"
|
||||
>
|
||||
待盘点
|
||||
</el-tag>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column label="初盘人" align="center" prop="firstCheckUserName" :show-overflow-tooltip="true" />
|
||||
<el-table-column label="初盘时间" align="center" prop="firstCheckDate" :show-overflow-tooltip="true" width="150"/>
|
||||
<el-table-column label="监盘人" align="center" prop="inspectUserName" :show-overflow-tooltip="true" width="100"/>
|
||||
<el-table-column label="复盘人" align="center" prop="secondCheckUserName" :show-overflow-tooltip="true" width="100"/>
|
||||
<el-table-column label="复盘时间" align="center" prop="secondCheckDate" :show-overflow-tooltip="true" width="150"/>
|
||||
<el-table-column label="总盈亏(元)" align="center" prop="totalProfitLoss" :show-overflow-tooltip="true" width="120">
|
||||
<template slot-scope="scope">
|
||||
<span>{{ (scope.row.totalProfitLoss/100).toFixed(2) }}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column label="操作时间" align="center" prop="upTime" :show-overflow-tooltip="true" width="150"/>
|
||||
<el-table-column label="操作" align="center" width="180" class-name="small-padding fixed-width">
|
||||
<template slot-scope="scope">
|
||||
<el-button
|
||||
size="mini"
|
||||
type="text"
|
||||
icon="el-icon-edit" v-if="scope.row.status==1"
|
||||
@click="handleUpdate(scope.row)"
|
||||
>编辑</el-button>
|
||||
<el-button
|
||||
size="mini"
|
||||
type="text"
|
||||
icon="el-icon-edit" v-if="scope.row.status==2"
|
||||
@click="handleView(scope.row)"
|
||||
>详情</el-button>
|
||||
<el-button
|
||||
size="mini"
|
||||
type="text"
|
||||
icon="el-icon-delete" v-if="scope.row.status==1"
|
||||
@click="handleDelete(scope.row)"
|
||||
>删除</el-button>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
|
||||
<pagination
|
||||
v-show="total>0"
|
||||
:total="total"
|
||||
:page.sync="queryParams.pageNum"
|
||||
:limit.sync="queryParams.pageSize"
|
||||
@pagination="getList"
|
||||
/>
|
||||
|
||||
<!-- 添加或修改参数配置对话框 -->
|
||||
<el-dialog :title="title" :visible.sync="open" width="500px" append-to-body>
|
||||
<el-form ref="form" :model="form" :rules="rules" label-width="80px">
|
||||
</el-form>
|
||||
<div slot="footer" class="dialog-footer">
|
||||
<el-button type="primary" @click="submitForm">确 定</el-button>
|
||||
<el-button @click="cancel">取 消</el-button>
|
||||
</div>
|
||||
</el-dialog>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import {getTreeArea} from "@/api/canteen/canteenRecord";
|
||||
import {checkInventoryPageApi} from "@/api/inventoryCount/index";
|
||||
export default {
|
||||
name: "",
|
||||
dicts: [],
|
||||
data() {
|
||||
return {
|
||||
orgOptions:[],
|
||||
selectedOrg: [], // 消费地选择
|
||||
// 遮罩层
|
||||
loading: true,
|
||||
loadingBtn: false,
|
||||
// 选中数组
|
||||
ids: [],
|
||||
// 非单个禁用
|
||||
single: true,
|
||||
// 非多个禁用
|
||||
multiple: true,
|
||||
// 显示搜索条件
|
||||
showSearch: true,
|
||||
// 总条数
|
||||
total: 0,
|
||||
//表格数据
|
||||
tableListData: [],
|
||||
// 弹出层标题
|
||||
title: "",
|
||||
// 是否显示弹出层
|
||||
open: false,
|
||||
// 查询参数
|
||||
queryParams: {
|
||||
pageNum: 1,
|
||||
pageSize: 10,
|
||||
},
|
||||
treeAreaOptions:[],//区域树
|
||||
wareHouseOptions:[],//仓库下拉选
|
||||
dateRange:this.defaultDateRange(),
|
||||
pickerOptions: {
|
||||
shortcuts: [{
|
||||
text: '最近一周',
|
||||
onClick(picker) {
|
||||
const start = new Date();
|
||||
const end = new Date();
|
||||
start.setTime(start.getTime() - 3600 * 1000 * 24 * 6);
|
||||
picker.$emit('pick', [start, end]);
|
||||
}
|
||||
},{
|
||||
text: '最近一个月',
|
||||
onClick(picker) {
|
||||
const start = new Date();
|
||||
const end = new Date();
|
||||
start.setTime(start.getTime() - 3600 * 1000 * 24 * 30);
|
||||
picker.$emit('pick', [start, end]);
|
||||
}
|
||||
},{
|
||||
text: '最近三个月',
|
||||
onClick(picker) {
|
||||
const start = new Date();
|
||||
const end = new Date();
|
||||
start.setTime(start.getTime() - 3600 * 1000 * 24 * 91);
|
||||
picker.$emit('pick', [start, end]);
|
||||
}
|
||||
}]
|
||||
},
|
||||
// 表单参数
|
||||
form: {},
|
||||
// 表单校验
|
||||
rules: {
|
||||
// canteenName: [
|
||||
// { required: true, message: "字典名称不能为空", trigger: "blur" }
|
||||
// ],
|
||||
// dictType: [
|
||||
// { required: true, message: "字典类型不能为空", trigger: "blur" }
|
||||
// ]
|
||||
}
|
||||
};
|
||||
},
|
||||
created() {
|
||||
this.getTree();
|
||||
//this.getAreaTreeData();
|
||||
// this.getWareHouseData()
|
||||
this.getList();
|
||||
},
|
||||
methods: {
|
||||
getSelectedOrgIds() {
|
||||
if (!this.selectedOrg || this.selectedOrg.length === 0) return [];
|
||||
const lastValue = this.selectedOrg[this.selectedOrg.length - 1];
|
||||
// 找到对应节点
|
||||
let stack = [...this.orgOptions];
|
||||
let node = null;
|
||||
for (let val of this.selectedOrg) {
|
||||
node = stack.find(item => item.orgId === val);
|
||||
if (!node) break;
|
||||
stack = node.children || [];
|
||||
}
|
||||
|
||||
if (node) {
|
||||
return this.getAllChildIds(node, this.orgOptions);
|
||||
}
|
||||
return [lastValue];
|
||||
},
|
||||
// 递归获取节点及子节点的所有 orgId
|
||||
getAllChildIds(node, options) {
|
||||
let ids = [node.orgId]; // 当前节点
|
||||
if (node.children && node.children.length > 0) {
|
||||
node.children.forEach(child => {
|
||||
ids = ids.concat(this.getAllChildIds(child, options)); // 递归获取子节点
|
||||
});
|
||||
}
|
||||
return ids;
|
||||
},
|
||||
//区域树
|
||||
getTree(){
|
||||
getTreeArea().then(res => {
|
||||
this.orgOptions = res;
|
||||
this.gzorgOptions = JSON.parse(JSON.stringify(res)); // 深拷贝,避免引用问题
|
||||
});
|
||||
},
|
||||
handleAreaChange(e){
|
||||
this.getWareHouseData()
|
||||
},
|
||||
/** 查询货品下拉结构 */
|
||||
getWareHouseData() {
|
||||
drpWareHousePageApi({ areaId:this.queryParams.areaId }).then((response) => {
|
||||
this.wareHouseOptions = response.rows||[];
|
||||
this.$set(this.queryParams,'warehouseId',null)
|
||||
});
|
||||
},
|
||||
/** 搜索按钮操作 */
|
||||
handleQuery() {
|
||||
this.queryParams.pageNum = 1;
|
||||
this.getList();
|
||||
},
|
||||
/** 重置按钮操作 */
|
||||
resetQuery() {
|
||||
this.dateRange = this.defaultDateRange()
|
||||
this.queryParams = {
|
||||
pageNum: 1,
|
||||
pageSize: 10,
|
||||
}
|
||||
this.resetForm("queryForm");
|
||||
this.handleQuery();
|
||||
},
|
||||
/** 查询列表 */
|
||||
getList() {
|
||||
this.loading = true;
|
||||
this.queryParams.selectedOrg = this.getSelectedOrgIds();
|
||||
// 基础查询参数
|
||||
let queryParams = {
|
||||
checkId: this.queryParams.checkId,
|
||||
areaId: this.queryParams.areaId,
|
||||
startTime: undefined,
|
||||
endTime: undefined,
|
||||
checkId:this.queryParams.checkId,
|
||||
selectedOrg: this.queryParams.selectedOrg,
|
||||
}
|
||||
|
||||
// 日期处理
|
||||
if (this.dateRange && this.dateRange.length > 0) {
|
||||
const [start, end] = this.dateRange
|
||||
const formatDate = d => {
|
||||
const date = new Date(d)
|
||||
const y = date.getFullYear()
|
||||
const m = String(date.getMonth() + 1).padStart(2, '0')
|
||||
const day = String(date.getDate()).padStart(2, '0')
|
||||
return `${y}-${m}-${day}`
|
||||
}
|
||||
queryParams.startTime = formatDate(start) + ' 00:00:00'
|
||||
queryParams.endTime = formatDate(end) + ' 23:59:59'
|
||||
}
|
||||
|
||||
// 合并分页参数
|
||||
let requestData = {
|
||||
...queryParams,
|
||||
pageNum: this.queryParams.pageNum,
|
||||
pageSize: this.queryParams.pageSize
|
||||
}
|
||||
checkInventoryPageApi(requestData).then(response => {
|
||||
this.tableListData = response.rows;
|
||||
this.total = Number(response.total); // total要从后台返回
|
||||
this.loading = false;
|
||||
});
|
||||
},
|
||||
/** 新增按钮操作 */
|
||||
handleAdd() {
|
||||
this.$router.push({ path: "/inventoryCount/inventoryCountEdit" });
|
||||
},
|
||||
/** 修改按钮操作 */
|
||||
handleView(row) {
|
||||
this.$router.push({ path: "/inventoryCount/inventoryCountDetail",query: {countRowData:JSON.stringify(row)} });
|
||||
},
|
||||
/** 修改按钮操作 */
|
||||
handleUpdate(row) {
|
||||
this.$router.push({ path: "/inventoryCount/inventoryCountEdit",query: {countRowData:JSON.stringify(row)} });
|
||||
},
|
||||
// 取消按钮
|
||||
cancel() {
|
||||
this.open = false;
|
||||
this.reset();
|
||||
},
|
||||
// 表单重置
|
||||
reset() {
|
||||
this.form = {};
|
||||
this.resetForm("form");
|
||||
},
|
||||
/** 提交按钮 */
|
||||
submitForm: function() {
|
||||
this.$refs["form"].validate(valid => {
|
||||
if (valid) {
|
||||
if (this.form.dictId != undefined) {
|
||||
// updateType(this.form).then(response => {
|
||||
// this.$modal.msgSuccess("修改成功");
|
||||
// this.open = false;
|
||||
// this.getList();
|
||||
// });
|
||||
} else {
|
||||
// addType(this.form).then(response => {
|
||||
// this.$modal.msgSuccess("新增成功");
|
||||
// this.open = false;
|
||||
// this.getList();
|
||||
// });
|
||||
}
|
||||
}
|
||||
});
|
||||
},
|
||||
/** 删除按钮操作 */
|
||||
handleDelete(row) {
|
||||
this.$modal.confirm('是否确认删除数据项?').then(function() {
|
||||
return delCheckInventoryApi({checkId:row.checkId});
|
||||
}).then(() => {
|
||||
this.getList();
|
||||
this.$modal.msgSuccess("删除成功");
|
||||
}).catch(() => {});
|
||||
},
|
||||
defaultDateRange() {
|
||||
const end = new Date(new Date().toLocaleDateString());
|
||||
end.setTime(end.getTime() + 24 * 60 * 60 * 1000 -1);
|
||||
const start = new Date((new Date().toLocaleDateString()));
|
||||
start.setTime(start.getTime() - 30 * 24 * 60 * 60 * 1000);
|
||||
this.start = parseInt(start.getTime() / 1000)
|
||||
this.end = parseInt(end.getTime() / 1000)
|
||||
return [start, end]
|
||||
},
|
||||
//日期
|
||||
formatDate(date) {
|
||||
// 格式化为 YYYY-MM-DD
|
||||
date = new Date(date)
|
||||
const year = date.getFullYear();
|
||||
const month = String(date.getMonth() + 1).padStart(2, '0'); // 月份从0开始
|
||||
const day = String(date.getDate()).padStart(2, '0');
|
||||
return `${year}-${month}-${day}`;
|
||||
},
|
||||
//日期时间
|
||||
formatDateTime(date) {
|
||||
// 格式化为 YYYY-MM-DD
|
||||
date = new Date(date)
|
||||
const year = date.getFullYear();
|
||||
const month = String(date.getMonth() + 1).padStart(2, '0'); // 月份从0开始
|
||||
const day = String(date.getDate()).padStart(2, '0');
|
||||
const hours = date.getHours() < 10 ? '0' + date.getHours() : date.getHours()
|
||||
const minutes = date.getMinutes() < 10 ? '0' + date.getMinutes() : date.getMinutes()
|
||||
const seconds = date.getSeconds() < 10 ? '0' + date.getSeconds() : date.getSeconds()
|
||||
return `${year}-${month}-${day} ${hours}:${minutes}:${seconds}`;
|
||||
}
|
||||
}
|
||||
};
|
||||
</script>
|
||||
Loading…
Reference in New Issue