文章目录
- 前言
- 一、选择本地文件
- 1.设计一个上传文件按钮
- 2.FileReader读取文件内容
- 二、使用拖拽方式
- 1.设计一个拖拽容器
- 2.拖拽文件的相关事件回调
- 三、使用粘贴方式
- 1.设计一个粘贴容器
- 2.paste事件回调
- 四、总结
前言
前端无法像app一样直接操作本地文件,对本地文件的操作和上传,通常使用以下三种方式:
- 通过input type = file 选择本地文件上传,这是最常见的方式
- 通过拖拽的方式把文件拖过来
- 在编辑框里面复制黏贴,这种方式常见于上传图片。
一、选择本地文件
1.设计一个上传文件按钮
通过input type = file 选择本地文件上传,通常会自定义一个按钮,然后盖在上面,因为type=file的input不容易改变样式。
这里使用label做样式覆盖,label 元素不会向用户呈现任何特殊效果。不过,它为鼠标用户改进了可用性。如果在 label 元素内点击文本,就会触发此控件。就是说,当用户选择该标签时,浏览器就会自动将焦点转到和标签相关的表单控件上。
注意:label中的for属性应与input元素的id一致
<form id="form"><label for="submit"><div class="lBut"><span>选择文件</span></div></label><input id="submit" type="file" /></form>
#submit {display: none;}.lBut {width: 87px;height: 24px;font-size: 14px;line-height: 24px;display: flex;justify-content: center;align-items: center;border-radius: 4px;margin-left: 28px;transition: all 0.5s;white-space: nowrap;background-color: #409eff;color: white;border: 1px solid #409eff;}
而通过表单选择的文件无法直接获取文件真实存放路径,文件里面内容也无法查看。formData格式的文件可以作为接口参数传给后台。
const inputFile = document.getElementById("submit");const form = document.getElementById("form");inputFile.addEventListener("change", function () {let formData = new FormData(form);console.log("formData :>> ", formData);console.log("inputFile.value :>> ", inputFile.value);});
2.FileReader读取文件内容
当选择文件后,触发input的change事件,在change的回调方法中初始化一个fileReader对象,fileReader有一个方法readAsDataURL可以读取文件并转为base64格式。在fileReader读取文件后触发onload回调方法,在回调方法中获取文件的结果,并创建一个img元素把结果作为src属性值,展示在页面上。
js代码如下:
const inputFile = document.getElementById("submit");const form = document.getElementById("form");inputFile.addEventListener("change", function () {let file = inputFile.files[0];if (!file) return;console.log("file :>> ", file);// 读取文件并转化为base64格式let fileReader = new FileReader();fileReader.readAsDataURL(file);fileReader.onload = function () {console.log("fileReader :>> ", fileReader);if (/^image\/[jpeg|png|gif]/.test(file.type)) {let img = document.createElement("img");img.src = fileReader.result;img.style.width = "500px";document.body.append(img);}};});
二、使用拖拽方式
1.设计一个拖拽容器
<body><div id="container">drag your image here</div></body><style>#container {width: 500px;height: 500px;border: 1px solid #dfdfdf;margin: 0 auto;text-align: center;vertical-align: middle;}
</style>
2.拖拽文件的相关事件回调
容器的dragover事件和drop事件的默认行为是打开新页面展示,需要阻止默认行为
在drop事件回调中,获取拖拽的文件,数据存储在event.dataTransfer.files中,然后就可以调用fileReader.readAsDataURL或添加到formData中了
const container = document.getElementById("container");container.addEventListener("dragover", function (event) {// 浏览器默认行为是打开新页面展示,需要阻止默认行为event.preventDefault();});container.addEventListener("drop", function (event) {console.log("event :>> ", event);event.preventDefault(); // 阻止默认的点击事件执行let file = event.dataTransfer.files[0];console.log("file :>> ", file);if (!file) return;showImg(file);});const showImg = (file) => {// 读取文件并转化为base64格式let fileReader = new FileReader();fileReader.readAsDataURL(file);fileReader.onload = function () {if (/^image\/[jpeg|png|gif]/.test(file.type)) {let img = document.createElement("img");img.src = fileReader.result;img.style.width = "500px";container.append(img);}};};
三、使用粘贴方式
1.设计一个粘贴容器
粘贴通常在一个编辑框操作,比如把div的contenteditable设置为true
<div id="container" contenteditable="true">paste your image here</div>
2.paste事件回调
粘贴的数据在event.clipboardData.files中,在容器的paste获取,代码如下:
const container = document.getElementById("container");container.addEventListener("paste", function () {event.preventDefault();let file = event.clipboardData.files[0];console.log("file :>> ", file);if (!file) return;showImg(file);});const showImg = (file) => {// 读取文件并转化为base64格式let fileReader = new FileReader();fileReader.readAsDataURL(file);fileReader.onload = function () {if (/^image\/[jpeg|png|gif]/.test(file.type)) {let img = document.createElement("img");img.src = fileReader.result;img.style.width = "500px";container.append(img);}};};
四、总结
文件的上传常见有三种方式:选择文件、拖拽和粘贴。选择文件通常使用表单,文件的数据在form.files中,form为表单元素;拖拽的方式,文件的数据在drop事件的event.dataTransfer.files中;粘贴的方式,文件的数据在paste事件的event.clipboardData.files中;在获取上传文件的数据后,使用fileReader来读取文件数据,展示在页面上,或者添加到formData上,通过接口传递给后台。