@lifesg/react-design-system 4.0.0-alpha.6 → 4.0.0-alpha.7

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 (684) hide show
  1. package/accordion/accordion.js.map +1 -1
  2. package/alert/alert.js.map +1 -1
  3. package/alert/types.d.ts +2 -0
  4. package/animations/loading-dots/loading-dots.d.ts +5 -2
  5. package/animations/loading-dots/loading-dots.js.map +1 -1
  6. package/animations/loading-dots-spinner/loading-dots-spinner.d.ts +3 -0
  7. package/animations/loading-dots-spinner/loading-dots-spinner.js.map +1 -1
  8. package/animations/loading-dots-spinner/lottie-animation.d.ts +2 -2
  9. package/animations/loading-dots-spinner/lottie-animation.js.map +1 -1
  10. package/animations/loading-spinner/loading-spinner.d.ts +5 -2
  11. package/animations/loading-spinner/loading-spinner.js.map +1 -1
  12. package/animations/themed-loading-spinner/themed-loading-spinner.d.ts +5 -2
  13. package/animations/themed-loading-spinner/themed-loading-spinner.js.map +1 -1
  14. package/animations/types.d.ts +13 -6
  15. package/avatar/avatar.js.map +1 -1
  16. package/badge/badge.js.map +1 -1
  17. package/badge/types.d.ts +13 -2
  18. package/box-container/box-container.js.map +1 -1
  19. package/box-container/types.d.ts +2 -0
  20. package/breadcrumb/breadcrumb.js.map +1 -1
  21. package/breadcrumb/types.d.ts +7 -2
  22. package/button/button.js.map +1 -1
  23. package/button/types.d.ts +5 -0
  24. package/calendar/calendar.js.map +1 -1
  25. package/calendar/types.d.ts +3 -3
  26. package/card/card.js.map +1 -1
  27. package/checkbox/checkbox.js.map +1 -1
  28. package/checkbox/types.d.ts +4 -0
  29. package/cjs/accordion/accordion.js.map +1 -1
  30. package/cjs/alert/alert.js.map +1 -1
  31. package/cjs/animations/loading-dots/loading-dots.js.map +1 -1
  32. package/cjs/animations/loading-dots-spinner/loading-dots-spinner.js.map +1 -1
  33. package/cjs/animations/loading-dots-spinner/lottie-animation.js.map +1 -1
  34. package/cjs/animations/loading-spinner/loading-spinner.js.map +1 -1
  35. package/cjs/animations/themed-loading-spinner/themed-loading-spinner.js.map +1 -1
  36. package/cjs/avatar/avatar.js.map +1 -1
  37. package/cjs/badge/badge.js.map +1 -1
  38. package/cjs/box-container/box-container.js.map +1 -1
  39. package/cjs/breadcrumb/breadcrumb.js.map +1 -1
  40. package/cjs/button/button.js.map +1 -1
  41. package/cjs/calendar/calendar.js.map +1 -1
  42. package/cjs/card/card.js.map +1 -1
  43. package/cjs/checkbox/checkbox.js.map +1 -1
  44. package/cjs/countdown-timer/countdown-timer.js.map +1 -1
  45. package/cjs/dashed-border/dashed-border.js.map +1 -1
  46. package/cjs/data-table/data-table.js.map +1 -1
  47. package/cjs/date-input/date-input.js.map +1 -1
  48. package/cjs/date-navigator/date-navigator.js.map +1 -1
  49. package/cjs/date-range-input/date-range-input.js.map +1 -1
  50. package/cjs/divider/divider.js.map +1 -1
  51. package/cjs/drawer/drawer.js.map +1 -1
  52. package/cjs/e-signature/e-signature.js.map +1 -1
  53. package/cjs/error-display/error-display.js.map +1 -1
  54. package/cjs/feedback-rating/feedback-rating.js.map +1 -1
  55. package/cjs/file-download/file-download.js.map +1 -1
  56. package/cjs/file-upload/file-item-edit.js.map +1 -1
  57. package/cjs/file-upload/file-list/file-list.js.map +1 -1
  58. package/cjs/file-upload/file-list-item/file-list-item.js.map +1 -1
  59. package/cjs/file-upload/file-list-item/file-list-item.styles.js +1 -1
  60. package/cjs/file-upload/file-list-item/file-list-item.styles.js.map +1 -1
  61. package/cjs/file-upload/file-list-item/{file-list-item.styles_o8000f.css → file-list-item.styles_kgtfke.css} +1 -1
  62. package/cjs/file-upload/file-upload.js.map +1 -1
  63. package/cjs/filter/addons/filter-item-checkbox-helpers.js.map +1 -1
  64. package/cjs/filter/addons/filter-item-checkbox.js.map +1 -1
  65. package/cjs/filter/filter-item.js +1 -1
  66. package/cjs/filter/filter-item.js.map +1 -1
  67. package/cjs/filter/filter.js.map +1 -1
  68. package/cjs/footer/footer.js.map +1 -1
  69. package/cjs/form/form-custom-field/form-custom-field.js +2 -0
  70. package/cjs/form/form-custom-field/form-custom-field.js.map +1 -0
  71. package/cjs/form/form-date-input/form-date-input.js +2 -0
  72. package/cjs/form/form-date-input/form-date-input.js.map +1 -0
  73. package/cjs/form/form-date-range-input/form-date-range-input.js +2 -0
  74. package/cjs/form/form-date-range-input/form-date-range-input.js.map +1 -0
  75. package/cjs/form/form-e-signature/form-e-signature.js +2 -0
  76. package/cjs/form/form-e-signature/form-e-signature.js.map +1 -0
  77. package/cjs/form/form-histogram-slider/form-histogram-slider.js +2 -0
  78. package/cjs/form/form-histogram-slider/form-histogram-slider.js.map +1 -0
  79. package/cjs/form/form-input/form-input.js +2 -0
  80. package/cjs/form/form-input/form-input.js.map +1 -0
  81. package/cjs/form/form-input-group/form-input-group.js +2 -0
  82. package/cjs/form/form-input-group/form-input-group.js.map +1 -0
  83. package/cjs/form/form-label/form-label-addon.js +2 -0
  84. package/cjs/form/form-label/form-label-addon.js.map +1 -0
  85. package/cjs/form/form-label/form-label-addon.styles.js +2 -0
  86. package/cjs/form/form-label/form-label-addon.styles.js.map +1 -0
  87. package/cjs/form/form-label/form-label-addon.styles_aztasj.css +1 -0
  88. package/cjs/form/form-label/form-label.js +2 -0
  89. package/cjs/form/form-label/form-label.js.map +1 -0
  90. package/cjs/form/form-label/form-label.styles.js +2 -0
  91. package/cjs/form/form-label/form-label.styles.js.map +1 -0
  92. package/cjs/form/form-label/form-label.styles_180zf7j.css +6 -0
  93. package/cjs/form/form-masked-input/form-masked-input.js +2 -0
  94. package/cjs/form/form-masked-input/form-masked-input.js.map +1 -0
  95. package/cjs/form/form-multi-select/form-multi-select.js +2 -0
  96. package/cjs/form/form-multi-select/form-multi-select.js.map +1 -0
  97. package/cjs/form/form-nested-multi-select/form-nested-multi-select.js +2 -0
  98. package/cjs/form/form-nested-multi-select/form-nested-multi-select.js.map +1 -0
  99. package/cjs/form/form-nested-select/form-nested-select.js +2 -0
  100. package/cjs/form/form-nested-select/form-nested-select.js.map +1 -0
  101. package/cjs/form/form-otp-verification/form-otp-verification.js +2 -0
  102. package/cjs/form/form-otp-verification/form-otp-verification.js.map +1 -0
  103. package/cjs/form/form-phone-number-input/form-phone-number-input.js +2 -0
  104. package/cjs/form/form-phone-number-input/form-phone-number-input.js.map +1 -0
  105. package/cjs/form/form-predictive-text-input/form-predictive-text-input.js +2 -0
  106. package/cjs/form/form-predictive-text-input/form-predictive-text-input.js.map +1 -0
  107. package/cjs/form/form-range-select/form-range-select.js +2 -0
  108. package/cjs/form/form-range-select/form-range-select.js.map +1 -0
  109. package/cjs/form/form-range-slider/form-range-slider.js +2 -0
  110. package/cjs/form/form-range-slider/form-range-slider.js.map +1 -0
  111. package/cjs/form/form-select/form-select.js +2 -0
  112. package/cjs/form/form-select/form-select.js.map +1 -0
  113. package/cjs/form/form-select-histogram/form-select-histogram.js +2 -0
  114. package/cjs/form/form-select-histogram/form-select-histogram.js.map +1 -0
  115. package/cjs/form/form-slider/form-slider.js +2 -0
  116. package/cjs/form/form-slider/form-slider.js.map +1 -0
  117. package/cjs/form/form-textarea/form-textarea.js +2 -0
  118. package/cjs/form/form-textarea/form-textarea.js.map +1 -0
  119. package/cjs/form/form-textarea/form-textarea.styles.js +2 -0
  120. package/cjs/form/form-textarea/form-textarea.styles.js.map +1 -0
  121. package/cjs/form/form-textarea/form-textarea.styles_1kneyif.css +3 -0
  122. package/cjs/form/form-time-range-picker/form-time-range-picker.js +2 -0
  123. package/cjs/form/form-time-range-picker/form-time-range-picker.js.map +1 -0
  124. package/cjs/form/form-timepicker/form-timepicker.js +2 -0
  125. package/cjs/form/form-timepicker/form-timepicker.js.map +1 -0
  126. package/cjs/form/form-unit-number-input/form-unit-number-input.js +2 -0
  127. package/cjs/form/form-unit-number-input/form-unit-number-input.js.map +1 -0
  128. package/cjs/form/form-wrapper.js +1 -1
  129. package/cjs/form/form-wrapper.js.map +1 -1
  130. package/cjs/form/index.js +1 -1
  131. package/cjs/form/index.js.map +1 -1
  132. package/cjs/fullscreen-image-carousel/fullscreen-image-carousel.js.map +1 -1
  133. package/cjs/histogram-slider/histogram-slider.js.map +1 -1
  134. package/cjs/image-button/image-button.js.map +1 -1
  135. package/cjs/input/input.js.map +1 -1
  136. package/cjs/input-group/input-group.js.map +1 -1
  137. package/cjs/input-multi-select/input-multi-select.js.map +1 -1
  138. package/cjs/input-nested-multi-select/input-nested-multi-select.js.map +1 -1
  139. package/cjs/input-nested-select/input-nested-select.js.map +1 -1
  140. package/cjs/input-range-select/input-range-select.js.map +1 -1
  141. package/cjs/input-range-slider/input-range-slider.js.map +1 -1
  142. package/cjs/input-select/input-select.js.map +1 -1
  143. package/cjs/input-slider/input-slider.js.map +1 -1
  144. package/cjs/input-textarea/textarea.js.map +1 -1
  145. package/cjs/input-textarea/textarea.styles.js +1 -1
  146. package/cjs/input-textarea/textarea.styles.js.map +1 -1
  147. package/cjs/input-textarea/{textarea.styles_22z4n3.css → textarea.styles_q77m5x.css} +1 -1
  148. package/cjs/language-switcher/language-switcher.js.map +1 -1
  149. package/cjs/layout/index.js.map +1 -1
  150. package/cjs/link-list/components/common.js.map +1 -1
  151. package/cjs/link-list/components/link-list-eager.js.map +1 -1
  152. package/cjs/link-list/components/link-list-lazy.js.map +1 -1
  153. package/cjs/link-list/link-list.js.map +1 -1
  154. package/cjs/local-nav/local-nav-dropdown/local-nav-dropdown.js.map +1 -1
  155. package/cjs/local-nav/local-nav-menu/local-nav-menu.js.map +1 -1
  156. package/cjs/markup/markup.js.map +1 -1
  157. package/cjs/masked-input/masked-input.js.map +1 -1
  158. package/cjs/masthead/masthead.js.map +1 -1
  159. package/cjs/menu/menu.js.map +1 -1
  160. package/cjs/modal/index.js.map +1 -1
  161. package/cjs/modal-v2/modal-v2.js.map +1 -1
  162. package/cjs/navbar/navbar.js.map +1 -1
  163. package/cjs/notification-banner/notification-banner.js.map +1 -1
  164. package/cjs/otp-input/otp-input.js +1 -1
  165. package/cjs/otp-input/otp-input.js.map +1 -1
  166. package/cjs/otp-verification/contact-input-section.js +1 -1
  167. package/cjs/otp-verification/contact-input-section.js.map +1 -1
  168. package/cjs/otp-verification/otp-verification.js.map +1 -1
  169. package/cjs/otp-verification/verification-section.js +1 -1
  170. package/cjs/otp-verification/verification-section.js.map +1 -1
  171. package/cjs/overlay/overlay.js.map +1 -1
  172. package/cjs/pagination/pagination.js.map +1 -1
  173. package/cjs/phone-number-input/phone-number-input.js.map +1 -1
  174. package/cjs/pill/pill.js.map +1 -1
  175. package/cjs/popover/popover-inline/popover-inline.js.map +1 -1
  176. package/cjs/popover/popover.js.map +1 -1
  177. package/cjs/predictive-text-input/predictive-text-input.js +1 -1
  178. package/cjs/predictive-text-input/predictive-text-input.js.map +1 -1
  179. package/cjs/progress-indicator/progress-indicator.js.map +1 -1
  180. package/cjs/radio-button/radio-button.js.map +1 -1
  181. package/cjs/schedule/schedule.js.map +1 -1
  182. package/cjs/select-histogram/select-histogram.js.map +1 -1
  183. package/cjs/shared/dropdown-list/dropdown-list.js +1 -1
  184. package/cjs/shared/dropdown-list/dropdown-list.js.map +1 -1
  185. package/cjs/shared/dropdown-wrapper/element-with-dropdown.js +1 -1
  186. package/cjs/shared/dropdown-wrapper/element-with-dropdown.js.map +1 -1
  187. package/cjs/sidenav/sidenav.js.map +1 -1
  188. package/cjs/singpass-button/singpass-button.js.map +1 -1
  189. package/cjs/smart-app-banner/smart-app-banner.js.map +1 -1
  190. package/cjs/tab/tab.js.map +1 -1
  191. package/cjs/table/table.js.map +1 -1
  192. package/cjs/tag/tag.js.map +1 -1
  193. package/cjs/text-list/index.js.map +1 -1
  194. package/cjs/theme/theme-provider/hooks.js.map +1 -1
  195. package/cjs/theme/theme-provider/index.js.map +1 -1
  196. package/cjs/theme/tokens/border.js.map +1 -1
  197. package/cjs/theme/tokens/breakpoint.js.map +1 -1
  198. package/cjs/theme/tokens/colour.js.map +1 -1
  199. package/cjs/theme/tokens/component.js.map +1 -1
  200. package/cjs/theme/tokens/font.js.map +1 -1
  201. package/cjs/theme/tokens/media-query.js.map +1 -1
  202. package/cjs/theme/tokens/motion.js.map +1 -1
  203. package/cjs/theme/tokens/radius.js.map +1 -1
  204. package/cjs/theme/tokens/shadow.js.map +1 -1
  205. package/cjs/theme/tokens/spacing.js.map +1 -1
  206. package/cjs/theme/utils/use-apply-styles.js.map +1 -1
  207. package/cjs/theme/utils/use-design-token.js.map +1 -1
  208. package/cjs/theme/utils/use-media-query.js.map +1 -1
  209. package/cjs/time-range-picker/combobox-picker/combobox-picker.js +1 -1
  210. package/cjs/time-range-picker/combobox-picker/combobox-picker.js.map +1 -1
  211. package/cjs/time-range-picker/time-range-picker.js.map +1 -1
  212. package/cjs/time-slot-bar/time-slot-bar.js.map +1 -1
  213. package/cjs/time-slot-bar-week/time-slot-bar-week.js.map +1 -1
  214. package/cjs/time-slot-week-view/time-slot-week-view.js.map +1 -1
  215. package/cjs/timeline/timeline.js.map +1 -1
  216. package/cjs/timepicker/timepicker.js.map +1 -1
  217. package/cjs/timetable/timetable.js.map +1 -1
  218. package/cjs/toast/toast.js.map +1 -1
  219. package/cjs/toggle/toggle.js.map +1 -1
  220. package/cjs/typography/index.js.map +1 -1
  221. package/cjs/uneditable-section/index.js.map +1 -1
  222. package/cjs/uneditable-section/section-item.js +1 -1
  223. package/cjs/uneditable-section/section-item.js.map +1 -1
  224. package/cjs/unit-number/unit-number-input.js.map +1 -1
  225. package/countdown-timer/countdown-timer.js.map +1 -1
  226. package/countdown-timer/types.d.ts +3 -3
  227. package/dashed-border/dashed-border.js.map +1 -1
  228. package/data-table/data-table.js.map +1 -1
  229. package/date-input/date-input.js.map +1 -1
  230. package/date-input/types.d.ts +1 -1
  231. package/date-navigator/date-navigator.js.map +1 -1
  232. package/date-navigator/types.d.ts +1 -1
  233. package/date-range-input/date-range-input.js.map +1 -1
  234. package/date-range-input/types.d.ts +1 -1
  235. package/divider/divider.js.map +1 -1
  236. package/divider/types.d.ts +1 -1
  237. package/docs/component-catalog.json +644 -0
  238. package/drawer/drawer.js.map +1 -1
  239. package/e-signature/e-signature.js.map +1 -1
  240. package/error-display/error-display.js.map +1 -1
  241. package/feedback-rating/feedback-rating.js.map +1 -1
  242. package/file-download/file-download.js.map +1 -1
  243. package/file-download/types.d.ts +6 -1
  244. package/file-upload/file-item-edit.d.ts +1 -1
  245. package/file-upload/file-item-edit.js.map +1 -1
  246. package/file-upload/file-list/file-list.d.ts +1 -1
  247. package/file-upload/file-list/file-list.js.map +1 -1
  248. package/file-upload/file-list-item/file-list-item.d.ts +1 -1
  249. package/file-upload/file-list-item/file-list-item.js.map +1 -1
  250. package/file-upload/file-list-item/file-list-item.styles.js +1 -1
  251. package/file-upload/file-list-item/file-list-item.styles.js.map +1 -1
  252. package/file-upload/file-list-item/{file-list-item.styles_o8000f.css → file-list-item.styles_kgtfke.css} +1 -1
  253. package/file-upload/file-upload.js.map +1 -1
  254. package/file-upload/types.d.ts +6 -2
  255. package/filter/addons/filter-item-checkbox-helpers.d.ts +2 -2
  256. package/filter/addons/filter-item-checkbox-helpers.js.map +1 -1
  257. package/filter/addons/filter-item-checkbox.d.ts +1 -1
  258. package/filter/addons/filter-item-checkbox.js.map +1 -1
  259. package/filter/addons/internal-types.d.ts +12 -0
  260. package/filter/addons/types.d.ts +60 -9
  261. package/filter/filter-item.js +1 -1
  262. package/filter/filter-item.js.map +1 -1
  263. package/filter/filter.d.ts +1 -1
  264. package/filter/filter.js.map +1 -1
  265. package/filter/index.d.ts +1 -0
  266. package/filter/types.d.ts +31 -63
  267. package/footer/footer.js.map +1 -1
  268. package/form/form-custom-field/form-custom-field.js +2 -0
  269. package/form/form-custom-field/form-custom-field.js.map +1 -0
  270. package/form/form-custom-field/index.d.ts +2 -0
  271. package/form/form-custom-field/types.d.ts +7 -0
  272. package/form/form-date-input/form-date-input.js +2 -0
  273. package/form/form-date-input/form-date-input.js.map +1 -0
  274. package/form/form-date-input/index.d.ts +2 -0
  275. package/form/form-date-input/types.d.ts +8 -0
  276. package/form/form-date-range-input/form-date-range-input.js +2 -0
  277. package/form/form-date-range-input/form-date-range-input.js.map +1 -0
  278. package/form/form-date-range-input/index.d.ts +2 -0
  279. package/form/form-date-range-input/types.d.ts +8 -0
  280. package/form/form-e-signature/form-e-signature.js +2 -0
  281. package/form/form-e-signature/form-e-signature.js.map +1 -0
  282. package/form/form-e-signature/index.d.ts +2 -0
  283. package/form/form-e-signature/types.d.ts +8 -0
  284. package/form/form-histogram-slider/form-histogram-slider.js +2 -0
  285. package/form/form-histogram-slider/form-histogram-slider.js.map +1 -0
  286. package/form/form-histogram-slider/index.d.ts +2 -0
  287. package/form/form-histogram-slider/types.d.ts +8 -0
  288. package/form/form-input/form-input.js +2 -0
  289. package/form/form-input/form-input.js.map +1 -0
  290. package/form/form-input/index.d.ts +2 -0
  291. package/form/form-input/types.d.ts +8 -0
  292. package/form/form-input-group/form-input-group.js +2 -0
  293. package/form/form-input-group/form-input-group.js.map +1 -0
  294. package/form/form-input-group/index.d.ts +2 -0
  295. package/form/form-input-group/types.d.ts +10 -0
  296. package/form/form-label/form-label-addon.js +2 -0
  297. package/form/form-label/form-label-addon.js.map +1 -0
  298. package/form/form-label/form-label-addon.styles.js +2 -0
  299. package/form/form-label/form-label-addon.styles.js.map +1 -0
  300. package/form/form-label/form-label-addon.styles_aztasj.css +1 -0
  301. package/form/form-label/form-label.js +2 -0
  302. package/form/form-label/form-label.js.map +1 -0
  303. package/form/form-label/form-label.styles.js +2 -0
  304. package/form/form-label/form-label.styles.js.map +1 -0
  305. package/form/form-label/form-label.styles_180zf7j.css +6 -0
  306. package/form/form-label/index.d.ts +2 -0
  307. package/form/form-label/types.d.ts +39 -0
  308. package/form/form-masked-input/form-masked-input.js +2 -0
  309. package/form/form-masked-input/form-masked-input.js.map +1 -0
  310. package/form/form-masked-input/index.d.ts +2 -0
  311. package/form/form-masked-input/types.d.ts +8 -0
  312. package/form/form-multi-select/form-multi-select.js +2 -0
  313. package/form/form-multi-select/form-multi-select.js.map +1 -0
  314. package/form/form-multi-select/index.d.ts +2 -0
  315. package/form/form-multi-select/types.d.ts +10 -0
  316. package/form/form-nested-multi-select/form-nested-multi-select.js +2 -0
  317. package/form/form-nested-multi-select/form-nested-multi-select.js.map +1 -0
  318. package/form/form-nested-multi-select/index.d.ts +2 -0
  319. package/form/form-nested-multi-select/types.d.ts +11 -0
  320. package/form/form-nested-select/form-nested-select.js +2 -0
  321. package/form/form-nested-select/form-nested-select.js.map +1 -0
  322. package/form/form-nested-select/index.d.ts +2 -0
  323. package/form/form-nested-select/types.d.ts +11 -0
  324. package/form/{form-otp-verification.d.ts → form-otp-verification/form-otp-verification.d.ts} +1 -1
  325. package/form/form-otp-verification/form-otp-verification.js +2 -0
  326. package/form/form-otp-verification/form-otp-verification.js.map +1 -0
  327. package/form/form-otp-verification/index.d.ts +2 -0
  328. package/form/form-otp-verification/types.d.ts +1 -0
  329. package/form/form-phone-number-input/form-phone-number-input.js +2 -0
  330. package/form/form-phone-number-input/form-phone-number-input.js.map +1 -0
  331. package/form/form-phone-number-input/index.d.ts +2 -0
  332. package/form/form-phone-number-input/types.d.ts +8 -0
  333. package/form/form-predictive-text-input/form-predictive-text-input.js +2 -0
  334. package/form/form-predictive-text-input/form-predictive-text-input.js.map +1 -0
  335. package/form/form-predictive-text-input/index.d.ts +2 -0
  336. package/form/form-predictive-text-input/types.d.ts +10 -0
  337. package/form/form-range-select/form-range-select.js +2 -0
  338. package/form/form-range-select/form-range-select.js.map +1 -0
  339. package/form/form-range-select/index.d.ts +2 -0
  340. package/form/form-range-select/types.d.ts +10 -0
  341. package/form/form-range-slider/form-range-slider.js +2 -0
  342. package/form/form-range-slider/form-range-slider.js.map +1 -0
  343. package/form/form-range-slider/index.d.ts +2 -0
  344. package/form/form-range-slider/types.d.ts +8 -0
  345. package/form/form-select/form-select.js +2 -0
  346. package/form/form-select/form-select.js.map +1 -0
  347. package/form/form-select/index.d.ts +2 -0
  348. package/form/form-select/types.d.ts +10 -0
  349. package/form/form-select-histogram/form-select-histogram.js +2 -0
  350. package/form/form-select-histogram/form-select-histogram.js.map +1 -0
  351. package/form/form-select-histogram/index.d.ts +2 -0
  352. package/form/form-select-histogram/types.d.ts +8 -0
  353. package/form/form-slider/form-slider.js +2 -0
  354. package/form/form-slider/form-slider.js.map +1 -0
  355. package/form/form-slider/index.d.ts +2 -0
  356. package/form/form-slider/types.d.ts +8 -0
  357. package/form/form-textarea/form-textarea.js +2 -0
  358. package/form/form-textarea/form-textarea.js.map +1 -0
  359. package/form/form-textarea/form-textarea.styles.js +2 -0
  360. package/form/form-textarea/form-textarea.styles.js.map +1 -0
  361. package/form/form-textarea/form-textarea.styles_1kneyif.css +3 -0
  362. package/form/form-textarea/index.d.ts +2 -0
  363. package/form/form-textarea/types.d.ts +8 -0
  364. package/form/form-time-range-picker/form-time-range-picker.js +2 -0
  365. package/form/form-time-range-picker/form-time-range-picker.js.map +1 -0
  366. package/form/form-time-range-picker/index.d.ts +2 -0
  367. package/form/form-time-range-picker/types.d.ts +8 -0
  368. package/form/form-timepicker/form-timepicker.js +2 -0
  369. package/form/form-timepicker/form-timepicker.js.map +1 -0
  370. package/form/form-timepicker/index.d.ts +2 -0
  371. package/form/form-timepicker/types.d.ts +8 -0
  372. package/form/form-unit-number-input/form-unit-number-input.js +2 -0
  373. package/form/form-unit-number-input/form-unit-number-input.js.map +1 -0
  374. package/form/form-unit-number-input/index.d.ts +2 -0
  375. package/form/form-unit-number-input/types.d.ts +8 -0
  376. package/form/form-wrapper.js +1 -1
  377. package/form/form-wrapper.js.map +1 -1
  378. package/form/index.d.ts +47 -24
  379. package/form/index.js +1 -1
  380. package/form/index.js.map +1 -1
  381. package/form/types.d.ts +1 -208
  382. package/fullscreen-image-carousel/fullscreen-image-carousel.js.map +1 -1
  383. package/histogram-slider/histogram-slider.js.map +1 -1
  384. package/image-button/image-button.js.map +1 -1
  385. package/input/input.js.map +1 -1
  386. package/input-group/input-group.js.map +1 -1
  387. package/input-group/types.d.ts +1 -1
  388. package/input-multi-select/input-multi-select.js.map +1 -1
  389. package/input-multi-select/types.d.ts +1 -1
  390. package/input-nested-multi-select/input-nested-multi-select.js.map +1 -1
  391. package/input-nested-select/input-nested-select.js.map +1 -1
  392. package/input-nested-select/types.d.ts +1 -1
  393. package/input-range-select/input-range-select.js.map +1 -1
  394. package/input-range-select/types.d.ts +1 -1
  395. package/input-range-slider/input-range-slider.js.map +1 -1
  396. package/input-select/input-select.js.map +1 -1
  397. package/input-select/types.d.ts +1 -1
  398. package/input-slider/input-slider.js.map +1 -1
  399. package/input-slider/types.d.ts +1 -1
  400. package/input-textarea/textarea.js.map +1 -1
  401. package/input-textarea/textarea.styles.js +1 -1
  402. package/input-textarea/textarea.styles.js.map +1 -1
  403. package/input-textarea/{textarea.styles_22z4n3.css → textarea.styles_q77m5x.css} +1 -1
  404. package/language-switcher/language-switcher.js.map +1 -1
  405. package/layout/index.js.map +1 -1
  406. package/link-list/components/common.d.ts +1 -1
  407. package/link-list/components/common.js.map +1 -1
  408. package/link-list/components/link-list-eager.d.ts +2 -2
  409. package/link-list/components/link-list-eager.js.map +1 -1
  410. package/link-list/components/link-list-lazy.d.ts +2 -2
  411. package/link-list/components/link-list-lazy.js.map +1 -1
  412. package/link-list/link-list.js.map +1 -1
  413. package/link-list/types.d.ts +89 -3
  414. package/local-nav/local-nav-dropdown/local-nav-dropdown.js.map +1 -1
  415. package/local-nav/local-nav-menu/local-nav-menu.js.map +1 -1
  416. package/markup/markup.js.map +1 -1
  417. package/masked-input/masked-input.js.map +1 -1
  418. package/masthead/masthead.js.map +1 -1
  419. package/menu/menu.js.map +1 -1
  420. package/menu/types.d.ts +17 -1
  421. package/modal/index.js.map +1 -1
  422. package/modal/types.d.ts +3 -1
  423. package/modal-v2/modal-v2.js.map +1 -1
  424. package/modal-v2/types.d.ts +17 -0
  425. package/navbar/navbar.js.map +1 -1
  426. package/navbar/types.d.ts +1 -0
  427. package/notification-banner/notification-banner.js.map +1 -1
  428. package/otp-input/otp-input.js +1 -1
  429. package/otp-input/otp-input.js.map +1 -1
  430. package/otp-input/types.d.ts +14 -9
  431. package/otp-verification/contact-input-section.js +1 -1
  432. package/otp-verification/contact-input-section.js.map +1 -1
  433. package/otp-verification/otp-verification.js.map +1 -1
  434. package/otp-verification/verification-section.js +1 -1
  435. package/otp-verification/verification-section.js.map +1 -1
  436. package/overlay/overlay.js.map +1 -1
  437. package/package.json +1 -1
  438. package/pagination/pagination.js.map +1 -1
  439. package/phone-number-input/phone-number-input.js.map +1 -1
  440. package/pill/pill.js.map +1 -1
  441. package/popover/popover-inline/index.d.ts +1 -0
  442. package/popover/popover-inline/popover-inline.d.ts +1 -1
  443. package/popover/popover-inline/popover-inline.js.map +1 -1
  444. package/popover/popover-inline/types.d.ts +36 -0
  445. package/popover/popover.js.map +1 -1
  446. package/popover/types.d.ts +2 -35
  447. package/predictive-text-input/predictive-text-input.js +1 -1
  448. package/predictive-text-input/predictive-text-input.js.map +1 -1
  449. package/predictive-text-input/types.d.ts +1 -1
  450. package/progress-indicator/progress-indicator.js.map +1 -1
  451. package/radio-button/radio-button.js.map +1 -1
  452. package/radio-button/types.d.ts +3 -0
  453. package/schedule/schedule.js.map +1 -1
  454. package/select-histogram/select-histogram.js.map +1 -1
  455. package/select-histogram/types.d.ts +1 -1
  456. package/shared/dropdown-list/dropdown-list.js +1 -1
  457. package/shared/dropdown-list/dropdown-list.js.map +1 -1
  458. package/shared/dropdown-wrapper/element-with-dropdown.d.ts +5 -4
  459. package/shared/dropdown-wrapper/element-with-dropdown.js +1 -1
  460. package/shared/dropdown-wrapper/element-with-dropdown.js.map +1 -1
  461. package/sidenav/sidenav.js.map +1 -1
  462. package/sidenav/types.d.ts +1 -0
  463. package/singpass-button/singpass-button.js.map +1 -1
  464. package/smart-app-banner/smart-app-banner.js.map +1 -1
  465. package/smart-app-banner/types.d.ts +2 -0
  466. package/tab/tab.js.map +1 -1
  467. package/table/table.d.ts +9 -8
  468. package/table/table.js.map +1 -1
  469. package/table/types.d.ts +35 -0
  470. package/tag/tag.js.map +1 -1
  471. package/text-list/index.js.map +1 -1
  472. package/theme/theme-provider/hooks.js.map +1 -1
  473. package/theme/theme-provider/index.js.map +1 -1
  474. package/theme/tokens/border.d.ts +9 -3
  475. package/theme/tokens/border.js.map +1 -1
  476. package/theme/tokens/breakpoint.js.map +1 -1
  477. package/theme/tokens/colour.d.ts +9 -3
  478. package/theme/tokens/colour.js.map +1 -1
  479. package/theme/tokens/component.d.ts +3 -1
  480. package/theme/tokens/component.js.map +1 -1
  481. package/theme/tokens/font.d.ts +6 -2
  482. package/theme/tokens/font.js.map +1 -1
  483. package/theme/tokens/media-query.d.ts +3 -1
  484. package/theme/tokens/media-query.js.map +1 -1
  485. package/theme/tokens/motion.d.ts +3 -1
  486. package/theme/tokens/motion.js.map +1 -1
  487. package/theme/tokens/radius.d.ts +3 -1
  488. package/theme/tokens/radius.js.map +1 -1
  489. package/theme/tokens/shadow.d.ts +3 -1
  490. package/theme/tokens/shadow.js.map +1 -1
  491. package/theme/tokens/spacing.d.ts +3 -1
  492. package/theme/tokens/spacing.js.map +1 -1
  493. package/theme/utils/use-apply-styles.js.map +1 -1
  494. package/theme/utils/use-design-token.js.map +1 -1
  495. package/theme/utils/use-media-query.js.map +1 -1
  496. package/time-range-picker/combobox-picker/combobox-picker.js +1 -1
  497. package/time-range-picker/combobox-picker/combobox-picker.js.map +1 -1
  498. package/time-range-picker/time-range-picker.js.map +1 -1
  499. package/time-range-picker/types.d.ts +1 -1
  500. package/time-slot-bar/time-slot-bar.js.map +1 -1
  501. package/time-slot-bar/types.d.ts +5 -1
  502. package/time-slot-bar-week/time-slot-bar-week.js.map +1 -1
  503. package/time-slot-bar-week/types.d.ts +6 -0
  504. package/time-slot-week-view/time-slot-week-view.js.map +1 -1
  505. package/time-slot-week-view/types.d.ts +2 -0
  506. package/timeline/timeline.js.map +1 -1
  507. package/timeline/types.d.ts +1 -1
  508. package/timepicker/timepicker.js.map +1 -1
  509. package/timepicker/types.d.ts +2 -2
  510. package/timetable/timetable.js.map +1 -1
  511. package/toast/toast.js.map +1 -1
  512. package/toast/types.d.ts +2 -0
  513. package/toggle/toggle.js.map +1 -1
  514. package/tools/shared/generated-file-formatter.d.ts +6 -0
  515. package/tools/shared/jsdoc-parser.d.ts +36 -0
  516. package/tools/shared/ts-morph-project-factory.d.ts +9 -0
  517. package/tools/shared/typescript-source-provider.d.ts +9 -0
  518. package/tools/storybook-argtypes/adapters/file-system-adapter.d.ts +69 -0
  519. package/tools/storybook-argtypes/arg-types-generator.d.ts +85 -0
  520. package/tools/storybook-argtypes/config/arg-types-config.d.ts +31 -0
  521. package/tools/storybook-argtypes/index.d.ts +11 -0
  522. package/tools/storybook-argtypes/services/arg-types-row-builder.d.ts +43 -0
  523. package/tools/storybook-argtypes/services/file-path-resolver.d.ts +118 -0
  524. package/tools/storybook-argtypes/services/index.d.ts +6 -0
  525. package/tools/storybook-argtypes/services/jsdoc-metadata-extractor.d.ts +33 -0
  526. package/tools/storybook-argtypes/services/story-registry-generator.d.ts +27 -0
  527. package/tools/storybook-argtypes/services/type-dependency-resolver.d.ts +46 -0
  528. package/tools/storybook-argtypes/services/type-formatting-service.d.ts +27 -0
  529. package/tools/storybook-argtypes/types.d.ts +102 -0
  530. package/typography/index.js.map +1 -1
  531. package/uneditable-section/index.js.map +1 -1
  532. package/uneditable-section/section-item.js +1 -1
  533. package/uneditable-section/section-item.js.map +1 -1
  534. package/uneditable-section/types.d.ts +2 -2
  535. package/unit-number/unit-number-input.js.map +1 -1
  536. package/cjs/form/form-custom-field.js +0 -2
  537. package/cjs/form/form-custom-field.js.map +0 -1
  538. package/cjs/form/form-date-input.js +0 -2
  539. package/cjs/form/form-date-input.js.map +0 -1
  540. package/cjs/form/form-date-range-input.js +0 -2
  541. package/cjs/form/form-date-range-input.js.map +0 -1
  542. package/cjs/form/form-e-signature.js +0 -2
  543. package/cjs/form/form-e-signature.js.map +0 -1
  544. package/cjs/form/form-histogram.js +0 -2
  545. package/cjs/form/form-histogram.js.map +0 -1
  546. package/cjs/form/form-input-group.js +0 -2
  547. package/cjs/form/form-input-group.js.map +0 -1
  548. package/cjs/form/form-input.js +0 -2
  549. package/cjs/form/form-input.js.map +0 -1
  550. package/cjs/form/form-label-addon.js +0 -2
  551. package/cjs/form/form-label-addon.js.map +0 -1
  552. package/cjs/form/form-label-addon.styles.js +0 -2
  553. package/cjs/form/form-label-addon.styles.js.map +0 -1
  554. package/cjs/form/form-label-addon.styles_b00z8p.css +0 -1
  555. package/cjs/form/form-label.js +0 -2
  556. package/cjs/form/form-label.js.map +0 -1
  557. package/cjs/form/form-label.styles.js +0 -2
  558. package/cjs/form/form-label.styles.js.map +0 -1
  559. package/cjs/form/form-label.styles_1nbe0bm.css +0 -6
  560. package/cjs/form/form-masked-input.js +0 -2
  561. package/cjs/form/form-masked-input.js.map +0 -1
  562. package/cjs/form/form-multi-select.js +0 -2
  563. package/cjs/form/form-multi-select.js.map +0 -1
  564. package/cjs/form/form-nested-multi-select.js +0 -2
  565. package/cjs/form/form-nested-multi-select.js.map +0 -1
  566. package/cjs/form/form-nested-select.js +0 -2
  567. package/cjs/form/form-nested-select.js.map +0 -1
  568. package/cjs/form/form-otp-verification.js +0 -2
  569. package/cjs/form/form-otp-verification.js.map +0 -1
  570. package/cjs/form/form-phone-number-input.js +0 -2
  571. package/cjs/form/form-phone-number-input.js.map +0 -1
  572. package/cjs/form/form-predictive-text-input.js +0 -2
  573. package/cjs/form/form-predictive-text-input.js.map +0 -1
  574. package/cjs/form/form-range-select.js +0 -2
  575. package/cjs/form/form-range-select.js.map +0 -1
  576. package/cjs/form/form-range-slider.js +0 -2
  577. package/cjs/form/form-range-slider.js.map +0 -1
  578. package/cjs/form/form-select-histogram.js +0 -2
  579. package/cjs/form/form-select-histogram.js.map +0 -1
  580. package/cjs/form/form-select.js +0 -2
  581. package/cjs/form/form-select.js.map +0 -1
  582. package/cjs/form/form-slider.js +0 -2
  583. package/cjs/form/form-slider.js.map +0 -1
  584. package/cjs/form/form-textarea.js +0 -2
  585. package/cjs/form/form-textarea.js.map +0 -1
  586. package/cjs/form/form-textarea.styles.js +0 -2
  587. package/cjs/form/form-textarea.styles.js.map +0 -1
  588. package/cjs/form/form-textarea.styles_3p9qoy.css +0 -3
  589. package/cjs/form/form-time-range-picker.js +0 -2
  590. package/cjs/form/form-time-range-picker.js.map +0 -1
  591. package/cjs/form/form-timepicker.js +0 -2
  592. package/cjs/form/form-timepicker.js.map +0 -1
  593. package/cjs/form/form-unit-number-input.js +0 -2
  594. package/cjs/form/form-unit-number-input.js.map +0 -1
  595. package/form/form-custom-field.js +0 -2
  596. package/form/form-custom-field.js.map +0 -1
  597. package/form/form-date-input.js +0 -2
  598. package/form/form-date-input.js.map +0 -1
  599. package/form/form-date-range-input.js +0 -2
  600. package/form/form-date-range-input.js.map +0 -1
  601. package/form/form-e-signature.js +0 -2
  602. package/form/form-e-signature.js.map +0 -1
  603. package/form/form-histogram.js +0 -2
  604. package/form/form-histogram.js.map +0 -1
  605. package/form/form-input-group.js +0 -2
  606. package/form/form-input-group.js.map +0 -1
  607. package/form/form-input.js +0 -2
  608. package/form/form-input.js.map +0 -1
  609. package/form/form-label-addon.js +0 -2
  610. package/form/form-label-addon.js.map +0 -1
  611. package/form/form-label-addon.styles.js +0 -2
  612. package/form/form-label-addon.styles.js.map +0 -1
  613. package/form/form-label-addon.styles_b00z8p.css +0 -1
  614. package/form/form-label.js +0 -2
  615. package/form/form-label.js.map +0 -1
  616. package/form/form-label.styles.js +0 -2
  617. package/form/form-label.styles.js.map +0 -1
  618. package/form/form-label.styles_1nbe0bm.css +0 -6
  619. package/form/form-masked-input.js +0 -2
  620. package/form/form-masked-input.js.map +0 -1
  621. package/form/form-multi-select.js +0 -2
  622. package/form/form-multi-select.js.map +0 -1
  623. package/form/form-nested-multi-select.js +0 -2
  624. package/form/form-nested-multi-select.js.map +0 -1
  625. package/form/form-nested-select.js +0 -2
  626. package/form/form-nested-select.js.map +0 -1
  627. package/form/form-otp-verification.js +0 -2
  628. package/form/form-otp-verification.js.map +0 -1
  629. package/form/form-phone-number-input.js +0 -2
  630. package/form/form-phone-number-input.js.map +0 -1
  631. package/form/form-predictive-text-input.js +0 -2
  632. package/form/form-predictive-text-input.js.map +0 -1
  633. package/form/form-range-select.js +0 -2
  634. package/form/form-range-select.js.map +0 -1
  635. package/form/form-range-slider.js +0 -2
  636. package/form/form-range-slider.js.map +0 -1
  637. package/form/form-select-histogram.js +0 -2
  638. package/form/form-select-histogram.js.map +0 -1
  639. package/form/form-select.js +0 -2
  640. package/form/form-select.js.map +0 -1
  641. package/form/form-slider.js +0 -2
  642. package/form/form-slider.js.map +0 -1
  643. package/form/form-textarea.js +0 -2
  644. package/form/form-textarea.js.map +0 -1
  645. package/form/form-textarea.styles.js +0 -2
  646. package/form/form-textarea.styles.js.map +0 -1
  647. package/form/form-textarea.styles_3p9qoy.css +0 -3
  648. package/form/form-time-range-picker.js +0 -2
  649. package/form/form-time-range-picker.js.map +0 -1
  650. package/form/form-timepicker.js +0 -2
  651. package/form/form-timepicker.js.map +0 -1
  652. package/form/form-unit-number-input.js +0 -2
  653. package/form/form-unit-number-input.js.map +0 -1
  654. package/link-list/internal-types.d.ts +0 -85
  655. /package/{codemod-utils.d.ts → codemods/codemod-utils.d.ts} +0 -0
  656. /package/{migrate-popover → codemods/migrate-popover}/index.d.ts +0 -0
  657. /package/{run-codemod.d.ts → codemods/run-codemod.d.ts} +0 -0
  658. /package/form/{form-custom-field.d.ts → form-custom-field/form-custom-field.d.ts} +0 -0
  659. /package/form/{form-date-input.d.ts → form-date-input/form-date-input.d.ts} +0 -0
  660. /package/form/{form-date-range-input.d.ts → form-date-range-input/form-date-range-input.d.ts} +0 -0
  661. /package/form/{form-e-signature.d.ts → form-e-signature/form-e-signature.d.ts} +0 -0
  662. /package/form/{form-histogram.d.ts → form-histogram-slider/form-histogram-slider.d.ts} +0 -0
  663. /package/form/{form-input.d.ts → form-input/form-input.d.ts} +0 -0
  664. /package/form/{form-input-group.d.ts → form-input-group/form-input-group.d.ts} +0 -0
  665. /package/form/{form-label-addon.d.ts → form-label/form-label-addon.d.ts} +0 -0
  666. /package/form/{form-label-addon.styles.d.ts → form-label/form-label-addon.styles.d.ts} +0 -0
  667. /package/form/{form-label.d.ts → form-label/form-label.d.ts} +0 -0
  668. /package/form/{form-label.styles.d.ts → form-label/form-label.styles.d.ts} +0 -0
  669. /package/form/{form-masked-input.d.ts → form-masked-input/form-masked-input.d.ts} +0 -0
  670. /package/form/{form-multi-select.d.ts → form-multi-select/form-multi-select.d.ts} +0 -0
  671. /package/form/{form-nested-multi-select.d.ts → form-nested-multi-select/form-nested-multi-select.d.ts} +0 -0
  672. /package/form/{form-nested-select.d.ts → form-nested-select/form-nested-select.d.ts} +0 -0
  673. /package/form/{form-phone-number-input.d.ts → form-phone-number-input/form-phone-number-input.d.ts} +0 -0
  674. /package/form/{form-predictive-text-input.d.ts → form-predictive-text-input/form-predictive-text-input.d.ts} +0 -0
  675. /package/form/{form-range-select.d.ts → form-range-select/form-range-select.d.ts} +0 -0
  676. /package/form/{form-range-slider.d.ts → form-range-slider/form-range-slider.d.ts} +0 -0
  677. /package/form/{form-select.d.ts → form-select/form-select.d.ts} +0 -0
  678. /package/form/{form-select-histogram.d.ts → form-select-histogram/form-select-histogram.d.ts} +0 -0
  679. /package/form/{form-slider.d.ts → form-slider/form-slider.d.ts} +0 -0
  680. /package/form/{form-textarea.d.ts → form-textarea/form-textarea.d.ts} +0 -0
  681. /package/form/{form-textarea.styles.d.ts → form-textarea/form-textarea.styles.d.ts} +0 -0
  682. /package/form/{form-time-range-picker.d.ts → form-time-range-picker/form-time-range-picker.d.ts} +0 -0
  683. /package/form/{form-timepicker.d.ts → form-timepicker/form-timepicker.d.ts} +0 -0
  684. /package/form/{form-unit-number-input.d.ts → form-unit-number-input/form-unit-number-input.d.ts} +0 -0
