@wemake4u/form-controls 2.0.0 → 2.0.2
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/README.md +252 -0
- package/THIRD_PARTY_LICENSES.txt +29 -0
- package/fesm2022/wemake4u-form-controls.mjs +13477 -7133
- package/fesm2022/wemake4u-form-controls.mjs.map +1 -1
- package/package.json +2 -1
- package/types/wemake4u-form-controls.d.ts +2909 -380
package/README.md
CHANGED
|
@@ -15,6 +15,258 @@ Requisiti: Angular 22 (`@angular/core`, `@angular/common`, `@angular/forms`) e i
|
|
|
15
15
|
La libreria **non include e non distribuisce** il Sirio web kit: genera il markup e le classi del kit, ma CSS,
|
|
16
16
|
font e immagini li deve fornire l'applicazione. Versione richiesta: **`sirio-kit-web` 9.1.0** (ultima versione rilasciata).
|
|
17
17
|
|
|
18
|
+
## Sola lettura: aspetto dei campi
|
|
19
|
+
|
|
20
|
+
Nel kit un campo in sola lettura ha lo stesso aspetto di un campo disabilitato (sfondo e bordo grigi). Con
|
|
21
|
+
`readonlyAppearance` i campi in sola lettura possono avere invece lo sfondo bianco e il bordo chiaro del kit, così
|
|
22
|
+
si distinguono dai disabilitati (che restano grigi):
|
|
23
|
+
|
|
24
|
+
| Valore | Aspetto in sola lettura |
|
|
25
|
+
| --- | --- |
|
|
26
|
+
| `filled` (default) | come il kit: sfondo e bordo grigi, uguale al disabilitato (anche la select, che il kit non copre) |
|
|
27
|
+
| `outline` | sfondo bianco, bordo chiaro del kit (`#e3e5e8`), testo nel colore normale del campo |
|
|
28
|
+
|
|
29
|
+
```ts
|
|
30
|
+
// Default per tutta l'applicazione (app.config.ts) o per un componente (providers)
|
|
31
|
+
providers: [provideSirioReadonlyAppearance('outline')]
|
|
32
|
+
```
|
|
33
|
+
|
|
34
|
+
```html
|
|
35
|
+
<!-- Override per il singolo controllo -->
|
|
36
|
+
<wm-sirio-select label="Provincia" readonly readonlyAppearance="outline" ... />
|
|
37
|
+
```
|
|
38
|
+
|
|
39
|
+
Vale per textbox, textarea, number, date, time, datetime, select (anche `searchable`), autocomplete, searchbar e
|
|
40
|
+
slider (campo numerico); prefissi e suffissi dei campi seguono lo stesso aspetto. Con `outline` restano invariati i
|
|
41
|
+
bordi degli stati di validazione (errore, valido, avviso) e del focus da tastiera. Checkbox, radio, checklist e
|
|
42
|
+
file upload non hanno un campo con sfondo: l'impostazione non li modifica.
|
|
43
|
+
|
|
44
|
+
## Select con ricerca: pulsante di azzeramento
|
|
45
|
+
|
|
46
|
+
Di default la select con `searchable` non mostra il pulsante "X" del kit: il valore si cambia scegliendo un'altra
|
|
47
|
+
opzione, o si azzera da codice. Con `clearable` il pulsante viene mostrato e svuota ricerca e selezione.
|
|
48
|
+
|
|
49
|
+
```html
|
|
50
|
+
<wm-sirio-select label="Comune" searchable clearable [options]="comuni" formControlName="comune" />
|
|
51
|
+
```
|
|
52
|
+
|
|
53
|
+
|
|
54
|
+
## Select: opzioni in caricamento
|
|
55
|
+
|
|
56
|
+
Con `loading` la select mostra che le opzioni stanno arrivando (es. da un servizio): il campo chiuso mostra
|
|
57
|
+
`loadingText` ("Caricamento in corso") al posto del placeholder con lo spinner del kit, la lista contiene solo la riga
|
|
58
|
+
"Caricamento in corso" con lo spinner, il combobox ha `aria-busy` e il messaggio è annunciato agli screen reader.
|
|
59
|
+
|
|
60
|
+
```html
|
|
61
|
+
<wm-sirio-select label="Provincia" [loading]="province() === null" [options]="province() ?? []" formControlName="prov" />
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
## Data grid
|
|
65
|
+
|
|
66
|
+
`wm-sirio-data-grid` genera la **tabella del kit** (`table.sirio-table`); filtri, ordinamento e paginazione dei dati
|
|
67
|
+
sono elaborati da [TanStack Table](https://tanstack.com/table) (`@tanstack/angular-table` 9, dipendenza installata con la
|
|
68
|
+
libreria; l'istanza è esposta come `table` per usi avanzati). La griglia ha ordinamento anche su più colonne,
|
|
69
|
+
paginazione (`wm-sirio-pagination`), selezione delle righe, colonne ridimensionabili e riordinabili, righe espandibili
|
|
70
|
+
(dettaglio e dati ad albero), raggruppamento con totali e i layout del kit. Le colonne si dichiarano con
|
|
71
|
+
`wm-sirio-grid-column`; celle e intestazioni personalizzate con i template `wmSirioGridCell` e
|
|
72
|
+
`wmSirioGridHeader`, la riga vuota con `wmSirioGridEmpty`, il dettaglio delle righe con `wmSirioGridDetail`.
|
|
73
|
+
Import unico: `imports: [SIRIO_DATA_GRID]`.
|
|
74
|
+
|
|
75
|
+
```html
|
|
76
|
+
<wm-sirio-data-grid caption="Pratiche" [data]="pratiche" rowId="id" selection="multiple" [(selected)]="scelte">
|
|
77
|
+
<wm-sirio-grid-column field="numero" header="Numero" sortable filter="text" />
|
|
78
|
+
<wm-sirio-grid-column field="importo" header="Importo" align="end" sortable [format]="euro" filter="number" />
|
|
79
|
+
<wm-sirio-grid-column field="stato" header="Stato">
|
|
80
|
+
<ng-template wmSirioGridCell let-row><span [wmSirioTag]="tipo(row)">{{ row.stato }}</span></ng-template>
|
|
81
|
+
</wm-sirio-grid-column>
|
|
82
|
+
</wm-sirio-data-grid>
|
|
83
|
+
```
|
|
84
|
+
|
|
85
|
+
- **Dati in memoria** (`[data]`): la griglia ordina (confronto numerico, per data o testo con le regole della lingua di
|
|
86
|
+
`LOCALE_ID`) e pagina.
|
|
87
|
+
- **Formati predefiniti**: `format` accetta una funzione `(valore, riga) => testo` oppure il nome di un formato, con le
|
|
88
|
+
opzioni in `formatOptions` (tutti seguono `LOCALE_ID`; `empty` = testo dei valori vuoti):
|
|
89
|
+
`number` (`decimals`, `minDecimals`/`maxDecimals`, `grouping`), `currency` (`currency`, default EUR), `percentage`
|
|
90
|
+
(`decimals`, `scale: 'percent'` se il valore è già 15), `date` (`precision`: `day`, `month`, `year`), `dateTime` e
|
|
91
|
+
`time` (`seconds`), `boolean` (`trueLabel`, `falseLabel`, default Sì/No), `map` (`values`: oggetto o `SirioOption[]`).
|
|
92
|
+
Numeri e date si leggono anche da testo (`'89.9'`, `'2026-01-31'`, `'2026-01-31T14:30'`). I formati numerici sono
|
|
93
|
+
allineati a destra (se `align` non è indicato), numeri e date usano il font del kit e si ordinano per valore; con `map`
|
|
94
|
+
il filtro `select` elenca tutti i codici con la loro etichetta. `provideSirioGridFormats({ defaults, formatDefaults,
|
|
95
|
+
formats })` imposta le opzioni di default e registra formati propri per nome (o sostituisce quelli predefiniti).
|
|
96
|
+
- **Formati di `LOCALE_ID`**: senza `format`, i numeri delle celle usano il separatore decimale della lingua (senza
|
|
97
|
+
separatore delle migliaia, così codici e anni restano invariati) e i valori `Date` il formato data; conteggi, numeri
|
|
98
|
+
e date nei chip dei filtri e nei risultati seguono `LOCALE_ID` (es. `it-IT`: "1234,5", "31/01/2026", "10.000").
|
|
99
|
+
- **Font dei numeri del kit**: le celle numeriche e di data (colonne con filtro `number`/`date`, o con valori numero o
|
|
100
|
+
`Date`), i numeri di riga, i conteggi e i totali dei gruppi usano la classe del kit `font-mono` (Roboto Mono, come
|
|
101
|
+
campi numerici, date e paginazione del kit); `mono` sulla colonna lo forza (`true`) o lo toglie (`false`).
|
|
102
|
+
- **Intestazioni su una riga**: il titolo è tagliato con i puntini (testo completo nel tooltip), l'indice di
|
|
103
|
+
ordinamento e l'imbuto del filtro restano visibili. `filterButton="hover"` mostra l'imbuto solo al passaggio del
|
|
104
|
+
mouse, con il focus o quando il filtro è attivo (come ag-grid); `filterButton="none"` toglie i controlli di filtro
|
|
105
|
+
dalla griglia (anche il pannello del layout a card): i filtri si impostano solo da codice (`[(filters)]`, `setFilter`); default `always`.
|
|
106
|
+
- **Riga di filtri** (`filterRow`): una riga sotto le intestazioni, come il floating filter di ag-grid. Ogni colonna
|
|
107
|
+
con filtro ha un campo per la condizione semplice (testo: contiene, numero e data: uguale, select e booleano: un
|
|
108
|
+
valore; con `filterOperators` l'operatore scelto) e l'imbuto con il popover degli operatori; una condizione che non
|
|
109
|
+
sta nel campo (es. "compreso tra", "vuoto", più valori) è mostrata come riepilogo. Esc svuota il filtro della
|
|
110
|
+
colonna. Il campo si chiama "Filtra per <colonna>" (`filterLabel`), l'imbuto "Altre condizioni per <colonna>"
|
|
111
|
+
(`filterMoreLabel`). Con la riga di filtri i chip dei filtri non sono mostrati; nel layout a card resta il pannello "Filtri".
|
|
112
|
+
- **Testo su una riga**: i testi lunghi vanno a capo (default); `[wrap]="false"` sulla colonna tiene il testo su una
|
|
113
|
+
riga (la colonna si allarga, o il testo è tagliato con i puntini se la colonna ha una larghezza). Lo stesso `field`
|
|
114
|
+
può comparire in più colonne (es. una data mostrata come data e come ora), ognuna con il proprio filtro: in `filters` la
|
|
115
|
+
prima colonna usa il `field`, le altre `field~2`, `field~3` (o il loro `filterKey`).
|
|
116
|
+
- **Colonna larga quanto il contenuto**: `fit` sulla colonna (es. una colonna di azioni): non prende parte dello
|
|
117
|
+
spazio libero della tabella, le celle restano su una riga e il titolo non viene tagliato.
|
|
118
|
+
- **Dati da un FormArray** (`[formArray]`): un `FormGroup` per riga; la griglia mostra `getRawValue()` di ogni gruppo
|
|
119
|
+
e segue le modifiche del FormArray (valori, righe aggiunte o tolte da codice). Le righe si modificano in una finestra
|
|
120
|
+
di dialogo del kit con il form di `<ng-template wmSirioGridEditor let-group>`, aperta da "Modifica" nella colonna
|
|
121
|
+
azioni (fissa a destra) o con il doppio clic (`editOnDoubleClick`). Il form lavora su una **copia** della riga creata
|
|
122
|
+
da `rowFactory(valore)` (senza `rowFactory`: copia generica con gli stessi controlli, valori e validatori): "Annulla"
|
|
123
|
+
scarta tutto, "Salva" segna i campi come toccati, attende i validatori asincroni e applica i valori solo se la copia è
|
|
124
|
+
valida (la riga diventa dirty). `saveHandler` / `deleteHandler` (funzioni che restituiscono un valore, una Promise o
|
|
125
|
+
un Observable) controllano la modifica prima di applicarla, ad esempio con una chiamata al server: `false` o un errore
|
|
126
|
+
la bloccano e il messaggio d'errore compare nella finestra. `addable` aggiunge "Aggiungi" (nuova riga da
|
|
127
|
+
`rowFactory(null)`, o `addRow(valoriIniziali)`, aggiunta in fondo), `deletable` "Elimina" sulle righe (con conferma,
|
|
128
|
+
`confirmDelete`) ed "Elimina selezionati" con la selezione multipla; `rowEditable` / `rowDeletable` scelgono le righe.
|
|
129
|
+
Con il FormArray disabilitato le righe si aprono in sola lettura ("Visualizza"). Dopo `markAllAsTouched()` le righe non
|
|
130
|
+
valide hanno il marcatore e l'icona di errore, gli errori del FormArray compaiono sotto la griglia
|
|
131
|
+
(`errorMessages`; per "almeno una riga" usare `Validators.required`, perché `Validators.minLength` ignora un array
|
|
132
|
+
vuoto). Eventi `(rowSave)` e `(rowDelete)`; metodi `editRow`, `addRow`, `deleteRow`, `deleteSelected`, `groupOf(riga)`.
|
|
133
|
+
Senza `rowId` la selezione segue il FormGroup della riga. Non si usa insieme a `[dataSource]`.
|
|
134
|
+
|
|
135
|
+
```html
|
|
136
|
+
<wm-sirio-data-grid [formArray]="righe" [rowFactory]="creaRiga" addable deletable (rowSave)="salvata($event)">
|
|
137
|
+
<wm-sirio-grid-column field="descrizione" header="Descrizione" />
|
|
138
|
+
<wm-sirio-grid-column field="importo" header="Importo" format="currency" />
|
|
139
|
+
<ng-template wmSirioGridEditor let-group let-isNew="isNew">
|
|
140
|
+
<div [formGroup]="group">
|
|
141
|
+
<wm-sirio-textbox formControlName="descrizione" label="Descrizione" />
|
|
142
|
+
<wm-sirio-number formControlName="importo" label="Importo" />
|
|
143
|
+
</div>
|
|
144
|
+
</ng-template>
|
|
145
|
+
</wm-sirio-data-grid>
|
|
146
|
+
```
|
|
147
|
+
- **Dati lato server** (`[dataSource]`): una funzione che riceve `{ page, pageSize, offset, sort, filters }` e restituisce
|
|
148
|
+
`{ rows, total }` (Observable, Promise o valore). Viene richiamata a ogni cambio di pagina o ordinamento e con
|
|
149
|
+
`reload()`; le risposte superate vengono ignorate (un Observable precedente viene annullato).
|
|
150
|
+
- **Totale facoltativo**: senza `total` il totale si ricava dalle pagine, come lo scroll infinito di ag-grid. Una
|
|
151
|
+
pagina piena significa che ce ne sono altre: "Successiva" resta attiva, la paginazione mostra "di 30+ elementi"
|
|
152
|
+
("oltre 30" per gli screen reader, testo `moreLabel`) e il conteggio dei risultati "oltre 30". Una pagina più corta
|
|
153
|
+
è l'ultima e fissa il totale. Cambiando ordinamento, filtri o righe per pagina si riparte da capo.
|
|
154
|
+
`wm-sirio-pagination` ha lo stesso comportamento con `hasMore`.
|
|
155
|
+
- **Errori**: oltre a `(loadError)`, la tabella mostra `loadErrorText` ("Non è stato possibile caricare i dati.") con
|
|
156
|
+
il pulsante "Riprova" (`retryLabel`), che richiama il data source; la paginazione resta per tornare indietro. Con
|
|
157
|
+
`<ng-template wmSirioGridError let-error let-retry="retry">` il contenuto è personalizzato.
|
|
158
|
+
- **Filtri per colonna** (`filter` sulla colonna): pulsante nell'intestazione che apre il popover del kit con i
|
|
159
|
+
controlli della libreria. Tipi: `text` (contiene, senza distinzione di maiuscole e accenti), `number` e `date`
|
|
160
|
+
(intervallo Da / A), `select` (con `filterOptions`, anche `filterMultiple`; **senza `filterOptions` la scelta è tra i
|
|
161
|
+
valori presenti nella colonna, con il numero di righe**, calcolati con gli altri filtri applicati), `boolean` (Sì / No). I filtri attivi
|
|
162
|
+
compaiono sopra la tabella come chip del kit, rimovibili uno a uno o tutti insieme; nel layout a card sono in un
|
|
163
|
+
pannello "Filtri". Stato two-way `[(filters)]` (per chiave di colonna, es. `{ comune: 'Roma', importo: { from: 1000 } }`),
|
|
164
|
+
filtro personalizzato con `filterPredicate`, ritardo dei filtri di testo con `filterDebounce` (300 ms).
|
|
165
|
+
Con `[dataSource]` i filtri attivi arrivano nella query (`query.filters`).
|
|
166
|
+
- **Operatori dei filtri**: con `filterOperators` sulla griglia (o sulla colonna: `true`, `false` o l'elenco degli
|
|
167
|
+
operatori ammessi) il popover ha una scelta "Condizione" sopra il valore e il filtro diventa
|
|
168
|
+
`{ operator, value, to? }` (`SirioGridFilterCondition`). Testo: contiene, non contiene, uguale a, diverso da, inizia
|
|
169
|
+
con, finisce con; numero: uguale a, diverso da, maggiore di, maggiore o uguale a, minore di, minore o uguale a,
|
|
170
|
+
compreso tra; data: uguale a, diverso da, prima del, dopo il, compreso tra; elenco: è uno di, non è uno di; per tutti
|
|
171
|
+
vuoto e non vuoto. Chip come "Importo: compreso tra 10.000 e 30.000"; etichette in `filterOperatorLabels`,
|
|
172
|
+
`filterConditionLabel`, `filterValueLabel`, `filterAndLabel`. Un valore semplice (es. uno stato salvato) viene letto
|
|
173
|
+
come condizione equivalente (testo → contiene, intervallo → compreso tra, elenco → è uno di).
|
|
174
|
+
- **Ordinamento**: `[(sort)]` è l'elenco dei criteri in ordine di priorità (`[{ field: 'comune', direction: 'asc' }]`).
|
|
175
|
+
Con `sortMode="multiple"` Maiusc+clic (o Maiusc+Invio) aggiunge una colonna ai criteri, mostrando la priorità
|
|
176
|
+
nell'intestazione; il clic semplice sostituisce l'ordinamento.
|
|
177
|
+
- **Colonne ridimensionabili** (`resizable`): maniglia sul bordo destro delle intestazioni per il mouse (trascinamento,
|
|
178
|
+
doppio clic per ripristinare); da tastiera Alt+frecce sull'intestazione, come ag-grid; `minWidth` / `maxWidth` e
|
|
179
|
+
`resizable="false"` sulla colonna; larghezze two-way `[(columnWidths)]` (px per chiave di colonna).
|
|
180
|
+
- **Colonne riordinabili** (`reorderable`): trascinamento delle intestazioni o Shift+frecce su un'intestazione, con
|
|
181
|
+
annuncio della nuova posizione; ordine two-way `[(columnOrder)]`. "Ripristina colonne" nella barra sopra la tabella.
|
|
182
|
+
- **Righe espandibili**: con `<ng-template wmSirioGridDetail let-row>` ogni riga ha un pulsante che apre un pannello di
|
|
183
|
+
dettaglio sotto di essa (`rowExpandable` per sceglierle); con `subRows` (proprietà o funzione) i dati sono un albero,
|
|
184
|
+
con rientro per livello. Stato two-way `[(expanded)]`, `expandAll()`, "Espandi tutto" / "Comprimi tutto".
|
|
185
|
+
- **Numero di riga** (`rowNumbers`): colonna "N." all'inizio, numero continuo tra le pagine nell'ordine e con i filtri
|
|
186
|
+
correnti (lato server dall'offset della query); le righe di gruppo non sono numerate, i figli degli alberi sì per
|
|
187
|
+
livello (1, 1.1, 1.2). È l'intestazione di riga (`role="rowheader"`); testi `rowNumberHeader` e `rowNumberLabel`.
|
|
188
|
+
- **Intestazioni raggruppate**: `group` sulla colonna con i nomi dei gruppi dal livello più alto, separati da `/`
|
|
189
|
+
(`group="Richiedente/Residenza"`); una riga d'intestazione per livello (`scope="colgroup"`), le colonne vicine con gli
|
|
190
|
+
stessi gruppi condividono la cella, un gruppo si divide se le sue colonne non sono vicine o stanno in blocchi fissi
|
|
191
|
+
diversi. Con `stickyHeader` le righe restano impilate.
|
|
192
|
+
- **Colonne flex**: `flex` sulla colonna (`flex="2"`, `flex` senza valore = 1) come in CSS / ag-grid: le colonne con
|
|
193
|
+
`flex` si dividono in proporzione la larghezza lasciata libera dalle altre (che tengono `width` o la larghezza del
|
|
194
|
+
contenuto), entro `minWidth` / `maxWidth`; si ricalcola quando cambia la larghezza della griglia. Una colonna flex
|
|
195
|
+
ridimensionata a mano tiene la sua larghezza fino al doppio clic sulla maniglia o a "Ripristina colonne".
|
|
196
|
+
- **Colonne fisse**: `fixed="left"` o `fixed="right"` sulla colonna la tiene ferma durante lo scroll orizzontale; più
|
|
197
|
+
colonne per lato, mostrate su quel lato della tabella (le colonne si spostano solo all'interno del proprio blocco).
|
|
198
|
+
Selezione, espansione e numero di riga restano fissi con le colonne di sinistra. `fixedFirstColumn` /
|
|
199
|
+
`fixedLastColumn` sono scorciatoie per la prima e l'ultima colonna. Attive nel contenitore responsive, non nel layout
|
|
200
|
+
a card; al bordo del blocco fisso compare l'indicatore di scroll del kit.
|
|
201
|
+
- **Classi e stili**: `rowClass` / `rowStyle` sulla griglia, `cellClass` / `cellStyle` sulla colonna (valori fissi o
|
|
202
|
+
funzioni: della riga e del suo indice per le righe, della riga e del valore per le celle), `headerClass` /
|
|
203
|
+
`headerStyle` sull'intestazione della colonna. Le classi sono come `ngClass` (testo, elenco o `{ classe: condizione }`),
|
|
204
|
+
gli stili come `ngStyle` (testo CSS o oggetto, anche `'width.px': 80`). Uno sfondo di `rowStyle` / `cellStyle` vale
|
|
205
|
+
anche sulle righe a strisce e sulle colonne fisse; la selezione copre lo sfondo della riga, non quello della cella.
|
|
206
|
+
Per gli sfondi è meglio usare gli stili: le classi del kit `sirio-bg-*` sulle righe non battono le strisce del kit.
|
|
207
|
+
|
|
208
|
+
```html
|
|
209
|
+
<wm-sirio-data-grid [data]="pratiche" [rowClass]="classeRiga" [rowStyle]="stileRiga">
|
|
210
|
+
<wm-sirio-grid-column field="importo" header="Importo" format="currency" headerClass="sirio-text-primary"
|
|
211
|
+
[cellClass]="importoNegativo" />
|
|
212
|
+
</wm-sirio-data-grid>
|
|
213
|
+
```
|
|
214
|
+
|
|
215
|
+
```ts
|
|
216
|
+
classeRiga = (riga: Pratica) => ({ 'sirio-text-disabled': riga.stato === 'Chiusa' });
|
|
217
|
+
stileRiga = (riga: Pratica) => (riga.scaduta ? { 'background-color': '#f7e4ea' } : null);
|
|
218
|
+
importoNegativo = (_riga: Pratica, valore: unknown) => ({ 'sirio-text-danger': Number(valore) < 0 });
|
|
219
|
+
```
|
|
220
|
+
- **Raggruppamento** (solo con `[data]`): colonne `groupable` e "Raggruppa per" sopra la tabella (`[(grouping)]`); le
|
|
221
|
+
righe di gruppo mostrano valore e numero di righe, le altre colonne il valore di `aggregate` (`sum`, `mean`, `min`,
|
|
222
|
+
`max`, `count`). Con gruppi o alberi la paginazione conta le righe di primo livello.
|
|
223
|
+
- **Paginazione**: `pageable`, `[(page)]`, `[(pageSize)]`, `pageSizeOptions`; aspetto di `wm-sirio-pagination` con
|
|
224
|
+
`paginationVariant` (`full`, `numbers` con i numeri di pagina e i puntini, oppure `compact`, una barra sottile con "Pagina 1 di 6" e i pulsanti prima / precedente / successiva / ultima), `paginationSiblings` e `paginationShowItems`.
|
|
225
|
+
- **Stato two-way**: `[(sort)]`, `[(page)]`, `[(pageSize)]`, `[(filters)]`, `[(grouping)]`, `[(expanded)]`,
|
|
226
|
+
`[(columnWidths)]`, `[(columnOrder)]`, `[(selected)]` (righe confrontate per `rowId`).
|
|
227
|
+
- **Salvataggio dello stato**: `getState()` restituisce lo stato scelto dall'utente come JSON (`SirioGridState`:
|
|
228
|
+
ordinamento, filtri, pagina e righe per pagina, ordine e larghezze delle colonne, raggruppamento, righe espanse,
|
|
229
|
+
`rowId` delle righe selezionate), `setState(stato)` lo ripristina (anche in parte; i filtri si applicano subito senza
|
|
230
|
+
tornare alla prima pagina, criteri di colonne non più presenti vengono ignorati), `resetState()` torna allo stato
|
|
231
|
+
iniziale; `(stateChange)` e il signal `state` seguono ogni modifica, per il salvataggio automatico.
|
|
232
|
+
- **Selezione**: `selection="single"` (radio) o `"multiple"` (checkbox del kit con "seleziona tutte"; `selectAll` sceglie
|
|
233
|
+
le righe prese: `page` quelle della pagina, default, `filtered` tutte quelle che passano i filtri su tutte le pagine,
|
|
234
|
+
come `selectAll: 'filtered'` di ag-grid, `all` tutte; con `[dataSource]` sempre la pagina caricata);
|
|
235
|
+
`selectOnRowClick` seleziona anche al clic sulla riga; con `[selectionColumn]="false"` niente colonna di checkbox:
|
|
236
|
+
si seleziona con il clic sulla riga (in `multiple` ogni clic aggiunge o toglie la riga) o con Spazio/Invio sulla riga
|
|
237
|
+
con il focus; `rowSelectable` (funzione della riga, come `isRowSelectable` di ag-grid) indica le righe selezionabili:
|
|
238
|
+
le altre hanno la casella disabilitata (nascosta con `hideUnselectable`), sono escluse da "seleziona tutte" e dalla
|
|
239
|
+
selezione con clic o tastiera; `(rowClick)` per il dettaglio. Con la selezione singola l'intestazione della colonna
|
|
240
|
+
di selezione è letta dagli screen reader come `selectionHeaderLabel` ("Selezione"). I campi dei filtri non si
|
|
241
|
+
registrano nel form che contiene la griglia.
|
|
242
|
+
- **Altezza**: senza impostazioni la griglia è alta quanto il contenuto (tutte le righe); `height` (come `style.height`)
|
|
243
|
+
la fissa, `minHeight` e `maxHeight` la limitano. Con un'altezza impostata le righe scorrono dentro la griglia con
|
|
244
|
+
l'intestazione sempre visibile, mentre "Raggruppa per", chip dei filtri e paginazione restano fuori dallo scroll e
|
|
245
|
+
contano nell'altezza. Con `stickyHeader` e senza altezza vale l'altezza del kit (450px per le righe).
|
|
246
|
+
- **Aspetto del kit**: `variant` (`default`, `dark`, `striped`), `size` (`xs`, `sm`, `md`, `lg`), contenitore
|
|
247
|
+
responsive con gli indicatori di scroll, `stickyHeader`, `fixedFirstColumn`, `fixedLastColumn`,
|
|
248
|
+
`cardOnMobile` (righe a card fino a 768px, con l'intestazione come etichetta di ogni cella).
|
|
249
|
+
- **Accessibilità**: `caption` (nascosta di default; dà anche il nome al paginatore, "Paginazione della tabella <caption>",
|
|
250
|
+
per distinguere più griglie nella stessa pagina), `aria-sort` e tastiera (Invio/Spazio) sulle intestazioni
|
|
251
|
+
ordinabili, `aria-selected`, `aria-expanded` sui pulsanti di espansione, `aria-level` per alberi e gruppi,
|
|
252
|
+
`aria-busy` durante il caricamento; numero di risultati, criteri di ordinamento e spostamenti di colonna annunciati.
|
|
253
|
+
- **Navigazione da tastiera** (`keyboardNavigation`, default `true`, come ag-grid e il pattern ARIA "grid"): la
|
|
254
|
+
griglia è una sola tappa del Tab (si entra sulla prima intestazione, poi sull'ultima cella visitata); le frecce si spostano tra intestazioni e celle, Home/Fine all'inizio e alla fine
|
|
255
|
+
della riga, Ctrl+Home/Ctrl+Fine alla prima e all'ultima cella; Tab esce dalla griglia. Una cella con pulsanti o
|
|
256
|
+
campi (es. le azioni, un template di cella) passa il focus ai suoi controlli, uno per tappa. La cella raggiunta viene
|
|
257
|
+
portata in vista fuori dalle colonne fisse e dall'intestazione fissa; Spazio/Invio su una cella seleziona la riga
|
|
258
|
+
quando non c'è la colonna di selezione. I campi della riga dei filtri restano tappe del Tab (usano le frecce); con
|
|
259
|
+
la riga dei filtri la griglia ha due tappe, intestazioni e righe: Tab va dall'intestazione ai filtri e dai filtri
|
|
260
|
+
alle righe, poi esce (Shift+Tab al contrario). Sull'intestazione, come
|
|
261
|
+
ag-grid: Invio/Spazio ordina (Shift+Invio ordinamento multiplo), Alt+frecce cambia la larghezza, Shift+frecce sposta la
|
|
262
|
+
colonna, Ctrl+Invio apre il filtro; Alt+frecce non arriva mai al browser (Alt+← è "Indietro" e farebbe lasciare la pagina). La tabella ha
|
|
263
|
+
`role="grid"` (`treegrid` con alberi e raggruppamenti, con `aria-level` sulle righe) e `aria-multiselectable` con la
|
|
264
|
+
selezione multipla. Con `[keyboardNavigation]="false"` è una tabella semplice: tappe del Tab solo le intestazioni
|
|
265
|
+
interattive e i controlli.
|
|
266
|
+
- **Pannelli dei filtri**: il calendario dei filtri data e l'elenco dei filtri a scelta si aprono sopra la pagina,
|
|
267
|
+
sotto il campo (sopra quando sotto non c'è spazio), senza essere tagliati dal contenitore scorrevole della griglia.
|
|
268
|
+
Vale per `wm-sirio-date` e `wm-sirio-select` dentro qualsiasi contenitore che ritaglia il contenuto.
|
|
269
|
+
|
|
18
270
|
## Browser supportati
|
|
19
271
|
|
|
20
272
|
Gli stessi di Angular 22: Chrome ed Edge 119+, Firefox 119+, Safari 17+ (macOS e iOS),
|
package/THIRD_PARTY_LICENSES.txt
CHANGED
|
@@ -63,3 +63,32 @@ FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
|
|
|
63
63
|
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
|
|
64
64
|
IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
|
|
65
65
|
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
|
66
|
+
|
|
67
|
+
--------------------------------------------------------------------------------
|
|
68
|
+
@tanstack/angular-table 9.3.1 (with @tanstack/table-core, @tanstack/angular-store,
|
|
69
|
+
@tanstack/store)
|
|
70
|
+
https://github.com/TanStack/table
|
|
71
|
+
License: MIT
|
|
72
|
+
--------------------------------------------------------------------------------
|
|
73
|
+
|
|
74
|
+
MIT License
|
|
75
|
+
|
|
76
|
+
Copyright (c) 2016 Tanner Linsley
|
|
77
|
+
|
|
78
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
79
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
80
|
+
in the Software without restriction, including without limitation the rights
|
|
81
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
82
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
83
|
+
furnished to do so, subject to the following conditions:
|
|
84
|
+
|
|
85
|
+
The above copyright notice and this permission notice shall be included in all
|
|
86
|
+
copies or substantial portions of the Software.
|
|
87
|
+
|
|
88
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
89
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
90
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
91
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
92
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
93
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
94
|
+
SOFTWARE.
|