@sqrzro/ui 4.0.0-alpha.4 → 4.0.0-alpha.41

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 (281) hide show
  1. package/dist/addon/config.d.ts +5 -0
  2. package/dist/addon/config.js +12 -0
  3. package/dist/addon/defaults.d.ts +3 -0
  4. package/dist/addon/defaults.js +6 -0
  5. package/dist/addon/index.d.ts +5 -0
  6. package/dist/addon/index.js +8 -0
  7. package/dist/addon/interfaces.d.ts +8 -0
  8. package/dist/components/buttons/ActionButton/index.d.ts +8 -6
  9. package/dist/components/buttons/ActionButton/index.js +3 -27
  10. package/dist/components/buttons/Button/index.d.ts +5 -5
  11. package/dist/components/buttons/Button/index.js +7 -17
  12. package/dist/components/collections/Collection/index.d.ts +9 -3
  13. package/dist/components/collections/Collection/index.js +8 -7
  14. package/dist/components/collections/DataTable/index.d.ts +14 -0
  15. package/dist/components/collections/DataTable/index.js +14 -0
  16. package/dist/components/collections/EmptyMessage/index.d.ts +1 -1
  17. package/dist/components/collections/EmptyMessage/index.js +6 -4
  18. package/dist/components/collections/EmptyMessageAction/index.d.ts +2 -2
  19. package/dist/components/collections/EmptyMessageAction/index.js +1 -1
  20. package/dist/components/collections/List/index.d.ts +6 -4
  21. package/dist/components/collections/List/index.js +2 -2
  22. package/dist/components/collections/ListClientComponent/index.d.ts +7 -4
  23. package/dist/components/collections/ListClientComponent/index.js +8 -5
  24. package/dist/components/collections/ListItem/index.d.ts +10 -3
  25. package/dist/components/collections/ListItem/index.js +15 -23
  26. package/dist/components/collections/ListItemMenu/index.d.ts +8 -0
  27. package/dist/components/collections/ListItemMenu/index.js +7 -0
  28. package/dist/components/collections/ListItemMeta/index.d.ts +6 -4
  29. package/dist/components/collections/ListItemMeta/index.js +13 -7
  30. package/dist/components/collections/ListItemSecondary/index.d.ts +5 -3
  31. package/dist/components/collections/ListItemSecondary/index.js +5 -5
  32. package/dist/components/collections/Pagination/index.d.ts +1 -1
  33. package/dist/components/collections/Pagination/index.js +6 -7
  34. package/dist/components/collections/PaginationLink/index.d.ts +9 -0
  35. package/dist/components/collections/PaginationLink/index.js +9 -0
  36. package/dist/components/collections/Table/index.d.ts +4 -5
  37. package/dist/components/collections/Table/index.js +2 -8
  38. package/dist/components/collections/TableClientComponent/index.d.ts +7 -6
  39. package/dist/components/collections/TableClientComponent/index.js +11 -26
  40. package/dist/components/collections/TableRow/index.d.ts +13 -0
  41. package/dist/components/collections/TableRow/index.js +15 -0
  42. package/dist/components/collections/interfaces.d.ts +41 -34
  43. package/dist/components/collections/utility/is-right-aligned.d.ts +3 -0
  44. package/dist/components/collections/utility/is-right-aligned.js +11 -0
  45. package/dist/components/collections/utility/normalize-href.d.ts +2 -0
  46. package/dist/components/collections/utility/normalize-href.js +8 -0
  47. package/dist/components/collections/utility/render-cell.d.ts +5 -0
  48. package/dist/components/collections/utility/render-cell.js +33 -0
  49. package/dist/components/elements/Badge/index.d.ts +12 -0
  50. package/dist/components/elements/Badge/index.js +9 -0
  51. package/dist/components/elements/InfoPanel/index.d.ts +11 -0
  52. package/dist/components/elements/InfoPanel/index.js +9 -0
  53. package/dist/components/{utility → elements}/Link/index.d.ts +1 -1
  54. package/dist/components/{utility → elements}/Link/index.js +6 -7
  55. package/dist/components/elements/Menu/index.d.ts +19 -0
  56. package/dist/components/elements/Menu/index.js +17 -0
  57. package/dist/components/elements/MenuItem/index.d.ts +7 -0
  58. package/dist/components/elements/MenuItem/index.js +12 -0
  59. package/dist/components/elements/Page/index.d.ts +19 -0
  60. package/dist/components/elements/Page/index.js +18 -0
  61. package/dist/components/elements/Reference/index.d.ts +9 -0
  62. package/dist/components/elements/Reference/index.js +16 -0
  63. package/dist/components/elements/Summary/index.d.ts +13 -0
  64. package/dist/components/elements/Summary/index.js +22 -0
  65. package/dist/components/errors/AppError/index.d.ts +19 -0
  66. package/dist/components/errors/AppError/index.js +9 -0
  67. package/dist/components/errors/AppForbiddenError/index.d.ts +7 -0
  68. package/dist/components/errors/AppForbiddenError/index.js +6 -0
  69. package/dist/components/errors/AppNotFoundError/index.d.ts +7 -0
  70. package/dist/components/errors/AppNotFoundError/index.js +6 -0
  71. package/dist/components/errors/AppServerError/index.d.ts +8 -0
  72. package/dist/components/errors/AppServerError/index.js +17 -0
  73. package/dist/components/index.d.ts +37 -6
  74. package/dist/components/index.js +18 -3
  75. package/dist/components/mail/Mail/index.d.ts +7 -0
  76. package/dist/components/mail/Mail/index.js +113 -0
  77. package/dist/components/mail/MailBlock/index.d.ts +5 -0
  78. package/dist/components/mail/MailBlock/index.js +5 -0
  79. package/dist/components/mail/MailButton/index.d.ts +7 -0
  80. package/dist/components/mail/MailButton/index.js +38 -0
  81. package/dist/components/mail/MailTable/index.d.ts +9 -0
  82. package/dist/components/mail/MailTable/index.js +7 -0
  83. package/dist/components/modals/ConfirmModal/index.d.ts +5 -3
  84. package/dist/components/modals/ConfirmModal/index.js +3 -3
  85. package/dist/components/modals/Modal/index.d.ts +4 -4
  86. package/dist/components/modals/Modal/index.js +3 -3
  87. package/dist/components/modals/ModalActions/index.d.ts +3 -3
  88. package/dist/components/modals/ModalActions/index.js +4 -3
  89. package/dist/components/utility/Action/index.d.ts +11 -0
  90. package/dist/components/utility/Action/index.js +48 -0
  91. package/dist/components/utility/ActionList/index.d.ts +5 -5
  92. package/dist/components/utility/ActionList/index.js +5 -3
  93. package/dist/components/utility/AppBody/index.d.ts +5 -0
  94. package/dist/components/utility/AppBody/index.js +9 -0
  95. package/dist/components/utility/Calendar/index.d.ts +32 -0
  96. package/dist/components/utility/Calendar/index.js +67 -0
  97. package/dist/components/utility/CalendarDay/index.d.ts +11 -0
  98. package/dist/components/utility/CalendarDay/index.js +23 -0
  99. package/dist/components/utility/Confirmable/index.d.ts +9 -0
  100. package/dist/components/utility/Confirmable/index.js +14 -0
  101. package/dist/components/utility/Container/index.d.ts +1 -1
  102. package/dist/components/utility/Container/index.js +2 -2
  103. package/dist/components/utility/Loader/index.d.ts +1 -1
  104. package/dist/components/utility/Loader/index.js +5 -4
  105. package/dist/components/utility/Popover/index.d.ts +1 -1
  106. package/dist/components/utility/Popover/index.js +5 -5
  107. package/dist/components/utility/Toast/index.d.ts +2 -2
  108. package/dist/components/utility/Toast/index.js +6 -4
  109. package/dist/components/utility/Toaster/index.js +5 -5
  110. package/dist/filters/components/FilterBar/index.d.ts +5 -2
  111. package/dist/filters/components/FilterBarClientComponent/index.d.ts +2 -4
  112. package/dist/filters/components/FilterBarClientComponent/index.js +3 -43
  113. package/dist/filters/components/FilterClearButton/index.d.ts +7 -2
  114. package/dist/filters/components/FilterClearButton/index.js +8 -4
  115. package/dist/filters/components/FilterControl/index.d.ts +1 -1
  116. package/dist/filters/components/FilterControl/index.js +11 -4
  117. package/dist/filters/components/FilterItem/index.d.ts +2 -1
  118. package/dist/filters/components/FilterItem/index.js +3 -7
  119. package/dist/filters/components/FilterPanel/index.d.ts +1 -1
  120. package/dist/filters/{utility/filter.d.ts → filter.d.ts} +1 -1
  121. package/dist/filters/{utility/filter.js → filter.js} +8 -8
  122. package/dist/filters/filters/BooleanFilter/index.js +1 -1
  123. package/dist/filters/filters/CalendarFilter/index.js +3 -2
  124. package/dist/filters/filters/DateFilter/index.d.ts +1 -1
  125. package/dist/filters/filters/DateFilter/index.js +9 -4
  126. package/dist/filters/filters/DropdownFilter/index.js +1 -1
  127. package/dist/filters/filters/Filter/index.d.ts +5 -4
  128. package/dist/filters/filters/Filter/index.js +7 -7
  129. package/dist/filters/filters/SearchFilter/index.d.ts +7 -2
  130. package/dist/filters/filters/SearchFilter/index.js +8 -8
  131. package/dist/filters/filters/interfaces.d.ts +0 -2
  132. package/dist/filters/index.d.ts +2 -1
  133. package/dist/filters/index.js +2 -1
  134. package/dist/filters/interfaces.d.ts +4 -4
  135. package/dist/filters/utility/parse-filters.d.ts +1 -1
  136. package/dist/filters/utility/parse-filters.js +3 -2
  137. package/dist/filters/utility/render-value.js +4 -4
  138. package/dist/filters/utility/transform-boolean.d.ts +1 -1
  139. package/dist/filters/utility/transform-date.d.ts +1 -1
  140. package/dist/filters/utility/transform-multi.d.ts +1 -1
  141. package/dist/forms/components/Autocomplete/index.d.ts +11 -0
  142. package/dist/forms/components/Autocomplete/index.js +37 -0
  143. package/dist/forms/components/CSVInput/index.d.ts +11 -0
  144. package/dist/forms/components/CSVInput/index.js +32 -0
  145. package/dist/forms/components/Dropdown/index.d.ts +1 -1
  146. package/dist/forms/components/Dropdown/index.js +8 -7
  147. package/dist/forms/components/DropdownItem/index.d.ts +9 -0
  148. package/dist/forms/components/DropdownItem/index.js +9 -0
  149. package/dist/forms/components/DropdownList/index.d.ts +1 -1
  150. package/dist/forms/components/DropdownList/index.js +7 -9
  151. package/dist/forms/components/EditableForm/index.d.ts +3 -3
  152. package/dist/forms/components/EditableForm/index.js +9 -9
  153. package/dist/forms/components/EditableFormField/index.d.ts +1 -1
  154. package/dist/forms/components/EditableFormField/index.js +3 -3
  155. package/dist/forms/components/EditableFormFields/index.d.ts +3 -0
  156. package/dist/forms/components/EditableFormFields/index.js +6 -0
  157. package/dist/forms/components/Form/index.d.ts +3 -2
  158. package/dist/forms/components/Form/index.js +5 -5
  159. package/dist/forms/components/FormError/index.d.ts +2 -2
  160. package/dist/forms/components/FormError/index.js +4 -3
  161. package/dist/forms/components/FormField/index.d.ts +4 -4
  162. package/dist/forms/components/FormField/index.js +8 -6
  163. package/dist/forms/components/FormFields/index.d.ts +14 -0
  164. package/dist/forms/components/FormFields/index.js +30 -0
  165. package/dist/forms/components/FormLabel/index.d.ts +1 -1
  166. package/dist/forms/components/FormLabel/index.js +4 -3
  167. package/dist/forms/components/ModalForm/index.js +1 -1
  168. package/dist/forms/components/NumberInput/index.d.ts +7 -0
  169. package/dist/forms/components/NumberInput/index.js +27 -0
  170. package/dist/forms/components/PasswordComplexity/index.d.ts +16 -0
  171. package/dist/forms/components/PasswordComplexity/index.js +14 -0
  172. package/dist/forms/components/PasswordComplexityItem/index.d.ts +8 -0
  173. package/dist/forms/components/PasswordComplexityItem/index.js +10 -0
  174. package/dist/forms/components/PasswordInput/index.d.ts +1 -1
  175. package/dist/forms/components/PasswordInput/index.js +6 -6
  176. package/dist/forms/components/PointsInput/index.d.ts +5 -0
  177. package/dist/forms/components/PointsInput/index.js +22 -0
  178. package/dist/forms/components/RangeCalendarInput/index.d.ts +5 -0
  179. package/dist/forms/components/RangeCalendarInput/index.js +10 -0
  180. package/dist/forms/components/StaticTextInput/index.d.ts +2 -3
  181. package/dist/forms/components/StaticTextInput/index.js +8 -8
  182. package/dist/forms/components/Switch/index.d.ts +1 -1
  183. package/dist/forms/components/Switch/index.js +5 -4
  184. package/dist/forms/components/TextArea/index.d.ts +14 -0
  185. package/dist/forms/components/TextArea/index.js +15 -0
  186. package/dist/forms/components/TextInput/index.d.ts +2 -2
  187. package/dist/forms/components/TextInput/index.js +7 -6
  188. package/dist/forms/hooks/useAutocomplete.d.ts +9 -0
  189. package/dist/forms/hooks/useAutocomplete.js +31 -0
  190. package/dist/forms/hooks/useDropdown.d.ts +2 -2
  191. package/dist/forms/hooks/useForm.d.ts +3 -5
  192. package/dist/forms/hooks/useForm.js +14 -24
  193. package/dist/forms/hooks/useModalForm.d.ts +2 -2
  194. package/dist/forms/index.d.ts +26 -4
  195. package/dist/forms/index.js +11 -3
  196. package/dist/forms/interfaces.d.ts +1 -0
  197. package/dist/forms/utility/format-file-size.d.ts +2 -0
  198. package/dist/forms/utility/format-file-size.js +11 -0
  199. package/dist/hooks/index.d.ts +3 -0
  200. package/dist/hooks/index.js +3 -0
  201. package/dist/hooks/useConfirmable.d.ts +21 -0
  202. package/dist/hooks/useConfirmable.js +58 -0
  203. package/dist/hooks/useDownload.d.ts +2 -0
  204. package/dist/hooks/useDownload.js +18 -0
  205. package/dist/hooks/usePopover.d.ts +12 -0
  206. package/dist/hooks/usePopover.js +24 -0
  207. package/dist/hooks/useSelected.d.ts +12 -0
  208. package/dist/hooks/useSelected.js +35 -0
  209. package/dist/hooks/useServerAction.d.ts +10 -0
  210. package/dist/hooks/useServerAction.js +17 -0
  211. package/dist/hooks/useSuccess.d.ts +10 -0
  212. package/dist/hooks/useSuccess.js +22 -0
  213. package/dist/navigation/components/AppNavigation/index.d.ts +3 -1
  214. package/dist/navigation/components/AppNavigation/index.js +4 -4
  215. package/dist/navigation/components/AppNavigationItem/index.d.ts +5 -3
  216. package/dist/navigation/components/AppNavigationItem/index.js +16 -7
  217. package/dist/navigation/components/Tabs/index.js +1 -4
  218. package/dist/navigation/hooks/useNavigation.d.ts +3 -3
  219. package/dist/navigation/hooks/useNavigation.js +5 -5
  220. package/dist/styles/classnames/config.d.ts +87 -0
  221. package/dist/styles/classnames/config.js +1 -0
  222. package/dist/styles/classnames/interfaces.d.ts +56 -0
  223. package/dist/styles/classnames/interfaces.js +1 -0
  224. package/dist/styles/classnames/utility/apply-sizes.d.ts +3 -0
  225. package/dist/styles/classnames/utility/apply-sizes.js +21 -0
  226. package/dist/styles/classnames/utility/apply-variants.d.ts +3 -0
  227. package/dist/styles/classnames/utility/apply-variants.js +26 -0
  228. package/dist/styles/classnames/utility/is-classname-object.d.ts +3 -0
  229. package/dist/styles/classnames/utility/is-classname-object.js +7 -0
  230. package/dist/styles/classnames/utility/parse-classnames.d.ts +6 -0
  231. package/dist/styles/classnames/utility/parse-classnames.js +33 -0
  232. package/dist/styles/context.d.ts +28 -0
  233. package/dist/styles/context.js +19 -0
  234. package/dist/styles/icons/config.d.ts +20 -0
  235. package/dist/styles/icons/config.js +1 -0
  236. package/dist/styles/icons/interfaces.d.ts +4 -0
  237. package/dist/styles/icons/interfaces.js +1 -0
  238. package/dist/styles/index.d.ts +6 -2
  239. package/dist/styles/index.js +2 -1
  240. package/dist/styles/styles.css +60 -0
  241. package/dist/utility/compare-dates.d.ts +2 -0
  242. package/dist/utility/compare-dates.js +13 -0
  243. package/dist/utility/convert-to-datauri.d.ts +2 -0
  244. package/dist/utility/convert-to-datauri.js +16 -0
  245. package/dist/utility/get-days.d.ts +2 -0
  246. package/dist/utility/get-days.js +5 -0
  247. package/dist/utility/get-weeks.d.ts +2 -0
  248. package/dist/utility/get-weeks.js +31 -0
  249. package/dist/utility/index.d.ts +1 -1
  250. package/dist/utility/interfaces.d.ts +33 -17
  251. package/dist/utility/is-data-object-array.d.ts +3 -0
  252. package/dist/utility/is-data-object-array.js +5 -0
  253. package/dist/utility/is-data-object.d.ts +3 -0
  254. package/dist/utility/is-data-object.js +4 -0
  255. package/dist/utility/is-date-highlighted.d.ts +2 -0
  256. package/dist/utility/is-date-highlighted.js +8 -0
  257. package/dist/utility/is-date-selected.d.ts +2 -0
  258. package/dist/utility/is-date-selected.js +16 -0
  259. package/package.json +28 -16
  260. package/dist/components/buttons/ConfirmableButton/index.d.ts +0 -7
  261. package/dist/components/buttons/ConfirmableButton/index.js +0 -13
  262. package/dist/components/collections/utility/filter-columns.d.ts +0 -3
  263. package/dist/components/collections/utility/filter-columns.js +0 -8
  264. package/dist/components/collections/utility/get-selected-from-search-params.d.ts +0 -2
  265. package/dist/components/collections/utility/get-selected-from-search-params.js +0 -5
  266. package/dist/components/collections/utility/set-selected-to-search-params.d.ts +0 -2
  267. package/dist/components/collections/utility/set-selected-to-search-params.js +0 -4
  268. package/dist/components/utility/ClassNames/index.d.ts +0 -6
  269. package/dist/components/utility/ClassNames/index.js +0 -7
  270. package/dist/components/utility/Page/index.d.ts +0 -18
  271. package/dist/components/utility/Page/index.js +0 -34
  272. package/dist/components/utility/RootLayout/index.d.ts +0 -12
  273. package/dist/components/utility/RootLayout/index.js +0 -14
  274. package/dist/styles/config.d.ts +0 -64
  275. package/dist/styles/config.js +0 -43
  276. package/dist/styles/icons.d.ts +0 -15
  277. package/dist/styles/icons.js +0 -7
  278. package/dist/styles/interfaces.d.ts +0 -41
  279. /package/dist/{styles → addon}/interfaces.js +0 -0
  280. /package/dist/styles/{tw.d.ts → classnames/utility/tw.d.ts} +0 -0
  281. /package/dist/styles/{tw.js → classnames/utility/tw.js} +0 -0
