@mui/x-date-pickers 6.0.1 → 6.0.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (69) hide show
  1. package/AdapterDateFns/index.js +1 -0
  2. package/AdapterDayjs/index.js +1 -0
  3. package/AdapterMoment/index.js +1 -0
  4. package/AdapterMomentHijri/index.d.ts +1 -1
  5. package/CHANGELOG.md +58 -5
  6. package/index.js +1 -1
  7. package/internals/components/PickersArrowSwitcher/PickersArrowSwitcher.js +8 -2
  8. package/internals/components/PickersModalDialog.d.ts +2 -2
  9. package/internals/components/PickersPopper.d.ts +1 -1
  10. package/internals/hooks/useField/useField.js +11 -5
  11. package/internals/hooks/useField/useField.types.d.ts +13 -8
  12. package/internals/hooks/useField/useField.utils.d.ts +3 -3
  13. package/internals/hooks/useField/useField.utils.js +63 -35
  14. package/internals/hooks/useField/useFieldCharacterEditing.js +4 -9
  15. package/internals/hooks/useField/useFieldState.js +43 -37
  16. package/internals/utils/valueManagers.js +11 -7
  17. package/legacy/AdapterDateFns/index.js +1 -0
  18. package/legacy/AdapterDayjs/index.js +1 -0
  19. package/legacy/AdapterMoment/index.js +1 -0
  20. package/legacy/index.js +1 -1
  21. package/legacy/internals/components/PickersArrowSwitcher/PickersArrowSwitcher.js +8 -2
  22. package/legacy/internals/hooks/useField/useField.js +11 -5
  23. package/legacy/internals/hooks/useField/useField.utils.js +64 -36
  24. package/legacy/internals/hooks/useField/useFieldCharacterEditing.js +4 -9
  25. package/legacy/internals/hooks/useField/useFieldState.js +45 -39
  26. package/legacy/internals/utils/valueManagers.js +4 -0
  27. package/legacy/locales/deDE.js +8 -5
  28. package/legacy/locales/frFR.js +30 -15
  29. package/legacy/locales/heIL.js +71 -0
  30. package/legacy/locales/index.js +1 -0
  31. package/legacy/tests/describeValue/testPickerOpenCloseLifeCycle.js +20 -1
  32. package/locales/deDE.js +4 -5
  33. package/locales/frFR.js +12 -15
  34. package/locales/heIL.d.ts +51 -0
  35. package/locales/heIL.js +57 -0
  36. package/locales/index.d.ts +1 -0
  37. package/locales/index.js +1 -0
  38. package/modern/AdapterDateFns/index.js +1 -0
  39. package/modern/AdapterDayjs/index.js +1 -0
  40. package/modern/AdapterMoment/index.js +1 -0
  41. package/modern/index.js +1 -1
  42. package/modern/internals/components/PickersArrowSwitcher/PickersArrowSwitcher.js +8 -2
  43. package/modern/internals/hooks/useField/useField.js +11 -5
  44. package/modern/internals/hooks/useField/useField.utils.js +63 -35
  45. package/modern/internals/hooks/useField/useFieldCharacterEditing.js +4 -9
  46. package/modern/internals/hooks/useField/useFieldState.js +43 -37
  47. package/modern/internals/utils/valueManagers.js +11 -7
  48. package/modern/locales/deDE.js +4 -5
  49. package/modern/locales/frFR.js +12 -15
  50. package/modern/locales/heIL.js +57 -0
  51. package/modern/locales/index.js +1 -0
  52. package/modern/tests/describeValue/testPickerOpenCloseLifeCycle.js +20 -1
  53. package/node/AdapterDateFns/index.js +1 -0
  54. package/node/AdapterDayjs/index.js +1 -0
  55. package/node/AdapterMoment/index.js +1 -0
  56. package/node/index.js +1 -1
  57. package/node/internals/components/PickersArrowSwitcher/PickersArrowSwitcher.js +8 -2
  58. package/node/internals/hooks/useField/useField.js +11 -5
  59. package/node/internals/hooks/useField/useField.utils.js +66 -38
  60. package/node/internals/hooks/useField/useFieldCharacterEditing.js +3 -8
  61. package/node/internals/hooks/useField/useFieldState.js +43 -37
  62. package/node/internals/utils/valueManagers.js +11 -7
  63. package/node/locales/deDE.js +4 -5
  64. package/node/locales/frFR.js +12 -15
  65. package/node/locales/heIL.js +64 -0
  66. package/node/locales/index.js +11 -0
  67. package/node/tests/describeValue/testPickerOpenCloseLifeCycle.js +19 -0
  68. package/package.json +2 -2
  69. package/tests/describeValue/testPickerOpenCloseLifeCycle.js +20 -1
