在html5中,DOM给文件中添加了一个files集合,在选取文件中,files中包含一个File对象,每一个对象都有下列属性:javascript
同时,使用FileReader对象,web应用程序能够异步的读取存储在用户计算机上的文件(或者原始数据缓冲)内容,可使用File对象或者Blob对象来指定所要处理的文件或数据。FileReader 提供了以下 几个方法。css
需求:若读取文件为图片,则以img展现出来,其余状况则以text的形式输出。html
<input type="file" id="files-list">
复制代码
reader = new FileReader();
if (/image/.test(files[0].type)) {
// 选择文件类型为图片
reader.readAsDataURL(files[0]);
type = "image";
} else {
// 其余文件类型,并指定编码类型
reader.readAsText(files[0], 'gb2312');
type = "text";
}
复制代码
reader.onload = function () {
var html = "";
switch (type) {
case "image":
html = "<img src=\"" + reader.result + "\">";
break;
case "text":
html = reader.result;
console.log(html);
break;
}
output.innerHTML = html;
};
复制代码
演示连接vue
读取图片html5
读取csv文件java
在利用readAsText进行读取的时候,要指定一下编码形式。如readAsText(files[0], 'gb2312');
复制代码
csv文件的特色: 每一行用换行符进行分隔,每一行的数据中每一项利用逗号分隔。
复制代码
上面已经能够将csv做为text进行输出了。下来继续拿取数据。git
利用上面所说的csv的特色就能够利用js进行循环遍历拿到每一项的数据。github
演示连接web
其中,我将CVS中的数据转化后,并拼在了table元素中:json
// 将读取的数据转化为table
function textToCsv(data) {
var allRows = data.split(/\n/);
var table = '<table>';
for (var singleRow = 0; singleRow < allRows.length - 1; singleRow++) {
if (singleRow === 0) {
table += '<thead>';
table += '<tr>';
} else {
table += '<tr>';
}
var rowCells = allRows[singleRow].split(',');
for (var rowCell = 0; rowCell < rowCells.length; rowCell++) {
if (singleRow === 0) {
// 表格的标题
table += '<th>';
table += rowCells[rowCell];
table += '</th>';
} else {
// 表格内容
table += '<td>';
table += rowCells[rowCell];
table += '</td>';
}
}
if (singleRow === 0) {
table += '</tr>';
table += '</thead>';
table += '<tbody>';
} else {
table += '</tr>';
}
}
table += '</tbody>';
table += '</table>';
console.log(table);
document.getElementById('table').innerHTML = table;
}
复制代码
效果图以下:
关于下载的操做,能够借助于a标签。先介绍下相关的属性:
上一个列子的下载就是用的上面的作法:
<a href="./file/会员.csv" download="demo.csv">下载测试文件</a>
复制代码
先准备数据 csv文件的头部数据:
var head = [
['姓名(最多10个字)', '手机号(必填)', '等级', '生日(好比:1989/08/08 或 1989-08-08)', '积分(限整数)']
];
复制代码
csv文件的主体数据:
var people = [{
"name": "吴三桂",
"phone": "18709237410",
"level": "黄金",
"birthday": "1989/8/5",
"points": "100"
}, {
"name": "史泰龙",
"phone": "18709237401",
"level": "青铜2",
"birthday": "1993/9/6",
"points": "300"
}, {
"name": "阿超",
"phone": "18883920287",
"level": "白金",
"birthday": "1993/9/3",
"points": "500"
}];
复制代码
下来就是数据的格式转换:
//. 将数据push到大数组中
var p = people;
for (var i = 0; i < p.length; i++) {
head.push([p[i].name, p[i].phone, p[i].level, p[i].birthday, p[i].points]);
}
// 按照csv文件内容格式,把每一个数组用 , 链接,造成一行,并存入新数组
var csvRows = [];
for (var j = 0; j < head.length; j++) {
csvRows.push(head[j].join(','))
}
//s4. 把新数组用 \n 回车链接
var csvString = csvRows.join('\n');
复制代码
最后实现下载:
//利用a标签实现下载
function saveAs(obj, fileName) {
var tmpa = document.createElement("a");
tmpa.download = fileName || "下载.csv";
tmpa.href ='data:attachment/csv,' + encodeURI(obj); //绑定a标签
tmpa.click(); //模拟点击实现下载
setTimeout(function () { //延时释放
URL.revokeObjectURL(obj); //用URL.revokeObjectURL()来释放这个object URL
}, 100);
}
复制代码
演示连接
效果图
下面将使用js-xlsx对csv文件进行操做:
xlsx相关api:
在JavaScript中,有2个函数分别用来处理解码和编码base64 字符串:
步骤:
var wb;//读取完成的数据
//导入
function importf(obj) {
if (!obj.files) {
return;
}
var f = obj.files[0];
var reader = new FileReader();
reader.readAsArrayBuffer(f);
reader.onload = function (e) {
var data = e.target.result;
var wb =XLSX.read(btoa(fixedData(data)), { type: 'base64' });//将数据转化为二进制
//wb.SheetNames[0]是获取Sheets中第一个Sheet的名字
//wb.Sheets[Sheet名]获取第一个Sheet的数据
document.getElementById("excel").innerHTML = JSON.stringify(XLSX.utils.sheet_to_json(wb.Sheets[wb.SheetNames[0]]));
};
}
复制代码
//文件流转BinaryString
function fixedData(data) {
let o = ''
let l = 0
const w = 10240
for (; l < data.byteLength / w; ++l) o += String.fromCharCode.apply(null, new Uint8Array(data.slice(l * w,
l * w + w)))
o += String.fromCharCode.apply(null, new Uint8Array(data.slice(l * w)))
return o
}
复制代码
效果图预览:
附上一个vue-element-admin关于Excel文件读取的源码: 查看连接
这里依然会用到js-xlsx, 文件下载采用FileSaver.js
<button onclick="downloadExl(people)">导出</button>
复制代码
var people = [{
"name": "吴三桂",
"phone": "18709237410",
"level": "黄金",
"birthday": "1989/8/5",
"points": "100"
}, {
"name": "史泰龙",
"phone": "18709237401",
"level": "青铜2",
"birthday": "1993/9/6",
"points": "300"
}, {
"name": "阿超",
"phone": "18883920287",
"level": "白金",
"birthday": "1993/9/3",
"points": "500"
}];
复制代码
下来定义一个wb保存导出数据
var wb = {
SheetNames: ["Sheet1"], //标题名
Sheets: { } //保存表内的数据
}
复制代码
!ref: 表示表格输出的范围
A1-Zx: 这些就对应的是Excel中单元格的位置;
其中:Sheet1相关参数介绍:
键名 | 值 |
---|---|
v | 原始值 |
t | b布尔值,e错误,n数字,d日期,s文本 |
更多属性请参照: 官方文档
const wopts = { bookType: 'xlsx', bookSST: false,type: 'binary' };
//这里的数据是用来定义导出的格式类型
// const wopts = { bookType: 'csv', bookSST: false, type: 'binary' };//ods格式
// const wopts = { bookType: 'ods', bookSST: false, type: 'binary' };//ods格式
// const wopts = { bookType: 'xlsb', bookSST: false, type: 'binary' };//xlsb格式
// const wopts = { bookType: 'fods', bookSST: false, type: 'binary' };//fods格式
// const wopts = { bookType: 'biff2', bookSST: false, type: 'binary' };//xls格式
复制代码
// 将指定的天然数转换为26进制表示。映射关系:[0-25] -> [A-Z]。
function getCharCol(n) {
var temCol = '',
s = '',
m = 0
while (n >= 0) {
m = n % 26 + 1
s = String.fromCharCode(m + 64) + s
n = (n - m) / 26
}
return s
};
["ID","手机号","等级" ,"生日","积分"].forEach((v,i)=>{data[getCharCol(i)+1] = { t: "s", v: v ,w:v};})
复制代码
利用XLSX.write(wb, wopts);
wb: 二进制数据流
wopts: 指定的导出格式等信息
下载保存此次不采用a标签的方式。采用FileSaver.js
saveAs(new Blob([s2ab(XLSX.write(wb, wopts))], {type: "application/octet-stream"}), "js-xlsx文件下载实例" + '.' + wopts.bookType);
复制代码
新人首次发帖,,你们勿喷!!!
参考文章: