一般我们上传文件都是用<input type="file">
标签来上传,但是这个UI太丑了,都得重新弄个标签写css来美化一下,现在出了一个新的API,可以直接用js就可以来获取文件上传了,下面我们来看一下showOpenFilePicker
-
showOpenFilePicker(options),写一段代码来看看怎么用,顺便写个预览图片的功能
html代码<button id="btn">点击选择图片</button>
js代码
let obtn=document.querySelector("#btn"); obtn.addEventListener("click",async ()=>{ const arrFileHandle = await window.showOpenFilePicker({ types: [{ accept: { 'image/*': ['.png', '.gif', '.jpeg', '.jpg', '.webp'] } }], // 可以选择多个图片 multiple: true }); //获取图片数据 这个file其实就是和input元素<input type="file" id="file">,document.querySelector("#file").files[0]一样 let file=await arrFileHandle[0].getFile(); //预览图片 previewImg(file); },false);
- 预览图片的第一种方式FileReader
function previewImg(file){ //转成base64 let read=new FileReader(); read.readAsDataURL(file); read.onload=(e)=>{ //创建img,插入页面中 let img=document.createElement("img"); img.src=read.result; obtn.appendChild(img); } }
- 预览图片的第二种方式createObjectURL
推荐使用第二种方式,因为createObjectURL有更好的性能,处理的更快let img=document.createElement("img"); //window.webkitURL.createObjectURL(file) 兼容chrome img.src=URL.createObjectURL(file); obtn.appendChild(img);
showOpenFilePicker(options)是可以传参数的,传的是一个对象{},其中支持下面这些属性:
- multiple: 布尔值,默认值是 false ,表示只能选择一个文件。
- excludeAcceptAllOption: 布尔值,默认值是 false ,表示是否排除下面 types 中的所有的accept文件类型。
-
types: 可选择的文件类型数组,每个数组项也是个对象,支持下面两个参数:
- description: 表示文件或者文件夹的描述,字符串,可选
- accept: 接受的文件类型,对象,然后对象的键是文件的MIME匹配,值是数组,表示支持的文件后缀。具体可以上面代码的示意。
- 预览图片的第一种方式FileReader
showDirectoryPicker和showOpenFilePicker用法差不多,直接看上面怎么用就行了,只不过showDirectoryPicker不用传参数
-
showSaveFilePicker,写一段代码看看怎么用,用input标签来模仿获取服务器文件信息,先用input标签上传一个图片,然后点击button,来保存获取的图片,注意我们是用input标签来模仿获取服务器文件信息的
html代码<input type="file" id="file"> <button id="btn">点击选择图片</button>
js代码
const obtn=document.querySelector("#btn"); const file=document.querySelector("#file"); obtn.addEventListener("click",async ()=>{ const hFile=await window.showSaveFilePicker({ types: [{ accept: { 'image/*': ['.png', '.gif', '.jpeg', '.jpg', '.webp'] //"text/plain": [".txt"] } }], //可以选择多个图片 multiple: true }); const w$ = await hFile.createWritable(); await w$.write(file.files[0]); //await w$.write('world'); await w$.close(); },false);
如果保存的是txt类似的文件,并且往里写入内容,浏览器会提示是否让保存的权限
浏览器询问权限
注意:
- 需要在https下使用,或者在本地localhost使用
-
因为是新的API,所以兼容性有点差,目前就chrome、edge、opara支持,别的都不支持
浏览器兼容性
参考文章: https://blog.csdn.net/LuckyWinty/article/details/119901944