@@ -1,8 +1,8 @@
1
1
  'use client';
2
2
  import { useRef, useState, useTransition } from 'react';
3
3
  import { formatTitle } from '@sqrzro/utility';
4
- import { useRouter } from 'next/navigation';
5
4
  import useDeepCompareEffect from 'use-deep-compare-effect';
5
+ import useSuccess from '../../hooks/useSuccess';
6
6
  import useToast from '../../hooks/useToast';
7
7
  const DEFAULT_TOAST_MESSAGES = {
8
8
  server: 'There was a problem submitting your request. Please try again later.',
@@ -120,9 +120,9 @@ function getToastMessage(key, toasts) {
120
120
  * handling additional form events or integrating with different server APIs.
121
121
  */
122
122
  function useForm({ defaults = {}, onError, onSubmit, onSuccess, onValidation, redirectOnSuccess, refreshOnSuccess, toasts, }) {
123
- const innerRef = useRef(null);
124
- const router = useRouter();
125
- const [isLoading, startTransition] = useTransition();
123
+ const ref = useRef(null);
124
+ const { handleSuccess } = useSuccess({ onSuccess, redirectOnSuccess, refreshOnSuccess });
125
+ const [isLoading] = useTransition();
126
126
  const [errors, setErrors] = useState(null);
127
127
  const [data, setData] = useState(defaults);
128
128
  const { toastError, toastSuccess } = useToast();
@@ -132,26 +132,15 @@ function useForm({ defaults = {}, onError, onSubmit, onSuccess, onValidation, re
132
132
  function handleChange(event) {
133
133
  setData((prev) => ({ ...prev, [event.target.name]: event.target.value }));
134
134
  }
135
- async function handleSuccess(response) {
136
- await onSuccess?.(response);
137
- if (redirectOnSuccess) {
138
- const redirect = typeof redirectOnSuccess === 'function'
139
- ? redirectOnSuccess(response)
140
- : redirectOnSuccess;
141
- if (redirect) {
142
- router.push(redirect);
143
- }
144
- }
145
- if (refreshOnSuccess) {
146
- router.refresh();
147
- }
135
+ async function handleFormSuccess(response) {
136
+ await handleSuccess(response);
148
137
  toastSuccess(getToastMessage('success', toasts));
149
138
  }
150
- function handleError(message) {
139
+ function handleFormError(message) {
151
140
  onError?.(message);
152
141
  toastError(getToastMessage('server', toasts));
153
142
  }
154
- function handleValidation(messages) {
143
+ function handleFormValidation(messages) {
155
144
  onValidation?.(messages);
156
145
  setErrors(messages);
157
146
  toastError(getToastMessage('validation', toasts));
@@ -163,13 +152,13 @@ function useForm({ defaults = {}, onError, onSubmit, onSuccess, onValidation, re
163
152
  setErrors(null);
164
153
  const fnReturn = await onSubmit(data);
165
154
  if (fnReturn.error) {
166
- return handleError(fnReturn.error);
155
+ return handleFormError(fnReturn.error);
167
156
  }
168
157
  if (fnReturn.validation) {
169
- return handleValidation(fnReturn.validation);
158
+ return handleFormValidation(fnReturn.validation);
170
159
  }
171
- if (fnReturn.data) {
172
- return handleSuccess(fnReturn.data);
160
+ if (fnReturn.data !== null) {
161
+ return handleFormSuccess(fnReturn.data);
173
162
  }
174
163
  }
175
164
  function fieldProps(name, label) {
@@ -196,13 +185,14 @@ function useForm({ defaults = {}, onError, onSubmit, onSuccess, onValidation, re
196
185
  formData: data,
197
186
  formProps: {
198
187
  action: handleSubmit,
188
+ ref,
199
189
  },
200
190
  isLoading,
201
191
  resetForm,
202
192
  setErrors,
203
193
  setFormData,
204
194
  submitForm: () => {
205
- setTimeout(() => innerRef.current?.requestSubmit(), 1);
195
+ setTimeout(() => ref.current?.requestSubmit(), 1);
206
196
  },
207
197
  };
208
198
  }
@@ -1,8 +1,8 @@
1
- import type { Action } from '../../utility/interfaces';
1
+ import type { SimpleActionObject } from '../../utility/interfaces';
2
2
  import type { ModalFormProps } from '../components/ModalForm';
3
3
  import type { UseFormArgs, UseFormReturn } from './useForm';
4
4
  export interface UseModalFormArgs<Request, Response> extends UseFormArgs<Request, Response> {
5
- actions?: Action[];
5
+ actions?: SimpleActionObject[];
6
6
  icon?: React.ReactNode;
7
7
  submitLabel?: string;
8
8
  title?: string;
@@ -1,4 +1,8 @@
1
1
  export * from './interfaces';
2
+ export type { AutocompleteProps } from './components/Autocomplete';
3
+ export { default as Autocomplete } from './components/Autocomplete';
4
+ export type { CSVInputClassNames, CSVInputProps } from './components/CSVInput';
5
+ export { default as CSVInput } from './components/CSVInput';
2
6
  export type { DropdownClassNames, DropdownProps } from './components/Dropdown';
3
7
  export { default as Dropdown } from './components/Dropdown';
4
8
  export type { EditableFormClassNames, EditableFormProps } from './components/EditableForm';
@@ -7,21 +11,39 @@ export type { EditableFormFieldProps } from './components/EditableFormField';
7
11
  export { default as EditableFormField } from './components/EditableFormField';
8
12
  export type { FormClassNames, FormProps } from './components/Form';
9
13
  export { default as Form } from './components/Form';
14
+ export type { FormErrorProps } from './components/FormError';
15
+ export { default as FormError } from './components/FormError';
10
16
  export type { FormFieldClassNames, FormFieldProps } from './components/FormField';
11
17
  export { default as FormField } from './components/FormField';
12
18
  export type { FormSubmitProps } from './components/FormSubmit';
13
19
  export { default as FormSubmit } from './components/FormSubmit';
14
20
  export type { ModalFormProps } from './components/ModalForm';
15
21
  export { default as ModalForm } from './components/ModalForm';
22
+ export type { PasswordComplexityProps } from './components/PasswordComplexity';
23
+ export { default as PasswordComplexity } from './components/PasswordComplexity';
24
+ export type { NumberInputProps } from './components/NumberInput';
25
+ export { default as NumberInput } from './components/NumberInput';
16
26
  export type { PasswordInputClassNames, PasswordInputProps } from './components/PasswordInput';
17
27
  export { default as PasswordInput } from './components/PasswordInput';
28
+ export type { PointsInputProps } from './components/PointsInput';
29
+ export { default as PointsInput } from './components/PointsInput';
30
+ export type { StaticTextInputClassNames, StaticTextInputProps } from './components/StaticTextInput';
31
+ export { default as StaticTextInput } from './components/StaticTextInput';
32
+ export type { TextAreaClassNames, TextAreaProps } from './components/TextArea';
33
+ export { default as TextArea } from './components/TextArea';
18
34
  export type { TextInputClassNames, TextInputProps } from './components/TextInput';
19
35
  export { default as TextInput } from './components/TextInput';
20
- export type { EditableDropdownFormFieldProps, EditableTextFormFieldProps, } from './components/EditableFormFields';
21
- export { EditableDropdownFormField, EditableTextFormField } from './components/EditableFormFields';
22
- export type { DropdownFormFieldProps, PasswordFormFieldProps, TextFormFieldProps, } from './components/FormFields';
23
- export { DropdownFormField, PasswordFormField, TextFormField } from './components/FormFields';
36
+ export type * from './components/EditableFormFields';
37
+ export * from './components/EditableFormFields';
38
+ export type * from './components/FormFields';
39
+ export * from './components/FormFields';
40
+ export type { UseAutocompleteArgs, UseAutocompleteReturn } from './hooks/useAutocomplete';
41
+ export { default as useAutocomplete } from './hooks/useAutocomplete';
42
+ export type { UseDropdownArgs, UseDropdownReturn } from './hooks/useDropdown';
24
43
  export { default as useDropdown } from './hooks/useDropdown';
44
+ export type { UseEditableFormArgs, UseEditableFormReturn } from './hooks/useEditableForm';
25
45
  export { default as useEditableForm } from './hooks/useEditableForm';
46
+ export type { UseFormArgs, UseFormReturn } from './hooks/useForm';
26
47
  export { default as useForm } from './hooks/useForm';
48
+ export type { UseModalFormArgs, UseModalFormReturn } from './hooks/useModalForm';
27
49
  export { default as useModalForm } from './hooks/useModalForm';
@@ -1,16 +1,24 @@
1
1
  export * from './interfaces';
2
+ export { default as Autocomplete } from './components/Autocomplete';
3
+ export { default as CSVInput } from './components/CSVInput';
2
4
  export { default as Dropdown } from './components/Dropdown';
3
5
  export { default as EditableForm } from './components/EditableForm';
4
6
  export { default as EditableFormField } from './components/EditableFormField';
5
7
  export { default as Form } from './components/Form';
8
+ export { default as FormError } from './components/FormError';
6
9
  export { default as FormField } from './components/FormField';
7
10
  export { default as FormSubmit } from './components/FormSubmit';
8
11
  export { default as ModalForm } from './components/ModalForm';
12
+ export { default as PasswordComplexity } from './components/PasswordComplexity';
13
+ export { default as NumberInput } from './components/NumberInput';
9
14
  export { default as PasswordInput } from './components/PasswordInput';
15
+ export { default as PointsInput } from './components/PointsInput';
16
+ export { default as StaticTextInput } from './components/StaticTextInput';
17
+ export { default as TextArea } from './components/TextArea';
10
18
  export { default as TextInput } from './components/TextInput';
11
- export { EditableDropdownFormField, EditableTextFormField } from './components/EditableFormFields';
12
- export { DropdownFormField, PasswordFormField, TextFormField } from './components/FormFields';
13
- // Hooks
19
+ export * from './components/EditableFormFields';
20
+ export * from './components/FormFields';
21
+ export { default as useAutocomplete } from './hooks/useAutocomplete';
14
22
  export { default as useDropdown } from './hooks/useDropdown';
15
23
  export { default as useEditableForm } from './hooks/useEditableForm';
16
24
  export { default as useForm } from './hooks/useForm';
@@ -26,6 +26,7 @@ export interface InputProps<V, T extends V = V> {
26
26
  id?: string;
27
27
  isDisabled?: boolean;
28
28
  name: string;
29
+ ref?: React.Ref<HTMLInputElement>;
29
30
  onChange?: (event: InputEvent<T>) => void;
30
31
  onKeyDown?: React.KeyboardEventHandler;
31
32
  value?: V;
@@ -0,0 +1,2 @@
1
+ declare function formatFileSize(size: number): string;
2
+ export default formatFileSize;
@@ -0,0 +1,11 @@
1
+ const BYTES_IN_KB = 1024;
2
+ const DECIMAL_PLACES = 3;
3
+ function formatFileSize(size) {
4
+ const units = ['B', 'KiB', 'MiB', 'GiB', 'TiB', 'PiB', 'EiB', 'ZiB', 'YiB'];
5
+ const exponent = Math.min(Math.floor(Math.log(size) / Math.log(BYTES_IN_KB)), units.length - 1);
6
+ const approx = size / BYTES_IN_KB ** exponent;
7
+ return exponent === 0
8
+ ? `${size} bytes`
9
+ : `${approx.toFixed(DECIMAL_PLACES)} ${units[exponent]} (${size} bytes)`;
10
+ }
11
+ export default formatFileSize;
@@ -1 +1,4 @@
1
1
  export { default as useClickOutside } from './useClickOutside';
2
+ export { default as useDownload } from './useDownload';
3
+ export { default as usePopover } from './usePopover';
4
+ export { default as useServerAction } from './useServerAction';
@@ -1 +1,4 @@
1
1
  export { default as useClickOutside } from './useClickOutside';
2
+ export { default as useDownload } from './useDownload';
3
+ export { default as usePopover } from './usePopover';
4
+ export { default as useServerAction } from './useServerAction';
@@ -0,0 +1,21 @@
1
+ import type { ActionEvent } from '../utility/interfaces';
2
+ interface UseConfirmableArgs {
3
+ isLoading?: boolean;
4
+ onBeforeConfirm?: () => void;
5
+ onConfirm: (event: ActionEvent, currentRef: HTMLButtonElement | null) => void;
6
+ onSuccess?: () => Promise<void> | void;
7
+ redirectOnSuccess?: string | false | ((response: Response) => string | false);
8
+ refreshOnSuccess?: boolean;
9
+ }
10
+ interface UseConfirmableReturn {
11
+ handle: (event?: ActionEvent) => void;
12
+ isOpen: boolean;
13
+ modalProps: {
14
+ isLoading: boolean;
15
+ onCancel: () => void;
16
+ onConfirm: () => void;
17
+ };
18
+ ref: React.RefObject<HTMLButtonElement | null>;
19
+ }
20
+ declare function useConfirmable({ isLoading, onBeforeConfirm, onConfirm, onSuccess, redirectOnSuccess, refreshOnSuccess, }: Readonly<UseConfirmableArgs>): UseConfirmableReturn;
21
+ export default useConfirmable;
@@ -0,0 +1,58 @@
1
+ 'use client';
2
+ import { useEffect, useRef, useState } from 'react';
3
+ import { useRouter } from 'next/navigation';
4
+ function useConfirmable({ isLoading, onBeforeConfirm, onConfirm, onSuccess, redirectOnSuccess, refreshOnSuccess, }) {
5
+ const ref = useRef(null);
6
+ const router = useRouter();
7
+ const [isModalOpen, setIsModalOpen] = useState(false);
8
+ const [isConfirmed, setIsConfirmed] = useState(false);
9
+ const [refEvent, setRefEvent] = useState();
10
+ function handle(event) {
11
+ onBeforeConfirm?.();
12
+ if (!isConfirmed) {
13
+ event?.preventDefault();
14
+ setIsModalOpen(true);
15
+ }
16
+ setRefEvent(event);
17
+ setIsConfirmed(false);
18
+ }
19
+ function handleConfirm() {
20
+ setIsConfirmed(true);
21
+ setTimeout(() => {
22
+ if (refEvent) {
23
+ onConfirm(refEvent, ref.current);
24
+ }
25
+ // If `isLoading` hasn't been set, we can just close the modal now. If it has, by
26
+ // setting `isConfirmed` to true above, we trigger the useEffect below to wait until
27
+ // after loading to close the modal.
28
+ if (typeof isLoading === 'undefined') {
29
+ setIsConfirmed(false);
30
+ setIsModalOpen(false);
31
+ }
32
+ }, 0);
33
+ }
34
+ function handleCancel() {
35
+ setIsModalOpen(false);
36
+ }
37
+ function handleSuccess() {
38
+ setIsConfirmed(false);
39
+ setIsModalOpen(false);
40
+ router.refresh();
41
+ }
42
+ useEffect(() => {
43
+ if (!isLoading && isConfirmed) {
44
+ handleSuccess();
45
+ }
46
+ }, [isLoading]);
47
+ return {
48
+ handle,
49
+ isOpen: isModalOpen,
50
+ modalProps: {
51
+ isLoading: isLoading ?? false,
52
+ onCancel: handleCancel,
53
+ onConfirm: handleConfirm,
54
+ },
55
+ ref,
56
+ };
57
+ }
58
+ export default useConfirmable;
@@ -0,0 +1,2 @@
1
+ declare function useDownload(): (data: Blob | string, filename: string) => void;
2
+ export default useDownload;
@@ -0,0 +1,18 @@
1
+ function download(data, filename) {
2
+ const href = typeof data === 'string' ? data : URL.createObjectURL(data);
3
+ // Create a temporary link element to trigger the download
4
+ const link = document.createElement('a');
5
+ link.href = href;
6
+ link.download = filename;
7
+ document.body.appendChild(link);
8
+ link.click();
9
+ // Clean up
10
+ document.body.removeChild(link);
11
+ if (typeof data !== 'string') {
12
+ URL.revokeObjectURL(href);
13
+ }
14
+ }
15
+ function useDownload() {
16
+ return download;
17
+ }
18
+ export default useDownload;
@@ -0,0 +1,12 @@
1
+ interface UsePopoverReturn<T extends HTMLElement = HTMLElement> {
2
+ controlProps: {
3
+ onClick: () => void;
4
+ };
5
+ isOpen: boolean;
6
+ ref: React.RefObject<T | null>;
7
+ targetProps: {
8
+ isOpen: boolean;
9
+ };
10
+ }
11
+ declare function usePopover<T extends HTMLElement = HTMLElement>(): UsePopoverReturn<T>;
12
+ export default usePopover;
@@ -0,0 +1,24 @@
1
+ import { useEffect } from 'react';
2
+ import useClickOutside from './useClickOutside';
3
+ import { usePathname } from 'next/navigation';
4
+ function usePopover() {
5
+ const pathname = usePathname();
6
+ const [isOpen, setIsOpen, ref] = useClickOutside();
7
+ function toggleIsOpen() {
8
+ setIsOpen(!isOpen);
9
+ }
10
+ useEffect(() => {
11
+ setIsOpen(false);
12
+ }, [pathname]);
13
+ return {
14
+ controlProps: {
15
+ onClick: toggleIsOpen,
16
+ },
17
+ isOpen,
18
+ ref,
19
+ targetProps: {
20
+ isOpen,
21
+ },
22
+ };
23
+ }
24
+ export default usePopover;
@@ -0,0 +1,12 @@
1
+ import type { InputEvent } from '../forms/interfaces';
2
+ interface UseSelectedReturn {
3
+ checkSelected: (id: string) => boolean;
4
+ isAllSelected: boolean;
5
+ onSelect: (event: InputEvent<boolean>) => void;
6
+ onSelectAll: () => void;
7
+ selected: string[];
8
+ }
9
+ declare function useSelected(data: {
10
+ id: string;
11
+ }[]): UseSelectedReturn;
12
+ export default useSelected;
@@ -0,0 +1,35 @@
1
+ import { toggleArrayItem } from '@sqrzro/utility';
2
+ import { useSearchParams } from 'next/navigation';
3
+ import useSearchParamsHref from './useSearchParamsHref';
4
+ function getSelectedFromSearchParams(searchParams) {
5
+ const selected = searchParams.get('selected');
6
+ return selected ? selected.split('|') : [];
7
+ }
8
+ function setSelectedToSearchParams(selected) {
9
+ return selected.length ? selected.join('|') : null;
10
+ }
11
+ function useSelected(data) {
12
+ const { setSearchParamsHref } = useSearchParamsHref();
13
+ const searchParams = useSearchParams();
14
+ const selected = getSelectedFromSearchParams(searchParams);
15
+ function onSelect(event) {
16
+ const value = toggleArrayItem(selected, event.target.name);
17
+ setSearchParamsHref({ selected: setSelectedToSearchParams(value) });
18
+ }
19
+ function onSelectAll() {
20
+ const value = selected.length === data.length ? [] : data.map((item) => item.id);
21
+ setSearchParamsHref({ selected: setSelectedToSearchParams(value) });
22
+ }
23
+ const isAllSelected = data.length > 0 && selected.length === data.length;
24
+ function checkSelected(id) {
25
+ return selected.includes(id);
26
+ }
27
+ return {
28
+ checkSelected,
29
+ isAllSelected,
30
+ onSelect,
31
+ onSelectAll,
32
+ selected,
33
+ };
34
+ }
35
+ export default useSelected;
@@ -0,0 +1,10 @@
1
+ import type { UseSuccessArgs } from './useSuccess';
2
+ interface UseServerActionArgs<Response> extends UseSuccessArgs<Response> {
3
+ onSuccess?: (response: Response) => void;
4
+ }
5
+ interface UseServerActionReturn {
6
+ handleClick: () => void;
7
+ isLoading: boolean;
8
+ }
9
+ declare function useServerAction<Response>(fn?: () => Promise<Response>, args?: UseServerActionArgs<Response>): UseServerActionReturn;
10
+ export default useServerAction;
@@ -0,0 +1,17 @@
1
+ import { useTransition } from 'react';
2
+ import useSuccess from './useSuccess';
3
+ function useServerAction(fn, args = {}) {
4
+ const { handleSuccess } = useSuccess(args);
5
+ const [isLoading, startTransition] = useTransition();
6
+ function handleClick() {
7
+ startTransition(async () => {
8
+ if (!fn) {
9
+ return;
10
+ }
11
+ const response = await fn();
12
+ await handleSuccess(response);
13
+ });
14
+ }
15
+ return { handleClick, isLoading };
16
+ }
17
+ export default useServerAction;
@@ -0,0 +1,10 @@
1
+ export interface UseSuccessArgs<Response> {
2
+ onSuccess?: (response: Response) => Promise<void> | void;
3
+ redirectOnSuccess?: string | false | ((response: Response) => Promise<string | false> | string | false);
4
+ refreshOnSuccess?: boolean;
5
+ }
6
+ interface UseSuccessReturn<Response> {
7
+ handleSuccess: (response: Response) => Promise<void>;
8
+ }
9
+ declare function useSuccess<Response>({ onSuccess, redirectOnSuccess, refreshOnSuccess, }: UseSuccessArgs<Response>): UseSuccessReturn<Response>;
10
+ export default useSuccess;
@@ -0,0 +1,22 @@
1
+ import { useRouter } from 'next/navigation';
2
+ function useSuccess({ onSuccess, redirectOnSuccess, refreshOnSuccess, }) {
3
+ const router = useRouter();
4
+ async function handleSuccess(response) {
5
+ if (onSuccess) {
6
+ await onSuccess(response);
7
+ }
8
+ if (redirectOnSuccess) {
9
+ const url = typeof redirectOnSuccess === 'function'
10
+ ? await redirectOnSuccess(response)
11
+ : redirectOnSuccess;
12
+ if (url) {
13
+ router.push(url);
14
+ }
15
+ }
16
+ else if (refreshOnSuccess) {
17
+ router.refresh();
18
+ }
19
+ }
20
+ return { handleSuccess };
21
+ }
22
+ export default useSuccess;
@@ -1,12 +1,14 @@
1
- import type { ClassNameProps, HighlightableClassName } from '../../../styles/interfaces';
1
+ import type { ClassNameProps, HighlightableClassName, SelectableClassName } from '../../../styles/classnames/interfaces';
2
2
  import type { NavigationObject } from '../../interfaces';
3
3
  export interface AppNavigationClassNames {
4
4
  root: string;
5
5
  list: string;
6
6
  item: HighlightableClassName;
7
7
  link: HighlightableClassName;
8
+ icon: SelectableClassName;
8
9
  }
9
10
  export interface AppNavigationProps extends ClassNameProps<AppNavigationClassNames> {
11
+ classNameKey?: 'appNavigation' | 'tabs';
10
12
  data: NavigationObject[];
11
13
  }
12
14
  declare function AppNavigation(props: Readonly<AppNavigationProps>): React.ReactElement;
@@ -1,13 +1,13 @@
1
1
  'use client';
2
2
  import { jsx as _jsx } from "react/jsx-runtime";
3
3
  import { Suspense } from 'react';
4
- import { getClassNames } from '../../../styles/config';
4
+ import { useClassNames } from '../../../styles/context';
5
5
  import useNavigation from '../../hooks/useNavigation';
6
6
  import AppNavigationItem from '../AppNavigationItem';
7
- function AppNavigationComponent({ classNameProps, classNames, data, }) {
8
- const componentClassNames = classNames || getClassNames('appNavigation')?.(classNameProps);
7
+ function AppNavigationComponent({ classNameKey, classNameProps, classNames, data, }) {
8
+ const componentClassNames = useClassNames(classNameKey ?? 'appNavigation', { props: classNameProps }, classNames);
9
9
  const navigation = useNavigation(data);
10
- return (_jsx("nav", { className: componentClassNames?.root, children: _jsx("ul", { className: componentClassNames?.list, children: navigation.map((item, index) => (_jsx(AppNavigationItem, { classNames: classNames, ...item }, index))) }) }));
10
+ return (_jsx("nav", { className: componentClassNames?.root, children: _jsx("ul", { className: componentClassNames?.list, children: navigation.map((item, index) => (_jsx(AppNavigationItem, { classNameKey: classNameKey, classNames: classNames, ...item }, index))) }) }));
11
11
  }
12
12
  function AppNavigation(props) {
13
13
  return (_jsx(Suspense, { children: _jsx(AppNavigationComponent, { ...props }) }));
@@ -1,6 +1,8 @@
1
1
  import type { NavigationObject } from '../../../navigation/interfaces';
2
- import type { ClassNameProps } from '../../../styles/interfaces';
2
+ import type { ClassNameProps } from '../../../styles/classnames/interfaces';
3
3
  import type { AppNavigationClassNames } from '../AppNavigation';
4
- export type AppNavigationItemProps = NavigationObject & ClassNameProps<AppNavigationClassNames>;
5
- declare function AppNavigationItem({ classNameProps, classNames, href, isActive, label, }: Readonly<AppNavigationItemProps>): React.ReactElement;
4
+ export interface AppNavigationItemProps extends NavigationObject, ClassNameProps<AppNavigationClassNames> {
5
+ classNameKey?: 'appNavigation' | 'tabs';
6
+ }
7
+ declare function AppNavigationItem({ children, classNameKey, classNameProps, classNames, href, isActive, label, }: Readonly<AppNavigationItemProps>): React.ReactElement;
6
8
  export default AppNavigationItem;
@@ -1,9 +1,18 @@
1
- import { jsx as _jsx } from "react/jsx-runtime";
2
- import Link from '../../../components/utility/Link';
3
- import { getClassNames } from '../../../styles/config';
4
- import tw from '../../../styles/tw';
5
- function AppNavigationItem({ classNameProps, classNames, href, isActive, label, }) {
6
- const componentClassNames = classNames || getClassNames('appNavigation')?.(classNameProps);
7
- return (_jsx("li", { className: tw(componentClassNames?.item?.default, isActive ? componentClassNames?.item?.highlighted : null), children: _jsx(Link, { className: tw(componentClassNames?.link?.default, isActive ? componentClassNames?.link?.highlighted : null), href: href, children: label }) }));
1
+ 'use client';
2
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
3
+ import Link from '../../../components/elements/Link';
4
+ import MenuItem from '../../../components/elements/MenuItem';
5
+ import Action from '../../../components/utility/Action';
6
+ import Popover from '../../../components/utility/Popover';
7
+ import usePopover from '../../../hooks/usePopover';
8
+ import { useClassNames, useIcon } from '../../../styles/context';
9
+ function AppNavigationItem({ children, classNameKey, classNameProps, classNames, href, isActive, label, }) {
10
+ const Icon = useIcon('appNavigation.menu');
11
+ const { controlProps, isOpen, ref, targetProps } = usePopover();
12
+ const componentClassNames = useClassNames(classNameKey ?? 'appNavigation', { props: classNameProps, states: { isHighlighted: isActive ?? false, isSelected: isOpen } }, classNames);
13
+ if (children?.length) {
14
+ return (_jsxs("li", { className: componentClassNames?.item, ref: ref, children: [_jsxs("button", { className: componentClassNames?.link, type: "button", ...controlProps, children: [label, Icon ? (_jsx("div", { className: componentClassNames?.icon, children: _jsx(Icon, {}) })) : null] }), _jsx("div", { className: "relative -mt-3", children: _jsx(Popover, { align: "left", vAlign: "bottom", ...targetProps, children: _jsx("ul", { children: children.map((item, index) => (_jsx("li", { children: _jsx(Action, { ...item, render: MenuItem }) }, index))) }) }) })] }));
15
+ }
16
+ return (_jsx("li", { className: componentClassNames?.item, children: _jsx(Link, { className: componentClassNames?.link, href: href, children: label }) }));
8
17
  }
9
18
  export default AppNavigationItem;
@@ -1,9 +1,6 @@
1
- 'use client';
2
1
  import { jsx as _jsx } from "react/jsx-runtime";
3
- import { getClassNames } from '../../../styles/config';
4
2
  import AppNavigation from '../AppNavigation';
5
3
  function Tabs({ classNameProps, classNames, ...props }) {
6
- const componentClassNames = classNames || getClassNames('tabs')?.(classNameProps);
7
- return _jsx(AppNavigation, { classNames: componentClassNames ?? {}, ...props });
4
+ return _jsx(AppNavigation, { classNameKey: "tabs", ...props });
8
5
  }
9
6
  export default Tabs;
@@ -1,7 +1,7 @@
1
- import type { Action } from '../../utility/interfaces';
1
+ import type { SimpleActionObject } from '../../utility/interfaces';
2
2
  import type { NavigationObject } from '../interfaces';
3
- interface NavigationAction extends Action {
4
- children?: Action[];
3
+ interface NavigationAction extends SimpleActionObject {
4
+ children?: SimpleActionObject[];
5
5
  }
6
6
  interface UseNavigationOptions {
7
7
  basePath?: string;
@@ -1,4 +1,4 @@
1
- import { joinUrl } from '@sqrzro/utility';
1
+ import { joinURL } from '@sqrzro/utility';
2
2
  import { usePathname, useSelectedLayoutSegments } from 'next/navigation';
3
3
  function getActivePath(pathname, hrefs) {
4
4
  return (hrefs
@@ -18,7 +18,7 @@ function getBasePath(pathname, segments) {
18
18
  function transformChildren(children, basePath) {
19
19
  return children.map(({ details, href, label }) => ({
20
20
  details,
21
- href: joinUrl(basePath, href),
21
+ href: joinURL(basePath, href),
22
22
  label,
23
23
  }));
24
24
  }
@@ -26,13 +26,13 @@ function useNavigation(data, options) {
26
26
  const pathname = usePathname();
27
27
  const segments = useSelectedLayoutSegments();
28
28
  const basePath = getBasePath(pathname, segments);
29
- const hrefs = data.map(({ href }) => joinUrl(basePath, href));
29
+ const hrefs = data.map(({ href }) => joinURL(basePath, href));
30
30
  const activePath = getActivePath(pathname, hrefs);
31
31
  return data.map((item) => ({
32
32
  ...item,
33
33
  children: transformChildren(item.children || [], item.href),
34
- href: joinUrl(basePath, item.href),
35
- isActive: joinUrl(basePath, item.href) === activePath,
34
+ href: joinURL(basePath, item.href),
35
+ isActive: joinURL(basePath, item.href) === activePath,
36
36
  }));
37
37
  }
38
38
  export default useNavigation;