마우스를 올리면 움직이는 3D 책 만들기
인터랙티브 웹과 어울리는 컴포넌트
3D 컴포넌트
Next.js 공식문서를 읽던 중, 3D 컴포넌트를 발견하였다.
마우스를 올리면 책이 움직인다. 이 컴포넌트를 보자마자 어떻게 구현한 것인지 궁금해져 바로 개발자도구를 켜서 이 페이지의 HTML, CSS를 구경해보았다. CSS 부분을 읽어보니 프레임워크나 라이브러리 없이 순수 CSS만을 이용해서 구현했다는 것을 알 수 있었다. 충분히 간단하게 구현해볼 수 있을 것 같다는 생각이 들었고, 바로 vscode를 켜서 만들어 보았다.
완성된 모습은 이렇게 생겼다. 라이브러리 없이 단순 CSS만으로 만들기 때문에 코드도 간단하고 자바스크립트 환경 어디서든 사용할 수 있다.
구현하는 방법
HTML
<div id="container">
<div class="book">
<div class="bookCover">
<div class="binder"></div>
<div class="content">
<div class="title">제목을 입력하세요</div>
<div class="subTitle">부제목을 입력하세요</div>
</div>
</div>
<div class="bookSide"></div>
<div class="bookBack"></div>
</div>
</div>
CSS
#container {
display: flex;
justify-content: center;
align-items: center;
}
.book {
display: flex;
align-items: center;
position: relative;
width: 240px; /* 책 가로 길이 */
height: 270px; /* 책 세로 길이 */
border-radius: 6px; /* 책 모서리 둥근 정도 */
.bookCover {
z-index: 10;
background-color: #e5e7eb; /* 책 색깔 */
border-radius: inherit;
box-shadow: inset -2px -2px 8px rgba(0, 0, 0, 0.03);
display: flex;
width: 100%;
height: 100%;
transition: transform 0.5s ease-in-out;
transform: perspective(300px) rotateY(0deg);
.binder {
width: 15%; /* 책 표지 왼쪽에 있는 바인더의 가로 길이 */
box-shadow: inset -2px -2px 5px rgba(0, 0, 0, 0.03);
border-top-left-radius: 6px; /* 책 모서리 둥근 정도 */
border-bottom-left-radius: 6px; /* 책 모서리 둥근 정도 */
}
.content {
width: 85%; /* 바인더를 제외한 표지의 가로 길이 */
padding: 36px;
display: flex;
border-top-right-radius: inherit;
border-bottom-right-radius: inherit;
flex-direction: column;
align-items: center;
/* 책 표지에 들어갈 내용들 */
.title {
font-weight: 600;
margin-bottom: 3px;
}
.subTitle {
font-size: 12px;
}
}
}
.bookSide {
z-index: 5;
position: absolute;
right: 0;
border-top-right-radius: 3px;
border-bottom-right-radius: 3px;
box-shadow: inset 4px 0 8px rgba(0, 0, 0, 0.1);
background-color: white;
width: 20px;
height: 100%;
transition: transform 0.5s ease-in-out;
transform: perspective(300px) rotateY(90deg) translateX(20px);
}
.bookBack {
position: absolute;
right: 0;
background-color: #e5e7eb; /* 책 색깔 */
border-radius: inherit;
width: 80%;
padding-left: 20px;
height: calc(100% - 10px);
transition: transform 0.5s ease-in-out;
transform: perspective(300px) rotateY(0deg);
}
}
.book:hover {
cursor: pointer;
.bookCover {
transition: transform 0.5s ease-in-out;
transform: perspective(300px) rotateY(-5deg);
}
.bookSide {
animation: transform 0.5s ease-in-out;
transform: perspective(300px) rotateY(30deg) translateX(20px);
}
.bookBack {
transition: transform 0.5s ease-in-out;
transform: perspective(300px) rotateY(-5deg) translateX(20px);
}
}
CSS의 transform의 perspective, rotate, translate를 이용하였다. 이를 구현하면서 순수 CSS의 기능만으로도 3D 컴포넌트를 구현할 수 있다는 것을 처음 알게 되어 놀라웠다. 그동안 CSS 라이브러리만 계속해서 이용했다보니 오히려 순수 CSS에 대한 지식이 부족해지지 않았나, 라고 반성도 하였다😅 인터랙티브한 웹에 관심이 많아서 Three.js도 약간 사용해본 적이 있었는데, 오히려 앞으로는 이런 간단한 수준의 3D는 순수 CSS를 이용하게 될 것 같다.
'개발 이야기 > 직접 해보기' 카테고리의 다른 글
[JavaScript] React에서 Pagination 라이브러리 사용해보기 (0) | 2024.01.17 |
---|---|
[JavaScript] CommonJS와 ESM을 모두 지원하는 React 라이브러리 개발 (Feat. 모듈이란 무엇인가) (0) | 2023.12.09 |
[React] 반응형 디자인 직접 코드로 구현해보기 (0) | 2023.08.09 |
[React Query] useQuery로 검색 기능을 만들던 중 마주친 문제 (0) | 2023.05.15 |
[React] Pagination + 검색 기능 로직 직접 만들어보기 (0) | 2023.02.18 |