[씨냅스Seanapse] (2) 화면 구현

HY🥗·2022년 6월 17일
0

seanapse

목록 보기
2/4
post-thumbnail

화면 시연

MyPage 제공 기능

지갑을 연동하고 프로필 이미지를 클릭하면 MyPage로 이동한다.
사용자가 연동한 계정 주소를 프로필 이미지 하단에서 확인할 수 있다.
사용자는 본인이 소유한 NFT 목록을 갤러리 형식으로 확인할 수 있다.
검색 창에서 NFT 이름을 검색하면 키워드가 이름에 포함된 NFT 목록을 조회할 수 있다.
NFT를 클릭하면 해당 NFT의 상세 정보 페이지로 이동한다.

화면 구조

├── src
│   ├── App.js
│   ├── components (mypage에서 필요한 components)
│   │   └── mypage
│   │       ├── Address.js
│   │       ├── Profile.js
│   │       ├── Search.js
│   │       ├── Username.js
│   │       └── index.js
│   ├── layouts (하위 컴포넌트 조립)
│   │   ├── Gallery.js
│   │   ├── Nft.js
│   │   ├── Top.js
│   ├── routes
│   │   └── MyPage.js (최종 페이지)

주요 컴포넌트

//MyPage.js
import {useState, useEffect} from 'react'
import { useNavigate } from "react-router-dom"
import Top from '../layouts/Top'
import Gallery from '../layouts/Gallery'

function MyPage({nftList, address}) {

    const [keyword, setKeyword] = useState('')
    const navigate = useNavigate()

    useEffect(()=> {
      // Home에서 지갑 연동을 하지 않으면 홈 화면으로 리다이렉트
      if(address === '') {
        navigate('/')
      }
    }, [])

    return (
        <div className="MyPage">
            <Top address={address} keyword={keyword} changeHandler={setKeyword}/>
      // props로 연동된 지갑 address, home에서 조회한 nft list, 이름 조회 시 필요한 검색어 keyword를 전달한다.
            <Gallery address={address} nftlist={nftList} keyword={keyword}/>
        </div>   
    )
}

export default MyPage;
//Gallery.js
import styled from 'styled-components'
import Nft from './Nft'

const StyledDiv = styled.div`
    display: flex;
    
    flex-wrap: wrap;
    align-self: stretch;
    width: 100%;
    margin-right: 50px;
    margin-left: 50px;
    margin-top: 10px;
`

function Gallery({nftlist, keyword, address}) {

    return (
        <StyledDiv>
            {nftlist.map((el,index) => {
                // 검색 키워드가 있을 때 && NFT 이름에 검색어가 포함되어 있지 않을 경우
                if(keyword !== '' && !((el.name).toLowerCase()).includes(keyword.toLowerCase()) ) {
                    return null;
                }
      			// 사용자 정보가 있을 때 && NFT 소유자의 주소와 같지 않을 경우
                if(address !== '' && (el.owner).toLowerCase() !== address.toLowerCase()) {
                    return null;
                }
                return (
                    <Nft el={el} key={index}/>
                )
            })}
        </StyledDiv>
    )
}

export default Gallery;
//Nft.js
import styled from "styled-components";
import { useNavigate } from 'react-router-dom'

const StyledDiv = styled.div`
    border-radius:10px;
    border: solid 1.5px #EAECEF;  
    width: 300px;
    height: 400px;
    padding: 10px;
    margin-top: 10px;
    margin-left: 20px;
    float: left; 
`

const NftCollectionName = styled.p`
    color: rgb(112, 122, 131);
    font-weight: 500;
    font-size: 13px;
`

const NftImage = styled.img`
    max-width: 100%;
`
const NftName = styled.p`
    color: rgb(53, 56, 64);
    font-size: 15px;
    letter-spacing: 0.1px;
    font-weight: 600;
    margin-top: -12px;
    text-align: left;
`

function NFT({el}) {

    const navigate = useNavigate();
    const imagePath = "https://ipfs.io/ipfs/" + (el.image).substr(7)
    return (
      // 클릭 시 상세 정보 페이지로 이동
        <StyledDiv key={el.index} onClick={() => navigate("/detail/" + el.tokenId)}>
      		// ipfs에 저장된 이미지 URL
            <NftImage src={imagePath} alt=""/>
            <NftCollectionName>Seanapse Collection</NftCollectionName>
            <NftName>{el.name}</NftName>
        </StyledDiv>
    )
}

export default NFT;
profile
사실은 공부를 비밀스럽게 하고 싶었다

0개의 댓글