zoukankan      html  css  js  c++  java
  • 在element table中导出指定列信息

    问题:

      这是今年在项目中遇到的一个需求,并且之前有个博客园的伙伴也问到过,当时很忙,没仔细去思考过,现在工作轻松一点了,写个总结,当是一个小笔记吧

    思路及原理:

      之前的导出我们在页面中设置了两个el-table标签,table1用来展示数据,另外一个table2负责导出数据(隐藏)。要导出指定的列,我们可以做的地方就在于控制隐藏的table2的列是否存在,这里我们使用v-if来控制,因为v-show仅仅是把元素的display属性设置为none,列依然存在,导出的时候还是导出全部列数据,所以使用v-if

    效果展示:

    这是表格显示的数据,有很多列的内容,下面先导出全都内容

    导出指定列数据:这里我随便勾选四个列导出

    基本的效果就是上面这样的了,全部数据那里的涂黑的部分是一些信息数据,隐藏一些不影响啥的,下面就直接放代码了。

    1、安装插件并引入

    import FileSaver from 'file-saver'
    import XLSX from 'xlsx'
    

    2、因为使用的地方比较多,所以我将导出功能封装成一个组件,方便引用,代码如下

    HTML部分:

    <div class="excel-export-page">
        <el-table v-show="false" id="exportTable" border height="300" :data="tableData">
          <template v-for="(item, index) in exportFeild.tableCol">
            <el-table-column
              v-if="item.checked"
              :key="index"
              :property="item.property"
              :label="item.colName"
            />
          </template>
        </el-table>
        <div class="export-dialog">
          <div style="display: flex;justify-content: space-between;align-items: center;">
            <span>页码</span>
            <div style="display: flex;align-items: center;">
              <div>
                <el-input v-model="pageStart" style=" 80px;" @change="pagesChange" />
              </div>
              <!-- ~
              <div>
                <el-input v-model="pageEnd" style=" 50px;" />
              </div> -->
              <span style="padding: 0 20px;">所有页</span>
              <el-checkbox v-model="getMore" @change="exprotAll" />
            </div>
          </div>
          <div style="color: blue;">联机下载最大记录数为1000
            <span style="color: red;">(导出最大量数据请在空闲时操作)</span>
          </div>
          <div class="export-clomon-choice">
            <div v-for="(item, index) in exportFeild.tableCol" :key="index" class="export-row-style">
              <el-checkbox v-model="item.checked">{{ item.colName }}</el-checkbox>
            </div>
          </div>
          <div class="export-btn-style">
            <el-button type="primary" size="mini" icon="el-icon-download" @click="getExportDt">导出</el-button>
          </div>
        </div>
      </div>

    CSS部分:

    <style lang="scss" scoped>
    .excel-export-page {
       100%;
      padding: 20px;
    }
    .export-dialog {
       100%;
    }
    .export-clomon-choice {
      height: 150px;
      border: 1px solid #AECAF0;
      overflow-y: scroll;
      margin-top: 2px;
      .export-row-style {
        border-top: 1px solid #ededed;
        padding-left: 10px;
      }
    }
    .export-btn-style {
      padding: 10px;
      display: flex;
      justify-content: center;
    }
    </style>
    

    JS部分:

    <script>
      import { postRequest } from '@/api/httpRequest.js'
      import FileSaver from 'file-saver'
      import XLSX from 'xlsx'
      import Vue from 'vue'
      export default {
        props: {
          exportFeild: {
            type: Object,
            default() {
              return {}
            }
          }
        },
        data() {
          return {
            dict: Vue.filter('dict'), // 获取到全局字典过滤器方法
            tableData: [],
            getMore: false,
            pageStart: 1,
            maxPage: 0
          }
        },
        watch: {
          'exportFeild.currentPage': {
            handler: function(newVal, oldVal) {
              this.pageStart = newVal
            },
            deep: true
          }
        },
        mounted() {
          this.pageStart = this.exportFeild.currentPage
        },
        methods: {
          // 是否导出最大量
          exprotAll(val) {
            if (val) {
              this.pageStart = 1
            } else {
              this.pageStart = parseInt(this.exportFeild.qryParams.nextPage)
            }
          },
          // 页码输入改变事件
          pagesChange(val) {
            if (this.getMore) {
              const totalPg = Math.ceil(this.exportFeild.total / 1000)
              if (this.pageStart > totalPg) {
                this.pageStart = totalPg
              }
            } else {
              const totals = Math.ceil(this.exportFeild.total / this.exportFeild.pageSize)
              if (this.pageStart > totals) {
                this.pageStart = totals
              }
            }
          },
          // 导出数据到Excel表
          exportExcel(id) {
            /* generate workbook object from table */
            var xlsxParam = { raw: true } // 导出的内容只做解析,不进行格式转换
            var wb = XLSX.utils.table_to_book(document.querySelector(id), xlsxParam)
     
            /* get binary string as output */
            var wbout = XLSX.write(wb, { bookType: 'xlsx', bookSST: true, type: 'array' })
            try {
              FileSaver.saveAs(new Blob([wbout], { type: 'application/octet-stream' }), this.exportFeild.exportFileName)
            } catch (e) {
              if (typeof console !== 'undefined') {
                console.log(e, wbout)
              }
            }
            return wbout
          },
          // 获取导出的数据,与展示的表格数据不一定是一致的
          getExportDt() {
            if (!this.getMore) {
              // 如果不是导出全部,则页码跟每页条数跟列表页一致
              this.exportFeild.qryParams.nextPage = String(this.pageStart)
              this.exportFeild.qryParams.everyPage = String(this.exportFeild.pageSize)
            } else {
              // 导出全部数据,可输入页码,让用户可选
              this.exportFeild.qryParams.nextPage = String(this.pageStart)
              this.exportFeild.qryParams.everyPage = '1000'
            }
            // 这里是我们是获取表格数据的请求方法,根据自己的项目请求方法切换一下就行
            postRequest(this.exportFeild.qryParams, this.exportFeild.ck).then(response => {
              if (response.rspCode === '0000') {
                if (response.body.resultList) {
                  this.tableData = response.body.resultList
                  this.exportFeild.tableCol.forEach(item => {
                    if (item.dictionaryFlag) {
                      this.tableData.forEach(item2 => {
                        const feildAttr = item.property.includes('.')
                        if (!feildAttr) {
                          item2[item.property] = this.dict(item2[item.property], item.dictionaryStr)
                        } else {
                          // 如果字段是drftInf.drftAttr这样的,这样进行赋值
                          const part1 = item.property.split('.')[0]
                          const part2 = item.property.split('.')[1]
                          item2[part1][part2] = this.dict(item2[part1][part2], item.dictionaryStr)
                        }
                        // item2[item.property] = this.dict(item2[item.property], item.dictionaryStr)
                      })
                    }
                  })
                  setTimeout(() => {
                    this.exportExcel('#exportTable')
                  }, 500)
                }
              } else {
                this.tableData = []
                this.$message({
                  type: 'error',
                  message: response.rspMsg
                })
              }
            }).catch(() => {})
          }
        }
      }
    </script>

    在指定页面引入导出组件:

    <el-dialog
            :visible.sync="exportDialog"
            width="500px"
            title="XLSX导出"
            @close="exportDialog=false"
          >
            <excel-page :export-feild="exportFeild" />
    </el-dialog>
    
    import excelPage from '@/views/common/print/excel-export/index.vue'
    
    components: { excelPage },
    data() {
      return {
        exportFeild: {} // 传入到组件的对象
      }
    },
    method: {
          // 导出到Excel,列表页导出按钮事件:
          printPDF() {
            if (this.tableData.length > 0) {
              this.exportDialog = true
              this.exportFeild = {
                currentPage: this.currentPage,
                pageSize: this.pageSize,
                total: this.total,
                tableCol: [
                  { checked: true, colName: '业务编号', property: 'contNo' }, // 这里设置checked为true是默认勾选状态
                  { checked: true, colName: '票据号码', property: 'drftNo' },
                  { checked: true, colName: '票据来源', property: 'srcTyp', dictionaryFlag: true, dictionaryStr: 'srcTyp' },
                  { checked: true, colName: '票据属性', property: 'drftAttr', dictionaryFlag: true, dictionaryStr: 'drftAttr' },
                  { checked: true, colName: '票据种类', property: 'drftTyp', dictionaryFlag: true, dictionaryStr: 'drftTyp' },
                  { checked: true, colName: '票据状态', property: 'drftStat', dictionaryFlag: true, dictionaryStr: 'drftStat' },
                  { checked: true, colName: '票面金额(元)', property: 'isseAmt' },
                  { checked: true, colName: '出票日', property: 'isseDt' },
                  { checked: true, colName: '到期日', property: 'dueDt' },
                  { checked: true, colName: '承兑人名称', property: 'accptrNm' },
                  { checked: true, colName: '出票人名称', property: 'drwrNm' },
                  { checked: true, colName: '出票人开户行名称', property: 'drwrBkNm' },
                  { checked: true, colName: '收款人开户行名称', property: 'pyeeBkNm' },
                  { checked: true, colName: '所属机构', property: 'orgId' },
                  { checked: true, colName: '交易对手', property: 'custName' },
                  { checked: true, colName: '经办人', property: 'jbStf' },
                  { checked: true, colName: '交易日期', property: 'txnDt' }
                ],
                qryParams: this.qryParams,
                ck: 'CXGZCX001',
                exportFileName: '票据交易查询.xlsx'
              }
            } else {
              this.$alert('暂无数据', '提示', {
                confirmButtonText: '确定',
                confirmButtonClass: 'ticket-comfirm-btn',
                callback: () => {}
              })
            }
          }     
    }
    

    最后组件引入这里的代码我就丢在一个框里展示了,偷懒一下

    总结:其实思路的才是重点,之前小伙伴问怎么做导出指定列内容的时候一时间没想到,还特意去搜了下有没有特定的插件可以处理,没找到,后面工作遇到了,仔细想想原理,然后一边修改一边测就出来了,所以写出来当个笔记,也许会帮助到遇到导出指定内容问题的其他小伙伴,当是一个思路上的提示吧。

  • 相关阅读:
    AngularJS使用angular-formly进行表单验证
    AngularJS使用ngMessages进行表单验证
    AngularJS订阅API服务
    AngularJS中module的导入导出
    Gulp快速入门
    AngularJS过滤排序思路
    AngularJS表单验证,手动验证或自动验证
    AngularJS的增删改查、state嵌套案例,不涉及服务端
    前端使用AngularJS的$resource,后端ASP.NET Web API,实现分页、过滤
    前端使用AngularJS的$resource,后端ASP.NET Web API,实现增删改查
  • 原文地址:https://www.cnblogs.com/secretAngel/p/14204388.html
Copyright © 2011-2022 走看看