react-spectrum
react-spectrum copied to clipboard
Add property format to DateInput to avoid relying on locale for formatting
Provide a general summary of the feature here
Currently in order to enforce a specific date format to the DateInput and DatePicker it is needed a workaround by using a I18nProvider with a locale that suites the wanted format.
๐ค Expected Behavior?
A simpler way to pass the format to the component that is not hacky and gives more flexibility to displaying time.
๐ฏ Current Behavior
<I18nProvider locale="zh-CN">
<DateInput style={{ display: 'flex' }}>
{(segment) => <DateSegment segment={segment} />}
</DateInput>
</I18nProvider>
Which is still not great as I'm using a completely different locale in order to have a close behavior to what I need but still not good as the results is YYYY/mm/dd and not YYYY-MM-DD and also not always 2 digits in the month and day values.
๐ Possible Solution
A prop where the desired format can be passed without needing to override any locale, something like:
<DateInput format="YYYY-MM-DD">
{(segment) => <DateSegment segment={segment} />}
</DateInput>
๐ฆ Context
The current solution is not great because the format still isn't what I need (YYYY-MM-DD) and it is a very hacky solution. Working on an international team it is important to set a common format to the calendars and not rely on users locale for that.
This is somewhat related with https://github.com/adobe/react-spectrum/issues/3986
๐ป Examples
Something similar to https://mui.com/x/react-date-pickers/adapters-locale/#custom-field-format or https://shahabyazdi.github.io/react-multi-date-picker/props/
๐งข Your Company/Team
No response
๐ท Tracking Issue
No response
Perhaps a bit related: https://github.com/adobe/react-spectrum/issues/6342#issuecomment-2387207522. That link describes some of the challenges we had in deciding what locale to even go with if one isn't specified. I'll bring up the possibility of modifying the format of the date via format like you mentioned to the team, but its hard to say in general what a user would expect to see IMO
@LFDanLu thank you for the reply! I think it makes sense for many B2C products to use like it is implemented and have the locale based on the user, but for corporate products sometimes it's quite important to be able to override the user setting to have a common date format for everyone and avoid confusion between colleagues (like 01/03/2024 is March or January? for instance).
The team discussed this today and even if we allowed the reordering of the segments, there is still a bunch of display things that need to be tied to a locale being provided such as formatting within the segments themselves (aka hour format, value formatting, etc)
@LFDanLu got it, thank you for considering it.
Just wanted to chime in to say that our team has a need for exactly this feature as well, so casting another vote for it.
@anarute - if you don't mind me asking, how are you solving this for the time being? The workaround mentioned?
Just wanted to chime in to say that our team has a need for exactly this feature as well, so casting another vote for it.
@anarute - if you don't mind me asking, how are you solving this for the time being? The workaround mentioned?
@mryechkin we are wrapping the component in a I18nProvider and forcing the locale to what we want, for example:
import { I18nProvider } from 'react-aria'
<ReactAriaDatePicker aria-label="Date navigation" onChange={onChange} {...props}>
<StyledGroup>
<I18nProvider locale="en-CA">
<StyledDateInput>
{(segment) => <StyledDateSegment segment={segment} />}
</StyledDateInput>
<StyledButton>
<Calendar20Regular />
</StyledButton>
</I18nProvider>
</StyledGroup>
<Popover>
<Dialog>
<I18nProvider locale="en-US">
<StyledCalendar>
...
</StyledCalendar>
</I18nProvider>
</Dialog>
</Popover>
</ReactAriaDatePicker>
Complete format control is unlikely to be supported in the near-term. We rely deeply on the browser's Intl.DateTimeFormat for date formatting, which does not currently support custom format strings (e.g. YYYY-MM-DD - see here for a thread about why that is: https://github.com/tc39/ecma402/issues/554).
Implementing a custom formatter is a monumental effort to do correctly, with many questions. For example, in what numbering system should the numbers be formatted? Latin only? Based on the locale? Are the separators and other strings translated or do they come directly from the format prop only? If the format string specifies that a segment is textual instead of numeric (e.g. "January" instead of "01"), is this translated and how does the user edit the value? Essentially, what parts of the formatting are and are not based on the locale is unclear.
If you want to force a particular locale, then doing it as suggested above (using I18nProvider) is the correct approach. If you want to customize the format beyond what a locale allows, then there are many many questions to be answered and this is not a simple task at all. Perhaps if Temporal standardizes a JS API to do this (https://github.com/js-temporal/proposal-temporal-v2/issues/5) we could support it, but I think until then this is probably not going to happen.