From d725dc65cf7f74df3aa3f5a0297fd6f8b767cdbc Mon Sep 17 00:00:00 2001
From: liusheng <337615773@qq.com>
Date: 星期五, 30 十月 2026 10:23:03 +0800
Subject: [PATCH] Merge branch 'subtask' of http://116.62.18.175:6699/r/~yxh/smartor-web into subtask
---
src/views/Satisfaction/sfstatistics/components/ChartsPanel.vue | 175 ++++++++++++++++++++++++++++++++++++++++++----------------
1 files changed, 127 insertions(+), 48 deletions(-)
diff --git a/src/views/Satisfaction/sfstatistics/components/ChartsPanel.vue b/src/views/Satisfaction/sfstatistics/components/ChartsPanel.vue
index 86c5b41..e5b5e64 100644
--- a/src/views/Satisfaction/sfstatistics/components/ChartsPanel.vue
+++ b/src/views/Satisfaction/sfstatistics/components/ChartsPanel.vue
@@ -41,7 +41,7 @@
<el-button type="primary" size="small" icon="el-icon-search" @click="refreshAll">鏌ヨ</el-button>
<el-button size="small" icon="el-icon-refresh" @click="handleReset">閲嶇疆</el-button>
</div>
- <el-button type="danger" size="small" icon="el-icon-download" @click="exportPDF">瀵煎嚭PDF</el-button>
+ <el-button type="danger" size="small" icon="el-icon-download" @click="exportExcel">瀵煎嚭Excel</el-button>
</div>
<el-row :gutter="20">
@@ -171,6 +171,8 @@
<script>
import * as echarts from 'echarts';
+import ExcelJS from 'exceljs';
+import { saveAs } from 'file-saver';
import { mydTrend, sltdMydTotalByDimension, sltdMydTotalByScore ,mzMydScoreRank} from "@/api/AiCentre/satisfaction";
import { getissuelist } from "@/api/AiCentre/questionnaire";
@@ -198,10 +200,10 @@
singleQuestionContent: '',
singleDeptWards: [],
- // 鎺掑悕缁村害绛涢��
- rankDimension: 'dept',
+ // 鎺掑悕缁村害绛涢�夛紙榛樿鎸夌梾鍖猴級
+ rankDimension: 'ward',
rankDeptWards: [],
- crossDimension: 'dept',
+ crossDimension: 'ward',
crossDeptWards: [],
// 鍥捐〃鏁版嵁
@@ -845,52 +847,129 @@
});
},
- async exportPDF() {
- const chartRefs = [
- { ref: this.$refs.chart1, id: 'chart1' },
- { ref: this.$refs.chart2, id: 'chart2' },
- { ref: this.$refs.chart4, id: 'chart4' },
- ];
- const chartImages = {};
- for (const { ref, id } of chartRefs) {
- if (ref) {
- const instance = echarts.getInstanceByDom(ref);
- if (instance) {
- chartImages[id] = instance.getDataURL({ type: 'png', pixelRatio: 2, backgroundColor: '#fff' });
+ // 瀵煎嚭锛氬浘琛ㄨ浆鍥剧墖 + 琛ㄦ牸锛屽唴瀹逛笌椤甸潰涓�鑷达紙鐩存帴涓嬭浇 xlsx锛屼笉渚濊禆鎵撳嵃锛�
+ async exportExcel() {
+ try {
+ const wb = new ExcelJS.Workbook();
+
+ // 鍥捐〃 sheet
+ const addImageSheet = (sheetName, title, refEl, tip) => {
+ const ws = wb.addWorksheet(sheetName, {
+ views: [{ showGridLines: false }],
+ });
+ ws.getCell('A1').value = title;
+ ws.getCell('A1').font = { size: 14, bold: true };
+ ws.mergeCells('A1:F1');
+ let anchorRow = 2.2;
+ if (tip) {
+ ws.getCell('A2').value = tip;
+ ws.mergeCells('A2:F2');
+ anchorRow = 2.8;
}
- }
+ for (let c = 1; c <= 6; c++) {
+ ws.getColumn(c).width = 18;
+ }
+ const inst = refEl ? echarts.getInstanceByDom(refEl) : null;
+ if (inst) {
+ const url = inst.getDataURL({
+ type: 'png',
+ pixelRatio: 2,
+ backgroundColor: '#fff',
+ });
+ const imgId = wb.addImage({
+ base64: url.split(',')[1],
+ extension: 'png',
+ });
+ ws.addImage(imgId, {
+ tl: { col: 0.1, row: anchorRow },
+ ext: { width: 900, height: 400 },
+ });
+ } else {
+ ws.getCell(`A${Math.ceil(anchorRow)}`).value = '鏆傛棤鏁版嵁';
+ }
+ return ws;
+ };
+
+ addImageSheet(
+ '缁煎悎寰楀垎瓒嬪娍',
+ '鎮h�呮弧鎰忓害缁煎悎寰楀垎瓒嬪娍',
+ this.$refs.chart1,
+ `鐜瘮 ${this.trendMoM}`
+ );
+ addImageSheet(
+ '鍒嗙被缁村害瀵规瘮',
+ `鍒嗙被缁村害 路 鍚勬寚鏍�${this.intervalLabel}瀵规瘮`,
+ this.$refs.chart2,
+ ''
+ );
+ addImageSheet(
+ '闄㈠尯缁村害瀵规瘮',
+ `闄㈠尯缁村害 路 鍚勯櫌鍖�${this.intervalLabel}瀵规瘮`,
+ this.$refs.chart4,
+ ''
+ );
+
+ // 鍗曢 路 閫夐」缁熻
+ const wsQ = wb.addWorksheet('鍗曢閫夐」缁熻');
+ wsQ.addRow(['鍗曢 路 閫夐」缁熻']).font = { size: 14, bold: true };
+ wsQ.mergeCells(1, 1, 1, 3);
+ const qHead = wsQ.addRow(['閫夐」', '鍚堣鏁伴噺', '鍗犳瘮姣斾緥']);
+ qHead.font = { bold: true };
+ (this.singleQuestionData || []).forEach((r) => {
+ wsQ.addRow([r.option, r.count, r.rate]);
+ });
+ wsQ.addRow([]);
+ wsQ.addRow([
+ `鏈鏈夋晥濉啓浜烘锛�${this.singleQuestionMeta.total}銆�缁煎悎寰楀垎锛�${this.singleQuestionMeta.score}`,
+ '',
+ '',
+ ]);
+ wsQ.mergeCells(wsQ.rowCount, 1, wsQ.rowCount, 3);
+ wsQ.columns.forEach((c, i) => {
+ c.width = i === 0 ? 36 : 16;
+ });
+
+ // 鎺掑悕琛ㄦ牸
+ const addRankSheet = (sheetName, title, rows, dimLabel) => {
+ const ws = wb.addWorksheet(sheetName);
+ ws.addRow([title]).font = { size: 14, bold: true };
+ ws.mergeCells(1, 1, 1, 4);
+ const head = ws.addRow(['鎺掑悕', dimLabel, '缁煎悎寰楀垎', '椤规暟']);
+ head.font = { bold: true };
+ (rows || []).forEach((r) => {
+ ws.addRow([r.rank, r.name, r.score, r.itemCount]);
+ });
+ if (!rows || !rows.length) {
+ ws.addRow(['鏆傛棤鏁版嵁', '', '', '']);
+ }
+ ws.columns.forEach((c, i) => {
+ c.width = i === 1 ? 30 : 12;
+ });
+ };
+ addRankSheet(
+ `${this.rankDimLabel}鎺掑悕`,
+ `${this.rankDimLabel}缁村害 路 闂ㄨ瘖鎮h�呮弧鎰忓害寰楀垎鎺掑悕`,
+ this.rankRows,
+ this.rankDimLabel
+ );
+ addRankSheet(
+ `鍗曢脳${this.crossDimLabel}鎺掑悕`,
+ `鍗曢脳${this.crossDimLabel} 路 寰楀垎鎺掑悕`,
+ this.crossRows,
+ this.crossDimLabel
+ );
+
+ const buffer = await wb.xlsx.writeBuffer();
+ const blob = new Blob([buffer], {
+ type: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet',
+ });
+ const range = (this.queryParams.dateRange || []).join('_');
+ saveAs(blob, `鍚勯」缁熻琛�${range ? '_' + range : ''}.xlsx`);
+ this.$message.success('瀵煎嚭鎴愬姛');
+ } catch (e) {
+ console.error('瀵煎嚭澶辫触:', e);
+ this.$message.error('瀵煎嚭澶辫触锛�' + (e.message || e));
}
-
- const printContent = this.$refs.pdfTarget.cloneNode(true);
- const chartBoxes = printContent.querySelectorAll('.chart-box');
- const imgKeys = Object.keys(chartImages);
- chartBoxes.forEach((box, i) => {
- if (imgKeys[i] && chartImages[imgKeys[i]]) {
- box.innerHTML = `<img src="${chartImages[imgKeys[i]]}" style="width:100%;height:auto;" />`;
- }
- });
-
- const win = window.open('', '_blank', 'width=900,height=800');
- if (!win) { this.$message.warning('璇峰厑璁稿脊鍑虹獥鍙d互瀵煎嚭PDF'); return; }
- win.document.write(`
- <html><head><meta charset="utf-8"><title>鍚勯」缁熻琛�</title>
- <style>
- body { font-family: 'Microsoft YaHei',sans-serif; padding: 20px; }
- .chart-card { break-inside: avoid; margin-bottom: 20px; border: 1px solid #ebeef5; border-radius: 6px; }
- .card-header { padding: 12px 16px; border-bottom: 1px solid #ebeef5; font-size: 15px; font-weight: 600; color: #303133; background: #f5f7fa; }
- .chart-box img { max-width: 100%; display: block; }
- table { width: 100%; border-collapse: collapse; margin: 12px 0; }
- th, td { border: 1px solid #d9d9d9; padding: 8px 12px; text-align: center; font-size: 12px; }
- th { background: #f0f2f5; font-weight: 600; }
- .table-footer { text-align: right; padding: 8px 0; font-size: 13px; color: #606266; }
- .export-bar, .filter-bar, .el-tag, .el-select, .el-radio-group { display: none; }
- @media print { @page { size: A4; margin: 10mm; } }
- </style></head><body>
- ${printContent.innerHTML}
- <script>window.onload=function(){window.print();}<\/script>
- </body></html>
- `);
- win.document.close();
},
},
};
--
Gitblit v1.9.3