@colisweb/rescript-toolkit 4.24.4 → 4.26.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.
package/package.json
CHANGED
|
@@ -37,6 +37,16 @@ let useUpdate = () => {
|
|
|
37
37
|
React.useCallback1(() => setState(SafeIncrement.increment), [])
|
|
38
38
|
}
|
|
39
39
|
|
|
40
|
+
let useDebounceValue = (value, ~debounceDuration=200) => {
|
|
41
|
+
let (state, setState) = React.useState(() => value)
|
|
42
|
+
|
|
43
|
+
useDebounce(() => {
|
|
44
|
+
setState(_ => value)
|
|
45
|
+
}, debounceDuration, [value])->ignore
|
|
46
|
+
|
|
47
|
+
state
|
|
48
|
+
}
|
|
49
|
+
|
|
40
50
|
let useGetSet = initialStateGetter => {
|
|
41
51
|
let state = React.useRef(initialStateGetter())
|
|
42
52
|
let update = useUpdate()
|
|
@@ -49,6 +49,7 @@ let make = (
|
|
|
49
49
|
~periodLength=7,
|
|
50
50
|
~children,
|
|
51
51
|
~onChange: option<state => unit>=?,
|
|
52
|
+
~disabledBefore: option<Js.Date.t>=?,
|
|
52
53
|
) => {
|
|
53
54
|
let {isSm} = Toolkit__Hooks.useMediaQuery()
|
|
54
55
|
|
|
@@ -56,13 +57,20 @@ let make = (
|
|
|
56
57
|
(state, action) =>
|
|
57
58
|
switch action {
|
|
58
59
|
| PreviousPeriod =>
|
|
60
|
+
let previousPeriodStart = state.period.start->DateFns.subDays(periodLength)
|
|
61
|
+
let selectedDay =
|
|
62
|
+
disabledBefore->Option.mapWithDefault(previousPeriodStart, disabledBefore =>
|
|
63
|
+
previousPeriodStart->DateFns.isBefore(disabledBefore)
|
|
64
|
+
? disabledBefore
|
|
65
|
+
: previousPeriodStart
|
|
66
|
+
)
|
|
59
67
|
UpdateWithSideEffects(
|
|
60
68
|
{
|
|
61
69
|
period: {
|
|
62
70
|
start: state.period.start->DateFns.subDays(periodLength)->DateFns.startOfDay,
|
|
63
71
|
end_: state.period.start->DateFns.subDays(1),
|
|
64
72
|
},
|
|
65
|
-
selectedDay
|
|
73
|
+
selectedDay,
|
|
66
74
|
},
|
|
67
75
|
({state}) => {
|
|
68
76
|
updateQueryParams(state)
|
|
@@ -114,19 +122,32 @@ let make = (
|
|
|
114
122
|
}
|
|
115
123
|
}
|
|
116
124
|
|
|
125
|
+
let selectedDayWithDefault =
|
|
126
|
+
selectedDay->Option.getWithDefault(startOfWeek->Option.getWithDefault(defaultPeriod.start))
|
|
127
|
+
|
|
128
|
+
let selectedDayNotInDisabledRange =
|
|
129
|
+
disabledBefore->Option.mapWithDefault(selectedDayWithDefault, disabledBefore =>
|
|
130
|
+
selectedDayWithDefault->DateFns.isBefore(disabledBefore)
|
|
131
|
+
? disabledBefore
|
|
132
|
+
: selectedDayWithDefault
|
|
133
|
+
)
|
|
134
|
+
|
|
117
135
|
{
|
|
118
136
|
period: startOfWeek->Option.mapWithDefault(defaultPeriod, start => {
|
|
119
137
|
start,
|
|
120
138
|
end_: isSm ? start->DateFns.addDays(periodLength - 1) : start->DateFns.addDays(2),
|
|
121
139
|
}),
|
|
122
|
-
selectedDay:
|
|
123
|
-
startOfWeek->Option.getWithDefault(defaultPeriod.start),
|
|
124
|
-
),
|
|
140
|
+
selectedDay: selectedDayNotInDisabledRange,
|
|
125
141
|
}
|
|
126
142
|
},
|
|
127
143
|
)
|
|
128
144
|
let intl = useIntl()
|
|
129
145
|
|
|
146
|
+
let days = DateFns.eachDayOfInterval({
|
|
147
|
+
start: period.start,
|
|
148
|
+
end_: period.end_,
|
|
149
|
+
})
|
|
150
|
+
|
|
130
151
|
<div className={containerClassName}>
|
|
131
152
|
<div className={cx(["border-neutral-300 flex justify-center items-center py-3", className])}>
|
|
132
153
|
<Toolkit__Ui_IconButton
|
|
@@ -135,19 +156,25 @@ let make = (
|
|
|
135
156
|
color=#neutral
|
|
136
157
|
onClick={_ => dispatch(PreviousPeriod)}
|
|
137
158
|
ariaLabel="previous week"
|
|
159
|
+
disabled=?{disabledBefore->Option.map(disabledBefore => {
|
|
160
|
+
let isPreviousPeriodOutOfBounds =
|
|
161
|
+
period.start->DateFns.subDays(1)->DateFns.isBefore(disabledBefore)
|
|
162
|
+
isPreviousPeriodOutOfBounds
|
|
163
|
+
})}
|
|
138
164
|
icon={<ReactIcons.MdKeyboardArrowLeft size=30 />}
|
|
139
165
|
/>
|
|
140
166
|
<div className="flex items-center mx-2">
|
|
141
|
-
{
|
|
142
|
-
start: period.start,
|
|
143
|
-
end_: period.end_,
|
|
144
|
-
})
|
|
167
|
+
{days
|
|
145
168
|
->Array.mapWithIndex((i, day) => {
|
|
146
169
|
let formattedDay =
|
|
147
170
|
intl->Intl.formatDateWithOptions(day, dateTimeFormatOptions(~weekday=#long, ()))
|
|
148
171
|
|
|
149
172
|
let isSelected = DateFns.isSameDay(selectedDay, day)
|
|
150
173
|
|
|
174
|
+
let isDisabled =
|
|
175
|
+
disabledBefore->Option.mapWithDefault(false, disabledBefore =>
|
|
176
|
+
day->DateFns.isBefore(disabledBefore)
|
|
177
|
+
)
|
|
151
178
|
<React.Fragment key={i->Int.toString ++ "-day"}>
|
|
152
179
|
{i == 0 || day->DateFns.isFirstDayOfMonth
|
|
153
180
|
? <p className="text-xs text-neutral-700 uppercase">
|
|
@@ -155,8 +182,11 @@ let make = (
|
|
|
155
182
|
</p>
|
|
156
183
|
: React.null}
|
|
157
184
|
<div
|
|
158
|
-
onClick={_ => dispatch(UpdateSelectedDay(day))}
|
|
159
|
-
className=
|
|
185
|
+
onClick={_ => isDisabled ? () : dispatch(UpdateSelectedDay(day))}
|
|
186
|
+
className={cx([
|
|
187
|
+
"flex flex-col items-stretch w-16 mx-1 font-display",
|
|
188
|
+
isDisabled ? "opacity-50 cursor-not-allowed" : "",
|
|
189
|
+
])}>
|
|
160
190
|
<p
|
|
161
191
|
className={cx([
|
|
162
192
|
"flex flex-col items-center justify-center uppercase text-xs w-full rounded-sm leading-tight py-1",
|