@trackunit/react-date-and-time-components 1.26.13 → 1.26.16

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.
package/index.cjs.js CHANGED
@@ -415,37 +415,70 @@ const cvaTriggerButton = cssClassVarianceUtilities.cvaMerge(["justify-start"], {
415
415
  */
416
416
  const useCalculateCustomDateRangeDisabledDays = () => {
417
417
  const { subtract, add, nowDate } = reactDateAndTimeHooks.useDateAndTime();
418
- return react.useCallback(({ maxDaysInRange, allowedDirection, }) => {
419
- if (!allowedDirection) {
420
- return undefined;
418
+ const calculateDateRange = useCalculateDateRange();
419
+ const matchesDisabledDays = react.useCallback((matcher, dateToCheck) => {
420
+ if (typeof matcher === "function") {
421
+ return matcher(dateToCheck);
421
422
  }
422
- if (!sharedUtils.nonNullable(maxDaysInRange)) {
423
- if (allowedDirection === "last") {
423
+ if (Array.isArray(matcher)) {
424
+ return matcher.some(disabledDate => disabledDate.toDateString() === dateToCheck.toDateString());
425
+ }
426
+ if ("furtherBackThanDays" in matcher) {
427
+ const dateRange = calculateDateRange({
428
+ direction: "last",
429
+ count: matcher.furtherBackThanDays,
430
+ unit: "day",
431
+ });
432
+ if (dateRange.start && dateRange.end) {
433
+ return dateToCheck < dateRange.start || dateToCheck > dateRange.end;
434
+ }
435
+ return false;
436
+ }
437
+ if (matcher.before && dateToCheck.getTime() <= subtract(matcher.before, 1, "days").getTime()) {
438
+ return true;
439
+ }
440
+ if (matcher.after && dateToCheck.getTime() >= matcher.after.getTime()) {
441
+ return true;
442
+ }
443
+ return false;
444
+ }, [calculateDateRange, subtract]);
445
+ return react.useCallback(({ maxDaysInRange, allowedDirection, disabledDays, }) => {
446
+ const calculatedDisabledDays = (() => {
447
+ if (!allowedDirection) {
448
+ return undefined;
449
+ }
450
+ if (!sharedUtils.nonNullable(maxDaysInRange)) {
451
+ if (allowedDirection === "last") {
452
+ return {
453
+ after: nowDate,
454
+ };
455
+ }
424
456
  return {
425
- after: nowDate,
457
+ before: nowDate,
426
458
  };
427
459
  }
428
- else {
460
+ const adjustedMaxDaysInRangeCount = maxDaysInRange - 1;
461
+ if (allowedDirection === "last") {
429
462
  return {
430
- before: nowDate,
463
+ before: subtract(nowDate, adjustedMaxDaysInRangeCount, "days"),
464
+ after: nowDate,
431
465
  };
432
466
  }
433
- }
434
- // Subtract 1 from maxDaysInRange since the range is inclusive of both start and end dates
435
- const adjustedMaxDaysInRangeCount = maxDaysInRange - 1;
436
- if (allowedDirection === "last") {
437
- return {
438
- before: subtract(nowDate, adjustedMaxDaysInRangeCount, "days"),
439
- after: nowDate,
440
- };
441
- }
442
- else {
443
467
  return {
444
468
  before: nowDate,
445
469
  after: add(nowDate, adjustedMaxDaysInRangeCount, "days"),
446
470
  };
471
+ })();
472
+ if (!calculatedDisabledDays) {
473
+ return disabledDays;
474
+ }
475
+ if (!disabledDays) {
476
+ return calculatedDisabledDays;
447
477
  }
448
- }, [nowDate, subtract, add]);
478
+ return date => {
479
+ return matchesDisabledDays(calculatedDisabledDays, date) || matchesDisabledDays(disabledDays, date);
480
+ };
481
+ }, [nowDate, subtract, add, matchesDisabledDays]);
449
482
  };
450
483
 
451
484
  /**
@@ -655,14 +688,14 @@ const isTemporalDirection = (direction) => {
655
688
  * ```
656
689
  * @param {DayRangeSelectProps} props - The props for the DayRangeSelect component
657
690
  */
658
- const DayRangeSelect = ({ className, "data-testid": dataTestId, disabled = false, selectedDateRange, onRangeSelect, allowedDirection = undefined, initialDateRangeOptions, showDateRangeSearch = true, showCustomDateRangeOption = true, timezone, maxDaysInRange, size = "medium", fullWidth = false, actionButton, popoverPlacement = "bottom-start", }) => {
691
+ const DayRangeSelect = ({ className, "data-testid": dataTestId, disabled = false, selectedDateRange, onRangeSelect, allowedDirection = undefined, initialDateRangeOptions, showDateRangeSearch = true, showCustomDateRangeOption = true, timezone, maxDaysInRange, disabledDays, size = "medium", fullWidth = false, actionButton, popoverPlacement = "bottom-start", }) => {
659
692
  const [t] = useTranslation();
660
693
  const parseTemporalPeriodFromText = useParseTemporalPeriodFromText();
661
694
  const filterTemporalPeriodsInRange = useFilterTemporalPeriodsInRange();
662
695
  const formatTemporalPeriodLabel = useFormatTemporalPeriodLabel();
663
696
  const calculateDateRange = useCalculateDateRange();
664
697
  const calculateCustomDateRangeDisabledDays = useCalculateCustomDateRangeDisabledDays();
665
- const customDateRangeDisabledDays = react.useMemo(() => calculateCustomDateRangeDisabledDays({ maxDaysInRange, allowedDirection }), [calculateCustomDateRangeDisabledDays, maxDaysInRange, allowedDirection]);
698
+ const customDateRangeDisabledDays = react.useMemo(() => calculateCustomDateRangeDisabledDays({ maxDaysInRange, allowedDirection, disabledDays }), [calculateCustomDateRangeDisabledDays, maxDaysInRange, allowedDirection, disabledDays]);
666
699
  const defaultTemporalPeriods = react.useMemo(() => {
667
700
  if (initialDateRangeOptions) {
668
701
  return filterTemporalPeriodsInRange({ temporalPeriods: initialDateRangeOptions, maxDaysInRange });
package/index.esm.js CHANGED
@@ -413,37 +413,70 @@ const cvaTriggerButton = cvaMerge(["justify-start"], {
413
413
  */
414
414
  const useCalculateCustomDateRangeDisabledDays = () => {
415
415
  const { subtract, add, nowDate } = useDateAndTime();
416
- return useCallback(({ maxDaysInRange, allowedDirection, }) => {
417
- if (!allowedDirection) {
418
- return undefined;
416
+ const calculateDateRange = useCalculateDateRange();
417
+ const matchesDisabledDays = useCallback((matcher, dateToCheck) => {
418
+ if (typeof matcher === "function") {
419
+ return matcher(dateToCheck);
419
420
  }
420
- if (!nonNullable(maxDaysInRange)) {
421
- if (allowedDirection === "last") {
421
+ if (Array.isArray(matcher)) {
422
+ return matcher.some(disabledDate => disabledDate.toDateString() === dateToCheck.toDateString());
423
+ }
424
+ if ("furtherBackThanDays" in matcher) {
425
+ const dateRange = calculateDateRange({
426
+ direction: "last",
427
+ count: matcher.furtherBackThanDays,
428
+ unit: "day",
429
+ });
430
+ if (dateRange.start && dateRange.end) {
431
+ return dateToCheck < dateRange.start || dateToCheck > dateRange.end;
432
+ }
433
+ return false;
434
+ }
435
+ if (matcher.before && dateToCheck.getTime() <= subtract(matcher.before, 1, "days").getTime()) {
436
+ return true;
437
+ }
438
+ if (matcher.after && dateToCheck.getTime() >= matcher.after.getTime()) {
439
+ return true;
440
+ }
441
+ return false;
442
+ }, [calculateDateRange, subtract]);
443
+ return useCallback(({ maxDaysInRange, allowedDirection, disabledDays, }) => {
444
+ const calculatedDisabledDays = (() => {
445
+ if (!allowedDirection) {
446
+ return undefined;
447
+ }
448
+ if (!nonNullable(maxDaysInRange)) {
449
+ if (allowedDirection === "last") {
450
+ return {
451
+ after: nowDate,
452
+ };
453
+ }
422
454
  return {
423
- after: nowDate,
455
+ before: nowDate,
424
456
  };
425
457
  }
426
- else {
458
+ const adjustedMaxDaysInRangeCount = maxDaysInRange - 1;
459
+ if (allowedDirection === "last") {
427
460
  return {
428
- before: nowDate,
461
+ before: subtract(nowDate, adjustedMaxDaysInRangeCount, "days"),
462
+ after: nowDate,
429
463
  };
430
464
  }
431
- }
432
- // Subtract 1 from maxDaysInRange since the range is inclusive of both start and end dates
433
- const adjustedMaxDaysInRangeCount = maxDaysInRange - 1;
434
- if (allowedDirection === "last") {
435
- return {
436
- before: subtract(nowDate, adjustedMaxDaysInRangeCount, "days"),
437
- after: nowDate,
438
- };
439
- }
440
- else {
441
465
  return {
442
466
  before: nowDate,
443
467
  after: add(nowDate, adjustedMaxDaysInRangeCount, "days"),
444
468
  };
469
+ })();
470
+ if (!calculatedDisabledDays) {
471
+ return disabledDays;
472
+ }
473
+ if (!disabledDays) {
474
+ return calculatedDisabledDays;
445
475
  }
446
- }, [nowDate, subtract, add]);
476
+ return date => {
477
+ return matchesDisabledDays(calculatedDisabledDays, date) || matchesDisabledDays(disabledDays, date);
478
+ };
479
+ }, [nowDate, subtract, add, matchesDisabledDays]);
447
480
  };
448
481
 
449
482
  /**
@@ -653,14 +686,14 @@ const isTemporalDirection = (direction) => {
653
686
  * ```
654
687
  * @param {DayRangeSelectProps} props - The props for the DayRangeSelect component
655
688
  */
656
- const DayRangeSelect = ({ className, "data-testid": dataTestId, disabled = false, selectedDateRange, onRangeSelect, allowedDirection = undefined, initialDateRangeOptions, showDateRangeSearch = true, showCustomDateRangeOption = true, timezone, maxDaysInRange, size = "medium", fullWidth = false, actionButton, popoverPlacement = "bottom-start", }) => {
689
+ const DayRangeSelect = ({ className, "data-testid": dataTestId, disabled = false, selectedDateRange, onRangeSelect, allowedDirection = undefined, initialDateRangeOptions, showDateRangeSearch = true, showCustomDateRangeOption = true, timezone, maxDaysInRange, disabledDays, size = "medium", fullWidth = false, actionButton, popoverPlacement = "bottom-start", }) => {
657
690
  const [t] = useTranslation();
658
691
  const parseTemporalPeriodFromText = useParseTemporalPeriodFromText();
659
692
  const filterTemporalPeriodsInRange = useFilterTemporalPeriodsInRange();
660
693
  const formatTemporalPeriodLabel = useFormatTemporalPeriodLabel();
661
694
  const calculateDateRange = useCalculateDateRange();
662
695
  const calculateCustomDateRangeDisabledDays = useCalculateCustomDateRangeDisabledDays();
663
- const customDateRangeDisabledDays = useMemo(() => calculateCustomDateRangeDisabledDays({ maxDaysInRange, allowedDirection }), [calculateCustomDateRangeDisabledDays, maxDaysInRange, allowedDirection]);
696
+ const customDateRangeDisabledDays = useMemo(() => calculateCustomDateRangeDisabledDays({ maxDaysInRange, allowedDirection, disabledDays }), [calculateCustomDateRangeDisabledDays, maxDaysInRange, allowedDirection, disabledDays]);
664
697
  const defaultTemporalPeriods = useMemo(() => {
665
698
  if (initialDateRangeOptions) {
666
699
  return filterTemporalPeriodsInRange({ temporalPeriods: initialDateRangeOptions, maxDaysInRange });
package/package.json CHANGED
@@ -1,20 +1,20 @@
1
1
  {
2
2
  "name": "@trackunit/react-date-and-time-components",
3
- "version": "1.26.13",
3
+ "version": "1.26.16",
4
4
  "repository": "https://github.com/Trackunit/manager",
5
5
  "license": "SEE LICENSE IN LICENSE.txt",
6
6
  "engines": {
7
7
  "node": ">=24.x"
8
8
  },
9
9
  "dependencies": {
10
- "@trackunit/react-components": "1.23.8",
11
- "@trackunit/date-and-time-utils": "1.12.6",
12
- "@trackunit/react-date-and-time-hooks": "1.23.9",
13
- "@trackunit/css-class-variance-utilities": "1.12.6",
14
- "@trackunit/ui-icons": "1.12.7",
15
- "@trackunit/shared-utils": "1.14.7",
16
- "@trackunit/i18n-library-translation": "1.20.9",
17
- "@trackunit/react-form-components": "1.24.13",
10
+ "@trackunit/react-components": "1.23.10",
11
+ "@trackunit/date-and-time-utils": "1.12.7",
12
+ "@trackunit/react-date-and-time-hooks": "1.23.11",
13
+ "@trackunit/css-class-variance-utilities": "1.12.7",
14
+ "@trackunit/ui-icons": "1.12.8",
15
+ "@trackunit/shared-utils": "1.14.8",
16
+ "@trackunit/i18n-library-translation": "1.20.11",
17
+ "@trackunit/react-form-components": "1.24.15",
18
18
  "string-ts": "^2.0.0",
19
19
  "tailwind-merge": "^2.0.0",
20
20
  "react-calendar": "^6.0.0"
@@ -43,6 +43,10 @@ export type DayRangeSelectProps = CommonProps & {
43
43
  * The maximum amount of days that can be selected
44
44
  */
45
45
  maxDaysInRange?: number;
46
+ /**
47
+ * Define any days which may not be selected in the custom date range picker.
48
+ */
49
+ disabledDays?: DayRangePickerProps["disabledDays"];
46
50
  /**
47
51
  * The size of the button.
48
52
  */
@@ -88,4 +92,4 @@ export type DayRangeSelectProps = CommonProps & {
88
92
  * ```
89
93
  * @param {DayRangeSelectProps} props - The props for the DayRangeSelect component
90
94
  */
91
- export declare const DayRangeSelect: ({ className, "data-testid": dataTestId, disabled, selectedDateRange, onRangeSelect, allowedDirection, initialDateRangeOptions, showDateRangeSearch, showCustomDateRangeOption, timezone, maxDaysInRange, size, fullWidth, actionButton, popoverPlacement, }: DayRangeSelectProps) => import("react/jsx-runtime").JSX.Element;
95
+ export declare const DayRangeSelect: ({ className, "data-testid": dataTestId, disabled, selectedDateRange, onRangeSelect, allowedDirection, initialDateRangeOptions, showDateRangeSearch, showCustomDateRangeOption, timezone, maxDaysInRange, disabledDays, size, fullWidth, actionButton, popoverPlacement, }: DayRangeSelectProps) => import("react/jsx-runtime").JSX.Element;
@@ -3,9 +3,10 @@ import { TemporalDirection } from "../../types";
3
3
  export type CalculateCustomDateRangeDisabledDaysProps = {
4
4
  maxDaysInRange: number | undefined;
5
5
  allowedDirection: TemporalDirection | undefined;
6
+ disabledDays?: DayRangePickerProps["disabledDays"];
6
7
  };
7
8
  /**
8
9
  * Calculate the disabled days for the custom date range picker based on the maxDaysInRange and allowedDirection.
9
10
  * The range is inclusive of both start and end dates, so we subtract 1 from maxDaysInRange to get the correct number of days.
10
11
  */
11
- export declare const useCalculateCustomDateRangeDisabledDays: () => ({ maxDaysInRange, allowedDirection, }: CalculateCustomDateRangeDisabledDaysProps) => DayRangePickerProps["disabledDays"] | undefined;
12
+ export declare const useCalculateCustomDateRangeDisabledDays: () => ({ maxDaysInRange, allowedDirection, disabledDays, }: CalculateCustomDateRangeDisabledDaysProps) => DayRangePickerProps["disabledDays"] | undefined;