Calendar 캘린더
월 단위 캘린더입니다. DatePicker core의 월 그리드 알고리즘을 재사용하며, 범위 제약과 방향키 그리드 내비게이션을 지원합니다.
기본 사용법
기본 사용법
2026년 10월
일월화수목금토
vue
<script setup>
import { ref } from 'vue'
const date = ref(new Date())
</script>
<template>
<LhCalendar v-model="date" />
</template>vue
<script>
export default {
data() {
return { date: new Date() }
},
}
</script>
<template>
<LhCalendar v-model="date" />
</template>기간 선택과 다중 선택
selection은 세 가지 모드를 지원합니다: 'single'(기본값) / 'range'(두 번 클릭으로 시작과 끝 지정) / 'multiple'(클릭으로 여러 날짜 전환).
기간 선택
2026년 10월
일월화수목금토
2026년 11월
일월화수목금토
vue
<script setup>
import { ref } from 'vue'
const span = ref([new Date(2026, 8, 5), new Date(2026, 8, 20)])
</script>
<template>
<LhCalendar v-model="span" selection="range" :panels="2" />
</template>vue
<script>
export default {
data() {
return { span: [new Date(2026, 8, 5), new Date(2026, 8, 20)] }
},
}
</script>
<template>
<LhCalendar v-model="span" selection="range" :panels="2" />
</template>다중 선택
2026년 10월
일월화수목금토
vue
<script setup>
import { ref } from 'vue'
const dates = ref([new Date(2026, 8, 10)])
</script>
<template>
<LhCalendar v-model="dates" selection="multiple" />
</template>vue
<script>
export default {
data() {
return { dates: [new Date(2026, 8, 10)] }
},
}
</script>
<template>
<LhCalendar v-model="dates" selection="multiple" />
</template>선택 가능 범위 제약
범위 제약
2026년 10월
일월화수목금토
vue
<script setup>
import { ref } from 'vue'
// 주의: JS의 월은 0부터 시작합니다. new Date(2026, 8, 1)은 9월 1일입니다
const range = [new Date(2026, 8, 1), new Date(2026, 8, 28)]
const rangeDate = ref(new Date())
</script>
<template>
<LhCalendar v-model="rangeDate" :range="range" />
</template>vue
<script>
export default {
data() {
return {
// 주의: JS의 월은 0부터 시작합니다. new Date(2026, 8, 1)은 9월 1일입니다
range: [new Date(2026, 8, 1), new Date(2026, 8, 28)],
rangeDate: new Date(),
}
},
}
</script>
<template>
<LhCalendar v-model="rangeDate" :range="range" />
</template>input 접기 형태
mode="input"은 상주하는 패널을 입력 상자 안에 넣고 클릭 시 펼쳐 세로 공간을 절약합니다. panels로 펼친 뒤의 월 패널 수를 제어하고, placeholder로 플레이스홀더 텍스트를 지정하며, close-on-select로 선택 후 자동으로 접을지 결정합니다.
input 형태 + 이중 패널
vue
<script setup>
import { ref } from 'vue'
const inputDate = ref(new Date())
</script>
<template>
<LhCalendar
v-model="inputDate"
mode="input"
:panels="2"
placeholder="날짜를 선택하세요"
/>
</template>vue
<script>
export default {
data() {
return { inputDate: new Date() }
},
}
</script>
<template>
<LhCalendar
v-model="inputDate"
mode="input"
:panels="2"
placeholder="날짜를 선택하세요"
/>
</template>선택 후 자동으로 접지 않기
vue
<script setup>
import { ref } from 'vue'
const inputDate2 = ref(new Date())
</script>
<template>
<LhCalendar
v-model="inputDate2"
mode="input"
:close-on-select="false"
placeholder="선택 후 패널을 펼친 상태로 유지"
/>
</template>vue
<script>
export default {
data() {
return { inputDate2: new Date() }
},
}
</script>
<template>
<LhCalendar
v-model="inputDate2"
mode="input"
:close-on-select="false"
placeholder="선택 후 패널을 펼친 상태로 유지"
/>
</template>API
LhCalendar Props
| 속성 | 설명 | 타입 | 기본값 |
|---|---|---|---|
| modelValue | 현재 선택된 날짜(제어형 v-model) | Date | Date[] | — |
| selection | 선택 모드: 단일(기본값) / 기간(시작과 끝 날짜) / 다중 | "single" | "range" | "multiple" | 'single' |
| range | 선택 가능한 날짜 범위 제약 | [Date, Date] | — |
| mode | 표시 형태 | "panel" | "input" | 'panel' |
| panels | 동시에 표시할 월 패널 수(flex 줄바꿈 배치) | number | 1 |
| placeholder | input 모드의 플레이스홀더 텍스트 | string | — |
| closeOnSelect | input 모드에서 선택 후 자동으로 패널을 접을지 여부 | boolean | true |
| sx | sx 빠른 레이아웃 속성 | LhSxProps | — |
Events
| 이벤트 | 설명 | 콜백 매개변수 |
|---|---|---|
| update:modelValue | 선택값이 변경될 때 발생(v-model) | (value: Date | Date[]) |
| change | 선택값이 변경될 때 발생 | (value: Date | Date[]) |
| select | 날짜를 선택할 때 발생(클릭 또는 키보드 내비게이션) | (value: Date) |
슬롯: cell(커스텀 셀), header(헤더).
접근성
- 그리드 의미로
role="grid"(행row, 셀gridcell)를 사용하고, 오늘 날짜에aria-current="date"를 표시합니다 - 방향키로 날짜 포커스를 이동합니다(±1일 / ±7일), Home/End로 행의 양끝, PageUp/Down으로 월 이동 — APG grid pattern에 맞춥니다
- 범위 밖의 날짜는 네이티브
disabled로 상호작용에서 제외합니다
타입 정의
이 컴포넌트가 외부로 내보내는 TypeScript 타입 구조는 다음과 같습니다(packages/components/calendar/src/types.ts와 @lh-ui/share/core/* 소스에서 자동 추출, 각 항목을 펼쳐 전체 정의를 확인하세요. 속성 설명은 위쪽 Props 표를 참고하세요).
LhCalendarMode
ts
/** 표시 형태: panel 상주 패널(기본값) / input 입력 상자 클릭 시 펼쳐지는 접기 패널 */
export type LhCalendarMode = 'panel' | 'input'LhCalendarValue
ts
/** 제어값의 형태는 selection에 따라 변화: 단일 Date / 기간 Date[](길이 2의 시작과 끝) / 다중 Date[].
* [Date, Date] 튜플을 사용하지 않는 이유: SFC 컴파일러가 튜플에서 런타임 타입을 추론하지 못해
* prop 검증 경고가 발생하기 때문입니다 */
export type LhCalendarValue = Date | Date[]LhCalendarProps
ts
export interface LhCalendarProps {
/** 현재 선택(제어형 v-model. 전달하지 않으면 컴포넌트 내부에서 선택 상태를 관리) */
modelValue?: LhCalendarValue
/** 선택 모드: 단일(기본값) / 기간(시작과 끝 날짜) / 다중 */
selection?: LhCalendarSelection
/** 선택 가능한 날짜 범위 제약 */
range?: LhCalendarRange
/** 표시 형태: panel 상주 패널(기본값) / input 입력 상자 클릭 시 펼쳐지는 접기 패널 */
mode?: LhCalendarMode
/** 동시에 표시할 월 패널 수(flex 줄바꿈 배치) */
panels?: number
/** input 모드의 플레이스홀더 텍스트 */
placeholder?: string
/** input 모드에서 선택 후 자동으로 패널을 접을지 여부 */
closeOnSelect?: boolean
/** sx 빠른 레이아웃 속성 */
sx?: LhSxProps
}LhCalendarSelection (@lh-ui/share/core/calendar에서 가져옴)
ts
/** 선택 모드: 단일 / 기간(시작과 끝) / 다중 */
export type LhCalendarSelection = 'single' | 'range' | 'multiple'LhCalendarRange (@lh-ui/share/core/calendar에서 가져옴)
ts
/** 선택 가능한 날짜 범위 제약 */
export type LhCalendarRange = [Date, Date]