-
MUI - 모달로 슬라이더 만들기MUI 2022. 7. 29. 05:00728x90반응형
MUI의 모달을 사용하여 모달 안에서 슬라이드를 구현해보자.
import 부분
나는 Marsonry라는 레이아웃을 적용하였다. 똑같이 적용하고 싶다면 @mui/lab을 설치하면 된다.
import React, { useState } from 'react'; import styled from '@emotion/styled'; import { Masonry } from '@mui/lab'; import { Box, Modal, IconButton, Typography } from '@mui/material'; import ArrowBackIosIcon from '@mui/icons-material/ArrowBackIos'; import ArrowForwardIosIcon from '@mui/icons-material/ArrowForwardIos';
함수 동작 부분
const [open, setOpen] = useState(false); const [imgindex, setImgindex] = useState(0); const handleOpen = index => { setImgindex(index.target.id); setOpen(true); }; const handleClose = () => setOpen(false); const backImg = () => { Number(imgindex) === 0 ? setImgindex(movie_image.length - 1) : setImgindex(imgindex - 1); }; const forwardImg = () => { setImgindex(Number(imgindex) + 1); if (imgindex === movie_image.length - 1) { setImgindex(0); } };
주의할점!
자바스크립트는 +와 - 를 문자와 숫자를 같은 타입이라고 생각하고 그대로 문자와 숫자를 더해버리기 때문에
숫자로만 판별해야 하는 조건에서는 Number()를 통해서 문자가 아닌 숫자라고 정해줘야 오류가 나지 않는다.
컴포넌트 UI 부분
<Box> <GalleryModal open={open} onClose={handleClose} aria-labelledby="modal-modal-title" aria-describedby="modal-modal-description" img={movie_image} imgindex={imgindex} > <ImgContainer> <GalleryButton sx={{ marginLeft: '-80px' }} onClick={backImg}> <ArrowBackIosIcon /> </GalleryButton> <Img src={movie_image[imgindex]} img={movie_image} imgindex={imgindex} /> <GalleryButton sx={{ marginLeft: '50px' }} onClick={forwardImg}> <ArrowForwardIosIcon /> </GalleryButton> <Box sx={{ textAlign: 'center', marginTop: '10px' }}> <NowImg>{Number(imgindex) + 1}</NowImg> <TotalImg> /{movie_image.length}</TotalImg> </Box> </ImgContainer> </GalleryModal> </Box>
전체 코드
import React, { useState } from 'react'; import styled from '@emotion/styled'; import { Masonry } from '@mui/lab'; import { Box, Modal, IconButton, Typography } from '@mui/material'; import ArrowBackIosIcon from '@mui/icons-material/ArrowBackIos'; import ArrowForwardIosIcon from '@mui/icons-material/ArrowForwardIos'; function MovieGallery({ movie_image }) { const [open, setOpen] = useState(false); const [imgindex, setImgindex] = useState(Number(0)); const handleOpen = index => { setImgindex(index.target.id); setOpen(true); }; const handleClose = () => setOpen(false); const backImg = () => { Number(imgindex) === 0 ? setImgindex(Number(movie_image.length) - 1) : setImgindex(Number(imgindex) - 1); }; const forwardImg = () => { setImgindex(Number(imgindex) + 1); if (imgindex === movie_image.length - 1) { setImgindex(0); } }; return ( <> <Box sx={{ width: '100%', minHeight: 429 }}> <Masonry columns={4} spacing={2}> {movie_image?.map((item, index) => ( <div key={index}> <MasonryImg id={index} src={`${item}?w=162&auto=format`} srcSet={`${item}?w=162&auto=format&dpr=2 2x`} alt={item.title} loading="lazy" onClick={handleOpen} style={{ borderRadius: 8, borderBottomLeftRadius: 8, borderBottomRightRadius: 8, display: 'block', width: '100%', boxShadow: '5px 7px 20px -4px rgba(0, 0, 0, 0.6)', }} /> </div> ))} </Masonry> </Box> <Box> <GalleryModal open={open} onClose={handleClose} aria-labelledby="modal-modal-title" aria-describedby="modal-modal-description" img={movie_image} imgindex={imgindex} > <ImgContainer> <GalleryButton sx={{ marginLeft: '-80px' }} onClick={backImg}> <ArrowBackIosIcon /> </GalleryButton> <Img src={movie_image[imgindex]} img={movie_image} imgindex={imgindex} /> <GalleryButton sx={{ marginLeft: '50px' }} onClick={forwardImg}> <ArrowForwardIosIcon /> </GalleryButton> <Box sx={{ textAlign: 'center', marginTop: '10px' }}> <NowImg>{Number(imgindex) + 1}</NowImg> <TotalImg> /{movie_image.length}</TotalImg> </Box> </ImgContainer> </GalleryModal> </Box> </> ); } export default MovieGallery; const ImgContainer = styled(Box)` position: relative; top: 50%; left: 50%; transform: translate(-50%, -50%); width: 800px; box-shadow: 24px; padding: 40px; outline: none; `; const MasonryImg = styled.img` cursor: pointer; transition: all ease 0.5s; :hover { transform: scale(1.04, 1.04); } `; const Img = styled.img` border-radius: 16px; width: 100%; `; const GalleryButton = styled(IconButton)` position: absolute; top: 50%; `; const GalleryModal = styled(Modal)``; const NowImg = styled(Typography)` display: inline; color: white; font-weight: bold; `; const TotalImg = styled(NowImg)``;
728x90반응형'MUI' 카테고리의 다른 글
Mui - Progressbar (0) 2022.07.20 MUI - TextField (0) 2022.07.16 MUI - Box (0) 2022.07.16 MUI를 사용하는 방법 (0) 2022.07.06