모바일에서 주로 사용되는 형태의 날짜 선택 컴포넌트를 만드려고 한다.
미리보기
환경
react : v18.3.1
styled-components: v6.1.13
react-mobile-picker : v1.0.1
React Mobile Picker 설치
npm install react-mobile-picker
NPM : https://www.npmjs.com/package/react-mobile-picker
코드
import { useEffect, useState } from "react";
import styled from "styled-components";
import Picker from "react-mobile-picker";
interface ISelections {
year: number[];
month: number[];
day: number[];
[key: string]: number[]; // 인덱스 시그니처 추가
}
const date = new Date();
const year = date.getFullYear();
const month = date.getMonth() + 1; // 0-based라 +1
const day = date.getDate();
// Helper 함수: 해당 연도와 월의 최대 일수 계산
const getDaysInMonth = (year: number, month: number) =>
new Date(year, month, 0).getDate();
const CustomDatePicker = () => {
// 초기 상태 설정
const [value, setValue] = useState({ year, month, day });
const [selections, setSelections] = useState<ISelections>({
year: Array.from({ length: 5 }, (_, i) => i + Number(year) - 2), // 최근 24년
month: Array.from({ length: 12 }, (_, i) => i + 1), // 1~12월
day: Array.from({ length: getDaysInMonth(year, month) }, (_, i) => i + 1), // 현재 월의 최대 일수
});
// value의 year 또는 month가 변경되면 day 배열 재생성
useEffect(() => {
const daysInMonth = getDaysInMonth(value.year, value.month);
setSelections((prev) => ({
...prev,
day: Array.from({ length: daysInMonth }, (_, i) => i + 1),
}));
// 현재 선택된 day가 새로 계산된 최대 일수를 초과할 경우 조정
if (value.day > daysInMonth) {
setValue((prev) => ({
...prev,
day: daysInMonth,
}));
}
}, [value.year, value.month]); // year 또는 month가 변경될 때 실행
return (
<>
<div>{`선택된 날짜 : ${value.year}-${value.month}-${value.day}`}</div>
<SLayout
style={{
width: "300px",
}}
>
<Picker
value={value}
onChange={setValue}
wheelMode="normal"
className="custom-picker"
>
{Object.keys(selections).map((date) => (
<Picker.Column key={date} name={date}>
{selections[date].map((option) => (
<Picker.Item key={option} value={option}>
{({ selected }) => (
<div
style={{
color: selected ? "white" : "black",
backgroundColor: selected ? "#d9d9d9" : "white",
padding: "2px 10px", // 여백 조정
margin: "2px 0", // 항목 간 간격 조정
borderRadius: "5px",
fontSize: "14px", // 텍스트 크기 조정
}}
>
{option}
</div>
)}
</Picker.Item>
))}
</Picker.Column>
))}
</Picker>
</SLayout>
</>
);
};
export default CustomDatePicker;
const SLayout = styled.div``;
'React' 카테고리의 다른 글
[React] input 태그의 왼쪽 0 제거하기 (0) | 2024.12.05 |
---|---|
[React] 근태(출퇴근) 관리 달력 만들기 (with. date-fns) (2) | 2024.11.27 |
[Webpack] 웹팩 환경에서 favicon 추가하는 방법 (1) | 2024.11.15 |
[React-Query] 리액트 쿼리 브라우저 복귀시 API 중복 요청 방지 (1) | 2024.10.29 |
[React] html2pdf.js를 활용해 PDF 다운로드 구현하기 (0) | 2024.07.17 |