baseui 10.3.0 → 10.7.0

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 (213) hide show
  1. package/app-nav-bar/user-menu.js +1 -0
  2. package/app-nav-bar/user-menu.js.flow +1 -0
  3. package/button/styled-components.js +1 -1
  4. package/button/styled-components.js.flow +4 -1
  5. package/card/styled-components.js +0 -1
  6. package/card/styled-components.js.flow +0 -1
  7. package/combobox/combobox.js +5 -1
  8. package/combobox/combobox.js.flow +4 -0
  9. package/combobox/index.d.ts +6 -3
  10. package/data-table/column-datetime.js +2 -0
  11. package/data-table/column-datetime.js.flow +2 -0
  12. package/data-table/data-table.js +13 -3
  13. package/data-table/data-table.js.flow +20 -4
  14. package/data-table/types.js.flow +2 -1
  15. package/datepicker/calendar-header.js +255 -109
  16. package/datepicker/calendar-header.js.flow +282 -145
  17. package/datepicker/calendar.js +6 -1
  18. package/datepicker/calendar.js.flow +5 -1
  19. package/datepicker/constants.js +9 -2
  20. package/datepicker/constants.js.flow +7 -0
  21. package/datepicker/datepicker.js +135 -73
  22. package/datepicker/datepicker.js.flow +161 -62
  23. package/datepicker/day.js +2 -0
  24. package/datepicker/day.js.flow +2 -0
  25. package/datepicker/index.d.ts +8 -0
  26. package/datepicker/month.js +4 -0
  27. package/datepicker/month.js.flow +3 -0
  28. package/datepicker/styled-components.js +116 -56
  29. package/datepicker/styled-components.js.flow +101 -36
  30. package/datepicker/types.js.flow +18 -1
  31. package/datepicker/utils/calendar-header-helpers.js +51 -0
  32. package/datepicker/utils/calendar-header-helpers.js.flow +53 -0
  33. package/datepicker/utils/date-helpers.js +1 -1
  34. package/datepicker/utils/date-helpers.js.flow +1 -1
  35. package/datepicker/week.js +1 -0
  36. package/datepicker/week.js.flow +1 -0
  37. package/dnd-list/index.js.flow +2 -1
  38. package/dnd-list/list.js +1 -2
  39. package/dnd-list/list.js.flow +1 -1
  40. package/dnd-list/styled-components.js +1 -1
  41. package/dnd-list/styled-components.js.flow +1 -0
  42. package/drawer/close-icon.js +3 -2
  43. package/drawer/close-icon.js.flow +2 -2
  44. package/drawer/drawer.js +5 -2
  45. package/drawer/drawer.js.flow +2 -2
  46. package/es/app-nav-bar/user-menu.js +1 -0
  47. package/es/button/styled-components.js +1 -1
  48. package/es/card/styled-components.js +0 -1
  49. package/es/combobox/combobox.js +5 -1
  50. package/es/data-table/column-datetime.js +2 -0
  51. package/es/data-table/data-table.js +13 -3
  52. package/es/datepicker/calendar-header.js +204 -93
  53. package/es/datepicker/calendar.js +7 -2
  54. package/es/datepicker/constants.js +6 -1
  55. package/es/datepicker/datepicker.js +70 -42
  56. package/es/datepicker/day.js +2 -0
  57. package/es/datepicker/month.js +3 -0
  58. package/es/datepicker/styled-components.js +98 -37
  59. package/es/datepicker/types.js +1 -1
  60. package/es/datepicker/utils/calendar-header-helpers.js +34 -0
  61. package/es/datepicker/utils/date-helpers.js +1 -1
  62. package/es/datepicker/week.js +1 -0
  63. package/es/dnd-list/index.js +2 -1
  64. package/es/dnd-list/list.js +1 -2
  65. package/es/dnd-list/styled-components.js +1 -0
  66. package/es/drawer/close-icon.js +3 -2
  67. package/es/drawer/drawer.js +5 -2
  68. package/es/helper/helper.js +1 -0
  69. package/es/layer/layer.js +8 -0
  70. package/es/list/list-heading.js +17 -6
  71. package/es/map-marker/constants.js +69 -0
  72. package/es/map-marker/fixed-marker.js +98 -0
  73. package/es/map-marker/floating-marker.js +65 -0
  74. package/es/map-marker/index.js +9 -0
  75. package/es/map-marker/pin-head.js +108 -0
  76. package/es/map-marker/styled-components.js +156 -0
  77. package/es/map-marker/types.js +8 -0
  78. package/es/menu/maybe-child-menu.js +1 -0
  79. package/es/popover/popover.js +6 -5
  80. package/es/popover/stateful-container.js +8 -2
  81. package/es/rating/emoticon-rating.js +3 -1
  82. package/es/rating/star-rating.js +3 -1
  83. package/es/select/select-component.js +20 -5
  84. package/es/select/styled-components.js +34 -4
  85. package/es/snackbar/snackbar-context.js +16 -4
  86. package/es/spinner/styled-components.js +1 -1
  87. package/es/table-semantic/styled-components.js +6 -4
  88. package/es/table-semantic/table-builder.js +3 -0
  89. package/es/themes/dark-theme/color-component-tokens.js +1 -1
  90. package/es/themes/light-theme/color-component-tokens.js +9 -9
  91. package/es/themes/shared/lighting.js +5 -1
  92. package/es/timepicker/timepicker.js +16 -11
  93. package/es/tooltip/styled-components.js +8 -0
  94. package/es/tooltip/tooltip.js +1 -0
  95. package/esm/app-nav-bar/user-menu.js +1 -0
  96. package/esm/button/styled-components.js +1 -1
  97. package/esm/card/styled-components.js +0 -1
  98. package/esm/combobox/combobox.js +5 -1
  99. package/esm/data-table/column-datetime.js +2 -0
  100. package/esm/data-table/data-table.js +13 -3
  101. package/esm/datepicker/calendar-header.js +255 -110
  102. package/esm/datepicker/calendar.js +7 -2
  103. package/esm/datepicker/constants.js +6 -1
  104. package/esm/datepicker/datepicker.js +136 -74
  105. package/esm/datepicker/day.js +2 -0
  106. package/esm/datepicker/month.js +3 -0
  107. package/esm/datepicker/styled-components.js +112 -55
  108. package/esm/datepicker/types.js +1 -1
  109. package/esm/datepicker/utils/calendar-header-helpers.js +45 -0
  110. package/esm/datepicker/utils/date-helpers.js +1 -1
  111. package/esm/datepicker/week.js +1 -0
  112. package/esm/dnd-list/index.js +2 -1
  113. package/esm/dnd-list/list.js +1 -2
  114. package/esm/dnd-list/styled-components.js +1 -1
  115. package/esm/drawer/close-icon.js +3 -2
  116. package/esm/drawer/drawer.js +5 -2
  117. package/esm/helper/helper.js +1 -0
  118. package/esm/layer/layer.js +8 -0
  119. package/esm/list/list-heading.js +17 -6
  120. package/esm/map-marker/constants.js +62 -0
  121. package/esm/map-marker/fixed-marker.js +137 -0
  122. package/esm/map-marker/floating-marker.js +94 -0
  123. package/esm/map-marker/index.js +9 -0
  124. package/esm/map-marker/pin-head.js +144 -0
  125. package/esm/map-marker/styled-components.js +168 -0
  126. package/esm/map-marker/types.js +8 -0
  127. package/esm/menu/maybe-child-menu.js +1 -0
  128. package/esm/popover/popover.js +6 -5
  129. package/esm/popover/stateful-container.js +8 -2
  130. package/esm/rating/emoticon-rating.js +2 -2
  131. package/esm/rating/star-rating.js +2 -2
  132. package/esm/select/select-component.js +19 -5
  133. package/esm/select/styled-components.js +28 -4
  134. package/esm/snackbar/snackbar-context.js +16 -4
  135. package/esm/spinner/styled-components.js +1 -1
  136. package/esm/table-semantic/styled-components.js +6 -4
  137. package/esm/table-semantic/table-builder.js +3 -0
  138. package/esm/themes/dark-theme/color-component-tokens.js +1 -1
  139. package/esm/themes/light-theme/color-component-tokens.js +9 -9
  140. package/esm/themes/shared/lighting.js +5 -1
  141. package/esm/timepicker/timepicker.js +17 -11
  142. package/esm/tooltip/styled-components.js +8 -0
  143. package/esm/tooltip/tooltip.js +1 -0
  144. package/helper/helper.js +1 -0
  145. package/helper/helper.js.flow +1 -0
  146. package/layer/layer.js +8 -0
  147. package/layer/layer.js.flow +9 -0
  148. package/link/index.d.ts +1 -0
  149. package/list/index.d.ts +36 -0
  150. package/list/list-heading.js +24 -7
  151. package/list/list-heading.js.flow +17 -8
  152. package/map-marker/constants.js +82 -0
  153. package/map-marker/constants.js.flow +74 -0
  154. package/map-marker/fixed-marker.js +152 -0
  155. package/map-marker/fixed-marker.js.flow +137 -0
  156. package/map-marker/floating-marker.js +109 -0
  157. package/map-marker/floating-marker.js.flow +102 -0
  158. package/map-marker/index.d.ts +105 -0
  159. package/map-marker/index.js +55 -0
  160. package/map-marker/index.js.flow +23 -0
  161. package/map-marker/package.json +4 -0
  162. package/map-marker/pin-head.js +159 -0
  163. package/map-marker/pin-head.js.flow +155 -0
  164. package/map-marker/styled-components.js +184 -0
  165. package/map-marker/styled-components.js.flow +177 -0
  166. package/map-marker/types.js +11 -0
  167. package/map-marker/types.js.flow +114 -0
  168. package/menu/index.d.ts +7 -0
  169. package/menu/maybe-child-menu.js +1 -0
  170. package/menu/maybe-child-menu.js.flow +1 -0
  171. package/menu/types.js.flow +12 -0
  172. package/modal/index.d.ts +1 -1
  173. package/modal/types.js.flow +4 -1
  174. package/package.json +5 -3
  175. package/popover/index.d.ts +2 -1
  176. package/popover/popover.js +6 -5
  177. package/popover/popover.js.flow +11 -4
  178. package/popover/stateful-container.js +8 -2
  179. package/popover/stateful-container.js.flow +5 -0
  180. package/popover/types.js.flow +6 -1
  181. package/rating/emoticon-rating.js +2 -2
  182. package/rating/emoticon-rating.js.flow +4 -1
  183. package/rating/star-rating.js +2 -2
  184. package/rating/star-rating.js.flow +4 -1
  185. package/select/select-component.js +19 -5
  186. package/select/select-component.js.flow +19 -5
  187. package/select/styled-components.js +28 -4
  188. package/select/styled-components.js.flow +30 -2
  189. package/select/types.js.flow +9 -0
  190. package/snackbar/index.d.ts +21 -16
  191. package/snackbar/snackbar-context.js +15 -4
  192. package/snackbar/snackbar-context.js.flow +15 -3
  193. package/spinner/styled-components.js +1 -1
  194. package/spinner/styled-components.js.flow +1 -1
  195. package/table-semantic/styled-components.js +6 -4
  196. package/table-semantic/styled-components.js.flow +6 -4
  197. package/table-semantic/table-builder.js +3 -0
  198. package/table-semantic/table-builder.js.flow +3 -0
  199. package/themes/dark-theme/color-component-tokens.js +1 -1
  200. package/themes/dark-theme/color-component-tokens.js.flow +1 -1
  201. package/themes/light-theme/color-component-tokens.js +9 -9
  202. package/themes/light-theme/color-component-tokens.js.flow +9 -9
  203. package/themes/shared/lighting.js +5 -1
  204. package/themes/shared/lighting.js.flow +4 -0
  205. package/themes/types.js.flow +4 -0
  206. package/timepicker/index.d.ts +1 -0
  207. package/timepicker/timepicker.js +17 -11
  208. package/timepicker/timepicker.js.flow +31 -12
  209. package/timepicker/types.js.flow +10 -0
  210. package/tooltip/styled-components.js +8 -0
  211. package/tooltip/styled-components.js.flow +8 -0
  212. package/tooltip/tooltip.js +1 -0
  213. package/tooltip/tooltip.js.flow +6 -1
