@1doc/1ds-react 2.7.2 → 2.9.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +1280 -0
- package/dist/components/AIContent/AIContent.d.ts +10 -0
- package/dist/components/AIContent/AIContent.js +1 -1
- package/dist/components/AILabel/AILabel.d.ts +4 -0
- package/dist/components/AILabel/AILabel.js +2 -2
- package/dist/components/Accordion/Accordion.d.ts +6 -2
- package/dist/components/Alert/Alert.css +2 -0
- package/dist/components/Alert/Alert.d.ts +3 -1
- package/dist/components/Alert/Alert.js +7 -1
- package/dist/components/AppHeader/AppHeader.css +82 -8
- package/dist/components/AppHeader/AppHeader.d.ts +12 -1
- package/dist/components/AppHeader/AppHeader.js +186 -1
- package/dist/components/AppNavItem/AppNavItem.css +11 -3
- package/dist/components/AppShell/AppShell.css +9 -0
- package/dist/components/AppShell/AppShell.d.ts +8 -0
- package/dist/components/AppShell/AppShell.js +4 -1
- package/dist/components/AppSidebar/AppSidebar.css +1 -1
- package/dist/components/AppSidebar/AppSidebar.d.ts +4 -0
- package/dist/components/AppSidebar/AppSidebar.js +3 -1
- package/dist/components/AttachmentCard/AttachmentCard.css +17 -1
- package/dist/components/AttachmentCard/AttachmentCard.d.ts +29 -2
- package/dist/components/AttachmentCard/AttachmentCard.js +88 -20
- package/dist/components/Avatar/Avatar.css +7 -2
- package/dist/components/Avatar/AvatarGroup.d.ts +27 -0
- package/dist/components/Avatar/AvatarGroup.js +28 -4
- package/dist/components/Badge/Badge.css +61 -3
- package/dist/components/Badge/Badge.d.ts +14 -4
- package/dist/components/Badge/Badge.js +1 -0
- package/dist/components/BottomSheet/BottomSheet.css +1 -0
- package/dist/components/BottomSheet/BottomSheet.d.ts +8 -0
- package/dist/components/BottomSheet/BottomSheet.js +14 -2
- package/dist/components/Box/Box.css +83 -0
- package/dist/components/Box/Box.d.ts +82 -2
- package/dist/components/Box/Box.js +42 -2
- package/dist/components/Button/Button.css +29 -0
- package/dist/components/Button/Button.d.ts +4 -4
- package/dist/components/Button/Button.js +4 -1
- package/dist/components/Calendar/Calendar.css +245 -0
- package/dist/components/Calendar/Calendar.d.ts +125 -0
- package/dist/components/Calendar/Calendar.js +320 -0
- package/dist/components/Chart/BarChart.d.ts +6 -0
- package/dist/components/Chart/BarChart.js +3 -1
- package/dist/components/Chart/LineChart.d.ts +6 -0
- package/dist/components/Chart/LineChart.js +3 -1
- package/dist/components/Checkbox/Checkbox.css +4 -1
- package/dist/components/Chips/Chips.css +39 -0
- package/dist/components/Chips/Chips.d.ts +7 -2
- package/dist/components/Chips/Chips.js +6 -2
- package/dist/components/Coachmark/Coachmark.css +118 -0
- package/dist/components/Coachmark/Coachmark.d.ts +75 -0
- package/dist/components/Coachmark/Coachmark.js +321 -0
- package/dist/components/CodeBlock/CodeBlock.css +96 -0
- package/dist/components/CodeBlock/CodeBlock.d.ts +47 -0
- package/dist/components/CodeBlock/CodeBlock.js +103 -0
- package/dist/components/ColorPicker/ColorPicker.css +133 -0
- package/dist/components/ColorPicker/ColorPicker.d.ts +73 -0
- package/dist/components/ColorPicker/ColorPicker.js +219 -0
- package/dist/components/Combobox/Combobox.css +11 -3
- package/dist/components/ConfirmAIAction/ConfirmAIAction.d.ts +11 -1
- package/dist/components/ConfirmAIAction/ConfirmAIAction.js +6 -1
- package/dist/components/ConfirmDialog/ConfirmDialog.css +3 -0
- package/dist/components/ConfirmDialog/ConfirmDialog.d.ts +14 -0
- package/dist/components/ConfirmDialog/ConfirmDialog.js +2 -2
- package/dist/components/DataTable/DataTable.css +80 -0
- package/dist/components/DataTable/DataTable.d.ts +23 -4
- package/dist/components/DataTable/DataTable.js +61 -15
- package/dist/components/DatePicker/DatePicker.css +8 -0
- package/dist/components/DatePicker/DatePicker.d.ts +4 -0
- package/dist/components/DatePicker/DatePicker.js +14 -1
- package/dist/components/DescriptionList/DescriptionList.css +113 -0
- package/dist/components/DescriptionList/DescriptionList.d.ts +59 -0
- package/dist/components/DescriptionList/DescriptionList.js +51 -0
- package/dist/components/Drawer/Drawer.css +1 -0
- package/dist/components/Dropdown/Dropdown.js +47 -29
- package/dist/components/FileInput/FileInput.css +24 -4
- package/dist/components/FileInput/FileInput.d.ts +22 -2
- package/dist/components/FileInput/FileInput.js +23 -2
- package/dist/components/Grid/Grid.js +5 -5
- package/dist/components/IconPicker/IconPicker.css +107 -0
- package/dist/components/IconPicker/IconPicker.d.ts +74 -0
- package/dist/components/IconPicker/IconPicker.js +194 -0
- package/dist/components/Input/Input.css +41 -3
- package/dist/components/Input/Input.d.ts +14 -1
- package/dist/components/Input/Input.js +72 -6
- package/dist/components/Kanban/Kanban.css +5 -0
- package/dist/components/Kanban/Kanban.d.ts +41 -0
- package/dist/components/Kanban/Kanban.js +59 -27
- package/dist/components/Kanban/KanbanCard.d.ts +2 -0
- package/dist/components/Kanban/KanbanCard.js +1 -1
- package/dist/components/Kanban/KanbanColumn.d.ts +2 -0
- package/dist/components/Kanban/KanbanColumn.js +3 -0
- package/dist/components/Kbd/Kbd.css +66 -0
- package/dist/components/Kbd/Kbd.d.ts +32 -0
- package/dist/components/Kbd/Kbd.js +40 -0
- package/dist/components/Link/Link.css +1 -1
- package/dist/components/List/List.css +136 -0
- package/dist/components/List/List.d.ts +82 -0
- package/dist/components/List/List.js +53 -0
- package/dist/components/List/ListItem.d.ts +85 -0
- package/dist/components/List/ListItem.js +81 -0
- package/dist/components/Modal/Modal.css +93 -8
- package/dist/components/Modal/Modal.d.ts +45 -7
- package/dist/components/Modal/Modal.js +106 -6
- package/dist/components/MultiSelect/MultiSelect.css +9 -1
- package/dist/components/MultiSelect/MultiSelect.js +45 -8
- package/dist/components/OrgChart/OrgChart.css +149 -0
- package/dist/components/OrgChart/OrgChart.d.ts +83 -0
- package/dist/components/OrgChart/OrgChart.js +297 -0
- package/dist/components/OtpInput/OtpInput.css +93 -0
- package/dist/components/OtpInput/OtpInput.d.ts +60 -0
- package/dist/components/OtpInput/OtpInput.js +215 -0
- package/dist/components/Pagination/Pagination.d.ts +6 -0
- package/dist/components/Pagination/Pagination.js +9 -1
- package/dist/components/PhoneInput/PhoneInput.css +9 -1
- package/dist/components/PhoneInput/PhoneInput.d.ts +10 -0
- package/dist/components/PhoneInput/PhoneInput.js +20 -3
- package/dist/components/Popover/Popover.d.ts +7 -0
- package/dist/components/Popover/Popover.js +11 -1
- package/dist/components/RichTextEditor/RichTextEditor.css +203 -0
- package/dist/components/RichTextEditor/RichTextEditor.d.ts +83 -0
- package/dist/components/RichTextEditor/RichTextEditor.js +494 -0
- package/dist/components/SegmentedControl/SegmentedControl.d.ts +2 -0
- package/dist/components/SegmentedControl/SegmentedControl.js +21 -8
- package/dist/components/Select/Select.css +71 -1
- package/dist/components/Select/Select.d.ts +12 -0
- package/dist/components/Select/Select.js +93 -10
- package/dist/components/SidePanel/SidePanel.css +4 -4
- package/dist/components/SidePanelItem/SidePanelItem.css +7 -5
- package/dist/components/SidePanelSearch/SidePanelSearch.css +2 -2
- package/dist/components/SidePanelSection/SidePanelSection.css +7 -5
- package/dist/components/Stack/Stack.css +49 -0
- package/dist/components/Stack/Stack.d.ts +65 -7
- package/dist/components/Stack/Stack.js +30 -2
- package/dist/components/StatCard/StatCard.css +73 -0
- package/dist/components/StatCard/StatCard.d.ts +17 -0
- package/dist/components/StatCard/StatCard.js +4 -1
- package/dist/components/Stepper/Stepper.css +4 -1
- package/dist/components/Stepper/Stepper.d.ts +8 -0
- package/dist/components/Stepper/Stepper.js +4 -4
- package/dist/components/Switch/Switch.css +1 -0
- package/dist/components/Tabs/Tab.d.ts +15 -0
- package/dist/components/Tabs/Tab.js +30 -1
- package/dist/components/Tabs/Tabs.css +132 -0
- package/dist/components/Tabs/Tabs.d.ts +7 -0
- package/dist/components/Tabs/Tabs.js +13 -2
- package/dist/components/Tag/Tag.css +85 -2
- package/dist/components/Tag/Tag.d.ts +13 -6
- package/dist/components/Tag/Tag.js +1 -0
- package/dist/components/Text/Text.d.ts +9 -1
- package/dist/components/Text/Text.js +2 -2
- package/dist/components/Textarea/Textarea.css +11 -3
- package/dist/components/TimePicker/TimePicker.css +8 -0
- package/dist/components/TimePicker/TimePicker.d.ts +6 -0
- package/dist/components/TimePicker/TimePicker.js +1 -1
- package/dist/components/Tooltip/Tooltip.css +40 -0
- package/dist/components/Tooltip/Tooltip.d.ts +11 -0
- package/dist/components/Tooltip/Tooltip.js +114 -11
- package/dist/index.d.ts +25 -0
- package/dist/index.js +14 -0
- package/dist/teste/AILabel.test.d.ts +1 -0
- package/dist/teste/AILabel.test.js +33 -0
- package/dist/teste/AccordionConteudoLivre.test.d.ts +1 -0
- package/dist/teste/AccordionConteudoLivre.test.js +29 -0
- package/dist/teste/Alert.test.d.ts +1 -0
- package/dist/teste/Alert.test.js +27 -0
- package/dist/teste/AtributosRepassados.test.d.ts +1 -0
- package/dist/teste/AtributosRepassados.test.js +52 -0
- package/dist/teste/AttachmentCardIA.test.d.ts +1 -0
- package/dist/teste/AttachmentCardIA.test.js +89 -0
- package/dist/teste/AvatarGroupOverlap.test.d.ts +1 -0
- package/dist/teste/AvatarGroupOverlap.test.js +56 -0
- package/dist/teste/BadgeTag.test.d.ts +1 -0
- package/dist/teste/BadgeTag.test.js +42 -0
- package/dist/teste/BottomSheet.test.d.ts +1 -0
- package/dist/teste/BottomSheet.test.js +23 -0
- package/dist/teste/BoxItemFlex.test.d.ts +1 -0
- package/dist/teste/BoxItemFlex.test.js +54 -0
- package/dist/teste/BoxLayout.test.d.ts +1 -0
- package/dist/teste/BoxLayout.test.js +35 -0
- package/dist/teste/Button.test.d.ts +1 -0
- package/dist/teste/Button.test.js +27 -0
- package/dist/teste/Calendar.test.d.ts +1 -0
- package/dist/teste/Calendar.test.js +221 -0
- package/dist/teste/ChipsXs.test.d.ts +1 -0
- package/dist/teste/ChipsXs.test.js +31 -0
- package/dist/teste/Coachmark.test.d.ts +1 -0
- package/dist/teste/Coachmark.test.js +149 -0
- package/dist/teste/ColorPicker.test.d.ts +1 -0
- package/dist/teste/ColorPicker.test.js +132 -0
- package/dist/teste/ConfirmAIAction.test.d.ts +1 -0
- package/dist/teste/ConfirmAIAction.test.js +33 -0
- package/dist/teste/DataTableCelulaLivre.test.d.ts +1 -0
- package/dist/teste/DataTableCelulaLivre.test.js +76 -0
- package/dist/teste/DataTableDocumento.test.d.ts +1 -0
- package/dist/teste/DataTableDocumento.test.js +92 -0
- package/dist/teste/DatePicker.test.js +23 -0
- package/dist/teste/Dropdown.test.js +111 -0
- package/dist/teste/FileInputTrigger.test.d.ts +1 -0
- package/dist/teste/FileInputTrigger.test.js +53 -0
- package/dist/teste/IconPicker.test.d.ts +1 -0
- package/dist/teste/IconPicker.test.js +130 -0
- package/dist/teste/InputMascaraEAfins.test.d.ts +1 -0
- package/dist/teste/InputMascaraEAfins.test.js +99 -0
- package/dist/teste/KbdCodeBlock.test.d.ts +1 -0
- package/dist/teste/KbdCodeBlock.test.js +95 -0
- package/dist/teste/List.test.d.ts +1 -0
- package/dist/teste/List.test.js +153 -0
- package/dist/teste/Modal.test.d.ts +1 -0
- package/dist/teste/Modal.test.js +26 -0
- package/dist/teste/ModalVariantes.test.d.ts +1 -0
- package/dist/teste/ModalVariantes.test.js +151 -0
- package/dist/teste/MultiSelectErro.test.d.ts +1 -0
- package/dist/teste/MultiSelectErro.test.js +62 -0
- package/dist/teste/NomeAcessivelSsr.test.d.ts +1 -0
- package/dist/teste/NomeAcessivelSsr.test.js +88 -0
- package/dist/teste/OrgChart.test.d.ts +1 -0
- package/dist/teste/OrgChart.test.js +162 -0
- package/dist/teste/OtpInput.test.d.ts +1 -0
- package/dist/teste/OtpInput.test.js +143 -0
- package/dist/teste/PopoverMaxHeight.test.d.ts +1 -0
- package/dist/teste/PopoverMaxHeight.test.js +38 -0
- package/dist/teste/RichTextEditor.test.d.ts +1 -0
- package/dist/teste/RichTextEditor.test.js +287 -0
- package/dist/teste/RotulosTraduziveis.test.d.ts +1 -0
- package/dist/teste/RotulosTraduziveis.test.js +405 -0
- package/dist/teste/SegmentedControl.test.js +33 -0
- package/dist/teste/Select.test.d.ts +1 -0
- package/dist/teste/Select.test.js +62 -0
- package/dist/teste/SelectPlacementFiltro.test.d.ts +1 -0
- package/dist/teste/SelectPlacementFiltro.test.js +88 -0
- package/dist/teste/Stack.test.d.ts +1 -0
- package/dist/teste/Stack.test.js +57 -0
- package/dist/teste/StatCardRotuloTopo.test.d.ts +1 -0
- package/dist/teste/StatCardRotuloTopo.test.js +34 -0
- package/dist/teste/TabsContadorFechavel.test.d.ts +1 -0
- package/dist/teste/TabsContadorFechavel.test.js +79 -0
- package/dist/teste/Tooltip.test.d.ts +1 -0
- package/dist/teste/Tooltip.test.js +109 -0
- package/dist/teste/TooltipDark.test.d.ts +1 -0
- package/dist/teste/TooltipDark.test.js +31 -0
- package/dist/utils/calendario.d.ts +28 -0
- package/dist/utils/calendario.js +73 -0
- package/dist/utils/chart.d.ts +4 -0
- package/dist/utils/chart.js +3 -2
- package/dist/utils/html-seguro.d.ts +27 -0
- package/dist/utils/html-seguro.js +97 -0
- package/dist/utils/id.d.ts +2 -0
- package/dist/utils/id.js +23 -0
- package/dist/utils/paleta-de-cores.d.ts +26 -0
- package/dist/utils/paleta-de-cores.js +10 -0
- package/dist/utils/texto.d.ts +5 -0
- package/dist/utils/texto.js +5 -0
- package/package.json +3 -3
- package/src/index.ts +26 -0
- package/src/teste/AILabel.test.tsx +41 -0
- package/src/teste/AccordionConteudoLivre.test.tsx +39 -0
- package/src/teste/Alert.test.tsx +32 -0
- package/src/teste/AtributosRepassados.test.tsx +73 -0
- package/src/teste/AttachmentCardIA.test.tsx +126 -0
- package/src/teste/AvatarGroupOverlap.test.tsx +74 -0
- package/src/teste/BadgeTag.test.tsx +64 -0
- package/src/teste/BottomSheet.test.tsx +25 -0
- package/src/teste/BoxItemFlex.test.tsx +81 -0
- package/src/teste/BoxLayout.test.tsx +50 -0
- package/src/teste/Button.test.tsx +39 -0
- package/src/teste/Calendar.test.tsx +282 -0
- package/src/teste/ChipsXs.test.tsx +41 -0
- package/src/teste/Coachmark.test.tsx +198 -0
- package/src/teste/ColorPicker.test.tsx +153 -0
- package/src/teste/ConfirmAIAction.test.tsx +41 -0
- package/src/teste/DataTableCelulaLivre.test.tsx +103 -0
- package/src/teste/DataTableDocumento.test.tsx +102 -0
- package/src/teste/DatePicker.test.tsx +38 -0
- package/src/teste/Dropdown.test.tsx +146 -0
- package/src/teste/FileInputTrigger.test.tsx +89 -0
- package/src/teste/IconPicker.test.tsx +145 -0
- package/src/teste/InputMascaraEAfins.test.tsx +124 -0
- package/src/teste/KbdCodeBlock.test.tsx +106 -0
- package/src/teste/List.test.tsx +269 -0
- package/src/teste/Modal.test.tsx +28 -0
- package/src/teste/ModalVariantes.test.tsx +173 -0
- package/src/teste/MultiSelectErro.test.tsx +97 -0
- package/src/teste/NomeAcessivelSsr.test.tsx +110 -0
- package/src/teste/OrgChart.test.tsx +183 -0
- package/src/teste/OtpInput.test.tsx +163 -0
- package/src/teste/PopoverMaxHeight.test.tsx +47 -0
- package/src/teste/RichTextEditor.test.tsx +329 -0
- package/src/teste/RotulosTraduziveis.test.tsx +545 -0
- package/src/teste/SegmentedControl.test.tsx +57 -0
- package/src/teste/Select.test.tsx +97 -0
- package/src/teste/SelectPlacementFiltro.test.tsx +110 -0
- package/src/teste/Stack.test.tsx +80 -0
- package/src/teste/StatCardRotuloTopo.test.tsx +44 -0
- package/src/teste/TabsContadorFechavel.test.tsx +144 -0
- package/src/teste/Tooltip.test.tsx +219 -0
- package/src/teste/TooltipDark.test.tsx +51 -0
- package/src/utils/calendario.ts +78 -0
- package/src/utils/chart.ts +7 -2
- package/src/utils/html-seguro.ts +94 -0
- package/src/utils/id.ts +24 -0
- package/src/utils/paleta-de-cores.ts +34 -0
- package/src/utils/texto.ts +5 -0
|
@@ -29,6 +29,16 @@ export interface AIContentProps {
|
|
|
29
29
|
sources?: string[];
|
|
30
30
|
notIncluded?: string;
|
|
31
31
|
hideLabel?: any;
|
|
32
|
+
/** Texto do selo interno, repassado ao AILabel. Troque para traduzir. @default 'IA' */
|
|
33
|
+
label?: string;
|
|
34
|
+
/** Descrição acessível do selo interno, repassada ao AILabel. Troque para traduzir. @default 'Conteúdo gerado por IA' */
|
|
35
|
+
ariaLabel?: string;
|
|
36
|
+
/** Título do painel de explicação, repassado ao AILabel. Troque para traduzir. @default 'Como isto foi gerado' */
|
|
37
|
+
explanationTitle?: string;
|
|
38
|
+
/** Título da lista de fontes no painel, repassado ao AILabel. Troque para traduzir. @default 'Baseado em' */
|
|
39
|
+
sourcesLabel?: string;
|
|
40
|
+
/** Título do bloco do que ficou de fora, repassado ao AILabel. Troque para traduzir. @default 'Não considerado' */
|
|
41
|
+
notIncludedLabel?: string;
|
|
32
42
|
className?: string;
|
|
33
43
|
id?: string;
|
|
34
44
|
children?: any;
|
|
@@ -36,6 +36,6 @@ function AIContent(props) {
|
|
|
36
36
|
props.onRevert(event);
|
|
37
37
|
}
|
|
38
38
|
}
|
|
39
|
-
return (_jsxs("div", { className: classes(), id: props.id, children: [mostraSelo() ? (_jsx("div", { className: "umds-aicontent__cabecalho", children: _jsx(AILabel, { size: "sm", explanation: props.explanation, sources: props.sources, notIncluded: props.notIncluded }) })) : null, _jsx("div", { className: "umds-aicontent__corpo", children: _jsx(_Fragment, { children: props.children }) }), foiEditado() ? (_jsxs("div", { className: "umds-aicontent__rodape", children: [_jsx("span", { className: "umds-aicontent__estado", children: props.editedLabel || "Editado por você" }), podeReverter() ? (_jsxs("button", { type: "button", className: "umds-aicontent__reverter", onClick: (event) => handleRevert(event), children: [_jsx(Icon, { size: "sm", variant: "inherit", icon: faRotateLeft }), _jsx("span", { children: props.revertLabel || "Reverter para a sugestão da IA" })] })) : null, estaTravado() ? (_jsx("span", { className: "umds-aicontent__travado", children: props.lockedLabel || "Confirmado — não é mais reversível" })) : null] })) : null] }));
|
|
39
|
+
return (_jsxs("div", { className: classes(), id: props.id, children: [mostraSelo() ? (_jsx("div", { className: "umds-aicontent__cabecalho", children: _jsx(AILabel, { size: "sm", label: props.label, ariaLabel: props.ariaLabel, explanationTitle: props.explanationTitle, sourcesLabel: props.sourcesLabel, notIncludedLabel: props.notIncludedLabel, explanation: props.explanation, sources: props.sources, notIncluded: props.notIncluded }) })) : null, _jsx("div", { className: "umds-aicontent__corpo", children: _jsx(_Fragment, { children: props.children }) }), foiEditado() ? (_jsxs("div", { className: "umds-aicontent__rodape", children: [_jsx("span", { className: "umds-aicontent__estado", children: props.editedLabel || "Editado por você" }), podeReverter() ? (_jsxs("button", { type: "button", className: "umds-aicontent__reverter", onClick: (event) => handleRevert(event), children: [_jsx(Icon, { size: "sm", variant: "inherit", icon: faRotateLeft }), _jsx("span", { children: props.revertLabel || "Reverter para a sugestão da IA" })] })) : null, estaTravado() ? (_jsx("span", { className: "umds-aicontent__travado", children: props.lockedLabel || "Confirmado — não é mais reversível" })) : null] })) : null] }));
|
|
40
40
|
}
|
|
41
41
|
export default AIContent;
|
|
@@ -34,6 +34,10 @@ export interface AILabelProps {
|
|
|
34
34
|
className?: string;
|
|
35
35
|
id?: string;
|
|
36
36
|
ariaLabel?: string;
|
|
37
|
+
/** Título da lista de fontes no painel. Troque para traduzir. @default 'Baseado em' */
|
|
38
|
+
sourcesLabel?: string;
|
|
39
|
+
/** Título do bloco do que ficou de fora, no painel. Troque para traduzir. @default 'Não considerado' */
|
|
40
|
+
notIncludedLabel?: string;
|
|
37
41
|
children?: any;
|
|
38
42
|
}
|
|
39
43
|
declare function AILabel(props: AILabelProps): import("react/jsx-runtime").JSX.Element;
|
|
@@ -5,7 +5,7 @@ import { useState } from "react";
|
|
|
5
5
|
import { faWandMagicSparkles } from "@fortawesome/free-solid-svg-icons";
|
|
6
6
|
import Icon from "../Icon/Icon";
|
|
7
7
|
function AILabel(props) {
|
|
8
|
-
const [internalOpen, setInternalOpen] = useState(() =>
|
|
8
|
+
const [internalOpen, setInternalOpen] = useState(() => props.defaultOpen === true);
|
|
9
9
|
const [uid, setUid] = useState(() => `umds-ailabel-${Math.random().toString(36).slice(2, 9)}`);
|
|
10
10
|
function baseId() {
|
|
11
11
|
return props.id || uid;
|
|
@@ -54,6 +54,6 @@ function AILabel(props) {
|
|
|
54
54
|
props.onFix(event);
|
|
55
55
|
}
|
|
56
56
|
}
|
|
57
|
-
return (_jsxs("span", { className: classes(), id: baseId(), children: [_jsxs("button", { type: "button", className: "umds-ailabel__selo", "aria-label": props.ariaLabel || "Conteúdo gerado por IA", "aria-expanded": temExplicacao() ? isOpen() : undefined, "aria-controls": temExplicacao() ? painelId() : undefined, disabled: !temExplicacao(), onClick: (event) => alternar(event), children: [_jsx(Icon, { size: "sm", variant: "inherit", icon: faWandMagicSparkles }), _jsx("span", { className: "umds-ailabel__texto", children: props.label || "IA" })] }), temExplicacao() && isOpen() ? (_jsxs("div", { className: "umds-ailabel__painel", role: "region", id: painelId(), children: [_jsx("p", { className: "umds-ailabel__painel-titulo", children: props.explanationTitle || "Como isto foi gerado" }), props.explanation ? (_jsx("div", { className: "umds-ailabel__painel-texto", children: props.explanation })) : null, props.sources && props.sources.length > 0 ? (_jsxs("div", { className: "umds-ailabel__bloco", children: [_jsx("p", { className: "umds-ailabel__rotulo", children: "Baseado em" }), _jsx("ul", { className: "umds-ailabel__lista", children: listaFontes()?.map((fonte) => (_jsx("li", { children: fonte }, fonte))) })] })) : null, props.notIncluded ? (_jsxs("div", { className: "umds-ailabel__bloco", children: [_jsx("p", { className: "umds-ailabel__rotulo", children: "
|
|
57
|
+
return (_jsxs("span", { className: classes(), id: baseId(), children: [_jsxs("button", { type: "button", className: "umds-ailabel__selo", "aria-label": props.ariaLabel || "Conteúdo gerado por IA", "aria-expanded": temExplicacao() ? isOpen() : undefined, "aria-controls": temExplicacao() ? painelId() : undefined, disabled: !temExplicacao(), onClick: (event) => alternar(event), children: [_jsx(Icon, { size: "sm", variant: "inherit", icon: faWandMagicSparkles }), _jsx("span", { className: "umds-ailabel__texto", children: props.label || "IA" })] }), temExplicacao() && isOpen() ? (_jsxs("div", { className: "umds-ailabel__painel", role: "region", id: painelId(), children: [_jsx("p", { className: "umds-ailabel__painel-titulo", children: props.explanationTitle || "Como isto foi gerado" }), props.explanation ? (_jsx("div", { className: "umds-ailabel__painel-texto", children: props.explanation })) : null, props.sources && props.sources.length > 0 ? (_jsxs("div", { className: "umds-ailabel__bloco", children: [_jsx("p", { className: "umds-ailabel__rotulo", children: props.sourcesLabel || "Baseado em" }), _jsx("ul", { className: "umds-ailabel__lista", children: listaFontes()?.map((fonte) => (_jsx("li", { children: fonte }, fonte))) })] })) : null, props.notIncluded ? (_jsxs("div", { className: "umds-ailabel__bloco", children: [_jsx("p", { className: "umds-ailabel__rotulo", children: props.notIncludedLabel || "Não considerado" }), _jsx("p", { className: "umds-ailabel__painel-texto", children: props.notIncluded })] })) : null, _jsx(_Fragment, { children: props.children }), props.onFix ? (_jsx("button", { type: "button", className: "umds-ailabel__acao", onClick: (event) => handleFix(event), children: props.fixLabel || "Corrigir manualmente" })) : null] })) : null] }));
|
|
58
58
|
}
|
|
59
59
|
export default AILabel;
|
|
@@ -2,14 +2,18 @@ import './Accordion.css';
|
|
|
2
2
|
export interface AccordionItemData {
|
|
3
3
|
id: string;
|
|
4
4
|
title: string;
|
|
5
|
-
/**
|
|
5
|
+
/**
|
|
6
|
+
* Conteúdo do painel. React: aceita qualquer nó. Vue: aqui vai só texto; para
|
|
7
|
+
* conteúdo livre (campos, botões) use o slot `#content-<id>` do item, que
|
|
8
|
+
* recebe `{ item }` e vale sobre este texto.
|
|
9
|
+
*/
|
|
6
10
|
content: any;
|
|
7
11
|
disabled?: boolean;
|
|
8
12
|
defaultOpen?: boolean;
|
|
9
13
|
}
|
|
10
14
|
/**
|
|
11
15
|
* Accordion component — lista de painéis expansíveis (sanfona).
|
|
12
|
-
* @property {AccordionItemData[]} items - Itens do accordion (id, title, content, disabled?, defaultOpen?)
|
|
16
|
+
* @property {AccordionItemData[]} items - Itens do accordion (id, title, content, disabled?, defaultOpen?). Conteúdo livre por item: no React, `content` aceita nó; no Vue, o slot `#content-<id>` (recebe `{ item }`).
|
|
13
17
|
* @property {boolean} multiple - Permite manter vários painéis abertos ao mesmo tempo
|
|
14
18
|
* @property {string} variant - Estilo visual: 'default' | 'bordered' | 'separated'
|
|
15
19
|
* @property {string} className - Classes CSS adicionais
|
|
@@ -133,6 +133,7 @@
|
|
|
133
133
|
|
|
134
134
|
.umds-alert__close:hover {
|
|
135
135
|
opacity: 1;
|
|
136
|
+
/* stylelint-disable-next-line 1ds/cor-por-token -- o DS não tem token de realce translúcido escuro (candidato a novo token) */
|
|
136
137
|
background-color: rgba(0, 0, 0, 0.08); /* realce suave de hover (sem token 1DS) */
|
|
137
138
|
}
|
|
138
139
|
|
|
@@ -212,6 +213,7 @@
|
|
|
212
213
|
|
|
213
214
|
/* Overrides for close icon on SOLID */
|
|
214
215
|
.umds-alert--solid .umds-alert__close:hover {
|
|
216
|
+
/* stylelint-disable-next-line 1ds/cor-por-token -- o DS não tem token de realce translúcido claro (candidato a novo token); currentColor mudaria o hover nos temas escuros, ver bloco de alto contraste abaixo */
|
|
215
217
|
background-color: rgba(255, 255, 255, 0.15); /* realce de hover sobre fundo escuro (sem token 1DS) */
|
|
216
218
|
}
|
|
217
219
|
|
|
@@ -17,7 +17,9 @@ export interface AlertProps {
|
|
|
17
17
|
*/
|
|
18
18
|
description?: string;
|
|
19
19
|
/**
|
|
20
|
-
* Variante semântica (cor/finalidade) do alerta.
|
|
20
|
+
* Variante semântica (cor/finalidade) do alerta. Também define como o
|
|
21
|
+
* leitor de tela anuncia: `negative` usa `role="alert"` (assertivo,
|
|
22
|
+
* interrompe a leitura); as demais usam `role="status"` (educado).
|
|
21
23
|
* @default 'neutral'
|
|
22
24
|
*/
|
|
23
25
|
variant?: "neutral" | "positive" | "info" | "negative";
|
|
@@ -22,6 +22,12 @@ function Alert(props) {
|
|
|
22
22
|
.filter(Boolean)
|
|
23
23
|
.join(" ");
|
|
24
24
|
}
|
|
25
|
+
function liveRole() {
|
|
26
|
+
return props.variant === "negative" ? "alert" : "status";
|
|
27
|
+
}
|
|
28
|
+
function ariaLive() {
|
|
29
|
+
return props.variant === "negative" ? "assertive" : "polite";
|
|
30
|
+
}
|
|
25
31
|
function iconName() {
|
|
26
32
|
const currentVariant = props.variant || "neutral";
|
|
27
33
|
if (currentVariant === "positive")
|
|
@@ -64,6 +70,6 @@ function Alert(props) {
|
|
|
64
70
|
}
|
|
65
71
|
};
|
|
66
72
|
}, []);
|
|
67
|
-
return (_jsx(_Fragment, { children: visible ? (_jsx(_Fragment, { children: _jsxs("div", { role: "
|
|
73
|
+
return (_jsx(_Fragment, { children: visible ? (_jsx(_Fragment, { children: _jsxs("div", { role: liveRole(), "aria-live": ariaLive(), id: props.id, className: classes(), children: [_jsx("div", { className: "umds-alert__icon-wrapper", children: _jsx(Icon, { variant: "inherit", size: "md", icon: iconName() }) }), _jsxs("div", { className: "umds-alert__content", children: [props.title ? (_jsx("div", { className: "umds-alert__title-container", children: _jsx(Text, { variant: "body2", as: "p", className: "umds-alert__title-text", children: props.title }) })) : null, props.description ? (_jsx(Text, { variant: "caption", as: "p", className: "umds-alert__description-text", children: props.description })) : null, props.content || props.children ? (_jsxs("div", { className: "umds-alert__actions", children: [props.content ? (_jsx(_Fragment, { children: props.content })) : null, !props.content ? _jsx(_Fragment, { children: props.children }) : null] })) : null] }), props.dismissable ? (_jsx("button", { type: "button", className: "umds-alert__close", onClick: (event) => handleClose(event), "aria-label": props.dismissLabel || "Dispensar alerta", children: _jsx(Icon, { variant: "inherit", size: "md", icon: faXmark }) })) : null] }) })) : null }));
|
|
68
74
|
}
|
|
69
75
|
export default Alert;
|
|
@@ -39,7 +39,7 @@
|
|
|
39
39
|
.umds-app-header__direita {
|
|
40
40
|
display: flex;
|
|
41
41
|
align-items: center;
|
|
42
|
-
gap:
|
|
42
|
+
gap: var(--umds-primitive-spacing-xxxs); /* 16px (protótipo 20px) */
|
|
43
43
|
}
|
|
44
44
|
|
|
45
45
|
/* ── Largura estreita: a barra nunca passa do contêiner ─────────────────────
|
|
@@ -48,8 +48,9 @@
|
|
|
48
48
|
(`min-width: 0`) mas nada DENTRO delas encolhia — itens `nowrap`, busca fixa
|
|
49
49
|
com `flex-shrink: 0` — e o conteúdo vazava para fora da barra, criando
|
|
50
50
|
rolagem horizontal na página. Agora a ordem de sacrifício é:
|
|
51
|
-
1.
|
|
52
|
-
o que tirar da esquerda: a esquerda
|
|
51
|
+
1. os itens de navegação do fim vão para o menu "Mais" (a direita só
|
|
52
|
+
perde espaço quando não há mais o que tirar da esquerda: a esquerda
|
|
53
|
+
tem base 0 e só cresce);
|
|
53
54
|
2. a busca encolhe até 96px;
|
|
54
55
|
3. o nome do usuário vira reticências.
|
|
55
56
|
Marca, ações e avatar nunca encolhem. Com espaço sobrando, nada disso age e
|
|
@@ -90,12 +91,84 @@
|
|
|
90
91
|
overflow-clip-margin: 4px; /* anel de foco: 2px de outline + 2px de offset */
|
|
91
92
|
}
|
|
92
93
|
|
|
94
|
+
/* ── Itens e menu "Mais" ─────────────────────────────────────────────────────
|
|
95
|
+
Recortar o último item deixava um pedaço dele clicável com ~13px de largura
|
|
96
|
+
(WCAG 2.5.8, `target-size`). Agora os itens que não cabem saem da barra e
|
|
97
|
+
vão para o menu "Mais" — quem decide quais é a medição do componente, que
|
|
98
|
+
marca cada excedente com `data-umds-excedente`. O recorte da `<nav>` acima
|
|
99
|
+
fica só como rede de segurança (um item ativo sozinho mais largo que a
|
|
100
|
+
barra). Com espaço sobrando, o botão não aparece e o desenho é o de sempre. */
|
|
101
|
+
.umds-app-header__itens {
|
|
102
|
+
display: flex;
|
|
103
|
+
align-items: center;
|
|
104
|
+
gap: var(--umds-primitive-spacing-xxs); /* 24px, o mesmo da nav */
|
|
105
|
+
/* Do tamanho do conteúdo: o "Mais" vem logo depois do último item visível. */
|
|
106
|
+
flex: 0 1 auto;
|
|
107
|
+
min-width: 0;
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
.umds-app-header__itens > [data-umds-excedente] {
|
|
111
|
+
display: none;
|
|
112
|
+
}
|
|
113
|
+
|
|
114
|
+
.umds-app-header__mais {
|
|
115
|
+
display: flex;
|
|
116
|
+
align-items: center;
|
|
117
|
+
flex-shrink: 0;
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
/* Sem excedentes: fora do fluxo e invisível (sai também da árvore de
|
|
121
|
+
acessibilidade e do Tab), mas com caixa, para a medição saber a largura. */
|
|
122
|
+
.umds-app-header__mais--vazio {
|
|
123
|
+
position: absolute;
|
|
124
|
+
visibility: hidden;
|
|
125
|
+
pointer-events: none;
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
/* O gatilho tem o desenho do `AppNavItem`: é mais um item da navegação. */
|
|
129
|
+
.umds-app-header__mais-gatilho {
|
|
130
|
+
box-sizing: border-box;
|
|
131
|
+
display: inline-flex;
|
|
132
|
+
align-items: center;
|
|
133
|
+
gap: var(--umds-primitive-spacing-nano); /* 8px, como no AppNavItem (protótipo 6px) */
|
|
134
|
+
min-height: 24px; /* alvo mínimo do WCAG 2.5.8 */
|
|
135
|
+
margin: 0;
|
|
136
|
+
padding: 0;
|
|
137
|
+
border: none;
|
|
138
|
+
background: none;
|
|
139
|
+
color: var(--umds-semantic-color-neutral-dark-pure);
|
|
140
|
+
font-family: inherit;
|
|
141
|
+
font-size: var(--umds-primitive-font-size-xxs); /* 14px */
|
|
142
|
+
font-weight: var(--umds-primitive-font-weight-semibold);
|
|
143
|
+
line-height: 1;
|
|
144
|
+
white-space: nowrap;
|
|
145
|
+
cursor: pointer;
|
|
146
|
+
transition: color var(--umds-semantic-motion-duration-fast)
|
|
147
|
+
var(--umds-semantic-motion-easing-standard);
|
|
148
|
+
}
|
|
149
|
+
|
|
150
|
+
.umds-app-header__mais-gatilho:hover,
|
|
151
|
+
.umds-app-header__mais-gatilho[aria-expanded="true"] {
|
|
152
|
+
color: var(--umds-semantic-color-primary-pure);
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
.umds-app-header__mais-gatilho:focus-visible {
|
|
156
|
+
outline: 2px solid var(--umds-semantic-color-primary-pure);
|
|
157
|
+
outline-offset: 2px;
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
.umds-app-header__mais-seta {
|
|
161
|
+
display: inline-flex;
|
|
162
|
+
align-items: center;
|
|
163
|
+
font-size: 10px; /* protótipo 10px, como as outras setas do cabeçalho */
|
|
164
|
+
}
|
|
165
|
+
|
|
93
166
|
/* ── Ação principal (o "+ Novo") ──────────────────────────────────────────── */
|
|
94
167
|
.umds-app-header__acao-principal {
|
|
95
168
|
background: var(--umds-semantic-color-primary-pure);
|
|
96
169
|
color: var(--umds-semantic-color-neutral-light-pure);
|
|
97
170
|
border: none;
|
|
98
|
-
border-radius:
|
|
171
|
+
border-radius: var(--umds-primitive-border-radius-sm); /* 8px — raio canônico (protótipo 6px) */
|
|
99
172
|
padding: 0 var(--umds-primitive-spacing-xxxs); /* 16px */
|
|
100
173
|
height: var(--umds-primitive-spacing-xs); /* 32px */
|
|
101
174
|
font-size: 13px; /* protótipo 13px — entre os degraus 12 e 14 */
|
|
@@ -104,7 +177,7 @@
|
|
|
104
177
|
cursor: pointer;
|
|
105
178
|
display: inline-flex;
|
|
106
179
|
align-items: center;
|
|
107
|
-
gap:
|
|
180
|
+
gap: var(--umds-primitive-spacing-nano); /* 8px, igual ao Button (protótipo 6px) */
|
|
108
181
|
white-space: nowrap;
|
|
109
182
|
transition: background var(--umds-semantic-motion-duration-fast)
|
|
110
183
|
var(--umds-semantic-motion-easing-standard);
|
|
@@ -133,8 +206,8 @@
|
|
|
133
206
|
max-width: 100%; /* encolhe com a busca quando falta espaço */
|
|
134
207
|
height: var(--umds-semantic-field-height-sm); /* 32px */
|
|
135
208
|
border: 1px solid var(--umds-semantic-color-neutral-light-down);
|
|
136
|
-
border-radius:
|
|
137
|
-
padding: 0 var(--umds-primitive-spacing-mini) 0
|
|
209
|
+
border-radius: var(--umds-primitive-border-radius-sm); /* 8px — raio canônico (protótipo 4px) */
|
|
210
|
+
padding: 0 var(--umds-primitive-spacing-mini) 0 var(--umds-primitive-spacing-xs); /* 0 12px 0 32px (protótipo 30px) */
|
|
138
211
|
font-size: 13px; /* protótipo 13px */
|
|
139
212
|
font-family: inherit;
|
|
140
213
|
color: var(--umds-semantic-color-neutral-dark-pure);
|
|
@@ -188,7 +261,7 @@
|
|
|
188
261
|
align-items: center;
|
|
189
262
|
margin-left: var(--umds-primitive-spacing-nano); /* 8px */
|
|
190
263
|
border-left: 1px solid var(--umds-semantic-color-neutral-light-medium);
|
|
191
|
-
padding-left:
|
|
264
|
+
padding-left: var(--umds-primitive-spacing-xxxs); /* 16px (protótipo 20px) */
|
|
192
265
|
position: relative;
|
|
193
266
|
min-width: 0;
|
|
194
267
|
}
|
|
@@ -252,6 +325,7 @@
|
|
|
252
325
|
|
|
253
326
|
@media (prefers-reduced-motion: reduce) {
|
|
254
327
|
.umds-app-header__acao-principal,
|
|
328
|
+
.umds-app-header__mais-gatilho,
|
|
255
329
|
.umds-app-header__busca-campo {
|
|
256
330
|
transition: none;
|
|
257
331
|
}
|
|
@@ -54,8 +54,19 @@ export interface AppHeaderProps {
|
|
|
54
54
|
className?: string;
|
|
55
55
|
/** Marca. O padrão é o `Logo` da 1Doc; passe outro conteúdo para substituir. */
|
|
56
56
|
brand?: any;
|
|
57
|
-
/**
|
|
57
|
+
/**
|
|
58
|
+
* Navegação principal — normalmente uma lista de `AppNavItem`.
|
|
59
|
+
*
|
|
60
|
+
* Quando os itens não cabem na barra, os do fim saem dela e vão para o
|
|
61
|
+
* menu "Mais" (o item ativo, `aria-current="page"`, fica na barra sempre
|
|
62
|
+
* que couber sozinho). Escolher um item do menu aciona o próprio item
|
|
63
|
+
* (o `onClick` dele). Item que abre submenu próprio (`hasMenu`) deve vir
|
|
64
|
+
* no começo da lista: o submenu é ancorado no item, e dentro do "Mais"
|
|
65
|
+
* não haveria onde ancorá-lo.
|
|
66
|
+
*/
|
|
58
67
|
children?: any;
|
|
68
|
+
/** Rótulo do botão que reúne os itens de navegação que não cabem. @default "Mais" */
|
|
69
|
+
moreLabel?: string;
|
|
59
70
|
/** Campo de busca próprio, no lugar do padrão. */
|
|
60
71
|
search?: any;
|
|
61
72
|
/** Ícones de ação: tema, idioma, notificações. Recebem espaçamento e cor da barra. */
|
|
@@ -1,10 +1,152 @@
|
|
|
1
1
|
"use client";
|
|
2
2
|
import { jsx as _jsx, Fragment as _Fragment, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
3
|
import './AppHeader.css';
|
|
4
|
+
import { useState, useRef, useEffect } from "react";
|
|
5
|
+
/** Atributo que tira da barra um item que foi para o menu "Mais". Atributo, e
|
|
6
|
+
* não classe: React e Vue reescrevem `class` do item a cada render dele, mas
|
|
7
|
+
* não tocam num atributo que não declararam. */
|
|
4
8
|
import { faChevronDown, faMagnifyingGlass, } from "@fortawesome/free-solid-svg-icons";
|
|
5
9
|
import Icon from "../Icon/Icon";
|
|
6
10
|
import Logo from "../Logo/Logo";
|
|
11
|
+
import Dropdown from "../Dropdown/Dropdown";
|
|
12
|
+
const ATRIBUTO_EXCEDENTE = "data-umds-excedente";
|
|
7
13
|
function AppHeader(props) {
|
|
14
|
+
const itensRef = useRef(null);
|
|
15
|
+
const maisRef = useRef(null);
|
|
16
|
+
const observadorTamanhoRef = useRef(null);
|
|
17
|
+
const observadorMutacaoRef = useRef(null);
|
|
18
|
+
const quadroRef = useRef(0);
|
|
19
|
+
const assinaturaRef = useRef("");
|
|
20
|
+
const [itensExcedentes, setItensExcedentes] = useState(() => []);
|
|
21
|
+
function rotuloMais() {
|
|
22
|
+
return props.moreLabel || "Mais";
|
|
23
|
+
}
|
|
24
|
+
function maisClasses() {
|
|
25
|
+
return itensExcedentes.length > 0
|
|
26
|
+
? "umds-app-header__mais"
|
|
27
|
+
: "umds-app-header__mais umds-app-header__mais--vazio";
|
|
28
|
+
}
|
|
29
|
+
function rotuloDoItem(item) {
|
|
30
|
+
const rotulo = item.querySelector(".umds-app-nav-item__rotulo");
|
|
31
|
+
const contador = item.querySelector(".umds-app-nav-item__contador");
|
|
32
|
+
let texto = "";
|
|
33
|
+
if (rotulo) {
|
|
34
|
+
texto = (rotulo.textContent || "").trim();
|
|
35
|
+
}
|
|
36
|
+
else {
|
|
37
|
+
texto = (item.getAttribute("aria-label") ||
|
|
38
|
+
item.textContent ||
|
|
39
|
+
"").trim();
|
|
40
|
+
if (contador) {
|
|
41
|
+
texto = texto.replace((contador.textContent || "").trim(), "").trim();
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
if (contador) {
|
|
45
|
+
const extra = (contador.getAttribute("aria-label") ||
|
|
46
|
+
contador.textContent ||
|
|
47
|
+
"").trim();
|
|
48
|
+
if (extra)
|
|
49
|
+
texto = texto + " (" + extra + ")";
|
|
50
|
+
}
|
|
51
|
+
return texto;
|
|
52
|
+
}
|
|
53
|
+
function medir() {
|
|
54
|
+
if (typeof window === "undefined" || !itensRef.current || !maisRef.current)
|
|
55
|
+
return;
|
|
56
|
+
const filhos = Array.prototype.slice.call(itensRef.current.children);
|
|
57
|
+
for (let i = 0; i < filhos.length; i++) {
|
|
58
|
+
filhos[i].removeAttribute(ATRIBUTO_EXCEDENTE);
|
|
59
|
+
}
|
|
60
|
+
const vao = parseFloat(window.getComputedStyle(itensRef.current).columnGap) || 0;
|
|
61
|
+
const nav = itensRef.current.parentElement;
|
|
62
|
+
if (!nav)
|
|
63
|
+
return;
|
|
64
|
+
const vaoNav = parseFloat(window.getComputedStyle(nav).columnGap) || 0;
|
|
65
|
+
const larguraMais = maisRef.current.getBoundingClientRect().width;
|
|
66
|
+
const espaco = nav.getBoundingClientRect().right -
|
|
67
|
+
itensRef.current.getBoundingClientRect().left;
|
|
68
|
+
const larguras = [];
|
|
69
|
+
let total = 0;
|
|
70
|
+
let ativo = -1;
|
|
71
|
+
for (let i = 0; i < filhos.length; i++) {
|
|
72
|
+
const largura = filhos[i].getBoundingClientRect().width;
|
|
73
|
+
larguras.push(largura);
|
|
74
|
+
total = total + largura + (i > 0 ? vao : 0);
|
|
75
|
+
if (ativo < 0 &&
|
|
76
|
+
(filhos[i].getAttribute("aria-current") === "page" ||
|
|
77
|
+
filhos[i].querySelector('[aria-current="page"]'))) {
|
|
78
|
+
ativo = i;
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
const ocultos = [];
|
|
82
|
+
// Meio pixel de folga: larguras fracionárias somadas erram na casa decimal.
|
|
83
|
+
if (total > espaco + 0.5) {
|
|
84
|
+
// Com o menu, o botão "Mais" fica no fim da barra, colado na busca:
|
|
85
|
+
// reserva o mesmo vão que separa as regiões do cabeçalho (20px).
|
|
86
|
+
const regiao = nav.parentElement;
|
|
87
|
+
const folga = regiao
|
|
88
|
+
? parseFloat(window.getComputedStyle(regiao).columnGap) || 0
|
|
89
|
+
: 0;
|
|
90
|
+
const disponivel = espaco - larguraMais - vaoNav - folga;
|
|
91
|
+
let usado = ativo >= 0 ? larguras[ativo] : 0;
|
|
92
|
+
let quantos = ativo >= 0 ? 1 : 0;
|
|
93
|
+
let cheio = false;
|
|
94
|
+
for (let i = 0; i < filhos.length; i++) {
|
|
95
|
+
if (i === ativo)
|
|
96
|
+
continue;
|
|
97
|
+
const extra = larguras[i] + (quantos > 0 ? vao : 0);
|
|
98
|
+
if (!cheio && usado + extra <= disponivel) {
|
|
99
|
+
usado = usado + extra;
|
|
100
|
+
quantos = quantos + 1;
|
|
101
|
+
}
|
|
102
|
+
else {
|
|
103
|
+
cheio = true;
|
|
104
|
+
ocultos.push(i);
|
|
105
|
+
}
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
const novos = [];
|
|
109
|
+
for (let j = 0; j < ocultos.length; j++) {
|
|
110
|
+
const indice = ocultos[j];
|
|
111
|
+
filhos[indice].setAttribute(ATRIBUTO_EXCEDENTE, "");
|
|
112
|
+
novos.push({
|
|
113
|
+
key: "item-" + indice,
|
|
114
|
+
label: rotuloDoItem(filhos[indice]),
|
|
115
|
+
});
|
|
116
|
+
}
|
|
117
|
+
// Só troca o estado quando o resultado muda: cada troca re-renderiza, e
|
|
118
|
+
// o re-render dispara os observadores de novo.
|
|
119
|
+
const assinatura = novos.map((n) => n.key + ":" + n.label).join("|");
|
|
120
|
+
if (assinatura !== assinaturaRef.current) {
|
|
121
|
+
assinaturaRef.current = assinatura;
|
|
122
|
+
setItensExcedentes(novos);
|
|
123
|
+
}
|
|
124
|
+
}
|
|
125
|
+
function agendarMedicao() {
|
|
126
|
+
if (typeof requestAnimationFrame === "undefined") {
|
|
127
|
+
medir();
|
|
128
|
+
return;
|
|
129
|
+
}
|
|
130
|
+
if (quadroRef.current)
|
|
131
|
+
return;
|
|
132
|
+
quadroRef.current = requestAnimationFrame(() => {
|
|
133
|
+
quadroRef.current = 0;
|
|
134
|
+
medir();
|
|
135
|
+
});
|
|
136
|
+
}
|
|
137
|
+
function acionarExcedente(item) {
|
|
138
|
+
if (!itensRef.current)
|
|
139
|
+
return;
|
|
140
|
+
const indice = parseInt(item.key.replace("item-", ""), 10);
|
|
141
|
+
const filho = itensRef.current.children[indice];
|
|
142
|
+
if (!filho)
|
|
143
|
+
return;
|
|
144
|
+
const alvo = filho.matches("button, a[href]")
|
|
145
|
+
? filho
|
|
146
|
+
: filho.querySelector('button, a[href], [role="button"], [role="link"]');
|
|
147
|
+
if (alvo)
|
|
148
|
+
alvo.click();
|
|
149
|
+
}
|
|
8
150
|
function classes() {
|
|
9
151
|
return [
|
|
10
152
|
"umds-app-header",
|
|
@@ -29,6 +171,49 @@ function AppHeader(props) {
|
|
|
29
171
|
props.onSearchChange(evento.target.value);
|
|
30
172
|
}
|
|
31
173
|
}
|
|
32
|
-
|
|
174
|
+
useEffect(() => {
|
|
175
|
+
if (typeof window === "undefined" || !itensRef.current)
|
|
176
|
+
return;
|
|
177
|
+
medir();
|
|
178
|
+
if (typeof ResizeObserver !== "undefined") {
|
|
179
|
+
observadorTamanhoRef.current = new ResizeObserver(() => agendarMedicao());
|
|
180
|
+
// A nav, e não a caixa dos itens: a caixa muda de largura a cada
|
|
181
|
+
// medição (itens entrando e saindo); a nav só quando a barra muda.
|
|
182
|
+
if (itensRef.current.parentElement)
|
|
183
|
+
observadorTamanhoRef.current.observe(itensRef.current.parentElement);
|
|
184
|
+
}
|
|
185
|
+
if (typeof MutationObserver !== "undefined") {
|
|
186
|
+
observadorMutacaoRef.current = new MutationObserver(() => agendarMedicao());
|
|
187
|
+
observadorMutacaoRef.current.observe(itensRef.current, {
|
|
188
|
+
childList: true,
|
|
189
|
+
subtree: true,
|
|
190
|
+
characterData: true,
|
|
191
|
+
attributes: true,
|
|
192
|
+
attributeFilter: ["aria-current", "class"],
|
|
193
|
+
});
|
|
194
|
+
}
|
|
195
|
+
if (typeof document !== "undefined" &&
|
|
196
|
+
document.fonts &&
|
|
197
|
+
document.fonts.ready) {
|
|
198
|
+
document.fonts.ready.then(() => agendarMedicao());
|
|
199
|
+
}
|
|
200
|
+
}, []);
|
|
201
|
+
useEffect(() => {
|
|
202
|
+
return () => {
|
|
203
|
+
if (observadorTamanhoRef.current) {
|
|
204
|
+
observadorTamanhoRef.current.disconnect();
|
|
205
|
+
observadorTamanhoRef.current = null;
|
|
206
|
+
}
|
|
207
|
+
if (observadorMutacaoRef.current) {
|
|
208
|
+
observadorMutacaoRef.current.disconnect();
|
|
209
|
+
observadorMutacaoRef.current = null;
|
|
210
|
+
}
|
|
211
|
+
if (quadroRef.current && typeof cancelAnimationFrame !== "undefined") {
|
|
212
|
+
cancelAnimationFrame(quadroRef.current);
|
|
213
|
+
quadroRef.current = 0;
|
|
214
|
+
}
|
|
215
|
+
};
|
|
216
|
+
}, []);
|
|
217
|
+
return (_jsxs("header", { className: classes(), children: [_jsxs("div", { className: "umds-app-header__esquerda", children: [_jsx("span", { className: "umds-app-header__marca", children: _jsx(_Fragment, { children: props.brand || _jsx(Logo, { size: "regular" }) }) }), _jsxs("nav", { className: "umds-app-header__nav", children: [props.primaryActionLabel ? (_jsxs("button", { type: "button", className: "umds-app-header__acao-principal", onClick: (event) => props.onPrimaryAction && props.onPrimaryAction(), children: [props.primaryActionIcon ? (_jsx(Icon, { customSize: "13px", icon: props.primaryActionIcon })) : null, props.primaryActionLabel] })) : null, _jsx("div", { className: "umds-app-header__itens", ref: itensRef, children: _jsx(_Fragment, { children: props.children }) }), _jsx("div", { className: maisClasses(), ref: maisRef, children: _jsx(Dropdown, { placement: "bottom-start", items: itensExcedentes, ariaLabel: rotuloMais(), onSelect: (item) => acionarExcedente(item), children: _jsxs("button", { type: "button", className: "umds-app-header__mais-gatilho", children: [rotuloMais(), _jsx("span", { className: "umds-app-header__mais-seta", "aria-hidden": "true", children: _jsx(Icon, { customSize: "10px", variant: "inherit", icon: faChevronDown }) })] }) }) })] })] }), _jsxs("div", { className: "umds-app-header__direita", children: [props.searchPlaceholder ? (_jsxs("div", { className: "umds-app-header__busca", children: [_jsx("span", { className: "umds-app-header__busca-icone", "aria-hidden": "true", children: _jsx(Icon, { customSize: "13px", icon: faMagnifyingGlass }) }), _jsx("input", { className: "umds-app-header__busca-campo", type: "search", value: props.searchValue, placeholder: props.searchPlaceholder, "aria-label": props.searchPlaceholder, onInput: (evento) => aoDigitar(evento) })] })) : null, _jsxs("div", { className: "umds-app-header__acoes", children: [_jsx(_Fragment, { children: props.search }), _jsx(_Fragment, { children: props.actions })] }), _jsx(_Fragment, { children: props.assistant }), props.userName ? (_jsxs("div", { className: "umds-app-header__usuario", children: [_jsxs("button", { type: "button", className: "umds-app-header__usuario-gatilho", "aria-haspopup": temMenu(), "aria-expanded": menuAberto(), onClick: (event) => props.onUserClick && props.onUserClick(), children: [_jsx("span", { className: "umds-app-header__avatar", "aria-hidden": "true", children: props.userInitials }), _jsx("span", { className: "umds-app-header__usuario-nome", children: props.userName }), _jsx("span", { className: "umds-app-header__usuario-seta", "aria-hidden": "true", children: _jsx(Icon, { customSize: "10px", icon: faChevronDown }) })] }), _jsx(_Fragment, { children: props.userMenu })] })) : null] })] }));
|
|
33
218
|
}
|
|
34
219
|
export default AppHeader;
|
|
@@ -17,7 +17,7 @@
|
|
|
17
17
|
box-sizing: border-box;
|
|
18
18
|
display: inline-flex;
|
|
19
19
|
align-items: center;
|
|
20
|
-
gap:
|
|
20
|
+
gap: var(--umds-primitive-spacing-nano); /* 8px, igual ao Button (protótipo 6px) */
|
|
21
21
|
margin: 0;
|
|
22
22
|
padding: 0;
|
|
23
23
|
border: none;
|
|
@@ -28,6 +28,14 @@
|
|
|
28
28
|
font-weight: var(--umds-primitive-font-weight-semibold);
|
|
29
29
|
line-height: 1;
|
|
30
30
|
white-space: nowrap;
|
|
31
|
+
/* Alvo mínimo do WCAG 2.5.8 (24×24). Com `line-height: 1` o botão tinha
|
|
32
|
+
~15px de altura e o axe reprovava `target-size` quando o vizinho chega
|
|
33
|
+
perto (ex.: a busca do cabeçalho). O item segue sem padding e sem fundo:
|
|
34
|
+
só a caixa clicável cresce, centralizada, e o texto não se move.
|
|
35
|
+
Largura: o rótulo já passa de 24px. NÃO declarar `min-width` — ele troca
|
|
36
|
+
o `min-width: auto` do item flex e deixa o `<nav>` apertado espremer os
|
|
37
|
+
itens um sobre o outro. */
|
|
38
|
+
min-height: 24px;
|
|
31
39
|
cursor: pointer;
|
|
32
40
|
position: relative;
|
|
33
41
|
transition: color var(--umds-semantic-motion-duration-fast)
|
|
@@ -56,8 +64,8 @@
|
|
|
56
64
|
|
|
57
65
|
.umds-app-nav-item__contador {
|
|
58
66
|
box-sizing: border-box;
|
|
59
|
-
padding: var(--umds-primitive-spacing-micro)
|
|
60
|
-
border-radius:
|
|
67
|
+
padding: var(--umds-primitive-spacing-micro) var(--umds-primitive-spacing-quarck); /* 2px 4px, como o contador do AppSidebar (protótipo 2px 6px) */
|
|
68
|
+
border-radius: var(--umds-primitive-border-radius-pill); /* protótipo 12px já era pílula (altura 15px) */
|
|
61
69
|
background-color: var(--umds-semantic-color-primary-pure);
|
|
62
70
|
color: var(--umds-semantic-color-neutral-light-pure);
|
|
63
71
|
font-size: 11px; /* protótipo 11px — abaixo do menor degrau (12) */
|
|
@@ -66,3 +66,12 @@
|
|
|
66
66
|
min-width: 0;
|
|
67
67
|
min-height: 0;
|
|
68
68
|
}
|
|
69
|
+
|
|
70
|
+
/* A região recebe foco por teclado (tabIndex 0) para rolar pelas setas.
|
|
71
|
+
Foco canônico de não-campo, com uma exceção, como nas Tabs: offset
|
|
72
|
+
NEGATIVO — a região encosta no cabeçalho e na barra lateral e o
|
|
73
|
+
`overflow` recortaria um contorno desenhado do lado de fora. */
|
|
74
|
+
.umds-app-shell__conteudo:focus-visible {
|
|
75
|
+
outline: 2px solid var(--umds-semantic-color-primary-pure);
|
|
76
|
+
outline-offset: -2px;
|
|
77
|
+
}
|
|
@@ -32,6 +32,7 @@ import './AppShell.css';
|
|
|
32
32
|
* contêiner da aplicação (`#root`/`#app`) precisam de `height: 100%` — sem
|
|
33
33
|
* isso a rolagem escapa para o `<body>` e cabeçalho e barra lateral rolam junto.
|
|
34
34
|
* @property {string} className - Classes CSS adicionais
|
|
35
|
+
* @property {string} contentLabel - Nome acessível da região de conteúdo (padrão "Conteúdo principal")
|
|
35
36
|
* @quandoUsar Como raiz de uma aplicação com cabeçalho fixo e navegação lateral. É o esqueleto da tela inteira, usado uma vez por app.
|
|
36
37
|
* @quandoNaoUsar Em página solta, tela de login ou conteúdo embutido em outro sistema — ali o layout é da página, não do app. Para agrupar conteúdo dentro de uma tela, use `Box`, `Stack` ou `Container`.
|
|
37
38
|
*/
|
|
@@ -44,6 +45,13 @@ export interface AppShellProps {
|
|
|
44
45
|
sidebar?: any;
|
|
45
46
|
/** Conteúdo da tela — é a única parte que rola. */
|
|
46
47
|
children?: any;
|
|
48
|
+
/**
|
|
49
|
+
* Nome acessível da região de conteúdo (o `<main>`).
|
|
50
|
+
* Padrão: "Conteúdo principal".
|
|
51
|
+
* A região recebe foco por teclado para poder ser rolada pelas setas, e
|
|
52
|
+
* todo elemento focável precisa de nome.
|
|
53
|
+
*/
|
|
54
|
+
contentLabel?: string;
|
|
47
55
|
}
|
|
48
56
|
declare function AppShell(props: AppShellProps): import("react/jsx-runtime").JSX.Element;
|
|
49
57
|
export default AppShell;
|
|
@@ -4,6 +4,9 @@ function AppShell(props) {
|
|
|
4
4
|
function classes() {
|
|
5
5
|
return ["umds-app-shell", props.className].filter(Boolean).join(" ");
|
|
6
6
|
}
|
|
7
|
-
|
|
7
|
+
function conteudoLabel() {
|
|
8
|
+
return props.contentLabel || "Conteúdo principal";
|
|
9
|
+
}
|
|
10
|
+
return (_jsx("div", { className: classes(), children: _jsxs("div", { className: "umds-app-shell__corpo", children: [_jsx(_Fragment, { children: props.sidebar }), _jsxs("div", { className: "umds-app-shell__principal", children: [_jsx(_Fragment, { children: props.header }), _jsx("main", { className: "umds-app-shell__conteudo", tabIndex: 0, "aria-label": conteudoLabel(), children: _jsx(_Fragment, { children: props.children }) })] })] }) }));
|
|
8
11
|
}
|
|
9
12
|
export default AppShell;
|
|
@@ -114,7 +114,7 @@
|
|
|
114
114
|
box-sizing: border-box;
|
|
115
115
|
min-width: var(--umds-primitive-spacing-xxxs);
|
|
116
116
|
padding: 0 var(--umds-primitive-spacing-quarck);
|
|
117
|
-
border-radius:
|
|
117
|
+
border-radius: var(--umds-primitive-border-radius-pill);
|
|
118
118
|
background-color: var(--umds-semantic-color-primary-pure);
|
|
119
119
|
color: var(--umds-semantic-color-neutral-light-pure);
|
|
120
120
|
font-size: var(--umds-primitive-font-size-xxxs);
|
|
@@ -57,6 +57,10 @@ export interface AppSidebarProps {
|
|
|
57
57
|
toggleable?: any;
|
|
58
58
|
/** Nome acessível da navegação. @default 'Navegação principal' */
|
|
59
59
|
ariaLabel?: string;
|
|
60
|
+
/** Nome acessível do botão de abrir com a barra fechada. Troque para traduzir. @default 'Abrir a navegação' */
|
|
61
|
+
expandLabel?: string;
|
|
62
|
+
/** Nome acessível do botão de fechar com a barra aberta. Troque para traduzir. @default 'Fechar a navegação' */
|
|
63
|
+
collapseLabel?: string;
|
|
60
64
|
/** Classes CSS adicionais. */
|
|
61
65
|
className?: string;
|
|
62
66
|
/** Acionado ao clicar num item (recebe o id). */
|
|
@@ -20,7 +20,9 @@ function AppSidebar(props) {
|
|
|
20
20
|
return props.ariaLabel || "Navegação principal";
|
|
21
21
|
}
|
|
22
22
|
function rotuloDoBotao() {
|
|
23
|
-
return props.collapsed
|
|
23
|
+
return props.collapsed
|
|
24
|
+
? props.expandLabel || "Abrir a navegação"
|
|
25
|
+
: props.collapseLabel || "Fechar a navegação";
|
|
24
26
|
}
|
|
25
27
|
function iconeDoBotao() {
|
|
26
28
|
return props.collapsed ? faAngleRight : faAngleLeft;
|