我正在使用 Next.js/React.js 构建一个图像上传表单,我希望用户能够为每个上传分配一个标签。我还想使用“URL.createObjectURL”显示图像预览。上传工作正常,但在上传页面上,我尝试遍历图像列表以显示预览并显示输入框以分配标签,但这些都没有显示。我不知道为什么。
编码:
import { useState } from "react";
import Head from 'next/head'
import Layout, { siteTitle } from '../../components/layout'
import Image from 'next/image'
export default function PrivatePage(props) {
const [images, setImages] = useState([])
const [imageURLS, setImageURLS] = useState([])
const [tag, setTag] = useState(null)
const uploadImageToClient = (event) => {
var imageList = images
var urlList = imageURLS
if (event.target.files && event.target.files[0]) {
imageList.push(event.target.files[0]);
urlList.push(URL.createObjectURL(event.target.files[0]))
setImages(imageList);
setImageURLS(urlList);
}
};
const uploadTagToClient = (event) => {
if (event.target.value) {
const i = event.target.value;
setTag(i);
}
};
const uploadToServer = async (event) => {
const body = new FormData()
images.map((file, index) => {
body.append(`file${index}`, file);
});
body.append("tag", tag)
const response = await fetch("/api/file", {
method: "POST",
body
});
};
return (
<Layout home>
<Head>
<title>{siteTitle}</title>
</Head>
<div className="container">
<div className="row">
<h4>Select Images</h4>
<div className="col">
<input type="file" className="btn btn-outline-success-inverse" onChange={uploadImageToClient} />
<input type="file" className="btn btn-outline-success-inverse" onChange={uploadImageToClient} />
</div>
<div className="col">
</div>
<button
className="btn btn-outline-success-inverse"
type="submit"
onClick={uploadToServer}
>
Send to server
</button>
{images.map((file, index) => {
return (
<div class="row ">
<lead>{file.name}</lead>
<input type="text" onChange={uploadTagToClient} />
<image src={imageURLS[index]}/>
</div>)
})}
</div>
</div>
</Layout>
);
}
澄清一下,images.map
里面什么都没有当我选择图像时显示。
最佳答案
发生此问题是因为您正在更改状态为 imageList.push
的数组。和 urlList.push
哪个 React 没有接受。这意味着状态实际上并没有得到更新,并且不会发生重新渲染。
要修复它,而不是改变那些状态数组,您需要在更新它们时创建新的。
const uploadImageToClient = (event) => {
if (event.target.files && event.target.files[0]) {
setImages((imageList) => [...imageList, event.target.files[0]]);
setImageURLS((urlList) => [
...urlList,
URL.createObjectURL(event.target.files[0])
]);
}
};
与主要问题无关,组件的渲染部分有几个小问题,特别是在
images.map
内部。 .key
外侧支撑 <div>
元素; <lead>
元素不存在,需要替换为有效元素; <image>
元素也不存在,您的意思可能是 <img>
或 <Image>
(来自 next/image
)。 关于javascript - 如何使用 React 显示图像上传预览?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/69035352/