@@ -1 +1 @@
1
- {"version":3,"file":"overlay.js","sources":["../../src/overlay/overlay.tsx"],"sourcesContent":["import {\n FloatingNode,\n FloatingTree,\n useFloatingNodeId,\n} from \"@floating-ui/react\";\nimport clsx from \"clsx\";\nimport type React from \"react\";\nimport { useEffect, useRef, useState } from \"react\";\nimport ReactDOM from \"react-dom\";\n\nimport { useApplyStyle, useInheritedThemeScope } from \"../theme\";\nimport { useId } from \"../util\";\nimport * as styles from \"./overlay.styles\";\nimport type { OverlayProps } from \"./types\";\nimport { useFloatingParent } from \"./use-floating-context\";\n\nconst OverlayComponent = ({\n show = false,\n rootId,\n onOverlayClick,\n children,\n backgroundBlur = true,\n disableTransition = false,\n enableOverlayClick = false,\n zIndex: customZIndex,\n id,\n containerRef,\n}: OverlayProps): JSX.Element | null => {\n // =============================================================================\n // CONST, STATE, REF\n // =============================================================================\n const [rootElement, setRootElement] = useState<HTMLElement | null>(null);\n const [isStacked, _setIsStacked] = useState<boolean>();\n const uid = useId();\n const nodeId = useFloatingNodeId();\n\n const stacked = useRef<boolean>();\n // Track where mousedown started to prevent closing drawer during text selection drag\n const mouseDownInsideModalRef = useRef(false);\n const rootRef = useRef<HTMLDivElement>(null);\n const wrapperRef = useRef<HTMLDivElement>(null);\n\n const overlayRootId = id\n ? `lifesg-ds-overlay-root-${id}`\n : \"lifesg-ds-overlay-root\";\n const zIndex = customZIndex ?? (isStacked ? 99999 : 99998);\n const { themeProps, themeStyle } = useInheritedThemeScope(show);\n\n useFloatingParent(zIndex);\n\n useApplyStyle(rootRef, { [styles.tokens.root.zIndex]: zIndex });\n\n // =============================================================================\n // EFFECTS\n // =============================================================================\n useEffect(() => {\n initialiseStylesForDocumentBody();\n setRootElement(getRootElement());\n\n return () => {\n removeOverlay();\n\n if (getOverlayOrder().length < 1) {\n if (isIOS()) {\n applyScrollLockClassForIOS(\"remove\");\n scrollToLastScrollPositionForIOS();\n }\n\n applyBodyStyleClass(\"remove\");\n }\n };\n }, []);\n\n useEffect(() => {\n if (show) {\n const isStacked = checkIfStacked();\n setStacked(isStacked);\n\n addOverlay();\n\n if (isIOS() && getOverlayOrder().length === 1) {\n saveScrollPosition();\n applyScrollLockClassForIOS(\"add\");\n }\n\n const timerId = setTimeout(() => {\n applyBodyStyleClass(\"add\");\n }, 200); // Allow overlay animations to complete\n\n return () => clearTimeout(timerId);\n } else {\n removeOverlay();\n\n if (isIOS() && getOverlayOrder().length < 1) {\n applyScrollLockClassForIOS(\"remove\");\n scrollToLastScrollPositionForIOS();\n }\n\n const timerId = setTimeout(() => {\n if (getOverlayOrder().length < 1) {\n applyBodyStyleClass(\"remove\");\n }\n }, 200); // Allow overlay animations to complete\n\n return () => clearTimeout(timerId);\n }\n }, [show]);\n\n // Track mousedown origin to distinguish clicks from text selection drags\n useEffect(() => {\n if (!show) return;\n\n document.addEventListener(\"mousedown\", handleDocumentMouseDown, true);\n return () => {\n document.removeEventListener(\n \"mousedown\",\n handleDocumentMouseDown,\n true\n );\n };\n }, [show]);\n\n // =============================================================================\n // REF FUNCTIONS\n // =============================================================================\n const setStacked = (data: boolean) => {\n stacked.current = data;\n _setIsStacked(data);\n };\n\n // =============================================================================\n // HELPER FUNCTIONS\n // =============================================================================\n const isIOS = () => /(iPad|iPhone|iPod)/g.test(navigator.userAgent);\n\n const getRootElement = (): HTMLElement | null => {\n if (document && rootId) {\n return document.getElementById(rootId);\n } else if (document) {\n // If rootId not specified, we'll use body\n return document.body;\n } else {\n return null;\n }\n };\n\n const checkIfStacked = () => {\n return getOverlayOrder().length > 0;\n };\n\n const initialiseStylesForDocumentBody = () => {\n const documentWidth = document.documentElement.clientWidth;\n const windowWidth = window.innerWidth;\n const scrollBarWidth = windowWidth - documentWidth;\n\n document.documentElement.style.setProperty(\n styles.tokens.global.scrollbarWidth,\n `${scrollBarWidth}px`\n );\n };\n\n /**\n * This sets the style of <body> to hide the scrollbar\n */\n const applyBodyStyleClass = (action: \"add\" | \"remove\") => {\n const isOverlayStyleClassApplied = document.body.classList.contains(\n styles.tokens.global.overlayOpenClass\n );\n\n if (action === \"add\" && !isOverlayStyleClassApplied) {\n document.body.classList.add(styles.tokens.global.overlayOpenClass);\n } else if (action === \"remove\" && isOverlayStyleClassApplied) {\n document.body.classList.remove(\n styles.tokens.global.overlayOpenClass\n );\n }\n };\n\n const getOverlayOrder = () => {\n const attr = document.body.dataset.lifesgDsOverlayOrder;\n return attr ? attr.split(\",\") : [];\n };\n\n const addOverlay = () => {\n const order = getOverlayOrder();\n document.body.dataset.lifesgDsOverlayOrder = [...order, uid].join(\",\");\n };\n\n const removeOverlay = () => {\n const order = getOverlayOrder();\n document.body.dataset.lifesgDsOverlayOrder = order\n .filter((o) => o !== uid)\n .join(\",\");\n };\n\n /**\n * This sets the style of <body> to further prevent scrolling on iOS\n *\n * ref: https://stackoverflow.com/a/57455820/3932279\n * `overflow: hidden` and `overscroll-behavior` is ignored by iOS, this is\n * an alternative solution\n *\n * as a side effect this causes the scroll position to reset, so additional\n * logic to restore the scroll on close is required\n */\n const applyScrollLockClassForIOS = (action: \"add\" | \"remove\") => {\n if (!isIOS()) {\n return;\n }\n\n const isClassApplied = document.body.classList.contains(\n styles.tokens.global.overlayScrollLockClass\n );\n\n if (action === \"add\" && !isClassApplied) {\n document.body.classList.add(\n styles.tokens.global.overlayScrollLockClass\n );\n } else if (action === \"remove\" && isClassApplied) {\n document.body.classList.remove(\n styles.tokens.global.overlayScrollLockClass\n );\n }\n };\n\n const saveScrollPosition = () => {\n const bodyStyle = document.body.style;\n const scrollY = bodyStyle.top ? bodyStyle.top : window.scrollY + \"px\";\n\n document.body.style.setProperty(styles.tokens.global.scrollY, scrollY);\n };\n\n const scrollToLastScrollPositionForIOS = () => {\n if (!isIOS()) {\n return;\n }\n\n const scrollY = document.body.style.getPropertyValue(\n styles.tokens.global.scrollY\n );\n requestAnimationFrame(() => {\n window.scrollTo({\n top: parseFloat(scrollY),\n });\n });\n };\n\n // =============================================================================\n // EVENT HANDLERS\n // =============================================================================\n const handleDocumentMouseDown = (e: MouseEvent) => {\n const container = containerRef?.current ?? wrapperRef.current;\n const wrapper = wrapperRef.current;\n if (!container) {\n mouseDownInsideModalRef.current = false;\n return;\n }\n\n const target = e.target as Node;\n const clickedOnWrapper = wrapper === target;\n const clickedOnContainer = container === target;\n const clickedInsideContainer = container.contains(target);\n\n // Track if mousedown started inside modal content\n mouseDownInsideModalRef.current =\n !clickedOnWrapper && (clickedOnContainer || clickedInsideContainer);\n };\n\n const handleWrapperClick = (event: React.MouseEvent<HTMLDivElement>) => {\n const container = containerRef?.current ?? wrapperRef.current;\n const wrapper = wrapperRef.current;\n if (!container) {\n mouseDownInsideModalRef.current = false;\n return;\n }\n\n const target = event.target as Node;\n const clickedOnWrapper = wrapper === target;\n const clickedOnContainer = container === target;\n const clickedInsideContainer = container.contains(target);\n const clickedInsideModal = clickedOnContainer || clickedInsideContainer;\n\n // Only close if both mousedown AND click happened outside modal\n if (\n (clickedOnWrapper || !clickedInsideModal) &&\n !mouseDownInsideModalRef.current &&\n onOverlayClick &&\n enableOverlayClick\n ) {\n event.preventDefault();\n onOverlayClick();\n }\n\n mouseDownInsideModalRef.current = false;\n };\n\n // =============================================================================\n // RENDER\n // =============================================================================\n const renderWrapper = () => (\n <FloatingNode id={nodeId}>\n <div\n ref={wrapperRef}\n data-testid=\"overlay-wrapper\"\n className={clsx(\n styles.wrapper,\n show ? styles.wrapperShow : styles.wrapperHide,\n isStacked && styles.wrapperStacked,\n backgroundBlur && styles.wrapperBackgroundBlur,\n disableTransition && styles.wrapperDisableTransition\n )}\n onClick={handleWrapperClick}\n >\n {children}\n </div>\n </FloatingNode>\n );\n\n const renderComponent = () => (\n <div\n ref={rootRef}\n id={overlayRootId}\n data-testid={overlayRootId}\n className={clsx(styles.root, show && styles.rootShow)}\n {...themeProps}\n style={themeStyle}\n >\n {children && renderWrapper()}\n </div>\n );\n\n return rootElement\n ? ReactDOM.createPortal(renderComponent(), rootElement)\n : null;\n};\n\n/**\n * A full-screen dimmed overlay backdrop.\n *\n * Use `Overlay` as the backdrop for modal dialogs, drawers, and similar\n * blocking UI patterns. It manages body scroll-lock automatically and stacks\n * correctly when multiple overlays are open at once.\n */\nexport const Overlay = (props: OverlayProps) => {\n return (\n <FloatingTree>\n <OverlayComponent {...props} />\n </FloatingTree>\n );\n};\n"],"names":["OverlayComponent","show","rootId","onOverlayClick","children","backgroundBlur","disableTransition","enableOverlayClick","zIndex","customZIndex","id","containerRef","rootElement","setRootElement","useState","isStacked","_setIsStacked","uid","useId","nodeId","useFloatingNodeId","stacked","useRef","mouseDownInsideModalRef","rootRef","wrapperRef","overlayRootId","themeProps","themeStyle","useInheritedThemeScope","useFloatingParent","useApplyStyle","styles.tokens","root","useEffect","initialiseStylesForDocumentBody","getRootElement","removeOverlay","getOverlayOrder","length","isIOS","applyScrollLockClassForIOS","scrollToLastScrollPositionForIOS","applyBodyStyleClass","checkIfStacked","setStacked","addOverlay","saveScrollPosition","timerId","setTimeout","clearTimeout","document","addEventListener","handleDocumentMouseDown","removeEventListener","data","current","test","navigator","userAgent","getElementById","body","documentWidth","documentElement","clientWidth","scrollBarWidth","window","innerWidth","style","setProperty","global","scrollbarWidth","action","isOverlayStyleClassApplied","classList","contains","overlayOpenClass","remove","add","attr","dataset","lifesgDsOverlayOrder","split","order","join","filter","o","isClassApplied","overlayScrollLockClass","bodyStyle","scrollY","top","getPropertyValue","requestAnimationFrame","scrollTo","parseFloat","e","container","_a","wrapper","target","clickedOnWrapper","clickedOnContainer","clickedInsideContainer","handleWrapperClick","event","preventDefault","ReactDOM","createPortal","_jsx","Object","assign","ref","className","clsx","styles.root","styles.rootShow","FloatingNode","styles.wrapper","styles.wrapperShow","styles.wrapperHide","styles.wrapperStacked","styles.wrapperBackgroundBlur","styles.wrapperDisableTransition","onClick","Overlay","props","FloatingTree"],"mappings":"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"}
1
+ {"version":3,"file":"overlay.js","sources":["../../src/overlay/overlay.tsx"],"sourcesContent":["import {\n FloatingNode,\n FloatingTree,\n useFloatingNodeId,\n} from \"@floating-ui/react\";\nimport clsx from \"clsx\";\nimport type React from \"react\";\nimport { useEffect, useRef, useState } from \"react\";\nimport ReactDOM from \"react-dom\";\n\nimport { useApplyStyle, useInheritedThemeScope } from \"../theme\";\nimport { useId } from \"../util\";\nimport * as styles from \"./overlay.styles\";\nimport type { OverlayProps } from \"./types\";\nimport { useFloatingParent } from \"./use-floating-context\";\n\nconst OverlayComponent = ({\n show = false,\n rootId,\n onOverlayClick,\n children,\n backgroundBlur = true,\n disableTransition = false,\n enableOverlayClick = false,\n zIndex: customZIndex,\n id,\n containerRef,\n}: OverlayProps): JSX.Element | null => {\n // =============================================================================\n // CONST, STATE, REF\n // =============================================================================\n const [rootElement, setRootElement] = useState<HTMLElement | null>(null);\n const [isStacked, _setIsStacked] = useState<boolean>();\n const uid = useId();\n const nodeId = useFloatingNodeId();\n\n const stacked = useRef<boolean>();\n // Track where mousedown started to prevent closing drawer during text selection drag\n const mouseDownInsideModalRef = useRef(false);\n const rootRef = useRef<HTMLDivElement>(null);\n const wrapperRef = useRef<HTMLDivElement>(null);\n\n const overlayRootId = id\n ? `lifesg-ds-overlay-root-${id}`\n : \"lifesg-ds-overlay-root\";\n const zIndex = customZIndex ?? (isStacked ? 99999 : 99998);\n const { themeProps, themeStyle } = useInheritedThemeScope(show);\n\n useFloatingParent(zIndex);\n\n useApplyStyle(rootRef, { [styles.tokens.root.zIndex]: zIndex });\n\n // =============================================================================\n // EFFECTS\n // =============================================================================\n useEffect(() => {\n initialiseStylesForDocumentBody();\n setRootElement(getRootElement());\n\n return () => {\n removeOverlay();\n\n if (getOverlayOrder().length < 1) {\n if (isIOS()) {\n applyScrollLockClassForIOS(\"remove\");\n scrollToLastScrollPositionForIOS();\n }\n\n applyBodyStyleClass(\"remove\");\n }\n };\n }, []);\n\n useEffect(() => {\n if (show) {\n const isStacked = checkIfStacked();\n setStacked(isStacked);\n\n addOverlay();\n\n if (isIOS() && getOverlayOrder().length === 1) {\n saveScrollPosition();\n applyScrollLockClassForIOS(\"add\");\n }\n\n const timerId = setTimeout(() => {\n applyBodyStyleClass(\"add\");\n }, 200); // Allow overlay animations to complete\n\n return () => clearTimeout(timerId);\n } else {\n removeOverlay();\n\n if (isIOS() && getOverlayOrder().length < 1) {\n applyScrollLockClassForIOS(\"remove\");\n scrollToLastScrollPositionForIOS();\n }\n\n const timerId = setTimeout(() => {\n if (getOverlayOrder().length < 1) {\n applyBodyStyleClass(\"remove\");\n }\n }, 200); // Allow overlay animations to complete\n\n return () => clearTimeout(timerId);\n }\n }, [show]);\n\n // Track mousedown origin to distinguish clicks from text selection drags\n useEffect(() => {\n if (!show) return;\n\n document.addEventListener(\"mousedown\", handleDocumentMouseDown, true);\n return () => {\n document.removeEventListener(\n \"mousedown\",\n handleDocumentMouseDown,\n true\n );\n };\n }, [show]);\n\n // =============================================================================\n // REF FUNCTIONS\n // =============================================================================\n const setStacked = (data: boolean) => {\n stacked.current = data;\n _setIsStacked(data);\n };\n\n // =============================================================================\n // HELPER FUNCTIONS\n // =============================================================================\n const isIOS = () => /(iPad|iPhone|iPod)/g.test(navigator.userAgent);\n\n const getRootElement = (): HTMLElement | null => {\n if (document && rootId) {\n return document.getElementById(rootId);\n } else if (document) {\n // If rootId not specified, we'll use body\n return document.body;\n } else {\n return null;\n }\n };\n\n const checkIfStacked = () => {\n return getOverlayOrder().length > 0;\n };\n\n const initialiseStylesForDocumentBody = () => {\n const documentWidth = document.documentElement.clientWidth;\n const windowWidth = window.innerWidth;\n const scrollBarWidth = windowWidth - documentWidth;\n\n document.documentElement.style.setProperty(\n styles.tokens.global.scrollbarWidth,\n `${scrollBarWidth}px`\n );\n };\n\n /**\n * This sets the style of <body> to hide the scrollbar\n */\n const applyBodyStyleClass = (action: \"add\" | \"remove\") => {\n const isOverlayStyleClassApplied = document.body.classList.contains(\n styles.tokens.global.overlayOpenClass\n );\n\n if (action === \"add\" && !isOverlayStyleClassApplied) {\n document.body.classList.add(styles.tokens.global.overlayOpenClass);\n } else if (action === \"remove\" && isOverlayStyleClassApplied) {\n document.body.classList.remove(\n styles.tokens.global.overlayOpenClass\n );\n }\n };\n\n const getOverlayOrder = () => {\n const attr = document.body.dataset.lifesgDsOverlayOrder;\n return attr ? attr.split(\",\") : [];\n };\n\n const addOverlay = () => {\n const order = getOverlayOrder();\n document.body.dataset.lifesgDsOverlayOrder = [...order, uid].join(\",\");\n };\n\n const removeOverlay = () => {\n const order = getOverlayOrder();\n document.body.dataset.lifesgDsOverlayOrder = order\n .filter((o) => o !== uid)\n .join(\",\");\n };\n\n /**\n * This sets the style of <body> to further prevent scrolling on iOS\n *\n * ref: https://stackoverflow.com/a/57455820/3932279\n * `overflow: hidden` and `overscroll-behavior` is ignored by iOS, this is\n * an alternative solution\n *\n * as a side effect this causes the scroll position to reset, so additional\n * logic to restore the scroll on close is required\n */\n const applyScrollLockClassForIOS = (action: \"add\" | \"remove\") => {\n if (!isIOS()) {\n return;\n }\n\n const isClassApplied = document.body.classList.contains(\n styles.tokens.global.overlayScrollLockClass\n );\n\n if (action === \"add\" && !isClassApplied) {\n document.body.classList.add(\n styles.tokens.global.overlayScrollLockClass\n );\n } else if (action === \"remove\" && isClassApplied) {\n document.body.classList.remove(\n styles.tokens.global.overlayScrollLockClass\n );\n }\n };\n\n const saveScrollPosition = () => {\n const bodyStyle = document.body.style;\n const scrollY = bodyStyle.top ? bodyStyle.top : window.scrollY + \"px\";\n\n document.body.style.setProperty(styles.tokens.global.scrollY, scrollY);\n };\n\n const scrollToLastScrollPositionForIOS = () => {\n if (!isIOS()) {\n return;\n }\n\n const scrollY = document.body.style.getPropertyValue(\n styles.tokens.global.scrollY\n );\n requestAnimationFrame(() => {\n window.scrollTo({\n top: parseFloat(scrollY),\n });\n });\n };\n\n // =============================================================================\n // EVENT HANDLERS\n // =============================================================================\n const handleDocumentMouseDown = (e: MouseEvent) => {\n const container = containerRef?.current ?? wrapperRef.current;\n const wrapper = wrapperRef.current;\n if (!container) {\n mouseDownInsideModalRef.current = false;\n return;\n }\n\n const target = e.target as Node;\n const clickedOnWrapper = wrapper === target;\n const clickedOnContainer = container === target;\n const clickedInsideContainer = container.contains(target);\n\n // Track if mousedown started inside modal content\n mouseDownInsideModalRef.current =\n !clickedOnWrapper && (clickedOnContainer || clickedInsideContainer);\n };\n\n const handleWrapperClick = (event: React.MouseEvent<HTMLDivElement>) => {\n const container = containerRef?.current ?? wrapperRef.current;\n const wrapper = wrapperRef.current;\n if (!container) {\n mouseDownInsideModalRef.current = false;\n return;\n }\n\n const target = event.target as Node;\n const clickedOnWrapper = wrapper === target;\n const clickedOnContainer = container === target;\n const clickedInsideContainer = container.contains(target);\n const clickedInsideModal = clickedOnContainer || clickedInsideContainer;\n\n // Only close if both mousedown AND click happened outside modal\n if (\n (clickedOnWrapper || !clickedInsideModal) &&\n !mouseDownInsideModalRef.current &&\n onOverlayClick &&\n enableOverlayClick\n ) {\n event.preventDefault();\n onOverlayClick();\n }\n\n mouseDownInsideModalRef.current = false;\n };\n\n // =============================================================================\n // RENDER\n // =============================================================================\n const renderWrapper = () => (\n <FloatingNode id={nodeId}>\n <div\n ref={wrapperRef}\n data-testid=\"overlay-wrapper\"\n className={clsx(\n styles.wrapper,\n show ? styles.wrapperShow : styles.wrapperHide,\n isStacked && styles.wrapperStacked,\n backgroundBlur && styles.wrapperBackgroundBlur,\n disableTransition && styles.wrapperDisableTransition\n )}\n onClick={handleWrapperClick}\n >\n {children}\n </div>\n </FloatingNode>\n );\n\n const renderComponent = () => (\n <div\n ref={rootRef}\n id={overlayRootId}\n data-testid={overlayRootId}\n className={clsx(styles.root, show && styles.rootShow)}\n {...themeProps}\n style={themeStyle}\n >\n {children && renderWrapper()}\n </div>\n );\n\n return rootElement\n ? ReactDOM.createPortal(renderComponent(), rootElement)\n : null;\n};\n\n// @catalog\n/**\n * A full-screen dimmed overlay backdrop.\n *\n * Use `Overlay` as the backdrop for modal dialogs, drawers, and similar\n * blocking UI patterns. It manages body scroll-lock automatically and stacks\n * correctly when multiple overlays are open at once.\n */\nexport const Overlay = (props: OverlayProps) => {\n return (\n <FloatingTree>\n <OverlayComponent {...props} />\n </FloatingTree>\n );\n};\n"],"names":["OverlayComponent","show","rootId","onOverlayClick","children","backgroundBlur","disableTransition","enableOverlayClick","zIndex","customZIndex","id","containerRef","rootElement","setRootElement","useState","isStacked","_setIsStacked","uid","useId","nodeId","useFloatingNodeId","stacked","useRef","mouseDownInsideModalRef","rootRef","wrapperRef","overlayRootId","themeProps","themeStyle","useInheritedThemeScope","useFloatingParent","useApplyStyle","styles.tokens","root","useEffect","initialiseStylesForDocumentBody","getRootElement","removeOverlay","getOverlayOrder","length","isIOS","applyScrollLockClassForIOS","scrollToLastScrollPositionForIOS","applyBodyStyleClass","checkIfStacked","setStacked","addOverlay","saveScrollPosition","timerId","setTimeout","clearTimeout","document","addEventListener","handleDocumentMouseDown","removeEventListener","data","current","test","navigator","userAgent","getElementById","body","documentWidth","documentElement","clientWidth","scrollBarWidth","window","innerWidth","style","setProperty","global","scrollbarWidth","action","isOverlayStyleClassApplied","classList","contains","overlayOpenClass","remove","add","attr","dataset","lifesgDsOverlayOrder","split","order","join","filter","o","isClassApplied","overlayScrollLockClass","bodyStyle","scrollY","top","getPropertyValue","requestAnimationFrame","scrollTo","parseFloat","e","container","_a","wrapper","target","clickedOnWrapper","clickedOnContainer","clickedInsideContainer","handleWrapperClick","event","preventDefault","ReactDOM","createPortal","_jsx","Object","assign","ref","className","clsx","styles.root","styles.rootShow","FloatingNode","styles.wrapper","styles.wrapperShow","styles.wrapperHide","styles.wrapperStacked","styles.wrapperBackgroundBlur","styles.wrapperDisableTransition","onClick","Overlay","props","FloatingTree"],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@lifesg/react-design-system",
3
- "version": "4.0.0-alpha.6",
3
+ "version": "4.0.0-alpha.7",
4
4
  "description": "A component design system for LifeSG web apps",
5
5
  "keywords": [
6
6
  "design-system"
@@ -1 +1 @@
1
- {"version":3,"file":"pagination.js","sources":["../../src/pagination/pagination.tsx"],"sourcesContent":["import { Chevron2LeftIcon } from \"@lifesg/react-icons/chevron-2-left\";\nimport { Chevron2RightIcon } from \"@lifesg/react-icons/chevron-2-right\";\nimport { ChevronLeftIcon } from \"@lifesg/react-icons/chevron-left\";\nimport { ChevronLineLeftIcon } from \"@lifesg/react-icons/chevron-line-left\";\nimport { ChevronLineRightIcon } from \"@lifesg/react-icons/chevron-line-right\";\nimport { ChevronRightIcon } from \"@lifesg/react-icons/chevron-right\";\nimport { EllipsisHorizontalIcon } from \"@lifesg/react-icons/ellipsis-horizontal\";\nimport clsx from \"clsx\";\nimport React, { useEffect, useState } from \"react\";\n\nimport { Input } from \"../input\";\nimport { InputSelect } from \"../input-select\";\nimport { VisuallyHidden } from \"../shared/accessibility\";\nimport { ClickableIcon } from \"../shared/clickable-icon\";\nimport { useMaxWidthMediaQuery } from \"../theme\";\nimport { Typography } from \"../typography\";\nimport { useId, useIsMounted } from \"../util\";\nimport * as styles from \"./pagination.styles\";\nimport type { PageSizeItemProps, PaginationProps } from \"./types\";\n\nconst Component = (\n {\n id,\n \"data-testid\": dataTestId,\n className,\n pageSize = 10,\n totalItems,\n activePage,\n pageSizeOptions = DEFAULT_OPTIONS,\n showFirstAndLastNav,\n showPageSizeChanger = false,\n onPageChange,\n onPageSizeChange,\n }: PaginationProps,\n ref: React.Ref<HTMLDivElement>\n) => {\n // =============================================================================\n // CONST, STATE, REF\n // =============================================================================\n\n const isMounted = useIsMounted();\n const isMobile = useMaxWidthMediaQuery(\"sm\");\n const [hoverRightButton, setHoverRightButton] = useState(false);\n const [hoverLeftButton, setHoverLeftButton] = useState(false);\n const [inputText, setInputText] = useState<string>(\"\");\n\n const [selectedOption, setSelectedOption] = useState<\n PageSizeItemProps | undefined\n >(pageSizeOptions[0]);\n const [pageSizeLocal, setPageSize] = useState<number>(\n !isMobile && showPageSizeChanger\n ? selectedOption\n ? selectedOption.value\n : pageSize\n : pageSize\n );\n\n const boundaryRange = 1;\n const siblingRange = 1;\n\n const internalId = useId();\n const paginationId = `${internalId}-pagination`;\n\n const totalPages = Math.ceil(totalItems / pageSizeLocal);\n const isFirstPage = activePage === 1;\n const isLastPage = activePage === totalPages;\n\n const firstPaginationItem =\n activePage > 1 ? () => handlePaginationItemClick(1) : undefined;\n const lastPaginationItem =\n activePage < totalPages\n ? () => handlePaginationItemClick(totalPages)\n : undefined;\n const prevPaginationItem =\n activePage > 1\n ? () => handlePaginationItemClick(activePage - 1)\n : undefined;\n const nextPaginationItem =\n activePage < totalPages\n ? () =>\n handlePaginationItemClick(parseInt(activePage.toString()) + 1)\n : undefined;\n\n // =============================================================================\n // EFFECTS\n // =============================================================================\n useEffect(() => {\n if (activePage) {\n setInputValue(activePage);\n }\n }, [activePage]);\n\n useEffect(() => {\n setPageSize(pageSize);\n setSelectedOption(\n pageSizeOptions.find((option) => option.value === pageSize)\n );\n }, [pageSize]);\n\n // =============================================================================\n // HELPER FUNCTIONS\n // =============================================================================\n const setInputValue = (value: number) => {\n setInputText(value.toString());\n };\n\n const closeAllTooltips = () => {\n setHoverRightButton(false);\n setHoverLeftButton(false);\n };\n\n // =============================================================================\n // EVENT HANDLERS\n // =============================================================================\n const handlePaginationItemClick = (pageIndex: number) => {\n if (onPageChange) {\n onPageChange(pageIndex);\n setInputValue(pageIndex);\n }\n };\n\n const handleFastForwardClick = () => {\n const currentIndex = Math.min(totalPages, activePage + 5);\n handlePaginationItemClick(currentIndex);\n setInputValue(currentIndex);\n setHoverRightButton(true);\n setHoverLeftButton(false);\n };\n\n const handleFastBackwardClick = () => {\n const currentIndex = Math.max(1, activePage - 5);\n handlePaginationItemClick(currentIndex);\n setInputValue(currentIndex);\n setHoverRightButton(false);\n setHoverLeftButton(true);\n };\n\n const handleInput = (event: React.ChangeEvent<HTMLInputElement>) => {\n const value = event.target.value;\n const numericRegex = /^[0-9]+$/;\n if (value === undefined || value.length === 0) {\n setInputText(\"\");\n } else if (!numericRegex.test(value)) {\n setInputText(value.replace(/[^0-9]/g, \"\"));\n } else {\n const newPage = parseInt(value.replace(/[^0-9]/g, \"\"));\n setInputValue(Math.max(1, Math.min(totalPages, newPage)));\n }\n };\n\n const handleInputSubmit = (event: React.FormEvent) => {\n event.preventDefault();\n if (inputText) {\n onPageChange?.(parseInt(inputText));\n }\n };\n\n const onHoverRightButton = () => {\n setHoverRightButton(true);\n };\n\n const onBlurRightButton = () => {\n setHoverRightButton(false);\n };\n\n const onHoverLeftButton = () => {\n setHoverLeftButton(true);\n };\n\n const onBlurLeftButton = () => {\n setHoverLeftButton(false);\n };\n\n const handleListItemClick = (item: PageSizeItemProps) => {\n setSelectedOption(item);\n const pagesize = item.value;\n const totalPage = Math.ceil(totalItems / pagesize);\n\n setPageSize(pagesize);\n\n const page = activePage >= totalPage ? totalPage : activePage;\n\n if (onPageSizeChange) {\n onPageSizeChange(page, pagesize);\n }\n };\n\n // =============================================================================\n // RENDER FUNCTIONS\n // =============================================================================\n const renderPaginationItems = () => {\n return [...Array(totalPages)].map((e, i) => {\n const pageIndex = i + 1;\n const startRange = boundaryRange + 2 + siblingRange * 2;\n const endRange = totalPages - startRange;\n const totalRange = (boundaryRange + siblingRange) * 2 + 3;\n const active = activePage === pageIndex;\n if (totalPages <= totalRange) {\n return (\n <button\n key={pageIndex}\n onClick={() => handlePaginationItemClick(pageIndex)}\n className={clsx(\n styles.pageItem,\n active && styles.pageItemSelected\n )}\n aria-label={`page ${pageIndex} of ${totalPages}`}\n aria-current={active ? \"page\" : false}\n onMouseOver={closeAllTooltips}\n onFocus={closeAllTooltips}\n >\n {pageIndex}\n </button>\n );\n }\n\n const ellipsisStart =\n activePage + siblingRange > startRange &&\n pageIndex === boundaryRange + 1;\n if (ellipsisStart) {\n return renderStartEllipsis(pageIndex);\n }\n\n const ellipsisEnd =\n activePage - siblingRange <= endRange &&\n pageIndex === totalPages - boundaryRange - 1;\n if (ellipsisEnd) {\n return renderEndEllipsis(pageIndex);\n }\n\n const paginationStart =\n (pageIndex <= startRange &&\n activePage + siblingRange <= startRange) ||\n pageIndex <= boundaryRange;\n const paginationMiddle =\n pageIndex === activePage ||\n (pageIndex <= activePage + siblingRange &&\n pageIndex >= activePage - siblingRange - 1);\n const paginationEnd =\n (pageIndex > endRange &&\n activePage - siblingRange > endRange) ||\n pageIndex > totalPages - boundaryRange;\n if (paginationStart || paginationMiddle || paginationEnd) {\n return (\n <button\n key={pageIndex}\n onClick={() => handlePaginationItemClick(pageIndex)}\n className={clsx(\n styles.pageItem,\n active && styles.pageItemSelected\n )}\n aria-label={`page ${pageIndex} of ${totalPages}`}\n aria-current={active ? \"page\" : false}\n onMouseOver={closeAllTooltips}\n onFocus={closeAllTooltips}\n >\n {pageIndex}\n </button>\n );\n }\n\n return null;\n });\n };\n\n const renderStartEllipsis = (pageIndex: number) => (\n <div key={pageIndex} className={styles.ellipsisContainer}>\n <ClickableIcon\n className={styles.iconButton}\n focusHighlight={false}\n focusOutline=\"browser\"\n aria-label={\"Previous 5 pages\"}\n onMouseEnter={onHoverLeftButton}\n onMouseLeave={onBlurLeftButton}\n onFocus={onHoverLeftButton}\n onBlur={onBlurLeftButton}\n onClick={handleFastBackwardClick}\n >\n {hoverLeftButton ? (\n <Chevron2LeftIcon aria-hidden />\n ) : (\n <EllipsisHorizontalIcon aria-hidden />\n )}\n </ClickableIcon>\n {hoverLeftButton && (\n <div className={styles.hover}>Previous 5 pages</div>\n )}\n </div>\n );\n\n const renderEndEllipsis = (pageIndex: number) => (\n <div key={pageIndex} className={styles.ellipsisContainer}>\n <ClickableIcon\n className={styles.iconButton}\n focusHighlight={false}\n focusOutline=\"browser\"\n aria-label={\"Next 5 pages\"}\n onMouseEnter={onHoverRightButton}\n onMouseLeave={onBlurRightButton}\n onFocus={onHoverRightButton}\n onBlur={onBlurRightButton}\n onClick={handleFastForwardClick}\n >\n {hoverRightButton ? (\n <Chevron2RightIcon aria-hidden />\n ) : (\n <EllipsisHorizontalIcon aria-hidden />\n )}\n </ClickableIcon>\n {hoverRightButton && (\n <div className={styles.hover}>Next 5 pages</div>\n )}\n </div>\n );\n\n const renderMobile = () => (\n <div className={styles.paginationMobileInput}>\n <form onSubmit={handleInputSubmit}>\n <Input\n className={styles.inputView}\n value={inputText}\n onChange={handleInput}\n autoComplete=\"off\"\n type=\"numeric\"\n id={(id || \"pagination\") + \"-input\"}\n data-testid={(dataTestId || \"pagination\") + \"-input\"}\n aria-label={`Page ${activePage} of ${totalPages}`}\n />\n </form>\n <Typography.BodyBL className={styles.labelDivider}>\n /\n </Typography.BodyBL>\n <Typography.BodyBL className={styles.label}>\n {totalPages}\n </Typography.BodyBL>\n </div>\n );\n\n return (\n <nav\n className={clsx(styles.paginationWrapper, className)}\n ref={ref}\n id={id || \"pagination-wrapper\"}\n data-testid={dataTestId || \"pagination\"}\n aria-labelledby={paginationId}\n >\n <VisuallyHidden id={paginationId} aria-hidden>\n pagination\n </VisuallyHidden>\n <div className={styles.paginationList}>\n <div className={styles.paginationMenu}>\n {showFirstAndLastNav && (\n <ClickableIcon\n className={clsx(\n styles.iconButton,\n styles.iconButtonNavigation\n )}\n onClick={firstPaginationItem}\n disabled={isFirstPage}\n focusHighlight={false}\n aria-label=\"First page\"\n focusOutline=\"browser\"\n >\n <ChevronLineLeftIcon aria-hidden />\n </ClickableIcon>\n )}\n <ClickableIcon\n className={clsx(\n styles.iconButton,\n styles.iconButtonNavigation\n )}\n onClick={prevPaginationItem}\n disabled={isFirstPage}\n focusHighlight={false}\n aria-label=\"Previous page\"\n focusOutline=\"browser\"\n >\n <ChevronLeftIcon aria-hidden />\n </ClickableIcon>\n {isMounted && isMobile\n ? renderMobile()\n : renderPaginationItems()}\n <ClickableIcon\n className={clsx(\n styles.iconButton,\n styles.iconButtonNavigation\n )}\n onClick={nextPaginationItem}\n disabled={isLastPage}\n focusHighlight={false}\n aria-label=\"Next page\"\n focusOutline=\"browser\"\n >\n <ChevronRightIcon aria-hidden />\n </ClickableIcon>\n {showFirstAndLastNav && (\n <ClickableIcon\n className={clsx(\n styles.iconButton,\n styles.iconButtonNavigation\n )}\n onClick={lastPaginationItem}\n disabled={isLastPage}\n focusHighlight={false}\n aria-label=\"Last page\"\n focusOutline=\"browser\"\n >\n <ChevronLineRightIcon aria-hidden />\n </ClickableIcon>\n )}\n </div>\n </div>\n {showPageSizeChanger && !isMobile && (\n <div className={styles.inputSelectWrapper}>\n <VisuallyHidden id={`${paginationId}-page-size`}>\n Items per page\n </VisuallyHidden>\n <InputSelect\n aria-labelledby={`${paginationId}-page-size`}\n options={pageSizeOptions}\n valueExtractor={(item) => item.value}\n listExtractor={(item) => item.label}\n displayValueExtractor={(item) => item.label}\n selectedOption={selectedOption}\n onSelectOption={handleListItemClick}\n />\n </div>\n )}\n </nav>\n );\n};\n/**\n * A navigation control for moving through paged content.\n *\n * Use `Pagination` to let users navigate between pages of a data set.\n */\nexport const Pagination = React.forwardRef(Component);\n\nconst DEFAULT_OPTIONS: PageSizeItemProps[] = [\n { value: 10, label: \"10 per page\" },\n { value: 20, label: \"20 per page\" },\n { value: 30, label: \"30 per page\" },\n];\n"],"names":["Pagination","React","forwardRef","id","dataTestId","className","pageSize","totalItems","activePage","pageSizeOptions","DEFAULT_OPTIONS","showFirstAndLastNav","showPageSizeChanger","onPageChange","onPageSizeChange","ref","isMounted","useIsMounted","isMobile","useMaxWidthMediaQuery","hoverRightButton","setHoverRightButton","useState","hoverLeftButton","setHoverLeftButton","inputText","setInputText","selectedOption","setSelectedOption","pageSizeLocal","setPageSize","value","paginationId","useId","totalPages","Math","ceil","isFirstPage","isLastPage","firstPaginationItem","handlePaginationItemClick","undefined","lastPaginationItem","prevPaginationItem","nextPaginationItem","parseInt","toString","useEffect","setInputValue","find","option","closeAllTooltips","pageIndex","handleFastForwardClick","currentIndex","min","handleFastBackwardClick","max","handleInput","event","target","length","test","newPage","replace","handleInputSubmit","preventDefault","onHoverRightButton","onBlurRightButton","onHoverLeftButton","onBlurLeftButton","renderStartEllipsis","_jsxs","styles.ellipsisContainer","children","_jsx","ClickableIcon","styles.iconButton","focusHighlight","focusOutline","onMouseEnter","onMouseLeave","onFocus","onBlur","onClick","Chevron2LeftIcon","EllipsisHorizontalIcon","styles.hover","renderEndEllipsis","Chevron2RightIcon","clsx","styles.paginationWrapper","VisuallyHidden","styles.paginationList","styles.paginationMenu","styles.iconButtonNavigation","disabled","ChevronLineLeftIcon","ChevronLeftIcon","styles.paginationMobileInput","onSubmit","Input","styles.inputView","onChange","autoComplete","type","Typography","BodyBL","styles.labelDivider","styles.label","Array","map","e","i","endRange","boundaryRange","active","styles.pageItem","styles.pageItemSelected","onMouseOver","ChevronRightIcon","ChevronLineRightIcon","styles.inputSelectWrapper","InputSelect","options","valueExtractor","item","listExtractor","label","displayValueExtractor","onSelectOption","pagesize","totalPage"],"mappings":"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"}
1
+ {"version":3,"file":"pagination.js","sources":["../../src/pagination/pagination.tsx"],"sourcesContent":["import { Chevron2LeftIcon } from \"@lifesg/react-icons/chevron-2-left\";\nimport { Chevron2RightIcon } from \"@lifesg/react-icons/chevron-2-right\";\nimport { ChevronLeftIcon } from \"@lifesg/react-icons/chevron-left\";\nimport { ChevronLineLeftIcon } from \"@lifesg/react-icons/chevron-line-left\";\nimport { ChevronLineRightIcon } from \"@lifesg/react-icons/chevron-line-right\";\nimport { ChevronRightIcon } from \"@lifesg/react-icons/chevron-right\";\nimport { EllipsisHorizontalIcon } from \"@lifesg/react-icons/ellipsis-horizontal\";\nimport clsx from \"clsx\";\nimport React, { useEffect, useState } from \"react\";\n\nimport { Input } from \"../input\";\nimport { InputSelect } from \"../input-select\";\nimport { VisuallyHidden } from \"../shared/accessibility\";\nimport { ClickableIcon } from \"../shared/clickable-icon\";\nimport { useMaxWidthMediaQuery } from \"../theme\";\nimport { Typography } from \"../typography\";\nimport { useId, useIsMounted } from \"../util\";\nimport * as styles from \"./pagination.styles\";\nimport type { PageSizeItemProps, PaginationProps } from \"./types\";\n\nconst Component = (\n {\n id,\n \"data-testid\": dataTestId,\n className,\n pageSize = 10,\n totalItems,\n activePage,\n pageSizeOptions = DEFAULT_OPTIONS,\n showFirstAndLastNav,\n showPageSizeChanger = false,\n onPageChange,\n onPageSizeChange,\n }: PaginationProps,\n ref: React.Ref<HTMLDivElement>\n) => {\n // =============================================================================\n // CONST, STATE, REF\n // =============================================================================\n\n const isMounted = useIsMounted();\n const isMobile = useMaxWidthMediaQuery(\"sm\");\n const [hoverRightButton, setHoverRightButton] = useState(false);\n const [hoverLeftButton, setHoverLeftButton] = useState(false);\n const [inputText, setInputText] = useState<string>(\"\");\n\n const [selectedOption, setSelectedOption] = useState<\n PageSizeItemProps | undefined\n >(pageSizeOptions[0]);\n const [pageSizeLocal, setPageSize] = useState<number>(\n !isMobile && showPageSizeChanger\n ? selectedOption\n ? selectedOption.value\n : pageSize\n : pageSize\n );\n\n const boundaryRange = 1;\n const siblingRange = 1;\n\n const internalId = useId();\n const paginationId = `${internalId}-pagination`;\n\n const totalPages = Math.ceil(totalItems / pageSizeLocal);\n const isFirstPage = activePage === 1;\n const isLastPage = activePage === totalPages;\n\n const firstPaginationItem =\n activePage > 1 ? () => handlePaginationItemClick(1) : undefined;\n const lastPaginationItem =\n activePage < totalPages\n ? () => handlePaginationItemClick(totalPages)\n : undefined;\n const prevPaginationItem =\n activePage > 1\n ? () => handlePaginationItemClick(activePage - 1)\n : undefined;\n const nextPaginationItem =\n activePage < totalPages\n ? () =>\n handlePaginationItemClick(parseInt(activePage.toString()) + 1)\n : undefined;\n\n // =============================================================================\n // EFFECTS\n // =============================================================================\n useEffect(() => {\n if (activePage) {\n setInputValue(activePage);\n }\n }, [activePage]);\n\n useEffect(() => {\n setPageSize(pageSize);\n setSelectedOption(\n pageSizeOptions.find((option) => option.value === pageSize)\n );\n }, [pageSize]);\n\n // =============================================================================\n // HELPER FUNCTIONS\n // =============================================================================\n const setInputValue = (value: number) => {\n setInputText(value.toString());\n };\n\n const closeAllTooltips = () => {\n setHoverRightButton(false);\n setHoverLeftButton(false);\n };\n\n // =============================================================================\n // EVENT HANDLERS\n // =============================================================================\n const handlePaginationItemClick = (pageIndex: number) => {\n if (onPageChange) {\n onPageChange(pageIndex);\n setInputValue(pageIndex);\n }\n };\n\n const handleFastForwardClick = () => {\n const currentIndex = Math.min(totalPages, activePage + 5);\n handlePaginationItemClick(currentIndex);\n setInputValue(currentIndex);\n setHoverRightButton(true);\n setHoverLeftButton(false);\n };\n\n const handleFastBackwardClick = () => {\n const currentIndex = Math.max(1, activePage - 5);\n handlePaginationItemClick(currentIndex);\n setInputValue(currentIndex);\n setHoverRightButton(false);\n setHoverLeftButton(true);\n };\n\n const handleInput = (event: React.ChangeEvent<HTMLInputElement>) => {\n const value = event.target.value;\n const numericRegex = /^[0-9]+$/;\n if (value === undefined || value.length === 0) {\n setInputText(\"\");\n } else if (!numericRegex.test(value)) {\n setInputText(value.replace(/[^0-9]/g, \"\"));\n } else {\n const newPage = parseInt(value.replace(/[^0-9]/g, \"\"));\n setInputValue(Math.max(1, Math.min(totalPages, newPage)));\n }\n };\n\n const handleInputSubmit = (event: React.FormEvent) => {\n event.preventDefault();\n if (inputText) {\n onPageChange?.(parseInt(inputText));\n }\n };\n\n const onHoverRightButton = () => {\n setHoverRightButton(true);\n };\n\n const onBlurRightButton = () => {\n setHoverRightButton(false);\n };\n\n const onHoverLeftButton = () => {\n setHoverLeftButton(true);\n };\n\n const onBlurLeftButton = () => {\n setHoverLeftButton(false);\n };\n\n const handleListItemClick = (item: PageSizeItemProps) => {\n setSelectedOption(item);\n const pagesize = item.value;\n const totalPage = Math.ceil(totalItems / pagesize);\n\n setPageSize(pagesize);\n\n const page = activePage >= totalPage ? totalPage : activePage;\n\n if (onPageSizeChange) {\n onPageSizeChange(page, pagesize);\n }\n };\n\n // =============================================================================\n // RENDER FUNCTIONS\n // =============================================================================\n const renderPaginationItems = () => {\n return [...Array(totalPages)].map((e, i) => {\n const pageIndex = i + 1;\n const startRange = boundaryRange + 2 + siblingRange * 2;\n const endRange = totalPages - startRange;\n const totalRange = (boundaryRange + siblingRange) * 2 + 3;\n const active = activePage === pageIndex;\n if (totalPages <= totalRange) {\n return (\n <button\n key={pageIndex}\n onClick={() => handlePaginationItemClick(pageIndex)}\n className={clsx(\n styles.pageItem,\n active && styles.pageItemSelected\n )}\n aria-label={`page ${pageIndex} of ${totalPages}`}\n aria-current={active ? \"page\" : false}\n onMouseOver={closeAllTooltips}\n onFocus={closeAllTooltips}\n >\n {pageIndex}\n </button>\n );\n }\n\n const ellipsisStart =\n activePage + siblingRange > startRange &&\n pageIndex === boundaryRange + 1;\n if (ellipsisStart) {\n return renderStartEllipsis(pageIndex);\n }\n\n const ellipsisEnd =\n activePage - siblingRange <= endRange &&\n pageIndex === totalPages - boundaryRange - 1;\n if (ellipsisEnd) {\n return renderEndEllipsis(pageIndex);\n }\n\n const paginationStart =\n (pageIndex <= startRange &&\n activePage + siblingRange <= startRange) ||\n pageIndex <= boundaryRange;\n const paginationMiddle =\n pageIndex === activePage ||\n (pageIndex <= activePage + siblingRange &&\n pageIndex >= activePage - siblingRange - 1);\n const paginationEnd =\n (pageIndex > endRange &&\n activePage - siblingRange > endRange) ||\n pageIndex > totalPages - boundaryRange;\n if (paginationStart || paginationMiddle || paginationEnd) {\n return (\n <button\n key={pageIndex}\n onClick={() => handlePaginationItemClick(pageIndex)}\n className={clsx(\n styles.pageItem,\n active && styles.pageItemSelected\n )}\n aria-label={`page ${pageIndex} of ${totalPages}`}\n aria-current={active ? \"page\" : false}\n onMouseOver={closeAllTooltips}\n onFocus={closeAllTooltips}\n >\n {pageIndex}\n </button>\n );\n }\n\n return null;\n });\n };\n\n const renderStartEllipsis = (pageIndex: number) => (\n <div key={pageIndex} className={styles.ellipsisContainer}>\n <ClickableIcon\n className={styles.iconButton}\n focusHighlight={false}\n focusOutline=\"browser\"\n aria-label={\"Previous 5 pages\"}\n onMouseEnter={onHoverLeftButton}\n onMouseLeave={onBlurLeftButton}\n onFocus={onHoverLeftButton}\n onBlur={onBlurLeftButton}\n onClick={handleFastBackwardClick}\n >\n {hoverLeftButton ? (\n <Chevron2LeftIcon aria-hidden />\n ) : (\n <EllipsisHorizontalIcon aria-hidden />\n )}\n </ClickableIcon>\n {hoverLeftButton && (\n <div className={styles.hover}>Previous 5 pages</div>\n )}\n </div>\n );\n\n const renderEndEllipsis = (pageIndex: number) => (\n <div key={pageIndex} className={styles.ellipsisContainer}>\n <ClickableIcon\n className={styles.iconButton}\n focusHighlight={false}\n focusOutline=\"browser\"\n aria-label={\"Next 5 pages\"}\n onMouseEnter={onHoverRightButton}\n onMouseLeave={onBlurRightButton}\n onFocus={onHoverRightButton}\n onBlur={onBlurRightButton}\n onClick={handleFastForwardClick}\n >\n {hoverRightButton ? (\n <Chevron2RightIcon aria-hidden />\n ) : (\n <EllipsisHorizontalIcon aria-hidden />\n )}\n </ClickableIcon>\n {hoverRightButton && (\n <div className={styles.hover}>Next 5 pages</div>\n )}\n </div>\n );\n\n const renderMobile = () => (\n <div className={styles.paginationMobileInput}>\n <form onSubmit={handleInputSubmit}>\n <Input\n className={styles.inputView}\n value={inputText}\n onChange={handleInput}\n autoComplete=\"off\"\n type=\"numeric\"\n id={(id || \"pagination\") + \"-input\"}\n data-testid={(dataTestId || \"pagination\") + \"-input\"}\n aria-label={`Page ${activePage} of ${totalPages}`}\n />\n </form>\n <Typography.BodyBL className={styles.labelDivider}>\n /\n </Typography.BodyBL>\n <Typography.BodyBL className={styles.label}>\n {totalPages}\n </Typography.BodyBL>\n </div>\n );\n\n return (\n <nav\n className={clsx(styles.paginationWrapper, className)}\n ref={ref}\n id={id || \"pagination-wrapper\"}\n data-testid={dataTestId || \"pagination\"}\n aria-labelledby={paginationId}\n >\n <VisuallyHidden id={paginationId} aria-hidden>\n pagination\n </VisuallyHidden>\n <div className={styles.paginationList}>\n <div className={styles.paginationMenu}>\n {showFirstAndLastNav && (\n <ClickableIcon\n className={clsx(\n styles.iconButton,\n styles.iconButtonNavigation\n )}\n onClick={firstPaginationItem}\n disabled={isFirstPage}\n focusHighlight={false}\n aria-label=\"First page\"\n focusOutline=\"browser\"\n >\n <ChevronLineLeftIcon aria-hidden />\n </ClickableIcon>\n )}\n <ClickableIcon\n className={clsx(\n styles.iconButton,\n styles.iconButtonNavigation\n )}\n onClick={prevPaginationItem}\n disabled={isFirstPage}\n focusHighlight={false}\n aria-label=\"Previous page\"\n focusOutline=\"browser\"\n >\n <ChevronLeftIcon aria-hidden />\n </ClickableIcon>\n {isMounted && isMobile\n ? renderMobile()\n : renderPaginationItems()}\n <ClickableIcon\n className={clsx(\n styles.iconButton,\n styles.iconButtonNavigation\n )}\n onClick={nextPaginationItem}\n disabled={isLastPage}\n focusHighlight={false}\n aria-label=\"Next page\"\n focusOutline=\"browser\"\n >\n <ChevronRightIcon aria-hidden />\n </ClickableIcon>\n {showFirstAndLastNav && (\n <ClickableIcon\n className={clsx(\n styles.iconButton,\n styles.iconButtonNavigation\n )}\n onClick={lastPaginationItem}\n disabled={isLastPage}\n focusHighlight={false}\n aria-label=\"Last page\"\n focusOutline=\"browser\"\n >\n <ChevronLineRightIcon aria-hidden />\n </ClickableIcon>\n )}\n </div>\n </div>\n {showPageSizeChanger && !isMobile && (\n <div className={styles.inputSelectWrapper}>\n <VisuallyHidden id={`${paginationId}-page-size`}>\n Items per page\n </VisuallyHidden>\n <InputSelect\n aria-labelledby={`${paginationId}-page-size`}\n options={pageSizeOptions}\n valueExtractor={(item) => item.value}\n listExtractor={(item) => item.label}\n displayValueExtractor={(item) => item.label}\n selectedOption={selectedOption}\n onSelectOption={handleListItemClick}\n />\n </div>\n )}\n </nav>\n );\n};\n// @catalog\n/**\n * A navigation control for moving through paged content.\n *\n * Use `Pagination` to let users navigate between pages of a data set.\n */\nexport const Pagination = React.forwardRef(Component);\n\nconst DEFAULT_OPTIONS: PageSizeItemProps[] = [\n { value: 10, label: \"10 per page\" },\n { value: 20, label: \"20 per page\" },\n { value: 30, label: \"30 per page\" },\n];\n"],"names":["Pagination","React","forwardRef","id","dataTestId","className","pageSize","totalItems","activePage","pageSizeOptions","DEFAULT_OPTIONS","showFirstAndLastNav","showPageSizeChanger","onPageChange","onPageSizeChange","ref","isMounted","useIsMounted","isMobile","useMaxWidthMediaQuery","hoverRightButton","setHoverRightButton","useState","hoverLeftButton","setHoverLeftButton","inputText","setInputText","selectedOption","setSelectedOption","pageSizeLocal","setPageSize","value","paginationId","useId","totalPages","Math","ceil","isFirstPage","isLastPage","firstPaginationItem","handlePaginationItemClick","undefined","lastPaginationItem","prevPaginationItem","nextPaginationItem","parseInt","toString","useEffect","setInputValue","find","option","closeAllTooltips","pageIndex","handleFastForwardClick","currentIndex","min","handleFastBackwardClick","max","handleInput","event","target","length","test","newPage","replace","handleInputSubmit","preventDefault","onHoverRightButton","onBlurRightButton","onHoverLeftButton","onBlurLeftButton","renderStartEllipsis","_jsxs","styles.ellipsisContainer","children","_jsx","ClickableIcon","styles.iconButton","focusHighlight","focusOutline","onMouseEnter","onMouseLeave","onFocus","onBlur","onClick","Chevron2LeftIcon","EllipsisHorizontalIcon","styles.hover","renderEndEllipsis","Chevron2RightIcon","clsx","styles.paginationWrapper","VisuallyHidden","styles.paginationList","styles.paginationMenu","styles.iconButtonNavigation","disabled","ChevronLineLeftIcon","ChevronLeftIcon","styles.paginationMobileInput","onSubmit","Input","styles.inputView","onChange","autoComplete","type","Typography","BodyBL","styles.labelDivider","styles.label","Array","map","e","i","endRange","boundaryRange","active","styles.pageItem","styles.pageItemSelected","onMouseOver","ChevronRightIcon","ChevronLineRightIcon","styles.inputSelectWrapper","InputSelect","options","valueExtractor","item","listExtractor","label","displayValueExtractor","onSelectOption","pagesize","totalPage"],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"phone-number-input.js","sources":["../../src/phone-number-input/phone-number-input.tsx"],"sourcesContent":["import { useEffect, useRef, useState } from \"react\";\n\nimport { InputGroup } from \"../input-group/input-group\";\nimport type { AddonProps, LabelAddon, ListAddon } from \"../input-group/types\";\nimport { useNextInputState } from \"../util\";\nimport { PhoneNumberInputHelper } from \"./phone-number-input-helper\";\nimport type { CountryValue, PhoneNumberInputProps } from \"./types\";\n\n/**\n * A phone number field composed of a country code selector and a number input.\n *\n * Use `PhoneNumberInput` when collecting an internationalised phone number.\n * The country code can be selected from a searchable dropdown or locked to a\n * fixed value via `fixedCountry`.\n */\nexport const PhoneNumberInput = ({\n id,\n onChange,\n value,\n allowClear,\n onClear,\n onBlur,\n error,\n fixedCountry = false,\n optionPlaceholder = \"Select\",\n optionSearchPlaceholder,\n enableSearch,\n onHideOptions,\n onShowOptions,\n placeholder,\n autoComplete,\n noBorder = false,\n getAriaLabel,\n ...otherProps\n}: PhoneNumberInputProps) => {\n // =============================================================================\n // CONST, STATE, REF\n // =============================================================================\n const [options] = useState<CountryValue[]>(\n PhoneNumberInputHelper.getCountries()\n );\n\n const [selectedCountry, setSelectedCountry] = useState<\n CountryValue | undefined\n >(undefined);\n const [inputValue, setInputValue] = useState<string>(\"\");\n\n const nodeRef = useRef<HTMLInputElement>(null);\n\n const getNextInputState = useNextInputState({\n ref: nodeRef,\n formatter: (value) =>\n PhoneNumberInputHelper.formatNumber(\n value.replace(/[^0-9]/g, \"\"),\n selectedCountry\n ),\n });\n\n const resolvedAriaLabel =\n getAriaLabel?.(selectedCountry) ?? \"Enter phone number\";\n\n // =============================================================================\n // EFFECTS\n // =============================================================================\n useEffect(() => {\n const selectedOption = options.filter(\n (country) =>\n country.countryCode === normaliseCountryCode(value?.countryCode)\n )[0];\n\n setSelectedCountry(selectedOption);\n setInputValue(\n PhoneNumberInputHelper.formatNumber(value?.number, selectedOption)\n );\n }, [value]);\n\n // =============================================================================\n // EVENT HANDLERS\n // =============================================================================\n const handleClear = () => {\n if (onClear) {\n onClear();\n } else {\n setInputValue(\"\");\n }\n };\n\n const handleInputChange = () => {\n const nextState = getNextInputState();\n if (!nextState) return;\n\n const { nextValue, updateCaretPosition } = nextState;\n\n updateCaretPosition();\n performLocalChangeHandler(nextValue, selectedCountry);\n if (onChange) {\n performOnChangeHandler(nextValue, selectedCountry);\n }\n };\n\n const handleSelectOption = (country: CountryValue) => {\n performLocalChangeHandler(inputValue, country);\n if (onChange) {\n performOnChangeHandler(inputValue, country);\n }\n };\n\n // =============================================================================\n // HELPER FUNCTIONS\n // =============================================================================\n const performOnChangeHandler = (\n inputValue: string,\n selectedCountry: CountryValue | undefined\n ) => {\n const formatedInputValue = PhoneNumberInputHelper.formatNumber(\n inputValue,\n selectedCountry\n );\n onChange?.({\n number: formatedInputValue.replace(/[\\s()]+/g, \"\"), // strip formatted spaces\n countryCode:\n selectedCountry && addPlusPrefix(selectedCountry.countryCode),\n });\n };\n\n const performLocalChangeHandler = (\n inputValue: string,\n selectedCountry: CountryValue | undefined\n ) => {\n setInputValue(\n PhoneNumberInputHelper.formatNumber(inputValue, selectedCountry)\n );\n\n setSelectedCountry(selectedCountry);\n };\n\n const getAddonProps = (): AddonProps<CountryValue, string> => {\n if (fixedCountry) {\n return {\n type: \"label\",\n attributes: {\n value: addPlusPrefix(selectedCountry?.countryCode),\n } as LabelAddon,\n };\n } else {\n return {\n type: \"list\",\n attributes: {\n \"aria-label\": \"Country code\",\n placeholder: optionPlaceholder,\n options,\n selectedOption: selectedCountry,\n enableSearch: enableSearch,\n searchPlaceholder: optionSearchPlaceholder,\n valueExtractor: (option) => `+${option.countryCode}`,\n listExtractor: (option) => ({\n title: option.name,\n secondaryLabel: addPlusPrefix(option.countryCode),\n }),\n onSelectOption: handleSelectOption,\n onHideOptions: onHideOptions,\n onShowOptions: onShowOptions,\n } as ListAddon<CountryValue, string>,\n };\n }\n };\n\n // =========================================================================\n // RENDER FUNCTIONS\n // =========================================================================\n return (\n <InputGroup\n id={id}\n ref={nodeRef}\n value={inputValue}\n onChange={handleInputChange}\n allowClear={allowClear && !!inputValue}\n onClear={handleClear}\n onBlur={onBlur}\n error={error}\n placeholder={placeholder}\n addon={getAddonProps()}\n inputMode=\"numeric\"\n autoComplete={autoComplete}\n noBorder={noBorder}\n aria-label={resolvedAriaLabel}\n {...otherProps}\n />\n );\n};\n\n// =============================================================================\n// HELPER FUNCTIONS\n// =============================================================================\n/**\n * This strips the + off the specified country code if it\n * is present.\n */\nconst normaliseCountryCode = (countryCode: string | undefined): string => {\n return countryCode ? countryCode.replace(\"+\", \"\") : \"\";\n};\n\nconst addPlusPrefix = (countryCode?: string): string => {\n if (!countryCode) return \"\";\n return countryCode.includes(\"+\") ? countryCode : `+${countryCode}`;\n};\n"],"names":["PhoneNumberInput","_a","id","onChange","value","allowClear","onClear","onBlur","error","fixedCountry","optionPlaceholder","optionSearchPlaceholder","enableSearch","onHideOptions","onShowOptions","placeholder","autoComplete","noBorder","getAriaLabel","otherProps","__rest","options","useState","PhoneNumberInputHelper","getCountries","selectedCountry","setSelectedCountry","undefined","inputValue","setInputValue","nodeRef","useRef","getNextInputState","useNextInputState","ref","formatter","formatNumber","replace","resolvedAriaLabel","_b","useEffect","selectedOption","filter","country","countryCode","normaliseCountryCode","number","handleSelectOption","performLocalChangeHandler","performOnChangeHandler","formatedInputValue","addPlusPrefix","_jsx","InputGroup","Object","assign","nextState","nextValue","updateCaretPosition","addon","type","attributes","searchPlaceholder","valueExtractor","option","listExtractor","title","name","secondaryLabel","onSelectOption","inputMode","includes"],"mappings":"+gBAeO,MAAMA,EAAoBC,WAAAC,GAC7BA,EAAEC,SACFA,EAAQC,MACRA,EAAKC,WACLA,EAAUC,QACVA,EAAOC,OACPA,EAAMC,MACNA,EAAKC,aACLA,GAAe,EAAKC,kBACpBA,EAAoB,SAAQC,wBAC5BA,EAAuBC,aACvBA,EAAYC,cACZA,EAAaC,cACbA,EAAaC,YACbA,EAAWC,aACXA,EAAYC,SACZA,GAAW,EAAKC,aAChBA,GAAYjB,EACTkB,EAAUC,EAAAnB,EAlBgB,sOAuB7B,MAAOoB,GAAWC,EACdC,EAAuBC,iBAGpBC,EAAiBC,GAAsBJ,OAE5CK,IACKC,EAAYC,GAAiBP,EAAiB,IAE/CQ,EAAUC,EAAyB,MAEnCC,EAAoBC,EAAkB,CACxCC,IAAKJ,EACLK,UAAY/B,GACRmB,EAAuBa,aACnBhC,EAAMiC,QAAQ,UAAW,IACzBZ,KAINa,EAC6B,QAA/BC,EAAArB,aAAY,EAAZA,EAAeO,UAAgB,IAAAc,EAAAA,EAAI,qBAKvCC,GAAU,KACN,MAAMC,EAAiBpB,EAAQqB,QAC1BC,GACGA,EAAQC,cAAgBC,EAAqBzC,aAAK,EAALA,EAAOwC,eAC1D,GAEFlB,EAAmBe,GACnBZ,EACIN,EAAuBa,aAAahC,aAAK,EAALA,EAAO0C,OAAQL,GACtD,GACF,CAACrC,IAKJ,MAqBM2C,EAAsBJ,IACxBK,EAA0BpB,EAAYe,GAClCxC,GACA8C,EAAuBrB,EAAYe,EACvC,EAMEM,EAAyB,CAC3BrB,EACAH,KAEA,MAAMyB,EAAqB3B,EAAuBa,aAC9CR,EACAH,GAEJtB,SAAAA,EAAW,CACP2C,OAAQI,EAAmBb,QAAQ,WAAY,IAC/CO,YACInB,GAAmB0B,EAAc1B,EAAgBmB,cACvD,EAGAI,EAA4B,CAC9BpB,EACAH,KAEAI,EACIN,EAAuBa,aAAaR,EAAYH,IAGpDC,EAAmBD,EAAgB,EAqCvC,OACI2B,EAACC,EAAUC,OAAAC,OAAA,CACPrD,GAAIA,EACJgC,IAAKJ,EACL1B,MAAOwB,EACPzB,SAxFkB,KACtB,MAAMqD,EAAYxB,IAClB,IAAKwB,EAAW,OAEhB,MAAMC,UAAEA,EAASC,oBAAEA,GAAwBF,EAE3CE,IACAV,EAA0BS,EAAWhC,GACjCtB,GACA8C,EAAuBQ,EAAWhC,EACtC,EA+EIpB,WAAYA,KAAgBuB,EAC5BtB,QAlGY,KACZA,EACAA,IAEAuB,EAAc,GAClB,EA8FItB,OAAQA,EACRC,MAAOA,EACPO,YAAaA,EACb4C,MA5CAlD,EACO,CACHmD,KAAM,QACNC,WAAY,CACRzD,MAAO+C,EAAc1B,aAAe,EAAfA,EAAiBmB,eAIvC,CACHgB,KAAM,OACNC,WAAY,CACR,aAAc,eACd9C,YAAaL,EACbW,UACAoB,eAAgBhB,EAChBb,aAAcA,EACdkD,kBAAmBnD,EACnBoD,eAAiBC,GAAW,IAAIA,EAAOpB,cACvCqB,cAAgBD,IAAM,CAClBE,MAAOF,EAAOG,KACdC,eAAgBjB,EAAca,EAAOpB,eAEzCyB,eAAgBtB,EAChBlC,cAAeA,EACfC,cAAeA,IAqBvBwD,UAAU,UACVtD,aAAcA,EACdC,SAAUA,EAAQ,aACNqB,GACRnB,GACN,EAWJ0B,EAAwBD,GACnBA,EAAcA,EAAYP,QAAQ,IAAK,IAAM,GAGlDc,EAAiBP,GACdA,EACEA,EAAY2B,SAAS,KAAO3B,EAAc,IAAIA,IAD5B"}
1
+ {"version":3,"file":"phone-number-input.js","sources":["../../src/phone-number-input/phone-number-input.tsx"],"sourcesContent":["import { useEffect, useRef, useState } from \"react\";\n\nimport { InputGroup } from \"../input-group/input-group\";\nimport type { AddonProps, LabelAddon, ListAddon } from \"../input-group/types\";\nimport { useNextInputState } from \"../util\";\nimport { PhoneNumberInputHelper } from \"./phone-number-input-helper\";\nimport type { CountryValue, PhoneNumberInputProps } from \"./types\";\n\n// @catalog\n/**\n * A phone number field composed of a country code selector and a number input.\n *\n * Use `PhoneNumberInput` when collecting an internationalised phone number.\n * The country code can be selected from a searchable dropdown or locked to a\n * fixed value via `fixedCountry`.\n */\nexport const PhoneNumberInput = ({\n id,\n onChange,\n value,\n allowClear,\n onClear,\n onBlur,\n error,\n fixedCountry = false,\n optionPlaceholder = \"Select\",\n optionSearchPlaceholder,\n enableSearch,\n onHideOptions,\n onShowOptions,\n placeholder,\n autoComplete,\n noBorder = false,\n getAriaLabel,\n ...otherProps\n}: PhoneNumberInputProps) => {\n // =============================================================================\n // CONST, STATE, REF\n // =============================================================================\n const [options] = useState<CountryValue[]>(\n PhoneNumberInputHelper.getCountries()\n );\n\n const [selectedCountry, setSelectedCountry] = useState<\n CountryValue | undefined\n >(undefined);\n const [inputValue, setInputValue] = useState<string>(\"\");\n\n const nodeRef = useRef<HTMLInputElement>(null);\n\n const getNextInputState = useNextInputState({\n ref: nodeRef,\n formatter: (value) =>\n PhoneNumberInputHelper.formatNumber(\n value.replace(/[^0-9]/g, \"\"),\n selectedCountry\n ),\n });\n\n const resolvedAriaLabel =\n getAriaLabel?.(selectedCountry) ?? \"Enter phone number\";\n\n // =============================================================================\n // EFFECTS\n // =============================================================================\n useEffect(() => {\n const selectedOption = options.filter(\n (country) =>\n country.countryCode === normaliseCountryCode(value?.countryCode)\n )[0];\n\n setSelectedCountry(selectedOption);\n setInputValue(\n PhoneNumberInputHelper.formatNumber(value?.number, selectedOption)\n );\n }, [value]);\n\n // =============================================================================\n // EVENT HANDLERS\n // =============================================================================\n const handleClear = () => {\n if (onClear) {\n onClear();\n } else {\n setInputValue(\"\");\n }\n };\n\n const handleInputChange = () => {\n const nextState = getNextInputState();\n if (!nextState) return;\n\n const { nextValue, updateCaretPosition } = nextState;\n\n updateCaretPosition();\n performLocalChangeHandler(nextValue, selectedCountry);\n if (onChange) {\n performOnChangeHandler(nextValue, selectedCountry);\n }\n };\n\n const handleSelectOption = (country: CountryValue) => {\n performLocalChangeHandler(inputValue, country);\n if (onChange) {\n performOnChangeHandler(inputValue, country);\n }\n };\n\n // =============================================================================\n // HELPER FUNCTIONS\n // =============================================================================\n const performOnChangeHandler = (\n inputValue: string,\n selectedCountry: CountryValue | undefined\n ) => {\n const formatedInputValue = PhoneNumberInputHelper.formatNumber(\n inputValue,\n selectedCountry\n );\n onChange?.({\n number: formatedInputValue.replace(/[\\s()]+/g, \"\"), // strip formatted spaces\n countryCode:\n selectedCountry && addPlusPrefix(selectedCountry.countryCode),\n });\n };\n\n const performLocalChangeHandler = (\n inputValue: string,\n selectedCountry: CountryValue | undefined\n ) => {\n setInputValue(\n PhoneNumberInputHelper.formatNumber(inputValue, selectedCountry)\n );\n\n setSelectedCountry(selectedCountry);\n };\n\n const getAddonProps = (): AddonProps<CountryValue, string> => {\n if (fixedCountry) {\n return {\n type: \"label\",\n attributes: {\n value: addPlusPrefix(selectedCountry?.countryCode),\n } as LabelAddon,\n };\n } else {\n return {\n type: \"list\",\n attributes: {\n \"aria-label\": \"Country code\",\n placeholder: optionPlaceholder,\n options,\n selectedOption: selectedCountry,\n enableSearch: enableSearch,\n searchPlaceholder: optionSearchPlaceholder,\n valueExtractor: (option) => `+${option.countryCode}`,\n listExtractor: (option) => ({\n title: option.name,\n secondaryLabel: addPlusPrefix(option.countryCode),\n }),\n onSelectOption: handleSelectOption,\n onHideOptions: onHideOptions,\n onShowOptions: onShowOptions,\n } as ListAddon<CountryValue, string>,\n };\n }\n };\n\n // =========================================================================\n // RENDER FUNCTIONS\n // =========================================================================\n return (\n <InputGroup\n id={id}\n ref={nodeRef}\n value={inputValue}\n onChange={handleInputChange}\n allowClear={allowClear && !!inputValue}\n onClear={handleClear}\n onBlur={onBlur}\n error={error}\n placeholder={placeholder}\n addon={getAddonProps()}\n inputMode=\"numeric\"\n autoComplete={autoComplete}\n noBorder={noBorder}\n aria-label={resolvedAriaLabel}\n {...otherProps}\n />\n );\n};\n\n// =============================================================================\n// HELPER FUNCTIONS\n// =============================================================================\n/**\n * This strips the + off the specified country code if it\n * is present.\n */\nconst normaliseCountryCode = (countryCode: string | undefined): string => {\n return countryCode ? countryCode.replace(\"+\", \"\") : \"\";\n};\n\nconst addPlusPrefix = (countryCode?: string): string => {\n if (!countryCode) return \"\";\n return countryCode.includes(\"+\") ? countryCode : `+${countryCode}`;\n};\n"],"names":["PhoneNumberInput","_a","id","onChange","value","allowClear","onClear","onBlur","error","fixedCountry","optionPlaceholder","optionSearchPlaceholder","enableSearch","onHideOptions","onShowOptions","placeholder","autoComplete","noBorder","getAriaLabel","otherProps","__rest","options","useState","PhoneNumberInputHelper","getCountries","selectedCountry","setSelectedCountry","undefined","inputValue","setInputValue","nodeRef","useRef","getNextInputState","useNextInputState","ref","formatter","formatNumber","replace","resolvedAriaLabel","_b","useEffect","selectedOption","filter","country","countryCode","normaliseCountryCode","number","handleSelectOption","performLocalChangeHandler","performOnChangeHandler","formatedInputValue","addPlusPrefix","_jsx","InputGroup","Object","assign","nextState","nextValue","updateCaretPosition","addon","type","attributes","searchPlaceholder","valueExtractor","option","listExtractor","title","name","secondaryLabel","onSelectOption","inputMode","includes"],"mappings":"+gBAgBO,MAAMA,EAAoBC,WAAAC,GAC7BA,EAAEC,SACFA,EAAQC,MACRA,EAAKC,WACLA,EAAUC,QACVA,EAAOC,OACPA,EAAMC,MACNA,EAAKC,aACLA,GAAe,EAAKC,kBACpBA,EAAoB,SAAQC,wBAC5BA,EAAuBC,aACvBA,EAAYC,cACZA,EAAaC,cACbA,EAAaC,YACbA,EAAWC,aACXA,EAAYC,SACZA,GAAW,EAAKC,aAChBA,GAAYjB,EACTkB,EAAUC,EAAAnB,EAlBgB,sOAuB7B,MAAOoB,GAAWC,EACdC,EAAuBC,iBAGpBC,EAAiBC,GAAsBJ,OAE5CK,IACKC,EAAYC,GAAiBP,EAAiB,IAE/CQ,EAAUC,EAAyB,MAEnCC,EAAoBC,EAAkB,CACxCC,IAAKJ,EACLK,UAAY/B,GACRmB,EAAuBa,aACnBhC,EAAMiC,QAAQ,UAAW,IACzBZ,KAINa,EAC6B,QAA/BC,EAAArB,aAAY,EAAZA,EAAeO,UAAgB,IAAAc,EAAAA,EAAI,qBAKvCC,GAAU,KACN,MAAMC,EAAiBpB,EAAQqB,QAC1BC,GACGA,EAAQC,cAAgBC,EAAqBzC,aAAK,EAALA,EAAOwC,eAC1D,GAEFlB,EAAmBe,GACnBZ,EACIN,EAAuBa,aAAahC,aAAK,EAALA,EAAO0C,OAAQL,GACtD,GACF,CAACrC,IAKJ,MAqBM2C,EAAsBJ,IACxBK,EAA0BpB,EAAYe,GAClCxC,GACA8C,EAAuBrB,EAAYe,EACvC,EAMEM,EAAyB,CAC3BrB,EACAH,KAEA,MAAMyB,EAAqB3B,EAAuBa,aAC9CR,EACAH,GAEJtB,SAAAA,EAAW,CACP2C,OAAQI,EAAmBb,QAAQ,WAAY,IAC/CO,YACInB,GAAmB0B,EAAc1B,EAAgBmB,cACvD,EAGAI,EAA4B,CAC9BpB,EACAH,KAEAI,EACIN,EAAuBa,aAAaR,EAAYH,IAGpDC,EAAmBD,EAAgB,EAqCvC,OACI2B,EAACC,EAAUC,OAAAC,OAAA,CACPrD,GAAIA,EACJgC,IAAKJ,EACL1B,MAAOwB,EACPzB,SAxFkB,KACtB,MAAMqD,EAAYxB,IAClB,IAAKwB,EAAW,OAEhB,MAAMC,UAAEA,EAASC,oBAAEA,GAAwBF,EAE3CE,IACAV,EAA0BS,EAAWhC,GACjCtB,GACA8C,EAAuBQ,EAAWhC,EACtC,EA+EIpB,WAAYA,KAAgBuB,EAC5BtB,QAlGY,KACZA,EACAA,IAEAuB,EAAc,GAClB,EA8FItB,OAAQA,EACRC,MAAOA,EACPO,YAAaA,EACb4C,MA5CAlD,EACO,CACHmD,KAAM,QACNC,WAAY,CACRzD,MAAO+C,EAAc1B,aAAe,EAAfA,EAAiBmB,eAIvC,CACHgB,KAAM,OACNC,WAAY,CACR,aAAc,eACd9C,YAAaL,EACbW,UACAoB,eAAgBhB,EAChBb,aAAcA,EACdkD,kBAAmBnD,EACnBoD,eAAiBC,GAAW,IAAIA,EAAOpB,cACvCqB,cAAgBD,IAAM,CAClBE,MAAOF,EAAOG,KACdC,eAAgBjB,EAAca,EAAOpB,eAEzCyB,eAAgBtB,EAChBlC,cAAeA,EACfC,cAAeA,IAqBvBwD,UAAU,UACVtD,aAAcA,EACdC,SAAUA,EAAQ,aACNqB,GACRnB,GACN,EAWJ0B,EAAwBD,GACnBA,EAAcA,EAAYP,QAAQ,IAAK,IAAM,GAGlDc,EAAiBP,GACdA,EACEA,EAAY2B,SAAS,KAAO3B,EAAc,IAAIA,IAD5B"}
package/pill/pill.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"pill.js","sources":["../../src/pill/pill.tsx"],"sourcesContent":["import clsx from \"clsx\";\nimport React from \"react\";\n\nimport * as styles from \"./pill.styles\";\nimport type { PillColorType, PillProps, PillType } from \"./types\";\n\nconst WRAPPER_CLASS: Record<PillType, Record<PillColorType, string>> = {\n solid: {\n black: styles.wrapperSolidBlack,\n grey: styles.wrapperSolidGrey,\n green: styles.wrapperSolidGreen,\n yellow: styles.wrapperSolidYellow,\n red: styles.wrapperSolidRed,\n blue: styles.wrapperSolidBlue,\n primary: styles.wrapperSolidPrimary,\n },\n outline: {\n black: styles.wrapperOutlineBlack,\n grey: styles.wrapperOutlineGrey,\n green: styles.wrapperOutlineGreen,\n yellow: styles.wrapperOutlineYellow,\n red: styles.wrapperOutlineRed,\n blue: styles.wrapperOutlineBlue,\n primary: styles.wrapperOutlinePrimary,\n },\n};\n\n/**\n * A compact label used to display status, category, or metadata.\n *\n * Use `Pill` to surface short, read-only information — such as a tag or status\n * badge — inline with other content.\n */\nexport const Pill = ({\n type,\n colorType = \"black\",\n children,\n icon,\n className,\n ...otherProps\n}: PillProps): JSX.Element => {\n return (\n <div\n {...otherProps}\n className={clsx(\n styles.wrapperBase,\n type === \"solid\" && styles.wrapperSolid,\n WRAPPER_CLASS[type][colorType],\n className\n )}\n >\n {icon && React.cloneElement(icon, { \"aria-hidden\": true })}\n <div className={styles.label}>{children}</div>\n </div>\n );\n};\n"],"names":["WRAPPER_CLASS","solid","black","styles.wrapperSolidBlack","grey","styles.wrapperSolidGrey","green","styles.wrapperSolidGreen","yellow","styles.wrapperSolidYellow","red","styles.wrapperSolidRed","blue","styles.wrapperSolidBlue","primary","styles.wrapperSolidPrimary","outline","styles.wrapperOutlineBlack","styles.wrapperOutlineGrey","styles.wrapperOutlineGreen","styles.wrapperOutlineYellow","styles.wrapperOutlineRed","styles.wrapperOutlineBlue","styles.wrapperOutlinePrimary","Pill","_a","type","colorType","children","icon","className","otherProps","__rest","_jsxs","Object","assign","clsx","styles.wrapperBase","styles.wrapperSolid","React","cloneElement","_jsx","styles.label"],"mappings":"oiBAMA,MAAMA,EAAiE,CACnEC,MAAO,CACHC,MAAOC,EACPC,KAAMC,EACNC,MAAOC,EACPC,OAAQC,EACRC,IAAKC,EACLC,KAAMC,EACNC,QAASC,GAEbC,QAAS,CACLd,MAAOe,EACPb,KAAMc,EACNZ,MAAOa,EACPX,OAAQY,EACRV,IAAKW,EACLT,KAAMU,EACNR,QAASS,IAUJC,EAAQC,IAAA,IAAAC,KACjBA,EAAIC,UACJA,EAAY,QAAOC,SACnBA,EAAQC,KACRA,EAAIC,UACJA,GAASL,EACNM,EAAUC,EAAAP,EANI,oDAQjB,OACIQ,EAAA,MAAAC,OAAAC,OAAA,GACQJ,EAAU,CACdD,UAAWM,EACPC,EACS,UAATX,GAAoBY,EACpBtC,EAAc0B,GAAMC,GACpBG,GACHF,SAAA,CAEAC,GAAQU,EAAMC,aAAaX,EAAM,CAAE,eAAe,IACnDY,EAAA,MAAA,CAAKX,UAAWY,EAAYd,SAAGA,OAC7B"}
1
+ {"version":3,"file":"pill.js","sources":["../../src/pill/pill.tsx"],"sourcesContent":["import clsx from \"clsx\";\nimport React from \"react\";\n\nimport * as styles from \"./pill.styles\";\nimport type { PillColorType, PillProps, PillType } from \"./types\";\n\nconst WRAPPER_CLASS: Record<PillType, Record<PillColorType, string>> = {\n solid: {\n black: styles.wrapperSolidBlack,\n grey: styles.wrapperSolidGrey,\n green: styles.wrapperSolidGreen,\n yellow: styles.wrapperSolidYellow,\n red: styles.wrapperSolidRed,\n blue: styles.wrapperSolidBlue,\n primary: styles.wrapperSolidPrimary,\n },\n outline: {\n black: styles.wrapperOutlineBlack,\n grey: styles.wrapperOutlineGrey,\n green: styles.wrapperOutlineGreen,\n yellow: styles.wrapperOutlineYellow,\n red: styles.wrapperOutlineRed,\n blue: styles.wrapperOutlineBlue,\n primary: styles.wrapperOutlinePrimary,\n },\n};\n\n// @catalog\n/**\n * A compact label used to display status, category, or metadata.\n *\n * Use `Pill` to surface short, read-only information — such as a tag or status\n * badge — inline with other content.\n */\nexport const Pill = ({\n type,\n colorType = \"black\",\n children,\n icon,\n className,\n ...otherProps\n}: PillProps): JSX.Element => {\n return (\n <div\n {...otherProps}\n className={clsx(\n styles.wrapperBase,\n type === \"solid\" && styles.wrapperSolid,\n WRAPPER_CLASS[type][colorType],\n className\n )}\n >\n {icon && React.cloneElement(icon, { \"aria-hidden\": true })}\n <div className={styles.label}>{children}</div>\n </div>\n );\n};\n"],"names":["WRAPPER_CLASS","solid","black","styles.wrapperSolidBlack","grey","styles.wrapperSolidGrey","green","styles.wrapperSolidGreen","yellow","styles.wrapperSolidYellow","red","styles.wrapperSolidRed","blue","styles.wrapperSolidBlue","primary","styles.wrapperSolidPrimary","outline","styles.wrapperOutlineBlack","styles.wrapperOutlineGrey","styles.wrapperOutlineGreen","styles.wrapperOutlineYellow","styles.wrapperOutlineRed","styles.wrapperOutlineBlue","styles.wrapperOutlinePrimary","Pill","_a","type","colorType","children","icon","className","otherProps","__rest","_jsxs","Object","assign","clsx","styles.wrapperBase","styles.wrapperSolid","React","cloneElement","_jsx","styles.label"],"mappings":"oiBAMA,MAAMA,EAAiE,CACnEC,MAAO,CACHC,MAAOC,EACPC,KAAMC,EACNC,MAAOC,EACPC,OAAQC,EACRC,IAAKC,EACLC,KAAMC,EACNC,QAASC,GAEbC,QAAS,CACLd,MAAOe,EACPb,KAAMc,EACNZ,MAAOa,EACPX,OAAQY,EACRV,IAAKW,EACLT,KAAMU,EACNR,QAASS,IAWJC,EAAQC,IAAA,IAAAC,KACjBA,EAAIC,UACJA,EAAY,QAAOC,SACnBA,EAAQC,KACRA,EAAIC,UACJA,GAASL,EACNM,EAAUC,EAAAP,EANI,oDAQjB,OACIQ,EAAA,MAAAC,OAAAC,OAAA,GACQJ,EAAU,CACdD,UAAWM,EACPC,EACS,UAATX,GAAoBY,EACpBtC,EAAc0B,GAAMC,GACpBG,GACHF,SAAA,CAEAC,GAAQU,EAAMC,aAAaX,EAAM,CAAE,eAAe,IACnDY,EAAA,MAAA,CAAKX,UAAWY,EAAYd,SAAGA,OAC7B"}
@@ -1 +1,2 @@
1
1
  export * from "./popover-inline";
2
+ export * from "./types";
@@ -1,4 +1,4 @@
1
- import type { PopoverInlineProps } from "../types";
1
+ import type { PopoverInlineProps } from "./types";
2
2
  /**
3
3
  * An inline text or icon element that opens a popover on interaction.
4
4
  *
@@ -1 +1 @@
1
- {"version":3,"file":"popover-inline.js","sources":["../../../src/popover/popover-inline/popover-inline.tsx"],"sourcesContent":["import clsx from \"clsx\";\n\nimport { PopoverTrigger } from \"../popover-trigger\";\nimport type { PopoverInlineProps } from \"../types\";\nimport * as styles from \"./popover-inline.styles\";\n\n/**\n * An inline text or icon element that opens a popover on interaction.\n *\n * Use `PopoverInline` to embed a labelled trigger directly within a body of content.\n */\nexport const PopoverInline = ({\n ariaLabel,\n content,\n icon,\n underlineStyle = \"default\",\n underlineHoverStyle = \"default\",\n ...otherProps\n}: PopoverInlineProps) => {\n // =========================================================================\n // RENDER FUNCTIONS\n // =========================================================================\n const hasContent = !!content;\n\n return (\n <PopoverTrigger {...otherProps}>\n <span\n aria-label={ariaLabel ?? (hasContent ? undefined : \"More info\")}\n role=\"button\"\n aria-haspopup=\"dialog\"\n tabIndex={0}\n className={styles.popoverInlineText}\n data-underline-style={underlineStyle}\n data-underline-hover-style={underlineHoverStyle}\n >\n {content}\n {icon && (\n <span\n className={clsx(\n hasContent && styles.popoverInlineIconWithContent\n )}\n >\n {icon}\n </span>\n )}\n </span>\n </PopoverTrigger>\n );\n};\n"],"names":["PopoverInline","_a","ariaLabel","content","icon","underlineStyle","underlineHoverStyle","otherProps","__rest","hasContent","_jsx","PopoverTrigger","Object","assign","children","_jsxs","undefined","role","tabIndex","className","styles.popoverInlineText","clsx","styles.popoverInlineIconWithContent"],"mappings":"gRAWO,MAAMA,EAAiBC,IAAA,IAAAC,UAC1BA,EAASC,QACTA,EAAOC,KACPA,EAAIC,eACJA,EAAiB,UAASC,oBAC1BA,EAAsB,WAASL,EAC5BM,EAAUC,EAAAP,EANa,uEAW1B,MAAMQ,IAAeN,EAErB,OACIO,EAACC,EAAcC,OAAAC,OAAA,CAAA,EAAKN,EAAU,CAAAO,SAC1BC,EAAA,OAAA,CAAA,aACgBb,QAAAA,EAAcO,OAAaO,EAAY,YACnDC,KAAK,SAAQ,gBACC,SACdC,SAAU,EACVC,UAAWC,yBACWf,EAAc,6BACRC,EAAmBQ,SAAA,CAE9CX,EACAC,GACGM,EAAA,OAAA,CACIS,UAAWE,EACPZ,GAAca,GACjBR,SAEAV,SAIA"}
1
+ {"version":3,"file":"popover-inline.js","sources":["../../../src/popover/popover-inline/popover-inline.tsx"],"sourcesContent":["import clsx from \"clsx\";\n\nimport { PopoverTrigger } from \"../popover-trigger\";\nimport * as styles from \"./popover-inline.styles\";\nimport type { PopoverInlineProps } from \"./types\";\n\n/**\n * An inline text or icon element that opens a popover on interaction.\n *\n * Use `PopoverInline` to embed a labelled trigger directly within a body of content.\n */\nexport const PopoverInline = ({\n ariaLabel,\n content,\n icon,\n underlineStyle = \"default\",\n underlineHoverStyle = \"default\",\n ...otherProps\n}: PopoverInlineProps) => {\n // =========================================================================\n // RENDER FUNCTIONS\n // =========================================================================\n const hasContent = !!content;\n\n return (\n <PopoverTrigger {...otherProps}>\n <span\n aria-label={ariaLabel ?? (hasContent ? undefined : \"More info\")}\n role=\"button\"\n aria-haspopup=\"dialog\"\n tabIndex={0}\n className={styles.popoverInlineText}\n data-underline-style={underlineStyle}\n data-underline-hover-style={underlineHoverStyle}\n >\n {content}\n {icon && (\n <span\n className={clsx(\n hasContent && styles.popoverInlineIconWithContent\n )}\n >\n {icon}\n </span>\n )}\n </span>\n </PopoverTrigger>\n );\n};\n"],"names":["PopoverInline","_a","ariaLabel","content","icon","underlineStyle","underlineHoverStyle","otherProps","__rest","hasContent","_jsx","PopoverTrigger","Object","assign","children","_jsxs","undefined","role","tabIndex","className","styles.popoverInlineText","clsx","styles.popoverInlineIconWithContent"],"mappings":"gRAWO,MAAMA,EAAiBC,IAAA,IAAAC,UAC1BA,EAASC,QACTA,EAAOC,KACPA,EAAIC,eACJA,EAAiB,UAASC,oBAC1BA,EAAsB,WAASL,EAC5BM,EAAUC,EAAAP,EANa,uEAW1B,MAAMQ,IAAeN,EAErB,OACIO,EAACC,EAAcC,OAAAC,OAAA,CAAA,EAAKN,EAAU,CAAAO,SAC1BC,EAAA,OAAA,CAAA,aACgBb,QAAAA,EAAcO,OAAaO,EAAY,YACnDC,KAAK,SAAQ,gBACC,SACdC,SAAU,EACVC,UAAWC,yBACWf,EAAc,6BACRC,EAAmBQ,SAAA,CAE9CX,EACAC,GACGM,EAAA,OAAA,CACIS,UAAWE,EACPZ,GAAca,GACjBR,SAEAV,SAIA"}
@@ -0,0 +1,36 @@
1
+ import type { PopoverTriggerProps } from "../types";
2
+ /**
3
+ * Underline decoration applied to the `PopoverInline` trigger span.
4
+ */
5
+ export type PopoverInlineStyle = "default" | "underline" | "underline-dashed";
6
+ /**
7
+ * Props for the `PopoverInline` component.
8
+ */
9
+ export interface PopoverInlineProps extends Omit<PopoverTriggerProps, "children"> {
10
+ /**
11
+ * Accessible label for the trigger button.
12
+ *
13
+ * @default "More info" when `content` is not provided
14
+ */
15
+ ariaLabel?: string | undefined;
16
+ /**
17
+ * Label text or element displayed inside the trigger span.
18
+ */
19
+ content?: React.ReactNode | undefined;
20
+ /**
21
+ * Icon element rendered after `content` inside the trigger span.
22
+ */
23
+ icon?: JSX.Element | undefined;
24
+ /**
25
+ * Underline style applied to the trigger span in its default state.
26
+ *
27
+ * @default "default"
28
+ */
29
+ underlineStyle?: PopoverInlineStyle | undefined;
30
+ /**
31
+ * Underline style applied to the trigger span on hover.
32
+ *
33
+ * @default "default"
34
+ */
35
+ underlineHoverStyle?: PopoverInlineStyle | undefined;
36
+ }
@@ -1 +1 @@
1
- {"version":3,"file":"popover.js","sources":["../../src/popover/popover.tsx"],"sourcesContent":["import clsx from \"clsx\";\nimport { useMemo, useRef } from \"react\";\n\nimport { Card } from \"../card\";\nimport { Markup } from \"../markup\";\nimport { ModalV2 } from \"../modal-v2\";\nimport { useApplyStyle, useMaxWidthMediaQuery } from \"../theme\";\nimport { Typography } from \"../typography\";\nimport * as styles from \"./popover.styles\";\nimport type { PopoverProps } from \"./types\";\n\n/**\n * The presentational overlay for a popover panel. Renders as a floating card\n * on desktop and modal on mobile.\n *\n * Use with `PopoverTrigger`, which manages visibility state and positioning.\n */\nexport const Popover = ({\n children,\n visible = false,\n onMobileClose,\n maxHeight,\n overflow,\n ariaLabel = \"More information\",\n id,\n className,\n \"data-testid\": testId = \"popover\",\n ...otherProps\n}: PopoverProps): JSX.Element => {\n // =============================================================================\n // CONST, STATE, REF\n // =============================================================================\n const isMobile = useMaxWidthMediaQuery(\"sm\");\n const popoverContainerRef = useRef<HTMLDivElement>(null);\n const popoverCardStyle = useMemo(\n () => ({\n [styles.tokens.popoverCard.maxHeight]:\n maxHeight === undefined ? null : `${maxHeight}px`,\n [styles.tokens.popoverCard.overflowY]: overflow ?? null,\n }),\n [maxHeight, overflow]\n );\n useApplyStyle(popoverContainerRef, popoverCardStyle);\n\n // =============================================================================\n // EVENT HANDLERS\n // =============================================================================\n const handleMobileClose = () => {\n if (onMobileClose) {\n onMobileClose();\n }\n };\n\n // =============================================================================\n // RENDER FUNCTIONS\n // =============================================================================\n const renderContent = () =>\n typeof children === \"string\" ? (\n <Typography.BodyMD>{children}</Typography.BodyMD>\n ) : (\n children\n );\n\n return (\n <>\n {visible && !isMobile && (\n <div\n ref={popoverContainerRef}\n tabIndex={0}\n data-testid={testId}\n {...otherProps}\n className={clsx(styles.popoverContainer, className)}\n id={id}\n role=\"dialog\"\n aria-label={ariaLabel}\n >\n <Card\n className={clsx(\n styles.popoverCard,\n maxHeight !== undefined &&\n styles.popoverCardWithMaxHeight,\n overflow && styles.popoverCardWithOverflow\n )}\n >\n <Markup baseTextSize=\"body-md\">\n {renderContent()}\n </Markup>\n </Card>\n </div>\n )}\n {isMobile && (\n <ModalV2\n show={visible}\n onOverlayClick={handleMobileClose}\n onClose={handleMobileClose}\n id={id}\n role=\"dialog\"\n aria-label={ariaLabel}\n >\n <ModalV2.Card>\n <ModalV2.Content>\n <Markup>{renderContent()}</Markup>\n </ModalV2.Content>\n <ModalV2.CloseButton />\n </ModalV2.Card>\n </ModalV2>\n )}\n </>\n );\n};\n"],"names":["Popover","_a","children","visible","onMobileClose","maxHeight","overflow","ariaLabel","id","className","testId","otherProps","__rest","isMobile","useMaxWidthMediaQuery","popoverContainerRef","useRef","popoverCardStyle","useMemo","styles.tokens","popoverCard","undefined","overflowY","useApplyStyle","handleMobileClose","renderContent","_jsx","Typography","BodyMD","_jsxs","_Fragment","Object","assign","ref","tabIndex","clsx","styles.popoverContainer","role","Card","styles.popoverCard","styles.popoverCardWithMaxHeight","styles.popoverCardWithOverflow","Markup","baseTextSize","ModalV2","show","onOverlayClick","onClose","Content","CloseButton"],"mappings":"o2BAiBO,MAAMA,EAAWC,IAAA,IAAAC,SACpBA,EAAQC,QACRA,GAAU,EAAKC,cACfA,EAAaC,UACbA,EAASC,SACTA,EAAQC,UACRA,EAAY,mBAAkBC,GAC9BA,EAAEC,UACFA,EACA,cAAeC,EAAS,WAAST,EAC9BU,EAAUC,EAAAX,EAVO,0GAepB,MAAMY,EAAWC,EAAsB,MACjCC,EAAsBC,EAAuB,MAC7CC,EAAmBC,GACrB,KAAA,CACI,CAACC,EAAcC,YAAYf,gBACTgB,IAAdhB,EAA0B,KAAO,GAAGA,MACxC,CAACc,EAAcC,YAAYE,WAAYhB,QAAAA,EAAY,QAEvD,CAACD,EAAWC,IAEhBiB,EAAcR,EAAqBE,GAKnC,MAAMO,EAAoB,KAClBpB,GACAA,GACJ,EAMEqB,EAAgB,IACE,iBAAbvB,EACHwB,EAACC,EAAWC,OAAM,CAAA1B,SAAEA,IAA6B,EAKzD,OACI2B,EAAAC,EAAA,CAAA5B,SAAA,CACKC,IAAYU,GACTa,EAAA,MAAAK,OAAAC,OAAA,CACIC,IAAKlB,EACLmB,SAAU,EAAC,cACExB,GACTC,EAAU,CACdF,UAAW0B,EAAKC,EAAyB3B,GACzCD,GAAIA,EACJ6B,KAAK,SAAQ,aACD9B,EAASL,SAErBwB,EAACY,EAAI,CACD7B,UAAW0B,EACPI,OACclB,IAAdhB,GACImC,EACJlC,GAAYmC,GACfvC,SAEDwB,EAACgB,EAAM,CAACC,aAAa,mBAChBlB,WAKhBZ,GACGa,EAACkB,EAAO,CACJC,KAAM1C,EACN2C,eAAgBtB,EAChBuB,QAASvB,EACThB,GAAIA,EACJ6B,KAAK,SAAQ,aACD9B,EAASL,SAErB2B,EAACe,EAAQN,KAAI,CAAApC,SAAA,CACTwB,EAACkB,EAAQI,QAAO,CAAA9C,SACZwB,EAACgB,EAAM,CAAAxC,SAAEuB,QAEbC,EAACkB,EAAQK,YAAW,CAAA,UAIjC"}
1
+ {"version":3,"file":"popover.js","sources":["../../src/popover/popover.tsx"],"sourcesContent":["import clsx from \"clsx\";\nimport { useMemo, useRef } from \"react\";\n\nimport { Card } from \"../card\";\nimport { Markup } from \"../markup\";\nimport { ModalV2 } from \"../modal-v2\";\nimport { useApplyStyle, useMaxWidthMediaQuery } from \"../theme\";\nimport { Typography } from \"../typography\";\nimport * as styles from \"./popover.styles\";\nimport type { PopoverProps } from \"./types\";\n\n// @catalog\n/**\n * The presentational overlay for a popover panel. Renders as a floating card\n * on desktop and modal on mobile.\n *\n * Use with `PopoverTrigger`, which manages visibility state and positioning.\n */\nexport const Popover = ({\n children,\n visible = false,\n onMobileClose,\n maxHeight,\n overflow,\n ariaLabel = \"More information\",\n id,\n className,\n \"data-testid\": testId = \"popover\",\n ...otherProps\n}: PopoverProps): JSX.Element => {\n // =============================================================================\n // CONST, STATE, REF\n // =============================================================================\n const isMobile = useMaxWidthMediaQuery(\"sm\");\n const popoverContainerRef = useRef<HTMLDivElement>(null);\n const popoverCardStyle = useMemo(\n () => ({\n [styles.tokens.popoverCard.maxHeight]:\n maxHeight === undefined ? null : `${maxHeight}px`,\n [styles.tokens.popoverCard.overflowY]: overflow ?? null,\n }),\n [maxHeight, overflow]\n );\n useApplyStyle(popoverContainerRef, popoverCardStyle);\n\n // =============================================================================\n // EVENT HANDLERS\n // =============================================================================\n const handleMobileClose = () => {\n if (onMobileClose) {\n onMobileClose();\n }\n };\n\n // =============================================================================\n // RENDER FUNCTIONS\n // =============================================================================\n const renderContent = () =>\n typeof children === \"string\" ? (\n <Typography.BodyMD>{children}</Typography.BodyMD>\n ) : (\n children\n );\n\n return (\n <>\n {visible && !isMobile && (\n <div\n ref={popoverContainerRef}\n tabIndex={0}\n data-testid={testId}\n {...otherProps}\n className={clsx(styles.popoverContainer, className)}\n id={id}\n role=\"dialog\"\n aria-label={ariaLabel}\n >\n <Card\n className={clsx(\n styles.popoverCard,\n maxHeight !== undefined &&\n styles.popoverCardWithMaxHeight,\n overflow && styles.popoverCardWithOverflow\n )}\n >\n <Markup baseTextSize=\"body-md\">\n {renderContent()}\n </Markup>\n </Card>\n </div>\n )}\n {isMobile && (\n <ModalV2\n show={visible}\n onOverlayClick={handleMobileClose}\n onClose={handleMobileClose}\n id={id}\n role=\"dialog\"\n aria-label={ariaLabel}\n >\n <ModalV2.Card>\n <ModalV2.Content>\n <Markup>{renderContent()}</Markup>\n </ModalV2.Content>\n <ModalV2.CloseButton />\n </ModalV2.Card>\n </ModalV2>\n )}\n </>\n );\n};\n"],"names":["Popover","_a","children","visible","onMobileClose","maxHeight","overflow","ariaLabel","id","className","testId","otherProps","__rest","isMobile","useMaxWidthMediaQuery","popoverContainerRef","useRef","popoverCardStyle","useMemo","styles.tokens","popoverCard","undefined","overflowY","useApplyStyle","handleMobileClose","renderContent","_jsx","Typography","BodyMD","_jsxs","_Fragment","Object","assign","ref","tabIndex","clsx","styles.popoverContainer","role","Card","styles.popoverCard","styles.popoverCardWithMaxHeight","styles.popoverCardWithOverflow","Markup","baseTextSize","ModalV2","show","onOverlayClick","onClose","Content","CloseButton"],"mappings":"o2BAkBO,MAAMA,EAAWC,IAAA,IAAAC,SACpBA,EAAQC,QACRA,GAAU,EAAKC,cACfA,EAAaC,UACbA,EAASC,SACTA,EAAQC,UACRA,EAAY,mBAAkBC,GAC9BA,EAAEC,UACFA,EACA,cAAeC,EAAS,WAAST,EAC9BU,EAAUC,EAAAX,EAVO,0GAepB,MAAMY,EAAWC,EAAsB,MACjCC,EAAsBC,EAAuB,MAC7CC,EAAmBC,GACrB,KAAA,CACI,CAACC,EAAcC,YAAYf,gBACTgB,IAAdhB,EAA0B,KAAO,GAAGA,MACxC,CAACc,EAAcC,YAAYE,WAAYhB,QAAAA,EAAY,QAEvD,CAACD,EAAWC,IAEhBiB,EAAcR,EAAqBE,GAKnC,MAAMO,EAAoB,KAClBpB,GACAA,GACJ,EAMEqB,EAAgB,IACE,iBAAbvB,EACHwB,EAACC,EAAWC,OAAM,CAAA1B,SAAEA,IAA6B,EAKzD,OACI2B,EAAAC,EAAA,CAAA5B,SAAA,CACKC,IAAYU,GACTa,EAAA,MAAAK,OAAAC,OAAA,CACIC,IAAKlB,EACLmB,SAAU,EAAC,cACExB,GACTC,EAAU,CACdF,UAAW0B,EAAKC,EAAyB3B,GACzCD,GAAIA,EACJ6B,KAAK,SAAQ,aACD9B,EAASL,SAErBwB,EAACY,EAAI,CACD7B,UAAW0B,EACPI,OACclB,IAAdhB,GACImC,EACJlC,GAAYmC,GACfvC,SAEDwB,EAACgB,EAAM,CAACC,aAAa,mBAChBlB,WAKhBZ,GACGa,EAACkB,EAAO,CACJC,KAAM1C,EACN2C,eAAgBtB,EAChBuB,QAASvB,EACThB,GAAIA,EACJ6B,KAAK,SAAQ,aACD9B,EAASL,SAErB2B,EAACe,EAAQN,KAAI,CAAApC,SAAA,CACTwB,EAACkB,EAAQI,QAAO,CAAA9C,SACZwB,EAACgB,EAAM,CAAAxC,SAAEuB,QAEbC,EAACkB,EAAQK,YAAW,CAAA,UAIjC"}
@@ -143,6 +143,8 @@ export interface PopoverTriggerProps {
143
143
  overflow?: PopoverOverflowType | undefined;
144
144
  /**
145
145
  * Accessible label for the popover dialog element.
146
+ *
147
+ * @default "More information"
146
148
  */
147
149
  popoverAriaLabel?: string | undefined;
148
150
  /**
@@ -168,39 +170,4 @@ export interface PopoverTriggerProps {
168
170
  */
169
171
  onPopoverDismiss?: (() => void) | undefined;
170
172
  }
171
- /**
172
- * Underline decoration applied to the `PopoverInline` trigger span.
173
- */
174
- export type PopoverInlineStyle = "default" | "underline" | "underline-dashed";
175
- /**
176
- * Props for the `PopoverInline` component.
177
- */
178
- export interface PopoverInlineProps extends Omit<PopoverTriggerProps, "children"> {
179
- /**
180
- * Accessible label for the trigger button.
181
- *
182
- * @default "More info" when `content` is not provided
183
- */
184
- ariaLabel?: string | undefined;
185
- /**
186
- * Label text or element displayed inside the trigger span.
187
- */
188
- content?: React.ReactNode | undefined;
189
- /**
190
- * Icon element rendered after `content` inside the trigger span.
191
- */
192
- icon?: JSX.Element | undefined;
193
- /**
194
- * Underline style applied to the trigger span in its default state.
195
- *
196
- * @default "default"
197
- */
198
- underlineStyle?: PopoverInlineStyle | undefined;
199
- /**
200
- * Underline style applied to the trigger span on hover.
201
- *
202
- * @default "default"
203
- */
204
- underlineHoverStyle?: PopoverInlineStyle | undefined;
205
- }
206
173
  export {};
@@ -1,2 +1,2 @@
1
- import{__rest as e,__awaiter as r}from"../_virtual/_tslib.js";import{jsx as t,Fragment as o,jsxs as i}from"react/jsx-runtime";import s from"../external/lodash/debounce.js";import{useState as l,useRef as n,useCallback as a,useEffect as d}from"react";import{Input as p}from"../input/input.js";import{VisuallyHidden as m,concatIds as c}from"../shared/accessibility/index.js";import"clsx";import"../theme/theme-provider/index.js";import"../theme/theme-provider/context.js";import"../theme/tokens/border.js";import"../theme/tokens/colour.js";import"../theme/tokens/font.js";import"../theme/tokens/media-query.js";import"../util/calendar-helper.js";import"../external/dayjs/dayjs.min.js";import{useId as u}from"../util/simple-id-generator.js";import"../util/string-helper.js";import"@react-aria/live-announcer";import"../theme/utils/use-media-query.js";import"../shared/dropdown-list/dropdown-label.styles_mloii0.css";import{DropdownList as h}from"../shared/dropdown-list/dropdown-list.js";import{DropdownListState as f}from"../shared/dropdown-list/dropdown-list-state.js";import"../shared/dropdown-list/expandable-element.js";import"@lifesg/react-icons/caret-right";import"@lifesg/react-icons/exclamation-circle-fill";import"@lifesg/react-icons/minus-square-fill";import"@lifesg/react-icons/square";import"@lifesg/react-icons/square-tick-fill";import"@lifesg/react-icons/tick";import"react-virtuoso";import"../markup/markup.js";import"../shared/component-loading-spinner/component-loading-spinner.styles_15eq02i.css";import{ElementWithDropdown as g}from"../shared/dropdown-wrapper/element-with-dropdown.js";import{InputWrapper as x}from"../shared/input-wrapper/input-wrapper.js";import"../shared/dropdown-list/dropdown-list.styles_konwm.css";import"../shared/dropdown-list/dropdown-search.js";import"../shared/dropdown-list/nested-dropdown-list.styles_wdhxoe.css";import"immer";import"../external/lodash/_getTag.js";import"../external/lodash/isArguments.js";import"../external/lodash/_baseGetTag.js";import"../external/lodash/isBuffer.js";import"../external/lodash/isTypedArray.js";import"../external/lodash/_Stack.js";import"../external/lodash/_SetCache.js";import"../external/lodash/_equalByTag.js";import"../shared/dropdown-list/virtuoso-components.js";const j=j=>{var{className:w,"data-testid":y,selectedOption:v,minimumCharacters:b=3,fetchOptions:_,placeholder:T="Enter here...",readOnly:O=!1,disabled:I=!1,error:k,valueExtractor:A,listExtractor:C,displayValueExtractor:E,onSelectOption:S,alignment:q,dropdownZIndex:N,dropdownRootNode:G,dropdownWidth:H,"aria-describedby":M}=j,P=e(j,["className","data-testid","selectedOption","minimumCharacters","fetchOptions","placeholder","readOnly","disabled","error","valueExtractor","listExtractor","displayValueExtractor","onSelectOption","alignment","dropdownZIndex","dropdownRootNode","dropdownWidth","aria-describedby"]);const B=e=>e?E?E(e):e.toString():"",[D,L]=l((()=>v?B(v):"")),[R,W]=l((()=>v?B(v):"")),[Z,$]=l([]),[F,V]=l(!0),[z,J]=l(!1),[K,Q]=l(!!v),[U,X]=l(v),[Y,ee]=l(!1),[re,te]=l(!1),oe=u(),[ie,se]=l(null),le=`${oe}-instruction`,ne=n(null),ae=n(null),de=n(_),pe=a((e=>r(void 0,void 0,void 0,(function*(){if(de.current){J(!1),V(!0);try{const r=yield de.current(e);W(e),$(null!=r?r:[]),V(!1)}catch(e){J(!0),V(!1)}}}))),[]),me=a(s((e=>{pe(e)}),500),[pe]);d((()=>{de.current=_}),[_]),d((()=>{D&&D.length>=b?K?D!==R&&me(D):(ee(!0),me(D)):me.cancel(),""===D&&U&&(null==S||S(void 0,void 0),we(),X(void 0)),v&&D!==B(v)&&Q(!1)}),[D,v]),d((()=>{L(v?B(v):""),W(v?B(v):""),X(v),$([]),Q(!!v)}),[v]),d((()=>{var e;const r=ye(),t=null!==(e=null==Z?void 0:Z.length)&&void 0!==e?e:0;"loading"===r&&D.length>=b?se("Loading suggested results"):"fail"!==r?!Y||F||z||se(0===t?D?"No results found.":null:`${t} result${t>1?"s":""} found. Press down arrow to scroll through the list.`):se("Suggestions failed to load. Try again.")}),[Z,D,z,F]),d((()=>()=>{me.cancel()}),[me]);const ce=(e,r)=>{var t;null===(t=ae.current)||void 0===t||t.focus(),L(B(e)),W(e?B(e):""),Q(!0),X(e),ee(!1),null==S||S(e,r)},ue=()=>{te(!0)},he=e=>{Y||!ne.current||ne.current.contains(e.relatedTarget)||(te(!1),xe())},fe=()=>{ee(!1),te(!1)},ge=()=>{L(""),$([]),Q(!1),ee(!1),null==S||S(void 0,void 0)},xe=()=>{if(!K)if(U){const e=B(U);L(e),ee(!1)}else ge()},je=e=>{L(e.target.value),Q(!1)},we=e=>{W(""),Q(!1),$([]),V(!0)},ye=()=>z?"fail":F?"loading":"success";return t(f,{children:t(g,{enabled:!O&&!I,isOpen:Y,renderElement:()=>i(x,{className:w,"data-testid":y,ref:ne,tabIndex:-1,onFocus:ue,onBlur:he,focused:re,disabled:I,readOnly:O,error:k,children:[i(m,{id:le,"aria-hidden":!0,children:["Type in ",b," or more characters for suggested results."]}),ie&&t(m,{"aria-live":"polite",children:ie}),t(p,Object.assign({role:"combobox",ref:ae,id:oe,type:"text",value:D,onChange:je,placeholder:T,readOnly:O,disabled:I,allowClear:!0,onClear:ge,"aria-expanded":Y,"aria-controls":oe,"aria-autocomplete":"list","aria-haspopup":"listbox",onBlur:D.length<b?xe:void 0,styleType:"no-border","aria-describedby":c(M,le)},P))]}),renderDropdown:()=>t(o,{children:t(h,{listboxId:oe,listItems:Z,onSelectItem:ce,onDismiss:fe,valueExtractor:A,listExtractor:C,itemsLoadState:ye(),itemTruncationType:"end",itemMaxLines:1,labelDisplayType:"next-line",disableItemFocus:!0,onRetry:()=>pe(D),width:H,matchElementWidth:!0})}),onOpen:()=>{!K&&D.length>=b&&te(!0)},onClose:()=>{ee(!1),te(!1),xe()},onDismiss:()=>{var e;ee(!1),te(!1),xe(),null===(e=ae.current)||void 0===e||e.focus()},clickToToggle:!1,offset:8,alignment:q,fitAvailableHeight:!0,customZIndex:N,rootNode:G})})};export{j as PredictiveTextInput};
1
+ import{__rest as e,__awaiter as r}from"../_virtual/_tslib.js";import{jsx as t,jsxs as o}from"react/jsx-runtime";import i from"../external/lodash/debounce.js";import{useState as s,useRef as l,useCallback as n,useEffect as a}from"react";import{Input as d}from"../input/input.js";import{VisuallyHidden as p,concatIds as m}from"../shared/accessibility/index.js";import"clsx";import"../theme/theme-provider/index.js";import"../theme/theme-provider/context.js";import"../theme/tokens/border.js";import"../theme/tokens/colour.js";import"../theme/tokens/font.js";import"../theme/tokens/media-query.js";import"../util/calendar-helper.js";import"../external/dayjs/dayjs.min.js";import{useId as c}from"../util/simple-id-generator.js";import"../util/string-helper.js";import"@react-aria/live-announcer";import"../theme/utils/use-media-query.js";import"../shared/dropdown-list/dropdown-label.styles_mloii0.css";import{DropdownList as u}from"../shared/dropdown-list/dropdown-list.js";import{DropdownListState as h}from"../shared/dropdown-list/dropdown-list-state.js";import"../shared/dropdown-list/expandable-element.js";import"@lifesg/react-icons/caret-right";import"@lifesg/react-icons/exclamation-circle-fill";import"@lifesg/react-icons/minus-square-fill";import"@lifesg/react-icons/square";import"@lifesg/react-icons/square-tick-fill";import"@lifesg/react-icons/tick";import"react-virtuoso";import"../markup/markup.js";import"../shared/component-loading-spinner/component-loading-spinner.styles_15eq02i.css";import{ElementWithDropdown as f}from"../shared/dropdown-wrapper/element-with-dropdown.js";import{InputWrapper as g}from"../shared/input-wrapper/input-wrapper.js";import"../shared/dropdown-list/dropdown-list.styles_konwm.css";import"../shared/dropdown-list/dropdown-search.js";import"../shared/dropdown-list/nested-dropdown-list.styles_wdhxoe.css";import"immer";import"../external/lodash/_getTag.js";import"../external/lodash/isArguments.js";import"../external/lodash/_baseGetTag.js";import"../external/lodash/isBuffer.js";import"../external/lodash/isTypedArray.js";import"../external/lodash/_Stack.js";import"../external/lodash/_SetCache.js";import"../external/lodash/_equalByTag.js";import"../shared/dropdown-list/virtuoso-components.js";const x=x=>{var{className:j,"data-testid":w,selectedOption:y,minimumCharacters:v=3,fetchOptions:b,placeholder:_="Enter here...",readOnly:T=!1,disabled:O=!1,error:I,valueExtractor:k,listExtractor:A,displayValueExtractor:C,onSelectOption:E,alignment:S,dropdownZIndex:q,dropdownRootNode:N,dropdownWidth:H,"aria-describedby":G}=x,M=e(x,["className","data-testid","selectedOption","minimumCharacters","fetchOptions","placeholder","readOnly","disabled","error","valueExtractor","listExtractor","displayValueExtractor","onSelectOption","alignment","dropdownZIndex","dropdownRootNode","dropdownWidth","aria-describedby"]);const P=e=>e?C?C(e):e.toString():"",[B,D]=s((()=>y?P(y):"")),[L,R]=s((()=>y?P(y):"")),[W,Z]=s([]),[$,F]=s(!0),[V,z]=s(!1),[J,K]=s(!!y),[Q,U]=s(y),[X,Y]=s(!1),[ee,re]=s(!1),te=c(),[oe,ie]=s(null),se=`${te}-instruction`,le=l(null),ne=l(null),ae=l(b),de=n((e=>r(void 0,void 0,void 0,(function*(){if(ae.current){z(!1),F(!0);try{const r=yield ae.current(e);R(e),Z(null!=r?r:[]),F(!1)}catch(e){z(!0),F(!1)}}}))),[]),pe=n(i((e=>{de(e)}),500),[de]);a((()=>{ae.current=b}),[b]),a((()=>{B&&B.length>=v?J?B!==L&&pe(B):(Y(!0),pe(B)):pe.cancel(),""===B&&Q&&(null==E||E(void 0,void 0),je(),U(void 0)),y&&B!==P(y)&&K(!1)}),[B,y]),a((()=>{D(y?P(y):""),R(y?P(y):""),U(y),K(!!y)}),[y]),a((()=>{var e;const r=we(),t=null!==(e=null==W?void 0:W.length)&&void 0!==e?e:0;"loading"===r&&B.length>=v?ie("Loading suggested results"):"fail"!==r?!X||$||V||ie(0===t?B?"No results found.":null:`${t} result${t>1?"s":""} found. Press down arrow to scroll through the list.`):ie("Suggestions failed to load. Try again.")}),[W,B,V,$]),a((()=>()=>{pe.cancel()}),[pe]);const me=(e,r)=>{var t;null===(t=ne.current)||void 0===t||t.focus(),D(P(e)),R(e?P(e):""),K(!0),U(e),Y(!1),null==E||E(e,r)},ce=()=>{re(!0)},ue=e=>{X||!le.current||le.current.contains(e.relatedTarget)||(re(!1),ge())},he=()=>{Y(!1),re(!1)},fe=()=>{D(""),K(!1),Y(!1),null==E||E(void 0,void 0)},ge=()=>{if(!J)if(Q){const e=P(Q);D(e),Y(!1)}else fe()},xe=e=>{D(e.target.value),K(!1)},je=e=>{R(""),K(!1),F(!0)},we=()=>V?"fail":$?"loading":"success";return t(h,{children:t(f,{enabled:!T&&!O,isOpen:X,renderElement:()=>o(g,{className:j,"data-testid":w,ref:le,tabIndex:-1,onFocus:ce,onBlur:ue,focused:ee,disabled:O,readOnly:T,error:I,children:[o(p,{id:se,"aria-hidden":!0,children:["Type in ",v," or more characters for suggested results."]}),oe&&t(p,{"aria-live":"polite",children:oe}),t(d,Object.assign({role:"combobox",ref:ne,id:te,type:"text",value:B,onChange:xe,placeholder:_,readOnly:T,disabled:O,allowClear:!0,onClear:fe,"aria-expanded":X,"aria-controls":te,"aria-autocomplete":"list","aria-haspopup":"listbox",onBlur:B.length<v?ge:void 0,styleType:"no-border","aria-describedby":m(G,se)},M))]}),renderDropdown:()=>t(u,{listboxId:te,listItems:W,onSelectItem:me,onDismiss:he,valueExtractor:k,listExtractor:A,itemsLoadState:we(),itemTruncationType:"end",itemMaxLines:1,labelDisplayType:"next-line",disableItemFocus:!0,onRetry:()=>de(B),width:H,matchElementWidth:!0}),onOpen:()=>{!J&&B.length>=v&&re(!0)},onClose:()=>{Y(!1),re(!1),ge()},onDismiss:()=>{var e;Y(!1),re(!1),ge(),null===(e=ne.current)||void 0===e||e.focus()},onHide:()=>{Z([]),F(!0),z(!1)},clickToToggle:!1,offset:8,alignment:S,fitAvailableHeight:!0,customZIndex:q,rootNode:N})})};export{x as PredictiveTextInput};
2
2
  //# sourceMappingURL=predictive-text-input.js.map