@seniorsistemas/angular-components 19.3.3 → 19.3.4

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 (76) hide show
  1. package/accordion/README.md +166 -0
  2. package/alert/README.md +92 -0
  3. package/autocomplete/README.md +162 -0
  4. package/badge/README.md +126 -0
  5. package/bignumber-input/README.md +122 -0
  6. package/breadcrumb/README.md +144 -0
  7. package/button/README.md +159 -0
  8. package/calendar-mask/README.md +89 -0
  9. package/card/README.md +133 -0
  10. package/chat/README.md +130 -0
  11. package/checkbox/README.md +108 -0
  12. package/checkbox-list/README.md +149 -0
  13. package/chips/README.md +152 -0
  14. package/code-editor/README.md +149 -0
  15. package/collapse-link/README.md +128 -0
  16. package/confirm-dialog/README.md +105 -0
  17. package/content-generator/README.md +111 -0
  18. package/control-errors/README.md +92 -0
  19. package/country-phone-picker/README.md +121 -0
  20. package/currency/README.md +90 -0
  21. package/custom-fields/README.md +142 -0
  22. package/dialog/README.md +152 -0
  23. package/dynamic-form/README.md +176 -0
  24. package/editable-overlay/README.md +98 -0
  25. package/empty-state/README.md +134 -0
  26. package/esm2022/loading-state/lib/loading-state/loading-state.component.mjs +4 -4
  27. package/fesm2022/seniorsistemas-angular-components-loading-state.mjs +3 -3
  28. package/fesm2022/seniorsistemas-angular-components-loading-state.mjs.map +1 -1
  29. package/fieldset/README.md +135 -0
  30. package/file-picker/README.md +162 -0
  31. package/file-upload/README.md +23 -7
  32. package/gantt/README.md +173 -0
  33. package/global-search/README.md +151 -0
  34. package/grid-menu/README.md +123 -0
  35. package/help-popover/README.md +134 -0
  36. package/ia-insight/README.md +24 -6
  37. package/image-cropper/README.md +140 -0
  38. package/infinite-scroll/README.md +130 -0
  39. package/info-sign/README.md +111 -0
  40. package/inline-edit/README.md +139 -0
  41. package/insights/README.md +159 -0
  42. package/interactive-content/README.md +120 -0
  43. package/kanban/README.md +184 -0
  44. package/label-value/README.md +154 -0
  45. package/loading-state/README.md +141 -0
  46. package/localized-number-input/README.md +128 -0
  47. package/mouse-events/README.md +157 -0
  48. package/navigation-button/README.md +160 -0
  49. package/numeric/README.md +147 -0
  50. package/numeric-mask/README.md +170 -0
  51. package/object-card/README.md +158 -0
  52. package/package.json +1 -1
  53. package/paginator/README.md +121 -0
  54. package/panel/README.md +147 -0
  55. package/password-strength/README.md +144 -0
  56. package/picklist/README.md +170 -0
  57. package/pin-code-field/README.md +137 -0
  58. package/product-header/README.md +33 -6
  59. package/profile-picture-picker/README.md +159 -0
  60. package/progressbar/README.md +136 -0
  61. package/radio-button/README.md +117 -0
  62. package/rating-scale/README.md +154 -0
  63. package/select/README.md +147 -0
  64. package/select-button/README.md +137 -0
  65. package/sidebar/README.md +117 -0
  66. package/slide-in-bar/README.md +122 -0
  67. package/slider/README.md +127 -0
  68. package/speech-recognition/README.md +104 -0
  69. package/split-button/README.md +126 -0
  70. package/spotlight/README.md +200 -0
  71. package/star-rating/README.md +127 -0
  72. package/stats-card/README.md +135 -0
  73. package/stepper/README.md +164 -0
  74. package/switch/README.md +125 -0
  75. package/table/README.md +185 -0
  76. package/text-area-ia/README.md +17 -6