@@ -6,11 +6,12 @@ LICENSE file in the root directory of this source tree.
6
6
  */
7
7
  // @flow
8
8
  import * as React from 'react';
9
- import ArrowRight from '../icon/arrow-right.js';
10
- import ArrowLeft from '../icon/arrow-left.js';
11
- import TriangleDown from '../icon/triangle-down.js';
9
+ import ChevronRight from '../icon/chevron-right.js';
10
+ import ChevronLeft from '../icon/chevron-left.js';
11
+ import ChevronDown from '../icon/chevron-down.js';
12
12
  import dateFnsAdapter from './utils/date-fns-adapter.js';
13
13
  import DateHelpers from './utils/date-helpers.js';
14
+ import {getFilteredMonthItems} from './utils/calendar-header-helpers.js';
14
15
  import {StatefulMenu} from '../menu/index.js';
15
16
  import {Popover} from '../popover/index.js';
16
17
  import {LocaleContext} from '../locale/index.js';
@@ -24,7 +25,7 @@ import {
24
25
  StyledMonthYearSelectButton,
25
26
  StyledMonthYearSelectIconContainer,
26
27
  } from './styled-components.js';
27
- import {ORIENTATION, WEEKDAYS} from './constants.js';
28
+ import {ORIENTATION, WEEKDAYS, DENSITY} from './constants.js';
28
29
  import {getOverrides, mergeOverrides} from '../helpers/overrides.js';
