美文网首页
xlsx 写文件

xlsx 写文件

作者: 陈海辉 | 来源:发表于2020-08-24 20:53 被阅读0次
// data
const data = [
  {
    id: 1,
    合并的列头1: '数据11',
    合并的列头2: '数据12',
    _style: { font: { sz: 14, bold: true, color: { rgb: 'FFFFAA00' } } },
    _merges: [{ s: { c: 1, r: 0 }, e: { c: 4, r: 0 } }],
  },
]
const utils = {
  writeFile(data, { tableName = 'sheet1', fileName = '下载', type = 'xlsx', title, head } = {}) {
    const bookType = { xlsx: 'xlsx', xls: 'biff8' }
    // 处理数据
    const tmpdata = this.dataHandle(data, title, head)
    // 设置区域 比如表格从A1到D10
    const outputPos = Object.keys(tmpdata)
    // tmpdata['B1'].s =  // 单元格样式
    // tmpdata['!merges'] = [{ s: { c: 1, r: 0 }, e: { c: 4, r: 0 } }] // 合并单元格

    const wb = {
      SheetNames: [tableName], //保存的表标题
      Sheets: {
        [tableName]: {
          ...tmpdata, // 数据
          '!ref': outputPos[0] + ':' + outputPos[outputPos.length - 1], // 设置填充区域
        },
      },
    }

    const xlsxDataStr = XLSX.write(wb, { ...this.wopts, bookType: bookType[type] })
    const bolb = new Blob([this.str2Buffer(xlsxDataStr)])

    this.saveAs(bolb, `${fileName}.${type}`)
  },
  // 浏览器下载
  saveAs(data, fileName) {
    const tmpa = document.createElement('a')
    tmpa.download = fileName
    tmpa.href = URL.createObjectURL(data)
    tmpa.click()
    setTimeout(function() {
      URL.revokeObjectURL(data)
    }, 100)
  },
  // 处理数据 ==> { A1: {v:1}, A2: {v:2} }
  dataHandle(head = [], title = [], data = []) {
    const tmpdata = {}
    ;[...head, ...title, ...data].forEach((item, index) => {
      const row = index + 1
      const { _style, _merges, ...other } = item
      Object.values(other).forEach((i, ind) => {
        const col = this.transNum2Char(ind)
        const val = { v: i }
        if (_style) val.s = _style
        tmpdata[col + row] = val
      })
    })
    return tmpdata
  },
  // 保存格式
  wopts: { bookType: 'xlsx', bookSST: false, type: 'binary', cellStyles: true },
  // 0 > A,  26 > AA
  transNum2Char(num) {
    // 保存每一位的 unicode 码
    let arr = []
    // 679 % 26 % 26 % 26  ===> [3, 1, 0]
    while (num >= 26) {
      arr.push((num % 26) + 1) // 0-25 需转换成 1-26
      num = parseInt(num / 26)
    }
    arr.push(num + 1) // 0-25 需转换成 1-26
    return arr
      .reverse()
      .map((i) => String.fromCharCode(i + 64))
      .join('')
  },
  // 将字符串转换成 buffer
  str2Buffer(s) {
    const buf = new ArrayBuffer(s.length)
    const view = new Uint8Array(buf)
    for (var i = 0; i != s.length; ++i) view[i] = s.charCodeAt(i) & 0xff
    return buf
  },
}

相关文章

网友评论

      本文标题:xlsx 写文件

      本文链接:https://www.haomeiwen.com/subject/tylojktx.html