概述
在我们做用户注册的时候经常会设计到用户头像之类的上传,这时我们会用到一个<input type="file">标签,但是我们该怎样获取标签中选取的图片呢?
这里我们使用HTML5中的FileReader接口来实现这样的操作。
demo
我用如下代码来讲述该怎样实现这样的操作:
HTML代码:
<form id="imgForm">
<input type="file" class="addBorder">
<br/>
<button type="button" οnclick="loadImg()">获取图片</button>
</form>
<div class="addBorder" id="imgDiv">
<img id="imgContent">
</div>
首先,肯定会有一个<form>已经<input>,form写不写action和method无所谓,因为既然我们要用JS/JQ来获取<input>表单的文件,那多半是要用到ajax来传输数据了。闲话不多说,先搞定获取图片的问题,再考虑接下来的。
CSS代码:
.addBorder{
border:1px solid #ccc;
}
#imgDiv{
width:100px;
height:100px;
}
#imgContent{
width: 100%;
height:100%;
}
这里CSS代码不过多赘述,只是简单地给元素一些样式。
JS代码:
function loadImg(){
//获取文件
var file = $("#imgForm").find("input")[0].files[0];
//创建读取文件的对象
var reader = new FileReader();
//创建文件读取相关的变量
var imgFile;
//为文件读取成功设置事件
reader.οnlοad=function(e) {
alert('文件读取完成');
imgFile = e.target.result;
console.log(imgFile);
$("#imgContent").attr('src', imgFile);
};
//正式读取文件
reader.readAsDataURL(file);
}
上面JS代码中,是为<button>的click事件所触发。首先一步,我们肯定要获取到对应表单(这里我用的是JQ,用JS也可),为什么说用JS也可以,注意我的文件获取,$("#imgForm").find("input")到这里这都还是一个jQuery对象,但是之后我们跟了一个[0],即$("#imgForm").find("input")[0]就已经是一个HTML对象。
接着,我们创建了一个FileReader对象,命名为reader。还声明了一个imgFile变量,这个变量主要用于存储读取文件之后所生成的对应文件的base64码。
之后这段reader.οnlοad=function(e){}是为读取文件绑定一个onload事件,类似于我们给HTML标签绑定onclick事件,当特定条件达到时,就调用该方法。
最后的,也是最重要的,就是开始读取文件了。用reader.readAsDataURL(file),根据大家编程经验也都能看出,就是调用FileReader类中的readAsDataURL方法,并把之前获取的file对象传进去。如果读取成功,则调用reader.onload事件。
这里,我还把读取结果输入到了控制台中,如下图控制台输出的base64码(部分)为:
光是一个图片就有这么多数据,具体我没研究过,不过我知道的就是图片越大,数据量也就越大。但是所有图片前一段都是类似的。如上图红色标注部分,都是“data:image/jpeg;base64,”,之后就是图片的正文内容。这个正文内容有什么用呢?我们可以把这些数据用base64编码格式写入对应图片格式的文件中,你会发现,图像出来了。一半我上传图片的方法就是获取图片的base64码,然后传给服务器,服务器再对应地生成一个后缀名一样的文件,并用base64编码写入这些数据,服务器端就已经生成了相同的图片,然后把图片地址保存到数据库中。(虽然说可以直接把这些数据存入数据库中,不过你可以想象一下,数据库中一个字段存这么多数据会是多么壮观的事情)。
注意事项
1.若想预览该图片,可以像demo中一样,直接把读取的文件的所有数据,包括数据头(就是控制台输出的所有数据,包括“data:image/jpeg;base64,”和后面的所有内容)一起写入一个<img>标签的src中。这样就可以看到<img>显示对应的图像。
2.若想存入服务器端的文件中,需要把数据头(data:image/jpeg;base64,)去掉,并且根据“image/“之后的内容(如“jpeg、png……”)来判断图片文件的后缀,从而在服务器端生成对应后缀的文件,并写入除开数据头之外的所有数据。
这里,我先给出一部分base64码中文件格式以及对应应该生成什么后缀的文件:
base64 | 对应后缀 |
jpeg | jpg |
png | png |
gif | gif |
bmp | bmp |
4.有些浏览器可能不支持FileReader接口,目前我用的是chrome浏览器,亲测能够完美运行。
参考资料
这里我要引用下面我参考的资料中两个伟大的表格,进一步给大家讲一下FileReader接口的相关知识。
方法名 | 参数 | 描述 |
---|---|---|
readAsBinaryString | file | 将文件读取为二进制编码 |
readAsText | file,[encoding] | 将文件读取为文本 |
readAsDataURL | file | 将文件读取为DataURL |
abort | (none) | 终端读取操作 |
事件 | 描述 |
onabort | 中断 |
onerror | 出错 |
onloadstart | 开始 |
onprogress | 正在读取 |
onload | 成功读取 |
onloadend | 读取完成,无论成功失败 |
参考资料:《HTML5学习之FileReader接口》——
http://blog.csdn.net/zk437092645/article/details/8745647
写在最后
欢迎有人来提出文章中的问题,大家相互学习,共同进步。相关代码我会在接下来上传到CSDN的CODE中,大家可以去下载运行。