vue3+vite完成前端下载excel文件/模板并规定单元格大小(纯前端)
生活随笔
收集整理的這篇文章主要介紹了
vue3+vite完成前端下载excel文件/模板并规定单元格大小(纯前端)
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
首先當然就是下載相關的npm包了
npm install --save file-save xlsx npm install --save script-loader然后我是在utils下面創建了一個用于存放關于這部分功能的文件夾
?然后接下來就是代碼了
//excel.jsimport { export_json_to_excel } from './Export2Excel' export function downloadFile (url) {try {var elemIF = document.createElement('iframe')elemIF.src = urlelemIF.style.display = 'none'document.body.appendChild(elemIF)} catch (e) {console.error(e)} } // 導出excel 表格 tabHeader 表頭 tabFilterVal 過濾的字段 tabList 數據集合 export function exportExcels (tabHeader, tabFilterVal, tabList, fileName = Math.random() * 100) {const data = formatJson(tabFilterVal, tabList)export_json_to_excel({header: tabHeader,data,filename: fileName})function formatJson (filterVal, tableData) {return tableData.map(v => {return filterVal.map(j => {return v[j]})})} }修改單元格需要修改Export2Excel.js的代碼,具體寫在備注里了?
//Export2Excel.js/* eslint-disable */ import {saveAs} from 'file-saver' import {SSF,utils,write} from 'xlsx'function generateArray (table) {var out = [];var rows = table.querySelectorAll('tr');var ranges = [];for (var R = 0; R < rows.length; ++R) {var outRow = [];var row = rows[R];var columns = row.querySelectorAll('td');for (var C = 0; C < columns.length; ++C) {var cell = columns[C];var colspan = cell.getAttribute('colspan');var rowspan = cell.getAttribute('rowspan');var cellValue = cell.innerText;if (cellValue !== "" && cellValue == +cellValue) cellValue = +cellValue;//Skip rangesranges.forEach(function (range) {if (R >= range.s.r && R <= range.e.r && outRow.length >= range.s.c && outRow.length <= range.e.c) {for (var i = 0; i <= range.e.c - range.s.c; ++i) outRow.push(null);}});//Handle Row Spanif (rowspan || colspan) {rowspan = rowspan || 1;colspan = colspan || 1;ranges.push({s: {r: R,c: outRow.length},e: {r: R + rowspan - 1,c: outRow.length + colspan - 1}});};//Handle ValueoutRow.push(cellValue !== "" ? cellValue : null);//Handle Colspanif (colspan)for (var k = 0; k < colspan - 1; ++k) outRow.push(null);}out.push(outRow);}return [out, ranges]; };function datenum (v, date1904) {if (date1904) v += 1462;var epoch = Date.parse(v);return (epoch - new Date(Date.UTC(1899, 11, 30))) / (24 * 60 * 60 * 1000); }function sheet_from_array_of_arrays (data, opts) {var ws = {};var range = {s: {c: 10000000,r: 10000000},e: {c: 0,r: 0}};for (var R = 0; R != data.length; ++R) {for (var C = 0; C != data[R].length; ++C) {if (range.s.r > R) range.s.r = R;if (range.s.c > C) range.s.c = C;if (range.e.r < R) range.e.r = R;if (range.e.c < C) range.e.c = C;var cell = {v: data[R][C]};if (cell.v == null) continue;var cell_ref = utils.encode_cell({c: C,r: R});if (typeof cell.v === 'number') cell.t = 'n';else if (typeof cell.v === 'boolean') cell.t = 'b';else if (cell.v instanceof Date) {cell.t = 'n';cell.z = SSF._table[14];cell.v = datenum(cell.v);} else cell.t = 's';ws[cell_ref] = cell;}}if (range.s.c < 10000000) ws['!ref'] = utils.encode_range(range);return ws; }function Workbook () {if (!(this instanceof Workbook)) return new Workbook();this.SheetNames = [];this.Sheets = {}; }function s2ab (s) {var buf = new ArrayBuffer(s.length);var view = new Uint8Array(buf);for (var i = 0; i != s.length; ++i) view[i] = s.charCodeAt(i) & 0xFF;return buf; }export function export_table_to_excel (id) {var theTable = document.getElementById(id);var oo = generateArray(theTable);var ranges = oo[1];/* original data */var data = oo[0];var ws_name = "SheetJS";var wb = new Workbook(),ws = sheet_from_array_of_arrays(data);/* add ranges to worksheet */// ws['!cols'] = ['apple', 'banan'];ws['!merges'] = ranges;/* add worksheet to workbook */wb.SheetNames.push(ws_name);wb.Sheets[ws_name] = ws;var wbout = write(wb, {bookType: 'xlsx',bookSST: false,type: 'binary'});saveAs(new Blob([s2ab(wbout)], {type: "application/octet-stream"}), "test.xlsx") }export function export_json_to_excel ({header,data,filename,autoWidth = true,bookType = 'xlsx'} = {}) {/* original data */filename = filename || 'excel-list'data = [...data]data.unshift(header);var ws_name = "SheetJS";var wb = new Workbook(),ws = sheet_from_array_of_arrays(data);if (autoWidth) {/*設置worksheet每列的最大寬度*/const colWidth = data.map(row => row.map(val => {/*val值為你設置的表頭也就是你的tagHeader*//*先判斷是否為null/undefined*/if (val == null) {return {/*如果為空單元格的寬度就是10*/'wch': 10};}/*再判斷是否為中文*/else if (val.toString().charCodeAt(0) > 255) {return {/*如果你的表頭為中文,單元格寬度就是你字符串長度的兩倍*//*如果你的表頭為中文就可以設置這里wch的值*/'wch': val.toString().length * 2};} else {return {/*如果你的表頭為英文,單元格寬度就是你字符串長度*//*如果你的表頭為英文就可以設置這里wch的值*/'wch': val.toString().length};}}))/*以第一行為初始值*/let result = colWidth[0];for (let i = 1; i < colWidth.length; i++) {for (let j = 0; j < colWidth[i].length; j++) {if (result[j]['wch'] < colWidth[i][j]['wch']) {result[j]['wch'] = colWidth[i][j]['wch'];}}}ws['!cols'] = result;}/* add worksheet to workbook */wb.SheetNames.push(ws_name);wb.Sheets[ws_name] = ws;var wbout = write(wb, {bookType: bookType,bookSST: false,type: 'binary'});saveAs(new Blob([s2ab(wbout)], {type: "application/octet-stream"}), `${filename}.${bookType}`); } //導出的excel數據 如果只想要模板不想里面有數據可以不創建此文件或者導出的數據字段都為空也行//模板數據 export const templateData = [{name:'',jobNumber:'',phone:'',email:'',} ]?然后就在你要寫這個功能的頁面引入相關的方法
import { exportExcels } from '@/utils/excelTemplate/excel' import {templateData} from '@/utils/excelTemplate/templateData'?引入完成之后直接在你的頁面給你的事件綁定這個方法就ok,如果你想要里面有數據的話可以把exportExcels這個方法的第三個參數改成引入的templateData的數據就行,我這里只想要模板,所以就沒有用,直接就是一個空數組了
const downExcelTemplate = () => {const tagHeader = ['員工名稱', '員工工號', '手機號', '郵箱']const tagFilterVal = ['name', 'jobNumber', 'phone', 'email']exportExcels(tagHeader,tagFilterVal,[],'員工表') }至此就結束了,網上也搜了很多方法不知道為啥報錯,感覺可能是因為我用的vue3的原因,然后就拿了一些自己再改改就ok了
這是最后生成的效果圖
總結
以上是生活随笔為你收集整理的vue3+vite完成前端下载excel文件/模板并规定单元格大小(纯前端)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 简单音乐播放器,上一曲下一曲,暂停
- 下一篇: Vue Element-ui上传图片踩坑