DateInput
An input field and popup calendar where users enter a date.
The Basics
What it is
DateInput is a field where users enter a date. They can either type the date or select it in the popup calendar.
How it works
- The user clicks or focuses on the DateInput, which makes it active.
- A cursor appears in the input element, and a calendar pops up.
- If the user tabs to the DateInput, the popup calendar doesn’t appear. This optimizes keyboard-based workflows (like data entry), which are disrupted by popups.
- To enter a date, the user can:
- Type the date.
- Click the date in the calendar, using the arrows and dropdowns to navigate the available date range. This automatically closes the popup and fills the input with the selected date.
- When finished, the user navigates away from the DateInput.
When to use
- To ask users to enter a specific date, such as date of birth
When not to use
- To ask users to enter a month and/or year, but not a specific day
- To ask users to enter a date range
What to use instead
Use Select to ask users to enter a month and/or year, but not a specific day.
Use DateRangeInput to pick a range of dates.
How to use
DateInput can be used as a standalone component, but it’s better when used with Form and FormField. Form provides a consistent, responsive layout, and FormField adds features like labels, error message handling, and hint text.
Limiting and disabling dates
By default, DateInput’s popup calendar opens to the current month and has a date range of +/- 5 years from today’s date. You can change this based on date availability. For example:
- Open the popup calendar to a specific month and year when the next available appointment is 2 months from today.
- Disable certain days when the clinic is closed on certain days of the week, or all appointments are fully booked.
- Allow only dates in the past or in the future when users are entering birthdates (past) or booking procedures (future).
- Set a range for the dates in the calendar when users are entering dates for reports on previous activity, like visit notes for the past 2 years.
Use labels and hint text to explain any disabled or restricted dates.
Opening the calendar (click vs. tab)
When users click the DateInput field, the popup calendar opens.
When users navigate to the field using the Tab key, however, the popup calendar does not open. This helps data entry staff and other heavy keyboard users enter data quickly, without interruption.
Keyboard shortcuts
DateInput supports these athenaOne date shortcuts:
t
= today's datet+[# of days]
= a future date: # of days after today (e.g.,t+5
)t-[# of days]
= a past date: # of days before today (e.g.,t-3
)
Style
Design details
Required fields
Forge offers three display options to indicate required form fields. See Form for details.
Spacing and size
The height of this component and the vertical space around it vary according to the form layout (i.e., medium, compact, super-compact). See Form for details.
Placement and hierarchy
No additional information for this component.
Content
Use sentence case for label text (“Date of birth”, not “Date Of Birth”).
DateInput’s default placeholder text uses the standard date format for athenahealth apps: MM-DD-YYYY.
Demos
Coding
Developer tips
DateInput is a thin wrapper around react-datepicker. The Forge package also includes the library date-fns, which contains useful utilities for manipulating JavaScript dates.
DateInput is rendered as an input[type="text"]
to avoid the browser’s default date input UI.
Validation not built in
DateInput doesn’t include internal validation.
Disabled days do get a disabled style in the popup calendar; users can’t select them via click or keyboard navigation in the calendar. However, users can still type a disabled date in the text input field. You need to implement any validation for those dates yourself.
Disabling dates
There are 4 ways to mark disabled dates in DateInput:
- Provide
excludeDates
an array of Date objects. All other dates are enabled. - Provide
includeDates
an array of Date objects. All other dates are disabled. - Provide
filterDate
a function. This function should accept a Date object argument and return a bool ({true}
for enabled,{false}
for disabled). - Use the
minDate
and/ormaxDate
props to set an upper or lower range.
Highlighting days
Like filterDate
, the dayClassname
prop can be given a function that takes a Date argument and returns custom class names for certain days in the calendar picker. You can use this to implement custom styling or behavior for a subset of days.
Starting date
By default, DateInput’s popup calendar opens to the current month. You can override this default behavior by providing a specific date to the openToDate
prop. This opens the calendar to that date’s month. It doesn’t preselect or highlight that exact date. It also doesn’t change the time range shown in the calendar’s year dropdown. To change that time range, set minDate
and maxDate
.
Popup calendar and keyboard navigation
Although the DateInput input field is accessible as a standard text input, the keyboard functionality of the popup calendar is disabled by default. We made this decision to maintain standard arrow key behavior in the text input field.
To re-enable keyboard navigation in the calendar (and disable keyboard navigation in the text input), set the disabledKeyboardNavigation
and preventOpenOnFocus
props to {false}
.
Required fields
Use the required
prop to mark DateInput as required.
Forge offers three options to indicate required form fields. When using Form with this component, set Form’s requiredVariation
prop. See Form for details.
Repository
Implementation links
DateInput directory in Bitbucket
Implementation details
It is strongly recommended to familiarize yourself with the Forge source code. While this documentation is a best effort to document the intent and usage of a component, sometimes some features only become clear when looking at the source code. Also, looking at Forge's source code may help identify and fix bugs in either your application or Forge itself.
Storybook files
Forge maintains at least one storybook file per component. While the primary audience for these files is typically the Forge team, these storybook files may cover usages of the component not covered by a demo. The storybook for the latest version of forge can be found at go/forge-storybook-lts.
Testing library
Forge strongly encourages using testing-library to write tests for your application.
"The more your tests resemble the way your software is used, the more confidence they can give you."
If you're having trouble testing a Forge component using testing-library, it would be a good idea to see how Forge tests its own components. For the most part, Forge tries to use screen.getByRole as much as it can, as that API provides the best feedback on a11y compliance. Forge discourages the use of document.querySelector and screen.getByTestId as both APIs encourage using implementation details to test your component, and discourage adding roles to your component.
With that being said, many of Forge's components were not built with accessibility in mind. These components do break the recommendations listed above.
Import statements
In Nimbus applications
athenaOne serves the Forge bundle independently from your application's bundle. Importing Forge components directly from '@athena/forge'
takes advantage of this feature.
import { DateInput } from '@athena/forge'
In standalone applications
Importing components using the exact path to the module takes advantage of webpack's tree shaking feature. Webpack will include only that module and its dependencies.
import DateInput from '@athena/forge/DateInput';
To use this import guidance, Typescript applications must use typescript >= 4.7.3
, and should add this setting to their tsconfig.json file:
{"compilerOptions": {"moduleResolution": "Node16",}}
If this setting doesn't work for your application, use this import statement instead:
import DateInput from '@athena/forge/dist/DateInput';