图片上传前获得预览图,并校验图片尺寸和宽高

图片上传前获得预览图,校验图片尺寸和宽高

实时预览demo

html中表单元素input[type=file]本身不提供图片预览效果,只能显示当前选择的文件名,需要查看预览效果的话没有API提供支持。某些特殊环境需要对上传图片的宽高有特定需求,需要严格把控,不符合规定不能上传。
出于安全考虑,前端是不能直接获取并显示需要上传的文件的,只能另辟蹊径,还好H5提供了文件系统,在处理这些问题时提供了很大支持,可以将本地文件先转化为base64文件格式,然后再展示到页面,就达到了预览的效果,但是万恶的IE9及其以下不识别H5的文件系统,好吧,只能用滤镜来做了。

上传图片预览

使用H5的FileReader方法处理本地上传文件为base64文件格式,然后将其绑定到预览图片标签img的src属性即可达到预览效果

兼容性(firefox3.6+ chrome6+ Safari5.2+ Opera11+及IE10浏览器支持FileReader对象)

上传图片宽高限制

获取上传图片宽高的策略:既然获取不到,那就索性创建一个img对象,然后把src指向上传图片,那么不就可以获取了吗?

但是万恶的IE又出问题了,本来new Image()后,获取新创建的图片对象onload()方法不去触发,浏览了很多博客都说是缓存机制造成的,src设置放在onload事件之后就可以解决,然而并没有效果,依旧是不会触发。
经过多次尝试后发现,不是不能触发onload事件,而是无法识别本地图片的链接,相当于只是创建了一个img标签,当然无法触发onload事件了,有些小伙伴获取的宽高都为0也就正常了。
因此我建议IE9以下版本的图片验证可以等上传成功后获取返回图片链接去判断,再去做处理。

注:获取图片宽度前必须先onload(),还有onload事件是异步的

1
2
<input id="browse" type="file" multiple>
<div id="preview"></div>

let’s also use a CSS to keep the resulting images a reasonable height:

1
#preview img{ height:100px; }

JavaScript:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
window.URL = window.URL || window.webkitURL;
var elBrowse = document.getElementById("browse"),
elPreview = document.getElementById("preview"),
useBlob = false && window.URL; // Set to `true` to use Blob instead of Data-URL
// 2.
function readImage (file) {
// Create a new FileReader instance
// https://developer.mozilla.org/en/docs/Web/API/FileReader
var reader = new FileReader();
// Once a file is successfully readed:
reader.addEventListener("load", function () {
// At this point `reader.result` contains already the Base64 Data-URL
// and we've could immediately show an image using
// `elPreview.insertAdjacentHTML("beforeend", "<img src='"+ reader.result +"'>");`
// But we want to get that image's width and height px values!
// Since the File Object does not hold the size of an image
// we need to create a new image and assign it's src, so when
// the image is loaded we can calculate it's width and height:
var image = new Image();
image.addEventListener("load", function () {
// Concatenate our HTML image info
var imageInfo = file.name +' '+ // get the value of `name` from the `file` Obj
image.width +'×'+ // But get the width from our `image`
image.height +' '+
file.type +' '+
Math.round(file.size/1024) +'KB';
// Finally append our created image and the HTML info string to our `#preview`
elPreview.appendChild( this );
elPreview.insertAdjacentHTML("beforeend", imageInfo +'<br>');
// If we set the variable `useBlob` to true:
// (Data-URLs can end up being really large
// `src="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAADAAAAA...........etc`
// Blobs are usually faster and the image src will hold a shorter blob name
// src="blob:http%3A//example.com/2a303acf-c34c-4d0a-85d4-2136eef7d723"
if (useBlob) {
// Free some memory for optimal performance
window.URL.revokeObjectURL(image.src);
}
});
image.src = useBlob ? window.URL.createObjectURL(file) : reader.result;
});
// https://developer.mozilla.org/en-US/docs/Web/API/FileReader/readAsDataURL
reader.readAsDataURL(file);
}
// 1.
// Once the user selects all the files to upload
// that will trigger a `change` event on the `#browse` input
elBrowse.addEventListener("change", function() {
// Let's store the FileList Array into a variable:
// https://developer.mozilla.org/en-US/docs/Web/API/FileList
var files = this.files;
// Let's create an empty `errors` String to collect eventual errors into:
var errors = "";
if (!files) {
errors += "File upload not supported by your browser.";
}
// Check for `files` (FileList) support and if contains at least one file:
if (files && files[0]) {
// Iterate over every File object in the FileList array
for(var i=0; i<files.length; i++) {
// Let's refer to the current File as a `file` variable
// https://developer.mozilla.org/en-US/docs/Web/API/File
var file = files[i];
// Test the `file.name` for a valid image extension:
// (pipe `|` delimit more image extensions)
// The regex can also be expressed like: /\.(png|jpe?g|gif)$/i
if ( (/\.(png|jpeg|jpg|gif)$/i).test(file.name) ) {
// SUCCESS! It's an image!
// Send our image `file` to our `readImage` function!
readImage( file );
} else {
errors += file.name +" Unsupported Image extension\n";
}
}
}
// Notify the user for any errors (i.e: try uploading a .txt file)
if (errors) {
alert(errors);
}
});
坚持原创技术分享,您的支持将鼓励我继续创作!