@nextelco/common-ui 2.1.105 → 2.1.107

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 (199) hide show
  1. package/dist/esm/index.js +201 -145
  2. package/dist/esm/index.js.map +1 -1
  3. package/dist/esm/legacy/components/atoms/InputData/InputData.js +2 -13
  4. package/dist/esm/legacy/components/atoms/InputData/InputData.js.map +1 -1
  5. package/dist/esm/legacy/components/charts/Charts.js +147 -57
  6. package/dist/esm/legacy/components/charts/Charts.js.map +1 -1
  7. package/dist/esm/legacy/components/layout/Layout/Layout.js +21 -82
  8. package/dist/esm/legacy/components/layout/Layout/Layout.js.map +1 -1
  9. package/dist/esm/legacy/components/layout/Sidebar/Sidebar.js +29 -218
  10. package/dist/esm/legacy/components/layout/Sidebar/Sidebar.js.map +1 -1
  11. package/dist/esm/legacy/components/molecules/ColumnPicker/ColumnPicker.js +77 -10
  12. package/dist/esm/legacy/components/molecules/ColumnPicker/ColumnPicker.js.map +1 -1
  13. package/dist/esm/legacy/components/molecules/DataTable/DataTable.js +445 -337
  14. package/dist/esm/legacy/components/molecules/DataTable/DataTable.js.map +1 -1
  15. package/dist/esm/legacy/components/molecules/UserAvatar/UserAvatar.js +15 -97
  16. package/dist/esm/legacy/components/molecules/UserAvatar/UserAvatar.js.map +1 -1
  17. package/dist/esm/legacy/components/organisms/MapaPontos/MapaPontos.js +3 -3
  18. package/dist/esm/legacy/components/organisms/MapaPontos/MapaPontos.js.map +1 -1
  19. package/dist/esm/legacy/components/organisms/PainelFiltros/PainelFiltros.js +15 -3
  20. package/dist/esm/legacy/components/organisms/PainelFiltros/PainelFiltros.js.map +1 -1
  21. package/dist/esm/legacy/components/organisms/Selector/Selector.js +4 -4
  22. package/dist/esm/legacy/components/organisms/Selector/Selector.js.map +1 -1
  23. package/dist/esm/legacy/components/ui/Avisos.js +23 -76
  24. package/dist/esm/legacy/components/ui/Avisos.js.map +1 -1
  25. package/dist/esm/legacy/components/ui/CabecalhoPagina.js +14 -27
  26. package/dist/esm/legacy/components/ui/CabecalhoPagina.js.map +1 -1
  27. package/dist/esm/legacy/components/ui/CaixaPesquisa.js +3 -51
  28. package/dist/esm/legacy/components/ui/CaixaPesquisa.js.map +1 -1
  29. package/dist/esm/legacy/components/ui/Confirmacao.js +13 -31
  30. package/dist/esm/legacy/components/ui/Confirmacao.js.map +1 -1
  31. package/dist/esm/legacy/components/ui/Escolha.js +21 -137
  32. package/dist/esm/legacy/components/ui/Escolha.js.map +1 -1
  33. package/dist/esm/legacy/components/ui/FaixaAviso.js +13 -11
  34. package/dist/esm/legacy/components/ui/FaixaAviso.js.map +1 -1
  35. package/dist/esm/legacy/components/ui/Separadores.js +11 -46
  36. package/dist/esm/legacy/components/ui/Separadores.js.map +1 -1
  37. package/dist/esm/legacy/components/ui/Ui.js +18 -115
  38. package/dist/esm/legacy/components/ui/Ui.js.map +1 -1
  39. package/dist/esm/legacy/components/ui/painelFlutuante.js +5 -44
  40. package/dist/esm/legacy/components/ui/painelFlutuante.js.map +1 -1
  41. package/dist/esm/v1/capabilities/overlay/useFloatingPanel.js +52 -0
  42. package/dist/esm/v1/capabilities/overlay/useFloatingPanel.js.map +1 -0
  43. package/dist/esm/v1/capabilities/theme/useIsDark.js +15 -0
  44. package/dist/esm/v1/capabilities/theme/useIsDark.js.map +1 -0
  45. package/dist/esm/v1/capabilities/theme/useTheme.js +66 -0
  46. package/dist/esm/v1/capabilities/theme/useTheme.js.map +1 -0
  47. package/dist/esm/v1/components/data/Pagination/Pagination.js +66 -0
  48. package/dist/esm/v1/components/data/Pagination/Pagination.js.map +1 -0
  49. package/dist/esm/v1/components/feedback/Toast/Toast.js +105 -0
  50. package/dist/esm/v1/components/feedback/Toast/Toast.js.map +1 -0
  51. package/dist/esm/v1/components/forms/FormField/FormField.js.map +1 -1
  52. package/dist/esm/v1/components/forms/FormGrid/FormGrid.js.map +1 -1
  53. package/dist/esm/v1/components/layout/AppShell/AppShell.js +89 -0
  54. package/dist/esm/v1/components/layout/AppShell/AppShell.js.map +1 -0
  55. package/dist/esm/v1/components/layout/Page/Page.js +16 -0
  56. package/dist/esm/v1/components/layout/Page/Page.js.map +1 -0
  57. package/dist/esm/v1/components/layout/PageHeader/PageHeader.js +26 -0
  58. package/dist/esm/v1/components/layout/PageHeader/PageHeader.js.map +1 -0
  59. package/dist/esm/v1/components/layout/SideNav/SideNav.js +277 -0
  60. package/dist/esm/v1/components/layout/SideNav/SideNav.js.map +1 -0
  61. package/dist/esm/v1/components/layout/navTrail.js +19 -0
  62. package/dist/esm/v1/components/layout/navTrail.js.map +1 -0
  63. package/dist/esm/v1/components/lists/ListFinder/ListFinder.js +4 -4
  64. package/dist/esm/v1/components/lists/ListFinder/ListFinder.js.map +1 -1
  65. package/dist/esm/v1/components/overlays/ConfirmDialog/ConfirmDialog.js +95 -0
  66. package/dist/esm/v1/components/overlays/ConfirmDialog/ConfirmDialog.js.map +1 -0
  67. package/dist/esm/v1/components/overlays/Dialog/Dialog.js.map +1 -1
  68. package/dist/esm/v1/components/overlays/Tooltip/Tooltip.js +98 -0
  69. package/dist/esm/v1/components/overlays/Tooltip/Tooltip.js.map +1 -0
  70. package/dist/esm/v1/components/overlays/Tooltip/TooltipLayer.js +84 -0
  71. package/dist/esm/v1/components/overlays/Tooltip/TooltipLayer.js.map +1 -0
  72. package/dist/esm/v1/components/overlays/Tooltip/TooltipPanel.js +33 -0
  73. package/dist/esm/v1/components/overlays/Tooltip/TooltipPanel.js.map +1 -0
  74. package/dist/esm/v1/components/overlays/topLayer.js +28 -0
  75. package/dist/esm/v1/components/overlays/topLayer.js.map +1 -0
  76. package/dist/esm/v1/components/tables/PaginatedTable/PaginatedTable.js.map +1 -1
  77. package/dist/esm/v1/components/tables/Table/Table.js.map +1 -1
  78. package/dist/esm/v1/foundations/icons/icons.js +61 -2
  79. package/dist/esm/v1/foundations/icons/icons.js.map +1 -1
  80. package/dist/esm/v1/primitives/buttons/Button/Button.js +18 -4
  81. package/dist/esm/v1/primitives/buttons/Button/Button.js.map +1 -1
  82. package/dist/esm/v1/primitives/buttons/SegmentedControl/SegmentedControl.js +65 -0
  83. package/dist/esm/v1/primitives/buttons/SegmentedControl/SegmentedControl.js.map +1 -0
  84. package/dist/esm/v1/primitives/buttons/SegmentedControl/segmentedStyles.js +10 -0
  85. package/dist/esm/v1/primitives/buttons/SegmentedControl/segmentedStyles.js.map +1 -0
  86. package/dist/esm/v1/primitives/display/Avatar/Avatar.js +120 -0
  87. package/dist/esm/v1/primitives/display/Avatar/Avatar.js.map +1 -0
  88. package/dist/esm/v1/primitives/display/Badge/Badge.js +23 -0
  89. package/dist/esm/v1/primitives/display/Badge/Badge.js.map +1 -0
  90. package/dist/esm/v1/primitives/display/Card/Card.js +22 -0
  91. package/dist/esm/v1/primitives/display/Card/Card.js.map +1 -0
  92. package/dist/esm/v1/primitives/display/FilterChips/FilterChips.js +45 -0
  93. package/dist/esm/v1/primitives/display/FilterChips/FilterChips.js.map +1 -0
  94. package/dist/esm/v1/primitives/display/Kpi/Kpi.js +103 -0
  95. package/dist/esm/v1/primitives/display/Kpi/Kpi.js.map +1 -0
  96. package/dist/esm/v1/primitives/display/Notice/Notice.js +71 -0
  97. package/dist/esm/v1/primitives/display/Notice/Notice.js.map +1 -0
  98. package/dist/esm/v1/primitives/display/Person/Person.js +14 -0
  99. package/dist/esm/v1/primitives/display/Person/Person.js.map +1 -0
  100. package/dist/esm/v1/primitives/forms/Checkbox/Checkbox.js +10 -5
  101. package/dist/esm/v1/primitives/forms/Checkbox/Checkbox.js.map +1 -1
  102. package/dist/esm/v1/primitives/forms/DateInput/DateInput.js +150 -0
  103. package/dist/esm/v1/primitives/forms/DateInput/DateInput.js.map +1 -0
  104. package/dist/esm/v1/primitives/forms/LookupInput/LookupInput.js.map +1 -1
  105. package/dist/esm/v1/primitives/forms/SearchInput/SearchInput.js +43 -0
  106. package/dist/esm/v1/primitives/forms/SearchInput/SearchInput.js.map +1 -0
  107. package/dist/esm/v1/primitives/forms/SelectInput/SelectInput.js +190 -12
  108. package/dist/esm/v1/primitives/forms/SelectInput/SelectInput.js.map +1 -1
  109. package/dist/esm/v1/primitives/forms/TextArea/TextArea.js.map +1 -1
  110. package/dist/esm/v1/primitives/forms/field.js +4 -2
  111. package/dist/esm/v1/primitives/forms/field.js.map +1 -1
  112. package/dist/esm/v1/primitives/lists/ListItem/ListItem.js +2 -2
  113. package/dist/esm/v1/primitives/lists/ListItem/ListItem.js.map +1 -1
  114. package/dist/esm/v1/primitives/navigation/Tabs/Tabs.js +96 -0
  115. package/dist/esm/v1/primitives/navigation/Tabs/Tabs.js.map +1 -0
  116. package/dist/style.components.css +1 -1
  117. package/dist/style.css +1 -1
  118. package/dist/style.layered.css +1 -1
  119. package/dist/tailwind.css +24 -0
  120. package/dist/theme-boot.js +1 -0
  121. package/dist/theme.css +10 -3
  122. package/dist/tokens.css +119 -0
  123. package/dist/types/legacy/components/atoms/InputData/InputData.d.ts +4 -1
  124. package/dist/types/legacy/components/charts/Charts.d.ts +58 -5
  125. package/dist/types/legacy/components/layout/Layout/Layout.d.ts +7 -20
  126. package/dist/types/legacy/components/layout/Sidebar/Sidebar.d.ts +13 -26
  127. package/dist/types/legacy/components/molecules/ColumnPicker/ColumnPicker.d.ts +56 -3
  128. package/dist/types/legacy/components/molecules/DataTable/DataTable.d.ts +72 -7
  129. package/dist/types/legacy/components/molecules/UserAvatar/UserAvatar.d.ts +4 -5
  130. package/dist/types/legacy/components/ui/Avisos.d.ts +6 -16
  131. package/dist/types/legacy/components/ui/CabecalhoPagina.d.ts +6 -20
  132. package/dist/types/legacy/components/ui/CaixaPesquisa.d.ts +2 -4
  133. package/dist/types/legacy/components/ui/Confirmacao.d.ts +3 -10
  134. package/dist/types/legacy/components/ui/Escolha.d.ts +5 -15
  135. package/dist/types/legacy/components/ui/FaixaAviso.d.ts +2 -6
  136. package/dist/types/legacy/components/ui/Separadores.d.ts +3 -10
  137. package/dist/types/legacy/components/ui/Ui.d.ts +12 -54
  138. package/dist/types/legacy/components/ui/painelFlutuante.d.ts +6 -10
  139. package/dist/types/legacy/exports/atoms.d.ts +1 -1
  140. package/dist/types/legacy/exports/charts.d.ts +2 -2
  141. package/dist/types/legacy/exports/hooks.d.ts +2 -2
  142. package/dist/types/legacy/exports/molecules.d.ts +2 -2
  143. package/dist/types/v1/capabilities/overlay/useFloatingPanel.d.ts +20 -0
  144. package/dist/types/v1/capabilities/theme/useIsDark.d.ts +10 -0
  145. package/dist/types/v1/capabilities/theme/useTheme.d.ts +29 -0
  146. package/dist/types/v1/components/data/Pagination/Pagination.d.ts +33 -0
  147. package/dist/types/v1/components/feedback/Toast/Toast.d.ts +51 -0
  148. package/dist/types/v1/components/forms/FormField/FormField.d.ts +3 -3
  149. package/dist/types/v1/components/forms/FormGrid/FormGrid.d.ts +2 -0
  150. package/dist/types/v1/components/layout/AppShell/AppShell.d.ts +35 -0
  151. package/dist/types/v1/components/layout/Page/Page.d.ts +23 -0
  152. package/dist/types/v1/components/layout/PageHeader/PageHeader.d.ts +35 -0
  153. package/dist/types/v1/components/layout/SideNav/SideNav.d.ts +92 -0
  154. package/dist/types/v1/components/layout/navTrail.d.ts +15 -0
  155. package/dist/types/v1/components/lists/ListFinder/ListFinder.d.ts +1 -1
  156. package/dist/types/v1/components/overlays/ConfirmDialog/ConfirmDialog.d.ts +59 -0
  157. package/dist/types/v1/components/overlays/Dialog/Dialog.d.ts +6 -3
  158. package/dist/types/v1/components/overlays/Tooltip/Tooltip.d.ts +34 -0
  159. package/dist/types/v1/components/overlays/Tooltip/TooltipLayer.d.ts +18 -0
  160. package/dist/types/v1/components/overlays/Tooltip/TooltipPanel.d.ts +23 -0
  161. package/dist/types/v1/components/overlays/topLayer.d.ts +23 -0
  162. package/dist/types/v1/components/tables/PaginatedTable/PaginatedTable.d.ts +1 -1
  163. package/dist/types/v1/components/tables/Table/Table.d.ts +1 -1
  164. package/dist/types/v1/foundations/icons/icons.d.ts +20 -0
  165. package/dist/types/v1/index.d.ts +43 -1
  166. package/dist/types/v1/primitives/buttons/Button/Button.d.ts +22 -5
  167. package/dist/types/v1/primitives/buttons/SegmentedControl/SegmentedControl.d.ts +28 -0
  168. package/dist/types/v1/primitives/buttons/SegmentedControl/segmentedStyles.d.ts +16 -0
  169. package/dist/types/v1/primitives/display/Avatar/Avatar.d.ts +30 -0
  170. package/dist/types/v1/primitives/display/Badge/Badge.d.ts +25 -0
  171. package/dist/types/v1/primitives/display/Card/Card.d.ts +22 -0
  172. package/dist/types/v1/primitives/display/FilterChips/FilterChips.d.ts +33 -0
  173. package/dist/types/v1/primitives/display/Kpi/Kpi.d.ts +68 -0
  174. package/dist/types/v1/primitives/display/Notice/Notice.d.ts +29 -0
  175. package/dist/types/v1/primitives/display/Person/Person.d.ts +15 -0
  176. package/dist/types/v1/primitives/forms/Checkbox/Checkbox.d.ts +7 -0
  177. package/dist/types/v1/primitives/forms/DateInput/DateInput.d.ts +43 -0
  178. package/dist/types/v1/primitives/forms/LookupInput/LookupInput.d.ts +3 -0
  179. package/dist/types/v1/primitives/forms/SearchInput/SearchInput.d.ts +23 -0
  180. package/dist/types/v1/primitives/forms/SelectInput/SelectInput.d.ts +61 -10
  181. package/dist/types/v1/primitives/forms/TextArea/TextArea.d.ts +3 -0
  182. package/dist/types/v1/primitives/forms/field.d.ts +2 -0
  183. package/dist/types/v1/primitives/lists/ListItem/ListItem.d.ts +2 -1
  184. package/dist/types/v1/primitives/navigation/Tabs/Tabs.d.ts +58 -0
  185. package/package.json +3 -3
  186. package/dist/esm/legacy/components/atoms/Tooltip/Tooltip.css +0 -17
  187. package/dist/esm/legacy/components/atoms/Tooltip/Tooltip.js +0 -41
  188. package/dist/esm/legacy/components/atoms/Tooltip/Tooltip.js.map +0 -1
  189. package/dist/esm/legacy/components/molecules/Search/Search.css +0 -18
  190. package/dist/esm/legacy/components/molecules/Search/Search.js +0 -30
  191. package/dist/esm/legacy/components/molecules/Search/Search.js.map +0 -1
  192. package/dist/esm/legacy/hooks/useTheme.js +0 -39
  193. package/dist/esm/legacy/hooks/useTheme.js.map +0 -1
  194. package/dist/esm/v1/primitives/lists/ListItem/ListCheckbox.js +0 -28
  195. package/dist/esm/v1/primitives/lists/ListItem/ListCheckbox.js.map +0 -1
  196. package/dist/types/legacy/components/atoms/Tooltip/Tooltip.d.ts +0 -13
  197. package/dist/types/legacy/components/molecules/Search/Search.d.ts +0 -7
  198. package/dist/types/legacy/hooks/useTheme.d.ts +0 -17
  199. package/dist/types/v1/primitives/lists/ListItem/ListCheckbox.d.ts +0 -14
