sprintify-ui 0.2.19 → 0.2.22

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 (405) hide show
  1. package/README.md +244 -244
  2. package/dist/sprintify-ui.es.js +7634 -7664
  3. package/dist/style.css +1 -1
  4. package/dist/tailwindcss/index.js +306 -306
  5. package/dist/types/src/components/BaseActionItem.vue.d.ts +40 -40
  6. package/dist/types/src/components/BaseActionItemButton.vue.d.ts +25 -25
  7. package/dist/types/src/components/BaseAddressForm.vue.d.ts +84 -84
  8. package/dist/types/src/components/BaseAlert.vue.d.ts +51 -51
  9. package/dist/types/src/components/BaseApp.vue.d.ts +9 -9
  10. package/dist/types/src/components/BaseAppDialogs.vue.d.ts +14 -14
  11. package/dist/types/src/components/BaseAppNotifications.vue.d.ts +2 -2
  12. package/dist/types/src/components/BaseAutocomplete.vue.d.ts +237 -237
  13. package/dist/types/src/components/BaseAutocompleteDrawer.vue.d.ts +91 -91
  14. package/dist/types/src/components/BaseAutocompleteFetch.vue.d.ts +210 -210
  15. package/dist/types/src/components/BaseAvatar.vue.d.ts +52 -52
  16. package/dist/types/src/components/BaseAvatarGroup.vue.d.ts +43 -43
  17. package/dist/types/src/components/BaseBadge.vue.d.ts +54 -54
  18. package/dist/types/src/components/BaseBelongsTo.vue.d.ts +216 -216
  19. package/dist/types/src/components/BaseBoolean.vue.d.ts +10 -10
  20. package/dist/types/src/components/BaseBreadcrumbs.vue.d.ts +14 -14
  21. package/dist/types/src/components/BaseButton.vue.d.ts +23 -23
  22. package/dist/types/src/components/BaseButtonGroup.vue.d.ts +143 -143
  23. package/dist/types/src/components/BaseCard.vue.d.ts +21 -21
  24. package/dist/types/src/components/BaseCardRow.vue.d.ts +16 -16
  25. package/dist/types/src/components/BaseCharacterCounter.vue.d.ts +49 -49
  26. package/dist/types/src/components/BaseClickOutside.vue.d.ts +26 -26
  27. package/dist/types/src/components/BaseClipboard.vue.d.ts +21 -21
  28. package/dist/types/src/components/BaseColor.vue.d.ts +80 -80
  29. package/dist/types/src/components/BaseContainer.vue.d.ts +34 -34
  30. package/dist/types/src/components/BaseCounter.vue.d.ts +42 -42
  31. package/dist/types/src/components/BaseCropper.vue.d.ts +76 -76
  32. package/dist/types/src/components/BaseCropperModal.vue.d.ts +28 -28
  33. package/dist/types/src/components/BaseDataIterator.vue.d.ts +212 -212
  34. package/dist/types/src/components/BaseDataIteratorSectionBox.vue.d.ts +20 -20
  35. package/dist/types/src/components/BaseDataIteratorSectionButton.vue.d.ts +17 -17
  36. package/dist/types/src/components/BaseDataIteratorSectionColumns.vue.d.ts +637 -637
  37. package/dist/types/src/components/BaseDataIteratorSectionModal.vue.d.ts +32 -32
  38. package/dist/types/src/components/BaseDataTable.vue.d.ts +385 -385
  39. package/dist/types/src/components/BaseDataTableRowAction.vue.d.ts +21 -21
  40. package/dist/types/src/components/BaseDatePicker.vue.d.ts +124 -124
  41. package/dist/types/src/components/BaseDateSelect.vue.d.ts +79 -79
  42. package/dist/types/src/components/BaseDescriptionList.vue.d.ts +9 -9
  43. package/dist/types/src/components/BaseDescriptionListItem.vue.d.ts +10 -10
  44. package/dist/types/src/components/BaseDialog.vue.d.ts +60 -60
  45. package/dist/types/src/components/BaseDisplayRelativeTime.vue.d.ts +68 -68
  46. package/dist/types/src/components/BaseDraggable.vue.d.ts +49 -49
  47. package/dist/types/src/components/BaseDropdown.vue.d.ts +65 -65
  48. package/dist/types/src/components/BaseDropdownAutocomplete.vue.d.ts +132 -132
  49. package/dist/types/src/components/BaseField.vue.d.ts +58 -58
  50. package/dist/types/src/components/BaseFieldI18n.vue.d.ts +93 -93
  51. package/dist/types/src/components/BaseFilePicker.vue.d.ts +72 -72
  52. package/dist/types/src/components/BaseFilePickerCrop.vue.d.ts +63 -63
  53. package/dist/types/src/components/BaseFileUploader.vue.d.ts +144 -144
  54. package/dist/types/src/components/BaseForm.vue.d.ts +134 -134
  55. package/dist/types/src/components/BaseGantt.vue.d.ts +425 -425
  56. package/dist/types/src/components/BaseHasMany.vue.d.ts +149 -149
  57. package/dist/types/src/components/BaseHeader.vue.d.ts +98 -98
  58. package/dist/types/src/components/BaseIconPicker.vue.d.ts +34 -34
  59. package/dist/types/src/components/BaseInput.vue.d.ts +174 -174
  60. package/dist/types/src/components/BaseInputError.vue.d.ts +9 -9
  61. package/dist/types/src/components/BaseInputLabel.vue.d.ts +43 -43
  62. package/dist/types/src/components/BaseInputPercent.vue.d.ts +138 -138
  63. package/dist/types/src/components/BaseLayoutNotificationDropdown.vue.d.ts +36 -36
  64. package/dist/types/src/components/BaseLayoutNotificationItem.vue.d.ts +16 -16
  65. package/dist/types/src/components/BaseLayoutNotificationItemContent.vue.d.ts +21 -21
  66. package/dist/types/src/components/BaseLayoutSidebar.vue.d.ts +51 -51
  67. package/dist/types/src/components/BaseLayoutSidebarConfigurable.vue.d.ts +87 -87
  68. package/dist/types/src/components/BaseLayoutStacked.vue.d.ts +23 -23
  69. package/dist/types/src/components/BaseLayoutStackedConfigurable.vue.d.ts +78 -78
  70. package/dist/types/src/components/BaseLoadingCover.vue.d.ts +96 -96
  71. package/dist/types/src/components/BaseMediaGallery.vue.d.ts +64 -64
  72. package/dist/types/src/components/BaseMediaGalleryItem.vue.d.ts +45 -45
  73. package/dist/types/src/components/BaseMediaItem.vue.d.ts +27 -27
  74. package/dist/types/src/components/BaseMediaLibrary.vue.d.ts +199 -199
  75. package/dist/types/src/components/BaseMediaList.vue.d.ts +47 -47
  76. package/dist/types/src/components/BaseMediaListItem.vue.d.ts +47 -47
  77. package/dist/types/src/components/BaseMediaPictures.vue.d.ts +55 -55
  78. package/dist/types/src/components/BaseMediaPicturesItem.vue.d.ts +54 -54
  79. package/dist/types/src/components/BaseMediaPreview.vue.d.ts +36 -36
  80. package/dist/types/src/components/BaseMenu.vue.d.ts +68 -68
  81. package/dist/types/src/components/BaseMenuItem.vue.d.ts +61 -61
  82. package/dist/types/src/components/BaseModalCenter.vue.d.ts +80 -80
  83. package/dist/types/src/components/BaseModalSide.vue.d.ts +62 -62
  84. package/dist/types/src/components/BaseNavbar.vue.d.ts +38 -38
  85. package/dist/types/src/components/BaseNavbarItem.vue.d.ts +26 -26
  86. package/dist/types/src/components/BaseNavbarItemContent.vue.d.ts +60 -60
  87. package/dist/types/src/components/BaseNavbarSideItem.vue.d.ts +44 -44
  88. package/dist/types/src/components/BaseNavbarSideItemContent.vue.d.ts +60 -60
  89. package/dist/types/src/components/BasePagination.vue.d.ts +35 -35
  90. package/dist/types/src/components/BasePanel.vue.d.ts +31 -31
  91. package/dist/types/src/components/BasePassword.vue.d.ts +67 -67
  92. package/dist/types/src/components/BaseProgressCircle.vue.d.ts +37 -37
  93. package/dist/types/src/components/BaseRadioGroup.vue.d.ts +105 -105
  94. package/dist/types/src/components/BaseReadMore.vue.d.ts +21 -21
  95. package/dist/types/src/components/BaseRichText.vue.d.ts +92 -92
  96. package/dist/types/src/components/BaseSelect.vue.d.ts +98 -98
  97. package/dist/types/src/components/BaseShortcut.vue.d.ts +86 -86
  98. package/dist/types/src/components/BaseSideNavigation.vue.d.ts +21 -21
  99. package/dist/types/src/components/BaseSideNavigationItem.vue.d.ts +41 -41
  100. package/dist/types/src/components/BaseSkeleton.vue.d.ts +31 -31
  101. package/dist/types/src/components/BaseStatistic.vue.d.ts +56 -56
  102. package/dist/types/src/components/BaseStepper.vue.d.ts +16 -16
  103. package/dist/types/src/components/BaseStepperItem.vue.d.ts +51 -51
  104. package/dist/types/src/components/BaseSwitch.vue.d.ts +87 -87
  105. package/dist/types/src/components/BaseSystemAlert.vue.d.ts +52 -52
  106. package/dist/types/src/components/BaseTabItem.vue.d.ts +41 -41
  107. package/dist/types/src/components/BaseTable.vue.d.ts +212 -212
  108. package/dist/types/src/components/BaseTableColumn.vue.d.ts +174 -174
  109. package/dist/types/src/components/BaseTabs.vue.d.ts +21 -21
  110. package/dist/types/src/components/BaseTagAutocomplete.vue.d.ts +209 -209
  111. package/dist/types/src/components/BaseTagAutocompleteFetch.vue.d.ts +141 -141
  112. package/dist/types/src/components/BaseTextarea.vue.d.ts +103 -103
  113. package/dist/types/src/components/BaseTextareaAutoresize.vue.d.ts +113 -113
  114. package/dist/types/src/components/BaseTimeline.vue.d.ts +14 -14
  115. package/dist/types/src/components/BaseTimelineItem.vue.d.ts +14 -14
  116. package/dist/types/src/components/BaseUniqueCode.vue.d.ts +33 -33
  117. package/dist/types/src/components/SlotComponent.d.ts +43 -43
  118. package/dist/types/src/components/index.d.ts +96 -96
  119. package/dist/types/src/composables/breakpoints.d.ts +27 -27
  120. package/dist/types/src/composables/clickOutside.d.ts +8 -8
  121. package/dist/types/src/composables/field.d.ts +19 -19
  122. package/dist/types/src/composables/hasOptions.d.ts +7 -7
  123. package/dist/types/src/composables/mediaQuery.d.ts +2 -2
  124. package/dist/types/src/composables/modal.d.ts +6 -6
  125. package/dist/types/src/composables/paginatedData.d.ts +7 -7
  126. package/dist/types/src/constants/MyConstants.d.ts +1 -1
  127. package/dist/types/src/constants/index.d.ts +2 -2
  128. package/dist/types/src/i18n/index.d.ts +1 -1
  129. package/dist/types/src/index.d.ts +222 -222
  130. package/dist/types/src/services/gantt/format.d.ts +24 -24
  131. package/dist/types/src/services/gantt/timescale.d.ts +26 -26
  132. package/dist/types/src/services/gantt/types.d.ts +67 -67
  133. package/dist/types/src/stores/dialogs.d.ts +9 -9
  134. package/dist/types/src/stores/i18n.d.ts +5 -5
  135. package/dist/types/src/stores/notifications.d.ts +10 -10
  136. package/dist/types/src/stores/systemAlerts.d.ts +9 -9
  137. package/dist/types/src/svg/BaseEmptyState.vue.d.ts +2 -2
  138. package/dist/types/src/svg/BaseSpinnerLarge.vue.d.ts +2 -2
  139. package/dist/types/src/svg/BaseSpinnerSmall.vue.d.ts +2 -2
  140. package/dist/types/src/types/Color.d.ts +9 -9
  141. package/dist/types/src/types/Country.d.ts +4 -4
  142. package/dist/types/src/types/ImagePickerResult.d.ts +5 -5
  143. package/dist/types/src/types/Media.d.ts +9 -9
  144. package/dist/types/src/types/Notification.d.ts +8 -8
  145. package/dist/types/src/types/Region.d.ts +5 -5
  146. package/dist/types/src/types/Status.d.ts +5 -5
  147. package/dist/types/src/types/StepperItem.d.ts +7 -7
  148. package/dist/types/src/types/TimelineItem.d.ts +8 -8
  149. package/dist/types/src/types/UploadedFile.d.ts +10 -10
  150. package/dist/types/src/types/User.d.ts +6 -6
  151. package/dist/types/src/types/index.d.ts +218 -218
  152. package/dist/types/src/utils/blob.d.ts +3 -3
  153. package/dist/types/src/utils/colors.d.ts +13 -13
  154. package/dist/types/src/utils/cropper/avatar.d.ts +5 -5
  155. package/dist/types/src/utils/cropper/cover.d.ts +5 -5
  156. package/dist/types/src/utils/cropper/presetInterface.d.ts +7 -7
  157. package/dist/types/src/utils/cropper/presets.d.ts +6 -6
  158. package/dist/types/src/utils/fileSizeFormat.d.ts +1 -1
  159. package/dist/types/src/utils/fileValidations.d.ts +2 -2
  160. package/dist/types/src/utils/index.d.ts +6 -6
  161. package/dist/types/src/utils/resizeImageFromURI.d.ts +1 -1
  162. package/dist/types/src/utils/scrollPreventer.d.ts +3 -3
  163. package/dist/types/src/utils/toHumanList.d.ts +1 -1
  164. package/package.json +139 -136
  165. package/src/assets/flatpickr.css +243 -243
  166. package/src/assets/form.css +6 -6
  167. package/src/assets/main.css +36 -36
  168. package/src/assets/tailwind.css +2 -2
  169. package/src/components/BaseActionItem.vue +68 -68
  170. package/src/components/BaseActionItemButton.vue +75 -75
  171. package/src/components/BaseAddressForm.stories.js +103 -103
  172. package/src/components/BaseAddressForm.vue +354 -354
  173. package/src/components/BaseAlert.stories.js +52 -52
  174. package/src/components/BaseAlert.vue +158 -158
  175. package/src/components/BaseApp.vue +16 -16
  176. package/src/components/BaseAppDialogs.vue +124 -124
  177. package/src/components/BaseAppNotifications.vue +76 -76
  178. package/src/components/BaseAutocomplete.stories.js +236 -236
  179. package/src/components/BaseAutocomplete.vue +523 -523
  180. package/src/components/BaseAutocompleteDrawer.vue +372 -372
  181. package/src/components/BaseAutocompleteFetch.stories.js +224 -224
  182. package/src/components/BaseAutocompleteFetch.vue +288 -288
  183. package/src/components/BaseAvatar.stories.js +39 -39
  184. package/src/components/BaseAvatar.vue +120 -120
  185. package/src/components/BaseAvatarGroup.stories.js +71 -71
  186. package/src/components/BaseAvatarGroup.vue +148 -148
  187. package/src/components/BaseBadge.stories.js +124 -124
  188. package/src/components/BaseBadge.vue +78 -78
  189. package/src/components/BaseBelongsTo.stories.js +223 -223
  190. package/src/components/BaseBelongsTo.vue +193 -193
  191. package/src/components/BaseBoolean.stories.js +35 -35
  192. package/src/components/BaseBoolean.vue +26 -26
  193. package/src/components/BaseBreadcrumbs.stories.js +45 -45
  194. package/src/components/BaseBreadcrumbs.vue +104 -104
  195. package/src/components/BaseButton.stories.js +88 -88
  196. package/src/components/BaseButton.vue +46 -46
  197. package/src/components/BaseButtonGroup.stories.js +86 -86
  198. package/src/components/BaseButtonGroup.vue +150 -150
  199. package/src/components/BaseCard.stories.js +61 -61
  200. package/src/components/BaseCard.vue +49 -49
  201. package/src/components/BaseCardRow.vue +34 -34
  202. package/src/components/BaseCharacterCounter.stories.js +30 -30
  203. package/src/components/BaseCharacterCounter.vue +64 -64
  204. package/src/components/BaseClickOutside.vue +37 -37
  205. package/src/components/BaseClipboard.stories.js +31 -31
  206. package/src/components/BaseClipboard.vue +99 -99
  207. package/src/components/BaseColor.stories.js +46 -46
  208. package/src/components/BaseColor.vue +154 -154
  209. package/src/components/BaseContainer.stories.js +34 -34
  210. package/src/components/BaseContainer.vue +50 -50
  211. package/src/components/BaseCounter.stories.js +47 -47
  212. package/src/components/BaseCounter.vue +82 -82
  213. package/src/components/BaseCropper.stories.js +113 -113
  214. package/src/components/BaseCropper.vue +458 -458
  215. package/src/components/BaseCropperModal.stories.js +54 -54
  216. package/src/components/BaseCropperModal.vue +143 -143
  217. package/src/components/BaseDataIterator.stories.js +197 -197
  218. package/src/components/BaseDataIterator.vue +802 -802
  219. package/src/components/BaseDataIteratorSectionBox.vue +36 -36
  220. package/src/components/BaseDataIteratorSectionButton.vue +42 -42
  221. package/src/components/BaseDataIteratorSectionColumns.vue +70 -70
  222. package/src/components/BaseDataIteratorSectionModal.vue +41 -41
  223. package/src/components/BaseDataTable.stories.js +341 -341
  224. package/src/components/BaseDataTable.vue +747 -747
  225. package/src/components/BaseDataTableRowAction.vue +34 -34
  226. package/src/components/BaseDatePicker.stories.js +130 -130
  227. package/src/components/BaseDatePicker.vue +296 -296
  228. package/src/components/BaseDateSelect.stories.js +47 -47
  229. package/src/components/BaseDateSelect.vue +241 -241
  230. package/src/components/BaseDescriptionList.stories.js +35 -35
  231. package/src/components/BaseDescriptionList.vue +13 -13
  232. package/src/components/BaseDescriptionListItem.vue +47 -47
  233. package/src/components/BaseDialog.stories.js +51 -51
  234. package/src/components/BaseDialog.vue +119 -119
  235. package/src/components/BaseDisplayRelativeTime.stories.js +59 -59
  236. package/src/components/BaseDisplayRelativeTime.vue +123 -123
  237. package/src/components/BaseDraggable.vue +71 -71
  238. package/src/components/BaseDropdown.stories.js +210 -210
  239. package/src/components/BaseDropdown.vue +280 -280
  240. package/src/components/BaseDropdownAutocomplete.stories.js +187 -187
  241. package/src/components/BaseDropdownAutocomplete.vue +236 -236
  242. package/src/components/BaseField.vue +112 -112
  243. package/src/components/BaseFieldI18n.stories.js +38 -38
  244. package/src/components/BaseFieldI18n.vue +170 -170
  245. package/src/components/BaseFilePicker.stories.js +84 -83
  246. package/src/components/BaseFilePicker.vue +166 -166
  247. package/src/components/BaseFilePickerCrop.stories.js +135 -134
  248. package/src/components/BaseFilePickerCrop.vue +130 -130
  249. package/src/components/BaseFileUploader.stories.js +90 -89
  250. package/src/components/BaseFileUploader.vue +174 -174
  251. package/src/components/BaseForm.stories.js +48 -46
  252. package/src/components/BaseForm.vue +331 -331
  253. package/src/components/BaseGantt.stories.js +133 -133
  254. package/src/components/BaseGantt.vue +336 -336
  255. package/src/components/BaseHasMany.stories.js +189 -189
  256. package/src/components/BaseHasMany.vue +137 -137
  257. package/src/components/BaseHeader.stories.js +127 -127
  258. package/src/components/BaseHeader.vue +191 -191
  259. package/src/components/BaseIconPicker.stories.js +22 -22
  260. package/src/components/BaseIconPicker.vue +225 -225
  261. package/src/components/BaseInput.stories.js +167 -167
  262. package/src/components/BaseInput.vue +264 -264
  263. package/src/components/BaseInputError.vue +7 -7
  264. package/src/components/BaseInputLabel.stories.js +36 -36
  265. package/src/components/BaseInputLabel.vue +75 -75
  266. package/src/components/BaseInputPercent.stories.js +65 -65
  267. package/src/components/BaseInputPercent.vue +139 -139
  268. package/src/components/BaseLayoutNotificationDropdown.vue +150 -150
  269. package/src/components/BaseLayoutNotificationItem.vue +53 -53
  270. package/src/components/BaseLayoutNotificationItemContent.vue +30 -30
  271. package/src/components/BaseLayoutSidebar.vue +236 -236
  272. package/src/components/BaseLayoutSidebarConfigurable.stories.js +166 -166
  273. package/src/components/BaseLayoutSidebarConfigurable.vue +181 -181
  274. package/src/components/BaseLayoutStacked.vue +52 -52
  275. package/src/components/BaseLayoutStackedConfigurable.stories.js +109 -109
  276. package/src/components/BaseLayoutStackedConfigurable.vue +158 -158
  277. package/src/components/BaseLoadingCover.stories.js +55 -55
  278. package/src/components/BaseLoadingCover.vue +101 -101
  279. package/src/components/BaseMediaGallery.vue +96 -96
  280. package/src/components/BaseMediaGalleryItem.vue +101 -101
  281. package/src/components/BaseMediaItem.stories.js +41 -41
  282. package/src/components/BaseMediaItem.vue +80 -80
  283. package/src/components/BaseMediaLibrary.stories.js +267 -268
  284. package/src/components/BaseMediaLibrary.vue +323 -323
  285. package/src/components/BaseMediaList.vue +68 -68
  286. package/src/components/BaseMediaListItem.vue +181 -181
  287. package/src/components/BaseMediaPictures.vue +64 -64
  288. package/src/components/BaseMediaPicturesItem.vue +100 -100
  289. package/src/components/BaseMediaPreview.stories.js +72 -72
  290. package/src/components/BaseMediaPreview.vue +106 -106
  291. package/src/components/BaseMenu.stories.js +125 -125
  292. package/src/components/BaseMenu.vue +165 -165
  293. package/src/components/BaseMenuItem.vue +118 -118
  294. package/src/components/BaseModalCenter.stories.js +68 -68
  295. package/src/components/BaseModalCenter.vue +134 -134
  296. package/src/components/BaseModalSide.stories.js +55 -55
  297. package/src/components/BaseModalSide.vue +122 -122
  298. package/src/components/BaseNavbar.stories.js +151 -151
  299. package/src/components/BaseNavbar.vue +91 -91
  300. package/src/components/BaseNavbarItem.vue +49 -49
  301. package/src/components/BaseNavbarItemContent.vue +97 -97
  302. package/src/components/BaseNavbarSideItem.vue +114 -114
  303. package/src/components/BaseNavbarSideItemContent.vue +111 -111
  304. package/src/components/BasePagination.stories.js +35 -35
  305. package/src/components/BasePagination.vue +266 -266
  306. package/src/components/BasePanel.stories.js +56 -56
  307. package/src/components/BasePanel.vue +42 -42
  308. package/src/components/BasePassword.stories.js +57 -57
  309. package/src/components/BasePassword.vue +107 -107
  310. package/src/components/BaseProgressCircle.stories.js +27 -27
  311. package/src/components/BaseProgressCircle.vue +80 -80
  312. package/src/components/BaseRadioGroup.stories.js +88 -88
  313. package/src/components/BaseRadioGroup.vue +125 -125
  314. package/src/components/BaseReadMore.stories.js +30 -30
  315. package/src/components/BaseReadMore.vue +73 -73
  316. package/src/components/BaseRichText.stories.js +102 -102
  317. package/src/components/BaseRichText.vue +182 -182
  318. package/src/components/BaseSelect.stories.js +118 -118
  319. package/src/components/BaseSelect.vue +224 -224
  320. package/src/components/BaseShortcut.stories.js +102 -102
  321. package/src/components/BaseShortcut.vue +112 -112
  322. package/src/components/BaseSideNavigation.stories.js +80 -80
  323. package/src/components/BaseSideNavigation.vue +32 -32
  324. package/src/components/BaseSideNavigationItem.vue +95 -95
  325. package/src/components/BaseSkeleton.stories.js +36 -36
  326. package/src/components/BaseSkeleton.vue +40 -40
  327. package/src/components/BaseStatistic.stories.js +51 -51
  328. package/src/components/BaseStatistic.vue +109 -109
  329. package/src/components/BaseStepper.stories.js +94 -94
  330. package/src/components/BaseStepper.vue +72 -72
  331. package/src/components/BaseStepperItem.stories.js +65 -65
  332. package/src/components/BaseStepperItem.vue +149 -149
  333. package/src/components/BaseSwitch.stories.js +130 -130
  334. package/src/components/BaseSwitch.vue +215 -215
  335. package/src/components/BaseSystemAlert.stories.js +63 -63
  336. package/src/components/BaseSystemAlert.vue +89 -89
  337. package/src/components/BaseTabItem.vue +96 -96
  338. package/src/components/BaseTable.vue +890 -890
  339. package/src/components/BaseTableColumn.vue +124 -124
  340. package/src/components/BaseTabs.stories.js +85 -85
  341. package/src/components/BaseTabs.vue +73 -73
  342. package/src/components/BaseTagAutocomplete.stories.js +258 -258
  343. package/src/components/BaseTagAutocomplete.vue +438 -438
  344. package/src/components/BaseTagAutocompleteFetch.stories.js +185 -185
  345. package/src/components/BaseTagAutocompleteFetch.vue +220 -220
  346. package/src/components/BaseTextarea.stories.js +58 -58
  347. package/src/components/BaseTextarea.vue +103 -103
  348. package/src/components/BaseTextareaAutoresize.stories.js +102 -102
  349. package/src/components/BaseTextareaAutoresize.vue +166 -166
  350. package/src/components/BaseTimeline.stories.js +53 -53
  351. package/src/components/BaseTimeline.vue +35 -35
  352. package/src/components/BaseTimelineItem.stories.js +78 -78
  353. package/src/components/BaseTimelineItem.vue +79 -79
  354. package/src/components/BaseUniqueCode.stories.js +36 -36
  355. package/src/components/BaseUniqueCode.vue +183 -183
  356. package/src/components/SlotComponent.ts +37 -37
  357. package/src/components/index.ts +194 -194
  358. package/src/composables/breakpoints.ts +94 -94
  359. package/src/composables/clickOutside.ts +80 -80
  360. package/src/composables/field.ts +117 -117
  361. package/src/composables/hasOptions.ts +68 -68
  362. package/src/composables/mediaQuery.ts +42 -42
  363. package/src/composables/modal.ts +73 -73
  364. package/src/composables/paginatedData.ts +65 -65
  365. package/src/constants/MyConstants.ts +1 -1
  366. package/src/constants/index.ts +5 -5
  367. package/src/env.d.ts +15 -15
  368. package/src/i18n/index.ts +60 -60
  369. package/src/index.ts +111 -111
  370. package/src/lang/en.json +87 -87
  371. package/src/lang/fr.json +87 -87
  372. package/src/services/gantt/format.ts +113 -113
  373. package/src/services/gantt/timescale.ts +242 -242
  374. package/src/services/gantt/types.ts +74 -74
  375. package/src/stores/dialogs.ts +45 -45
  376. package/src/stores/i18n.ts +14 -14
  377. package/src/stores/notifications.ts +47 -47
  378. package/src/stores/systemAlerts.ts +33 -33
  379. package/src/svg/BaseEmptyState.vue +38 -38
  380. package/src/svg/BaseSpinnerLarge.vue +59 -59
  381. package/src/svg/BaseSpinnerSmall.vue +15 -15
  382. package/src/types/Color.ts +9 -9
  383. package/src/types/Country.ts +4 -4
  384. package/src/types/ImagePickerResult.ts +5 -5
  385. package/src/types/Media.ts +10 -10
  386. package/src/types/Notification.ts +10 -10
  387. package/src/types/Region.ts +5 -5
  388. package/src/types/Status.ts +5 -5
  389. package/src/types/StepperItem.ts +8 -8
  390. package/src/types/TimelineItem.ts +8 -8
  391. package/src/types/UploadedFile.ts +11 -11
  392. package/src/types/User.ts +7 -7
  393. package/src/types/index.ts +267 -267
  394. package/src/utils/blob.ts +30 -30
  395. package/src/utils/colors.ts +200 -200
  396. package/src/utils/cropper/avatar.ts +33 -33
  397. package/src/utils/cropper/cover.ts +41 -41
  398. package/src/utils/cropper/presetInterface.ts +16 -16
  399. package/src/utils/cropper/presets.ts +7 -7
  400. package/src/utils/fileSizeFormat.ts +15 -15
  401. package/src/utils/fileValidations.ts +26 -26
  402. package/src/utils/index.ts +16 -16
  403. package/src/utils/resizeImageFromURI.ts +118 -118
  404. package/src/utils/scrollPreventer.ts +11 -11
  405. package/src/utils/toHumanList.ts +20 -20
