Tema
BaseFieldset
Agrupa controles que respondem a uma mesma pergunta: várias caixas de seleção ou alguns interruptores. É um <fieldset> nativo com <legend>, ajuda, erro e aviso do grupo.
Uso
- Use quando duas ou mais caixas ou interruptores só fazem sentido juntos e precisam de um título comum: "Documentos anexados", "Avisos por e-mail".
- A legenda é a pergunta ou o assunto do grupo; o rótulo de cada controle é a resposta, curto e sem pontuação final.
- Para escolher uma opção entre várias, use
BaseRadioGroup, que já é um fieldset com o comportamento de rádio. - Para um período (vigência, prazo de execução), use
BaseDateRange, que tem rótulo visível para início e fim e valida a ordem das datas. - Não coloque um único campo num fieldset: use
BaseField. E não coloqueBaseFieldsetdentro deBaseField, que criaria um segundo rótulo apontando para nenhum campo. orientation="horizontal"só para duas ou três opções curtas. Na horizontal, a legenda fica a 6 px das opções, como o rótulo de umBaseField, e as opções têm no mínimo a altura de um campo de texto, então o grupo se alinha aos campos ao lado numaBaseFormGrid.hide-labelsó quando um título visível logo acima já diz o que o grupo é. A legenda continua para o leitor de tela.
Estados
- Inválido sempre mostra ícone e texto sob o grupo. Sem
invalid-text, aparece "Revise as opções deste grupo"; prefira uma mensagem que diga o que corrigir. CadaBaseCheckboxdentro recebe do grupo oaria-invalide a borda de erro: não repitainvalidnem dê texto de erro a cada caixa. BaseSwitchnão tem estado inválido. Num grupo de interruptores marcadoinvalid, a mensagem sob o grupo é o único sinal, e ela é lida quando cada interruptor recebe o foco.- Aviso só aparece com
warn-text. Cominvalidewarnao mesmo tempo, vale o erro. - Desabilitado desliga todos os controles de uma vez pelo
disablednativo do fieldset. Diga na ajuda por que o grupo não pode mudar. - Não há estado somente leitura: o HTML não tem
readonlypara caixa de seleção nem para interruptor. Mostre o valor como texto ou usedisabledcom o motivo.
Estilo
| Propriedade | Token |
|---|---|
| Legenda | --tj-text-secondary, --tj-text-sm, semibold; desabilitado --tj-text-placeholder |
| Obrigatório | * em --tj-support-error-text |
| Opcional | "(opcional)" em --tj-text-helper, peso regular |
| Ajuda | --tj-text-helper, --tj-text-sm |
| Erro | ícone e texto --tj-support-error-text, medium; borda das caixas --tj-support-error-text |
| Aviso | ícone e texto --tj-support-warning-text, medium; borda das caixas --tj-support-warning-text |
| Espaço legenda → opções | 6 px (--tj-space-1 × 1,5), o mesmo do rótulo de BaseField |
| Espaço entre opções | --tj-space-2 na vertical; na horizontal --tj-space-6 entre colunas e --tj-space-3 entre linhas |
| Ícone → texto da mensagem | 6 px (--tj-space-1 × 1,5) |
| Altura na horizontal | no mínimo --tj-control-md, alinhada a um campo de texto |
| Moldura | nenhuma: sem borda nem recuo, como no Carbon |
Diferença em relação ao protótipo v3: lá o grupo era um <fieldset class="tj-field"> montado à mão em cada tela; aqui a legenda, as mensagens e o espaço vêm do componente, com os mesmos tokens do BaseRadioGroup. O par de campos do protótipo (.tj-pair) virou o BaseDateRange.
Código
vue
<BaseFieldset label="Documentos anexados" :invalid="erro" invalid-text="Marque pelo menos um documento antes de enviar" required>
<BaseCheckbox v-model="planilha" label="Planilha orçamentária" />
<BaseCheckbox v-model="art" label="ART do responsável técnico" />
</BaseFieldset>| Propriedade | Tipo | Padrão | Descrição |
|---|---|---|---|
label | string | — | Pergunta ou assunto do grupo (obrigatório), vira a legenda |
orientation | 'vertical' | 'horizontal' | 'vertical' | Controles em coluna ou em linha |
helperText | string | — | Ajuda abaixo dos controles |
invalid / invalidText | boolean / string | — / 'Revise as opções deste grupo' | Erro do grupo, no lugar da ajuda; cada caixa recebe aria-invalid |
warn / warnText | boolean / string | — | Aviso, no lugar da ajuda; sem warnText não aparece |
required / optional | boolean | — | Marca na legenda; required é dito em palavras ao leitor de tela. Para "marque pelo menos um", não ponha required nos controles (o navegador exigiria todos): a tela valida o grupo e liga invalid com invalidText |
disabled | boolean | — | Desabilita todos os controles do grupo |
hideLabel | boolean | — | Legenda só para leitor de tela |
Slot padrão: os controles do grupo. O componente não emite eventos; cada controle tem o próprio v-model.
Acessibilidade
Segue o padrão de agrupamento do WAI-ARIA (papel group) com os elementos nativos, como recomenda a técnica H71 do WCAG.
- O grupo é um
<fieldset>com<legend>: o leitor de tela anuncia a legenda ao entrar no grupo, antes do primeiro controle. - Ajuda, erro e aviso do grupo entram no
aria-describedbyde cada caixa e de cada interruptor, depois da ajuda própria do controle, como noBaseRadioGroup. Assim a mensagem é lida quando o controle recebe o foco, mesmo em leitores que não anunciam a descrição de um grupo (VoiceOver, TalkBack) ou quando o usuário pula direto para um controle. - Com
invalid, cadaBaseCheckboxrecebearia-invalid="true"do grupo e ouve o motivo na mesma descrição. A cor nunca é o único sinal: erro e aviso têm ícone e texto. - O HTML não tem
requiredpara um grupo ("marque pelo menos um"), então a legenda diz "(obrigatório)" em texto escondido, e o*visível fica escondido do leitor de tela. - Teclado: cada caixa ou interruptor entra na ordem do Tab e muda com Espaço. O fieldset não recebe foco nem muda a ordem.
disabledusa o atributo nativo do fieldset: todos os controles saem da ordem do Tab e são anunciados como indisponíveis.- Testado com axe em todos os estados e em combinações (obrigatório com legenda escondida, desabilitado com ajuda, erro e aviso juntos), com caixas e com interruptores. O axe roda sem layout, então o contraste das cores é conferido na documentação renderizada, em tema claro e escuro.