ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

从0-1超详细教你实现前端读取excel表格并渲染到界面

2022-01-25 23:35:11  阅读:179  来源: 互联网

标签:files xlsx const 读取 表格 excel headers excellist


@

目录

  • 本文旨在解决无需调用后端接口,实现前端读取表格文件,获取文件内容,渲染到界面的需求
  • 我的其他文章可以解决扩展需求:
  • 读取解析表格后执行自动单元格合并
  • 读取解析表格后根据数据对比分析自动设置单元格颜色
  • 读取解析表格后执行数据分析(透析)生成可满足用户自定义需求的echarts关系图
  • 下载界面表格功能

说明

公司平时做后台管理系统比较多,类似需求更是十分常见,我也写过类似帖子,但是都是只放代码从来不写注释和步骤,嘿嘿,话不多说,此文章为完整的记录:

前提

平时我经常使用的是:
Ant Design + Angular
Element UI + Vue
Ant Design + Vue
方便起见,今天我们使用Element UI + Vue
基于vue-element-admin直接开始

代码仓库

1.码云地址
2.github地址

步骤一:准备工作

  1. 点击进入vue-element-admin下载
    在这里插入图片描述
  2. 下载解压在这里插入图片描述
  3. 安装依赖、运行在这里插入图片描述
    在这里插入图片描述在这里插入图片描述
  4. 运行成功在这里插入图片描述
    在这里插入图片描述

步骤二:实现导入表格解析

  1. 进入以下路径;

src\views\dashboard\index.vue

  1. 删除无用代码,准备开始;
<template>
 <div class="dashboard-container">
   
 </div>
</template>

<script>
export default {
 name: 'Dashboard'
}
</script>

<style lang="scss" scoped>

</style>

在这里插入图片描述

  1. 增加 导入 按钮,保存刷新;
<template>
  <div class="dashboard-container">
    <!-- 导入按钮 -->
    <div class="button_group">
      <a
        href="javascript:;"
        class="button_s my_file el-button button_s el-button--primary el-button--small"
      >
        <input type="file" class="my_input" @change="importExcel" id="upload" />导入
      </a>
    </div>
    <!-- 导入按钮 -->
  </div>
</template>

<script>
export default {
  name: 'Dashboard',
  methods: {
    /**
     * 导入表格
     */
     importExcel(e) {
      
    }
  }
}
</script>

<style lang="scss" scoped>
// 按钮样式
.button_group {
  .button_s {
    width: 78px;
    margin: 5px 10px 5px 5px;
  }
  .button_m {
    width: 100px;
    margin: 5px 10px 5px 5px;
  }
  .my_file {
    position: relative;
    .my_input {
      position: absolute;
      opacity: 0;
      width: 78px;
      height: 30px;
      top: 0;
      left: 0;
    }
  }
}
// 按钮样式
</style>

在这里插入图片描述

  1. 下载xlsx 、引入;在这里插入图片描述
    在这里插入图片描述

  2. 编写导入表格 功能、保存刷新;

<script>
import xlsx from "xlsx";
export default {
  name: 'Dashboard',
  methods: {
    /**
     * 导入表格
     */
     importExcel(e) {
      const files = e.target.files;
      console.log(files);
      if (!files.length) {
        return ;
      } else if (!/\.(xls|xlsx)$/.test(files[0].name.toLowerCase())) {
        return alert("上传格式不正确,请上传xls或者xlsx格式");
      }
      const fileReader = new FileReader();
      fileReader.onload = ev => {
        try {
          const data = ev.target.result;
          const XLSX = xlsx;
          const workbook = XLSX.read(data, {
            type: "binary"
          });
          const wsname = workbook.SheetNames[0]; //取第一张表,wb.SheetNames[0]是获取Sheets中第一个Sheet的名字
          const ws = XLSX.utils.sheet_to_json(workbook.Sheets[wsname]); //生成json表格内容,wb.Sheets[Sheet名]获取第一个Sheet的数据
          const excellist = []; //清空接收数据
          //编辑数据
          for (var i = 0; i < ws.length; i++) {
            excellist.push(ws[i]);
          }
          console.log("读取结果", excellist); // 此时得到的是一个内容是对象的数组需要处理
        } catch (e) {
          return alert("读取失败!");;
        }
      };
      fileReader.readAsBinaryString(files[0]);
      var input = document.getElementById("upload");
      input.value = "";
    }
  }
}
</script>
  1. 编写如下表格,用来测试功能在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述

  2. 有时候,表格题目是中文,读取后我们想要得到英文属性名,那么 增加如下代码 、再次测试;