29
30
  import type {HeaderPropsT} from './types.js';
30
31
  import type {LocaleT} from '../locale/types.js';
@@ -45,17 +46,17 @@ const DIRECTION = {
45
46
  PREVIOUS: 'previous',
46
47
  };
47
48
 
48
- function yearMonthToId(year, month) {
49
- return `${year}-${month}`;
50
- }
51
-
52
49
  function idToYearMonth(id) {
53
50
  return id.split('-').map(Number);
54
51
  }
55
52
 
56
53
  export default class CalendarHeader<T = Date> extends React.Component<
57
54
  HeaderPropsT<T>,
58
- {isMonthYearDropdownOpen: boolean, isFocusVisible: boolean},
55
+ {
56
+ isMonthDropdownOpen: boolean,
57
+ isYearDropdownOpen: boolean,
58
+ isFocusVisible: boolean,
59
+ },
59
60
  > {
60
61
  static defaultProps = {
61
62
  adapter: dateFnsAdapter,
@@ -67,34 +68,134 @@ export default class CalendarHeader<T = Date> extends React.Component<
67
68
  };
68
69
 
69
70
  dateHelpers: DateHelpers<T>;
70
- items: Array<{id: string, label: string}>;
71
- minYear: number;
72
- maxYear: number;
71
+ monthItems: Array<{id: string, label: string, disabled?: boolean}>;
72
+ yearItems: Array<{id: string, label: string, disabled?: boolean}>;
73
73
 
74
74
  constructor(props: HeaderPropsT<T>) {
75
75
  super(props);
76
76
  this.dateHelpers = new DateHelpers(props.adapter);
77
- this.items = [];
77
+ this.monthItems = [];
78
+ this.yearItems = [];
78
79
  }
79
80
 
80
81
  state = {
81
- isMonthYearDropdownOpen: false,
82
+ isMonthDropdownOpen: false,
83
+ isYearDropdownOpen: false,
82
84
  isFocusVisible: false,
83
85
  };
84
86
 
87
+ componentDidMount() {
88
+ this.getYearItems();
89
+ this.getMonthItems();
90
+ }
91
+
92
+ componentDidUpdate(prevProps: HeaderPropsT<T>) {
93
+ const selectedMonthDidChange =
94
+ this.dateHelpers.getMonth(this.props.date) !==
95
+ this.dateHelpers.getMonth(prevProps.date);
96
+
97
+ const selectedYearDidChange =
98
+ this.dateHelpers.getYear(this.props.date) !==
99
+ this.dateHelpers.getYear(prevProps.date);
100
+
101
+ if (selectedMonthDidChange) {
102
+ // re-calculate yearItems
103
+ this.getYearItems();
104
+ }
105
+
106
+ if (selectedYearDidChange) {
107
+ // re-calculate monthItems
108
+ this.getMonthItems();
109
+ }
110
+ }
111
+
85
112
  getDateProp: () => T = () => {
86
113
  return this.props.date || this.dateHelpers.date();
87
114
  };
88
115
 
89
- handleYearChange = ({value}: {value: Array<{id: number}>}) => {
90
- if (this.props.onYearChange) {
91
- // $FlowFixMe
92
- this.props.onYearChange({
93
- date: this.dateHelpers.setYear(this.getDateProp(), value[0].id),
94
- });
116
+ getYearItems = () => {
117
+ const date = this.getDateProp();
118
+ const maxDate = this.props.maxDate;
119
+ const minDate = this.props.minDate;
120
+ const maxYear = maxDate ? this.dateHelpers.getYear(maxDate) : MAX_YEAR;
121
+ const minYear = minDate ? this.dateHelpers.getYear(minDate) : MIN_YEAR;
122
+ const selectedMonth = this.dateHelpers.getMonth(date);
123
+
124
+ // TODO: this logic can be optimized to only run when minDate / maxDate change
125
+ this.yearItems = Array.from(
126
+ {length: maxYear - minYear + 1},
127
+ (_, i) => minYear + i,
128
+ ).map(year => ({id: year.toString(), label: year.toString()}));
129
+ const monthOfMaxDate = maxDate
130
+ ? this.dateHelpers.getMonth(maxDate)
131
+ : MAX_MONTH;
132
+ const monthOfMinDate = minDate
133
+ ? this.dateHelpers.getMonth(minDate)
134
+ : MIN_MONTH;
135
+ // Generates array like [0,1,.... monthOfMaxDate]
136
+ const maxYearMonths = Array.from({length: monthOfMaxDate + 1}, (x, i) => i);
137
+ // Generates array like [monthOfMinDate, ...., 10, 11]
138
+ const minYearMonths = Array.from(
139
+ {length: 12 - monthOfMinDate},
140
+ (x, i) => i + monthOfMinDate,
141
+ );
142
+
143
+ if (selectedMonth > maxYearMonths[maxYearMonths.length - 1]) {
144
+ const lastIdx = this.yearItems.length - 1;
145
+ this.yearItems[lastIdx] = {...this.yearItems[lastIdx], disabled: true};
146
+ }
147
+
148
+ if (selectedMonth < minYearMonths[0]) {
149
+ this.yearItems[0] = {...this.yearItems[0], disabled: true};
95
150
  }
96
151
  };
97
152
 
153
+ getMonthItems = () => {
154
+ const date = this.getDateProp();
155
+ const year = this.dateHelpers.getYear(date);
156
+ const maxDate = this.props.maxDate;
157
+ const minDate = this.props.minDate;
158
+ const maxYear = maxDate ? this.dateHelpers.getYear(maxDate) : MAX_YEAR;
159
+ const minYear = minDate ? this.dateHelpers.getYear(minDate) : MIN_YEAR;
160
+
161
+ const monthOfMaxDate = maxDate
162
+ ? this.dateHelpers.getMonth(maxDate)
163
+ : MAX_MONTH;
164
+ // Generates array like [0,1,.... monthOfMaxDate]
165
+ const maxYearMonths = Array.from({length: monthOfMaxDate + 1}, (x, i) => i);
166
+
167
+ const monthOfMinDate = minDate
168
+ ? this.dateHelpers.getMonth(minDate)
169
+ : MIN_MONTH;
170
+
171
+ // Generates array like [monthOfMinDate, ...., 10, 11]
172
+ const minYearMonths = Array.from(
173
+ {length: 12 - monthOfMinDate},
174
+ (x, i) => i + monthOfMinDate,
175
+ );
176
+
177
+ const maxMinYearMonthsIntersection = maxYearMonths.filter(year =>
178
+ minYearMonths.includes(year),
179
+ );
180
+
181
+ const filterMonthsList =
182
+ year === maxYear && year === minYear
183
+ ? maxMinYearMonthsIntersection
184
+ : year === maxYear
185
+ ? maxYearMonths
186
+ : year === minYear
187
+ ? minYearMonths
188
+ : null;
189
+
190
+ const formatMonthLabel = month =>
191
+ this.dateHelpers.getMonthInLocale(month, this.props.locale);
192
+
193
+ this.monthItems = getFilteredMonthItems({
194
+ filterMonthsList,
195
+ formatMonthLabel,
196
+ });
197
+ };
198
+
98
199
  increaseMonth = () => {
99
200
  if (this.props.onMonthChange) {
100
201
  // $FlowFixMe
@@ -165,7 +266,7 @@ export default class CalendarHeader<T = Date> extends React.Component<
165
266
  theme: ThemeT,
166
267
  }) => {
167
268
  const date = this.getDateProp();
168
- const {overrides = {}} = this.props;
269
+ const {overrides = {}, density} = this.props;
169
270
  const allPrevDaysDisabled = this.dateHelpers.monthDisabledBefore(
170
271
  date,
171
272
  this.props,
@@ -194,7 +295,7 @@ export default class CalendarHeader<T = Date> extends React.Component<
194
295
  );
195
296
  const [PrevButtonIcon, prevButtonIconProps] = getOverrides(
196
297
  overrides.PrevButtonIcon,
197
- theme.direction === 'rtl' ? ArrowRight : ArrowLeft,
298
+ theme.direction === 'rtl' ? ChevronRight : ChevronLeft,
198
299
  );
199
300
  let clickHandler = this.decreaseMonth;
200
301
  if (allPrevDaysDisabled) {
@@ -214,7 +315,7 @@ export default class CalendarHeader<T = Date> extends React.Component<
214
315
  >
215
316
  {isHidden ? null : (
216
317
  <PrevButtonIcon
217
- size={'24px'}
318
+ size={density === DENSITY.high ? 24 : 36}
218
319
  overrides={{Svg: {style: navBtnStyle}}}
219
320
  {...prevButtonIconProps}
220
321
  />
@@ -231,7 +332,7 @@ export default class CalendarHeader<T = Date> extends React.Component<
231
332
  theme: ThemeT,
232
333
  }) => {
233
334
  const date = this.getDateProp();
234
- const {overrides = {}} = this.props;
335
+ const {overrides = {}, density} = this.props;
235
336
  const allNextDaysDisabled = this.dateHelpers.monthDisabledAfter(
236
337
  date,
237
338
  this.props,
@@ -260,7 +361,7 @@ export default class CalendarHeader<T = Date> extends React.Component<
260
361
  );
261
362
  const [NextButtonIcon, nextButtonIconProps] = getOverrides(
262
363
  overrides.NextButtonIcon,
263
- theme.direction === 'rtl' ? ArrowLeft : ArrowRight,
364
+ theme.direction === 'rtl' ? ChevronLeft : ChevronRight,
264
365
  );
265
366
 
266
367
  let clickHandler = this.increaseMonth;
@@ -287,7 +388,7 @@ export default class CalendarHeader<T = Date> extends React.Component<
287
388
  >
288
389
  {isHidden ? null : (
289
390
  <NextButtonIcon
290
- size={'24px'}
391
+ size={density === DENSITY.high ? 24 : 36}
291
392
  overrides={{Svg: {style: navBtnStyle}}}
292
393
  {...nextButtonIconProps}
293
394
  />
@@ -297,7 +398,7 @@ export default class CalendarHeader<T = Date> extends React.Component<
297
398
  };
298
399
 
299
400
  canArrowsOpenDropdown = (event: KeyboardEvent) => {
300
- if (!this.state.isMonthYearDropdownOpen) {
401
+ if (!this.state.isMonthDropdownOpen && !this.state.isYearDropdownOpen) {
301
402
  if (event.key === 'ArrowUp' || event.key === 'ArrowDown') {
302
403
  return true;
303
404
  }
@@ -307,7 +408,10 @@ export default class CalendarHeader<T = Date> extends React.Component<
307
408
 
308
409
  renderMonthYearDropdown = () => {
309
410
  const date = this.getDateProp();
310
- const {locale, maxDate, minDate, overrides = {}} = this.props;
411
+ const month = this.dateHelpers.getMonth(date);
412
+ const year = this.dateHelpers.getYear(date);
413
+
414
+ const {locale, overrides = {}, density} = this.props;
311
415
  const [MonthYearSelectButton, monthYearSelectButtonProps] = getOverrides(
312
416
  overrides.MonthYearSelectButton,
313
417
  StyledMonthYearSelectButton,
@@ -335,138 +439,169 @@ export default class CalendarHeader<T = Date> extends React.Component<
335
439
  // $FlowFixMe
336
440
  menuProps.overrides = menuOverrides;
337
441
 
338
- const defaultMonths = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11];
339
- const maxYear = maxDate ? this.dateHelpers.getYear(maxDate) : MAX_YEAR;
340
- const minYear = minDate ? this.dateHelpers.getYear(minDate) : MIN_YEAR;
341
- const maxDateMonth = maxDate
342
- ? this.dateHelpers.getMonth(maxDate)
343
- : MAX_MONTH;
344
- // Generates array like [0,1,.... maxDateMonth]
345
- const maxYearMonths = Array.from({length: maxDateMonth + 1}, (x, i) => i);
346
-
347
- const minDateMonth = minDate
348
- ? this.dateHelpers.getMonth(minDate)
349
- : MIN_MONTH;
350
- // Generates array like [minDateMonth, ...., 10, 11]
351
- const minYearMonths = Array.from(
352
- {length: 12 - minDateMonth},
353
- (x, i) => i + minDateMonth,
442
+ const initialMonthIndex = this.monthItems.findIndex(
443
+ month => month.id === this.dateHelpers.getMonth(date).toString(),
444
+ );
445
+ const initialYearIndex = this.yearItems.findIndex(
446
+ year => year.id === this.dateHelpers.getYear(date).toString(),
354
447
  );
355
448
 
356
- if (this.maxYear !== maxYear || this.minYear !== minYear) {
357
- this.maxYear = maxYear;
358
- this.minYear = minYear;
359
- this.items = [];
360
- for (let i = minYear; i <= maxYear; i++) {
361
- let months;
362
- if (i === minYear && i === maxYear) {
363
- months = maxYearMonths.filter(month => minYearMonths.includes(month));
364
- } else if (i === minYear) {
365
- months = minYearMonths;
366
- } else if (i === maxYear) {
367
- months = maxYearMonths;
368
- } else {
369
- months = defaultMonths;
370
- }
371
- months.forEach(month => {
372
- this.items.push({
373
- id: yearMonthToId(i, month),
374
- label: `${this.dateHelpers.getMonthInLocale(month, locale)} ${i}`,
375
- });
376
- });
377
- }
378
- }
379
-
380
- const initialIndex = this.items.findIndex(item => {
381
- return (
382
- item.id ===
383
- yearMonthToId(
384
- this.dateHelpers.getYear(date),
385
- this.dateHelpers.getMonth(date),
386
- )
387
- );
388
- });
389
-
390
- const monthYearTitle = `${this.dateHelpers.getMonthInLocale(
449
+ const monthTitle = `${this.dateHelpers.getMonthInLocale(
391
450
  this.dateHelpers.getMonth(date),
392
451
  locale,
393
- )} ${this.dateHelpers.getYear(date)}`;
452
+ )}`;
453
+ const yearTitle = `${this.dateHelpers.getYear(date)}`;
394
454
 
395
455
  return this.isMultiMonthHorizontal() ? (
396
- <div>{monthYearTitle}</div>
456
+ <div>{`${monthTitle} ${yearTitle}`}</div>
397
457
  ) : (
398
- <OverriddenPopover
399
- placement="bottom"
400
- autoFocus={true}
401
- focusLock={true}
402
- isOpen={this.state.isMonthYearDropdownOpen}
403
- onClick={() => {
404
- this.setState(prev => ({
405
- isMonthYearDropdownOpen: !prev.isMonthYearDropdownOpen,
406
- }));
407
- }}
408
- onClickOutside={() => this.setState({isMonthYearDropdownOpen: false})}
409
- onEsc={() => this.setState({isMonthYearDropdownOpen: false})}
410
- content={() => (
411
- <OverriddenStatefulMenu
412
- initialState={{
413
- highlightedIndex: initialIndex,
414
- isFocused: true,
458
+ <>
459
+ {/* Month Selection */}
460
+ <OverriddenPopover
461
+ placement="bottom"
462
+ autoFocus={true}
463
+ focusLock={true}
464
+ isOpen={this.state.isMonthDropdownOpen}
465
+ onClick={() => {
466
+ this.setState(prev => ({
467
+ isMonthDropdownOpen: !prev.isMonthDropdownOpen,
468
+ }));
469
+ }}
470
+ onClickOutside={() => this.setState({isMonthDropdownOpen: false})}
471
+ onEsc={() => this.setState({isMonthDropdownOpen: false})}
472
+ content={() => (
473
+ <OverriddenStatefulMenu
474
+ initialState={{
475
+ highlightedIndex: initialMonthIndex,
476
+ isFocused: true,
477
+ }}
478
+ items={this.monthItems}
479
+ onItemSelect={({item, event}) => {
480
+ event.preventDefault();
481
+ const month = idToYearMonth(item.id);
482
+ const updatedDate = this.dateHelpers.set(date, {
483
+ year,
484
+ month,
485
+ });
486
+ this.props.onMonthChange &&
487
+ this.props.onMonthChange({date: updatedDate});
488
+ this.setState({isMonthDropdownOpen: false});
489
+ }}
490
+ {...menuProps}
491
+ />
492
+ )}
493
+ {...popoverProps}
494
+ >
495
+ <MonthYearSelectButton
496
+ aria-live="polite"
497
+ type="button"
498
+ $isFocusVisible={this.state.isFocusVisible}
499
+ $density={density}
500
+ onKeyUp={event => {
501
+ if (this.canArrowsOpenDropdown(event)) {
502
+ this.setState({isMonthDropdownOpen: true});
503
+ }
415
504
  }}
416
- items={this.items}
417
- onItemSelect={({item, event}) => {
418
- event.preventDefault();
419
- const [year, month] = idToYearMonth(item.id);
420
- const updatedDate = this.dateHelpers.set(date, {
421
- year,
422
- month,
423
- });
424
- this.props.onMonthChange &&
425
- this.props.onMonthChange({date: updatedDate});
426
- this.props.onYearChange &&
427
- this.props.onYearChange({date: updatedDate});
428
- this.setState({isMonthYearDropdownOpen: false});
505
+ onKeyDown={event => {
506
+ if (this.canArrowsOpenDropdown(event)) {
507
+ // disables page scroll
508
+ event.preventDefault();
509
+ }
510
+
511
+ if (event.key === 'Tab') {
512
+ this.setState({isMonthDropdownOpen: false});
513
+ }
429
514
  }}
430
- {...menuProps}
431
- />
432
- )}
433
- {...popoverProps}
434
- >
435
- <MonthYearSelectButton
436
- aria-live="polite"
437
- type="button"
438
- $isFocusVisible={this.state.isFocusVisible}
439
- onKeyUp={event => {
440
- if (this.canArrowsOpenDropdown(event)) {
441
- this.setState({isMonthYearDropdownOpen: true});
442
- }
443
- }}
444
- onKeyDown={event => {
445
- if (this.canArrowsOpenDropdown(event)) {
446
- // disables page scroll
447
- event.preventDefault();
448
- }
449
-
450
- if (event.key === 'Tab') {
451
- this.setState({isMonthYearDropdownOpen: false});
452
- }
515
+ {...monthYearSelectButtonProps}
516
+ >
517
+ {monthTitle}
518
+ <MonthYearSelectIconContainer
519
+ {...monthYearSelectIconContainerProps}
520
+ >
521
+ <ChevronDown
522
+ title=""
523
+ overrides={{Svg: {props: {role: 'presentation'}}}}
524
+ size={density === DENSITY.high ? 16 : 24}
525
+ />
526
+ </MonthYearSelectIconContainer>
527
+ </MonthYearSelectButton>
528
+ </OverriddenPopover>
529
+
530
+ {/* Year Selection */}
531
+ <OverriddenPopover
532
+ placement="bottom"
533
+ focusLock={true}
534
+ isOpen={this.state.isYearDropdownOpen}
535
+ onClick={() => {
536
+ this.setState(prev => ({
537
+ isYearDropdownOpen: !prev.isYearDropdownOpen,
538
+ }));
453
539
  }}
454
- {...monthYearSelectButtonProps}
455
- >
456
- {monthYearTitle}
457
- <MonthYearSelectIconContainer {...monthYearSelectIconContainerProps}>
458
- <TriangleDown
459
- title=""
460
- overrides={{Svg: {props: {role: 'presentation'}}}}
540
+ onClickOutside={() => this.setState({isYearDropdownOpen: false})}
541
+ onEsc={() => this.setState({isYearDropdownOpen: false})}
542
+ content={() => (
543
+ <OverriddenStatefulMenu
544
+ initialState={{
545
+ highlightedIndex: initialYearIndex,
546
+ isFocused: true,
547
+ }}
548
+ items={this.yearItems}
549
+ onItemSelect={({item, event}) => {
550
+ event.preventDefault();
551
+ const year = idToYearMonth(item.id);
552
+ const updatedDate = this.dateHelpers.set(date, {
553
+ year,
554
+ month,
555
+ });
556
+ this.props.onYearChange &&
557
+ this.props.onYearChange({date: updatedDate});
558
+ this.setState({isYearDropdownOpen: false});
559
+ }}
560
+ {...menuProps}
461
561
  />
462
- </MonthYearSelectIconContainer>
463
- </MonthYearSelectButton>
464
- </OverriddenPopover>
562
+ )}
563
+ {...popoverProps}
564
+ >
565
+ <MonthYearSelectButton
566
+ aria-live="polite"
567
+ type="button"
568
+ $isFocusVisible={this.state.isFocusVisible}
569
+ $density={density}
570
+ onKeyUp={event => {
571
+ if (this.canArrowsOpenDropdown(event)) {
572
+ this.setState({isYearDropdownOpen: true});
573
+ }
574
+ }}
575
+ onKeyDown={event => {
576
+ if (this.canArrowsOpenDropdown(event)) {
577
+ // disables page scroll
578
+ event.preventDefault();
579
+ }
580
+
581
+ if (event.key === 'Tab') {
582
+ this.setState({isYearDropdownOpen: false});
583
+ }
584
+ }}
585
+ {...monthYearSelectButtonProps}
586
+ >
587
+ {yearTitle}
588
+ <MonthYearSelectIconContainer
589
+ {...monthYearSelectIconContainerProps}
590
+ >
591
+ <ChevronDown
592
+ title=""
593
+ overrides={{Svg: {props: {role: 'presentation'}}}}
594
+ size={density === DENSITY.high ? 16 : 24}
595
+ />
596
+ </MonthYearSelectIconContainer>
597
+ </MonthYearSelectButton>
598
+ </OverriddenPopover>
599
+ </>
465
600
  );
466
601
  };
467
602
 
468
603
  render() {
469
- const {overrides = {}} = this.props;
604
+ const {overrides = {}, density} = this.props;
470
605
  const [CalendarHeader, calendarHeaderProps] = getOverrides(
471
606
  overrides.CalendarHeader,
472
607
  StyledCalendarHeader,
@@ -492,6 +627,7 @@ export default class CalendarHeader<T = Date> extends React.Component<
492
627
  <>
493
628
  <CalendarHeader
494
629
  {...calendarHeaderProps}
630
+ $density={this.props.density}
495
631
  onFocus={forkFocus(calendarHeaderProps, this.handleFocus)}
496
632
  onBlur={forkBlur(calendarHeaderProps, this.handleBlur)}
497
633
  >
@@ -513,6 +649,7 @@ export default class CalendarHeader<T = Date> extends React.Component<
513
649
  this.props.locale,
514
650
  )}
515
651
  {...weekdayHeaderProps}
652
+ $density={density}
516
653
  >
517
654
  {this.dateHelpers.getWeekdayMinInLocale(
518
655
  day,
@@ -426,10 +426,13 @@ var Calendar = /*#__PURE__*/function (_React$Component) {
426
426
  "aria-roledescription": translations.ariaRoleDescCalMonth,
427
427
  "aria-multiselectable": _this.props.range || null,
428
428
  onKeyDown: _this.onKeyDown
429
- }, calendarContainerProps), /*#__PURE__*/React.createElement(_month.default, {
429
+ }, calendarContainerProps, {
430
+ $density: _this.props.density
431
+ }), /*#__PURE__*/React.createElement(_month.default, {
430
432
  adapter: _this.props.adapter,
431
433
  date: monthDate,
432
434
  dateLabel: _this.props.dateLabel,
435
+ density: _this.props.density,
433
436
  excludeDates: _this.props.excludeDates,
434
437
  filterDate: _this.props.filterDate,
435
438
  highlightedDate: _this.state.highlightedDate,
@@ -711,6 +714,7 @@ var Calendar = /*#__PURE__*/function (_React$Component) {
711
714
 
712
715
  return /*#__PURE__*/React.createElement(_index2.LocaleContext.Consumer, null, function (locale) {
713
716
  return /*#__PURE__*/React.createElement(Root, _extends({
717
+ $density: _this2.props.density,
714
718
  "data-baseweb": "calendar",
715
719
  role: "application",
716
720
  "aria-roledescription": "datepicker",
@@ -742,6 +746,7 @@ exports.default = Calendar;
742
746
  _defineProperty(Calendar, "defaultProps", {
743
747
  autoFocusCalendar: false,
744
748
  dateLabel: null,
749
+ density: _constants.DENSITY.default,
745
750
  excludeDates: null,
746
751
  filterDate: null,
747
752
  highlightedDate: null,
@@ -23,7 +23,7 @@ import dateFnsAdapter from './utils/date-fns-adapter.js';
23
23
  import DateHelpers from './utils/date-helpers.js';
24
24
  import {getOverrides, mergeOverrides} from '../helpers/overrides.js';
25
25
  import type {CalendarPropsT, CalendarInternalState} from './types.js';
26
- import {ORIENTATION} from './constants.js';
26
+ import {DENSITY, ORIENTATION} from './constants.js';
27
27
 
28
28
  export default class Calendar<T = Date> extends React.Component<
29
29
  CalendarPropsT<T>,
@@ -32,6 +32,7 @@ export default class Calendar<T = Date> extends React.Component<
32
32
  static defaultProps: {adapter: DateIOAdapter<Date>} = {
33
33
  autoFocusCalendar: false,
34
34
  dateLabel: null,
35
+ density: DENSITY.default,
35
36
  excludeDates: null,
36
37
  filterDate: null,
37
38
  highlightedDate: null,
@@ -442,11 +443,13 @@ export default class Calendar<T = Date> extends React.Component<
442
443
  aria-multiselectable={this.props.range || null}
443
444
  onKeyDown={this.onKeyDown}
444
445
  {...calendarContainerProps}
446
+ $density={this.props.density}
445
447
  >
446
448
  <Month
447
449
  adapter={this.props.adapter}
448
450
  date={monthDate}
449
451
  dateLabel={this.props.dateLabel}
452
+ density={this.props.density}
450
453
  excludeDates={this.props.excludeDates}
451
454
  filterDate={this.props.filterDate}
452
455
  highlightedDate={this.state.highlightedDate}
@@ -643,6 +646,7 @@ export default class Calendar<T = Date> extends React.Component<
643
646
  <LocaleContext.Consumer>
644
647
  {locale => (
645
648
  <Root
649
+ $density={this.props.density}
646
650
  data-baseweb="calendar"
647
651
  role="application"
648
652
  aria-roledescription="datepicker"
@@ -3,7 +3,7 @@
3
3
  Object.defineProperty(exports, "__esModule", {
4
4
  value: true
5
5
  });
6
- exports.WEEKDAYS = exports.STATE_CHANGE_TYPE = exports.ORIENTATION = exports.ISO_MONTH_FORMAT = exports.ISO_FORMAT = exports.DISPLAY_FORMAT = void 0;
6
+ exports.DENSITY = exports.DEFAULT_MONTHS = exports.WEEKDAYS = exports.STATE_CHANGE_TYPE = exports.ORIENTATION = exports.ISO_MONTH_FORMAT = exports.ISO_FORMAT = exports.DISPLAY_FORMAT = void 0;
7
7
 
8
8
  /*
9
9
  Copyright (c) Uber Technologies, Inc.
@@ -33,4 +33,11 @@ var STATE_CHANGE_TYPE = Object.freeze({
33
33
  });
34
34
  exports.STATE_CHANGE_TYPE = STATE_CHANGE_TYPE;
35
35
  var WEEKDAYS = [0, 1, 2, 3, 4, 5, 6];
36
- exports.WEEKDAYS = WEEKDAYS;
36
+ exports.WEEKDAYS = WEEKDAYS;
37
+ var DEFAULT_MONTHS = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11];
38
+ exports.DEFAULT_MONTHS = DEFAULT_MONTHS;
39
+ var DENSITY = {
40
+ high: 'high',
41
+ default: 'default'
42
+ };
43
+ exports.DENSITY = DENSITY;
@@ -26,6 +26,13 @@ export const STATE_CHANGE_TYPE = Object.freeze({
26
26
 
27
27
  export const WEEKDAYS = [0, 1, 2, 3, 4, 5, 6];
28
28
 
29
+ export const DEFAULT_MONTHS = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11];
30
+
31
+ export const DENSITY = {
32
+ high: 'high',
33
+ default: 'default',
34
+ };
35
+
29
36
  declare var __DEV__: boolean;
30
37
  declare var __NODE__: boolean;
31
38
  declare var __BROWSER__: boolean;