A single-date calendar for selecting dates with month navigation, locale support, and customizable day cells.
import { Calendar } from 'heroui-native-pro' ;
< Calendar >
< Calendar.Header >
< Calendar.Heading />
< Calendar.NavButton slot = "previous" />
< Calendar.NavButton slot = "next" />
</ Calendar.Header >
< Calendar.Grid >
< Calendar.GridHeader >
{( day ) => < Calendar.HeaderCell day = {day} />}
</ Calendar.GridHeader >
< Calendar.GridBody >
{( date ) => < Calendar.Cell date = {date} />}
</ Calendar.GridBody >
</ Calendar.Grid >
</ Calendar >
< Calendar >
< Calendar.Header >
< Calendar.YearPickerTrigger >
< Calendar.YearPickerTriggerHeading />
< Calendar.YearPickerTriggerIndicator />
</ Calendar.YearPickerTrigger >
< Calendar.NavButton slot = "previous" />
< Calendar.NavButton slot = "next" />
</ Calendar.Header >
< Calendar.Grid >
< Calendar.GridHeader >
{( day ) => < Calendar.HeaderCell day = {day} />}
</ Calendar.GridHeader >
< Calendar.GridBody >
{( date ) => < Calendar.Cell date = {date} />}
</ Calendar.GridBody >
</ Calendar.Grid >
< Calendar.YearPickerGrid >
< Calendar.YearPickerGridBody >
{( renderProps ) => (
< Calendar.YearPickerCell
year = {renderProps.year}
isSelected = {renderProps.isSelected}
/>
)}
</ Calendar.YearPickerGridBody >
</ Calendar.YearPickerGrid >
</ Calendar >
Calendar : Root container that manages single-date selection state, locale, and animation settings. Supports controlled and uncontrolled modes with min/max constraints and date unavailability filtering.
Calendar.Header : Toolbar row for navigation controls and the month/year title.
Calendar.Heading : Month/year label text. The primitive computes the heading string automatically when children are omitted.
Calendar.NavButton : Previous or next month navigation button. Renders a default chevron icon using the theme accent color; override via iconProps or pass custom children.
Calendar.Grid : Month grid container that provides internal grid context to the header and body.
Calendar.GridHeader : Weekday labels row. Requires a render function (day: string) => ReactElement as children.
Calendar.GridBody : Day cells matrix. Requires a render function (date: CalendarDate) => ReactElement as children.
Calendar.HeaderCell : Single weekday header cell. Stringifiable children are wrapped in HeaderCellLabel; pass day when omitting children.
Calendar.HeaderCellLabel : Text slot for a weekday header cell label.
Calendar.Cell : Selectable day cell. By default renders CellBody with CellLabel inside. Pass a render function as children to customize the cell content.
Calendar.CellBody : Inner rounded region of a day cell with press scale animation. Pass cellRenderProps for data attribute selectors.
Calendar.CellLabel : Day number label. Pass cellRenderProps for data attribute selectors.
Calendar.CellIndicator : Dot marker under a day cell (e.g. for events). Pass cellRenderProps for data-selected styling.
Calendar.YearPickerTrigger : Pressable trigger that replaces Heading to toggle the year picker overlay.
Calendar.YearPickerTriggerHeading : Month/year label text inside the year picker trigger.
Calendar.YearPickerTriggerIndicator : Animated chevron icon indicating the year picker open state.
Calendar.YearPickerGrid : Overlay container positioned over the month grid when the year picker is open.
Calendar.YearPickerGridBody : Scrollable list of year cells inside the year picker grid.
Calendar.YearPickerCell : Pressable year cell that selects a year and closes the picker.
The Calendar component uses compound parts to build a date picker. GridHeader and GridBody require render function children.
< Calendar accessibilityLabel = "Event date" >
< Calendar.Header >
< Calendar.Heading />
< Calendar.NavButton slot = "previous" />
< Calendar.NavButton slot = "next" />
</ Calendar.Header >
< Calendar.Grid >
< Calendar.GridHeader >
{( day ) => < Calendar.HeaderCell day = {day} />}
</ Calendar.GridHeader >
< Calendar.GridBody >
{( date ) => < Calendar.Cell date = {date} />}
</ Calendar.GridBody >
</ Calendar.Grid >
</ Calendar >
Set an initial selected date with defaultValue using @internationalized/date.
< Calendar defaultValue = { parseDate ( '2026-06-19' )}>
< Calendar.Header >
< Calendar.Heading />
< Calendar.NavButton slot = "previous" />
< Calendar.NavButton slot = "next" />
</ Calendar.Header >
< Calendar.Grid >
< Calendar.GridHeader >
{( day ) => < Calendar.HeaderCell day = {day} />}
</ Calendar.GridHeader >
< Calendar.GridBody >
{( date ) => < Calendar.Cell date = {date} />}
</ Calendar.GridBody >
</ Calendar.Grid >
</ Calendar >
Use value and onChange to control the selected date externally.
const [ date , setDate ] = useState ( today ( getLocalTimeZone ()));
< Calendar value = {date} onChange = {setDate}>
< Calendar.Header >
< Calendar.Heading />
< Calendar.NavButton slot = "previous" />
< Calendar.NavButton slot = "next" />
</ Calendar.Header >
< Calendar.Grid >
< Calendar.GridHeader >
{( day ) => < Calendar.HeaderCell day = {day} />}
</ Calendar.GridHeader >
< Calendar.GridBody >
{( date ) => < Calendar.Cell date = {date} />}
</ Calendar.GridBody >
</ Calendar.Grid >
</ Calendar >;
Restrict navigation and selection to a date range using minValue and maxValue.
const now = today ( getLocalTimeZone ());
< Calendar minValue = {now} maxValue = {now. add ({ months: 2 })}>
< Calendar.Header >
< Calendar.Heading />
< Calendar.NavButton slot = "previous" />
< Calendar.NavButton slot = "next" />
</ Calendar.Header >
< Calendar.Grid >
< Calendar.GridHeader >
{( day ) => < Calendar.HeaderCell day = {day} />}
</ Calendar.GridHeader >
< Calendar.GridBody >
{( date ) => < Calendar.Cell date = {date} />}
</ Calendar.GridBody >
</ Calendar.Grid >
</ Calendar >;
Mark specific dates as unavailable using the isDateUnavailable callback.
const isDateUnavailable = ( date : DateValue ) => isWeekend (date, 'en-US' );
< Calendar isDateUnavailable = {isDateUnavailable}>
< Calendar.Header >
< Calendar.Heading />
< Calendar.NavButton slot = "previous" />
< Calendar.NavButton slot = "next" />
</ Calendar.Header >
< Calendar.Grid >
< Calendar.GridHeader >
{( day ) => < Calendar.HeaderCell day = {day} />}
</ Calendar.GridHeader >
< Calendar.GridBody >
{( date ) => < Calendar.Cell date = {date} />}
</ Calendar.GridBody >
</ Calendar.Grid >
</ Calendar >;
Use a render function on Calendar.Cell to add dot indicators under specific dates.
< Calendar.GridBody >
{( date ) => (
< Calendar.Cell date = {date}>
{( renderProps ) => (
< Calendar.CellBody cellRenderProps = {renderProps}>
< Calendar.CellLabel cellRenderProps = {renderProps}>
{renderProps.formattedDate}
</ Calendar.CellLabel >
{datesWithEvents. includes (date.day) && (
< Calendar.CellIndicator cellRenderProps = {renderProps} />
)}
</ Calendar.CellBody >
)}
</ Calendar.Cell >
)}
</ Calendar.GridBody >
Pass a BCP 47 locale string to render the calendar in a different language and calendar system.
< Calendar locale = "hi-IN-u-ca-indian" >
< Calendar.Header >
< Calendar.Heading />
< Calendar.NavButton slot = "previous" />
< Calendar.NavButton slot = "next" />
</ Calendar.Header >
< Calendar.Grid >
< Calendar.GridHeader >
{( day ) => < Calendar.HeaderCell day = {day} />}
</ Calendar.GridHeader >
< Calendar.GridBody >
{( date ) => < Calendar.Cell date = {date} />}
</ Calendar.GridBody >
</ Calendar.Grid >
</ Calendar >
Disable the entire calendar and all navigation controls.
< Calendar isDisabled >
< Calendar.Header >
< Calendar.Heading />
< Calendar.NavButton slot = "previous" />
< Calendar.NavButton slot = "next" />
</ Calendar.Header >
< Calendar.Grid >
< Calendar.GridHeader >
{( day ) => < Calendar.HeaderCell day = {day} />}
</ Calendar.GridHeader >
< Calendar.GridBody >
{( date ) => < Calendar.Cell date = {date} />}
</ Calendar.GridBody >
</ Calendar.Grid >
</ Calendar >
Add a year picker overlay by replacing Heading with YearPickerTrigger and adding a YearPickerGrid inside the root.
< Calendar >
< Calendar.Header >
< Calendar.YearPickerTrigger >
< Calendar.YearPickerTriggerHeading />
< Calendar.YearPickerTriggerIndicator />
</ Calendar.YearPickerTrigger >
< Calendar.NavButton slot = "previous" />
< Calendar.NavButton slot = "next" />
</ Calendar.Header >
< Calendar.Grid >
< Calendar.GridHeader >
{( day ) => < Calendar.HeaderCell day = {day} />}
</ Calendar.GridHeader >
< Calendar.GridBody >
{( date ) => < Calendar.Cell date = {date} />}
</ Calendar.GridBody >
</ Calendar.Grid >
< Calendar.YearPickerGrid >
< Calendar.YearPickerGridBody >
{( renderProps ) => (
< Calendar.YearPickerCell
year = {renderProps.year}
isSelected = {renderProps.isSelected}
/>
)}
</ Calendar.YearPickerGridBody >
</ Calendar.YearPickerGrid >
</ Calendar >
import {
getLocalTimeZone,
isToday,
parseDate,
today,
type DateValue,
} from '@internationalized/date' ;
import { Calendar } from 'heroui-native-pro' ;
import { useState } from 'react' ;
import { View } from 'react-native' ;
const datesWithEvents = [ 3 , 7 , 12 , 15 , 21 , 28 ];
export default function CalendarExample () {
const [ date , setDate ] = useState < DateValue >( parseDate ( '2026-06-19' ));
return (
< View className = "flex-1 justify-center px-5" >
< Calendar value = {date} onChange = {setDate} accessibilityLabel = "Event date" >
< Calendar.Header >
< Calendar.Heading />
< Calendar.NavButton slot = "previous" />
< Calendar.NavButton slot = "next" />
</ Calendar.Header >
< Calendar.Grid >
< Calendar.GridHeader >
{( day ) => < Calendar.HeaderCell >{day}</ Calendar.HeaderCell >}
</ Calendar.GridHeader >
< Calendar.GridBody >
{( date ) => (
< Calendar.Cell date = {date}>
{( renderProps ) => (
< Calendar.CellBody cellRenderProps = {renderProps}>
< Calendar.CellLabel cellRenderProps = {renderProps}>
{renderProps.formattedDate}
</ Calendar.CellLabel >
{( isToday (date, getLocalTimeZone ()) ||
datesWithEvents. includes (date.day)) && (
< Calendar.CellIndicator cellRenderProps = {renderProps} />
)}
</ Calendar.CellBody >
)}
</ Calendar.Cell >
)}
</ Calendar.GridBody >
</ Calendar.Grid >
</ Calendar >
</ View >
);
}
prop type default description childrenReact.ReactNode | ((props: { state: CalendarState }) => React.ReactNode)- Calendar content or render function receiving calendar state valueDateValue | null- Controlled selected date defaultValueDateValue | null- Default selected date for uncontrolled usage minValueDateValue | null- Minimum selectable date; disables earlier dates and navigation maxValueDateValue | null- Maximum selectable date; disables later dates and navigation isDateUnavailable(date: DateValue) => boolean- Callback to mark specific dates as unavailable isDisabledbooleanfalseWhether the entire calendar is disabled isReadOnlybooleanfalseWhether the calendar value is immutable isInvalidboolean- Whether the current selection is invalid firstDayOfWeek'sun' | 'mon' | 'tue' | 'wed' | 'thu' | 'fri' | 'sat'- Override the first day of the week localestring- BCP 47 locale; defaults to the environment locale isYearPickerOpenboolean- Controlled open state for the year picker overlay defaultYearPickerOpenbooleanfalseInitial open state for the year picker in uncontrolled mode classNamestring- Additional CSS classes for the root container animationAnimationRootDisableAll- Animation configuration for the calendar subtree onChange(value: MappedDateValue<DateValue>) => void- Handler called when the selected date changes onYearPickerOpenChange(isOpen: boolean) => void- Handler called when the year picker open state changes ...ViewPropsViewProps- All standard React Native View props are supported
Animation configuration for the Calendar root. Can be:
"disable-all": Disable all animations including children (cascades down)
undefined: Use default animations
prop type default description childrenReact.ReactNode- Header content (Heading, NavButtons, etc.) classNamestring- Additional CSS classes for the header row container ...ViewPropsViewProps- All standard React Native View props are supported
prop type default description childrenReact.ReactNode- Custom heading text; auto-computed month/year when omitted classNamestring- Additional CSS classes for the heading text ...TextPropsTextProps- All standard React Native Text props are supported
prop type default description childrenReact.ReactNode- Custom icon content; replaces the default chevron when provided slot'previous' | 'next'- Navigation direction; determines which chevron icon is rendered isDisabledboolean- Merged with calendar isDisabled and range boundary state classNamestring- Additional CSS classes for the pressable iconPropsCalendarNavButtonIconProps- Overrides for the built-in chevron; ignored with custom children ...PressablePropsPressableProps- All standard React Native Pressable props are supported
prop type default description sizenumber18Icon size in logical pixels colorstringTheme accent Icon stroke/fill color
prop type default description childrenReact.ReactNode- Grid content (GridHeader, GridBody) offsetDateDuration- Offset from the visible range start for multi-month grids weekdayStyle'narrow' | 'short' | 'long'- Weekday label format classNamestring- Additional CSS classes for the grid container ...ViewPropsViewProps- All standard React Native View props are supported
prop type default description children(day: string) => React.ReactElement- Render function called for each weekday label (required) classNamestring- Additional CSS classes for the weekday row wrapper ...ViewPropsViewProps- All standard React Native View props are supported
prop type default description children(date: CalendarDate) => React.ReactElement- Render function called for each day in the month (required) classNamestring- Additional CSS classes for the grid body ...ViewPropsViewProps- All standard React Native View props are supported
prop type default description childrenReact.ReactNode- Custom cell content; stringifiable children are wrapped in HeaderCellLabel daystring- Weekday label string from GridHeader's render callback; used when children is omitted classNamestring- Additional CSS classes for the header cell container ...ViewPropsViewProps- All standard React Native View props are supported
prop type default description childrenReact.ReactNode- Weekday label text classNamestring- Additional CSS classes for the label text ...TextPropsTextProps- All standard React Native Text props are supported
prop type default description dateCalendarDate- The calendar date this cell represents (required) childrenReact.ReactNode | ((renderProps: CalendarCellRenderProps) => React.ReactNode)- Custom cell content; defaults to CellBody with CellLabel inside isDisabledboolean- Merged with calendar isDisabled and cell-specific disabled state classNamestring- Additional CSS classes for the day cell pressable ...PressablePropsPressableProps- All standard React Native Pressable props are supported
Render props received by the Calendar.Cell children render function.
property type description dateCalendarDateThe calendar date for this cell formattedDatestringLocale-formatted day number string isSelectedbooleanWhether this date is currently selected isTodaybooleanWhether this date is today isDisabledbooleanWhether this date is disabled isUnavailablebooleanWhether this date is unavailable via isDateUnavailable isOutsideMonthbooleanWhether this date is outside the currently visible month isFocusedbooleanWhether this date is currently focused isInvalidbooleanWhether this date is invalid per minValue/maxValue constraints isPressedbooleanWhether the day cell pressable is in a pressed state isRangeStartbooleanFirst day of the highlighted range (range calendar only) isRangeEndbooleanLast day of the highlighted range (range calendar only) isRangeFilledbooleanWhether the range spans more than one day (range calendar only) isRangeMiddlebooleanStrictly inside the range, not start or end (range calendar only) isRangeMiddleRowStartbooleanRange middle cell at the start of a row (range calendar only) isRangeMiddleRowEndbooleanRange middle cell at the end of a row (range calendar only)
prop type default description childrenReact.ReactNode- Body content (typically CellLabel and optional CellIndicator) cellRenderPropsCalendarCellRenderProps- Render props from Calendar.Cell's children callback; drives data-* selectors isAnimatedStyleActivebooleantrueWhether animated scale styles are applied; set false for custom logic classNamestring- Additional CSS classes for the cell body container animationCalendarCellBodyAnimation- Press scale animation configuration ...ViewPropsViewProps- All standard React Native View props are supported
attribute values description data-todaybooleanWhether the date is today data-outside-monthbooleanWhether the date is outside the visible month data-unavailablebooleanWhether the date is unavailable data-disabledbooleanWhether the date is disabled data-focusedbooleanWhether the date is focused data-invalidbooleanWhether the date is invalid data-selectedbooleanWhether the date is selected data-pressedbooleanWhether the cell is pressed data-range-startbooleanFirst day of a range (range calendar only) data-range-endbooleanLast day of a range (range calendar only) data-range-filledbooleanRange spans multiple days (range calendar only) data-range-middlebooleanInside the range, not start/end (range only) data-range-middle-row-startbooleanRange middle at row start (range calendar only) data-range-middle-row-endbooleanRange middle at row end (range calendar only) data-disabled-not-outside-monthbooleanDisabled but within the visible month
Animation configuration for Calendar.CellBody press feedback. Can be:
false or "disabled": Disable press animation
undefined: Use default animation
object: Custom animation configuration
prop type default description scale.value[number, number][1, 0.9]Scale values [unpressed, pressed] scale.timingConfigWithTimingConfig{ duration: 120 }Animation timing configuration
prop type default description childrenReact.ReactNode- Label text (usually the day number) cellRenderPropsCalendarCellRenderProps- Render props from Calendar.Cell's children callback; drives data-* selectors classNamestring- Additional CSS classes for the label text ...TextPropsTextProps- All standard React Native Text props are supported
Same data attributes as Calendar.CellBody. See above.
prop type default description cellRenderPropsCalendarCellRenderProps- Render props from Calendar.Cell's children callback; drives data-* selectors classNamestring- Additional CSS classes for the indicator dot container ...ViewPropsViewProps- All standard React Native View props are supported
Same data attributes as Calendar.CellBody. See above.
prop type default description childrenReact.ReactNode | ((values: YearPickerTriggerRenderProps) => React.ReactNode)- Trigger content or render function ...PressablePropsPressableProps- All standard React Native Pressable props are supported
property type description isOpenbooleanWhether the year picker is open monthYearstringFormatted month/year heading string toggle() => voidToggle the year picker open state
prop type default description childrenReact.ReactNode | ((values: YearPickerTriggerRenderProps) => React.ReactNode)- Heading text or render function; auto-computed when omitted ...TextPropsTextProps- All standard React Native Text props are supported
prop type default description childrenReact.ReactNode | ((values: YearPickerTriggerRenderProps) => React.ReactNode)- Custom indicator content or render function iconProps{ size?: number; color?: string }- Overrides for the default chevron icon isAnimatedStyleActivebooleantrueWhether animated rotation styles are applied animationYearPickerIndicatorAnimation- Rotation animation configuration ...ViewPropsViewProps- All standard React Native View props are supported
Animation configuration for the year picker trigger chevron rotation. Can be:
false or "disabled": Disable rotation animation
undefined: Use default animation
object: Custom animation configuration
prop type default description rotation.value[number, number][0, 90]Rotation degrees [closed, open] rotation.springConfigWithSpringConfigDefault spring Spring configuration for the rotation
prop type default description childrenReact.ReactNode- Grid content (YearPickerGridBody) isAnimatedStyleActivebooleantrueWhether animated opacity styles are applied animationYearPickerGridAnimation- Opacity animation configuration ...ViewPropsViewProps- All standard React Native View props are supported
Animation configuration for the year picker grid overlay. Can be:
false or "disabled": Disable opacity animation
undefined: Use default animation
object: Custom animation configuration
prop type default description opacity.value[number, number][0, 1]Opacity values [closed, open] opacity.timingConfigWithTimingConfig{ duration: 200 }Timing configuration for the opacity
prop type default description children(values: YearPickerCellRenderProps) => React.ReactNode- Render function called for each year ...FlatListPropsFlatListProps<number>- FlatList props except data, renderItem, keyExtractor, numColumns, and columnWrapperStyle
property type description yearnumberThe year number formattedYearstringLocale-formatted year string isSelectedbooleanWhether this year matches the selection isCurrentYearbooleanWhether this year is the current year isOpenbooleanWhether the year picker is open selectYear() => voidSelect this year and close the picker
prop type default description yearnumber- The year this cell represents (required) isSelectedboolean- Whether this year is selected (required) childrenReact.ReactNode | ((values: YearPickerCellRenderProps) => React.ReactNode)- Custom cell content or render function ...PressablePropsPressableProps- All standard React Native Pressable props are supported
Hook to access the calendar state context. Must be used within a Calendar component.
import { useCalendar } from 'heroui-native-pro' ;
const state = useCalendar ();
property type description valueCalendarDate | nullCurrently selected date setValue(value: CalendarDate | null) => voidSet the selected date visibleRangeRangeValue<CalendarDate>The date range currently visible in the calendar focusedDateCalendarDateCurrently focused date setFocusedDate(value: CalendarDate) => voidSet the focused date isDisabledbooleanWhether the calendar is disabled isReadOnlybooleanWhether the calendar is read-only isValueInvalidbooleanWhether the current value is invalid timeZonestringTime zone of displayed dates minValueDateValue | null | undefinedMinimum allowed date maxValueDateValue | null | undefinedMaximum allowed date focusNextPage() => voidNavigate to the next month focusPreviousPage() => voidNavigate to the previous month selectFocusedDate() => voidSelect the currently focused date selectDate(date: CalendarDate) => voidSelect a specific date isSelected(date: CalendarDate) => booleanCheck if a date is selected isInvalid(date: CalendarDate) => booleanCheck if a date is invalid isCellDisabled(date: CalendarDate) => booleanCheck if a date cell is disabled isCellUnavailable(date: CalendarDate) => booleanCheck if a date cell is unavailable isCellFocused(date: CalendarDate) => booleanCheck if a date cell is focused getDatesInWeek(weekIndex: number, startDate?: CalendarDate) => Array<CalendarDate | null>Get dates for a week row