5단계로 Tailwind로 메뉴를 여는 애니메이션을 만드는 방법
35883 단어 csstailwindcssreactjavascript
저는 개발자 학생이고 다른 사람들을 도울 수 있는 콘텐츠 제작을 시작하고 싶습니다. 저는 개발자 커뮤니티에서 시작하고 있기 때문에 초보자들이 겪는 많은 어려움에 공감할 수 있으며, 그 중 일부는 너무 단순해 보이고 인터넷에 내용 설명조차 없다는 것을 알고 있습니다.
오늘은 표지 gif에 있는 것과 같은 메뉴를 만드는 것을 도와드리겠습니다. 보너스로 현재 페이지를 탐색 모음에서 다른 색상으로 설정했습니다. 이 기사에서는 React 애플리케이션을 사용할 것입니다. 즉, 다른 종류의 프레임워크를 사용하는 경우(또는 전혀 사용하지 않는 경우) 일부 프로세스가 다를 수 있습니다. 페이지 스타일을 변경하는 논리를 만들기 위해 React Hooks를 사용하겠습니다.
프로젝트는 여기에서 사용할 수 있습니다repository. 이를 사용하려면 README 파일의 지침을 따르기만 하면 됩니다. 또한 보고 싶다면 결과와 함께 deploy이 있습니다.
나는 내 프로젝트에서 이 기능을 사용하는 것을 좋아하지만 방법을 설명하는 튜토리얼을 본 적이 없습니다. 그럼 시작하겠습니다!😄
1. 프로젝트에 Tailwind 설치
따라서 먼저 Tailwind를 설치해야 합니다. documentation(코딩할 때 가장 친한 친구라고도 함)를 살펴보는 것이 좋습니다.
2. 컴포넌트 생성
이제 메뉴 구성 요소를 만들어야 합니다. 나는 React를 사용할 때 그것을 분리하여 페이지에 추가하는 것을 선호합니다. 다음은 타이머 프로젝트에서 생성한 탐색 메뉴의 예입니다.
// component: Nav
import logo from '../assets/images/icon.png'
import Button from '../components/Button';
import LinkComponent from "./LinkComponent";
const Nav = () => {
return (
<nav>
<Button
func={() => setIsOpen(!isOpen)}
txt={<img alt="menu-burguer" src={logo} />}
/>
<div>
<LinkComponent path={"/"} txt={"Home Page"} />
<LinkComponent path={"/countdown"} txt={"Countdown"} />
<LinkComponent path={"/timer"} txt={"Timer"} />
<LinkComponent path={"/settings"} txt={"Settings"} />
<LinkComponent path={"/about"} txt={"About"} />
</div>
</nav>
);
}
export default Nav;
// component: Button
const Button = ({ func, txt, isDisabled, className }) => {
return (
<button
className={className}
disabled={isDisabled}
type="button"
onClick={ func }
>
{ txt }
</button>
);
}
Button.defaultProps = {
isDisabled: false,
}
export default Button;
// component: LinkComponent
import { Link } from "react-router-dom"
const LinkComponent = ({ path, txt }) => {
return (
<Link
to={path}
>
{txt}
</Link>
);
}
export default LinkComponent;
3. 논리 만들기
이 애니메이션이 예상대로 작동하려면 HTML 클래스를 변경할 수 있는 코드가 있어야 합니다. 그것은 메뉴를 열고 닫을 때 다른 애니메이션이 필요하기 때문에 중요합니다. 게다가 바에 설정된 위치는 애니메이션이 끝났을 때 머물러야 할 위치라는 것이 기본입니다.
// component: Nav
import { useState } from "react";
import logo from '../assets/images/icon.png'
import Button from '../components/Button';
import LinkComponent from "./LinkComponent";
const Nav = () => {
// the state used to change the current situation (open or closed)
const [isOpen, setIsOpen] = useState(false);
return (
<nav>
<Button
// when the "menu" button is clicked, it sets the state for the opposite boolean value
func={() => setIsOpen(!isOpen)}
txt={<img alt="menu-burguer" src={logo} />}
/>
// this is the div where the menu is "hidden", so it's where the change of classes needs to happen
<div
className={isOpen ? ('class for open menu') : ('class for closed menu')}
>
<LinkComponent path={"/"} txt={"Home Page"} />
<LinkComponent path={"/countdown"} txt={"Countdown"} />
<LinkComponent path={"/timer"} txt={"Timer"} />
<LinkComponent path={"/settings"} txt={"Settings"} />
<LinkComponent path={"/about"} txt={"About"} />
</div>
</nav>
);
}
export default Nav;
현재 페이지에 대한 링크가 강조 표시되는 보너스 부분은 더 많은 논리가 필요하기 때문에 조금 더 복잡합니다.
// component: LinkComponent
import { useContext, useEffect, useState } from "react";
import { Link, useRouteMatch } from "react-router-dom"
import TimeContext from "../context/TimeContext";
const LinkComponent = ({ path, txt }) => {
// first, we need to get the current pathname
const pathname = useRouteMatch();
const [isCurrent, setIsCurent] = useState(false);
const [currentPath, setCurrentPath] = useState('/');
// always when the pathname is changed the function occurs
useEffect(() => {
setCurrentPath(pathname.path)
}, [pathname]);
// always when the pathname or the path (props) is changed the function occurs
useEffect(() => {
const changeIsCurrent = () => {
if (currentPath === path) {
setIsCurent(true);
} else {
setIsCurent(false);
}
}
changeIsCurrent();
}, [currentPath, path]);
return (
// where happens the highlight depends if it's true (happen) or false (don't happen)
<Link
className={isCurrent ? ('class when the page is the current'): ('class when the page is not the current')}
to={path}
>
{txt}
</Link>
);
}
export default LinkComponent;
4. 애니메이션 만들기
tailwind.config.js 문서에는 사용자 지정 설정을 추가할 수 있는 개체가 있습니다. 예제와 같이 애니메이션 구성을 추가할 것입니다.
// tailwind.config.js
/** @type {import('tailwindcss').Config} */
module.exports = {
content: ["./src/**/*.{js,jsx,ts,tsx}"],
theme: {
extend: {
animation: {
openmenu: 'openmenu 1s ease-in',
closemenu: 'closemenu 1s ease-in',
},
keyframes: {
openmenu: {
// initial position
'0%': {left: '-224px'},
// final position
'100%': {left: '0px'}
},
closemenu: {
// initial position
'0%': {left: '0px'},
// final position
'100%': {left: '-224px'}
},
}
},
},
plugins: [],
}
5. 메뉴 구성 요소에 클래스 추가
이제 애니메이션이 있으므로 구성 요소에 추가할 차례입니다. 이것은 내 타이머 프로젝트의 결과이지만 원하는 방식으로 스타일을 지정할 수 있습니다.
경고: 애니메이션의
final position
를 구성 요소의 default
로 설정하는 것을 잊지 마십시오. 애니메이션이 끝나면 설정된 위치로 리디렉션되기 때문에 필요합니다.// component: Nav
import { useState } from "react";
import logo from '../assets/images/icon.png'
import Button from '../components/Button';
import LinkComponent from "./LinkComponent";
const Nav = () => {
const [isOpen, setIsOpen] = useState(false);
return (
<nav className="font-epilogue">
<Button
className="w-20"
func={() => setIsOpen(!isOpen)}
txt={<img alt="menu-burguer" src={logo} />}
/>
<div
className={isOpen ?
"left-[0px] font-epilogue flex top-[12vh] animate-openmenu w-56 absolute flex-col bg-light-ocean p-12 h-[88vh]" :
"animate-closemenu top-[12vh] left-[-224px] flex w-56 absolute flex-col bg-light-ocean p-12 h-[88vh]"}
>
<LinkComponent path={"/"} txt={"Home Page"} />
<LinkComponent path={"/countdown"} txt={"Countdown"} />
<LinkComponent path={"/timer"} txt={"Timer"} />
<LinkComponent path={"/settings"} txt={"Settings"} />
<LinkComponent path={"/about"} txt={"About"} />
</div>
</nav>
);
}
export default Nav;
// component: LinkComponent
import { useContext, useEffect, useState } from "react";
import { Link, useRouteMatch } from "react-router-dom"
import TimeContext from "../context/TimeContext";
const LinkComponent = ({ path, txt }) => {
const pathname = useRouteMatch();
const { currentPath } = useContext(TimeContext);
const [isCurrent, setIsCurent] = useState(false);
const [currentPath, setCurrentPath] = useState('/');
useEffect(() => {
setCurrentPath(pathname.path)
}, [pathname]);
useEffect(() => {
const changeIsCurrent = () => {
if (currentPath === path) {
setIsCurent(true);
} else {
setIsCurent(false);
}
}
changeIsCurrent();
}, [currentPath, path]);
return (
<Link
className={isCurrent ? (
"mb-3 text-dark-purple font-bold bg-soft-purple p-2 text-center rounded-2xl"): (
"mb-3 text-dark-purple hover:font-bold p-2 text-center")}
to={path}
>
{txt}
</Link>
);
}
export default LinkComponent;
이 튜토리얼이 즐거웠기를 바랍니다. 개선할 수 있는 부분이 있으면 주저하지 말고 저에게 연락해 주세요! 모든 피드백을 환영합니다.✨
Reference
이 문제에 관하여(5단계로 Tailwind로 메뉴를 여는 애니메이션을 만드는 방법), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://dev.to/maysab/how-to-create-an-animation-to-open-a-menu-with-tailwind-in-5-steps-1llj텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)