@@ -1,747 +1,747 @@
1
- <template>
2
- <BaseDataIterator
3
- ref="dataIterator"
4
- :url="url"
5
- :url-query="urlQuery"
6
- :default-query="defaultQuery"
7
- :searchable="searchable"
8
- :actions="actions"
9
- :history-mode="historyMode"
10
- :layout="layout"
11
- :sections="sectionsInternal"
12
- :scroll-top-on-fetch="maxHeight ? false : scrollTopOnFetch"
13
- @fetch="onFetch"
14
- @will-scroll-top="onWillScrollTop"
15
- >
16
- <template
17
- #default="{
18
- items,
19
- loading,
20
- sortField,
21
- sortDirection,
22
- onSortChange,
23
- error,
24
- firstLoad,
25
- }"
26
- >
27
- <BaseCard
28
- clipped
29
- class="w-full overflow-hidden"
30
- >
31
- <div v-if="newCheckedRows.length">
32
- <div
33
- class="flex items-center justify-between border-b border-slate-200 bg-slate-50 py-2 pl-3 pr-2 text-sm"
34
- >
35
- <div>
36
- <span class="mr-3 text-slate-500">{{
37
- t('sui.x_rows_selected', {
38
- count: newCheckedRows.length,
39
- })
40
- }}.</span>
41
- <button
42
- type="button"
43
- class="mr-3 inline text-slate-700 underline"
44
- @click="uncheckAll()"
45
- >
46
- {{ t('sui.deselect_all') }}
47
- </button>
48
- </div>
49
- <BaseMenu
50
- v-if="checkableActions?.length"
51
- tw-menu="w-52"
52
- :items="checkableActions"
53
- >
54
- <template #button="{ open }">
55
- <div
56
- class="flex h-10 w-10 items-center justify-center rounded-full border border-slate-300 bg-white duration-150 hover:bg-slate-50"
57
- :class="[
58
- open ? 'ring-2 ring-primary-500 ring-offset-2' : false,
59
- ]"
60
- >
61
- <BaseIcon icon="heroicons-solid:dots-vertical" />
62
- </div>
63
- </template>
64
- </BaseMenu>
65
- </div>
66
- </div>
67
-
68
- <BaseTable
69
- ref="table"
70
- :checked-rows="newCheckedRows"
71
- :data="items"
72
- :loading="loading"
73
- :detailed="detailed"
74
- :has-detailed-visible="hasDetailedVisible"
75
- :checkable="checkable"
76
- :is-row-checkable="isRowCheckable"
77
- checkbox-position="left"
78
- :sort-field="sortField"
79
- :sort-direction="sortDirection"
80
- :max-height="maxHeight"
81
- :visible-columns="visibleColumns"
82
- @update:checked-rows="onCheckedRowsUpdate"
83
- @sort="onSortChange"
84
- @cell-click="onCellClick"
85
- >
86
- <template #default>
87
- <slot />
88
-
89
- <BaseTableColumn
90
- v-slot="{ row }"
91
- :visible="rowActionsInternal.length"
92
- :toggle="false"
93
- :clickable="false"
94
- custom-key="actions"
95
- class="overflow-hidden"
96
- >
97
- <div class="flex justify-end gap-1 pr-2 text-right">
98
- <div class="btn-group">
99
- <template
100
- v-for="rowAction in visibleRowActions"
101
- :key="rowAction.icon"
102
- >
103
- <BaseDataTableRowAction
104
- :row="row"
105
- :row-action="rowAction"
106
- />
107
- </template>
108
- <BaseMenu
109
- v-if="showRowActionMenu"
110
- :items="rowActionMenuItems(row)"
111
- size="sm"
112
- button-class="btn flex h-8 w-8 p-0 items-center justify-center"
113
- >
114
- <template #button>
115
- <BaseIcon icon="heroicons-solid:dots-vertical" />
116
- </template>
117
- </BaseMenu>
118
- </div>
119
- </div>
120
- </BaseTableColumn>
121
- </template>
122
-
123
- <template #detail="propsDetail">
124
- <slot
125
- name="detail"
126
- v-bind="propsDetail"
127
- />
128
- </template>
129
-
130
- <template #checkedHeader="propsCheckHeader">
131
- <slot
132
- name="checkedHeader"
133
- v-bind="propsCheckHeader"
134
- />
135
- </template>
136
-
137
- <template #empty>
138
- <div
139
- v-if="error"
140
- class="flex items-center justify-center py-16"
141
- >
142
- <div class="flex flex-col items-center justify-center">
143
- <BaseIcon
144
- icon="heroicons:x-circle"
145
- class="h-10 w-10 text-red-600"
146
- />
147
- <p class="mt-3 text-center text-sm text-slate-600">
148
- {{ t('sui.whoops') }}
149
- </p>
150
- </div>
151
- </div>
152
- <div
153
- v-else-if="firstLoad"
154
- class="flex items-center justify-center py-16"
155
- >
156
- <div class="flex flex-col items-center">
157
- <BaseEmptyState class="w-32" />
158
-
159
- <p class="mt-3 text-center text-sm text-slate-600">
160
- {{ t('sui.nothing_found') }}
161
- </p>
162
- </div>
163
- </div>
164
- </template>
165
- </BaseTable>
166
- </BaseCard>
167
- </template>
168
-
169
- <template
170
- v-if="$slots.filters"
171
- #filters="{ query, updateQuery, updateQueryValue }"
172
- >
173
- <slot
174
- name="filters"
175
- :query="query"
176
- :update-query="updateQuery"
177
- :update-query-value="updateQueryValue"
178
- />
179
- </template>
180
-
181
- <template #sidebarTop="sidebarProps">
182
- <slot
183
- name="sidebarTop"
184
- v-bind="sidebarProps"
185
- />
186
- </template>
187
-
188
- <template #sidebarBottom="sidebarProps">
189
- <slot
190
- name="sidebarBottom"
191
- v-bind="sidebarProps"
192
- />
193
- </template>
194
-
195
- <template
196
- v-if="toggleable"
197
- #columns
198
- >
199
- <BaseDataIteratorSectionColumns
200
- v-model:visibleColumns="visibleColumns"
201
- :table="table"
202
- @update:visible-columns="onUpdateVisibleColumn"
203
- />
204
- </template>
205
-
206
- <template
207
- v-for="section in sections"
208
- :key="section.name"
209
- #[section.name]
210
- >
211
- <slot :name="section.name" />
212
- </template>
213
- </BaseDataIterator>
214
- </template>
215
-
216
- <script lang="ts" setup>
217
- import { PropType } from 'vue';
218
- import { t } from '@/i18n';
219
- import {
220
- Collection,
221
- CollectionItem,
222
- DataIteratorSection,
223
- DataTableQuery,
224
- MenuItemInterface,
225
- PaginatedCollection,
226
- ResourceCollection,
227
- RowAction,
228
- } from '@/types';
229
- import { useDialogsStore } from '@/stores/dialogs';
230
- import { useNotificationsStore } from '../stores/notifications';
231
- import BaseDataIterator from './BaseDataIterator.vue';
232
- import { cloneDeep, isArray } from 'lodash';
233
-
234
- import BaseCard from './BaseCard.vue';
235
- import BaseTable from './BaseTable.vue';
236
- import BaseTableColumn from './BaseTableColumn.vue';
237
- import BaseDataIteratorSectionColumns from './BaseDataIteratorSectionColumns.vue';
238
- import { BaseIcon, config } from '@/index';
239
- import BaseEmptyState from '../svg/BaseEmptyState.vue';
240
- import { RouteLocationRaw } from 'vue-router';
241
- import BaseMenu from './BaseMenu.vue';
242
- import BaseDataTableRowAction from './BaseDataTableRowAction.vue';
243
-
244
- const router = useRouter();
245
-
246
- const http = config.http;
247
-
248
- const dialogs = useDialogsStore();
249
- const notifications = useNotificationsStore();
250
-
251
- const table = ref<null | InstanceType<typeof BaseTable>>(null);
252
-
253
- const props = defineProps({
254
- /**
255
- * Base URL from which to make requests
256
- */
257
- url: {
258
- required: true,
259
- type: String,
260
- },
261
-
262
- /**
263
- * Query params that always get applied
264
- */
265
- urlQuery: {
266
- default: undefined,
267
- type: Object as PropType<Record<string, any>>,
268
- },
269
-
270
- /**
271
- * Query params that gets applied by default
272
- * These may be overwritten by URL params generated by the data-table or filters
273
- */
274
- defaultQuery: {
275
- default: undefined,
276
- type: Object as PropType<DataTableQuery>,
277
- },
278
-
279
- /**
280
- * Show url for router link
281
- */
282
- showUrl: {
283
- default: undefined,
284
- type: Function as PropType<
285
- ((row: CollectionItem) => RouteLocationRaw) | undefined
286
- >,
287
- },
288
-
289
- /**
290
- * Show/Hide edit button
291
- */
292
- editButton: {
293
- default: true,
294
- type: Boolean,
295
- },
296
-
297
- /**
298
- * Edit url for router link
299
- */
300
- editUrl: {
301
- default: undefined,
302
- type: Function as PropType<
303
- ((row: CollectionItem) => RouteLocationRaw) | undefined
304
- >,
305
- },
306
-
307
- /**
308
- * Show/Hide delete button
309
- */
310
- deleteButton: {
311
- default: true,
312
- type: Boolean,
313
- },
314
-
315
- /**
316
- * Delete endpoint to delete an item
317
- */
318
- deleteUrl: {
319
- default: undefined,
320
- type: Function as PropType<((row: CollectionItem) => string) | undefined>,
321
- },
322
-
323
- /**
324
- * Show toggle-able details on each row
325
- */
326
- detailed: {
327
- default: false,
328
- type: Boolean,
329
- },
330
-
331
- /**
332
- * Check is a given row has details
333
- */
334
- hasDetailedVisible: {
335
- default() {
336
- return true;
337
- },
338
- type: Function as PropType<(row: any) => boolean>,
339
- },
340
-
341
- /**
342
- * Makes row checkable
343
- */
344
- checkable: {
345
- default: false,
346
- type: Boolean,
347
- },
348
-
349
- /**
350
- * Actions on each row
351
- */
352
- checkableActions: {
353
- default: undefined,
354
- type: Array as PropType<MenuItemInterface[]>,
355
- },
356
-
357
- /**
358
- * Checked rows array
359
- */
360
- checkedRows: {
361
- default() {
362
- return [];
363
- },
364
- type: Array as PropType<Record<string, any>[]>,
365
- },
366
-
367
- /**
368
- * Check is a given row is checkable
369
- */
370
- isRowCheckable: {
371
- default() {
372
- return () => true;
373
- },
374
- type: Function,
375
- },
376
-
377
- /**
378
- * Adds a search bar
379
- */
380
- searchable: {
381
- default: true,
382
- type: Boolean,
383
- },
384
-
385
- /**
386
- * Shows the column toggle utility
387
- */
388
- toggleable: {
389
- default: true,
390
- type: Boolean,
391
- },
392
-
393
- /**
394
- * Actions
395
- */
396
- actions: {
397
- default: undefined,
398
- type: Array as PropType<MenuItemInterface[]>,
399
- },
400
-
401
- /**
402
- * Save data table state in URL
403
- */
404
- historyMode: {
405
- default: false,
406
- type: Boolean,
407
- },
408
-
409
- /*
410
- * Max height (in px)
411
- */
412
- maxHeight: {
413
- default: undefined,
414
- type: Number,
415
- },
416
-
417
- /**
418
- * Layout type
419
- */
420
- layout: {
421
- default: 'default',
422
- type: String as PropType<'default' | 'compact'>,
423
- },
424
-
425
- sections: {
426
- default: undefined,
427
- type: Array as PropType<DataIteratorSection[]>,
428
- },
429
-
430
- rowActions: {
431
- default: undefined,
432
- type: Array as PropType<RowAction[]>,
433
- },
434
-
435
- numberOfVisibleRowActions: {
436
- default: 2,
437
- type: Number,
438
- },
439
-
440
- /**
441
- * Scroll to top when fetching new data
442
- */
443
- scrollTopOnFetch: {
444
- default: true,
445
- type: Boolean,
446
- },
447
- });
448
-
449
- const emit = defineEmits([
450
- 'cell-click',
451
- 'delete',
452
- 'update:checked-rows',
453
- 'fetch',
454
- ]);
455
-
456
- const dataIterator = ref<null | InstanceType<typeof BaseDataIterator>>(null);
457
-
458
- /*
459
- |--------------------------------------------------------------------------
460
- | Handlers
461
- |--------------------------------------------------------------------------
462
- */
463
-
464
- function onCellClick(payload: CollectionItem) {
465
- if (props.showUrl) {
466
- router.push(props.showUrl(payload));
467
- }
468
- emit('cell-click', payload);
469
- }
470
-
471
- /*
472
- |--------------------------------------------------------------------------
473
- | Gate helpers
474
- |--------------------------------------------------------------------------
475
- */
476
-
477
- const gate = (row: CollectionItem, action: string): boolean => {
478
- if (row.can && Object.prototype.hasOwnProperty.call(row.can, action)) {
479
- return row.can[action];
480
- }
481
- return true;
482
- };
483
-
484
- const canUpdate = (row: CollectionItem): boolean => {
485
- return gate(row, 'update');
486
- };
487
-
488
- const canDelete = (row: CollectionItem): boolean => {
489
- return gate(row, 'delete');
490
- };
491
-
492
- function onDeleteClick(row: CollectionItem) {
493
- dialogs.push({
494
- title: t('sui.delete_record') + '?',
495
- message: t('sui.delete_record_description'),
496
- color: 'danger',
497
- closeOnOutsideClick: true,
498
- confirmText: t('sui.yes_delete'),
499
- onConfirm: () => onDelete(row),
500
- });
501
- }
502
-
503
- const onDelete = (row: CollectionItem) => {
504
- if (!props.deleteUrl) {
505
- return;
506
- }
507
-
508
- http
509
- .delete(props.deleteUrl(row))
510
- .then((response) => {
511
- if (response.data && response.data.message) {
512
- notifications.push({
513
- title: t('sui.success'),
514
- text: response.data.message,
515
- color: 'success',
516
- });
517
- }
518
- emit('delete', row);
519
-
520
- // Refetch even if URL is the same
521
- fetch();
522
- })
523
- .catch((error) => {
524
- notifications.push({
525
- title: t('sui.error'),
526
- text: error.response.data?.message ?? 'Unknown error',
527
- color: 'danger',
528
- });
529
- });
530
- };
531
-
532
- /*
533
- |--------------------------------------------------------------------------
534
- | Toggle columns
535
- |--------------------------------------------------------------------------
536
- */
537
-
538
- const visibleColumns = ref<number[]>([]);
539
-
540
- // Find visible columns in local storage
541
- const VISIBLE_COLUMNS_LOCAL_STORAGE = 'sprintify.visible_columns.';
542
- const VISIBLE_COLUMNS_LOCAL_STORAGE_KEY =
543
- VISIBLE_COLUMNS_LOCAL_STORAGE + window.location.pathname;
544
-
545
- const visibleColumnsFromStorage = JSON.parse(
546
- localStorage.getItem(VISIBLE_COLUMNS_LOCAL_STORAGE_KEY) + ''
547
- ) as number[];
548
-
549
- // If found, set visibleColumns
550
- if (
551
- visibleColumnsFromStorage &&
552
- isArray(visibleColumnsFromStorage) &&
553
- visibleColumnsFromStorage.length > 0
554
- ) {
555
- visibleColumns.value = visibleColumnsFromStorage;
556
- }
557
-
558
- // If nothing is found, set visibleColumns to all columns from table
559
- const unWatchTable = watch(
560
- () => table.value,
561
- () => {
562
- if (
563
- table.value &&
564
- table.value.newColumns.length &&
565
- visibleColumns.value.length == 0
566
- ) {
567
- visibleColumns.value = table.value.newColumns
568
- .filter((c) => c.toggle)
569
- .filter((c) => c.toggleDefault ?? true)
570
- .map((c) => c.newKey);
571
-
572
- unWatchTable();
573
- }
574
- }
575
- );
576
-
577
- /**
578
- * Update local storage when check input update
579
- */
580
- function onUpdateVisibleColumn() {
581
- localStorage.setItem(
582
- VISIBLE_COLUMNS_LOCAL_STORAGE_KEY,
583
- JSON.stringify(visibleColumns.value)
584
- );
585
- }
586
-
587
- /*
588
- |--------------------------------------------------------------------------
589
- | Row Actions
590
- |--------------------------------------------------------------------------
591
- */
592
-
593
- const rowActionsInternal = computed<RowAction[]>(() => {
594
- const actions = cloneDeep(props.rowActions) ?? [];
595
-
596
- if (props.editUrl && props.editButton) {
597
- actions.push({
598
- label: t('sui.edit'),
599
- icon: 'heroicons:cog-6-tooth-solid',
600
- to: (row: CollectionItem) => (props.editUrl ? props.editUrl(row) : ''),
601
- disabled: (row: CollectionItem) => !canUpdate(row),
602
- });
603
- }
604
-
605
- if (props.deleteUrl && props.deleteButton) {
606
- actions.push({
607
- label: t('sui.delete'),
608
- icon: 'heroicons:trash-20-solid',
609
- action: onDeleteClick,
610
- disabled: (row: CollectionItem) => !canDelete(row),
611
- });
612
- }
613
-
614
- return actions;
615
- });
616
-
617
- const visibleRowActions = computed<RowAction[]>(() => {
618
- return rowActionsInternal.value.slice(0, props.numberOfVisibleRowActions);
619
- });
620
-
621
- const showRowActionMenu = computed<boolean>(() => {
622
- return rowActionsInternal.value.length > props.numberOfVisibleRowActions;
623
- });
624
-
625
- function rowActionMenuItems(row: CollectionItem): MenuItemInterface[] {
626
- return rowActionsInternal.value.map((action) => {
627
- return {
628
- label: action.label,
629
- icon: action.icon,
630
- disabled: action.disabled && action.disabled(row),
631
- action: action.action
632
- ? () => {
633
- if (action.action) action.action(row);
634
- }
635
- : undefined,
636
- to: action.to ? action.to(row) : undefined,
637
- };
638
- });
639
- }
640
-
641
- /*
642
- |--------------------------------------------------------------------------
643
- | Checkable
644
- |--------------------------------------------------------------------------
645
- */
646
-
647
- const newCheckedRows = ref<Record<string, any>[]>([]);
648
-
649
- watch(
650
- () => props.checkedRows,
651
- (checkedRows) => {
652
- newCheckedRows.value = checkedRows;
653
- }
654
- );
655
-
656
- function uncheckAll() {
657
- table.value?.uncheckAll();
658
- }
659
-
660
- const sectionsInternal = computed<DataIteratorSection[]>(() => {
661
- const sections = props.sections ?? [];
662
-
663
- if (props.toggleable) {
664
- return [
665
- ...sections,
666
- {
667
- name: 'columns',
668
- icon: 'heroicons:table-cells-20-solid',
669
- title: t('sui.columns'),
670
- closeText: t('sui.apply'),
671
- opened: false,
672
- },
673
- ];
674
- }
675
-
676
- return sections;
677
- });
678
-
679
- function onCheckedRowsUpdate(checkedRows: Record<string, any>[]) {
680
- newCheckedRows.value = checkedRows;
681
- emit('update:checked-rows', checkedRows);
682
- }
683
-
684
- /*
685
- |--------------------------------------------------------------------------
686
- | Scrolling behavior
687
- |--------------------------------------------------------------------------
688
- */
689
-
690
- function onWillScrollTop() {
691
- if (!props.scrollTopOnFetch) {
692
- return;
693
- }
694
-
695
- if (props.maxHeight) {
696
- table.value?.scrollTop();
697
-
698
- const top = dataIterator.value?.$el?.getBoundingClientRect()?.top ?? 0;
699
-
700
- if (top < 0) {
701
- dataIterator.value?.scrollIntoView();
702
- }
703
- }
704
- }
705
-
706
- /*
707
- |--------------------------------------------------------------------------
708
- | On fetch
709
- |--------------------------------------------------------------------------
710
- */
711
-
712
- function onFetch(
713
- payload: null | ResourceCollection | PaginatedCollection | Collection
714
- ) {
715
- emit('fetch', payload);
716
- }
717
-
718
- /*
719
- |--------------------------------------------------------------------------
720
- | Exposed functions
721
- |--------------------------------------------------------------------------
722
- */
723
-
724
- function fetch() {
725
- if (!dataIterator.value) {
726
- return;
727
- }
728
- dataIterator.value.fetch();
729
- }
730
-
731
- function fetchWithoutLoading() {
732
- if (!dataIterator.value) {
733
- return;
734
- }
735
- dataIterator.value.fetchWithoutLoading();
736
- }
737
-
738
- const dataIteratorQuery = computed((): DataTableQuery | null => {
739
- return dataIterator.value?.query ?? null;
740
- });
741
-
742
- defineExpose({
743
- fetch,
744
- fetchWithoutLoading,
745
- query: dataIteratorQuery,
746
- });
747
- </script>
1
+ <template>
2
+ <BaseDataIterator
3
+ ref="dataIterator"
4
+ :url="url"
5
+ :url-query="urlQuery"
6
+ :default-query="defaultQuery"
7
+ :searchable="searchable"
8
+ :actions="actions"
9
+ :history-mode="historyMode"
10
+ :layout="layout"
11
+ :sections="sectionsInternal"
12
+ :scroll-top-on-fetch="maxHeight ? false : scrollTopOnFetch"
13
+ @fetch="onFetch"
14
+ @will-scroll-top="onWillScrollTop"
15
+ >
16
+ <template
17
+ #default="{
18
+ items,
19
+ loading,
20
+ sortField,
21
+ sortDirection,
22
+ onSortChange,
23
+ error,
24
+ firstLoad,
25
+ }"
26
+ >
27
+ <BaseCard
28
+ clipped
29
+ class="w-full overflow-hidden"
30
+ >
31
+ <div v-if="newCheckedRows.length">
32
+ <div
33
+ class="flex items-center justify-between border-b border-slate-200 bg-slate-50 py-2 pl-3 pr-2 text-sm"
34
+ >
35
+ <div>
36
+ <span class="mr-3 text-slate-500">{{
37
+ t('sui.x_rows_selected', {
38
+ count: newCheckedRows.length,
39
+ })
40
+ }}.</span>
41
+ <button
42
+ type="button"
43
+ class="mr-3 inline text-slate-700 underline"
44
+ @click="uncheckAll()"
45
+ >
46
+ {{ t('sui.deselect_all') }}
47
+ </button>
48
+ </div>
49
+ <BaseMenu
50
+ v-if="checkableActions?.length"
51
+ tw-menu="w-52"
52
+ :items="checkableActions"
53
+ >
54
+ <template #button="{ open }">
55
+ <div
56
+ class="flex h-10 w-10 items-center justify-center rounded-full border border-slate-300 bg-white duration-150 hover:bg-slate-50"
57
+ :class="[
58
+ open ? 'ring-2 ring-primary-500 ring-offset-2' : false,
59
+ ]"
60
+ >
61
+ <BaseIcon icon="heroicons-solid:dots-vertical" />
62
+ </div>
63
+ </template>
64
+ </BaseMenu>
65
+ </div>
66
+ </div>
67
+
68
+ <BaseTable
69
+ ref="table"
70
+ :checked-rows="newCheckedRows"
71
+ :data="items"
72
+ :loading="loading"
73
+ :detailed="detailed"
74
+ :has-detailed-visible="hasDetailedVisible"
75
+ :checkable="checkable"
76
+ :is-row-checkable="isRowCheckable"
77
+ checkbox-position="left"
78
+ :sort-field="sortField"
79
+ :sort-direction="sortDirection"
80
+ :max-height="maxHeight"
81
+ :visible-columns="visibleColumns"
82
+ @update:checked-rows="onCheckedRowsUpdate"
83
+ @sort="onSortChange"
84
+ @cell-click="onCellClick"
85
+ >
86
+ <template #default>
87
+ <slot />
88
+
89
+ <BaseTableColumn
90
+ v-slot="{ row }"
91
+ :visible="rowActionsInternal.length"
92
+ :toggle="false"
93
+ :clickable="false"
94
+ custom-key="actions"
95
+ class="overflow-hidden"
96
+ >
97
+ <div class="flex justify-end gap-1 pr-2 text-right">
98
+ <div class="btn-group">
99
+ <template
100
+ v-for="rowAction in visibleRowActions"
101
+ :key="rowAction.icon"
102
+ >
103
+ <BaseDataTableRowAction
104
+ :row="row"
105
+ :row-action="rowAction"
106
+ />
107
+ </template>
108
+ <BaseMenu
109
+ v-if="showRowActionMenu"
110
+ :items="rowActionMenuItems(row)"
111
+ size="sm"
112
+ button-class="btn flex h-8 w-8 p-0 items-center justify-center"
113
+ >
114
+ <template #button>
115
+ <BaseIcon icon="heroicons-solid:dots-vertical" />
116
+ </template>
117
+ </BaseMenu>
118
+ </div>
119
+ </div>
120
+ </BaseTableColumn>
121
+ </template>
122
+
123
+ <template #detail="propsDetail">
124
+ <slot
125
+ name="detail"
126
+ v-bind="propsDetail"
127
+ />
128
+ </template>
129
+
130
+ <template #checkedHeader="propsCheckHeader">
131
+ <slot
132
+ name="checkedHeader"
133
+ v-bind="propsCheckHeader"
134
+ />
135
+ </template>
136
+
137
+ <template #empty>
138
+ <div
139
+ v-if="error"
140
+ class="flex items-center justify-center py-16"
141
+ >
142
+ <div class="flex flex-col items-center justify-center">
143
+ <BaseIcon
144
+ icon="heroicons:x-circle"
145
+ class="h-10 w-10 text-red-600"
146
+ />
147
+ <p class="mt-3 text-center text-sm text-slate-600">
148
+ {{ t('sui.whoops') }}
149
+ </p>
150
+ </div>
151
+ </div>
152
+ <div
153
+ v-else-if="firstLoad"
154
+ class="flex items-center justify-center py-16"
155
+ >
156
+ <div class="flex flex-col items-center">
157
+ <BaseEmptyState class="w-32" />
158
+
159
+ <p class="mt-3 text-center text-sm text-slate-600">
160
+ {{ t('sui.nothing_found') }}
161
+ </p>
162
+ </div>
163
+ </div>
164
+ </template>
165
+ </BaseTable>
166
+ </BaseCard>
167
+ </template>
168
+
169
+ <template
170
+ v-if="$slots.filters"
171
+ #filters="{ query, updateQuery, updateQueryValue }"
172
+ >
173
+ <slot
174
+ name="filters"
175
+ :query="query"
176
+ :update-query="updateQuery"
177
+ :update-query-value="updateQueryValue"
178
+ />
179
+ </template>
180
+
181
+ <template #sidebarTop="sidebarProps">
182
+ <slot
183
+ name="sidebarTop"
184
+ v-bind="sidebarProps"
185
+ />
186
+ </template>
187
+
188
+ <template #sidebarBottom="sidebarProps">
189
+ <slot
190
+ name="sidebarBottom"
191
+ v-bind="sidebarProps"
192
+ />
193
+ </template>
194
+
195
+ <template
196
+ v-if="toggleable"
197
+ #columns
198
+ >
199
+ <BaseDataIteratorSectionColumns
200
+ v-model:visibleColumns="visibleColumns"
201
+ :table="table"
202
+ @update:visible-columns="onUpdateVisibleColumn"
203
+ />
204
+ </template>
205
+
206
+ <template
207
+ v-for="section in sections"
208
+ :key="section.name"
209
+ #[section.name]
210
+ >
211
+ <slot :name="section.name" />
212
+ </template>
213
+ </BaseDataIterator>
214
+ </template>
215
+
216
+ <script lang="ts" setup>
217
+ import { PropType } from 'vue';
218
+ import { t } from '@/i18n';
219
+ import {
220
+ Collection,
221
+ CollectionItem,
222
+ DataIteratorSection,
223
+ DataTableQuery,
224
+ MenuItemInterface,
225
+ PaginatedCollection,
226
+ ResourceCollection,
227
+ RowAction,
228
+ } from '@/types';
229
+ import { useDialogsStore } from '@/stores/dialogs';
230
+ import { useNotificationsStore } from '../stores/notifications';
231
+ import BaseDataIterator from './BaseDataIterator.vue';
232
+ import { cloneDeep, isArray } from 'lodash';
233
+
234
+ import BaseCard from './BaseCard.vue';
235
+ import BaseTable from './BaseTable.vue';
236
+ import BaseTableColumn from './BaseTableColumn.vue';
237
+ import BaseDataIteratorSectionColumns from './BaseDataIteratorSectionColumns.vue';
238
+ import { BaseIcon, config } from '@/index';
239
+ import BaseEmptyState from '../svg/BaseEmptyState.vue';
240
+ import { RouteLocationRaw } from 'vue-router';
241
+ import BaseMenu from './BaseMenu.vue';
242
+ import BaseDataTableRowAction from './BaseDataTableRowAction.vue';
243
+
244
+ const router = useRouter();
245
+
246
+ const http = config.http;
247
+
248
+ const dialogs = useDialogsStore();
249
+ const notifications = useNotificationsStore();
250
+
251
+ const table = ref<null | InstanceType<typeof BaseTable>>(null);
252
+
253
+ const props = defineProps({
254
+ /**
255
+ * Base URL from which to make requests
256
+ */
257
+ url: {
258
+ required: true,
259
+ type: String,
260
+ },
261
+
262
+ /**
263
+ * Query params that always get applied
264
+ */
265
+ urlQuery: {
266
+ default: undefined,
267
+ type: Object as PropType<Record<string, any>>,
268
+ },
269
+
270
+ /**
271
+ * Query params that gets applied by default
272
+ * These may be overwritten by URL params generated by the data-table or filters
273
+ */
274
+ defaultQuery: {
275
+ default: undefined,
276
+ type: Object as PropType<DataTableQuery>,
277
+ },
278
+
279
+ /**
280
+ * Show url for router link
281
+ */
282
+ showUrl: {
283
+ default: undefined,
284
+ type: Function as PropType<
285
+ ((row: CollectionItem) => RouteLocationRaw) | undefined
286
+ >,
287
+ },
288
+
289
+ /**
290
+ * Show/Hide edit button
291
+ */
292
+ editButton: {
293
+ default: true,
294
+ type: Boolean,
295
+ },
296
+
297
+ /**
298
+ * Edit url for router link
299
+ */
300
+ editUrl: {
301
+ default: undefined,
302
+ type: Function as PropType<
303
+ ((row: CollectionItem) => RouteLocationRaw) | undefined
304
+ >,
305
+ },
306
+
307
+ /**
308
+ * Show/Hide delete button
309
+ */
310
+ deleteButton: {
311
+ default: true,
312
+ type: Boolean,
313
+ },
314
+
315
+ /**
316
+ * Delete endpoint to delete an item
317
+ */
318
+ deleteUrl: {
319
+ default: undefined,
320
+ type: Function as PropType<((row: CollectionItem) => string) | undefined>,
321
+ },
322
+
323
+ /**
324
+ * Show toggle-able details on each row
325
+ */
326
+ detailed: {
327
+ default: false,
328
+ type: Boolean,
329
+ },
330
+
331
+ /**
332
+ * Check is a given row has details
333
+ */
334
+ hasDetailedVisible: {
335
+ default() {
336
+ return true;
337
+ },
338
+ type: Function as PropType<(row: any) => boolean>,
339
+ },
340
+
341
+ /**
342
+ * Makes row checkable
343
+ */
344
+ checkable: {
345
+ default: false,
346
+ type: Boolean,
347
+ },
348
+
349
+ /**
350
+ * Actions on each row
351
+ */
352
+ checkableActions: {
353
+ default: undefined,
354
+ type: Array as PropType<MenuItemInterface[]>,
355
+ },
356
+
357
+ /**
358
+ * Checked rows array
359
+ */
360
+ checkedRows: {
361
+ default() {
362
+ return [];
363
+ },
364
+ type: Array as PropType<Record<string, any>[]>,
365
+ },
366
+
367
+ /**
368
+ * Check is a given row is checkable
369
+ */
370
+ isRowCheckable: {
371
+ default() {
372
+ return () => true;
373
+ },
374
+ type: Function,
375
+ },
376
+
377
+ /**
378
+ * Adds a search bar
379
+ */
380
+ searchable: {
381
+ default: true,
382
+ type: Boolean,
383
+ },
384
+
385
+ /**
386
+ * Shows the column toggle utility
387
+ */
388
+ toggleable: {
389
+ default: true,
390
+ type: Boolean,
391
+ },
392
+
393
+ /**
394
+ * Actions
395
+ */
396
+ actions: {
397
+ default: undefined,
398
+ type: Array as PropType<MenuItemInterface[]>,
399
+ },
400
+
401
+ /**
402
+ * Save data table state in URL
403
+ */
404
+ historyMode: {
405
+ default: false,
406
+ type: Boolean,
407
+ },
408
+
409
+ /*
410
+ * Max height (in px)
411
+ */
412
+ maxHeight: {
413
+ default: undefined,
414
+ type: Number,
415
+ },
416
+
417
+ /**
418
+ * Layout type
419
+ */
420
+ layout: {
421
+ default: 'default',
422
+ type: String as PropType<'default' | 'compact'>,
423
+ },
424
+
425
+ sections: {
426
+ default: undefined,
427
+ type: Array as PropType<DataIteratorSection[]>,
428
+ },
429
+
430
+ rowActions: {
431
+ default: undefined,
432
+ type: Array as PropType<RowAction[]>,
433
+ },
434
+
435
+ numberOfVisibleRowActions: {
436
+ default: 2,
437
+ type: Number,
438
+ },
439
+
440
+ /**
441
+ * Scroll to top when fetching new data
442
+ */
443
+ scrollTopOnFetch: {
444
+ default: true,
445
+ type: Boolean,
446
+ },
447
+ });
448
+
449
+ const emit = defineEmits([
450
+ 'cell-click',
451
+ 'delete',
452
+ 'update:checked-rows',
453
+ 'fetch',
454
+ ]);
455
+
456
+ const dataIterator = ref<null | InstanceType<typeof BaseDataIterator>>(null);
457
+
458
+ /*
459
+ |--------------------------------------------------------------------------
460
+ | Handlers
461
+ |--------------------------------------------------------------------------
462
+ */
463
+
464
+ function onCellClick(payload: CollectionItem) {
465
+ if (props.showUrl) {
466
+ router.push(props.showUrl(payload));
467
+ }
468
+ emit('cell-click', payload);
469
+ }
470
+
471
+ /*
472
+ |--------------------------------------------------------------------------
473
+ | Gate helpers
474
+ |--------------------------------------------------------------------------
475
+ */
476
+
477
+ const gate = (row: CollectionItem, action: string): boolean => {
478
+ if (row.can && Object.prototype.hasOwnProperty.call(row.can, action)) {
479
+ return row.can[action];
480
+ }
481
+ return true;
482
+ };
483
+
484
+ const canUpdate = (row: CollectionItem): boolean => {
485
+ return gate(row, 'update');
486
+ };
487
+
488
+ const canDelete = (row: CollectionItem): boolean => {
489
+ return gate(row, 'delete');
490
+ };
491
+
492
+ function onDeleteClick(row: CollectionItem) {
493
+ dialogs.push({
494
+ title: t('sui.delete_record') + '?',
495
+ message: t('sui.delete_record_description'),
496
+ color: 'danger',
497
+ closeOnOutsideClick: true,
498
+ confirmText: t('sui.yes_delete'),
499
+ onConfirm: () => onDelete(row),
500
+ });
501
+ }
502
+
503
+ const onDelete = (row: CollectionItem) => {
504
+ if (!props.deleteUrl) {
505
+ return;
506
+ }
507
+
508
+ http
509
+ .delete(props.deleteUrl(row))
510
+ .then((response) => {
511
+ if (response.data && response.data.message) {
512
+ notifications.push({
513
+ title: t('sui.success'),
514
+ text: response.data.message,
515
+ color: 'success',
516
+ });
517
+ }
518
+ emit('delete', row);
519
+
520
+ // Refetch even if URL is the same
521
+ fetch();
522
+ })
523
+ .catch((error) => {
524
+ notifications.push({
525
+ title: t('sui.error'),
526
+ text: error.response.data?.message ?? 'Unknown error',
527
+ color: 'danger',
528
+ });
529
+ });
530
+ };
531
+
532
+ /*
533
+ |--------------------------------------------------------------------------
534
+ | Toggle columns
535
+ |--------------------------------------------------------------------------
536
+ */
537
+
538
+ const visibleColumns = ref<number[]>([]);
539
+
540
+ // Find visible columns in local storage
541
+ const VISIBLE_COLUMNS_LOCAL_STORAGE = 'sprintify.visible_columns.';
542
+ const VISIBLE_COLUMNS_LOCAL_STORAGE_KEY =
543
+ VISIBLE_COLUMNS_LOCAL_STORAGE + window.location.pathname;
544
+
545
+ const visibleColumnsFromStorage = JSON.parse(
546
+ localStorage.getItem(VISIBLE_COLUMNS_LOCAL_STORAGE_KEY) + ''
547
+ ) as number[];
548
+
549
+ // If found, set visibleColumns
550
+ if (
551
+ visibleColumnsFromStorage &&
552
+ isArray(visibleColumnsFromStorage) &&
553
+ visibleColumnsFromStorage.length > 0
554
+ ) {
555
+ visibleColumns.value = visibleColumnsFromStorage;
556
+ }
557
+
558
+ // If nothing is found, set visibleColumns to all columns from table
559
+ const unWatchTable = watch(
560
+ () => table.value,
561
+ () => {
562
+ if (
563
+ table.value &&
564
+ table.value.newColumns.length &&
565
+ visibleColumns.value.length == 0
566
+ ) {
567
+ visibleColumns.value = table.value.newColumns
568
+ .filter((c) => c.toggle)
569
+ .filter((c) => c.toggleDefault ?? true)
570
+ .map((c) => c.newKey);
571
+
572
+ unWatchTable();
573
+ }
574
+ }
575
+ );
576
+
577
+ /**
578
+ * Update local storage when check input update
579
+ */
580
+ function onUpdateVisibleColumn() {
581
+ localStorage.setItem(
582
+ VISIBLE_COLUMNS_LOCAL_STORAGE_KEY,
583
+ JSON.stringify(visibleColumns.value)
584
+ );
585
+ }
586
+
587
+ /*
588
+ |--------------------------------------------------------------------------
589
+ | Row Actions
590
+ |--------------------------------------------------------------------------
591
+ */
592
+
593
+ const rowActionsInternal = computed<RowAction[]>(() => {
594
+ const actions = cloneDeep(props.rowActions) ?? [];
595
+
596
+ if (props.editUrl && props.editButton) {
597
+ actions.push({
598
+ label: t('sui.edit'),
599
+ icon: 'heroicons:cog-6-tooth-solid',
600
+ to: (row: CollectionItem) => (props.editUrl ? props.editUrl(row) : ''),
601
+ disabled: (row: CollectionItem) => !canUpdate(row),
602
+ });
603
+ }
604
+
605
+ if (props.deleteUrl && props.deleteButton) {
606
+ actions.push({
607
+ label: t('sui.delete'),
608
+ icon: 'heroicons:trash-20-solid',
609
+ action: onDeleteClick,
610
+ disabled: (row: CollectionItem) => !canDelete(row),
611
+ });
612
+ }
613
+
614
+ return actions;
615
+ });
616
+
617
+ const visibleRowActions = computed<RowAction[]>(() => {
618
+ return rowActionsInternal.value.slice(0, props.numberOfVisibleRowActions);
619
+ });
620
+
621
+ const showRowActionMenu = computed<boolean>(() => {
622
+ return rowActionsInternal.value.length > props.numberOfVisibleRowActions;
623
+ });
624
+
625
+ function rowActionMenuItems(row: CollectionItem): MenuItemInterface[] {
626
+ return rowActionsInternal.value.map((action) => {
627
+ return {
628
+ label: action.label,
629
+ icon: action.icon,
630
+ disabled: action.disabled && action.disabled(row),
631
+ action: action.action
632
+ ? () => {
633
+ if (action.action) action.action(row);
634
+ }
635
+ : undefined,
636
+ to: action.to ? action.to(row) : undefined,
637
+ };
638
+ });
639
+ }
640
+
641
+ /*
642
+ |--------------------------------------------------------------------------
643
+ | Checkable
644
+ |--------------------------------------------------------------------------
645
+ */
646
+
647
+ const newCheckedRows = ref<Record<string, any>[]>([]);
648
+
649
+ watch(
650
+ () => props.checkedRows,
651
+ (checkedRows) => {
652
+ newCheckedRows.value = checkedRows;
653
+ }
654
+ );
655
+
656
+ function uncheckAll() {
657
+ table.value?.uncheckAll();
658
+ }
659
+
660
+ const sectionsInternal = computed<DataIteratorSection[]>(() => {
661
+ const sections = props.sections ?? [];
662
+
663
+ if (props.toggleable) {
664
+ return [
665
+ ...sections,
666
+ {
667
+ name: 'columns',
668
+ icon: 'heroicons:table-cells-20-solid',
669
+ title: t('sui.columns'),
670
+ closeText: t('sui.apply'),
671
+ opened: false,
672
+ },
673
+ ];
674
+ }
675
+
676
+ return sections;
677
+ });
678
+
679
+ function onCheckedRowsUpdate(checkedRows: Record<string, any>[]) {
680
+ newCheckedRows.value = checkedRows;
681
+ emit('update:checked-rows', checkedRows);
682
+ }
683
+
684
+ /*
685
+ |--------------------------------------------------------------------------
686
+ | Scrolling behavior
687
+ |--------------------------------------------------------------------------
688
+ */
689
+
690
+ function onWillScrollTop() {
691
+ if (!props.scrollTopOnFetch) {
692
+ return;
693
+ }
694
+
695
+ if (props.maxHeight) {
696
+ table.value?.scrollTop();
697
+
698
+ const top = dataIterator.value?.$el?.getBoundingClientRect()?.top ?? 0;
699
+
700
+ if (top < 0) {
701
+ dataIterator.value?.scrollIntoView();
702
+ }
703
+ }
704
+ }
705
+
706
+ /*
707
+ |--------------------------------------------------------------------------
708
+ | On fetch
709
+ |--------------------------------------------------------------------------
710
+ */
711
+
712
+ function onFetch(
713
+ payload: null | ResourceCollection | PaginatedCollection | Collection
714
+ ) {
715
+ emit('fetch', payload);
716
+ }
717
+
718
+ /*
719
+ |--------------------------------------------------------------------------
720
+ | Exposed functions
721
+ |--------------------------------------------------------------------------
722
+ */
723
+
724
+ function fetch() {
725
+ if (!dataIterator.value) {
726
+ return;
727
+ }
728
+ dataIterator.value.fetch();
729
+ }
730
+
731
+ function fetchWithoutLoading() {
732
+ if (!dataIterator.value) {
733
+ return;
734
+ }
735
+ dataIterator.value.fetchWithoutLoading();
736
+ }
737
+
738
+ const dataIteratorQuery = computed((): DataTableQuery | null => {
739
+ return dataIterator.value?.query ?? null;
740
+ });
741
+
742
+ defineExpose({
743
+ fetch,
744
+ fetchWithoutLoading,
745
+ query: dataIteratorQuery,
746
+ });
747
+ </script>