React 实现图片上传和展示功能 您所在的位置:网站首页 上传图片啊 React 实现图片上传和展示功能

React 实现图片上传和展示功能

2023-12-28 10:48| 来源: 网络整理| 查看: 265

基本介绍 📝 最近完成了产品提出的一个类似微信发图文朋友圈的需求(以下实现均基于 React + mobx 项目): 1⃣️ 通过➕号按钮选择系统图片,最多可选择9张图,选择的图片以九宫格形式展示 2⃣️ 选择图片后开始上传,图片大小限制为 20 MB,超过限制不上传且不展示 3⃣️ 展示图片上传过程中的 loading 状态 4⃣️ 图片上传失败可点重试按钮重新上传 5⃣️ 可以删除选中的图片(若上传中删除前还需中断 xhr 请求) 6⃣️ 发布后的图片内容按照一定规则展示(单图片、四宫格和九宫格) 历尽千辛万苦终于实现了以上的功能,具体效果如下: 上传图片页面: show.gif 展示页面(单图,按照单图规则展示): image.png 展示页面(四图,四宫格): image.png 展示页面(多图,九宫格): image.png 该需求涉及到许多零散的知识点,遂以此文做总结记录,下面将介绍思路和具体的实现代码。 思路分析 🤔 选择图片 选择图片可以用设置 type 属性为 file 值的 input 标签: 通过设置其 multiple 属性和 accept 属性可以使得 input 标签支持多选和仅支持选择 gif、jpg/jpeg 和 png 类型的文件。 image.png 当点击标签时,则可以从文件系统中选择照片。我们的需求是提供一个➕号按钮作为选择图片的入口,这里可以使用 ref 获取该 input 元素,当点击➕号按钮时触发 input 的点击事件,即可以调用系统的相册进行图片选取。 限制图片大小和数量、预览本地图片 当 input 元素的 change 事件被触发时,可以通过 input.files 获取到当前选中文件的 FileList 类数组对象,当选择两张图片后,打印 FileList 对象: image.png 可以看到每个 File 对象都有 size 字段,可以用来判断图片大小(字节)是否超过限制(20MB 是20 * 1024 * 1024)。 区别于原生 APP,web 网页无法阻止用户选择超过 9 张图片,只能在代码中做限制,当总选择的图片超过 9 张则做超出数量提示和截断处理(取前 9 张图)。 由于可以获取到每张图片的 File 对象,则可以使用 URL.createObjectURL() 创建一个对象 URL,可以作为 img 标签的 src 值进行传入,则能实现本地图片的预览功能。 需要注意的是,当不再需要这些使用 URL.createObjectURL() 创建的 URL 对象时,每个对象必须通过调用 URL.revokeObjectURL() 方法来释放,让浏览器知道不用在内存中继续保留对这个文件的引用了(可设置图片的load事件处理器来释放对象URL,当图片加载完成之后对象URL就不再需要了)。 const localUrl = URL.createObjectURL(flieList[0]) // localUrl 可作为图片的源 span''/span // 无需使用时释放内存 window.URL.revokeObjectURL(localUrl); 上传图片和失败重试 通过前面的分析,我们可以获取到每张图片的 File 对象,我们就可以通过新建一个 FromData 对象,并将 File 对象添加到 FromData 对象中,使用 XMLHttpRequest 来处理无刷新上传图片。 const xhr = new XMLHttpRequest(); const formData = new FormData(); formData.append('file', fileData); xhr.open('POST', UPLOAD_IMAGE_URL); // 需要后端提供上传 URL xhr.send(formData); xhr.onreadystatechange = () => { if (xhr.readyState === 4) { if (xhr.status === 200) { // handle response } else { // handle error } } } 上传失败时则重新执行以上上传逻辑。 图片展示 发布后的图片需要按照一定的规则展示: 单张图使用微信朋友圈图片的显示规则,需要获取图片原本的宽高,因此需要后端在上传图片完成后返回图片的原始宽高。 四张图时使用四宫格 其他数量的图片以九宫格形式展示 为了使得图片在保持其宽高比的同时填充 img 元素的整个内容框,我们通过可以设置 img 元素的 object-fit CSS 属性值为 cover 来实现。 下面将介绍整个图片上传和展示功能的具体实现代码。 具体实现 🧐 上传图片页面相关组件

这部分将实现创建页的上传图片组件,当添加图片张数少于9张时展示➕号按钮,图片添加后开始上传图片,图片上传过程中展示 loading 状态,添加的图片可以被删除,即效果如下: show.gif

首先是 UploadImage 组件,代码如下: image.png image.png

UploadImage 组件中使用了 ImageItem 子组件,封装了上传、删除、重试逻辑,相关代码如下: image.png

样式文件代码如下: image.png

可以看到,在使用 UploadImage 组件时需要传入 imageList 和及其更新方法 updateImageList。接下来我们看使用 updateImageList 组件的最外层组件 PostEditorView 的相关代码:

image.png

上面的代码可以看到,可以写一些自定义 hooks 来减小 PostEditorView 组件的大小:

useConfirmModal 封装提交内容时的弹框逻辑 useAlertModal 封装图片上传失败时的弹框逻辑 useUploadInput 封装选择图片相关逻辑

至此,上传图片页面相关组件的代码均已展示完成,建议结合思路阅读相关代码,仅提供思路,部分无关代码已删除。

展示图片页面组件

这部分将实现内容页的展示图片组件。BlogImageList 组件相关代码如下: image.png

样式文件代码如下: image.png

在展示页面,只需要将带图片id、原始宽高的图片列表传给组件即可。

PS:单张图使用微信朋友圈图片的显示规则,如下图所示,假设图片宽高比 X,当图片 1:1 时显示的尺寸为 Y * Y(在项目中 Y = 180,L = 4):

image.png

总结 👀 本文主要整理了在 React 项目实现图片上传和展示功能的相关思路和代码,涉及到使用 input[type=file] 标签来唤起系统选择图片功能,使用 URL.createObjectURL() 对 File 对象进行处理实现本地图片预览,以及使用 xhr 实现无刷新图片上传等知识点。

以上内容如有遗漏错误,欢迎留言 ✍️指出,一起进步💪💪💪

如果觉得本文对你有帮助,🏀🏀留下你宝贵的 👍

参考资料 前端图片上传那些事儿 在web应用程序中使用文件 MDN - URL.createObjectURL() 微信朋友圈图片的显示规则


【本文地址】

公司简介

联系我们

今日新闻

    推荐新闻

    专题文章
      CopyRight 2018-2019 实验室设备网 版权所有