@homecode/ui 4.17.0 → 4.17.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.
package/dist/esm/index.js CHANGED
@@ -45,6 +45,8 @@ export { env };
45
45
  export { config } from './src/tools/config.js';
46
46
  import * as array from './src/tools/array.js';
47
47
  export { array };
48
+ import * as date from './src/tools/date.js';
49
+ export { date };
48
50
  import * as string from './src/tools/string.js';
49
51
  export { string };
50
52
  import * as number from './src/tools/number.js';
@@ -25,7 +25,7 @@ const renderDayDefault = (val, props) => {
25
25
  const { day, year, month } = val;
26
26
  return (jsx("div", { ...props, children: day }, `${year}-${month}-${day}`));
27
27
  };
28
- function Calendar({ className, value, onDayPointerDown, onDayPointerUp, renderDay, renderWeekDayLabel, renderMonthLabel, renderMonthesLabel, renderYearLabel, startOfWeek = 1, weekendClassName, hideOtherMonthDays, size, }) {
28
+ function Calendar({ className, value, onDayPointerDown, onDayPointerUp, renderDay, renderWeekDayLabel, renderMonthLabel, renderMonthesLabel, renderYearLabel, startOfWeek = 1, weekendClassName, hideOtherMonthDays, isDayDisabled, size, }) {
29
29
  const date = useMemo(() => valueToDate(value), [value]);
30
30
  const [month, setMonth] = useState(date.getMonth() + 1);
31
31
  const [year, setYear] = useState(date.getFullYear());
@@ -50,8 +50,8 @@ function Calendar({ className, value, onDayPointerDown, onDayPointerUp, renderDa
50
50
  // @ts-ignore
51
51
  size: size, label: renderYearLabel?.(year) ?? 'Year', value: year,
52
52
  // @ts-ignore
53
- onChange: onYearChange, onBlur: onYearBlur }), jsx(Select, { className: S.month, size: size, label: renderMonthesLabel?.(month) ?? 'Month', options: monthOptions, value: month, onChange: val => setMonth(val) })] }), jsx("div", { className: S.weekDays, children: weekDaysArray.map((day, weekdayIndex) => (jsx("div", { className: cn(S.day, isWeekend(weekdayIndex) && weekendClassName), children: renderWeekDayLabel?.(day) ?? weekDays[day] }, `weekday-${day}`))) }), jsx("div", { className: S.days, children: daysArray.map((day, weekdayIndex) => {
54
- const className = cn(S.day, day.currentMonth && S.currMonth, isWeekend(weekdayIndex) && weekendClassName, isSameDay(day, value) && S.selected);
53
+ onChange: onYearChange, onBlur: onYearBlur }), jsx(Select, { className: S.month, size: size, label: renderMonthesLabel?.(month) ?? 'Month', options: monthOptions, value: month, onChange: val => setMonth(val), required: true, hideRequiredStar: true })] }), jsx("div", { className: S.weekDays, children: weekDaysArray.map((day, weekdayIndex) => (jsx("div", { className: cn(S.day, isWeekend(weekdayIndex) && weekendClassName), children: renderWeekDayLabel?.(day) ?? weekDays[day] }, `weekday-${day}`))) }), jsx("div", { className: S.days, children: daysArray.map((day, weekdayIndex) => {
54
+ const className = cn(S.day, day.currentMonth && S.currMonth, isWeekend(weekdayIndex) && weekendClassName, isSameDay(day, value) && S.selected, isDayDisabled?.(day) && S.disabled);
55
55
  const dayProps = { className };
56
56
  if (onDayPointerDown) {
57
57
  dayProps.onPointerDown = () => onDayPointerDown(day);
@@ -1,7 +1,7 @@
1
1
  import styleInject from '../../../node_modules/style-inject/dist/style-inject.es.js';
2
2
 
3
- var css_248z = ".Calendar_size-s__MFLPb{font-size:.5em}.Calendar_size-m__IGeoI{font-size:.75em}.Calendar_size-l__a2zct{font-size:1em}.Calendar_root__v8Jg6{display:flex;flex-direction:column}.Calendar_header__IHzS-{align-items:center;display:flex;justify-content:space-between}.Calendar_month__gi10Q{width:100%!important}.Calendar_year__UlmLM{min-width:5em}.Calendar_year__UlmLM input{min-width:0;min-width:auto}.Calendar_month__gi10Q{margin-left:var(--indent-s)}.Calendar_weekDays__Pglyw{align-items:center;color:var(--accent-color-alpha-500);display:flex;font-size:.75em;margin-top:var(--indent-s);width:100%}.Calendar_weekDays__Pglyw .Calendar_day__A3NG-{padding:1.5em 0}.Calendar_size-s__MFLPb .Calendar_weekDays__Pglyw .Calendar_day__A3NG-:first-child{border-top-left-radius:4px}.Calendar_size-s__MFLPb .Calendar_weekDays__Pglyw .Calendar_day__A3NG-:last-child{border-top-right-radius:4px}.Calendar_size-m__IGeoI .Calendar_weekDays__Pglyw .Calendar_day__A3NG-:first-child{border-top-left-radius:6px}.Calendar_size-m__IGeoI .Calendar_weekDays__Pglyw .Calendar_day__A3NG-:last-child{border-top-right-radius:6px}.Calendar_size-l__a2zct .Calendar_weekDays__Pglyw .Calendar_day__A3NG-:first-child{border-top-left-radius:8px}.Calendar_size-l__a2zct .Calendar_weekDays__Pglyw .Calendar_day__A3NG-:last-child{border-top-right-radius:8px}.Calendar_days__64U-y{display:flex;flex-wrap:wrap;justify-content:space-between;-webkit-user-select:none;-moz-user-select:none;user-select:none}.Calendar_days__64U-y .Calendar_day__A3NG-:not(.Calendar_currMonth__oL4nl){color:var(--accent-color-alpha-500)}.Calendar_hideOtherMonthDays__DydjR .Calendar_days__64U-y .Calendar_day__A3NG-:not(.Calendar_currMonth__oL4nl){opacity:0;pointer-events:none}.Calendar_size-s__MFLPb .Calendar_days__64U-y .Calendar_day__A3NG-:last-child{border-bottom-right-radius:4px}.Calendar_size-m__IGeoI .Calendar_days__64U-y .Calendar_day__A3NG-:last-child{border-bottom-right-radius:6px}.Calendar_size-l__a2zct .Calendar_days__64U-y .Calendar_day__A3NG-:last-child{border-bottom-right-radius:8px}.Calendar_day__A3NG-{align-items:center;display:flex;height:2em;justify-content:center;min-width:0;min-width:auto;padding:0;width:14.28571%}.Calendar_day__A3NG-.Calendar_selected__ffB6-{background-color:var(--active-color-alpha-500)!important}.Calendar_day__A3NG-.Calendar_currMonth__oL4nl{font-weight:700}";
4
- var S = {"size-s":"Calendar_size-s__MFLPb","size-m":"Calendar_size-m__IGeoI","size-l":"Calendar_size-l__a2zct","root":"Calendar_root__v8Jg6","header":"Calendar_header__IHzS-","month":"Calendar_month__gi10Q","year":"Calendar_year__UlmLM","weekDays":"Calendar_weekDays__Pglyw","day":"Calendar_day__A3NG-","days":"Calendar_days__64U-y","currMonth":"Calendar_currMonth__oL4nl","hideOtherMonthDays":"Calendar_hideOtherMonthDays__DydjR","selected":"Calendar_selected__ffB6-"};
3
+ var css_248z = ".Calendar_size-s__MFLPb{font-size:.5em}.Calendar_size-m__IGeoI{font-size:.75em}.Calendar_size-l__a2zct{font-size:1em}.Calendar_root__v8Jg6{display:flex;flex-direction:column}.Calendar_header__IHzS-{align-items:center;display:flex;justify-content:space-between}.Calendar_month__gi10Q{width:100%}.Calendar_year__UlmLM{min-width:5em}.Calendar_year__UlmLM input{min-width:0;min-width:auto}.Calendar_month__gi10Q{margin-left:var(--indent-s)}.Calendar_weekDays__Pglyw{align-items:center;color:var(--accent-color-alpha-500);display:flex;font-size:.75em;margin-top:var(--indent-s);width:100%}.Calendar_weekDays__Pglyw .Calendar_day__A3NG-{padding:1.5em 0}.Calendar_size-s__MFLPb .Calendar_weekDays__Pglyw .Calendar_day__A3NG-:first-child{border-top-left-radius:4px}.Calendar_size-s__MFLPb .Calendar_weekDays__Pglyw .Calendar_day__A3NG-:last-child{border-top-right-radius:4px}.Calendar_size-m__IGeoI .Calendar_weekDays__Pglyw .Calendar_day__A3NG-:first-child{border-top-left-radius:6px}.Calendar_size-m__IGeoI .Calendar_weekDays__Pglyw .Calendar_day__A3NG-:last-child{border-top-right-radius:6px}.Calendar_size-l__a2zct .Calendar_weekDays__Pglyw .Calendar_day__A3NG-:first-child{border-top-left-radius:8px}.Calendar_size-l__a2zct .Calendar_weekDays__Pglyw .Calendar_day__A3NG-:last-child{border-top-right-radius:8px}.Calendar_days__64U-y{display:flex;flex-wrap:wrap;justify-content:space-between;-webkit-user-select:none;-moz-user-select:none;user-select:none}.Calendar_days__64U-y .Calendar_day__A3NG-:not(.Calendar_currMonth__oL4nl){color:var(--accent-color-alpha-500)}.Calendar_hideOtherMonthDays__DydjR .Calendar_days__64U-y .Calendar_day__A3NG-:not(.Calendar_currMonth__oL4nl){opacity:0;pointer-events:none}.Calendar_size-s__MFLPb .Calendar_days__64U-y .Calendar_day__A3NG-:first-child{border-top-left-radius:4px}.Calendar_size-m__IGeoI .Calendar_days__64U-y .Calendar_day__A3NG-:first-child{border-top-left-radius:6px}.Calendar_size-l__a2zct .Calendar_days__64U-y .Calendar_day__A3NG-:first-child{border-top-left-radius:8px}.Calendar_size-s__MFLPb .Calendar_days__64U-y .Calendar_day__A3NG-:last-child{border-bottom-right-radius:4px}.Calendar_size-m__IGeoI .Calendar_days__64U-y .Calendar_day__A3NG-:last-child{border-bottom-right-radius:6px}.Calendar_size-l__a2zct .Calendar_days__64U-y .Calendar_day__A3NG-:last-child{border-bottom-right-radius:8px}.Calendar_size-s__MFLPb .Calendar_days__64U-y .Calendar_day__A3NG-:nth-child(7){border-top-right-radius:4px}.Calendar_size-m__IGeoI .Calendar_days__64U-y .Calendar_day__A3NG-:nth-child(7){border-top-right-radius:6px}.Calendar_size-l__a2zct .Calendar_days__64U-y .Calendar_day__A3NG-:nth-child(7){border-top-right-radius:8px}.Calendar_size-s__MFLPb .Calendar_days__64U-y .Calendar_day__A3NG-:nth-last-child(7){border-bottom-left-radius:4px}.Calendar_size-m__IGeoI .Calendar_days__64U-y .Calendar_day__A3NG-:nth-last-child(7){border-bottom-left-radius:6px}.Calendar_size-l__a2zct .Calendar_days__64U-y .Calendar_day__A3NG-:nth-last-child(7){border-bottom-left-radius:8px}.Calendar_day__A3NG-{align-items:center;display:flex;height:2em;justify-content:center;min-width:0;min-width:auto;padding:0;width:14.28571%}.Calendar_day__A3NG-.Calendar_disabled__sZi-f{background-color:var(--accent-color-alpha-100);border-radius:0;opacity:.3;pointer-events:none}.Calendar_day__A3NG-.Calendar_selected__ffB6-{background-color:var(--active-color-alpha-500)!important}.Calendar_day__A3NG-.Calendar_currMonth__oL4nl{font-weight:700}";
4
+ var S = {"size-s":"Calendar_size-s__MFLPb","size-m":"Calendar_size-m__IGeoI","size-l":"Calendar_size-l__a2zct","root":"Calendar_root__v8Jg6","header":"Calendar_header__IHzS-","month":"Calendar_month__gi10Q","year":"Calendar_year__UlmLM","weekDays":"Calendar_weekDays__Pglyw","day":"Calendar_day__A3NG-","days":"Calendar_days__64U-y","currMonth":"Calendar_currMonth__oL4nl","hideOtherMonthDays":"Calendar_hideOtherMonthDays__DydjR","disabled":"Calendar_disabled__sZi-f","selected":"Calendar_selected__ffB6-"};
5
5
  styleInject(css_248z);
6
6
 
7
7
  export { S as default };
@@ -1,3 +1,14 @@
1
+ function dateToString(date) {
2
+ return `${date.year}-${date.month}-${date.day}`;
3
+ }
4
+ function strigToDate(dateString) {
5
+ const [year, month, day] = dateString.split('-');
6
+ return {
7
+ year: Number(year),
8
+ month: Number(month),
9
+ day: Number(day),
10
+ };
11
+ }
1
12
  function isDateEqual(date1, date2) {
2
13
  return (date1.year === date2.year &&
3
14
  date1.month === date2.month &&
@@ -17,4 +28,4 @@ function isDateBetween(date, startDate, endDate) {
17
28
  return isDateAfter(date, startDate) && isDateBefore(date, endDate);
18
29
  }
19
30
 
20
- export { isDateAfter, isDateBefore, isDateBetween, isDateEqual };
31
+ export { dateToString, isDateAfter, isDateBefore, isDateBetween, isDateEqual, strigToDate };
@@ -3,7 +3,7 @@ import { useState, useCallback, createElement } from 'react';
3
3
  import cn from 'classnames';
4
4
  import { Calendar } from '../Calendar/Calendar.js';
5
5
  import { Button } from '../Button/Button.js';
6
- import { isDateAfter, isDateBetween, isDateEqual } from './DatePicker.helpers.js';
6
+ import { dateToString, isDateAfter, strigToDate, isDateBetween, isDateEqual } from './DatePicker.helpers.js';
7
7
  import S from './DatePicker.styl.js';
8
8
 
9
9
  function DatePicker(props) {
@@ -11,32 +11,36 @@ function DatePicker(props) {
11
11
  const isRange = Array.isArray(value);
12
12
  const [isPicking, setIsPicking] = useState(false);
13
13
  const onFirstDateChange = useCallback((val) => {
14
- onChange(isRange ? [val, value[1]] : val);
14
+ const valStr = dateToString(val);
15
+ onChange(isRange ? [valStr, value[1]] : valStr);
15
16
  }, [value, onChange, isRange]);
16
17
  const onPointerDown = () => setIsPicking(true);
17
18
  const onPointerUp = () => setIsPicking(false);
18
19
  const renderDay = useCallback((val, { className, ...props }) => {
19
20
  const { day, year, month } = val;
21
+ const valStr = dateToString(val);
20
22
  if (isRange && isPicking) {
21
23
  props.onPointerOver = () => {
22
- const newVal = isDateAfter(value[0], val)
23
- ? [val, value[0]]
24
- : [value[0], val];
24
+ const newVal = isDateAfter(strigToDate(value[0]), val)
25
+ ? [valStr, value[0]]
26
+ : [value[0], valStr];
25
27
  onChange(newVal);
26
28
  };
27
29
  }
28
30
  const classes = [className, S.day];
29
31
  if (isRange) {
30
- if (isDateBetween(val, ...value))
32
+ const from = strigToDate(value[0]);
33
+ const to = strigToDate(value[1]);
34
+ if (isDateBetween(val, from, to))
31
35
  classes.push(S.between);
32
- if (isDateEqual(val, value[0]))
36
+ if (isDateEqual(val, from))
33
37
  classes.push(S.start);
34
- if (isDateEqual(val, value[1]))
38
+ if (isDateEqual(val, to))
35
39
  classes.push(S.end);
36
40
  }
37
41
  return (createElement(Button, { ...props, variant: "clear", className: cn(classes), size: size, key: `${year}-${month}-${day}` }, day));
38
42
  }, [size, isPicking, isRange, value, onChange]);
39
- return (jsxs("div", { className: cn(S.root, props.className), onPointerDown: onPointerDown, onPointerUp: onPointerUp, children: [jsx(Calendar, { size: size, hideOtherMonthDays: isRange, ...calendarProps, renderDay: renderDay, value: isRange ? value[0] : value, onDayPointerDown: onFirstDateChange, onDayPointerUp: undefined }), isRange && (jsx(Calendar, { size: size, hideOtherMonthDays: isRange, ...calendarProps, renderDay: renderDay, value: value[1], onDayPointerDown: val => onChange([value[0], val]), onDayPointerUp: val => onChange([value[0], val]) }))] }));
43
+ return (jsxs("div", { className: cn(S.root, props.className), onPointerDown: onPointerDown, onPointerUp: onPointerUp, children: [jsx(Calendar, { size: size, hideOtherMonthDays: isRange, ...calendarProps, renderDay: renderDay, value: strigToDate(isRange ? value[0] : value), onDayPointerDown: onFirstDateChange, onDayPointerUp: undefined }), isRange && (jsx(Calendar, { size: size, hideOtherMonthDays: isRange, ...calendarProps, renderDay: renderDay, value: strigToDate(value[1]), onDayPointerDown: val => onChange([value[0], dateToString(val)]), onDayPointerUp: val => onChange([value[0], dateToString(val)]) }))] }));
40
44
  }
41
45
 
42
46
  export { DatePicker };
@@ -1,5 +1,6 @@
1
1
  import { jsx, jsxs, Fragment } from 'react/jsx-runtime';
2
2
  import cn from 'classnames';
3
+ import { strToDate } from '../../tools/date.js';
3
4
  import { DateTime } from '../DateTime/DateTime.js';
4
5
  import { DatePicker } from '../DatePicker/DatePicker.js';
5
6
  import { Button } from '../Button/Button.js';
@@ -9,7 +10,7 @@ import S from './DatePickerInput.styl.js';
9
10
  function DatePickerInput(props) {
10
11
  const { value, variant = 'default', size = 'm', popupProps, displayFormat = 'MMM Do YYYY', } = props;
11
12
  const isRange = Array.isArray(value);
12
- return (jsx(Popup, { size: size, focusControl: true, direction: "bottom-right", ...popupProps, trigger: jsx(Button, { variant: variant, size: size, children: isRange ? (jsxs(Fragment, { children: [jsx(DateTime, { value: new Date(value[0].year, value[0].month - 1, value[0].day), format: displayFormat }), ' - ', jsx(DateTime, { value: new Date(value[1].year, value[1].month - 1, value[1].day), format: displayFormat })] })) : (jsx(DateTime, { value: new Date(value.year, value.month - 1, value.day), format: displayFormat })) }), contentProps: {
13
+ return (jsx(Popup, { size: size, focusControl: true, direction: "bottom-right", ...popupProps, trigger: jsx(Button, { variant: variant, size: size, children: isRange ? (jsxs(Fragment, { children: [jsx(DateTime, { value: strToDate(value[0]), format: displayFormat }), ' - ', jsx(DateTime, { value: strToDate(value[1]), format: displayFormat })] })) : (jsx(DateTime, { value: strToDate(value), format: displayFormat })) }), contentProps: {
13
14
  className: cn(S.popupContent, isRange && S.range, S[`size-${size}`]),
14
15
  }, content: jsx(DatePicker, { ...props, className: S.content, calendarProps: { className: S.calendar } }) }));
15
16
  }
@@ -242,7 +242,8 @@ class Popup extends Component {
242
242
  return;
243
243
  }
244
244
  // if scrolling outside this popup - close it
245
- if (!this.isPointerOver(e.target, S.content)) {
245
+ if (!this.isPointerOver(e.target, S.content) &&
246
+ !childs[this.id]?.length) {
246
247
  this.needDropOffset = true;
247
248
  this.close();
248
249
  }
@@ -280,7 +281,7 @@ class Popup extends Component {
280
281
  this.focused = false;
281
282
  this.props.triggerProps?.onBlur?.(e);
282
283
  // give time to fire clicks inside popup
283
- this.timers.after(80, () => {
284
+ this.timers.after(60, () => {
284
285
  if (!this.isLastClickInside())
285
286
  this.close();
286
287
  });
@@ -0,0 +1,11 @@
1
+ /**
2
+ * Convert ISO 8601 format ("YYYY-MM-DD") to Date object
3
+ * @param str
4
+ * @returns Date
5
+ */
6
+ const strToDate = (str) => {
7
+ const [year, month, day] = str.split('-').map(Number);
8
+ return new Date(year, month - 1, day);
9
+ };
10
+
11
+ export { strToDate };
@@ -1,3 +1,3 @@
1
1
  /// <reference types="react" />
2
2
  import * as T from './Calendar.types';
3
- export declare function Calendar({ className, value, onDayPointerDown, onDayPointerUp, renderDay, renderWeekDayLabel, renderMonthLabel, renderMonthesLabel, renderYearLabel, startOfWeek, weekendClassName, hideOtherMonthDays, size, }: T.Props): JSX.Element;
3
+ export declare function Calendar({ className, value, onDayPointerDown, onDayPointerUp, renderDay, renderWeekDayLabel, renderMonthLabel, renderMonthesLabel, renderYearLabel, startOfWeek, weekendClassName, hideOtherMonthDays, isDayDisabled, size, }: T.Props): JSX.Element;
@@ -22,4 +22,5 @@ export type Props = {
22
22
  renderMonthLabel?: (month: number) => string;
23
23
  weekendClassName?: string;
24
24
  hideOtherMonthDays?: boolean;
25
+ isDayDisabled?: (day: Day) => boolean;
25
26
  };
@@ -1,4 +1,10 @@
1
1
  import type { Date } from 'uilib/types';
2
+ export declare function dateToString(date: Date): string;
3
+ export declare function strigToDate(dateString: string): {
4
+ year: number;
5
+ month: number;
6
+ day: number;
7
+ };
2
8
  export declare function isDateEqual(date1: Date, date2: Date): boolean;
3
9
  export declare function isDateBefore(date1: Date, date2: Date): boolean;
4
10
  export declare function isDateAfter(date1: Date, date2: Date): boolean;
@@ -1,6 +1,6 @@
1
- import type { Size, Date } from 'uilib/types';
1
+ import type { Size } from 'uilib/types';
2
2
  import type { Props as CalendarProps } from 'uilib/components/Calendar/Calendar.types';
3
- export type Value = Date | [Date, Date];
3
+ export type Value = string | [string, string];
4
4
  export type Props = {
5
5
  className?: string;
6
6
  value: Value;
@@ -1,6 +1,6 @@
1
- import type { Date, Size, Variant } from 'uilib/types';
1
+ import type { Size, Variant } from 'uilib/types';
2
2
  import type { Props as PopupProps } from 'uilib/components/Popup/Popup.types';
3
- export type Value = Date | [Date, Date];
3
+ export type Value = string | [string, string];
4
4
  export type Props = {
5
5
  className?: string;
6
6
  size?: Size;
@@ -0,0 +1,6 @@
1
+ /**
2
+ * Convert ISO 8601 format ("YYYY-MM-DD") to Date object
3
+ * @param str
4
+ * @returns Date
5
+ */
6
+ export declare const strToDate: (str: string) => Date;
@@ -1,6 +1,7 @@
1
1
  export * as env from './env';
2
2
  export { config } from './config';
3
3
  export * as array from './array';
4
+ export * as date from './date';
4
5
  export * as string from './string';
5
6
  export * as number from './number';
6
7
  export * as object from './object';
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@homecode/ui",
3
- "version": "4.17.0",
3
+ "version": "4.17.2",
4
4
  "description": "React UI components library",
5
5
  "scripts": {
6
6
  "test": "echo \"Error: no test specified\" && exit 1",
@@ -40,7 +40,7 @@
40
40
  "types": "dist/esm/types/index.d.ts",
41
41
  "type": "module",
42
42
  "dependencies": {
43
- "@homecode/ui": "^4.11.1",
43
+ "@homecode/ui": "^4.17.1",
44
44
  "@pmmmwh/react-refresh-webpack-plugin": "^0.5.10",
45
45
  "@rollup/plugin-typescript": "^11.0.0",
46
46
  "classnames": "^2.3.2",