@@ -0,0 +1,117 @@
1
+ # RadioButton
2
+
3
+ ![Status](https://img.shields.io/badge/status-stable-brightgreen)
4
+
5
+ Componente de botão de opção (radio button) individual com integração nativa ao Angular Forms. Permite seleção única em grupos, utilizando o atributo `name` para garantir exclusividade. Pode ser usado isolado ou em conjunto com `RadioButtonGroupComponent`.
6
+
7
+ ## Quando usar
8
+
9
+ - Seleção exclusiva entre duas ou mais opções mutuamente exclusivas
10
+ - Formulários onde o usuário deve escolher exatamente uma opção de um conjunto pequeno e visível
11
+
12
+ ## Quando não usar
13
+
14
+ - Para seleção de múltiplas opções simultaneamente — use `Checkbox`
15
+ - Para conjuntos grandes de opções — use `Select` (dropdown)
16
+ - Para toggle simples entre dois estados — use `Switch`
17
+
18
+ ## Instalação
19
+
20
+ ```typescript
21
+ import { RadioButtonComponent } from '@seniorsistemas/angular-components/radio-button';
22
+
23
+ @Component({
24
+ standalone: true,
25
+ imports: [RadioButtonComponent, FormsModule],
26
+ })
27
+ export class MeuComponent {}
28
+ ```
29
+
30
+ ## Uso básico
31
+
32
+ ```html
33
+ <s-radiobutton
34
+ value="opcaoA"
35
+ name="minhasOpcoes"
36
+ label="Opção A"
37
+ [(ngModel)]="selecionado"
38
+ ></s-radiobutton>
39
+ ```
40
+
41
+ ## API
42
+
43
+ ### Inputs
44
+
45
+ | Propriedade | Tipo | Padrão | Obrigatório | Descrição |
46
+ |-------------|------|--------|:-----------:|-----------|
47
+ | `label` | `string` | — | Sim | Texto exibido ao lado do botão de opção |
48
+ | `name` | `string` | — | Sim | Nome do grupo. Deve ser igual para todos os botões do mesmo grupo |
49
+ | `value` | `unknown` | — | Sim | Valor associado ao botão. Emitido ao formulário quando selecionado |
50
+ | `buttonDisabled` | `boolean` | `false` | Não | Two-way binding para desabilitar o botão individualmente |
51
+ | `inputId` | `string` | `'RadioButton_X'` | Não | ID único do `<input>` interno, usado para acessibilidade |
52
+
53
+ ### Outputs
54
+
55
+ | Evento | Tipo | Descrição |
56
+ |--------|------|-----------|
57
+ | `focusedInput` | `OutputEmitterRef<FocusEvent>` | Emitido quando o campo interno recebe foco |
58
+ | `inputFocusLost` | `OutputEmitterRef<FocusEvent>` | Emitido quando o campo interno perde o foco |
59
+
60
+ ## Exemplos
61
+
62
+ ### Grupo com ngModel
63
+
64
+ ```html
65
+ <div style="display: flex; flex-direction: column; gap: 8px;">
66
+ <s-radiobutton value="BR" name="paises" label="Brasil" [(ngModel)]="selecionado"></s-radiobutton>
67
+ <s-radiobutton value="JP" name="paises" label="Japão" [(ngModel)]="selecionado"></s-radiobutton>
68
+ <s-radiobutton value="CA" name="paises" label="Canadá" [(ngModel)]="selecionado"></s-radiobutton>
69
+ </div>
70
+ <p>Selecionado: {{ selecionado }}</p>
71
+ ```
72
+
73
+ ### Grupo com Reactive Forms
74
+
75
+ ```html
76
+ <form [formGroup]="form">
77
+ <s-radiobutton value="BR" name="pais" label="Brasil" formControlName="pais"></s-radiobutton>
78
+ <s-radiobutton value="JP" name="pais" label="Japão" formControlName="pais"></s-radiobutton>
79
+ <s-radiobutton value="CA" name="pais" label="Canadá" formControlName="pais"></s-radiobutton>
80
+ </form>
81
+ ```
82
+
83
+ ### Com item desabilitado
84
+
85
+ ```html
86
+ <s-radiobutton value="BR" name="paises" label="Brasil" [(ngModel)]="selecionado"></s-radiobutton>
87
+ <s-radiobutton value="JP" name="paises" label="Japão (indisponível)" [(ngModel)]="selecionado" [buttonDisabled]="true"></s-radiobutton>
88
+ <s-radiobutton value="CA" name="paises" label="Canadá" [(ngModel)]="selecionado"></s-radiobutton>
89
+ ```
90
+
91
+ ### Com ID customizado (para testes ou acessibilidade)
92
+
93
+ ```html
94
+ <s-radiobutton
95
+ value="opcaoA"
96
+ name="grupo"
97
+ label="Opção A"
98
+ inputId="radio-opcao-a"
99
+ [(ngModel)]="selecionado"
100
+ ></s-radiobutton>
101
+ ```
102
+
103
+ ## Acessibilidade
104
+
105
+ - Cada botão é um `<input type="radio">` nativo, totalmente acessível por teclado e leitores de tela
106
+ - Navegação por teclado:
107
+ - `Tab`: move o foco para o grupo de radio buttons
108
+ - `Setas ↑↓` ou `←→`: navegam entre as opções do mesmo grupo (`name`)
109
+ - `Space` ou `Enter`: seleciona o botão em foco
110
+ - O `label` é associado ao `<input>` via `inputId`, garantindo clicabilidade e semântica correta
111
+ - Itens desabilitados são sinalizados com `disabled` nativo
112
+
113
+ ## Componentes relacionados
114
+
115
+ - [`RadioButtonGroup`](../radio-button-group/README.md) — agrupamento com layout e registro centralizado de radio buttons
116
+ - [`Checkbox`](../checkbox/README.md) — seleção múltipla
117
+ - [`Switch`](../switch/README.md) — alternador booleano simples
@@ -0,0 +1,154 @@
1
+ # RatingScale
2
+
3
+ ![Status](https://img.shields.io/badge/status-stable-brightgreen)
4
+
5
+ Componente de escala de avaliação que permite ao usuário selecionar um nó de uma escala visual. Ideal para pesquisas de satisfação (NPS, CSAT) e questionários de feedback. Implementa `ControlValueAccessor` para integração com Reactive Forms e Template-Driven Forms.
6
+
7
+ ## Quando usar
8
+
9
+ - Pesquisas de satisfação com representação visual emocional (ícones de humor)
10
+ - Net Promoter Score (NPS) com escala numérica de 0 a 10
11
+ - Avaliação de atendimento, suporte ou experiência do usuário
12
+ - Formulários de feedback com escalas qualitativas ou quantitativas
13
+
14
+ ## Quando não usar
15
+
16
+ - Para avaliações com estrelas — use `StarRating`
17
+ - Para seleção de uma opção de um conjunto sem representação visual de escala — use `RadioButtonGroup`
18
+ - Quando a escala tem mais de 15 itens e o espaço horizontal é limitado
19
+
20
+ ## Instalação
21
+
22
+ ```typescript
23
+ import { RatingScaleModule } from '@seniorsistemas/angular-components/rating-scale';
24
+
25
+ @NgModule({ imports: [RatingScaleModule] })
26
+ export class MeuModulo {}
27
+ ```
28
+
29
+ ## Uso básico
30
+
31
+ ```html
32
+ <s-rating-scale
33
+ [nodes]="nosAvaliacao"
34
+ startLabel="Insatisfeito"
35
+ endLabel="Satisfeito"
36
+ [(ngModel)]="avaliacaoSelecionada"
37
+ />
38
+ ```
39
+
40
+ ## API
41
+
42
+ ### Inputs
43
+
44
+ | Propriedade | Tipo | Padrão | Obrigatório | Descrição |
45
+ |-------------|------|--------|:-----------:|-----------|
46
+ | `nodes` | `RatingScaleNode[]` | — | Sim | Lista de nós que compõem a escala. Cada nó é uma opção clicável |
47
+ | `startLabel` | `string` | `undefined` | Não | Rótulo exibido abaixo do primeiro nó (extremo negativo) |
48
+ | `endLabel` | `string` | `undefined` | Não | Rótulo exibido abaixo do último nó (extremo positivo) |
49
+ | `disabled` | `boolean` | `false` | Não | Desabilita o componente, impedindo seleção de qualquer nó |
50
+
51
+ ### Tipos
52
+
53
+ ```typescript
54
+ interface RatingScaleNode {
55
+ id: string; // Identificador único do nó (obrigatório)
56
+ title?: string; // Texto exibido abaixo do ícone
57
+ icon?: string; // Classe do ícone Font Awesome (ex: 'fa-smile')
58
+ }
59
+ ```
60
+
61
+ > O `FormControl` deve ser do tipo `RatingScaleNode`. O componente emite o objeto `RatingScaleNode` completo quando um nó é selecionado.
62
+
63
+ ## Exemplos
64
+
65
+ ### Escala de humor com ícones
66
+
67
+ ```typescript
68
+ const nosHumor: RatingScaleNode[] = [
69
+ { id: 'very-happy', title: 'Muito feliz', icon: 'fa-laugh-wink' },
70
+ { id: 'happy', title: 'Feliz', icon: 'fa-smile' },
71
+ { id: 'normal', title: 'Normal', icon: 'fa-meh' },
72
+ { id: 'sad', title: 'Triste', icon: 'fa-sad-tear' },
73
+ { id: 'very-sad', title: 'Muito triste', icon: 'fa-sad-cry' },
74
+ ];
75
+ ```
76
+
77
+ ```html
78
+ <form [formGroup]="form">
79
+ <s-rating-scale
80
+ formControlName="avaliacao"
81
+ [nodes]="nosHumor"
82
+ startLabel="Triste"
83
+ endLabel="Feliz"
84
+ ></s-rating-scale>
85
+ </form>
86
+ ```
87
+
88
+ ### Escala numérica NPS (1 a 10)
89
+
90
+ ```typescript
91
+ const nosNPS: RatingScaleNode[] = Array.from({ length: 10 }, (_, i) => ({
92
+ id: String(i + 1),
93
+ title: String(i + 1),
94
+ }));
95
+ ```
96
+
97
+ ```html
98
+ <s-rating-scale
99
+ formControlName="nps"
100
+ [nodes]="nosNPS"
101
+ startLabel="Muito insatisfeito"
102
+ endLabel="Muito satisfeito"
103
+ ></s-rating-scale>
104
+ ```
105
+
106
+ ### Com valor pré-selecionado
107
+
108
+ ```typescript
109
+ this.form = new FormGroup({
110
+ avaliacao: new FormControl(nosHumor[1]), // 'Feliz' pré-selecionado
111
+ });
112
+ ```
113
+
114
+ ### Desabilitado (somente leitura)
115
+
116
+ ```html
117
+ <s-rating-scale
118
+ formControlName="avaliacao"
119
+ [nodes]="nosHumor"
120
+ [disabled]="true"
121
+ startLabel="Triste"
122
+ endLabel="Feliz"
123
+ ></s-rating-scale>
124
+ ```
125
+
126
+ ### Apenas ícones (sem títulos nos nós)
127
+
128
+ ```html
129
+ <s-rating-scale
130
+ [nodes]="[
131
+ { id: 'very-happy', icon: 'fa-laugh-wink' },
132
+ { id: 'happy', icon: 'fa-smile' },
133
+ { id: 'normal', icon: 'fa-meh' },
134
+ { id: 'sad', icon: 'fa-sad-tear' },
135
+ { id: 'very-sad', icon: 'fa-sad-cry' }
136
+ ]"
137
+ startLabel="Triste"
138
+ endLabel="Feliz"
139
+ [(ngModel)]="avaliacao"
140
+ ></s-rating-scale>
141
+ ```
142
+
143
+ ## Acessibilidade
144
+
145
+ - Cada nó é um elemento `<button>` nativo, navegável por `Tab`, `Enter` e `Space`
146
+ - O nó selecionado recebe destaque visual
147
+ - Os ícones requerem Font Awesome disponível na aplicação
148
+ - `startLabel` e `endLabel` contextualizam os extremos da escala para todos os usuários
149
+ - Em modo `disabled`, nenhum nó aceita interação e o estilo visual indica o estado inativo
150
+
151
+ ## Componentes relacionados
152
+
153
+ - [`StarRating`](../star-rating/README.md) — avaliação por estrelas com escala numérica fixa
154
+ - [`RadioButtonGroup`](../radio-button-group/README.md) — seleção única em lista de opções
@@ -0,0 +1,147 @@
1
+ # Select
2
+
3
+ ![Status](https://img.shields.io/badge/status-stable-brightgreen)
4
+
5
+ Componente de seleção dropdown genérico com suporte a seleção simples e múltipla, filtro, agrupamento, virtual scroll e acessibilidade ARIA completa. Implementa `ControlValueAccessor` para integração com Angular Forms.
6
+
7
+ ## Quando usar
8
+
9
+ - Selecionar uma ou mais opções de uma lista fixa de itens
10
+ - Substituir `<select>` nativo com estilo customizado e recursos avançados
11
+ - Listas longas que precisam de busca textual (`filter`)
12
+ - Opções organizadas por categoria (`group`)
13
+ - Listas com muitos itens que exigem virtualização (`virtualScroll`)
14
+
15
+ ## Quando não usar
16
+
17
+ - Listas com poucas opções sempre visíveis — prefira `SelectButton` ou `RadioButtonGroup`
18
+ - Busca com carregamento dinâmico de resultados — prefira `Autocomplete`
19
+ - Entrada de múltiplos valores livres — prefira `Chips`
20
+
21
+ ## Instalação
22
+
23
+ ```typescript
24
+ import { SelectComponent } from '@seniorsistemas/angular-components/select';
25
+
26
+ @Component({ standalone: true, imports: [SelectComponent] })
27
+ export class MeuComponent {}
28
+ ```
29
+
30
+ ## Uso básico
31
+
32
+ ```html
33
+ <s-select
34
+ formControlName="pais"
35
+ [options]="paises"
36
+ optionLabel="nome"
37
+ optionValue="codigo"
38
+ placeholder="Selecione um país" />
39
+ ```
40
+
41
+ ## API
42
+
43
+ ### Inputs
44
+
45
+ | Propriedade | Tipo | Padrão | Obrigatório | Descrição |
46
+ |-------------|------|--------|:-----------:|-----------|
47
+ | `options` | `T[]` | — | Sim | Lista de opções disponíveis para seleção |
48
+ | `placeholder` | `string` | `''` | Não | Texto exibido quando nenhuma opção está selecionada |
49
+ | `optionLabel` | `keyof T` | `undefined` | Não | Chave do objeto usada como texto de exibição. Obrigatório quando `options` são objetos |
50
+ | `optionValue` | `keyof T` | `undefined` | Não | Chave do objeto cujo valor será emitido ao formulário |
51
+ | `multiple` | `boolean` | `false` | Não | Habilita seleção de múltiplas opções com checkboxes |
52
+ | `filter` | `boolean` | `false` | Não | Exibe campo de busca textual no topo do dropdown |
53
+ | `filterBy` | `keyof T \| (keyof T)[]` | `undefined` | Não | Campo(s) usados para filtragem textual. Padrão: `optionLabel` |
54
+ | `showClear` | `boolean` | `false` | Não | Exibe botão X para limpar a seleção atual |
55
+ | `checkmark` | `boolean` | `false` | Não | Exibe ícone de checkmark ao lado da opção selecionada |
56
+ | `group` | `boolean` | `false` | Não | Habilita agrupamento. As opções devem ter estrutura `{ name, items[] }` |
57
+ | `virtualScroll` | `boolean` | `false` | Não | Virtualiza a lista para melhor performance com grandes volumes |
58
+ | `virtualScrollItemSize` | `number` | `37` | Não | Altura fixa de cada item em pixels para cálculo do virtual scroll |
59
+ | `emptyMessage` | `string \| null` | `null` | Não | Mensagem exibida quando nenhuma opção corresponde ao filtro |
60
+ | `disabled` | `boolean` (model) | `false` | Não | Controla o estado desabilitado via two-way binding |
61
+ | `showOptions` | `boolean` (model) | `false` | Não | Controla a visibilidade do painel via two-way binding |
62
+ | `ariaLabel` | `string` | `''` | Não | Label de acessibilidade do componente |
63
+ | `ariaLabelledBy` | `string` | `''` | Não | ID do elemento externo que descreve o componente |
64
+
65
+ ### Tipos
66
+
67
+ ```typescript
68
+ // Estrutura para opções agrupadas
69
+ interface GroupedOption {
70
+ name: string; // label do grupo
71
+ items: T[]; // opções filhas
72
+ }
73
+ ```
74
+
75
+ ## Exemplos
76
+
77
+ ### Seleção simples
78
+
79
+ ```html
80
+ <form [formGroup]="form">
81
+ <s-select
82
+ formControlName="pais"
83
+ [options]="paises"
84
+ optionLabel="nome"
85
+ optionValue="nome"
86
+ placeholder="Selecione um país"
87
+ [showClear]="true"
88
+ ariaLabel="Selecione um país"
89
+ ></s-select>
90
+ </form>
91
+ ```
92
+
93
+ ### Com filtro de busca
94
+
95
+ ```html
96
+ <s-select
97
+ formControlName="pais"
98
+ [options]="paises"
99
+ optionLabel="nome"
100
+ optionValue="nome"
101
+ placeholder="Buscar país..."
102
+ [filter]="true"
103
+ [showClear]="true"
104
+ ></s-select>
105
+ ```
106
+
107
+ ### Seleção múltipla
108
+
109
+ ```html
110
+ <s-select
111
+ formControlName="paises"
112
+ [options]="paises"
113
+ optionLabel="nome"
114
+ optionValue="nome"
115
+ placeholder="Selecione países..."
116
+ [multiple]="true"
117
+ [filter]="true"
118
+ [showClear]="true"
119
+ ></s-select>
120
+ ```
121
+
122
+ ### Opções agrupadas
123
+
124
+ ```html
125
+ <s-select
126
+ formControlName="pais"
127
+ [options]="paisesPorContinente"
128
+ optionLabel="nome"
129
+ optionValue="nome"
130
+ placeholder="Selecione por continente..."
131
+ [group]="true"
132
+ ariaLabel="Selecione um país por continente"
133
+ ></s-select>
134
+ ```
135
+
136
+ ## Acessibilidade
137
+
138
+ - O componente implementa o padrão ARIA `combobox` com `role="combobox"`, `aria-expanded` e `aria-haspopup`
139
+ - Navegação pelo teclado: `ArrowDown`/`ArrowUp` para mover entre opções, `Enter`/`Espaço` para selecionar, `Escape` para fechar
140
+ - Com `filter` aberto: `ArrowDown` move o foco para a lista, `Escape` retorna foco ao campo de busca
141
+ - Os inputs `ariaLabel` e `ariaLabelledBy` permitem associar descrições externas para leitores de tela
142
+ - Ao fechar o dropdown, o foco retorna automaticamente ao elemento trigger
143
+
144
+ ## Componentes relacionados
145
+
146
+ - [`SelectButton`](../select-button/README.md) — quando as opções devem estar sempre visíveis como botões
147
+ - [`Autocomplete`](../autocomplete/README.md) — quando a lista é carregada dinamicamente via busca
@@ -0,0 +1,137 @@
1
+ # SelectButton
2
+
3
+ ![Status](https://img.shields.io/badge/status-stable-brightgreen)
4
+
5
+ Componente para seleção de uma ou múltiplas opções através de botões visuais agrupados. Alternativa visual ao `select` ou `radio button` quando as opções são poucas e devem estar sempre visíveis. Implementa `ControlValueAccessor` para integração com Angular Forms.
6
+
7
+ ## Quando usar
8
+
9
+ - Filtros de período (hoje, semana, mês) em dashboards
10
+ - Alternância entre modos de visualização (lista, grade, mapa)
11
+ - Seleção de tipo ou categoria com opções mutuamente exclusivas e poucas alternativas (até 5)
12
+ - Filtros com múltiplos critérios aplicáveis simultaneamente (`multiple: true`)
13
+
14
+ ## Quando não usar
15
+
16
+ - Listas com muitas opções — prefira `Select` com dropdown
17
+ - Seleção única com rótulos descritivos longos — prefira `RadioButtonGroup`
18
+ - Entrada de valores livres — prefira `Chips`
19
+
20
+ ## Instalação
21
+
22
+ ```typescript
23
+ import { SelectButtonModule } from '@seniorsistemas/angular-components/select-button';
24
+
25
+ @NgModule({ imports: [SelectButtonModule] })
26
+ export class MeuModule {}
27
+ ```
28
+
29
+ ## Uso básico
30
+
31
+ ```html
32
+ <s-select-button
33
+ formControlName="periodo"
34
+ [items]="periodos"
35
+ />
36
+ ```
37
+
38
+ ## API
39
+
40
+ ### Inputs
41
+
42
+ | Propriedade | Tipo | Padrão | Obrigatório | Descrição |
43
+ |-------------|------|--------|:-----------:|-----------|
44
+ | `items` | `SelectButtonItem[]` | — | Sim | Lista de itens exibidos como botões de seleção |
45
+ | `multiple` | `boolean` | `false` | Não | Permite selecionar múltiplos itens simultaneamente |
46
+
47
+ ### Outputs
48
+
49
+ | Evento | Tipo | Descrição |
50
+ |--------|------|-----------|
51
+ | `itemSelected` | `EventEmitter<SelectButtonItem[]>` | Emitido após a seleção ser atualizada. Emite o array completo de itens ativos |
52
+ | `itemClicked` | `EventEmitter<SelectButtonItem>` | Emitido quando um item habilitado é clicado, antes da atualização da seleção |
53
+
54
+ ### Tipos
55
+
56
+ ```typescript
57
+ interface SelectButtonItem {
58
+ label: string; // Texto exibido no botão. Obrigatório.
59
+ value: any; // Valor associado. Obrigatório.
60
+ disabled?: boolean; // Desabilita o item individualmente.
61
+ }
62
+ ```
63
+
64
+ ## Exemplos
65
+
66
+ ### Seleção única — filtro de período
67
+
68
+ ```html
69
+ <form [formGroup]="form">
70
+ <s-select-button
71
+ formControlName="periodo"
72
+ [items]="periodos"
73
+ [multiple]="false"
74
+ (itemSelected)="onPeriodoChange($event)"
75
+ ></s-select-button>
76
+ </form>
77
+ ```
78
+
79
+ ```typescript
80
+ periodos: SelectButtonItem[] = [
81
+ { label: 'Hoje', value: 'today' },
82
+ { label: 'Esta semana', value: 'week' },
83
+ { label: 'Este mês', value: 'month' },
84
+ { label: 'Este ano', value: 'year' },
85
+ ];
86
+ ```
87
+
88
+ ### Seleção múltipla
89
+
90
+ ```html
91
+ <form [formGroup]="form">
92
+ <s-select-button
93
+ formControlName="frameworks"
94
+ [items]="frameworks"
95
+ [multiple]="true"
96
+ (itemSelected)="onSelecionados($event)"
97
+ (itemClicked)="onClicado($event)"
98
+ ></s-select-button>
99
+ </form>
100
+ ```
101
+
102
+ ### Com item desabilitado individualmente
103
+
104
+ ```html
105
+ <s-select-button
106
+ formControlName="status"
107
+ [items]="statusItems"
108
+ ></s-select-button>
109
+ ```
110
+
111
+ ```typescript
112
+ statusItems: SelectButtonItem[] = [
113
+ { label: 'Ativo', value: 'active' },
114
+ { label: 'Inativo', value: 'inactive' },
115
+ { label: 'Bloqueado', value: 'blocked', disabled: true },
116
+ ];
117
+ ```
118
+
119
+ ### Com valor pré-selecionado via FormControl
120
+
121
+ ```typescript
122
+ form = new FormGroup({
123
+ selection: new FormControl([{ label: 'Angular', value: 'angular' }])
124
+ });
125
+ ```
126
+
127
+ ## Acessibilidade
128
+
129
+ - Cada item do grupo é renderizado como um `<button>` com `role="button"`
130
+ - Itens desabilitados recebem o atributo `disabled` nativo e não respondem a foco ou clique
131
+ - O estado de seleção é indicado visualmente por classes CSS; recomenda-se associar `aria-pressed` via customização para leitores de tela
132
+ - O componente inteiro pode ser desabilitado via `FormControl.disable()` ou `setDisabledState`
133
+
134
+ ## Componentes relacionados
135
+
136
+ - [`Select`](../select/README.md) — quando há muitas opções ou o espaço é limitado
137
+ - [`RadioButtonGroup`](../radio-button-group/README.md) — seleção única com layout vertical/horizontal
@@ -0,0 +1,117 @@
1
+ # Sidebar
2
+
3
+ ![Status](https://img.shields.io/badge/status-stable-brightgreen)
4
+
5
+ Componente de painel lateral deslizante que aparece sobre o conteúdo vindo do lado direito da tela. Suporta templates customizados para cabeçalho, corpo e rodapé via `sTemplate`, bloqueio automático de scroll e confirmação de fechamento.
6
+
7
+ ## Quando usar
8
+
9
+ - Exibir detalhes de um item selecionado sem sair da página atual
10
+ - Formulários simples de edição rápida sem necessidade de uma nova rota
11
+ - Painéis de filtros avançados em listas e tabelas
12
+ - Configurações ou propriedades de um elemento da interface
13
+ - Fluxos complementares que não devem interromper o contexto principal
14
+
15
+ ## Quando não usar
16
+
17
+ - Confirmações de ações destrutivas — prefira `ConfirmDialog`
18
+ - Conteúdo crítico que exige atenção exclusiva do usuário — prefira `Dialog` modal
19
+ - Navegação principal da aplicação — prefira um menu lateral (`nav`) fixo
20
+
21
+ ## Instalação
22
+
23
+ ```typescript
24
+ import { SidebarModule } from '@seniorsistemas/angular-components/sidebar';
25
+
26
+ @NgModule({ imports: [SidebarModule] })
27
+ export class MeuModule {}
28
+ ```
29
+
30
+ ## Uso básico
31
+
32
+ ```html
33
+ <s-sidebar [(visible)]="sidebarAberta" header="Detalhes">
34
+ <p>Conteúdo do painel lateral.</p>
35
+ </s-sidebar>
36
+
37
+ <button (click)="sidebarAberta = true">Abrir Sidebar</button>
38
+ ```
39
+
40
+ ## API
41
+
42
+ ### Inputs
43
+
44
+ | Propriedade | Tipo | Padrão | Obrigatório | Descrição |
45
+ |-------------|------|--------|:-----------:|-----------|
46
+ | `visible` | `ModelSignal<boolean>` | `false` | Não | Controla a visibilidade da sidebar. Suporta `[(visible)]` |
47
+ | `closable` | `boolean` | `true` | Não | Exibe o botão de fechar (X) no cabeçalho |
48
+ | `dismissible` | `boolean` | `true` | Não | Fechar ao clicar no backdrop (área escurecida fora do painel) |
49
+ | `closeOnEscape` | `boolean` | `true` | Não | Fechar ao pressionar a tecla Escape |
50
+ | `header` | `string` | `undefined` | Não | Texto exibido no cabeçalho padrão. Substituível via `sTemplate="header"` |
51
+ | `largeSized` | `boolean` | `false` | Não | Aumenta a largura da sidebar para acomodar mais conteúdo |
52
+ | `cache` | `boolean` | `false` | Não | Mantém o conteúdo no DOM quando fechada, preservando estado interno |
53
+ | `registerConfirmClose` | `() => boolean` | `() => true` | Não | Função chamada antes de fechar; retornar `false` bloqueia o fechamento |
54
+
55
+ ## Exemplos
56
+
57
+ ### Sidebar básica
58
+
59
+ ```html
60
+ <s-sidebar [(visible)]="visible" header="Filtros Avançados" [closable]="true">
61
+ <p>Conteúdo do painel.</p>
62
+ </s-sidebar>
63
+ <s-button label="Abrir" (clicked)="visible = true"></s-button>
64
+ ```
65
+
66
+ ### Sidebar grande
67
+
68
+ ```html
69
+ <s-sidebar [(visible)]="visible" header="Edição de Registro" [largeSized]="true">
70
+ <!-- formulário complexo -->
71
+ </s-sidebar>
72
+ ```
73
+
74
+ ### Com templates customizados
75
+
76
+ ```html
77
+ <s-sidebar [(visible)]="visible">
78
+ <ng-template sTemplate="header">
79
+ <div style="display: flex; align-items: center; gap: 8px;">
80
+ <i class="fa fa-filter"></i>
81
+ <span>Filtros Avançados</span>
82
+ </div>
83
+ </ng-template>
84
+ <ng-template sTemplate="body">
85
+ <!-- conteúdo do painel -->
86
+ </ng-template>
87
+ <ng-template sTemplate="footer">
88
+ <s-button label="Aplicar" priority="primary" (clicked)="visible = false"></s-button>
89
+ </ng-template>
90
+ </s-sidebar>
91
+ ```
92
+
93
+ ### Com confirmação de fechamento
94
+
95
+ ```typescript
96
+ confirmClose = (): boolean => {
97
+ return window.confirm('Deseja realmente fechar? As alterações serão perdidas.');
98
+ };
99
+ ```
100
+
101
+ ```html
102
+ <s-sidebar [(visible)]="visible" [registerConfirmClose]="confirmClose">
103
+ <!-- formulário com alterações não salvas -->
104
+ </s-sidebar>
105
+ ```
106
+
107
+ ## Acessibilidade
108
+
109
+ - A sidebar utiliza `cdkTrapFocus` para aprisionar o foco dentro do painel enquanto aberta
110
+ - Pressionar `Escape` fecha a sidebar quando `closeOnEscape = true`
111
+ - O painel entra e sai com animação de deslizamento (300ms) vindo da direita
112
+ - Ao abrir, o scroll da página é bloqueado automaticamente e restaurado ao fechar
113
+
114
+ ## Componentes relacionados
115
+
116
+ - [`Dialog`](../dialog/README.md) — modal centralizado para confirmações e conteúdo crítico
117
+ - [`SlideInBar`](../slide-in-bar/README.md) — painel que expande/colapsa embutido no layout