@@ -1 +1 @@
1
- {"version":3,"file":"Selector.js","sources":["../../../../../../src/legacy/components/organisms/Selector/Selector.tsx"],"sourcesContent":["import React, { ReactNode, useEffect, useId, useState } from 'react'\r\nimport {\r\n faMinus,\r\n faPlus,\r\n faQuestion,\r\n faSave,\r\n} from '@fortawesome/free-solid-svg-icons'\r\nimport { IconProp } from '@fortawesome/fontawesome-svg-core'\r\nimport { ActionButton, IconText, IconButton } from '../../../exports/atoms'\r\nimport {\r\n ActionButtonThemeStyled,\r\n IconButtonThemeStyled,\r\n IconTextDarkThemeStyled,\r\n IconTextLightThemeStyled,\r\n} from '../../../styles/themes/ButtonThemes'\r\n\r\nimport Modal from '../../molecules/Modal/Modal'\r\nimport Search from '../../molecules/Search/Search'\r\nimport { Fetcher } from '../../../types/Fetcher'\r\nimport { LazyLoader } from '../LazyLoader/LazyLoader'\r\nimport './Selector.scss'\r\nimport { SelectableElement } from '../../../types/SelectableElement'\r\nimport Spinner from '../../layout/Spinner/Spinner'\r\nimport TooltipWrapper from '../../atoms/Tooltip/Tooltip'\r\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome'\r\n\r\ntype SelectorProps<T extends SelectableElement> = {\r\n title: string\r\n onClose: () => void\r\n onConfirm: (selected: T[]) => void\r\n onDisabled?: (disabled: T) => ReactNode\r\n initiallySelected: T[]\r\n blocked?: string[]\r\n single?: boolean\r\n icon: IconProp\r\n fetcher: Fetcher\r\n working?: boolean\r\n}\r\n\r\n/** @deprecated Legacy — não usar em código novo. Ver Storybook › Legacy. */\r\nexport const Selector = <T extends SelectableElement>({\r\n title,\r\n icon,\r\n onClose,\r\n onConfirm,\r\n initiallySelected,\r\n blocked = [],\r\n fetcher,\r\n single = false,\r\n working = false,\r\n onDisabled,\r\n}: SelectorProps<T>) => {\r\n const scrollContainerId = useId()\r\n const [selectedElements, setSelectedElements] =\r\n useState<T[]>(initiallySelected)\r\n\r\n const [filter, setFilter] = useState({\r\n term: {\r\n type: 'text',\r\n active: false,\r\n text: '',\r\n },\r\n })\r\n\r\n useEffect(() => {\r\n setSelectedElements(initiallySelected)\r\n }, [initiallySelected])\r\n\r\n const handleSearch = (text: string) => {\r\n setFilter({\r\n term: {\r\n type: 'text',\r\n active: text != '' ? true : false,\r\n text: text,\r\n },\r\n })\r\n }\r\n\r\n const toggleElementSelection = (element: T) => {\r\n const isSelected = selectedElements.some((se) => se.id === element.id)\r\n\r\n if (isSelected) {\r\n setSelectedElements(selectedElements.filter((se) => se.id !== element.id))\r\n } else {\r\n if (single) {\r\n setSelectedElements([element])\r\n } else {\r\n setSelectedElements([...selectedElements, element])\r\n }\r\n }\r\n }\r\n\r\n const renderElement = (element: T) => {\r\n const isSelected = selectedElements.some((se) => se.id === element.id)\r\n const isBlocked = blocked.includes(element.id)\r\n const isDisabled = element.disabled || false\r\n\r\n return (\r\n <li\r\n key={element.id}\r\n className={`cui-selector__elements-list-item ${\r\n isSelected\r\n ? 'cui-selector__elements-list-item-selected'\r\n : 'cui-selector__elements-list-item-not-selected'\r\n } ${isBlocked ? 'cui-selector__elements-list-item-blocked' : ''}`}\r\n onClick={\r\n !isBlocked && !isDisabled\r\n ? () => toggleElementSelection(element)\r\n : undefined\r\n }\r\n >\r\n <span className={'cui-selector__elements-list-item-description'}>\r\n <IconText\r\n icon={icon}\r\n text={element.name}\r\n theme={\r\n isSelected ? IconTextDarkThemeStyled : IconTextLightThemeStyled\r\n }\r\n />\r\n </span>\r\n <span className={'cui-selector__elements-list-item-option'}>\r\n {element.code && <label>{element.code}</label>}\r\n {!isBlocked && !isDisabled ? (\r\n <IconButton\r\n onClick={() => {\r\n toggleElementSelection(element)\r\n }}\r\n icon={isSelected ? faMinus : faPlus}\r\n theme={IconButtonThemeStyled}\r\n />\r\n ) : (\r\n <TooltipWrapper\r\n interactive={true}\r\n tip={\r\n onDisabled ? (\r\n onDisabled(element)\r\n ) : isBlocked ? (\r\n <div>Bloqueado...</div>\r\n ) : (\r\n <div>Sem dados....</div>\r\n )\r\n }\r\n >\r\n <IconButton\r\n onClick={() => {}}\r\n icon={faQuestion}\r\n theme={IconButtonThemeStyled}\r\n disabled={true}\r\n />\r\n </TooltipWrapper>\r\n )}\r\n </span>\r\n </li>\r\n )\r\n }\r\n\r\n const renderSelectedElements = () => {\r\n if (selectedElements.length === 0) {\r\n return (\r\n <p className=\"cui-selector__selected-empty\">\r\n Sem elementos selecionados...\r\n </p>\r\n )\r\n }\r\n\r\n return (\r\n <ul className=\"cui-selector__selected-list\">\r\n {selectedElements.map((element) => {\r\n const isBlocked = blocked.includes(element.id)\r\n\r\n if (isBlocked) return null\r\n\r\n return (\r\n <li key={element.id} className=\"cui-selector__selected-list-item\">\r\n <span className={'cui-selector__selected-list-info'}>\r\n <IconText\r\n icon={icon}\r\n theme={IconTextDarkThemeStyled}\r\n text={element.name}\r\n />\r\n </span>\r\n <span className={'cui-selector__selected-list-option'}>\r\n <IconButton\r\n icon={faMinus}\r\n onClick={() =>\r\n setSelectedElements(\r\n selectedElements.filter((e) => e.id !== element.id)\r\n )\r\n }\r\n theme={IconButtonThemeStyled}\r\n />\r\n </span>\r\n </li>\r\n )\r\n })}\r\n </ul>\r\n )\r\n }\r\n\r\n const handleConfirm = () => {\r\n onConfirm(selectedElements)\r\n }\r\n\r\n return (\r\n <Modal title={title} onClose={onClose}>\r\n <div className=\"cui-selector\">\r\n <div className=\"cui-selector__search\">\r\n <Search handleSearch={handleSearch} />\r\n </div>\r\n\r\n <div className=\"cui-selector__selected\">{renderSelectedElements()}</div>\r\n\r\n <div id={scrollContainerId} className=\"cui-selector__elements\">\r\n <LazyLoader<T>\r\n endpoint={fetcher.endpoint}\r\n params={{\r\n filters: {\r\n ...fetcher.params,\r\n ...(filter.term.active && {\r\n term: {\r\n type: filter.term.type,\r\n text: filter.term.text,\r\n },\r\n }),\r\n },\r\n }}\r\n limit={15}\r\n scrollableTarget={scrollContainerId}\r\n >\r\n {(items, loading, error) => (\r\n <ul className=\"cui-selector__elements-list\">\r\n {items.length > 0 ? (\r\n items.map((element) => renderElement(element))\r\n ) : (\r\n <li className=\"cui-selector__elements-empty\">\r\n No elements found\r\n </li>\r\n )}\r\n </ul>\r\n )}\r\n </LazyLoader>\r\n </div>\r\n\r\n <div className=\"cui-selector__confirmation\">\r\n {!working ? (\r\n <ActionButton\r\n title=\"Confirmar\"\r\n icon={<FontAwesomeIcon icon={faSave} />}\r\n onClick={handleConfirm}\r\n theme={ActionButtonThemeStyled}\r\n />\r\n ) : (\r\n <Spinner />\r\n )}\r\n </div>\r\n </div>\r\n </Modal>\r\n )\r\n}\r\n"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"Selector.js","sources":["../../../../../../src/legacy/components/organisms/Selector/Selector.tsx"],"sourcesContent":["import React, { ReactNode, useEffect, useId, useState } from 'react'\r\nimport {\r\n faMinus,\r\n faPlus,\r\n faQuestion,\r\n faSave,\r\n} from '@fortawesome/free-solid-svg-icons'\r\nimport { IconProp } from '@fortawesome/fontawesome-svg-core'\r\nimport { ActionButton, IconText, IconButton } from '../../../exports/atoms'\r\nimport {\r\n ActionButtonThemeStyled,\r\n IconButtonThemeStyled,\r\n IconTextDarkThemeStyled,\r\n IconTextLightThemeStyled,\r\n} from '../../../styles/themes/ButtonThemes'\r\n\r\nimport Modal from '../../molecules/Modal/Modal'\r\nimport SearchInput from '../../../../v1/primitives/forms/SearchInput/SearchInput'\r\nimport { Fetcher } from '../../../types/Fetcher'\r\nimport { LazyLoader } from '../LazyLoader/LazyLoader'\r\nimport './Selector.scss'\r\nimport { SelectableElement } from '../../../types/SelectableElement'\r\nimport Spinner from '../../layout/Spinner/Spinner'\r\nimport TooltipWrapper from '../../../../v1/components/overlays/Tooltip/Tooltip'\r\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome'\r\n\r\ntype SelectorProps<T extends SelectableElement> = {\r\n title: string\r\n onClose: () => void\r\n onConfirm: (selected: T[]) => void\r\n onDisabled?: (disabled: T) => ReactNode\r\n initiallySelected: T[]\r\n blocked?: string[]\r\n single?: boolean\r\n icon: IconProp\r\n fetcher: Fetcher\r\n working?: boolean\r\n}\r\n\r\n/** @deprecated Legacy — não usar em código novo. Ver Storybook › Legacy. */\r\nexport const Selector = <T extends SelectableElement>({\r\n title,\r\n icon,\r\n onClose,\r\n onConfirm,\r\n initiallySelected,\r\n blocked = [],\r\n fetcher,\r\n single = false,\r\n working = false,\r\n onDisabled,\r\n}: SelectorProps<T>) => {\r\n const scrollContainerId = useId()\r\n const [selectedElements, setSelectedElements] =\r\n useState<T[]>(initiallySelected)\r\n\r\n const [filter, setFilter] = useState({\r\n term: {\r\n type: 'text',\r\n active: false,\r\n text: '',\r\n },\r\n })\r\n\r\n useEffect(() => {\r\n setSelectedElements(initiallySelected)\r\n }, [initiallySelected])\r\n\r\n const handleSearch = (text: string) => {\r\n setFilter({\r\n term: {\r\n type: 'text',\r\n active: text != '' ? true : false,\r\n text: text,\r\n },\r\n })\r\n }\r\n\r\n const toggleElementSelection = (element: T) => {\r\n const isSelected = selectedElements.some((se) => se.id === element.id)\r\n\r\n if (isSelected) {\r\n setSelectedElements(selectedElements.filter((se) => se.id !== element.id))\r\n } else {\r\n if (single) {\r\n setSelectedElements([element])\r\n } else {\r\n setSelectedElements([...selectedElements, element])\r\n }\r\n }\r\n }\r\n\r\n const renderElement = (element: T) => {\r\n const isSelected = selectedElements.some((se) => se.id === element.id)\r\n const isBlocked = blocked.includes(element.id)\r\n const isDisabled = element.disabled || false\r\n\r\n return (\r\n <li\r\n key={element.id}\r\n className={`cui-selector__elements-list-item ${\r\n isSelected\r\n ? 'cui-selector__elements-list-item-selected'\r\n : 'cui-selector__elements-list-item-not-selected'\r\n } ${isBlocked ? 'cui-selector__elements-list-item-blocked' : ''}`}\r\n onClick={\r\n !isBlocked && !isDisabled\r\n ? () => toggleElementSelection(element)\r\n : undefined\r\n }\r\n >\r\n <span className={'cui-selector__elements-list-item-description'}>\r\n <IconText\r\n icon={icon}\r\n text={element.name}\r\n theme={\r\n isSelected ? IconTextDarkThemeStyled : IconTextLightThemeStyled\r\n }\r\n />\r\n </span>\r\n <span className={'cui-selector__elements-list-item-option'}>\r\n {element.code && <label>{element.code}</label>}\r\n {!isBlocked && !isDisabled ? (\r\n <IconButton\r\n onClick={() => {\r\n toggleElementSelection(element)\r\n }}\r\n icon={isSelected ? faMinus : faPlus}\r\n theme={IconButtonThemeStyled}\r\n />\r\n ) : (\r\n <TooltipWrapper\r\n interactive={true}\r\n tip={\r\n onDisabled ? (\r\n onDisabled(element)\r\n ) : isBlocked ? (\r\n <div>Bloqueado...</div>\r\n ) : (\r\n <div>Sem dados....</div>\r\n )\r\n }\r\n >\r\n <IconButton\r\n onClick={() => {}}\r\n icon={faQuestion}\r\n theme={IconButtonThemeStyled}\r\n disabled={true}\r\n />\r\n </TooltipWrapper>\r\n )}\r\n </span>\r\n </li>\r\n )\r\n }\r\n\r\n const renderSelectedElements = () => {\r\n if (selectedElements.length === 0) {\r\n return (\r\n <p className=\"cui-selector__selected-empty\">\r\n Sem elementos selecionados...\r\n </p>\r\n )\r\n }\r\n\r\n return (\r\n <ul className=\"cui-selector__selected-list\">\r\n {selectedElements.map((element) => {\r\n const isBlocked = blocked.includes(element.id)\r\n\r\n if (isBlocked) return null\r\n\r\n return (\r\n <li key={element.id} className=\"cui-selector__selected-list-item\">\r\n <span className={'cui-selector__selected-list-info'}>\r\n <IconText\r\n icon={icon}\r\n theme={IconTextDarkThemeStyled}\r\n text={element.name}\r\n />\r\n </span>\r\n <span className={'cui-selector__selected-list-option'}>\r\n <IconButton\r\n icon={faMinus}\r\n onClick={() =>\r\n setSelectedElements(\r\n selectedElements.filter((e) => e.id !== element.id)\r\n )\r\n }\r\n theme={IconButtonThemeStyled}\r\n />\r\n </span>\r\n </li>\r\n )\r\n })}\r\n </ul>\r\n )\r\n }\r\n\r\n const handleConfirm = () => {\r\n onConfirm(selectedElements)\r\n }\r\n\r\n return (\r\n <Modal title={title} onClose={onClose}>\r\n <div className=\"cui-selector\">\r\n <div className=\"cui-selector__search\">\r\n <SearchInput value={filter.term.text} onChange={handleSearch} className=\"w-full\" />\r\n </div>\r\n\r\n <div className=\"cui-selector__selected\">{renderSelectedElements()}</div>\r\n\r\n <div id={scrollContainerId} className=\"cui-selector__elements\">\r\n <LazyLoader<T>\r\n endpoint={fetcher.endpoint}\r\n params={{\r\n filters: {\r\n ...fetcher.params,\r\n ...(filter.term.active && {\r\n term: {\r\n type: filter.term.type,\r\n text: filter.term.text,\r\n },\r\n }),\r\n },\r\n }}\r\n limit={15}\r\n scrollableTarget={scrollContainerId}\r\n >\r\n {(items, loading, error) => (\r\n <ul className=\"cui-selector__elements-list\">\r\n {items.length > 0 ? (\r\n items.map((element) => renderElement(element))\r\n ) : (\r\n <li className=\"cui-selector__elements-empty\">\r\n No elements found\r\n </li>\r\n )}\r\n </ul>\r\n )}\r\n </LazyLoader>\r\n </div>\r\n\r\n <div className=\"cui-selector__confirmation\">\r\n {!working ? (\r\n <ActionButton\r\n title=\"Confirmar\"\r\n icon={<FontAwesomeIcon icon={faSave} />}\r\n onClick={handleConfirm}\r\n theme={ActionButtonThemeStyled}\r\n />\r\n ) : (\r\n <Spinner />\r\n )}\r\n </div>\r\n </div>\r\n </Modal>\r\n )\r\n}\r\n"],"names":["TooltipWrapper"],"mappings":";;;;;;;;;;;;;;AAwCO,MAAM,WAAW,CAA8B;AAAA,EACpD;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA,UAAU,CAAA;AAAA,EACV;AAAA,EACA,SAAS;AAAA,EACT,UAAU;AAAA,EACV;AACF,MAAwB;AACtB,QAAM,oBAAoB,MAAA;AAC1B,QAAM,CAAC,kBAAkB,mBAAmB,IAC1C,SAAc,iBAAiB;AAEjC,QAAM,CAAC,QAAQ,SAAS,IAAI,SAAS;AAAA,IACnC,MAAM;AAAA,MACJ,MAAM;AAAA,MACN,QAAQ;AAAA,MACR,MAAM;AAAA,IAAA;AAAA,EACR,CACD;AAED,YAAU,MAAM;AACd,wBAAoB,iBAAiB;AAAA,EACvC,GAAG,CAAC,iBAAiB,CAAC;AAEtB,QAAM,eAAe,CAAC,SAAiB;AACrC,cAAU;AAAA,MACR,MAAM;AAAA,QACJ,MAAM;AAAA,QACN,QAAQ,QAAQ,KAAK,OAAO;AAAA,QAC5B;AAAA,MAAA;AAAA,IACF,CACD;AAAA,EACH;AAEA,QAAM,yBAAyB,CAAC,YAAe;AAC7C,UAAM,aAAa,iBAAiB,KAAK,CAAC,OAAO,GAAG,OAAO,QAAQ,EAAE;AAErE,QAAI,YAAY;AACd,0BAAoB,iBAAiB,OAAO,CAAC,OAAO,GAAG,OAAO,QAAQ,EAAE,CAAC;AAAA,IAC3E,OAAO;AACL,UAAI,QAAQ;AACV,4BAAoB,CAAC,OAAO,CAAC;AAAA,MAC/B,OAAO;AACL,4BAAoB,CAAC,GAAG,kBAAkB,OAAO,CAAC;AAAA,MACpD;AAAA,IACF;AAAA,EACF;AAEA,QAAM,gBAAgB,CAAC,YAAe;AACpC,UAAM,aAAa,iBAAiB,KAAK,CAAC,OAAO,GAAG,OAAO,QAAQ,EAAE;AACrE,UAAM,YAAY,QAAQ,SAAS,QAAQ,EAAE;AAC7C,UAAM,aAAa,QAAQ,YAAY;AAEvC,WACE;AAAA,MAAC;AAAA,MAAA;AAAA,QAEC,WAAW,oCACT,aACI,8CACA,+CACN,IAAI,YAAY,6CAA6C,EAAE;AAAA,QAC/D,SACE,CAAC,aAAa,CAAC,aACX,MAAM,uBAAuB,OAAO,IACpC;AAAA,QAGN,UAAA;AAAA,UAAA,oBAAC,QAAA,EAAK,WAAW,gDACf,UAAA;AAAA,YAAC;AAAA,YAAA;AAAA,cACC;AAAA,cACA,MAAM,QAAQ;AAAA,cACd,OACE,aAAa,0BAA0B;AAAA,YAAA;AAAA,UAAA,GAG7C;AAAA,UACA,qBAAC,QAAA,EAAK,WAAW,2CACd,UAAA;AAAA,YAAA,QAAQ,QAAQ,oBAAC,SAAA,EAAO,UAAA,QAAQ,MAAK;AAAA,YACrC,CAAC,aAAa,CAAC,aACd;AAAA,cAAC;AAAA,cAAA;AAAA,gBACC,SAAS,MAAM;AACb,yCAAuB,OAAO;AAAA,gBAChC;AAAA,gBACA,MAAM,aAAa,UAAU;AAAA,gBAC7B,OAAO;AAAA,cAAA;AAAA,YAAA,IAGT;AAAA,cAACA;AAAAA,cAAA;AAAA,gBACC,aAAa;AAAA,gBACb,KACE,aACE,WAAW,OAAO,IAChB,YACF,oBAAC,OAAA,EAAI,UAAA,eAAA,CAAY,IAEjB,oBAAC,OAAA,EAAI,UAAA,iBAAa;AAAA,gBAItB,UAAA;AAAA,kBAAC;AAAA,kBAAA;AAAA,oBACC,SAAS,MAAM;AAAA,oBAAC;AAAA,oBAChB,MAAM;AAAA,oBACN,OAAO;AAAA,oBACP,UAAU;AAAA,kBAAA;AAAA,gBAAA;AAAA,cACZ;AAAA,YAAA;AAAA,UACF,EAAA,CAEJ;AAAA,QAAA;AAAA,MAAA;AAAA,MApDK,QAAQ;AAAA,IAAA;AAAA,EAuDnB;AAEA,QAAM,yBAAyB,MAAM;AACnC,QAAI,iBAAiB,WAAW,GAAG;AACjC,aACE,oBAAC,KAAA,EAAE,WAAU,gCAA+B,UAAA,iCAE5C;AAAA,IAEJ;AAEA,+BACG,MAAA,EAAG,WAAU,+BACX,UAAA,iBAAiB,IAAI,CAAC,YAAY;AACjC,YAAM,YAAY,QAAQ,SAAS,QAAQ,EAAE;AAE7C,UAAI,UAAW,QAAO;AAEtB,aACE,qBAAC,MAAA,EAAoB,WAAU,oCAC7B,UAAA;AAAA,QAAA,oBAAC,QAAA,EAAK,WAAW,oCACf,UAAA;AAAA,UAAC;AAAA,UAAA;AAAA,YACC;AAAA,YACA,OAAO;AAAA,YACP,MAAM,QAAQ;AAAA,UAAA;AAAA,QAAA,GAElB;AAAA,QACA,oBAAC,QAAA,EAAK,WAAW,sCACf,UAAA;AAAA,UAAC;AAAA,UAAA;AAAA,YACC,MAAM;AAAA,YACN,SAAS,MACP;AAAA,cACE,iBAAiB,OAAO,CAAC,MAAM,EAAE,OAAO,QAAQ,EAAE;AAAA,YAAA;AAAA,YAGtD,OAAO;AAAA,UAAA;AAAA,QAAA,EACT,CACF;AAAA,MAAA,EAAA,GAlBO,QAAQ,EAmBjB;AAAA,IAEJ,CAAC,EAAA,CACH;AAAA,EAEJ;AAEA,QAAM,gBAAgB,MAAM;AAC1B,cAAU,gBAAgB;AAAA,EAC5B;AAEA,6BACG,OAAA,EAAM,OAAc,SACnB,UAAA,qBAAC,OAAA,EAAI,WAAU,gBACb,UAAA;AAAA,IAAA,oBAAC,OAAA,EAAI,WAAU,wBACb,UAAA,oBAAC,aAAA,EAAY,OAAO,OAAO,KAAK,MAAM,UAAU,cAAc,WAAU,UAAS,GACnF;AAAA,IAEA,oBAAC,OAAA,EAAI,WAAU,0BAA0B,oCAAyB;AAAA,IAElE,oBAAC,OAAA,EAAI,IAAI,mBAAmB,WAAU,0BACpC,UAAA;AAAA,MAAC;AAAA,MAAA;AAAA,QACC,UAAU,QAAQ;AAAA,QAClB,QAAQ;AAAA,UACN,SAAS;AAAA,YACP,GAAG,QAAQ;AAAA,YACX,GAAI,OAAO,KAAK,UAAU;AAAA,cACxB,MAAM;AAAA,gBACJ,MAAM,OAAO,KAAK;AAAA,gBAClB,MAAM,OAAO,KAAK;AAAA,cAAA;AAAA,YACpB;AAAA,UACF;AAAA,QACF;AAAA,QAEF,OAAO;AAAA,QACP,kBAAkB;AAAA,QAEjB,UAAA,CAAC,OAAO,SAAS,UAChB,oBAAC,QAAG,WAAU,+BACX,UAAA,MAAM,SAAS,IACd,MAAM,IAAI,CAAC,YAAY,cAAc,OAAO,CAAC,wBAE5C,MAAA,EAAG,WAAU,gCAA+B,UAAA,oBAAA,CAE7C,EAAA,CAEJ;AAAA,MAAA;AAAA,IAAA,GAGN;AAAA,IAEA,oBAAC,OAAA,EAAI,WAAU,8BACZ,WAAC,UACA;AAAA,MAAC;AAAA,MAAA;AAAA,QACC,OAAM;AAAA,QACN,MAAM,oBAAC,iBAAA,EAAgB,MAAM,OAAA,CAAQ;AAAA,QACrC,SAAS;AAAA,QACT,OAAO;AAAA,MAAA;AAAA,IAAA,IAGT,oBAAC,SAAA,CAAA,CAAQ,EAAA,CAEb;AAAA,EAAA,EAAA,CACF,EAAA,CACF;AAEJ;"}
@@ -1,83 +1,30 @@
1
- import { jsxs, jsx } from "react/jsx-runtime";
2
- import { useState, useRef, useCallback, useEffect, useMemo, useContext, createContext } from "react";
3
- const Contexto = createContext(null);
4
- const DURACAO = { sucesso: 4e3, info: 5e3, aviso: 7e3, erro: 9e3 };
1
+ import { jsx } from "react/jsx-runtime";
2
+ import { useMemo } from "react";
3
+ import ToastProvider, { useToast } from "../../../v1/components/feedback/Toast/Toast.js";
4
+ const opcoesV1 = (o = {}) => ({
5
+ duration: o.duracao,
6
+ action: o.acao && { label: o.acao.rotulo, onClick: o.acao.onClick }
7
+ });
5
8
  function AvisosProvider({ children, rotuloFechar = "Fechar aviso", maximo = 4 }) {
6
- const [avisos, setAvisos] = useState([]);
7
- const seq = useRef(0);
8
- const temporizadores = useRef(/* @__PURE__ */ new Map());
9
- const fechar = useCallback((id) => {
10
- const t = temporizadores.current.get(id);
11
- if (t) clearTimeout(t);
12
- temporizadores.current.delete(id);
13
- setAvisos((l) => l.filter((a) => a.id !== id));
14
- }, []);
15
- const mostrar = useCallback(
16
- (tipo, mensagem, opcoes = {}) => {
17
- const id = ++seq.current;
18
- setAvisos((l) => [...l, { id, tipo, mensagem, ...opcoes }].slice(-maximo));
19
- const duracao = opcoes.duracao ?? DURACAO[tipo];
20
- if (duracao > 0) temporizadores.current.set(id, setTimeout(() => fechar(id), duracao));
21
- return id;
22
- },
23
- [fechar, maximo]
24
- );
25
- useEffect(() => {
26
- const mapa = temporizadores.current;
27
- return () => mapa.forEach((t) => clearTimeout(t));
28
- }, []);
29
- const api = useMemo(
9
+ return /* @__PURE__ */ jsx(ToastProvider, { closeLabel: rotuloFechar, max: maximo, children });
10
+ }
11
+ function useAvisos() {
12
+ let toast;
13
+ try {
14
+ toast = useToast();
15
+ } catch {
16
+ throw new Error("useAvisos tem de ser usado dentro de um <AvisosProvider>.");
17
+ }
18
+ return useMemo(
30
19
  () => ({
31
- sucesso: (m, o) => mostrar("sucesso", m, o),
32
- erro: (m, o) => mostrar("erro", m, o),
33
- aviso: (m, o) => mostrar("aviso", m, o),
34
- info: (m, o) => mostrar("info", m, o),
35
- fechar
20
+ sucesso: (m, o) => toast.success(m, opcoesV1(o)),
21
+ erro: (m, o) => toast.error(m, opcoesV1(o)),
22
+ aviso: (m, o) => toast.warning(m, opcoesV1(o)),
23
+ info: (m, o) => toast.info(m, opcoesV1(o)),
24
+ fechar: toast.dismiss
36
25
  }),
37
- [mostrar, fechar]
26
+ [toast]
38
27
  );
39
- const estilos = {
40
- sucesso: ["border-ok/30", "bg-ok-bg text-ok", "✓"],
41
- erro: ["border-incumprido/30", "bg-incumprido-bg text-incumprido", "!"],
42
- aviso: ["border-risco/30", "bg-risco-bg text-risco", "!"],
43
- info: ["border-sky-200", "bg-sky-50 text-sky-700", "i"]
44
- };
45
- return /* @__PURE__ */ jsxs(Contexto.Provider, { value: api, children: [
46
- children,
47
- /* @__PURE__ */ jsx("div", { "aria-live": "polite", className: "pointer-events-none fixed bottom-4 right-4 z-[70] flex w-[min(420px,calc(100vw-2rem))] flex-col gap-2", children: avisos.map((a) => {
48
- const [borda, icone, simbolo] = estilos[a.tipo];
49
- return /* @__PURE__ */ jsxs(
50
- "div",
51
- {
52
- role: a.tipo === "erro" ? "alert" : "status",
53
- className: `pointer-events-auto flex items-center gap-3 rounded-xl border ${borda} bg-white px-3.5 py-3 shadow-lg dark:bg-slate-900`,
54
- children: [
55
- /* @__PURE__ */ jsx("span", { "aria-hidden": "true", className: `flex h-6 w-6 shrink-0 items-center justify-center rounded-full text-xs font-black ${icone}`, children: simbolo }),
56
- /* @__PURE__ */ jsx("span", { className: "min-w-0 flex-1 text-sm font-semibold text-slate-800 dark:text-slate-100", children: a.mensagem }),
57
- a.acao && /* @__PURE__ */ jsx(
58
- "button",
59
- {
60
- type: "button",
61
- onClick: () => {
62
- a.acao.onClick();
63
- fechar(a.id);
64
- },
65
- className: "shrink-0 text-xs font-bold text-proef-blue hover:text-proef-navy",
66
- children: a.acao.rotulo
67
- }
68
- ),
69
- /* @__PURE__ */ jsx("button", { type: "button", onClick: () => fechar(a.id), "aria-label": rotuloFechar, className: "shrink-0 text-slate-400 hover:text-slate-700", children: "×" })
70
- ]
71
- },
72
- a.id
73
- );
74
- }) })
75
- ] });
76
- }
77
- function useAvisos() {
78
- const api = useContext(Contexto);
79
- if (!api) throw new Error("useAvisos tem de ser usado dentro de um <AvisosProvider>.");
80
- return api;
81
28
  }
82
29
  export {
83
30
  AvisosProvider,
@@ -1 +1 @@
1
- {"version":3,"file":"Avisos.js","sources":["../../../../../src/legacy/components/ui/Avisos.tsx"],"sourcesContent":["import React, { createContext, useCallback, useContext, useEffect, useMemo, useRef, useState, type ReactNode } from 'react'\r\n\r\n/** @deprecated Legacy — não usar em código novo. Ver Storybook › Legacy. */\r\nexport type TipoAviso = 'sucesso' | 'erro' | 'aviso' | 'info'\r\n\r\n/** @deprecated Legacy — não usar em código novo. Ver Storybook › Legacy. */\r\nexport interface OpcoesAviso {\r\n /** Botão no aviso (ex: \"Tentar de novo\", \"Desfazer\"). */\r\n acao?: { rotulo: string; onClick: () => void }\r\n /** Milissegundos até fechar sozinho. 0 = só fecha à mão. */\r\n duracao?: number\r\n}\r\n\r\ninterface Aviso extends OpcoesAviso {\r\n id: number\r\n tipo: TipoAviso\r\n mensagem: ReactNode\r\n}\r\n\r\n/** @deprecated Legacy — não usar em código novo. Ver Storybook › Legacy. */\r\nexport interface AvisosApi {\r\n sucesso: (mensagem: ReactNode, opcoes?: OpcoesAviso) => number\r\n erro: (mensagem: ReactNode, opcoes?: OpcoesAviso) => number\r\n aviso: (mensagem: ReactNode, opcoes?: OpcoesAviso) => number\r\n info: (mensagem: ReactNode, opcoes?: OpcoesAviso) => number\r\n fechar: (id: number) => void\r\n}\r\n\r\nconst Contexto = createContext<AvisosApi | null>(null)\r\n\r\n/** Erros ficam mais tempo: ler uma mensagem de erro demora mais do que um \"Guardado\". */\r\nconst DURACAO: Record<TipoAviso, number> = { sucesso: 4000, info: 5000, aviso: 7000, erro: 9000 }\r\n\r\n/** @deprecated Legacy — não usar em código novo. Ver Storybook › Legacy. */\r\nexport interface AvisosProviderProps {\r\n children: ReactNode\r\n /** Rótulo do botão de fechar (leitores de ecrã). */\r\n rotuloFechar?: string\r\n /** Máximo de avisos visíveis ao mesmo tempo; os mais antigos saem. */\r\n maximo?: number\r\n}\r\n\r\n/**\r\n * Avisos de resultado de ações (\"Guardado\", \"Não foi possível eliminar\").\r\n *\r\n * Substituem os `alert()` do browser e as caixas de erro feitas em cada página.\r\n * Pôr o provider uma vez à volta da app e usar `useAvisos()` onde for preciso.\r\n * Erros de validação de formulário NÃO vão aqui: ficam junto aos campos.\r\n * @deprecated Legacy — não usar em código novo. Ver Storybook › Legacy.\r\n */\r\nexport function AvisosProvider({ children, rotuloFechar = 'Fechar aviso', maximo = 4 }: AvisosProviderProps) {\r\n const [avisos, setAvisos] = useState<Aviso[]>([])\r\n const seq = useRef(0)\r\n const temporizadores = useRef(new Map<number, ReturnType<typeof setTimeout>>())\r\n\r\n const fechar = useCallback((id: number) => {\r\n const t = temporizadores.current.get(id)\r\n if (t) clearTimeout(t)\r\n temporizadores.current.delete(id)\r\n setAvisos((l) => l.filter((a) => a.id !== id))\r\n }, [])\r\n\r\n const mostrar = useCallback(\r\n (tipo: TipoAviso, mensagem: ReactNode, opcoes: OpcoesAviso = {}) => {\r\n const id = ++seq.current\r\n setAvisos((l) => [...l, { id, tipo, mensagem, ...opcoes }].slice(-maximo))\r\n const duracao = opcoes.duracao ?? DURACAO[tipo]\r\n if (duracao > 0) temporizadores.current.set(id, setTimeout(() => fechar(id), duracao))\r\n return id\r\n },\r\n [fechar, maximo]\r\n )\r\n\r\n useEffect(() => {\r\n const mapa = temporizadores.current\r\n return () => mapa.forEach((t) => clearTimeout(t))\r\n }, [])\r\n\r\n const api = useMemo<AvisosApi>(\r\n () => ({\r\n sucesso: (m, o) => mostrar('sucesso', m, o),\r\n erro: (m, o) => mostrar('erro', m, o),\r\n aviso: (m, o) => mostrar('aviso', m, o),\r\n info: (m, o) => mostrar('info', m, o),\r\n fechar,\r\n }),\r\n [mostrar, fechar]\r\n )\r\n\r\n const estilos: Record<TipoAviso, [string, string, string]> = {\r\n sucesso: ['border-ok/30', 'bg-ok-bg text-ok', '✓'],\r\n erro: ['border-incumprido/30', 'bg-incumprido-bg text-incumprido', '!'],\r\n aviso: ['border-risco/30', 'bg-risco-bg text-risco', '!'],\r\n info: ['border-sky-200', 'bg-sky-50 text-sky-700', 'i'],\r\n }\r\n\r\n return (\r\n <Contexto.Provider value={api}>\r\n {children}\r\n <div aria-live=\"polite\" className=\"pointer-events-none fixed bottom-4 right-4 z-[70] flex w-[min(420px,calc(100vw-2rem))] flex-col gap-2\">\r\n {avisos.map((a) => {\r\n const [borda, icone, simbolo] = estilos[a.tipo]\r\n return (\r\n <div\r\n key={a.id}\r\n role={a.tipo === 'erro' ? 'alert' : 'status'}\r\n className={`pointer-events-auto flex items-center gap-3 rounded-xl border ${borda} bg-white px-3.5 py-3 shadow-lg dark:bg-slate-900`}\r\n >\r\n <span aria-hidden=\"true\" className={`flex h-6 w-6 shrink-0 items-center justify-center rounded-full text-xs font-black ${icone}`}>\r\n {simbolo}\r\n </span>\r\n <span className=\"min-w-0 flex-1 text-sm font-semibold text-slate-800 dark:text-slate-100\">{a.mensagem}</span>\r\n {a.acao && (\r\n <button\r\n type=\"button\"\r\n onClick={() => {\r\n a.acao!.onClick()\r\n fechar(a.id)\r\n }}\r\n className=\"shrink-0 text-xs font-bold text-proef-blue hover:text-proef-navy\"\r\n >\r\n {a.acao.rotulo}\r\n </button>\r\n )}\r\n <button type=\"button\" onClick={() => fechar(a.id)} aria-label={rotuloFechar} className=\"shrink-0 text-slate-400 hover:text-slate-700\">\r\n ×\r\n </button>\r\n </div>\r\n )\r\n })}\r\n </div>\r\n </Contexto.Provider>\r\n )\r\n}\r\n\r\n/**\r\n * Avisos da app. Tem de estar dentro de um `AvisosProvider`.\r\n * @deprecated Legacy — não usar em código novo. Ver Storybook › Legacy.\r\n */\r\nexport function useAvisos(): AvisosApi {\r\n const api = useContext(Contexto)\r\n if (!api) throw new Error('useAvisos tem de ser usado dentro de um <AvisosProvider>.')\r\n return api\r\n}\r\n"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"Avisos.js","sources":["../../../../../src/legacy/components/ui/Avisos.tsx"],"sourcesContent":["import React, { useMemo, type ReactNode } from 'react'\r\nimport ToastProvider, { useToast, type ToastOptions } from '../../../v1/components/feedback/Toast/Toast'\r\n\r\n/*\r\n * Migrado para o V1: os avisos são o `ToastProvider` / `useToast` do V1. Este\r\n * ficheiro só traduz a API antiga (em português) para a nova, para as apps que\r\n * ainda a usam continuarem a funcionar sem mudanças.\r\n */\r\n\r\n/** @deprecated Legacy — usar `useToast` do V1. */\r\nexport type TipoAviso = 'sucesso' | 'erro' | 'aviso' | 'info'\r\n\r\n/** @deprecated Legacy — usar `ToastOptions` do V1. */\r\nexport interface OpcoesAviso {\r\n /** Botão no aviso (ex: \"Tentar de novo\", \"Desfazer\"). */\r\n acao?: { rotulo: string; onClick: () => void }\r\n /** Milissegundos até fechar sozinho. 0 = só fecha à mão. */\r\n duracao?: number\r\n}\r\n\r\n/** @deprecated Legacy — usar `ToastApi` do V1. */\r\nexport interface AvisosApi {\r\n sucesso: (mensagem: ReactNode, opcoes?: OpcoesAviso) => number\r\n erro: (mensagem: ReactNode, opcoes?: OpcoesAviso) => number\r\n aviso: (mensagem: ReactNode, opcoes?: OpcoesAviso) => number\r\n info: (mensagem: ReactNode, opcoes?: OpcoesAviso) => number\r\n fechar: (id: number) => void\r\n}\r\n\r\n/** @deprecated Legacy — usar `ToastProviderProps` do V1. */\r\nexport interface AvisosProviderProps {\r\n children: ReactNode\r\n /** Rótulo do botão de fechar (leitores de ecrã). */\r\n rotuloFechar?: string\r\n /** Máximo de avisos visíveis ao mesmo tempo; os mais antigos saem. */\r\n maximo?: number\r\n}\r\n\r\nconst opcoesV1 = (o: OpcoesAviso = {}): ToastOptions => ({\r\n duration: o.duracao,\r\n action: o.acao && { label: o.acao.rotulo, onClick: o.acao.onClick },\r\n})\r\n\r\n/** @deprecated Legacy — usar `ToastProvider` do V1. */\r\nexport function AvisosProvider({ children, rotuloFechar = 'Fechar aviso', maximo = 4 }: AvisosProviderProps) {\r\n return (\r\n <ToastProvider closeLabel={rotuloFechar} max={maximo}>\r\n {children}\r\n </ToastProvider>\r\n )\r\n}\r\n\r\n/** @deprecated Legacy — usar `useToast` do V1. */\r\nexport function useAvisos(): AvisosApi {\r\n let toast: ReturnType<typeof useToast>\r\n try {\r\n toast = useToast()\r\n } catch {\r\n // A mensagem de sempre, com o nome que estas apps conhecem.\r\n throw new Error('useAvisos tem de ser usado dentro de um <AvisosProvider>.')\r\n }\r\n return useMemo<AvisosApi>(\r\n () => ({\r\n sucesso: (m, o) => toast.success(m, opcoesV1(o)),\r\n erro: (m, o) => toast.error(m, opcoesV1(o)),\r\n aviso: (m, o) => toast.warning(m, opcoesV1(o)),\r\n info: (m, o) => toast.info(m, opcoesV1(o)),\r\n fechar: toast.dismiss,\r\n }),\r\n [toast],\r\n )\r\n}\r\n"],"names":[],"mappings":";;;AAsCA,MAAM,WAAW,CAAC,IAAiB,QAAsB;AAAA,EACvD,UAAU,EAAE;AAAA,EACZ,QAAQ,EAAE,QAAQ,EAAE,OAAO,EAAE,KAAK,QAAQ,SAAS,EAAE,KAAK,QAAA;AAC5D;AAGO,SAAS,eAAe,EAAE,UAAU,eAAe,gBAAgB,SAAS,KAA0B;AAC3G,6BACG,eAAA,EAAc,YAAY,cAAc,KAAK,QAC3C,UACH;AAEJ;AAGO,SAAS,YAAuB;AACrC,MAAI;AACJ,MAAI;AACF,YAAQ,SAAA;AAAA,EACV,QAAQ;AAEN,UAAM,IAAI,MAAM,2DAA2D;AAAA,EAC7E;AACA,SAAO;AAAA,IACL,OAAO;AAAA,MACL,SAAS,CAAC,GAAG,MAAM,MAAM,QAAQ,GAAG,SAAS,CAAC,CAAC;AAAA,MAC/C,MAAM,CAAC,GAAG,MAAM,MAAM,MAAM,GAAG,SAAS,CAAC,CAAC;AAAA,MAC1C,OAAO,CAAC,GAAG,MAAM,MAAM,QAAQ,GAAG,SAAS,CAAC,CAAC;AAAA,MAC7C,MAAM,CAAC,GAAG,MAAM,MAAM,KAAK,GAAG,SAAS,CAAC,CAAC;AAAA,MACzC,QAAQ,MAAM;AAAA,IAAA;AAAA,IAEhB,CAAC,KAAK;AAAA,EAAA;AAEV;"}
@@ -1,30 +1,17 @@
1
- import { jsxs, jsx } from "react/jsx-runtime";
2
- function CabecalhoPagina({
3
- titulo,
4
- descricao,
5
- caminho,
6
- acoes,
7
- extra,
8
- rotuloCaminho = "Caminho"
9
- }) {
10
- return /* @__PURE__ */ jsxs("header", { className: "flex flex-col gap-3", children: [
11
- caminho && caminho.length > 0 && /* @__PURE__ */ jsx("nav", { "aria-label": rotuloCaminho, children: /* @__PURE__ */ jsx("ol", { className: "flex flex-wrap items-center gap-1.5 text-xs font-semibold text-slate-500 dark:text-slate-400", children: caminho.map((n, i) => {
12
- const ultimo = i === caminho.length - 1;
13
- return /* @__PURE__ */ jsxs("li", { className: "flex items-center gap-1.5", children: [
14
- ultimo ? /* @__PURE__ */ jsx("span", { "aria-current": "page", className: "text-slate-600 dark:text-slate-300", children: n.rotulo }) : n.href ? /* @__PURE__ */ jsx("a", { href: n.href, onClick: n.onClick, className: "text-proef-blue hover:text-proef-navy hover:underline dark:text-sky-300 dark:hover:text-sky-200", children: n.rotulo }) : n.onClick ? /* @__PURE__ */ jsx("button", { type: "button", onClick: n.onClick, className: "text-proef-blue hover:text-proef-navy hover:underline dark:text-sky-300 dark:hover:text-sky-200", children: n.rotulo }) : /* @__PURE__ */ jsx("span", { children: n.rotulo }),
15
- !ultimo && /* @__PURE__ */ jsx("span", { "aria-hidden": "true", className: "text-slate-300 dark:text-slate-600", children: "›" })
16
- ] }, i);
17
- }) }) }),
18
- /* @__PURE__ */ jsxs("div", { className: "flex flex-col gap-4 lg:flex-row lg:items-end lg:justify-between", children: [
19
- /* @__PURE__ */ jsxs("div", { className: "min-w-0", children: [
20
- /* @__PURE__ */ jsx("h1", { className: "m-0 text-2xl md:text-4xl font-black uppercase tracking-tighter text-proef-navy dark:text-slate-100", children: titulo }),
21
- /* @__PURE__ */ jsx("div", { className: "mt-1 h-1 w-12 bg-proef-turquoise" }),
22
- descricao && /* @__PURE__ */ jsx("p", { className: "mt-3 text-sm font-medium text-slate-500 dark:text-slate-400", children: descricao }),
23
- extra && /* @__PURE__ */ jsx("div", { className: "mt-2 flex flex-wrap items-center gap-2", children: extra })
24
- ] }),
25
- acoes && /* @__PURE__ */ jsx("div", { className: "flex flex-wrap items-center gap-2 shrink-0", children: acoes })
26
- ] })
27
- ] });
1
+ import { jsx } from "react/jsx-runtime";
2
+ import PageHeader from "../../../v1/components/layout/PageHeader/PageHeader.js";
3
+ function CabecalhoPagina({ titulo, descricao, caminho, acoes, extra, rotuloCaminho = "Caminho" }) {
4
+ return /* @__PURE__ */ jsx(
5
+ PageHeader,
6
+ {
7
+ title: titulo,
8
+ description: descricao,
9
+ breadcrumb: caminho?.map((n) => ({ label: n.rotulo, href: n.href, onClick: n.onClick })),
10
+ actions: acoes,
11
+ extra,
12
+ breadcrumbLabel: rotuloCaminho
13
+ }
14
+ );
28
15
  }
29
16
  export {
30
17
  CabecalhoPagina as default
@@ -1 +1 @@
1
- {"version":3,"file":"CabecalhoPagina.js","sources":["../../../../../src/legacy/components/ui/CabecalhoPagina.tsx"],"sourcesContent":["import React, { type ReactNode } from 'react'\r\n\r\n/**\r\n * Um nível do caminho por cima do título.\r\n * @deprecated Legacy — não usar em código novo. Ver Storybook › Legacy.\r\n */\r\nexport interface NivelCaminho {\r\n rotulo: ReactNode\r\n /** Ligação normal. Para o router da app, usar `onClick` (ex: `() => navigate('/x')`). */\r\n href?: string\r\n onClick?: () => void\r\n}\r\n\r\n/** @deprecated Legacy — não usar em código novo. Ver Storybook › Legacy. */\r\nexport interface CabecalhoPaginaProps {\r\n titulo: ReactNode\r\n descricao?: ReactNode\r\n /**\r\n * Caminho até à página (área › lista › registo). O último nível é a página\r\n * atual e não leva ligação, mesmo que a traga.\r\n */\r\n caminho?: NivelCaminho[]\r\n /** Botões da página (ex: \"Novo\", \"Editar\"). Ficam à direita e descem em ecrã estreito. */\r\n acoes?: ReactNode\r\n /** Linha extra por baixo da descrição (etiquetas de estado, responsável…). */\r\n extra?: ReactNode\r\n /** Rótulo acessível da navegação do caminho. */\r\n rotuloCaminho?: string\r\n}\r\n\r\n/**\r\n * Cabeçalho comum a todas as páginas: caminho, título com a barra turquesa,\r\n * descrição e ações.\r\n *\r\n * Existe para o título deixar de ser desenhado à mão em cada ecrã — com\r\n * tamanhos, cores e posições diferentes de página para página. O nome no menu,\r\n * o título e o último nível do caminho devem ser o mesmo texto.\r\n * @deprecated Legacy — não usar em código novo. Ver Storybook › Legacy.\r\n */\r\nexport default function CabecalhoPagina({\r\n titulo,\r\n descricao,\r\n caminho,\r\n acoes,\r\n extra,\r\n rotuloCaminho = 'Caminho',\r\n}: CabecalhoPaginaProps) {\r\n return (\r\n <header className=\"flex flex-col gap-3\">\r\n {caminho && caminho.length > 0 && (\r\n <nav aria-label={rotuloCaminho}>\r\n <ol className=\"flex flex-wrap items-center gap-1.5 text-xs font-semibold text-slate-500 dark:text-slate-400\">\r\n {caminho.map((n, i) => {\r\n const ultimo = i === caminho.length - 1\r\n return (\r\n <li key={i} className=\"flex items-center gap-1.5\">\r\n {ultimo ? (\r\n <span aria-current=\"page\" className=\"text-slate-600 dark:text-slate-300\">\r\n {n.rotulo}\r\n </span>\r\n ) : n.href ? (\r\n <a href={n.href} onClick={n.onClick} className=\"text-proef-blue hover:text-proef-navy hover:underline dark:text-sky-300 dark:hover:text-sky-200\">\r\n {n.rotulo}\r\n </a>\r\n ) : n.onClick ? (\r\n <button type=\"button\" onClick={n.onClick} className=\"text-proef-blue hover:text-proef-navy hover:underline dark:text-sky-300 dark:hover:text-sky-200\">\r\n {n.rotulo}\r\n </button>\r\n ) : (\r\n <span>{n.rotulo}</span>\r\n )}\r\n {!ultimo && (\r\n <span aria-hidden=\"true\" className=\"text-slate-300 dark:text-slate-600\">\r\n ›\r\n </span>\r\n )}\r\n </li>\r\n )\r\n })}\r\n </ol>\r\n </nav>\r\n )}\r\n <div className=\"flex flex-col gap-4 lg:flex-row lg:items-end lg:justify-between\">\r\n <div className=\"min-w-0\">\r\n <h1 className=\"m-0 text-2xl md:text-4xl font-black uppercase tracking-tighter text-proef-navy dark:text-slate-100\">\r\n {titulo}\r\n </h1>\r\n <div className=\"mt-1 h-1 w-12 bg-proef-turquoise\" />\r\n {descricao && <p className=\"mt-3 text-sm font-medium text-slate-500 dark:text-slate-400\">{descricao}</p>}\r\n {extra && <div className=\"mt-2 flex flex-wrap items-center gap-2\">{extra}</div>}\r\n </div>\r\n {acoes && <div className=\"flex flex-wrap items-center gap-2 shrink-0\">{acoes}</div>}\r\n </div>\r\n </header>\r\n )\r\n}\r\n"],"names":[],"mappings":";AAuCA,SAAwB,gBAAgB;AAAA,EACtC;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA,gBAAgB;AAClB,GAAyB;AACvB,SACE,qBAAC,UAAA,EAAO,WAAU,uBACf,UAAA;AAAA,IAAA,WAAW,QAAQ,SAAS,KAC3B,oBAAC,SAAI,cAAY,eACf,UAAA,oBAAC,MAAA,EAAG,WAAU,gGACX,UAAA,QAAQ,IAAI,CAAC,GAAG,MAAM;AACrB,YAAM,SAAS,MAAM,QAAQ,SAAS;AACtC,aACE,qBAAC,MAAA,EAAW,WAAU,6BACnB,UAAA;AAAA,QAAA,6BACE,QAAA,EAAK,gBAAa,QAAO,WAAU,sCACjC,YAAE,OAAA,CACL,IACE,EAAE,2BACH,KAAA,EAAE,MAAM,EAAE,MAAM,SAAS,EAAE,SAAS,WAAU,mGAC5C,UAAA,EAAE,QACL,IACE,EAAE,UACJ,oBAAC,UAAA,EAAO,MAAK,UAAS,SAAS,EAAE,SAAS,WAAU,mGACjD,UAAA,EAAE,OAAA,CACL,IAEA,oBAAC,QAAA,EAAM,YAAE,OAAA,CAAO;AAAA,QAEjB,CAAC,UACA,oBAAC,QAAA,EAAK,eAAY,QAAO,WAAU,sCAAqC,UAAA,IAAA,CAExE;AAAA,MAAA,EAAA,GAnBK,CAqBT;AAAA,IAEJ,CAAC,GACH,GACF;AAAA,IAEF,qBAAC,OAAA,EAAI,WAAU,mEACb,UAAA;AAAA,MAAA,qBAAC,OAAA,EAAI,WAAU,WACb,UAAA;AAAA,QAAA,oBAAC,MAAA,EAAG,WAAU,sGACX,UAAA,QACH;AAAA,QACA,oBAAC,OAAA,EAAI,WAAU,mCAAA,CAAmC;AAAA,QACjD,aAAa,oBAAC,KAAA,EAAE,WAAU,+DAA+D,UAAA,WAAU;AAAA,QACnG,SAAS,oBAAC,OAAA,EAAI,WAAU,0CAA0C,UAAA,MAAA,CAAM;AAAA,MAAA,GAC3E;AAAA,MACC,SAAS,oBAAC,OAAA,EAAI,WAAU,8CAA8C,UAAA,MAAA,CAAM;AAAA,IAAA,EAAA,CAC/E;AAAA,EAAA,GACF;AAEJ;"}
1
+ {"version":3,"file":"CabecalhoPagina.js","sources":["../../../../../src/legacy/components/ui/CabecalhoPagina.tsx"],"sourcesContent":["import React, { type ReactNode } from 'react'\r\nimport PageHeader from '../../../v1/components/layout/PageHeader/PageHeader'\r\n\r\n/*\r\n * Migrado para o V1: o cabeçalho é o `PageHeader` do V1 (ou o `Page`, que o\r\n * inclui). Este ficheiro só traduz a API antiga (em português) para a nova,\r\n * para as apps que ainda a usam continuarem a funcionar sem mudanças.\r\n */\r\n\r\n/** @deprecated Legacy — usar `BreadcrumbItem` do V1. */\r\nexport interface NivelCaminho {\r\n rotulo: ReactNode\r\n /** Ligação normal. Para o router da app, usar `onClick` (ex: `() => navigate('/x')`). */\r\n href?: string\r\n onClick?: () => void\r\n}\r\n\r\n/** @deprecated Legacy — usar `PageHeaderProps` do V1. */\r\nexport interface CabecalhoPaginaProps {\r\n titulo: ReactNode\r\n descricao?: ReactNode\r\n /** Caminho até à página (área › lista › registo). O último nível é a página atual. */\r\n caminho?: NivelCaminho[]\r\n /** Botões da página (ex: \"Novo\", \"Editar\"). */\r\n acoes?: ReactNode\r\n /** Linha extra por baixo da descrição (etiquetas de estado, responsável…). */\r\n extra?: ReactNode\r\n /** Rótulo acessível da navegação do caminho. */\r\n rotuloCaminho?: string\r\n}\r\n\r\n/** @deprecated Legacy — usar `PageHeader` (ou `Page`) do V1. */\r\nexport default function CabecalhoPagina({ titulo, descricao, caminho, acoes, extra, rotuloCaminho = 'Caminho' }: CabecalhoPaginaProps) {\r\n return (\r\n <PageHeader\r\n title={titulo}\r\n description={descricao}\r\n breadcrumb={caminho?.map((n) => ({ label: n.rotulo, href: n.href, onClick: n.onClick }))}\r\n actions={acoes}\r\n extra={extra}\r\n breadcrumbLabel={rotuloCaminho}\r\n />\r\n )\r\n}\r\n"],"names":[],"mappings":";;AAgCA,SAAwB,gBAAgB,EAAE,QAAQ,WAAW,SAAS,OAAO,OAAO,gBAAgB,aAAmC;AACrI,SACE;AAAA,IAAC;AAAA,IAAA;AAAA,MACC,OAAO;AAAA,MACP,aAAa;AAAA,MACb,YAAY,SAAS,IAAI,CAAC,OAAO,EAAE,OAAO,EAAE,QAAQ,MAAM,EAAE,MAAM,SAAS,EAAE,UAAU;AAAA,MACvF,SAAS;AAAA,MACT;AAAA,MACA,iBAAiB;AAAA,IAAA;AAAA,EAAA;AAGvB;"}
@@ -1,55 +1,7 @@
1
- import { jsxs, jsx } from "react/jsx-runtime";
1
+ import { jsx } from "react/jsx-runtime";
2
+ import SearchInput from "../../../v1/primitives/forms/SearchInput/SearchInput.js";
2
3
  function CaixaPesquisa({ valor, onMudar, placeholder = "Pesquisar…", rotulo, className = "w-56", autoFocus }) {
3
- return /* @__PURE__ */ jsxs("div", { className: `relative ${className}`, children: [
4
- /* @__PURE__ */ jsxs(
5
- "svg",
6
- {
7
- xmlns: "http://www.w3.org/2000/svg",
8
- width: "14",
9
- height: "14",
10
- viewBox: "0 0 24 24",
11
- fill: "none",
12
- stroke: "currentColor",
13
- strokeWidth: "2",
14
- strokeLinecap: "round",
15
- strokeLinejoin: "round",
16
- className: "pointer-events-none absolute left-2.5 top-1/2 -translate-y-1/2 text-slate-400",
17
- "aria-hidden": true,
18
- children: [
19
- /* @__PURE__ */ jsx("circle", { cx: "11", cy: "11", r: "8" }),
20
- /* @__PURE__ */ jsx("path", { d: "m21 21-4.3-4.3" })
21
- ]
22
- }
23
- ),
24
- /* @__PURE__ */ jsx(
25
- "input",
26
- {
27
- type: "search",
28
- value: valor,
29
- onChange: (e) => onMudar(e.target.value),
30
- onKeyDown: (e) => {
31
- if (e.key === "Escape" && valor) {
32
- e.stopPropagation();
33
- onMudar("");
34
- }
35
- },
36
- placeholder,
37
- "aria-label": rotulo ?? placeholder,
38
- autoFocus,
39
- className: "h-8 w-full rounded-lg border border-slate-300 dark:border-slate-600 bg-white dark:bg-slate-900 pl-8 pr-7 text-sm text-slate-800 dark:text-slate-100 placeholder:text-slate-400 outline-none focus:border-proef-blue focus:ring-1 focus:ring-proef-blue dark:focus:border-proef-turquoise dark:focus:ring-proef-turquoise [&::-webkit-search-cancel-button]:hidden"
40
- }
41
- ),
42
- valor && /* @__PURE__ */ jsx(
43
- "button",
44
- {
45
- type: "button",
46
- onClick: () => onMudar(""),
47
- "aria-label": "Limpar pesquisa",
48
- className: "appearance-none cursor-pointer bg-transparent border-0 absolute right-1.5 top-1/2 -translate-y-1/2 px-1 text-base leading-none text-slate-400 hover:text-slate-700 dark:hover:text-slate-200",
49
- children: "×"
50
- }
51
- )
52
- ] });
4
+ return /* @__PURE__ */ jsx(SearchInput, { value: valor, onChange: onMudar, placeholder, label: rotulo, className, autoFocus });
53
5
  }
54
6
  export {
55
7
  CaixaPesquisa as default
@@ -1 +1 @@
1
- {"version":3,"file":"CaixaPesquisa.js","sources":["../../../../../src/legacy/components/ui/CaixaPesquisa.tsx"],"sourcesContent":["import React from 'react'\r\n\r\nexport interface CaixaPesquisaProps {\r\n valor: string\r\n onMudar: (valor: string) => void\r\n placeholder?: string\r\n /** Nome acessível (leitores de ecrã). Por omissão, o placeholder. */\r\n rotulo?: string\r\n /** Largura (classes tailwind). Por omissão w-56. */\r\n className?: string\r\n autoFocus?: boolean\r\n}\r\n\r\n/**\r\n * Caixa de pesquisa das barras de tabela e listas: mesma altura (h-8) e cantos (rounded-lg) dos botões, do\r\n * Exportar e do seletor de colunas. Lupa à esquerda; com texto, um \"×\" para limpar (Esc também limpa).\r\n */\r\nexport default function CaixaPesquisa({ valor, onMudar, placeholder = 'Pesquisar…', rotulo, className = 'w-56', autoFocus }: CaixaPesquisaProps) {\r\n return (\r\n <div className={`relative ${className}`}>\r\n <svg\r\n xmlns=\"http://www.w3.org/2000/svg\"\r\n width=\"14\"\r\n height=\"14\"\r\n viewBox=\"0 0 24 24\"\r\n fill=\"none\"\r\n stroke=\"currentColor\"\r\n strokeWidth=\"2\"\r\n strokeLinecap=\"round\"\r\n strokeLinejoin=\"round\"\r\n className=\"pointer-events-none absolute left-2.5 top-1/2 -translate-y-1/2 text-slate-400\"\r\n aria-hidden\r\n >\r\n <circle cx=\"11\" cy=\"11\" r=\"8\" />\r\n <path d=\"m21 21-4.3-4.3\" />\r\n </svg>\r\n <input\r\n type=\"search\"\r\n value={valor}\r\n onChange={(e) => onMudar(e.target.value)}\r\n onKeyDown={(e) => {\r\n if (e.key === 'Escape' && valor) {\r\n e.stopPropagation()\r\n onMudar('')\r\n }\r\n }}\r\n placeholder={placeholder}\r\n aria-label={rotulo ?? placeholder}\r\n autoFocus={autoFocus}\r\n className=\"h-8 w-full rounded-lg border border-slate-300 dark:border-slate-600 bg-white dark:bg-slate-900 pl-8 pr-7 text-sm text-slate-800 dark:text-slate-100 placeholder:text-slate-400 outline-none focus:border-proef-blue focus:ring-1 focus:ring-proef-blue dark:focus:border-proef-turquoise dark:focus:ring-proef-turquoise [&::-webkit-search-cancel-button]:hidden\"\r\n />\r\n {valor && (\r\n <button\r\n type=\"button\"\r\n onClick={() => onMudar('')}\r\n aria-label=\"Limpar pesquisa\"\r\n className=\"appearance-none cursor-pointer bg-transparent border-0 absolute right-1.5 top-1/2 -translate-y-1/2 px-1 text-base leading-none text-slate-400 hover:text-slate-700 dark:hover:text-slate-200\"\r\n >\r\n ×\r\n </button>\r\n )}\r\n </div>\r\n )\r\n}\r\n"],"names":[],"mappings":";AAiBA,SAAwB,cAAc,EAAE,OAAO,SAAS,cAAc,cAAc,QAAQ,YAAY,QAAQ,aAAiC;AAC/I,SACE,qBAAC,OAAA,EAAI,WAAW,YAAY,SAAS,IACnC,UAAA;AAAA,IAAA;AAAA,MAAC;AAAA,MAAA;AAAA,QACC,OAAM;AAAA,QACN,OAAM;AAAA,QACN,QAAO;AAAA,QACP,SAAQ;AAAA,QACR,MAAK;AAAA,QACL,QAAO;AAAA,QACP,aAAY;AAAA,QACZ,eAAc;AAAA,QACd,gBAAe;AAAA,QACf,WAAU;AAAA,QACV,eAAW;AAAA,QAEX,UAAA;AAAA,UAAA,oBAAC,YAAO,IAAG,MAAK,IAAG,MAAK,GAAE,KAAI;AAAA,UAC9B,oBAAC,QAAA,EAAK,GAAE,iBAAA,CAAiB;AAAA,QAAA;AAAA,MAAA;AAAA,IAAA;AAAA,IAE3B;AAAA,MAAC;AAAA,MAAA;AAAA,QACC,MAAK;AAAA,QACL,OAAO;AAAA,QACP,UAAU,CAAC,MAAM,QAAQ,EAAE,OAAO,KAAK;AAAA,QACvC,WAAW,CAAC,MAAM;AAChB,cAAI,EAAE,QAAQ,YAAY,OAAO;AAC/B,cAAE,gBAAA;AACF,oBAAQ,EAAE;AAAA,UACZ;AAAA,QACF;AAAA,QACA;AAAA,QACA,cAAY,UAAU;AAAA,QACtB;AAAA,QACA,WAAU;AAAA,MAAA;AAAA,IAAA;AAAA,IAEX,SACC;AAAA,MAAC;AAAA,MAAA;AAAA,QACC,MAAK;AAAA,QACL,SAAS,MAAM,QAAQ,EAAE;AAAA,QACzB,cAAW;AAAA,QACX,WAAU;AAAA,QACX,UAAA;AAAA,MAAA;AAAA,IAAA;AAAA,EAED,GAEJ;AAEJ;"}
1
+ {"version":3,"file":"CaixaPesquisa.js","sources":["../../../../../src/legacy/components/ui/CaixaPesquisa.tsx"],"sourcesContent":["import React from 'react'\r\nimport SearchInput from '../../../v1/primitives/forms/SearchInput/SearchInput'\r\n\r\n/*\r\n * Migrado para o V1: a caixa de pesquisa é o `SearchInput` do V1 (mesmo\r\n * aspeto e comportamento). Este ficheiro só traduz a API antiga.\r\n */\r\n\r\n/** @deprecated Legacy — usar `SearchInputProps` do V1. */\r\nexport interface CaixaPesquisaProps {\r\n valor: string\r\n onMudar: (valor: string) => void\r\n placeholder?: string\r\n /** Nome acessível (leitores de ecrã). Por omissão, o placeholder. */\r\n rotulo?: string\r\n /** Largura (classes tailwind). Por omissão w-56. */\r\n className?: string\r\n autoFocus?: boolean\r\n}\r\n\r\n/** @deprecated Legacy — usar `SearchInput` do V1. */\r\nexport default function CaixaPesquisa({ valor, onMudar, placeholder = 'Pesquisar…', rotulo, className = 'w-56', autoFocus }: CaixaPesquisaProps) {\r\n return <SearchInput value={valor} onChange={onMudar} placeholder={placeholder} label={rotulo} className={className} autoFocus={autoFocus} />\r\n}\r\n"],"names":[],"mappings":";;AAqBA,SAAwB,cAAc,EAAE,OAAO,SAAS,cAAc,cAAc,QAAQ,YAAY,QAAQ,aAAiC;AAC/I,SAAO,oBAAC,aAAA,EAAY,OAAO,OAAO,UAAU,SAAS,aAA0B,OAAO,QAAQ,WAAsB,UAAA,CAAsB;AAC5I;"}
@@ -1,5 +1,5 @@
1
- import { jsx, jsxs } from "react/jsx-runtime";
2
- import { useId, useRef, useEffect } from "react";
1
+ import { jsx } from "react/jsx-runtime";
2
+ import ConfirmDialog from "../../../v1/components/overlays/ConfirmDialog/ConfirmDialog.js";
3
3
  function Confirmacao({
4
4
  aberto,
5
5
  titulo,
@@ -12,37 +12,19 @@ function Confirmacao({
12
12
  aConfirmar = false,
13
13
  acaoSecundaria
14
14
  }) {
15
- const idTitulo = useId();
16
- const refCancelar = useRef(null);
17
- const refConfirmar = useRef(null);
18
- useEffect(() => {
19
- if (!aberto) return;
20
- (variante === "perigo" ? refCancelar : refConfirmar).current?.focus();
21
- const esc = (e) => {
22
- if (e.key === "Escape" && !aConfirmar) onCancelar();
23
- };
24
- window.addEventListener("keydown", esc);
25
- return () => window.removeEventListener("keydown", esc);
26
- }, [aberto, variante, aConfirmar, onCancelar]);
27
- if (!aberto) return null;
28
- const btn = "rounded-md px-4 py-2.5 text-[11px] font-black uppercase tracking-widest disabled:opacity-50 disabled:cursor-not-allowed";
29
- const principal = variante === "perigo" ? "bg-incumprido text-white border border-incumprido hover:opacity-90" : "bg-proef-navy text-white border border-proef-navy hover:bg-proef-blue";
30
15
  return /* @__PURE__ */ jsx(
31
- "div",
16
+ ConfirmDialog,
32
17
  {
33
- onClick: (e) => {
34
- if (e.target === e.currentTarget && !aConfirmar) onCancelar();
35
- },
36
- className: "fixed inset-0 z-[60] flex items-center justify-center bg-[rgba(20,30,50,0.45)] p-4",
37
- children: /* @__PURE__ */ jsxs("div", { role: "alertdialog", "aria-modal": "true", "aria-labelledby": idTitulo, className: "w-full max-w-md rounded-2xl bg-white p-6 shadow-2xl dark:bg-slate-900", children: [
38
- /* @__PURE__ */ jsx("h2", { id: idTitulo, className: "m-0 text-base font-black uppercase tracking-tight text-proef-navy dark:text-slate-100", children: titulo }),
39
- children && /* @__PURE__ */ jsx("div", { className: "mt-2 text-sm leading-relaxed text-slate-600 dark:text-slate-300", children }),
40
- /* @__PURE__ */ jsxs("div", { className: "mt-6 flex flex-wrap justify-end gap-2", children: [
41
- /* @__PURE__ */ jsx("button", { ref: refCancelar, type: "button", onClick: onCancelar, disabled: aConfirmar, className: `${btn} border border-slate-200 bg-white text-slate-600 hover:border-slate-400 dark:bg-slate-800 dark:border-slate-700 dark:text-slate-300 dark:hover:border-slate-400`, children: textoCancelar }),
42
- acaoSecundaria && /* @__PURE__ */ jsx("button", { type: "button", onClick: acaoSecundaria.onClick, disabled: aConfirmar, className: `${btn} border border-proef-navy bg-white text-proef-navy hover:bg-slate-50 dark:bg-slate-800 dark:border-sky-400 dark:text-sky-300 dark:hover:bg-slate-700`, children: acaoSecundaria.rotulo }),
43
- /* @__PURE__ */ jsx("button", { ref: refConfirmar, type: "button", onClick: onConfirmar, disabled: aConfirmar, "aria-busy": aConfirmar, className: `${btn} ${principal}`, children: textoConfirmar })
44
- ] })
45
- ] })
18
+ open: aberto,
19
+ title: titulo,
20
+ message: children,
21
+ tone: variante === "perigo" ? "danger" : "default",
22
+ confirmLabel: textoConfirmar,
23
+ cancelLabel: textoCancelar,
24
+ loading: aConfirmar,
25
+ secondaryAction: acaoSecundaria && { label: acaoSecundaria.rotulo, onClick: acaoSecundaria.onClick },
26
+ onConfirm: onConfirmar,
27
+ onCancel: onCancelar
46
28
  }
47
29
  );
48
30
  }
@@ -1 +1 @@
1
- {"version":3,"file":"Confirmacao.js","sources":["../../../../../src/legacy/components/ui/Confirmacao.tsx"],"sourcesContent":["import React, { useEffect, useId, useRef, type ReactNode } from 'react'\r\n\r\n/** @deprecated Legacy — não usar em código novo. Ver Storybook › Legacy. */\r\nexport interface ConfirmacaoProps {\r\n aberto: boolean\r\n titulo: ReactNode\r\n /** Explicação: o que vai acontecer, a que registo, se é reversível. */\r\n children?: ReactNode\r\n onConfirmar: () => void\r\n onCancelar: () => void\r\n /** Texto do botão — o verbo da ação (\"Eliminar\", \"Submeter\"), não \"OK\". */\r\n textoConfirmar?: string\r\n textoCancelar?: string\r\n /** `perigo` pinta a ação a vermelho e põe o foco em Cancelar. */\r\n variante?: 'normal' | 'perigo'\r\n /** A ação está a correr: botões desativados. */\r\n aConfirmar?: boolean\r\n /** Uma segunda saída (ex: \"Desativar\" em vez de eliminar, \"Eliminar só o contrato\"). */\r\n acaoSecundaria?: { rotulo: string; onClick: () => void }\r\n}\r\n\r\n/**\r\n * Pedido de confirmação antes de uma ação. Substitui o `window.confirm()` do\r\n * browser, que mostra o endereço do servidor, não diz que registo é e só tem\r\n * \"OK\".\r\n *\r\n * Esc e clicar fora cancelam (exceto enquanto `aConfirmar`).\r\n * @deprecated Legacy — não usar em código novo. Ver Storybook › Legacy.\r\n */\r\nexport default function Confirmacao({\r\n aberto,\r\n titulo,\r\n children,\r\n onConfirmar,\r\n onCancelar,\r\n textoConfirmar = 'Confirmar',\r\n textoCancelar = 'Cancelar',\r\n variante = 'normal',\r\n aConfirmar = false,\r\n acaoSecundaria,\r\n}: ConfirmacaoProps) {\r\n const idTitulo = useId()\r\n const refCancelar = useRef<HTMLButtonElement>(null)\r\n const refConfirmar = useRef<HTMLButtonElement>(null)\r\n\r\n useEffect(() => {\r\n if (!aberto) return\r\n // Numa ação destrutiva o Enter por engano não deve apagar nada.\r\n ;(variante === 'perigo' ? refCancelar : refConfirmar).current?.focus()\r\n const esc = (e: KeyboardEvent): void => {\r\n if (e.key === 'Escape' && !aConfirmar) onCancelar()\r\n }\r\n window.addEventListener('keydown', esc)\r\n return () => window.removeEventListener('keydown', esc)\r\n }, [aberto, variante, aConfirmar, onCancelar])\r\n\r\n if (!aberto) return null\r\n\r\n const btn = 'rounded-md px-4 py-2.5 text-[11px] font-black uppercase tracking-widest disabled:opacity-50 disabled:cursor-not-allowed'\r\n const principal =\r\n variante === 'perigo'\r\n ? 'bg-incumprido text-white border border-incumprido hover:opacity-90'\r\n : 'bg-proef-navy text-white border border-proef-navy hover:bg-proef-blue'\r\n\r\n return (\r\n <div\r\n onClick={(e) => {\r\n if (e.target === e.currentTarget && !aConfirmar) onCancelar()\r\n }}\r\n className=\"fixed inset-0 z-[60] flex items-center justify-center bg-[rgba(20,30,50,0.45)] p-4\"\r\n >\r\n <div role=\"alertdialog\" aria-modal=\"true\" aria-labelledby={idTitulo} className=\"w-full max-w-md rounded-2xl bg-white p-6 shadow-2xl dark:bg-slate-900\">\r\n <h2 id={idTitulo} className=\"m-0 text-base font-black uppercase tracking-tight text-proef-navy dark:text-slate-100\">\r\n {titulo}\r\n </h2>\r\n {children && <div className=\"mt-2 text-sm leading-relaxed text-slate-600 dark:text-slate-300\">{children}</div>}\r\n <div className=\"mt-6 flex flex-wrap justify-end gap-2\">\r\n <button ref={refCancelar} type=\"button\" onClick={onCancelar} disabled={aConfirmar} className={`${btn} border border-slate-200 bg-white text-slate-600 hover:border-slate-400 dark:bg-slate-800 dark:border-slate-700 dark:text-slate-300 dark:hover:border-slate-400`}>\r\n {textoCancelar}\r\n </button>\r\n {acaoSecundaria && (\r\n <button type=\"button\" onClick={acaoSecundaria.onClick} disabled={aConfirmar} className={`${btn} border border-proef-navy bg-white text-proef-navy hover:bg-slate-50 dark:bg-slate-800 dark:border-sky-400 dark:text-sky-300 dark:hover:bg-slate-700`}>\r\n {acaoSecundaria.rotulo}\r\n </button>\r\n )}\r\n <button ref={refConfirmar} type=\"button\" onClick={onConfirmar} disabled={aConfirmar} aria-busy={aConfirmar} className={`${btn} ${principal}`}>\r\n {textoConfirmar}\r\n </button>\r\n </div>\r\n </div>\r\n </div>\r\n )\r\n}\r\n"],"names":[],"mappings":";;AA6BA,SAAwB,YAAY;AAAA,EAClC;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA,iBAAiB;AAAA,EACjB,gBAAgB;AAAA,EAChB,WAAW;AAAA,EACX,aAAa;AAAA,EACb;AACF,GAAqB;AACnB,QAAM,WAAW,MAAA;AACjB,QAAM,cAAc,OAA0B,IAAI;AAClD,QAAM,eAAe,OAA0B,IAAI;AAEnD,YAAU,MAAM;AACd,QAAI,CAAC,OAAQ;AAEZ,KAAC,aAAa,WAAW,cAAc,cAAc,SAAS,MAAA;AAC/D,UAAM,MAAM,CAAC,MAA2B;AACtC,UAAI,EAAE,QAAQ,YAAY,CAAC,WAAY,YAAA;AAAA,IACzC;AACA,WAAO,iBAAiB,WAAW,GAAG;AACtC,WAAO,MAAM,OAAO,oBAAoB,WAAW,GAAG;AAAA,EACxD,GAAG,CAAC,QAAQ,UAAU,YAAY,UAAU,CAAC;AAE7C,MAAI,CAAC,OAAQ,QAAO;AAEpB,QAAM,MAAM;AACZ,QAAM,YACJ,aAAa,WACT,uEACA;AAEN,SACE;AAAA,IAAC;AAAA,IAAA;AAAA,MACC,SAAS,CAAC,MAAM;AACd,YAAI,EAAE,WAAW,EAAE,iBAAiB,CAAC,WAAY,YAAA;AAAA,MACnD;AAAA,MACA,WAAU;AAAA,MAEV,UAAA,qBAAC,SAAI,MAAK,eAAc,cAAW,QAAO,mBAAiB,UAAU,WAAU,yEAC7E,UAAA;AAAA,QAAA,oBAAC,MAAA,EAAG,IAAI,UAAU,WAAU,yFACzB,UAAA,QACH;AAAA,QACC,YAAY,oBAAC,OAAA,EAAI,WAAU,mEAAmE,UAAS;AAAA,QACxG,qBAAC,OAAA,EAAI,WAAU,yCACb,UAAA;AAAA,UAAA,oBAAC,UAAA,EAAO,KAAK,aAAa,MAAK,UAAS,SAAS,YAAY,UAAU,YAAY,WAAW,GAAG,GAAG,mKACjG,UAAA,eACH;AAAA,UACC,kBACC,oBAAC,UAAA,EAAO,MAAK,UAAS,SAAS,eAAe,SAAS,UAAU,YAAY,WAAW,GAAG,GAAG,wJAC3F,yBAAe,QAClB;AAAA,8BAED,UAAA,EAAO,KAAK,cAAc,MAAK,UAAS,SAAS,aAAa,UAAU,YAAY,aAAW,YAAY,WAAW,GAAG,GAAG,IAAI,SAAS,IACvI,UAAA,eAAA,CACH;AAAA,QAAA,EAAA,CACF;AAAA,MAAA,EAAA,CACF;AAAA,IAAA;AAAA,EAAA;AAGN;"}
1
+ {"version":3,"file":"Confirmacao.js","sources":["../../../../../src/legacy/components/ui/Confirmacao.tsx"],"sourcesContent":["import React, { type ReactNode } from 'react'\r\nimport ConfirmDialog from '../../../v1/components/overlays/ConfirmDialog/ConfirmDialog'\r\n\r\n/*\r\n * Migrado para o V1: a confirmação é o `ConfirmDialog` do V1 (ou `useConfirm`).\r\n * Este ficheiro só traduz a API antiga (em português) para a nova, para as\r\n * apps que ainda a usam continuarem a funcionar sem mudanças.\r\n */\r\n\r\n/** @deprecated Legacy — usar `ConfirmDialog` ou `useConfirm` do V1. */\r\nexport interface ConfirmacaoProps {\r\n aberto: boolean\r\n titulo: ReactNode\r\n /** Explicação: o que vai acontecer, a que registo, se é reversível. */\r\n children?: ReactNode\r\n onConfirmar: () => void\r\n onCancelar: () => void\r\n /** Texto do botão — o verbo da ação (\"Eliminar\", \"Submeter\"), não \"OK\". */\r\n textoConfirmar?: string\r\n textoCancelar?: string\r\n /** `perigo` pinta a ação a vermelho e põe o foco em Cancelar. */\r\n variante?: 'normal' | 'perigo'\r\n /** A ação está a correr: botões desativados. */\r\n aConfirmar?: boolean\r\n /** Uma segunda saída (ex: \"Desativar\" em vez de eliminar, \"Eliminar só o contrato\"). */\r\n acaoSecundaria?: { rotulo: string; onClick: () => void }\r\n}\r\n\r\n/** @deprecated Legacy — usar `ConfirmDialog` ou `useConfirm` do V1. */\r\nexport default function Confirmacao({\r\n aberto,\r\n titulo,\r\n children,\r\n onConfirmar,\r\n onCancelar,\r\n textoConfirmar = 'Confirmar',\r\n textoCancelar = 'Cancelar',\r\n variante = 'normal',\r\n aConfirmar = false,\r\n acaoSecundaria,\r\n}: ConfirmacaoProps) {\r\n return (\r\n <ConfirmDialog\r\n open={aberto}\r\n title={titulo}\r\n message={children}\r\n tone={variante === 'perigo' ? 'danger' : 'default'}\r\n confirmLabel={textoConfirmar}\r\n cancelLabel={textoCancelar}\r\n loading={aConfirmar}\r\n secondaryAction={acaoSecundaria && { label: acaoSecundaria.rotulo, onClick: acaoSecundaria.onClick }}\r\n onConfirm={onConfirmar}\r\n onCancel={onCancelar}\r\n />\r\n )\r\n}\r\n"],"names":[],"mappings":";;AA6BA,SAAwB,YAAY;AAAA,EAClC;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA,iBAAiB;AAAA,EACjB,gBAAgB;AAAA,EAChB,WAAW;AAAA,EACX,aAAa;AAAA,EACb;AACF,GAAqB;AACnB,SACE;AAAA,IAAC;AAAA,IAAA;AAAA,MACC,MAAM;AAAA,MACN,OAAO;AAAA,MACP,SAAS;AAAA,MACT,MAAM,aAAa,WAAW,WAAW;AAAA,MACzC,cAAc;AAAA,MACd,aAAa;AAAA,MACb,SAAS;AAAA,MACT,iBAAiB,kBAAkB,EAAE,OAAO,eAAe,QAAQ,SAAS,eAAe,QAAA;AAAA,MAC3F,WAAW;AAAA,MACX,UAAU;AAAA,IAAA;AAAA,EAAA;AAGhB;"}