在vue中将element的表格进行导出为pdf/word/excel样式,需要进行一些处理,比较麻烦
网页样式导出为表格
导出为word
导出为PDF
一、编写工具函数和前置对element样式的修改函数
@param {String} inerHTML 需要导出的html字段
@param {String} typeName 需要导出的文件类型
(注意最外层需要一个单独的容器包裹,使用)
// 导出函数exportfunctionexportFileByInerHTML(inerHTML, typeName){const dateTime=newDate();const dateTimeStr=
dateTime.getFullYear()+"-"+
dateTime.getMonth()+"-"+
dateTime.getDay();let blob;try{//word文档为msword,docx为vnd,pdf文档为pdf,msexcel 为excel
blob=newBlob([inerHTML],{
type:"application/file"});}catch(e){if(typeof console!=="undefined"){this.$message.error("导出失败");
console.log(e);}}let objectUrl=URL.createObjectURL(blob);let link= document.createElement("a");let fname=`表格_${dateTimeStr}.${typeName}`;//下载文件的名字
link.href= objectUrl;
link.setAttribute("download", fname);
document.body.appendChild(link);
link.click();}
1. 因为表格只支持最原生的border,但是element的样式没有设置,并且最右侧
和底部
是没有线条
的,然后最右侧和底部被element的css样式的before和after覆盖了,我们都要自己去设置和清除
2. element表格其实是两个table组成,第一个table是表头,第二个table是内容,我们要把第一个的tr放到第二个的table里面,导出结束后复原。
打印pdf需要进行的样式修改,通过vuedata中 { isPrintToPdfFlag: false}来控制‘
在<el-tabler>
的外层加一个class标识符
<divid="print-table"class="table-container":class="{'printToPdf': isPrintToPdfFlag}"><tableclass="table-configurable"border="0"cellspacing="0"cellpadding="0">
......</table></div>
.printToPdf {
/deep/ .el-table {
&--border {
&::after {
background-color: none;
}
&--group {
&::after {
background-color: none;
}
}
&::after {
background-color: none;
}
}
}
}
前置设置:
// todo设置表格样式setTableStyle(){//table-designer-container是我自己的外层class,换成你自己的!!!!!!!!!!!!!!!let tableDomList= document.querySelector(".table-designer-container").getElementsByTagName("table");// 去除element的覆盖层this.isPrintToPdfFlag=true;let headRightTh= tableDomList[0].getElementsByTagName("tr")[0].getElementsByTagName("th");
headRightTh[headRightTh.length-2].style.borderRight="1px solid #ABABAB";// 遍历两个tablelet tableLength= tableDomList.length;for(let i=0; i< tableLength; i++){
tableDomList[i].setAttribute("border","1");
tableDomList[i].style.border="#ffffff";let childTr= tableDomList[i].getElementsByTagName("tr");let childTrLength= childTr.length;// 第一个table是头部,没有td会报错if(i>0){for(let j=0; j< childTrLength; j++){let childTd= childTr[j].getElementsByTagName("td");let childTdLength= childTd.length;// 修改最后一个的边框值if(childTd[childTdLength-1].style){
childTd[childTdLength-1].style.borderRight="1px solid #ABABAB";}for(let k=0; k< childTdLength; k++){
childTd[k].style.padding="8px 0";//改变之后与element高度一致
childTd[k].style.valign="center";
childTd[k].style.align="center";
childTd[k].style.textAlign="center";if(j== childTrLength-1){
childTd[k].style.borderBottom="1px solid #ABABAB";}}}}else{// 去除第一个table去除最右侧的空白thlet childTr= tableDomList[i].getElementsByTagName("tr");let childTrLength= childTr.length;for(let i=0; i< childTrLength; i++){let lastTh= childTr[i].querySelector(".gutter");if(lastTh){
lastTh.parentNode.removeChild(lastTh);}}}}// print-table是我自己的外层id,换成你自己的idreturn document.querySelector("#print-table .el-table").innerHTML;}
导出后要清除设置
// todo清除表格样式clearTableStyle(){//table-designer-container是我自己的外层class,换成你自己的!!!!!!!!!!!!!!!let tableDomList= document.querySelector(".table-designer-container").getElementsByTagName("table");// 去除第一个table表头最右侧的边框let headRightTh= tableDomList[0].getElementsByTagName("tr")[0].getElementsByTagName("th");
headRightTh[headRightTh.length-2].style.borderRight="1px solid #EBEEF5";//去除右侧和最底部的样式for(let i=0; i< tableDomList.length; i++){
tableDomList[i].setAttribute("border","0");
tableDomList[i].style.border="none";let childTr= tableDomList[i].getElementsByTagName("tr");let childTrLength= childTr.length;// 第一个table是头部,没有td会报错if(i>0){for(let j=0; j< childTrLength; j++){let childTd= childTr[j].getElementsByTagName("td");let childTdLength= childTd.length;// 修改最后一个的边框值if(childTd[childTdLength-1].style){
childTd[childTdLength-1].style.borderRight="none";}for(let k=0; k< childTdLength; k++){if(j== childTrLength-1){
childTd[k].style.borderBottom="1px solid #EBEEF5";}}}}}},
二、导出excel和word
// 设置边框this.setTableStyle()// 变换结点,让空格// #print-table是我自己的外层idlet _table_body= document.querySelector("#print-table .el-table__body-wrapper .el-table__body tbody");let _docHtml= document.querySelector("#print-table .el-table__header-wrapper .el-table__header");
_docHtml.appendChild(_table_body);let _header_wrapper= document.querySelector("#print-table .el-table__header-wrapper");exportFileByInerHTML(_header_wrapper.innerHTML,"doc");//导出表格就用‘’xlsx/xls之类的// 导出完毕要把dom界面复原,然后再去除修改的格式let _table__body= document.querySelector("#print-table .el-table__body-wrapper .el-table__body")
_table__body.appendChild(_docHtml.querySelector('tbody'));this.clearTableStyle();
三、导出为pdf,借助iframe
生成自己的代码片段,然后借助浏览器自带的打印功能,要手动选择另存为PDF!!!!!!
<!-- 导出pdf--><iframeid="exportPdf"src="localhost:8080/TableDesigner.html"width="0"height="0"></iframe>
this.setTableStyle();let iframe= document.getElementById("exportPdf");let doc= iframe.contentWindow.document;// #print-table是自己的外层idlet tcontent= document.querySelector("#print-table .el-table").innerHTML;//获取table表中数据//将获取到html标签数据赋值给iframe中组件中id中,组件的样式将影响html标签数据
doc.getElementsByTagName("body")[0].innerHTML= tcontent;
iframe.contentWindow.print();//调取iframe打印,数据过多打印会自动分页//清除样式this.clearTableStyle();