@@ -31,6 +31,7 @@ const formatTokenMap = {
31
31
  // Day of the month
32
32
  d: 'day',
33
33
  dd: 'day',
34
+ do: 'day',
34
35
  // Day of the week
35
36
  E: {
36
37
  sectionType: 'weekDay',
@@ -22,6 +22,7 @@ const formatTokenMap = {
22
22
  // Day of the month
23
23
  D: 'day',
24
24
  DD: 'day',
25
+ Do: 'day',
25
26
  // Day of the week
26
27
  d: 'weekDay',
27
28
  dd: {
@@ -21,6 +21,7 @@ const formatTokenMap = {
21
21
  // Day of the month
22
22
  D: 'day',
23
23
  DD: 'day',
24
+ Do: 'day',
24
25
  // Day of the week
25
26
  E: 'weekDay',
26
27
  e: 'weekDay',
@@ -14,5 +14,5 @@ export declare class AdapterMomentHijri extends BaseAdapterMomentHijri implement
14
14
  */
15
15
  expandFormat: (format: string) => string;
16
16
  getFormatHelperText: (format: string) => string;
17
- getWeekNumber: (date: defaultMoment.Moment) => any;
17
+ getWeekNumber: (date: defaultMoment.Moment) => number;
18
18
  }
package/CHANGELOG.md CHANGED
@@ -3,6 +3,59 @@
3
3
  All notable changes to this project will be documented in this file.
4
4
  See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
5
5
 
6
+ ## 6.0.2
7
+
8
+ _Mar 16, 2023_
9
+
10
+ We'd like to offer a big thanks to the 10 contributors who made this release possible. Here are some highlights ✨:
11
+
12
+ - 🚀 Fire `onChange` when filling a partial date (#8082) @flaviendelangle
13
+ - 🎁 Support date format like `1st` (`do`) (#8188) @flaviendelangle
14
+ - 🌍 Add Hebrew (he-IL) locale (#8222) @ylarom
15
+ - 🌍 Improve Brazilian Portuguese (pt-BR), German (de-DE), and French (fr-FR) locales
16
+ - 📚 Documentation improvements
17
+ - 🐞 Bugfixes
18
+
19
+ ### `@mui/x-data-grid@v6.0.2` / `@mui/x-data-grid-pro@v6.0.2` / `@mui/x-data-grid-premium@v6.0.2`
20
+
21
+ #### Changes
22
+
23
+ - [DataGrid] Fix <kbd>Space</kbd> triggering edit mode (#8180) @m4theushw
24
+ - [DataGrid] Remove warning when adding a custom column type (#8227) @m4theushw
25
+ - [l10n] Improve Brazilian Portuguese (pt-BR) locale (#8198) @JoaoSerafim3001
26
+
27
+ ### `@mui/x-date-pickers@v6.0.2` / `@mui/x-date-pickers-pro@v6.0.2`
28
+
29
+ #### Changes
30
+
31
+ - [l10n] Add Hebrew (he-IL) locale (#8222) @ylarom
32
+ - [l10n] Improve German (de-DE) locale (#8204) @sebkasanzew
33
+ - [l10n] Improve French (fr-FR) locale (#8229) @marvinroger
34
+ - [DateRangePicker] Allow overriding `slotProps.textField` (#8201) @LukasTy
35
+ - [fields] Fire `onChange` when filling a partial date (#8082) @flaviendelangle
36
+ - [fields] Fix editing in shadow dom (#8254) @flaviendelangle
37
+ - [fields] Remove the duplicated warning about invalid adapter (#8187) @flaviendelangle
38
+ - [fields] Support date format like `1st` (`do`) (#8188) @flaviendelangle
39
+ - [pickers] Fix to avoid selecting sections on mobile picker field (#8228) @LukasTy
40
+ - [pickers] Inherit previous and next icons size from their parent button (#8218) @flaviendelangle
41
+
42
+ ### Docs
43
+
44
+ - [docs] Add a warning in the migration guide for people re-enabling the clock on desktop (#8184) @flaviendelangle
45
+ - [docs] Add a warning for `luxon` macro tokens (#8245) @flaviendelangle
46
+ - [docs] Complete pickers customization pages (#8066) @alexfauquette
47
+ - [docs] Fix 301 redirection @oliviertassinari
48
+ - [docs] Fix 404 links to customization Material UI APIs (#8200) @oliviertassinari
49
+ - [docs] Fix `moment-hijri` demo (#8255) @LukasTy
50
+ - [docs] Improve migration diff (#8240) @oliviertassinari
51
+ - [docs] Change **What's new** page url to point to announcement blog post (#8186) @joserodolfofreitas
52
+ - [docs] Resolve 301 in changelog @oliviertassinari
53
+
54
+ ### Core
55
+
56
+ - [core] Regen api docs (#8220) @flaviendelangle
57
+ - [core] Remove duplicated `/` (#8223) @alexfauquette
58
+
6
59
  ## 6.0.1
7
60
 
8
61
  _Mar 9, 2023_
@@ -1025,7 +1078,7 @@ We'd like to offer a big thanks to the 6 contributors who made this release poss
1025
1078
  <DataGridPremium unstable_cellSelection />
1026
1079
  ```
1027
1080
 
1028
- See [the documentation](https://mui.com/x/react-data-grid/selection/#cell-selection) for more information
1081
+ See [the documentation](https://mui.com/x/react-data-grid/cell-selection/) for more information
1029
1082
 
1030
1083
  - 🌍 Support the Right To Left orientation on the fields components
1031
1084
  - 📚 Documentation improvements
@@ -3082,7 +3135,7 @@ _Sep 2, 2022_
3082
3135
 
3083
3136
  🎉 We are excited to finally introduce a stable release (v5.0.0) for the `@mui/x-date-pickers` and `@mui/x-date-pickers-pro` packages!
3084
3137
 
3085
- If you are still using picker components from the `lab`, take a look at the [migration guide](https://mui.com/x/react-date-pickers/migration-lab/).
3138
+ If you are still using picker components from the `lab`, take a look at the [migration guide](https://mui.com/x/migration/migration-pickers-lab/).
3086
3139
 
3087
3140
  We'd like to offer a big thanks to the 9 contributors who made this release possible. Here are some highlights ✨:
3088
3141
 
@@ -4133,7 +4186,7 @@ We'd like to offer a big thanks to the 7 contributors who made this release poss
4133
4186
 
4134
4187
  Date and time picker components have been moved to the MUI X repository.
4135
4188
  They are now accessible in their own packages: `@mui/x-date-pickers` and `@mui/x-date-pickers-pro`.
4136
- For more information, you can read the [blog article](https://mui.com/blog/lab-date-pickers-to-mui-x/) and the [migration guide](https://mui.com/x/react-date-pickers/migration-lab/).
4189
+ For more information, you can read the [blog article](https://mui.com/blog/lab-date-pickers-to-mui-x/) and the [migration guide](https://mui.com/x/migration/migration-pickers-lab/).
4137
4190
 
4138
4191
  - 📝 Add `onProcessRowUpdateError` prop to simplify error management in edit mode (#4267) @m4theushw
4139
4192
  - ✨ Add generic typing to `GridColDef` and derived interfaces (#4064) @flaviendelangle
@@ -6781,7 +6834,7 @@ Big thanks to the 11 contributors who made this release possible. Here are some
6781
6834
  - 💅 Add `columnHeader`, `row` and `cell` to the `classes` prop (#1660) @DanailH
6782
6835
  - ✅ Add the `isRowSelectable` prop to disable selection on certain rows (#1659) @m4theushw
6783
6836
 
6784
- See the documentation for [more details](https://mui.com/x/react-data-grid/selection/#disable-selection-on-certain-rows).
6837
+ See the documentation for [more details](https://v4.mui.com/components/data-grid/selection/#disable-selection-on-certain-rows).
6785
6838
 
6786
6839
  - ⚡️ Add new icon slot to be displayed when the column is unsorted (#1415) @m4theushw
6787
6840
  - ⚙ Improve consistency of the API to prepare for the first beta release
@@ -7309,7 +7362,7 @@ Big thanks to the 4 contributors who made this release possible. Here are some h
7309
7362
  - 📍 Add support for default locales (#983) @DanailH
7310
7363
  We have built the infrastructure to support around 100 [default locales](https://mui.com/x/react-data-grid/localization/#supported-locales). If you have localized the data grid in your application. Please do consider contributing new translations back to Material UI by opening a pull request.
7311
7364
  - 🎁 Add new `selectionModel` prop (#986) @dtassone
7312
- The prop can be used to control the selected rows in the data grid. [See the docs](https://mui.com/x/react-data-grid/selection/#controlled-selection).
7365
+ The prop can be used to control the selected rows in the data grid. [See the docs](https://v4.mui.com/components/data-grid/selection/#controlled-selection).
7313
7366
  - 💅 Add support for default props from theme (#1019) @DanailH
7314
7367
  - 🙌 Fix scrollbar size on windows (#1061) @dtassone
7315
7368
  - 🐛 Polish existing features, fix 9 issues.
package/index.js CHANGED
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @mui/x-date-pickers v6.0.1
2
+ * @mui/x-date-pickers v6.0.2
3
3
  *
4
4
  * @license MIT
5
5
  * This source code is licensed under the MIT license found in the
@@ -95,7 +95,7 @@ export const PickersArrowSwitcher = /*#__PURE__*/React.forwardRef(function Picke
95
95
  elementType: PreviousIconButton,
96
96
  externalSlotProps: (_slotProps$previousIc = slotProps == null ? void 0 : slotProps.previousIconButton) != null ? _slotProps$previousIc : componentsProps == null ? void 0 : componentsProps.previousIconButton,
97
97
  additionalProps: {
98
- size: 'small',
98
+ size: 'medium',
99
99
  title: leftProps.label,
100
100
  'aria-label': leftProps.label,
101
101
  disabled: leftProps.isDisabled,
@@ -112,7 +112,7 @@ export const PickersArrowSwitcher = /*#__PURE__*/React.forwardRef(function Picke
112
112
  elementType: NextIconButton,
113
113
  externalSlotProps: (_slotProps$nextIconBu = slotProps == null ? void 0 : slotProps.nextIconButton) != null ? _slotProps$nextIconBu : componentsProps == null ? void 0 : componentsProps.nextIconButton,
114
114
  additionalProps: {
115
- size: 'small',
115
+ size: 'medium',
116
116
  title: rightProps.label,
117
117
  'aria-label': rightProps.label,
118
118
  disabled: rightProps.isDisabled,
@@ -129,6 +129,9 @@ export const PickersArrowSwitcher = /*#__PURE__*/React.forwardRef(function Picke
129
129
  const _useSlotProps = useSlotProps({
130
130
  elementType: LeftArrowIcon,
131
131
  externalSlotProps: (_slotProps$leftArrowI = slotProps == null ? void 0 : slotProps.leftArrowIcon) != null ? _slotProps$leftArrowI : componentsProps == null ? void 0 : componentsProps.leftArrowIcon,
132
+ additionalProps: {
133
+ fontSize: 'inherit'
134
+ },
132
135
  ownerState: undefined
133
136
  }),
134
137
  leftArrowIconProps = _objectWithoutPropertiesLoose(_useSlotProps, _excluded2);
@@ -137,6 +140,9 @@ export const PickersArrowSwitcher = /*#__PURE__*/React.forwardRef(function Picke
137
140
  const _useSlotProps2 = useSlotProps({
138
141
  elementType: RightArrowIcon,
139
142
  externalSlotProps: (_slotProps$rightArrow = slotProps == null ? void 0 : slotProps.rightArrowIcon) != null ? _slotProps$rightArrow : componentsProps == null ? void 0 : componentsProps.rightArrowIcon,
143
+ additionalProps: {
144
+ fontSize: 'inherit'
145
+ },
140
146
  ownerState: undefined
141
147
  }),
142
148
  rightArrowIconProps = _objectWithoutPropertiesLoose(_useSlotProps2, _excluded3);
@@ -16,7 +16,7 @@ export interface PickersModalDialogSlotsComponent {
16
16
  */
17
17
  MobilePaper?: React.JSXElementConstructor<MuiPaperProps>;
18
18
  /**
19
- * Custom component for the mobile dialog [Transition](https://mui.com/material-ui/transitions).
19
+ * Custom component for the mobile dialog [Transition](https://mui.com/material-ui/transitions/).
20
20
  * @default Fade from @mui/material
21
21
  */
22
22
  MobileTransition?: React.JSXElementConstructor<MuiTransitionProps>;
@@ -31,7 +31,7 @@ export interface PickersModalDialogSlotsComponentsProps {
31
31
  */
32
32
  mobilePaper?: Partial<MuiPaperProps>;
33
33
  /**
34
- * Props passed down to the mobile [Transition](https://mui.com/material-ui/transitions) component.
34
+ * Props passed down to the mobile [Transition](https://mui.com/material-ui/transitions/) component.
35
35
  */
36
36
  mobileTransition?: Partial<MuiTransitionProps>;
37
37
  }
@@ -14,7 +14,7 @@ export interface PickersPopperSlotsComponent {
14
14
  */
15
15
  DesktopPaper?: React.JSXElementConstructor<MuiPaperProps>;
16
16
  /**
17
- * Custom component for the desktop popper [Transition](https://mui.com/material-ui/transitions).
17
+ * Custom component for the desktop popper [Transition](https://mui.com/material-ui/transitions/).
18
18
  * @default Grow from @mui/material
19
19
  */
20
20
  DesktopTransition?: React.JSXElementConstructor<MuiTransitionProps>;
@@ -10,11 +10,9 @@ import { useUtils } from '../useUtils';
10
10
  import { adjustSectionValue, isAndroid, cleanString } from './useField.utils';
11
11
  import { useFieldState } from './useFieldState';
12
12
  import { useFieldCharacterEditing } from './useFieldCharacterEditing';
13
+ import { getActiveElement } from '../../utils/utils';
13
14
  export const useField = params => {
14
15
  const utils = useUtils();
15
- if (!utils.formatTokenMap) {
16
- throw new Error('This adapter is not compatible with the field components');
17
- }
18
16
  const {
19
17
  state,
20
18
  selectedSectionIndexes,
@@ -61,6 +59,10 @@ export const useField = params => {
61
59
  const focusTimeoutRef = React.useRef(undefined);
62
60
  const syncSelectionFromDOM = () => {
63
61
  var _selectionStart;
62
+ if (readOnly) {
63
+ setSelectedSections(null);
64
+ return;
65
+ }
64
66
  const browserStartIndex = (_selectionStart = inputRef.current.selectionStart) != null ? _selectionStart : 0;
65
67
  const nextSectionIndex = browserStartIndex <= state.sections[0].startInInput ? 1 // Special case if browser index is in invisible characters at the beginning.
66
68
  : state.sections.findIndex(section => section.startInInput - section.startSeparator.length > browserStartIndex);
@@ -87,7 +89,7 @@ export const useField = params => {
87
89
  if (!input || input !== inputRef.current) {
88
90
  return;
89
91
  }
90
- if (selectedSectionIndexes != null) {
92
+ if (selectedSectionIndexes != null || readOnly) {
91
93
  return;
92
94
  }
93
95
  if (
@@ -258,6 +260,10 @@ export const useField = params => {
258
260
  });
259
261
  useEnhancedEffect(() => {
260
262
  if (selectedSectionIndexes == null) {
263
+ if (inputRef.current.selectionStart !== 0 || inputRef.current.selectionEnd !== 0) {
264
+ // Ensure input selection range is in sync with component selection indexes
265
+ inputRef.current.setSelectionRange(0, 0);
266
+ }
261
267
  return;
262
268
  }
263
269
  const firstSelectedSection = state.sections[selectedSectionIndexes.startIndex];
@@ -315,7 +321,7 @@ export const useField = params => {
315
321
  }
316
322
  return 'tel';
317
323
  }, [selectedSectionIndexes, state.sections]);
318
- const inputHasFocus = inputRef.current && inputRef.current === document.activeElement;
324
+ const inputHasFocus = inputRef.current && inputRef.current === getActiveElement(document);
319
325
  const shouldShowPlaceholder = !inputHasFocus && (!state.value || valueManager.areValuesEqual(utils, state.value, valueManager.emptyValue));
320
326
  return _extends({
321
327
  placeholder: state.placeholder,
@@ -152,14 +152,19 @@ export interface FieldSection {
152
152
  endSeparator: string;
153
153
  }
154
154
  export type FieldSectionWithoutPosition<TSection extends FieldSection = FieldSection> = Omit<TSection, 'start' | 'end' | 'startInInput' | 'endInInput'>;
155
- export type FieldSectionsValueBoundaries<TDate> = Record<FieldSectionType, (params: {
156
- currentDate: TDate | null;
157
- format: string;
158
- contentType: 'digit' | 'letter';
159
- }) => {
155
+ export type FieldSectionValueBoundaries<TDate, SectionType extends FieldSectionType> = {
160
156
  minimum: number;
161
157
  maximum: number;
162
- }>;
158
+ } & (SectionType extends 'day' ? {
159
+ longestMonth: TDate;
160
+ } : {});
161
+ export type FieldSectionsValueBoundaries<TDate> = {
162
+ [SectionType in FieldSectionType]: (params: {
163
+ currentDate: TDate | null;
164
+ format: string;
165
+ contentType: 'digit' | 'letter';
166
+ }) => FieldSectionValueBoundaries<TDate, SectionType>;
167
+ };
163
168
  export type FieldChangeHandler<TValue, TError> = (value: TValue, context: FieldChangeHandlerContext<TError>) => void;
164
169
  export interface FieldChangeHandlerContext<TError> {
165
170
  validationError: TError;
@@ -205,12 +210,12 @@ export interface FieldValueManager<TValue, TDate, TSection extends FieldSection,
205
210
  * @template TValue, TDate, TSection
206
211
  * @param {MuiPickersAdapter<TDate>} utils The utils to manipulate the date.
207
212
  * @param {PickersLocaleText<TDate>} localeText The localization object to generate the placeholders.
208
- * @param {TSection[] | null} prevSections The last section list stored in state.
213
+ * @param {TSection[] | null} sections The sections to use as a fallback if a date is null or invalid.
209
214
  * @param {TValue} value The current value to generate sections from.
210
215
  * @param {string} format The date format.
211
216
  * @returns {TSection[]} The new section list.
212
217
  */
213
- getSectionsFromValue: (utils: MuiPickersAdapter<TDate>, localeText: PickersLocaleText<TDate>, prevSections: TSection[] | null, value: TValue, format: string) => TSection[];
218
+ getSectionsFromValue: (utils: MuiPickersAdapter<TDate>, localeText: PickersLocaleText<TDate>, sections: TSection[] | null, value: TValue, format: string) => TSection[];
214
219
  /**
215
220
  * Creates the string value to render in the input based on the current section list.
216
221
  * @template TSection
@@ -1,15 +1,15 @@
1
- import { FieldSection, AvailableAdjustKeyCode, FieldSectionsValueBoundaries, SectionOrdering, FieldValueType, FieldSectionWithoutPosition } from './useField.types';
1
+ import { FieldSection, AvailableAdjustKeyCode, FieldSectionsValueBoundaries, SectionOrdering, FieldValueType, FieldSectionWithoutPosition, FieldSectionValueBoundaries } from './useField.types';
2
2
  import { MuiPickersAdapter, FieldSectionType } from '../../models';
3
3
  import { PickersLocaleText } from '../../../locales/utils/pickersLocaleTextApi';
4
4
  export declare const getDateSectionConfigFromFormatToken: <TDate>(utils: MuiPickersAdapter<TDate>, formatToken: string) => Pick<FieldSection, 'type' | 'contentType'>;
5
5
  export declare const getDaysInWeekStr: <TDate>(utils: MuiPickersAdapter<TDate>, format: string) => string[];
6
- export declare const cleanLeadingZerosInNumericSectionValue: <TDate>(utils: MuiPickersAdapter<TDate>, format: string, value: string) => string;
7
6
  export declare const getLetterEditingOptions: <TDate>(utils: MuiPickersAdapter<TDate>, sectionType: FieldSectionType, format: string) => string[];
7
+ export declare const cleanDigitSectionValue: <TDate>(utils: MuiPickersAdapter<TDate>, value: number, sectionType: FieldSectionType, format: string, hasLeadingZeros: boolean, sectionBoundaries: FieldSectionValueBoundaries<TDate, any>) => string;
8
8
  export declare const adjustSectionValue: <TDate, TSection extends FieldSection>(utils: MuiPickersAdapter<TDate>, section: TSection, keyCode: AvailableAdjustKeyCode, sectionsValueBoundaries: FieldSectionsValueBoundaries<TDate>, activeDate: TDate | null) => string;
9
9
  export declare const cleanString: (dirtyString: string) => string;
10
10
  export declare const addPositionPropertiesToSections: <TSection extends FieldSection>(sections: FieldSectionWithoutPosition<TSection>[]) => TSection[];
11
11
  export declare const changeSectionValueFormat: <TDate>(utils: MuiPickersAdapter<TDate>, valueStr: string, currentFormat: string, newFormat: string) => string;
12
- export declare const doesSectionHaveTrailingZeros: <TDate>(utils: MuiPickersAdapter<TDate>, contentType: 'digit' | 'letter', sectionType: FieldSectionType, format: string) => boolean;
12
+ export declare const doesSectionHaveLeadingZeros: <TDate>(utils: MuiPickersAdapter<TDate>, contentType: 'digit' | 'letter', sectionType: FieldSectionType, format: string) => boolean;
13
13
  export declare const splitFormatIntoSections: <TDate>(utils: MuiPickersAdapter<TDate>, localeText: PickersLocaleText<TDate>, format: string, date: TDate | null) => FieldSectionWithoutPosition<FieldSection>[];
14
14
  /**
15
15
  * Some date libraries like `dayjs` don't support parsing from date with escaped characters.
@@ -41,19 +41,6 @@ export const getDaysInWeekStr = (utils, format) => {
41
41
  }
42
42
  return elements.map(weekDay => utils.formatByString(weekDay, format));
43
43
  };
44
- export const cleanLeadingZerosInNumericSectionValue = (utils, format, value) => {
45
- const size = utils.formatByString(utils.date(), format).length;
46
- let cleanValue = value;
47
-
48
- // We remove the leading zeros
49
- cleanValue = Number(cleanValue).toString();
50
-
51
- // We add enough leading zeros to fill the section
52
- while (cleanValue.length < size) {
53
- cleanValue = `0${cleanValue}`;
54
- }
55
- return cleanValue;
56
- };
57
44
  export const getLetterEditingOptions = (utils, sectionType, format) => {
58
45
  switch (sectionType) {
59
46
  case 'month':
@@ -75,42 +62,70 @@ export const getLetterEditingOptions = (utils, sectionType, format) => {
75
62
  }
76
63
  }
77
64
  };
65
+ export const cleanDigitSectionValue = (utils, value, sectionType, format, hasLeadingZeros, sectionBoundaries) => {
66
+ const hasLetter = () => {
67
+ const startOfYear = utils.startOfYear(utils.date());
68
+ const startOfYearStr = utils.formatByString(startOfYear, format);
69
+ return Number.isNaN(Number(startOfYearStr));
70
+ };
71
+ if (process.env.NODE_ENV !== 'production') {
72
+ if (sectionType !== 'day' && hasLetter()) {
73
+ throw new Error([`MUI: The token "${format}" is a digit format with letter in it.'
74
+ This type of format is only supported for 'day' sections`].join('\n'));
75
+ }
76
+ }
77
+ if (sectionType === 'day' && hasLetter()) {
78
+ const date = utils.setDate(sectionBoundaries.longestMonth, value);
79
+ return utils.formatByString(date, format);
80
+ }
81
+
82
+ // queryValue without leading `0` (`01` => `1`)
83
+ const valueStr = value.toString();
84
+ if (hasLeadingZeros) {
85
+ const size = utils.formatByString(utils.date(), format).length;
86
+ let cleanValueStr = valueStr;
87
+
88
+ // Remove the leading zeros
89
+ cleanValueStr = Number(cleanValueStr).toString();
90
+
91
+ // Add enough leading zeros to fill the section
92
+ while (cleanValueStr.length < size) {
93
+ cleanValueStr = `0${cleanValueStr}`;
94
+ }
95
+ return cleanValueStr;
96
+ }
97
+ return valueStr;
98
+ };
78
99
  export const adjustSectionValue = (utils, section, keyCode, sectionsValueBoundaries, activeDate) => {
79
100
  const delta = getDeltaFromKeyCode(keyCode);
80
101
  const isStart = keyCode === 'Home';
81
102
  const isEnd = keyCode === 'End';
82
103
  const shouldSetAbsolute = section.value === '' || isStart || isEnd;
83
- const cleanDigitSectionValue = value => {
84
- const valueStr = value.toString();
85
- if (section.hasLeadingZeros) {
86
- return cleanLeadingZerosInNumericSectionValue(utils, section.format, valueStr);
87
- }
88
- return valueStr;
89
- };
90
104
  const adjustDigitSection = () => {
91
105
  const sectionBoundaries = sectionsValueBoundaries[section.type]({
92
106
  currentDate: activeDate,
93
107
  format: section.format,
94
108
  contentType: section.contentType
95
109
  });
110
+ const getCleanValue = value => cleanDigitSectionValue(utils, value, section.type, section.format, section.hasLeadingZeros, sectionBoundaries);
96
111
  if (shouldSetAbsolute) {
97
112
  if (section.type === 'year' && !isEnd && !isStart) {
98
113
  return utils.formatByString(utils.date(), section.format);
99
114
  }
100
115
  if (delta > 0 || isStart) {
101
- return cleanDigitSectionValue(sectionBoundaries.minimum);
116
+ return getCleanValue(sectionBoundaries.minimum);
102
117
  }
103
- return cleanDigitSectionValue(sectionBoundaries.maximum);
118
+ return getCleanValue(sectionBoundaries.maximum);
104
119
  }
105
- const currentSectionValue = Number(section.value);
120
+ const currentSectionValue = parseInt(section.value, 10);
106
121
  const newSectionValueNumber = currentSectionValue + delta;
107
122
  if (newSectionValueNumber > sectionBoundaries.maximum) {
108
- return cleanDigitSectionValue(sectionBoundaries.minimum);
123
+ return getCleanValue(sectionBoundaries.minimum);
109
124
  }
110
125
  if (newSectionValueNumber < sectionBoundaries.minimum) {
111
- return cleanDigitSectionValue(sectionBoundaries.maximum);
126
+ return getCleanValue(sectionBoundaries.maximum);
112
127
  }
113
- return cleanDigitSectionValue(newSectionValueNumber);
128
+ return getCleanValue(newSectionValueNumber);
114
129
  };
115
130
  const adjustLetterSection = () => {
116
131
  const options = getLetterEditingOptions(utils, section.type, section.format);
@@ -233,7 +248,7 @@ export const changeSectionValueFormat = (utils, valueStr, currentFormat, newForm
233
248
  return utils.formatByString(utils.parse(valueStr, currentFormat), newFormat);
234
249
  };
235
250
  const isFourDigitYearFormat = (utils, format) => utils.formatByString(utils.date(), format).length === 4;
236
- export const doesSectionHaveTrailingZeros = (utils, contentType, sectionType, format) => {
251
+ export const doesSectionHaveLeadingZeros = (utils, contentType, sectionType, format) => {
237
252
  if (contentType !== 'digit') {
238
253
  return false;
239
254
  }
@@ -307,13 +322,13 @@ export const splitFormatIntoSections = (utils, localeText, format, date) => {
307
322
  return expandedToken;
308
323
  }
309
324
  const sectionConfig = getDateSectionConfigFromFormatToken(utils, token);
310
- const sectionValue = date == null ? '' : utils.formatByString(date, token);
311
- const hasTrailingZeroes = doesSectionHaveTrailingZeros(utils, sectionConfig.contentType, sectionConfig.type, token);
325
+ const sectionValue = date == null || !utils.isValid(date) ? '' : utils.formatByString(date, token);
326
+ const hasLeadingZeros = doesSectionHaveLeadingZeros(utils, sectionConfig.contentType, sectionConfig.type, token);
312
327
  sections.push(_extends({}, sectionConfig, {
313
328
  format: token,
314
329
  value: sectionValue,
315
330
  placeholder: getSectionPlaceholder(utils, localeText, sectionConfig, token),
316
- hasLeadingZeros: hasTrailingZeroes,
331
+ hasLeadingZeros,
317
332
  startSeparator: sections.length === 0 ? startSeparator : '',
318
333
  endSeparator: '',
319
334
  modified: false
@@ -406,10 +421,22 @@ export const createDateStrForInputFromSections = sections => {
406
421
  export const getSectionsBoundaries = utils => {
407
422
  const today = utils.date();
408
423
  const endOfYear = utils.endOfYear(today);
409
- const maxDaysInMonth = utils.getMonthArray(today).reduce((acc, month) => {
424
+ const {
425
+ maxDaysInMonth,
426
+ longestMonth
427
+ } = utils.getMonthArray(today).reduce((acc, month) => {
410
428
  const daysInMonth = utils.getDaysInMonth(month);
411
- return Math.max(acc, daysInMonth);
412
- }, 0);
429
+ if (daysInMonth > acc.maxDaysInMonth) {
430
+ return {
431
+ maxDaysInMonth: daysInMonth,
432
+ longestMonth: month
433
+ };
434
+ }
435
+ return acc;
436
+ }, {
437
+ maxDaysInMonth: 0,
438
+ longestMonth: null
439
+ });
413
440
  return {
414
441
  year: ({
415
442
  format
@@ -426,7 +453,8 @@ export const getSectionsBoundaries = utils => {
426
453
  currentDate
427
454
  }) => ({
428
455
  minimum: 1,
429
- maximum: currentDate != null && utils.isValid(currentDate) ? utils.getDaysInMonth(currentDate) : maxDaysInMonth
456
+ maximum: currentDate != null && utils.isValid(currentDate) ? utils.getDaysInMonth(currentDate) : maxDaysInMonth,
457
+ longestMonth: longestMonth
430
458
  }),
431
459
  weekDay: ({
432
460
  format,
@@ -567,7 +595,7 @@ export const clampDaySection = (utils, sections, sectionsValueBoundaries) => {
567
595
  contentType: section.contentType
568
596
  });
569
597
  return _extends({}, section, {
570
- value: section.hasLeadingZeros ? cleanLeadingZerosInNumericSectionValue(utils, section.format, dayBoundaries.minimum.toString()) : dayBoundaries.minimum.toString()
598
+ value: cleanDigitSectionValue(utils, dayBoundaries.minimum, section.type, section.format, section.hasLeadingZeros, dayBoundaries)
571
599
  });
572
600
  });
573
601
  const startOfMonth = getDateFromDateSections(utils, sectionsForStartOfMonth);
@@ -2,7 +2,7 @@ import _extends from "@babel/runtime/helpers/esm/extends";
2
2
  import * as React from 'react';
3
3
  import useEventCallback from '@mui/utils/useEventCallback';
4
4
  import { useUtils } from '../useUtils';
5
- import { changeSectionValueFormat, cleanLeadingZerosInNumericSectionValue, doesSectionHaveTrailingZeros, getDateSectionConfigFromFormatToken, getDaysInWeekStr, getLetterEditingOptions } from './useField.utils';
5
+ import { changeSectionValueFormat, cleanDigitSectionValue, doesSectionHaveLeadingZeros, getDateSectionConfigFromFormatToken, getDaysInWeekStr, getLetterEditingOptions } from './useField.utils';
6
6
  const QUERY_LIFE_DURATION_MS = 5000;
7
7
  const isQueryResponseWithoutValue = response => response.saveQuery != null;
8
8
 
@@ -138,7 +138,7 @@ export const useFieldCharacterEditing = ({
138
138
  return applyQuery(params, getFirstSectionValueMatchingWithQuery);
139
139
  };
140
140
  const applyNumericEditing = params => {
141
- const getNewSectionValue = (queryValue, sectionType, format, hasTrailingZeroes, contentType) => {
141
+ const getNewSectionValue = (queryValue, sectionType, format, hasLeadingZeros, contentType) => {
142
142
  const queryValueNumber = Number(`${queryValue}`);
143
143
  const sectionBoundaries = sectionsValueBoundaries[sectionType]({
144
144
  currentDate: null,
@@ -160,12 +160,7 @@ export const useFieldCharacterEditing = ({
160
160
  };
161
161
  }
162
162
  const shouldGoToNextSection = Number(`${queryValue}0`) > sectionBoundaries.maximum || queryValue.length === sectionBoundaries.maximum.toString().length;
163
-
164
- // queryValue without leading `0` (`01` => `1`)
165
- let newSectionValue = queryValueNumber.toString();
166
- if (hasTrailingZeroes) {
167
- newSectionValue = cleanLeadingZerosInNumericSectionValue(utils, format, newSectionValue);
168
- }
163
+ const newSectionValue = cleanDigitSectionValue(utils, queryValueNumber, sectionType, format, hasLeadingZeros, sectionBoundaries);
169
164
  return {
170
165
  sectionValue: newSectionValue,
171
166
  shouldGoToNextSection
@@ -179,7 +174,7 @@ export const useFieldCharacterEditing = ({
179
174
  // When editing a letter-format month and the user presses a digit,
180
175
  // We can support the numeric editing by using the digit-format month and re-formatting the result.
181
176
  if (activeSection.type === 'month') {
182
- const response = getNewSectionValue(queryValue, activeSection.type, 'MM', doesSectionHaveTrailingZeros(utils, 'digit', 'month', 'MM'), 'digit');
177
+ const response = getNewSectionValue(queryValue, activeSection.type, 'MM', doesSectionHaveLeadingZeros(utils, 'digit', 'month', 'MM'), 'digit');
183
178
  if (isQueryResponseWithoutValue(response)) {
184
179
  return response;
185
180
  }