前两天有几个小伙伴找我问我关于js-xlsx导出时列头合并单元格的问题,因为小伙伴需要导出的效果都不太一样,所以我在这里对其解决思路简单的给讲一下,大家根据实际情况自行修改。
1.通过导入获取列头JSON数据
其实合并单元格我早在文章《纯前端利用 js-xlsx 之合并单元格(3)》中有讲到过可能当时将的比较简单所以这次我们讲下比较复杂的情况.。
首先我先创建一个xlsx文件里面只存放我的列头数据比如:
导入示例代码:
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title></title>
<script src="xlsx.core.min.js"></script>
</head>
<body>
<input type="file" onchange="importf(this)" />
<div id="demo"></div>
<script>
var WB;
var rABS = true; //是否将文件读取为二进制字符串
function importf(obj) {//导入
if (!obj.files) { return; }
var f = obj.files[0];
{
var reader = new FileReader();
var name = f.name;
reader.onload = function (e) {
var data = e.target.result;
WB = XLSX.read(data, { type: 'binary' });
document.getElementById("demo").innerHTML = JSON.stringify(WB.Sheets[WB.SheetNames[0]]);
};
if (rABS) reader.readAsBinaryString(f);
else reader.readAsArrayBuffer(f);
}
}
</script>
</body>
</html>
可以看到导出结果:
整理后我们得到关键数据:
{ "A1": { "v": "日期" }, "B1": { "v": "配送信息" }, "C1": { "v": "" }, "D1": { "v": "" }, "E1": { "v": "" }, "F1": { "v": "" }, "A2": { "v": "" }, "B2": { "v": "姓名" }, "C2": { "v": "地址" }, "D2": { "v": "" }, "E2": { "v": "" }, "F2": { "v": "" }, "A3": { "v": "" }, "B3": { "v": "" }, "C3": { "v": "省份" }, "D3": { "v": "市区" }, "E3": { "v": "地址" }, "F3": { "v": "邮编" }, "!merges": [{ "s": { "c": 1, "r": 0 }, "e": { "c": 5, "r": 0 } }, { "s": { "c": 2, "r": 1 }, "e": { "c": 5, "r": 1 } }, { "s": { "c": 0, "r": 0 }, "e": { "c": 0, "r": 2 } }, { "s": { "c": 1, "r": 1 }, "e": { "c": 1, "r": 2 } }] }
2.尝试导出列头
代码中的xlsx.utils.min.js相关示例可查看文章《js-xlsx工具类库 xlsxUtils 使用示例》
代码示例:
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title></title>
<script src="xlsx.core.min.js"></script>
<script src="xlsx.utils.min.js"></script>
<script>
function saveAs(obj, fileName) {//当然可以自定义简单的下载文件实现方式
var tmpa = document.createElement("a");
tmpa.download = fileName || "下载";
tmpa.href = URL.createObjectURL(obj); //绑定a标签
tmpa.click(); //模拟点击实现下载
setTimeout(function () { //延时释放
URL.revokeObjectURL(obj); //用URL.revokeObjectURL()来释放这个object URL
}, 100);
}
</script>
</head>
<body>
<input type="button" onclick="downloadExl()" value="导出" />
<div id="demo"></div>
<script>
var head = { "A1": { "v": "日期" }, "B1": { "v": "配送信息" }, "C1": { "v": "" }, "D1": { "v": "" }, "E1": { "v": "" }, "F1": { "v": "" }, "A2": { "v": "" }, "B2": { "v": "姓名" }, "C2": { "v": "地址" }, "D2": { "v": "" }, "E2": { "v": "" }, "F2": { "v": "" }, "A3": { "v": "" }, "B3": { "v": "" }, "C3": { "v": "省份" }, "D3": { "v": "市区" }, "E3": { "v": "地址" }, "F3": { "v": "邮编" }, "!merges": [{ "s": { "c": 1, "r": 0 }, "e": { "c": 5, "r": 0 } }, { "s": { "c": 2, "r": 1 }, "e": { "c": 5, "r": 1 } }, { "s": { "c": 0, "r": 0 }, "e": { "c": 0, "r": 2 } }, { "s": { "c": 1, "r": 1 }, "e": { "c": 1, "r": 2 } }] };
function downloadExl() {
var wb = xlsxUtils.format2WB(head, undefined, undefined, "A1:F3");
saveAs(xlsxUtils.format2Blob(wb), "这里是下载的文件名.xlsx");
}
</script>
</body>
</html>
成功导出的效果:
3.导出数据与自定义列头
一般情况下我们导出的JSON数据是这样的:
[{
"riqi": "2016/5/1",
"ming": "关爱单身狗",
"sheng": "上海",
"shi": "普陀区",
"dizhi": "上海市普陀区金沙江路 1518 弄",
"youbian": "200333"
}, {
"riqi": "2016/5/2",
"ming": "关爱单身狗",
"sheng": "上海",
"shi": "普陀区",
"dizhi": "上海市普陀区金沙江路 1518 弄",
"youbian": "200333"
}, {
"riqi": "2016/5/3",
"ming": "关爱单身狗",
"sheng": "上海",
"shi": "普陀区",
"dizhi": "上海市普陀区金沙江路 1518 弄",
"youbian": "200333"
}, {
"riqi": "2016/5/4",
"ming": "关爱单身狗",
"sheng": "上海",
"shi": "普陀区",
"dizhi": "上海市普陀区金沙江路 1518 弄",
"youbian": "200333"
}, {
"riqi": "2016/5/5",
"ming": "关爱单身狗",
"sheng": "上海",
"shi": "普陀区",
"dizhi": "上海市普陀区金沙江路 1518 弄",
"youbian": "200333"
}, {
"riqi": "2016/5/6",
"ming": "关爱单身狗",
"sheng": "上海",
"shi": "普陀区",
"dizhi": "上海市普陀区金沙江路 1518 弄",
"youbian": "200333"
}, {
"riqi": "2016/5/7",
"ming": "关爱单身狗",
"sheng": "上海",
"shi": "普陀区",
"dizhi": "上海市普陀区金沙江路 1518 弄",
"youbian": "200333"
}]
那好,只要将数据和列头的json数据进行整合导出就行了,不过注意一点就是因为列头数据跟导出数据列可能无法根据英文字段对应,所以我们需要手动声明顺序数组去匹配对应:
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title></title>
<script src="xlsx.core.min.js"></script>
<script src="xlsx.utils.min.js"></script>
<script>
function saveAs(obj, fileName) {//当然可以自定义简单的下载文件实现方式
var tmpa = document.createElement("a");
tmpa.download = fileName || "下载";
tmpa.href = URL.createObjectURL(obj); //绑定a标签
tmpa.click(); //模拟点击实现下载
setTimeout(function () { //延时释放
URL.revokeObjectURL(obj); //用URL.revokeObjectURL()来释放这个object URL
}, 100);
}
</script>
<script>
var Data = [{ "riqi": "2016/5/1", "ming": "关爱单身狗", "sheng": "上海", "shi": "普陀区", "dizhi": "上海市普陀区金沙江路 1518 弄", "youbian": "200333" }, { "riqi": "2016/5/2", "ming": "关爱单身狗", "sheng": "上海", "shi": "普陀区", "dizhi": "上海市普陀区金沙江路 1518 弄", "youbian": "200333" }, { "riqi": "2016/5/3", "ming": "关爱单身狗", "sheng": "上海", "shi": "普陀区", "dizhi": "上海市普陀区金沙江路 1518 弄", "youbian": "200333" }, { "riqi": "2016/5/4", "ming": "关爱单身狗", "sheng": "上海", "shi": "普陀区", "dizhi": "上海市普陀区金沙江路 1518 弄", "youbian": "200333" }, { "riqi": "2016/5/5", "ming": "关爱单身狗", "sheng": "上海", "shi": "普陀区", "dizhi": "上海市普陀区金沙江路 1518 弄", "youbian": "200333" }, { "riqi": "2016/5/6", "ming": "关爱单身狗", "sheng": "上海", "shi": "普陀区", "dizhi": "上海市普陀区金沙江路 1518 弄", "youbian": "200333" }, { "riqi": "2016/5/7", "ming": "关爱单身狗", "sheng": "上海", "shi": "普陀区", "dizhi": "上海市普陀区金沙江路 1518 弄", "youbian": "200333" }];
</script>
</head>
<body>
<input type="button" onclick="downloadExl()" value="导出" />
<script>
var head = { "A1": { "v": "日期" }, "B1": { "v": "配送信息" }, "C1": { "v": "" }, "D1": { "v": "" }, "E1": { "v": "" }, "F1": { "v": "" }, "A2": { "v": "" }, "B2": { "v": "姓名" }, "C2": { "v": "地址" }, "D2": { "v": "" }, "E2": { "v": "" }, "F2": { "v": "" }, "A3": { "v": "" }, "B3": { "v": "" }, "C3": { "v": "省份" }, "D3": { "v": "市区" }, "E3": { "v": "地址" }, "F3": { "v": "邮编" }, "!merges": [{ "s": { "c": 1, "r": 0 }, "e": { "c": 5, "r": 0 } }, { "s": { "c": 2, "r": 1 }, "e": { "c": 5, "r": 1 } }, { "s": { "c": 0, "r": 0 }, "e": { "c": 0, "r": 2 } }, { "s": { "c": 1, "r": 1 }, "e": { "c": 1, "r": 2 } }] };
var keyMap = ["riqi", "ming", "sheng", "shi", "dizhi", "youbian"];//通过设置数组让导出时可以按顺序显示
var wopts = { bookType: 'xlsx', bookSST: false, type: 'binary' };
function downloadExl() {
var data = xlsxUtils.format2Sheet(Data, 0, 3, keyMap);//偏移3行按keyMap顺序转换
var dataKeys = Object.keys(data);
for (var k in head) data[k] = head[k];//追加列头
var wb = xlsxUtils.format2WB(data, undefined, undefined, "A1:" + dataKeys[dataKeys.length - 1]);
saveAs(xlsxUtils.format2Blob(wb), "这里是下载的文件名.xlsx");
}
</script>
</body>
</html>
最终导出效果:
在线查看
大概思路就是这样的,如果大家有跟好的办法可以在文章下面评论区留言或交流。