<script>
import xlsx from "xlsx";
export default {
  name: 'Dashboard',
  methods: {
    getHeader(sheet) {
      const XLSX = xlsx;
      const headers = [];
      const range = XLSX.utils.decode_range(sheet["!ref"]); // worksheet['!ref'] 是工作表的有效范围
      let C;
      /* 获取单元格值 start in the first row */
      const R = range.s.r; // 行 // C 列
      let i = 0;
      for (C = range.s.c; C <= range.e.c; ++C) {
        var cell =
          sheet[
            XLSX.utils.encode_cell({ c: C, r: R })
          ]; /* 根据地址得到单元格的值find the cell in the first row */
        var hdr = "UNKNOWN" + C; // 如果有空表头,会替换为您想要的默认值replace with your desired default
        // XLSX.utils.format_cell 生成单元格文本值
        if (cell && cell.t) hdr = XLSX.utils.format_cell(cell);
        if(hdr.indexOf('UNKNOWN') > -1){
          if(!i) {
            hdr = '__EMPTY';
          }else {
            hdr = '__EMPTY_' + i;
          }
          i++;
        }
        headers.push(hdr);
      }
      return headers;
    },
    /**
     * 导入表格
     */
     importExcel(e) {
      const files = e.target.files;
      console.log(files);
      if (!files.length) {
        return ;
      } else if (!/\.(xls|xlsx)$/.test(files[0].name.toLowerCase())) {
        return alert("上传格式不正确,请上传xls或者xlsx格式");
      }
      const fileReader = new FileReader();
      fileReader.onload = ev => {
        try {
          const data = ev.target.result;
          const XLSX = xlsx;
          const workbook = XLSX.read(data, {
            type: "binary"
          });
          const wsname = workbook.SheetNames[0]; //取第一张表,wb.SheetNames[0]是获取Sheets中第一个Sheet的名字
          const ws = XLSX.utils.sheet_to_json(workbook.Sheets[wsname]); //生成json表格内容,wb.Sheets[Sheet名]获取第一个Sheet的数据
          const excellist = []; //清空接收数据
          //编辑数据
          for (var i = 0; i < ws.length; i++) {
            excellist.push(ws[i]);
          }
          console.log("读取结果", excellist); // 此时得到的是一个内容是对象的数组需要处理
          // 获取表头2-1
          const a = workbook.Sheets[workbook.SheetNames[0]];
          const headers = this.getHeader(a);
          console.log('headers', headers);
          // 获取表头2-2
        } catch (e) {
          return alert("读取失败!");;
        }
      };
      fileReader.readAsBinaryString(files[0]);
      var input = document.getElementById("upload");
      input.value = "";
    }
  }
}
</script>

我们把表格改成不规则状态、保存、打开界面测试
在这里插入图片描述
在这里插入图片描述

步骤三:实现表格渲染

  1. 界面增加 表格组件
<!-- 表格组件 -->
    <div class="myTable">
      <el-table
        max-height="600"
        :data="dataArr"
        v-loading="tableLoading"
        :span-method="objectSpanMethod"
        border
        style="width: 100%"
      >
        <el-table-column
          :prop="item.prop"
          :label="item.label"
          :width="item.width"
          v-for="(item, i) in tableColumn"
          :key="i"
        ></el-table-column>
      </el-table>
    </div>
    <!-- 表格组件 -->
data() {
    return {
      dataArr: [], // 表格内容数据数组
      // countArr: {}, // 分析表格数据以及表头,得到一个对照数组,用来进行自定义合并,本文暂时只写基础,不介绍自动合并单元格了哟~~我的其他文章有写自定义合并实现方法~
      tableColumn: [], // 表格表头配置数组
      tableLoading: false // 表格是否loading
    };
  },

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
2. 增加 表格渲染方法

备注:表格渲染方法中有一部分代码是用来映射中英文属性名的,这个是我增加的一个功能,有时候也不不需要使用,可以按自己需求来修改代码;

setTable(headers, excellist) {
      const tableTitleData = []; // 存储表格表头数据
      const tableMapTitle = {}; // 设置表格内容中英文对照用
      headers.forEach((_, i) => {
        tableMapTitle[_] = "prop" + i;
        tableTitleData.push({
          prop: "prop" + i,
          label: _,
          width: 100
        });
      });
      console.log("tableTitleData", tableTitleData);
      // 映射表格内容属性名为英文
      const newTableData = [];
      excellist.forEach(_ => {
        const newObj = {};
        Object.keys(_).forEach(key => {
          newObj[tableMapTitle[key]] = _[key];
        });
        newTableData.push(newObj);
      });
      console.log('newTableData',newTableData);
      this.tableColumn = tableTitleData;
      this.dataArr = newTableData;
    },

在这里插入图片描述

  1. 调用 表格渲染方法
		// 在importExcel(e)方法中添加下面代码
          // 渲染表格1-1
          this.setTable(headers, excellist);
          // 渲染表格1-2

在这里插入图片描述

  1. 功能测试在这里插入图片描述
    在这里插入图片描述

结语

本代码支持不规则数据,没有表头的也可以渲染到界面哦~~
欢迎大家指出我代码的错误~
如果有更好的写法,欢迎大家提出来,共同进步哟~~

标签:files,xlsx,const,读取,表格,excel,headers,excellist
来源: https://www.cnblogs.com/sugartang/p/15845019.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有