能,choose是唯一能获取原始File对象的回调,其obj.files为标准FileList,可直接用于预览、MD5计算、压缩等操作;before和done均无法访问。

layui upload 的 choose 回调里能拿到本地文件对象吗?
能,而且必须在这里拿——choose 是唯一能访问原始 File 对象的时机。上传还没发起,但用户已选中图片,此时用 URL.createObjectURL(file) 就能生成可预览的本地临时地址。
注意:before 和 done 都拿不到原始 File,前者只接收 obj(含 files 数组但不暴露原生对象),后者只收服务端返回数据;只有 choose 的参数 obj 里有 obj.files,且它是标准 FileList,可直接索引取 obj.files[0]。
- 别在
done里尝试用input[type=file]再读取,浏览器出于安全限制已清空其value - 预览图建议用
标签,设置src为URL.createObjectURL(file)即可 - 每次新选图前记得调用
URL.revokeObjectURL(oldSrc)避免内存泄漏(尤其多图场景)
怎么把预览图塞进 layui upload 的默认预览区?
layui upload 默认不提供缩略图容器,得自己加 DOM。推荐在绑定 upload 的容器内紧挨着 input 插入一个 ,然后在 choose 里操作这个 。
示例关键代码:
layui.use('upload', function(){
var upload = layui.upload;
upload.render({
elem: '#uploadBtn',
url: '/api/upload',
choose: function(obj){
var file = obj.files[0];
if(file && /image\/\w+/.test(file.type)){
var img = document.getElementById('preview-img');
// 清旧地址
if(img.src) URL.revokeObjectURL(img.src);
// 设新地址
img.src = URL.createObjectURL(file);
}
}
});
});
单图上传时要不要限制文件类型和大小?
要,而且得在 choose 里做——服务端校验是兜底,前端拦截能立刻反馈,避免无效上传。
- 类型判断:用
file.type匹配/^image\//,比后缀名可靠(用户可改后缀) - 大小判断:用
file.size > 2 * 1024 * 1024限制 2MB,超了直接layer.msg('图片不能超过 2MB')并 return - 注意:IE10+ 支持
File.type,但部分低版本安卓 WebView 可能返回空字符串,可 fallback 到file.name.split('.').pop().toLowerCase()做补充校验
预览图和实际上传的图尺寸/质量不一致怎么办?
预览图是原始文件缩放显示,跟上传内容无关;但如果你需要上传前压缩(比如大图转为 1200px 宽、80% 质量的 JPEG),那就得在 choose 后手动 canvas 绘制压缩,再用 canvas.toBlob() 生成新 File,最后替换 obj.files(需 hack,因 FileList 只读)或改用 FormData 手动提交。
这已超出 layui upload 默认流程,属于进阶需求。简单方案是:预览用原图,上传仍走 layui 默认逻辑;真要压缩,就放弃 url 配置,改用 auto: false + bindAction 自定义提交,自己构造 FormData。
容易被忽略的是:canvas 压缩后的 Blob 需用 new File([blob], filename, {type: 'image/jpeg'}) 包一层才能当图片传,否则后端可能解析失败。











