이미지 미리보기

한신웅·2022년 3월 13일
0

Project

목록 보기
7/7
post-thumbnail

서론

2차 프로젝트때 나는 '호스트 되기'페이지를 맡았다.
'호스트 되기'는 꽤 많은 페이지로 구성되어 있다. 모든 정보를 한 페이지가 아닌 여러 페이지에서 받아오는 방식이었다. 그 중 숙소 이미지를 등록하는 페이지가 있었는데 미리보기 기능이 필요했다.

본론

useState()

const [previews, setPreviews] = useState([]);
  • input을 통해 들어올 state를 만든다.

Input 설정

<form>
	<input type="file" multiple accept="images/*"
	onChange={uploadImages} />
    <button>전송</button>
</form>
  • type은 이미지를 등록할 것이기 때문에 file로.
  • multiple로 해야 여러장의 이미지를 선택하고 등록할 수 있다.
  • accpet는 여러가지 속성이 있고 선택사항도 많지만 나는 image면 다 되게끔 설정을 해놨다.
  • onChange={uploadImages} 등록.

uploadImages()

e.target.value

const uploadImages = e => {
	console.log(e.target.value);
  };

  • 파일들을 선택하고 console로 어떻게 들어왔는지 확인하면 위의 이미지와 같이 들어오는데 이걸로는 미리보기를 할 수가 없다. 그래서 사용한 것이

Object.entries & URL.createObjectURL

 const uploadImages = e => {
    let imagesArray = Object.entries(e.target.files).map(e =>
      URL.createObjectURL(e[1])
    );
    setPreviews([...images, ...imagesArray]);
  };
  • 들어온 데이터를 가공해야 하는데 files들을 그냥 map함수를 사용하면 원하는 것을 가져올 수 없다. 그러므로 객체가 갖고있는 모든 속성들을 키와 값 쌍으로 배열 형태로 반환하여 주는 Object.entries()를 활용한다. 아래는 console로 찍은 결과물.

  • 그리고 이미지를 보여주려면 경로를 알아야하는데 URL.createObjectURL을 사용하여 blob타입의 경로를 받아낸다. 아래는 console로 찍은 결과물.

  • 그렇게 나온 경로들을 set함수를 이용해 담는다.

render

<div>
	{previews.length > 0 &&
	previews.map((image, idx) => {
		return (
			<PreviewImage key={image}>
			<img src={image} alt="미리보기" />
			<button onClick={() => deleteFile(idx)}>삭제</button>
			</PreviewImage>
		);
	})}
</div>
  • 조건부 렌더링을 사용하여 이미지를 보여준다.
  • 그리고 삭제버튼까지 추가.

deleteFile

 const deleteFile = e => {
    const deleteImage = previews.filter((image, idx) => idx !== e);
    setPreviews(deleteImage);
  };
  • 삭제 함수까지 구현해주면 끝.

결론

내가 한 방법 말고 FileReader.readAsDataURL()를 이용한 방법도 있다고 한다. 그건 내가 사용해보지 않아서 잘 모르겠다. 내 방법이 맞지 않다면 위의 적은 방법을 검색해보고 이용하면 될 것 같다.

아래는 결과물이다. 그런데 파일을 다 지우고나면 올린 파일 갯수가 남아있다. 그거는 시간 관계상 처리하지 못했다. 다음에 기회가 되면 꼭!

profile
genius🚀

0개의 댓글

관련 채용 정보