在vue中将element的表格进行导出为pdf/word/excel样式,需要进行一些处理,比较麻烦

网页样式
在这里插入图片描述
导出为表格
在这里插入图片描述
导出为word
在这里插入图片描述
导出为PDF
在这里插入图片描述

一、编写工具函数和前置对element样式的修改函数

@param {String} inerHTML 需要导出的html字段
@param {String} typeName 需要导出的文件类型
(注意最外层需要一个单独的容器包裹,使用)

// 导出函数
export function exportFileByInerHTML(inerHTML, typeName) {
  const dateTime = new Date();
      const dateTimeStr =
        dateTime.getFullYear() +
        "-" +
        dateTime.getMonth() +
        "-" +
        dateTime.getDay();
      let blob;
      try {
        //word文档为msword,docx为vnd,pdf文档为pdf,msexcel 为excel
        blob = new Blob([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标识符

<div id="print-table" class="table-container" :class="{'printToPdf': isPrintToPdfFlag}">
	<table class="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";

      // 遍历两个table
      let 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去除最右侧的空白th
          let 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,换成你自己的id
    return 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是我自己的外层id
let _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-->
<iframe id="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是自己的外层id
let 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();

看完点个赞,谢谢!
在这里插入图片描述

GitHub 加速计划 / eleme / element
54.06 K
14.63 K
下载
A Vue.js 2.0 UI Toolkit for Web
最近提交(Master分支:3 个月前 )
c345bb45 7 个月前
a07f3a59 * Update transition.md * Update table.md * Update transition.md * Update table.md * Update transition.md * Update table.md * Update table.md * Update transition.md * Update popover.md 7 个月前
Logo

旨在为数千万中国开发者提供一个无缝且高效的云端环境,以支持学习、使用和贡献开源项目。

更多推荐