@cityway/bo-ui 1.1.0-beta004 → 1.1.0-beta005
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/cityway-bo-ui-1.1.0-beta004.tgz +0 -0
- package/cityway-bo-ui-1.1.0-beta005.tgz +0 -0
- package/docs/components/page-header.md +45 -0
- package/docs/components/table.md +6 -0
- package/fesm2022/cityway-bo-ui.mjs +128 -10
- package/fesm2022/cityway-bo-ui.mjs.map +1 -1
- package/index.d.ts +83 -5
- package/package.json +2 -2
|
Binary file
|
|
Binary file
|
|
@@ -32,12 +32,16 @@ En-tête de page transverse du back-office. Couvre :
|
|
|
32
32
|
| `actions` | `PageHeaderActionEnum[]` | `[]` | Liste des actions à afficher. Voir enum §3. L'ordre d'affichage est imposé par le template (cf. §5). |
|
|
33
33
|
| `isLoading` | `PageHeaderActionState` | `{}` | Map action → `boolean` ; passe l'action en état chargement. |
|
|
34
34
|
| `isDisabled` | `PageHeaderActionState` | `{}` | Map action → `boolean` ; désactive l'action. |
|
|
35
|
+
| `columns` | `TableColumn[]` | `[]` | Colonnes du tableau associé. **Fourni → un menu déroulant « Colonnes » apparaît** (cases à cocher afficher/masquer). Voir §6 bis. |
|
|
36
|
+
| `storageKey` | `string` | — | Identifiant **stable** du tableau pour persister l'état en localStorage (ex. `'users/list'`). Sans clé : le menu fonctionne mais l'état n'est pas mémorisé. |
|
|
37
|
+
| `columnsLabel` | `string` | `_COMMON._TABLE.COLUMNS` | Clé i18n du libellé du bouton « Colonnes ». |
|
|
35
38
|
|
|
36
39
|
### Outputs
|
|
37
40
|
|
|
38
41
|
| Output | Payload | Description |
|
|
39
42
|
|--------|---------|-------------|
|
|
40
43
|
| `action` | `PageHeaderActionEnum` | Émis au clic sur une action de la barre. Le bouton retour n'émet pas (géré en interne). |
|
|
44
|
+
| `columnsChange` | `TableColumn[]` | Émis quand la visibilité des colonnes change (colonnes avec `hidden` à jour). À renvoyer dans le `signal`/state lié à la `cw-table`. |
|
|
41
45
|
|
|
42
46
|
### Contenu projeté
|
|
43
47
|
|
|
@@ -134,6 +138,47 @@ onAction(action: PageHeaderActionEnum): void {
|
|
|
134
138
|
|
|
135
139
|
---
|
|
136
140
|
|
|
141
|
+
## 4 bis. Menu « Colonnes » (visibilité + persistance)
|
|
142
|
+
|
|
143
|
+
Quand on passe `columns` au page-header, un bouton **Colonnes** apparaît : un dropdown de cases à cocher pour afficher/masquer chaque colonne du tableau associé. L'état (colonnes masquées) est **persisté en localStorage** par tableau.
|
|
144
|
+
|
|
145
|
+
```ts
|
|
146
|
+
import { PageHeaderComponent, TableComponent, TableColumn } from '@cityway/bo-ui';
|
|
147
|
+
|
|
148
|
+
@Component({
|
|
149
|
+
standalone: true,
|
|
150
|
+
imports: [PageHeaderComponent, TableComponent],
|
|
151
|
+
template: `
|
|
152
|
+
<cw-page-header
|
|
153
|
+
[title]="'DOMAIN.USERS.TITLE'"
|
|
154
|
+
[columns]="columns()"
|
|
155
|
+
storageKey="users/list"
|
|
156
|
+
(columnsChange)="columns.set($event)">
|
|
157
|
+
</cw-page-header>
|
|
158
|
+
|
|
159
|
+
<cw-table [columns]="columns()" [data]="rows()"></cw-table>
|
|
160
|
+
`,
|
|
161
|
+
})
|
|
162
|
+
export class UsersPage {
|
|
163
|
+
// Source de vérité unique, liée au header (contrôle) ET à la table (rendu).
|
|
164
|
+
columns = signal<TableColumn[]>([
|
|
165
|
+
{ key: 'name', label: 'DOMAIN.USERS.NAME' },
|
|
166
|
+
{ key: 'email', label: 'DOMAIN.USERS.EMAIL' },
|
|
167
|
+
{ key: 'createdAt', label: 'DOMAIN.USERS.CREATED', hidden: true }, // masquée par défaut
|
|
168
|
+
{ key: 'actions', label: '', type: 'actions' }, // jamais masquable
|
|
169
|
+
]);
|
|
170
|
+
}
|
|
171
|
+
```
|
|
172
|
+
|
|
173
|
+
Règles :
|
|
174
|
+
- **Activation** : le menu n'apparaît que si `columns` contient au moins une colonne masquable. Sans `columns`, pas de menu.
|
|
175
|
+
- **Colonnes exclues** : `type='actions'` (jamais masquable) et toute colonne `hideable: false`.
|
|
176
|
+
- **Garde-fou** : impossible de masquer la **dernière** colonne masquable visible (sa case est désactivée).
|
|
177
|
+
- **Persistance** : une seule clé localStorage `cw-table-columns` → `{ [storageKey]: string[] }`, **on ne stocke que les clés des colonnes masquées**. Au chargement, l'état mémorisé prime sur les `hidden` du config ; **sans `storageKey`**, le menu fonctionne mais rien n'est mémorisé.
|
|
178
|
+
- **Helpers** : `loadHiddenColumns(storageKey)` / `saveHiddenColumns(storageKey, keys)` exportés par `@cityway/bo-ui` (le page-header les utilise en interne).
|
|
179
|
+
|
|
180
|
+
---
|
|
181
|
+
|
|
137
182
|
## 5. Notes d'intégration
|
|
138
183
|
|
|
139
184
|
- **i18n** : `title` et `description` passent par `translate` → fournir des **clés**, pas du texte en dur. `description` est rendue en `[innerHTML]` (peut contenir du HTML/markup traduit).
|
package/docs/components/table.md
CHANGED
|
@@ -36,6 +36,9 @@ Dépend de `@cityway/basic-ui` (badge, button, icon, image, loader, modale de su
|
|
|
36
36
|
| `pagination` | `Pagination` | `undefined` | Config de pagination (intègre `cw-pagination`). |
|
|
37
37
|
| `bulkActions` | `BulkAction[]` | `[]` | Actions groupées (nécessite `checkbox`). |
|
|
38
38
|
| `rowActions` | `RowActionsConfig` | `undefined` | Actions par ligne (API déclarative). |
|
|
39
|
+
| `emptyStateNoData` | `TableEmptyStateConfig` | `undefined` | État vide quand `data` est vide **et** table non filtrée (`cw-empty-state`). |
|
|
40
|
+
| `emptyStateNoResult` | `TableEmptyStateConfig` | `undefined` | État vide quand un filtrage ne renvoie rien (`isFiltered=true`). |
|
|
41
|
+
| `isFiltered` | `boolean` | `false` | Des filtres sont actifs → pilote le choix noData vs noResult. |
|
|
39
42
|
|
|
40
43
|
### Outputs
|
|
41
44
|
|
|
@@ -75,6 +78,7 @@ interface TableColumn {
|
|
|
75
78
|
hidden?: boolean;
|
|
76
79
|
clickable?: boolean; // rend la cellule cliquable (-> cellClick)
|
|
77
80
|
translate?: boolean; // traduit la VALEUR (text/link). Défaut false. Voir ci-dessous.
|
|
81
|
+
hideable?: boolean; // proposée au masquage dans le menu « Colonnes ». Défaut true.
|
|
78
82
|
}
|
|
79
83
|
|
|
80
84
|
interface BadgeConfig {
|
|
@@ -190,6 +194,8 @@ rowActions: RowActionsConfig = {
|
|
|
190
194
|
## 5. Notes d'intégration
|
|
191
195
|
|
|
192
196
|
- **i18n** : tous les `label` (colonnes, actions) sont des **clés** traduites en interne.
|
|
197
|
+
- **Visibilité des colonnes** : le menu « Colonnes » (afficher/masquer + persistance localStorage) est porté par **`cw-page-header`** (lui passer `[columns]` + `storageKey`, relier `(columnsChange)`). La `cw-table` ne fait que rendre les colonnes non `hidden` ; côté colonne, `hideable: false` exclut du menu et `type='actions'` est exclu d'office. Voir la doc `cw-page-header` §4 bis.
|
|
198
|
+
- **État vide** : fournir `emptyStateNoData` et/ou `emptyStateNoResult` (+ `isFiltered`) pour afficher un `cw-empty-state` (illustration + titre + description + 2 boutons avec `click`). Sans config, la table garde le texte `NO_RESULT`. Voir la doc `cw-empty-state`.
|
|
193
199
|
- **Traduction des VALEURS de cellule** : les colonnes `text` / `link` affichent la donnée **brute par défaut**. Mettre `translate: true` **uniquement** quand la valeur est elle-même une clé i18n (enum / statut affiché en texte). Sinon une donnée qui coïncide avec une clé serait traduite à tort — typiquement un code applicatif `"NEWS"` rendu en `[object Object]` car la clé pointe sur une branche d'objet. (Les `badge` traduisent déjà leur `label` ; les en-têtes `label` sont toujours traduits.)
|
|
194
200
|
- **OnPush** : `data`/`columns` sont des signals → fournir des références à jour (set/update du signal).
|
|
195
201
|
- **`rowActions` vs `#actionsTemplate`** : ne fournir qu'un seul. `rowActions` est l'API recommandée ; le template custom reste pour les cas hors standard.
|
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
import * as i0 from '@angular/core';
|
|
2
|
-
import { input, ChangeDetectionStrategy, Component, output, effect, HostListener, Directive, computed, inject, contentChild, signal, isSignal, DestroyRef, viewChild, contentChildren } from '@angular/core';
|
|
2
|
+
import { input, ChangeDetectionStrategy, Component, output, effect, HostListener, Directive, computed, inject, contentChild, signal, isSignal, DestroyRef, afterNextRender, viewChild, contentChildren } from '@angular/core';
|
|
3
3
|
import * as i1$1 from '@ngx-translate/core';
|
|
4
4
|
import { TranslateModule } from '@ngx-translate/core';
|
|
5
5
|
import * as i1 from '@angular/common';
|
|
6
6
|
import { CommonModule, NgTemplateOutlet, Location } from '@angular/common';
|
|
7
7
|
import * as i2 from '@angular/cdk/drag-drop';
|
|
8
8
|
import { moveItemInArray, transferArrayItem, DragDropModule } from '@angular/cdk/drag-drop';
|
|
9
|
-
import { CardComponent, SpriteIconEnum, IconSizeEnum, BoButtonTypeEnum, ButtonPositionEnum, ButtonIconSizeEnum, AlertTypeEnum, CardTypeEnum, BadgeComponent, IconComponent, ButtonComponent, AlertComponent, FormFieldTypeEnum, FormFieldComponent, ModalsService, IconTypeEnum, IconUiTypeEnum, BadgeTypeEnum, ModalsType, LoaderComponent, ImageComponent, DropdownItemDirective } from '@cityway/basic-ui';
|
|
9
|
+
import { CardComponent, SpriteIconEnum, IconSizeEnum, BoButtonTypeEnum, ButtonPositionEnum, ButtonIconSizeEnum, AlertTypeEnum, CardTypeEnum, BadgeComponent, IconComponent, ButtonComponent, AlertComponent, FormFieldTypeEnum, FormFieldComponent, ModalsService, IconTypeEnum, IconUiTypeEnum, EmptyStateIllustrationEnum, BadgeTypeEnum, ModalsType, LoaderComponent, ImageComponent, EmptyStateComponent, DropdownItemDirective } from '@cityway/basic-ui';
|
|
10
10
|
import * as i1$2 from '@angular/forms';
|
|
11
11
|
import { FormControl, ReactiveFormsModule, FormGroup } from '@angular/forms';
|
|
12
12
|
import { takeUntilDestroyed } from '@angular/core/rxjs-interop';
|
|
@@ -510,6 +510,12 @@ class TableComponent {
|
|
|
510
510
|
this.pagination = input(undefined, ...(ngDevMode ? [{ debugName: "pagination" }] : []));
|
|
511
511
|
this.bulkActions = input([], ...(ngDevMode ? [{ debugName: "bulkActions" }] : []));
|
|
512
512
|
this.rowActions = input(undefined, ...(ngDevMode ? [{ debugName: "rowActions" }] : []));
|
|
513
|
+
/** Etat vide affiche quand il n'y a aucune donnee (table non filtree). */
|
|
514
|
+
this.emptyStateNoData = input(undefined, ...(ngDevMode ? [{ debugName: "emptyStateNoData" }] : []));
|
|
515
|
+
/** Etat vide affiche quand un filtrage ne renvoie aucun resultat (`isFiltered=true`). */
|
|
516
|
+
this.emptyStateNoResult = input(undefined, ...(ngDevMode ? [{ debugName: "emptyStateNoResult" }] : []));
|
|
517
|
+
/** Indique que des filtres sont actifs : pilote le choix noData vs noResult. */
|
|
518
|
+
this.isFiltered = input(false, ...(ngDevMode ? [{ debugName: "isFiltered" }] : []));
|
|
513
519
|
this.cellClick = output();
|
|
514
520
|
this.sortChange = output();
|
|
515
521
|
this.selectionChange = output();
|
|
@@ -524,6 +530,9 @@ class TableComponent {
|
|
|
524
530
|
this.iconSize = IconSizeEnum;
|
|
525
531
|
this.spriteIcon = SpriteIconEnum;
|
|
526
532
|
this.buttonType = BoButtonTypeEnum;
|
|
533
|
+
this.illustrationEnum = EmptyStateIllustrationEnum;
|
|
534
|
+
/** Config d'etat vide a afficher selon le contexte (filtre ou non). `undefined` -> fallback texte. */
|
|
535
|
+
this.currentEmptyState = computed(() => this.isFiltered() ? this.emptyStateNoResult() : this.emptyStateNoData(), ...(ngDevMode ? [{ debugName: "currentEmptyState" }] : []));
|
|
527
536
|
this.currentSortKey = signal(null, ...(ngDevMode ? [{ debugName: "currentSortKey" }] : []));
|
|
528
537
|
this.currentSortDirection = signal('asc', ...(ngDevMode ? [{ debugName: "currentSortDirection" }] : []));
|
|
529
538
|
this.selectedRows = signal(new Set(), ...(ngDevMode ? [{ debugName: "selectedRows" }] : []));
|
|
@@ -734,7 +743,7 @@ class TableComponent {
|
|
|
734
743
|
return typeof descriptor.link === 'function' ? descriptor.link(row) : descriptor.link;
|
|
735
744
|
}
|
|
736
745
|
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.20", ngImport: i0, type: TableComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
|
|
737
|
-
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.20", type: TableComponent, isStandalone: true, selector: "cw-table", inputs: { checkbox: { classPropertyName: "checkbox", publicName: "checkbox", isSignal: true, isRequired: false, transformFunction: null }, title: { classPropertyName: "title", publicName: "title", isSignal: true, isRequired: false, transformFunction: null }, columns: { classPropertyName: "columns", publicName: "columns", isSignal: true, isRequired: false, transformFunction: null }, data: { classPropertyName: "data", publicName: "data", isSignal: true, isRequired: false, transformFunction: null }, loading: { classPropertyName: "loading", publicName: "loading", isSignal: true, isRequired: false, transformFunction: null }, rowClassFn: { classPropertyName: "rowClassFn", publicName: "rowClassFn", isSignal: true, isRequired: false, transformFunction: null }, pagination: { classPropertyName: "pagination", publicName: "pagination", isSignal: true, isRequired: false, transformFunction: null }, bulkActions: { classPropertyName: "bulkActions", publicName: "bulkActions", isSignal: true, isRequired: false, transformFunction: null }, rowActions: { classPropertyName: "rowActions", publicName: "rowActions", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { cellClick: "cellClick", sortChange: "sortChange", selectionChange: "selectionChange", paginationChange: "paginationChange", bulkDelete: "bulkDelete", bulkAction: "bulkAction" }, host: { classAttribute: "cw-table" }, queries: [{ propertyName: "actionsTemplate", first: true, predicate: ["actionsTemplate"], descendants: true, isSignal: true }], ngImport: i0, template: "@if (checkbox() && selectedRows().size > 0) {\n <div class=\"table-selection-info mb-2 d-flex align-items-center gap-2 flex-wrap\">\n <span>\n {{ selectedRows().size }} {{ '_COMMON._TABLE._BULK_ACTION.SELECTED_ITEMS_CURRENT_PAGE' | translate }}\n </span>\n @for (action of bulkActions(); track $index) {\n <cw-button\n [type]=\"resolveVariant(action)\"\n [label]=\"action.label\"\n [withIcon]=\"action.icon\"\n [isDisabled]=\"resolveDisabled(action)\"\n (btnAction)=\"onBulkActionClick(action)\">\n </cw-button>\n }\n </div>\n}\n\n<div class=\"table-responsive\">\n <table class=\"table\">\n <caption class=\"visually-hidden\" [innerHTML]=\"'_COMMON._TABLE.CAPTION' | translate: { label: title() } \"></caption>\n <thead>\n <tr>\n @if(checkbox()) {\n <th scope=\"col\" width=\"10\">\n <div class=\"field-check\">\n <input class=\"field-check-input\" type=\"checkbox\" id=\"checkme\" [checked]=\"allSelected()\"\n [indeterminate]=\"someSelected()\" (change)=\"toggleAll()\">\n <label class=\"field-check-label\" for=\"checkme\">\n <span class=\"visually-hidden\">{{ '_COMMON._TABLE._THEAD.CHECK_LINE' | translate }}</span>\n </label>\n </div>\n </th>\n }\n\n @for (column of columns(); track column.key) {\n @if (!column.hidden) {\n <th scope=\"col\" [class.p-0]=\"column.sort\">\n @if (column.sort) {\n <button class=\"d-flex-h gap-2xs\" [class]=\"getSortClass(column.key)\" (click)=\"setSortProperty(column.key)\">\n {{ column.label | translate}}\n <cw-icon\n [icon]=\"getSortIcon(column.key)\"\n [label]=\"'_COMMON._TABLE._SORT.LABEL' | translate\"\n [type]=\"iconType.default\"\n [iconSize]=\"iconSize['xs']\"></cw-icon>\n </button>\n }\n @else {\n {{ column.label | translate }}\n }\n </th>\n }\n }\n </tr>\n </thead>\n <tbody>\n @if (loading()) {\n <tr>\n <td colspan=\"100\">\n <cw-loader></cw-loader>\n </td>\n </tr>\n }\n @else if (!data() || data().length === 0) {\n <tr>\n <td class=\"table-info no-result\" colspan=\"100\">\n {{ '_COMMON._TABLE.NO_RESULT' | translate }}\n </td>\n </tr>\n }\n @else {\n @for (row of data(); track row) {\n <tr [class.tr-selected]=\"isSelected(row)\" [class]=\"getRowClass(row)\">\n @if (checkbox()) {\n <td>\n <input class=\"field-check-input\" type=\"checkbox\" [checked]=\"isSelected(row)\" (change)=\"toggleRow(row)\" [id]=\"'check-' + row.id\"\n [attr.aria-label]=\"'S\u00E9lectionner la ligne ' + row.id\">\n <label class=\"visually-hidden\" [for]=\"'check-' + row.id\">S\u00E9lectionner la ligne {{row.id}}</label>\n </td>\n }\n @for (column of columns(); track column.key) {\n @if (!column.hidden) {\n <td [class.text-end]=\"column.align === 'right'\" [class.text-center]=\"column.align === 'center'\"\n [class.td-actions]=\"column.type === 'actions'\">\n @switch (column.type) {\n @case ('link') {\n <a href=\"javascript:void(0)\" (click)=\"onCellClick(row, column)\">\n {{ column.translate ? (row[column.key] | translate) : row[column.key] }}\n </a>\n }\n @case ('badge') {\n <cw-badge\n [type]=\"getBadge(column, row[column.key]).type\"\n [label]=\"getBadge(column, row[column.key]).label ?? row[column.key]\"\n [withIcon]=\"getBadge(column, row[column.key]).withIcon\"\n [iconPosition]=\"getBadge(column, row[column.key]).iconPosition\"></cw-badge>\n }\n @case ('icon') {\n @if (isClickable(column)) {\n <a href=\"javascript:void(0)\" (click)=\"onCellClick(row, column)\" [attr.aria-label]=\"row[column.key].label\">\n <cw-icon\n [icon]=\"row[column.key].icon\"\n [label]=\"row[column.key].label\"\n [type]=\"iconType.default\"\n [iconSize]=\"iconSize['md']\"\n [iconCssClass]=\"row[column.key].iconCssClass\"\n ></cw-icon>\n </a>\n } @else {\n <cw-icon\n [icon]=\"row[column.key].icon\"\n [label]=\"row[column.key].label\"\n [type]=\"iconType.default\"\n [iconSize]=\"iconSize['md']\"\n [iconCssClass]=\"row[column.key].iconCssClass\"\n ></cw-icon>\n }\n }\n @case ('image') {\n @if (isClickable(column)) {\n <a href=\"javascript:void(0)\" (click)=\"onCellClick(row, column)\" [attr.aria-label]=\"row[column.key].label\">\n <cw-image\n [source]=\"row[column.key].source\"\n [alt]=\"row[column.key].label\"\n [isAriaHidden]=\"true\"\n [cssClass]=\"row[column.key].iconCssClass\"\n width=\"32\"\n height=\"32\"\n ></cw-image>\n </a>\n } @else {\n <cw-image\n [source]=\"row[column.key].source\"\n [alt]=\"row[column.key].label\"\n [isAriaHidden]=\"true\"\n [cssClass]=\"row[column.key].iconCssClass\"\n width=\"32\"\n height=\"32\"\n ></cw-image>\n }\n }\n @case ('check') {\n @if (isTruthy(row[column.key])) {\n <cw-icon\n [icon]=\"spriteIcon.checkCircle\"\n [label]=\"'_COMMON._PRO_SENTENCE.YES' | translate\"\n [type]=\"iconType.default\"\n iconCssClass=\"text-success\"\n [iconSize]=\"iconSize['md']\"></cw-icon>\n } @else {\n <cw-icon\n [icon]=\"spriteIcon.closeCircle\"\n [label]=\"'_COMMON._PRO_SENTENCE.NO' | translate\"\n [type]=\"iconType.default\"\n iconCssClass=\"text-danger\"\n [iconSize]=\"iconSize['md']\"></cw-icon>\n }\n }\n @case ('actions') {\n @if (usingRowActions) {\n @let actions = getResolvedActions(row);\n @if (actions.length > 0) {\n @if (!useDropdownActions()) {\n @for (action of actions; track $index) {\n <cw-button\n [type]=\"buttonType.ghost\"\n [label]=\"action.label\"\n [withIcon]=\"action.icon\"\n [link]=\"action.link\"\n [isDisabled]=\"action.disabled\"\n [cssClass]=\"actionCssClass(action)\"\n (btnAction)=\"onRowActionClick(action, row)\">\n </cw-button>\n }\n } @else {\n <cw-button\n [label]=\"'_COMMON._TABLE.ACTIONS_MENU'\"\n [withIcon]=\"spriteIcon.menuVertical\"\n [withOnlyIcon]=\"true\"\n [type]=\"buttonType.ghost\"\n [isDropdown]=\"true\"\n [hideCaret]=\"true\">\n <ul class=\"p-0 m-0\">\n @for (action of actions; track $index) {\n <li>\n @if (action.link) {\n <cw-button\n [type]=\"buttonType.ghost\"\n [label]=\"action.label\"\n [withIcon]=\"action.icon\"\n [link]=\"action.link\"\n [isDisabled]=\"action.disabled\"\n [cssClass]=\"'dropdown-item ' + actionCssClass(action)\">\n </cw-button>\n } @else {\n <cw-button\n [type]=\"buttonType.ghost\"\n [label]=\"action.label\"\n [withIcon]=\"action.icon\"\n [isDisabled]=\"action.disabled\"\n [cssClass]=\"'dropdown-item ' + actionCssClass(action)\"\n (btnAction)=\"onRowActionClick(action, row)\">\n </cw-button>\n }\n </li>\n }\n </ul>\n </cw-button>\n }\n }\n } @else {\n <ng-container\n *ngTemplateOutlet=\"actionsTemplate(); context: { $implicit: row }\">\n </ng-container>\n }\n }\n @default {\n {{ column.translate ? (row[column.key] | translate) : row[column.key] }}\n }\n }\n </td>\n }\n }\n </tr>\n }\n }\n </tbody>\n </table>\n</div>\n\n@if (pagination()) {\n <cw-pagination\n [pagination]=\"pagination()!\"\n (paginationChange)=\"paginationChange.emit($event)\">\n </cw-pagination>\n}\n", dependencies: [{ kind: "ngmodule", type: TranslateModule }, { kind: "component", type: LoaderComponent, selector: "cw-loader", inputs: ["size", "displayText"] }, { kind: "component", type: BadgeComponent, selector: "cw-badge", inputs: ["type", "label", "withIcon", "iconPosition", "cssClass", "skeletonMode", "dataTest"] }, { kind: "component", type: ButtonComponent, selector: "cw-button", inputs: ["type", "label", "id", "link", "isDropdown", "hideCaret", "withIcon", "withOnlyIcon", "iconSize", "iconPosition", "dropdownPosition", "isMinWidth", "isDisabled", "isLoading", "cssClass", "dataTest", "skeletonMode", "withTooltip", "tooltipText", "tooltipTitle", "tooltipTrigger", "tooltipPosition", "tooltipType"], outputs: ["btnAction", "dropDownClicked"] }, { kind: "directive", type: NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "component", type: PaginationComponent, selector: "cw-pagination", inputs: ["pagination"], outputs: ["paginationChange"] }, { kind: "component", type: IconComponent, selector: "cw-icon", inputs: ["icon", "label", "type", "iconSize", "iconCssClass", "iconUiType", "iconColorCustom", "spritePath"] }, { kind: "component", type: ImageComponent, selector: "cw-image", inputs: ["source", "alt", "isAriaHidden", "cssClass", "width", "height"] }, { kind: "pipe", type: i1$1.TranslatePipe, name: "translate" }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
|
|
746
|
+
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.20", type: TableComponent, isStandalone: true, selector: "cw-table", inputs: { checkbox: { classPropertyName: "checkbox", publicName: "checkbox", isSignal: true, isRequired: false, transformFunction: null }, title: { classPropertyName: "title", publicName: "title", isSignal: true, isRequired: false, transformFunction: null }, columns: { classPropertyName: "columns", publicName: "columns", isSignal: true, isRequired: false, transformFunction: null }, data: { classPropertyName: "data", publicName: "data", isSignal: true, isRequired: false, transformFunction: null }, loading: { classPropertyName: "loading", publicName: "loading", isSignal: true, isRequired: false, transformFunction: null }, rowClassFn: { classPropertyName: "rowClassFn", publicName: "rowClassFn", isSignal: true, isRequired: false, transformFunction: null }, pagination: { classPropertyName: "pagination", publicName: "pagination", isSignal: true, isRequired: false, transformFunction: null }, bulkActions: { classPropertyName: "bulkActions", publicName: "bulkActions", isSignal: true, isRequired: false, transformFunction: null }, rowActions: { classPropertyName: "rowActions", publicName: "rowActions", isSignal: true, isRequired: false, transformFunction: null }, emptyStateNoData: { classPropertyName: "emptyStateNoData", publicName: "emptyStateNoData", isSignal: true, isRequired: false, transformFunction: null }, emptyStateNoResult: { classPropertyName: "emptyStateNoResult", publicName: "emptyStateNoResult", isSignal: true, isRequired: false, transformFunction: null }, isFiltered: { classPropertyName: "isFiltered", publicName: "isFiltered", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { cellClick: "cellClick", sortChange: "sortChange", selectionChange: "selectionChange", paginationChange: "paginationChange", bulkDelete: "bulkDelete", bulkAction: "bulkAction" }, host: { classAttribute: "cw-table" }, queries: [{ propertyName: "actionsTemplate", first: true, predicate: ["actionsTemplate"], descendants: true, isSignal: true }], ngImport: i0, template: "@if (checkbox() && selectedRows().size > 0) {\n <div class=\"table-selection-info mb-2 d-flex align-items-center gap-2 flex-wrap\">\n <span>\n {{ selectedRows().size }} {{ '_COMMON._TABLE._BULK_ACTION.SELECTED_ITEMS_CURRENT_PAGE' | translate }}\n </span>\n @for (action of bulkActions(); track $index) {\n <cw-button\n [type]=\"resolveVariant(action)\"\n [label]=\"action.label\"\n [withIcon]=\"action.icon\"\n [isDisabled]=\"resolveDisabled(action)\"\n (btnAction)=\"onBulkActionClick(action)\">\n </cw-button>\n }\n </div>\n}\n\n<div class=\"table-responsive\">\n <table class=\"table\">\n <caption class=\"visually-hidden\" [innerHTML]=\"'_COMMON._TABLE.CAPTION' | translate: { label: title() } \"></caption>\n <thead>\n <tr>\n @if(checkbox()) {\n <th scope=\"col\" width=\"10\">\n <div class=\"field-check\">\n <input class=\"field-check-input\" type=\"checkbox\" id=\"checkme\" [checked]=\"allSelected()\"\n [indeterminate]=\"someSelected()\" (change)=\"toggleAll()\">\n <label class=\"field-check-label\" for=\"checkme\">\n <span class=\"visually-hidden\">{{ '_COMMON._TABLE._THEAD.CHECK_LINE' | translate }}</span>\n </label>\n </div>\n </th>\n }\n\n @for (column of columns(); track column.key) {\n @if (!column.hidden) {\n <th scope=\"col\" [class.p-0]=\"column.sort\">\n @if (column.sort) {\n <button class=\"d-flex-h gap-2xs\" [class]=\"getSortClass(column.key)\" (click)=\"setSortProperty(column.key)\">\n {{ column.label | translate}}\n <cw-icon\n [icon]=\"getSortIcon(column.key)\"\n [label]=\"'_COMMON._TABLE._SORT.LABEL' | translate\"\n [type]=\"iconType.default\"\n [iconSize]=\"iconSize['xs']\"></cw-icon>\n </button>\n }\n @else {\n {{ column.label | translate }}\n }\n </th>\n }\n }\n </tr>\n </thead>\n <tbody>\n @if (loading()) {\n <tr>\n <td colspan=\"100\">\n <cw-loader></cw-loader>\n </td>\n </tr>\n }\n @else if (!data() || data().length === 0) {\n <tr>\n <td class=\"table-info no-result\" colspan=\"100\">\n @if (currentEmptyState(); as empty) {\n <cw-empty-state\n [illustration]=\"empty.illustration ?? (isFiltered() ? illustrationEnum.noResult : illustrationEnum.noData)\"\n [imageSource]=\"empty.imageSource\"\n [title]=\"empty.title\"\n [description]=\"empty.description\"\n [primaryButton]=\"empty.primaryButton\"\n [secondaryButton]=\"empty.secondaryButton\"\n (primaryClick)=\"empty.primaryButton?.click?.()\"\n (secondaryClick)=\"empty.secondaryButton?.click?.()\">\n </cw-empty-state>\n } @else {\n {{ '_COMMON._TABLE.NO_RESULT' | translate }}\n }\n </td>\n </tr>\n }\n @else {\n @for (row of data(); track row) {\n <tr [class.tr-selected]=\"isSelected(row)\" [class]=\"getRowClass(row)\">\n @if (checkbox()) {\n <td>\n <input class=\"field-check-input\" type=\"checkbox\" [checked]=\"isSelected(row)\" (change)=\"toggleRow(row)\" [id]=\"'check-' + row.id\"\n [attr.aria-label]=\"'S\u00E9lectionner la ligne ' + row.id\">\n <label class=\"visually-hidden\" [for]=\"'check-' + row.id\">S\u00E9lectionner la ligne {{row.id}}</label>\n </td>\n }\n @for (column of columns(); track column.key) {\n @if (!column.hidden) {\n <td [class.text-end]=\"column.align === 'right'\" [class.text-center]=\"column.align === 'center'\"\n [class.td-actions]=\"column.type === 'actions'\">\n @switch (column.type) {\n @case ('link') {\n <a href=\"javascript:void(0)\" (click)=\"onCellClick(row, column)\">\n {{ column.translate ? (row[column.key] | translate) : row[column.key] }}\n </a>\n }\n @case ('badge') {\n <cw-badge\n [type]=\"getBadge(column, row[column.key]).type\"\n [label]=\"getBadge(column, row[column.key]).label ?? row[column.key]\"\n [withIcon]=\"getBadge(column, row[column.key]).withIcon\"\n [iconPosition]=\"getBadge(column, row[column.key]).iconPosition\"></cw-badge>\n }\n @case ('icon') {\n @if (isClickable(column)) {\n <a href=\"javascript:void(0)\" (click)=\"onCellClick(row, column)\" [attr.aria-label]=\"row[column.key].label\">\n <cw-icon\n [icon]=\"row[column.key].icon\"\n [label]=\"row[column.key].label\"\n [type]=\"iconType.default\"\n [iconSize]=\"iconSize['md']\"\n [iconCssClass]=\"row[column.key].iconCssClass\"\n ></cw-icon>\n </a>\n } @else {\n <cw-icon\n [icon]=\"row[column.key].icon\"\n [label]=\"row[column.key].label\"\n [type]=\"iconType.default\"\n [iconSize]=\"iconSize['md']\"\n [iconCssClass]=\"row[column.key].iconCssClass\"\n ></cw-icon>\n }\n }\n @case ('image') {\n @if (isClickable(column)) {\n <a href=\"javascript:void(0)\" (click)=\"onCellClick(row, column)\" [attr.aria-label]=\"row[column.key].label\">\n <cw-image\n [source]=\"row[column.key].source\"\n [alt]=\"row[column.key].label\"\n [isAriaHidden]=\"true\"\n [cssClass]=\"row[column.key].iconCssClass\"\n width=\"32\"\n height=\"32\"\n ></cw-image>\n </a>\n } @else {\n <cw-image\n [source]=\"row[column.key].source\"\n [alt]=\"row[column.key].label\"\n [isAriaHidden]=\"true\"\n [cssClass]=\"row[column.key].iconCssClass\"\n width=\"32\"\n height=\"32\"\n ></cw-image>\n }\n }\n @case ('check') {\n @if (isTruthy(row[column.key])) {\n <cw-icon\n [icon]=\"spriteIcon.checkCircle\"\n [label]=\"'_COMMON._PRO_SENTENCE.YES' | translate\"\n [type]=\"iconType.default\"\n iconCssClass=\"text-success\"\n [iconSize]=\"iconSize['md']\"></cw-icon>\n } @else {\n <cw-icon\n [icon]=\"spriteIcon.closeCircle\"\n [label]=\"'_COMMON._PRO_SENTENCE.NO' | translate\"\n [type]=\"iconType.default\"\n iconCssClass=\"text-danger\"\n [iconSize]=\"iconSize['md']\"></cw-icon>\n }\n }\n @case ('actions') {\n @if (usingRowActions) {\n @let actions = getResolvedActions(row);\n @if (actions.length > 0) {\n @if (!useDropdownActions()) {\n @for (action of actions; track $index) {\n <cw-button\n [type]=\"buttonType.ghost\"\n [label]=\"action.label\"\n [withIcon]=\"action.icon\"\n [link]=\"action.link\"\n [isDisabled]=\"action.disabled\"\n [cssClass]=\"actionCssClass(action)\"\n (btnAction)=\"onRowActionClick(action, row)\">\n </cw-button>\n }\n } @else {\n <cw-button\n [label]=\"'_COMMON._TABLE.ACTIONS_MENU'\"\n [withIcon]=\"spriteIcon.menuVertical\"\n [withOnlyIcon]=\"true\"\n [type]=\"buttonType.ghost\"\n [isDropdown]=\"true\"\n [hideCaret]=\"true\">\n <ul class=\"p-0 m-0\">\n @for (action of actions; track $index) {\n <li>\n @if (action.link) {\n <cw-button\n [type]=\"buttonType.ghost\"\n [label]=\"action.label\"\n [withIcon]=\"action.icon\"\n [link]=\"action.link\"\n [isDisabled]=\"action.disabled\"\n [cssClass]=\"'dropdown-item ' + actionCssClass(action)\">\n </cw-button>\n } @else {\n <cw-button\n [type]=\"buttonType.ghost\"\n [label]=\"action.label\"\n [withIcon]=\"action.icon\"\n [isDisabled]=\"action.disabled\"\n [cssClass]=\"'dropdown-item ' + actionCssClass(action)\"\n (btnAction)=\"onRowActionClick(action, row)\">\n </cw-button>\n }\n </li>\n }\n </ul>\n </cw-button>\n }\n }\n } @else {\n <ng-container\n *ngTemplateOutlet=\"actionsTemplate(); context: { $implicit: row }\">\n </ng-container>\n }\n }\n @default {\n {{ column.translate ? (row[column.key] | translate) : row[column.key] }}\n }\n }\n </td>\n }\n }\n </tr>\n }\n }\n </tbody>\n </table>\n</div>\n\n@if (pagination()) {\n <cw-pagination\n [pagination]=\"pagination()!\"\n (paginationChange)=\"paginationChange.emit($event)\">\n </cw-pagination>\n}\n", dependencies: [{ kind: "ngmodule", type: TranslateModule }, { kind: "component", type: LoaderComponent, selector: "cw-loader", inputs: ["size", "displayText"] }, { kind: "component", type: BadgeComponent, selector: "cw-badge", inputs: ["type", "label", "withIcon", "iconPosition", "cssClass", "skeletonMode", "dataTest"] }, { kind: "component", type: ButtonComponent, selector: "cw-button", inputs: ["type", "label", "id", "link", "isDropdown", "hideCaret", "withIcon", "withOnlyIcon", "iconSize", "iconPosition", "dropdownPosition", "isMinWidth", "isDisabled", "isLoading", "cssClass", "dataTest", "skeletonMode", "withTooltip", "tooltipText", "tooltipTitle", "tooltipTrigger", "tooltipPosition", "tooltipType"], outputs: ["btnAction", "dropDownClicked"] }, { kind: "directive", type: NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "component", type: PaginationComponent, selector: "cw-pagination", inputs: ["pagination"], outputs: ["paginationChange"] }, { kind: "component", type: IconComponent, selector: "cw-icon", inputs: ["icon", "label", "type", "iconSize", "iconCssClass", "iconUiType", "iconColorCustom", "spritePath"] }, { kind: "component", type: ImageComponent, selector: "cw-image", inputs: ["source", "alt", "isAriaHidden", "cssClass", "width", "height"] }, { kind: "component", type: EmptyStateComponent, selector: "cw-empty-state", inputs: ["illustration", "illustrationBasePath", "imageSource", "imageAlt", "title", "description", "primaryButton", "secondaryButton", "dataTest"], outputs: ["primaryClick", "secondaryClick"] }, { kind: "pipe", type: i1$1.TranslatePipe, name: "translate" }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
|
|
738
747
|
}
|
|
739
748
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.20", ngImport: i0, type: TableComponent, decorators: [{
|
|
740
749
|
type: Component,
|
|
@@ -747,9 +756,10 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.20", ngImpo
|
|
|
747
756
|
NgTemplateOutlet,
|
|
748
757
|
PaginationComponent,
|
|
749
758
|
IconComponent,
|
|
750
|
-
ImageComponent
|
|
751
|
-
], template: "@if (checkbox() && selectedRows().size > 0) {\n <div class=\"table-selection-info mb-2 d-flex align-items-center gap-2 flex-wrap\">\n <span>\n {{ selectedRows().size }} {{ '_COMMON._TABLE._BULK_ACTION.SELECTED_ITEMS_CURRENT_PAGE' | translate }}\n </span>\n @for (action of bulkActions(); track $index) {\n <cw-button\n [type]=\"resolveVariant(action)\"\n [label]=\"action.label\"\n [withIcon]=\"action.icon\"\n [isDisabled]=\"resolveDisabled(action)\"\n (btnAction)=\"onBulkActionClick(action)\">\n </cw-button>\n }\n </div>\n}\n\n<div class=\"table-responsive\">\n <table class=\"table\">\n <caption class=\"visually-hidden\" [innerHTML]=\"'_COMMON._TABLE.CAPTION' | translate: { label: title() } \"></caption>\n <thead>\n <tr>\n @if(checkbox()) {\n <th scope=\"col\" width=\"10\">\n <div class=\"field-check\">\n <input class=\"field-check-input\" type=\"checkbox\" id=\"checkme\" [checked]=\"allSelected()\"\n [indeterminate]=\"someSelected()\" (change)=\"toggleAll()\">\n <label class=\"field-check-label\" for=\"checkme\">\n <span class=\"visually-hidden\">{{ '_COMMON._TABLE._THEAD.CHECK_LINE' | translate }}</span>\n </label>\n </div>\n </th>\n }\n\n @for (column of columns(); track column.key) {\n @if (!column.hidden) {\n <th scope=\"col\" [class.p-0]=\"column.sort\">\n @if (column.sort) {\n <button class=\"d-flex-h gap-2xs\" [class]=\"getSortClass(column.key)\" (click)=\"setSortProperty(column.key)\">\n {{ column.label | translate}}\n <cw-icon\n [icon]=\"getSortIcon(column.key)\"\n [label]=\"'_COMMON._TABLE._SORT.LABEL' | translate\"\n [type]=\"iconType.default\"\n [iconSize]=\"iconSize['xs']\"></cw-icon>\n </button>\n }\n @else {\n {{ column.label | translate }}\n }\n </th>\n }\n }\n </tr>\n </thead>\n <tbody>\n @if (loading()) {\n <tr>\n <td colspan=\"100\">\n <cw-loader></cw-loader>\n </td>\n </tr>\n }\n @else if (!data() || data().length === 0) {\n <tr>\n <td class=\"table-info no-result\" colspan=\"100\">\n {{ '_COMMON._TABLE.NO_RESULT' | translate }}\n </td>\n </tr>\n }\n @else {\n @for (row of data(); track row) {\n <tr [class.tr-selected]=\"isSelected(row)\" [class]=\"getRowClass(row)\">\n @if (checkbox()) {\n <td>\n <input class=\"field-check-input\" type=\"checkbox\" [checked]=\"isSelected(row)\" (change)=\"toggleRow(row)\" [id]=\"'check-' + row.id\"\n [attr.aria-label]=\"'S\u00E9lectionner la ligne ' + row.id\">\n <label class=\"visually-hidden\" [for]=\"'check-' + row.id\">S\u00E9lectionner la ligne {{row.id}}</label>\n </td>\n }\n @for (column of columns(); track column.key) {\n @if (!column.hidden) {\n <td [class.text-end]=\"column.align === 'right'\" [class.text-center]=\"column.align === 'center'\"\n [class.td-actions]=\"column.type === 'actions'\">\n @switch (column.type) {\n @case ('link') {\n <a href=\"javascript:void(0)\" (click)=\"onCellClick(row, column)\">\n {{ column.translate ? (row[column.key] | translate) : row[column.key] }}\n </a>\n }\n @case ('badge') {\n <cw-badge\n [type]=\"getBadge(column, row[column.key]).type\"\n [label]=\"getBadge(column, row[column.key]).label ?? row[column.key]\"\n [withIcon]=\"getBadge(column, row[column.key]).withIcon\"\n [iconPosition]=\"getBadge(column, row[column.key]).iconPosition\"></cw-badge>\n }\n @case ('icon') {\n @if (isClickable(column)) {\n <a href=\"javascript:void(0)\" (click)=\"onCellClick(row, column)\" [attr.aria-label]=\"row[column.key].label\">\n <cw-icon\n [icon]=\"row[column.key].icon\"\n [label]=\"row[column.key].label\"\n [type]=\"iconType.default\"\n [iconSize]=\"iconSize['md']\"\n [iconCssClass]=\"row[column.key].iconCssClass\"\n ></cw-icon>\n </a>\n } @else {\n <cw-icon\n [icon]=\"row[column.key].icon\"\n [label]=\"row[column.key].label\"\n [type]=\"iconType.default\"\n [iconSize]=\"iconSize['md']\"\n [iconCssClass]=\"row[column.key].iconCssClass\"\n ></cw-icon>\n }\n }\n @case ('image') {\n @if (isClickable(column)) {\n <a href=\"javascript:void(0)\" (click)=\"onCellClick(row, column)\" [attr.aria-label]=\"row[column.key].label\">\n <cw-image\n [source]=\"row[column.key].source\"\n [alt]=\"row[column.key].label\"\n [isAriaHidden]=\"true\"\n [cssClass]=\"row[column.key].iconCssClass\"\n width=\"32\"\n height=\"32\"\n ></cw-image>\n </a>\n } @else {\n <cw-image\n [source]=\"row[column.key].source\"\n [alt]=\"row[column.key].label\"\n [isAriaHidden]=\"true\"\n [cssClass]=\"row[column.key].iconCssClass\"\n width=\"32\"\n height=\"32\"\n ></cw-image>\n }\n }\n @case ('check') {\n @if (isTruthy(row[column.key])) {\n <cw-icon\n [icon]=\"spriteIcon.checkCircle\"\n [label]=\"'_COMMON._PRO_SENTENCE.YES' | translate\"\n [type]=\"iconType.default\"\n iconCssClass=\"text-success\"\n [iconSize]=\"iconSize['md']\"></cw-icon>\n } @else {\n <cw-icon\n [icon]=\"spriteIcon.closeCircle\"\n [label]=\"'_COMMON._PRO_SENTENCE.NO' | translate\"\n [type]=\"iconType.default\"\n iconCssClass=\"text-danger\"\n [iconSize]=\"iconSize['md']\"></cw-icon>\n }\n }\n @case ('actions') {\n @if (usingRowActions) {\n @let actions = getResolvedActions(row);\n @if (actions.length > 0) {\n @if (!useDropdownActions()) {\n @for (action of actions; track $index) {\n <cw-button\n [type]=\"buttonType.ghost\"\n [label]=\"action.label\"\n [withIcon]=\"action.icon\"\n [link]=\"action.link\"\n [isDisabled]=\"action.disabled\"\n [cssClass]=\"actionCssClass(action)\"\n (btnAction)=\"onRowActionClick(action, row)\">\n </cw-button>\n }\n } @else {\n <cw-button\n [label]=\"'_COMMON._TABLE.ACTIONS_MENU'\"\n [withIcon]=\"spriteIcon.menuVertical\"\n [withOnlyIcon]=\"true\"\n [type]=\"buttonType.ghost\"\n [isDropdown]=\"true\"\n [hideCaret]=\"true\">\n <ul class=\"p-0 m-0\">\n @for (action of actions; track $index) {\n <li>\n @if (action.link) {\n <cw-button\n [type]=\"buttonType.ghost\"\n [label]=\"action.label\"\n [withIcon]=\"action.icon\"\n [link]=\"action.link\"\n [isDisabled]=\"action.disabled\"\n [cssClass]=\"'dropdown-item ' + actionCssClass(action)\">\n </cw-button>\n } @else {\n <cw-button\n [type]=\"buttonType.ghost\"\n [label]=\"action.label\"\n [withIcon]=\"action.icon\"\n [isDisabled]=\"action.disabled\"\n [cssClass]=\"'dropdown-item ' + actionCssClass(action)\"\n (btnAction)=\"onRowActionClick(action, row)\">\n </cw-button>\n }\n </li>\n }\n </ul>\n </cw-button>\n }\n }\n } @else {\n <ng-container\n *ngTemplateOutlet=\"actionsTemplate(); context: { $implicit: row }\">\n </ng-container>\n }\n }\n @default {\n {{ column.translate ? (row[column.key] | translate) : row[column.key] }}\n }\n }\n </td>\n }\n }\n </tr>\n }\n }\n </tbody>\n </table>\n</div>\n\n@if (pagination()) {\n <cw-pagination\n [pagination]=\"pagination()!\"\n (paginationChange)=\"paginationChange.emit($event)\">\n </cw-pagination>\n}\n" }]
|
|
752
|
-
}], ctorParameters: () => [], propDecorators: { checkbox: [{ type: i0.Input, args: [{ isSignal: true, alias: "checkbox", required: false }] }], title: [{ type: i0.Input, args: [{ isSignal: true, alias: "title", required: false }] }], columns: [{ type: i0.Input, args: [{ isSignal: true, alias: "columns", required: false }] }], data: [{ type: i0.Input, args: [{ isSignal: true, alias: "data", required: false }] }], loading: [{ type: i0.Input, args: [{ isSignal: true, alias: "loading", required: false }] }], rowClassFn: [{ type: i0.Input, args: [{ isSignal: true, alias: "rowClassFn", required: false }] }], pagination: [{ type: i0.Input, args: [{ isSignal: true, alias: "pagination", required: false }] }], bulkActions: [{ type: i0.Input, args: [{ isSignal: true, alias: "bulkActions", required: false }] }], rowActions: [{ type: i0.Input, args: [{ isSignal: true, alias: "rowActions", required: false }] }], cellClick: [{ type: i0.Output, args: ["cellClick"] }], sortChange: [{ type: i0.Output, args: ["sortChange"] }], selectionChange: [{ type: i0.Output, args: ["selectionChange"] }], paginationChange: [{ type: i0.Output, args: ["paginationChange"] }], bulkDelete: [{ type: i0.Output, args: ["bulkDelete"] }], bulkAction: [{ type: i0.Output, args: ["bulkAction"] }], actionsTemplate: [{ type: i0.ContentChild, args: ['actionsTemplate', { isSignal: true }] }] } });
|
|
759
|
+
ImageComponent,
|
|
760
|
+
EmptyStateComponent
|
|
761
|
+
], template: "@if (checkbox() && selectedRows().size > 0) {\n <div class=\"table-selection-info mb-2 d-flex align-items-center gap-2 flex-wrap\">\n <span>\n {{ selectedRows().size }} {{ '_COMMON._TABLE._BULK_ACTION.SELECTED_ITEMS_CURRENT_PAGE' | translate }}\n </span>\n @for (action of bulkActions(); track $index) {\n <cw-button\n [type]=\"resolveVariant(action)\"\n [label]=\"action.label\"\n [withIcon]=\"action.icon\"\n [isDisabled]=\"resolveDisabled(action)\"\n (btnAction)=\"onBulkActionClick(action)\">\n </cw-button>\n }\n </div>\n}\n\n<div class=\"table-responsive\">\n <table class=\"table\">\n <caption class=\"visually-hidden\" [innerHTML]=\"'_COMMON._TABLE.CAPTION' | translate: { label: title() } \"></caption>\n <thead>\n <tr>\n @if(checkbox()) {\n <th scope=\"col\" width=\"10\">\n <div class=\"field-check\">\n <input class=\"field-check-input\" type=\"checkbox\" id=\"checkme\" [checked]=\"allSelected()\"\n [indeterminate]=\"someSelected()\" (change)=\"toggleAll()\">\n <label class=\"field-check-label\" for=\"checkme\">\n <span class=\"visually-hidden\">{{ '_COMMON._TABLE._THEAD.CHECK_LINE' | translate }}</span>\n </label>\n </div>\n </th>\n }\n\n @for (column of columns(); track column.key) {\n @if (!column.hidden) {\n <th scope=\"col\" [class.p-0]=\"column.sort\">\n @if (column.sort) {\n <button class=\"d-flex-h gap-2xs\" [class]=\"getSortClass(column.key)\" (click)=\"setSortProperty(column.key)\">\n {{ column.label | translate}}\n <cw-icon\n [icon]=\"getSortIcon(column.key)\"\n [label]=\"'_COMMON._TABLE._SORT.LABEL' | translate\"\n [type]=\"iconType.default\"\n [iconSize]=\"iconSize['xs']\"></cw-icon>\n </button>\n }\n @else {\n {{ column.label | translate }}\n }\n </th>\n }\n }\n </tr>\n </thead>\n <tbody>\n @if (loading()) {\n <tr>\n <td colspan=\"100\">\n <cw-loader></cw-loader>\n </td>\n </tr>\n }\n @else if (!data() || data().length === 0) {\n <tr>\n <td class=\"table-info no-result\" colspan=\"100\">\n @if (currentEmptyState(); as empty) {\n <cw-empty-state\n [illustration]=\"empty.illustration ?? (isFiltered() ? illustrationEnum.noResult : illustrationEnum.noData)\"\n [imageSource]=\"empty.imageSource\"\n [title]=\"empty.title\"\n [description]=\"empty.description\"\n [primaryButton]=\"empty.primaryButton\"\n [secondaryButton]=\"empty.secondaryButton\"\n (primaryClick)=\"empty.primaryButton?.click?.()\"\n (secondaryClick)=\"empty.secondaryButton?.click?.()\">\n </cw-empty-state>\n } @else {\n {{ '_COMMON._TABLE.NO_RESULT' | translate }}\n }\n </td>\n </tr>\n }\n @else {\n @for (row of data(); track row) {\n <tr [class.tr-selected]=\"isSelected(row)\" [class]=\"getRowClass(row)\">\n @if (checkbox()) {\n <td>\n <input class=\"field-check-input\" type=\"checkbox\" [checked]=\"isSelected(row)\" (change)=\"toggleRow(row)\" [id]=\"'check-' + row.id\"\n [attr.aria-label]=\"'S\u00E9lectionner la ligne ' + row.id\">\n <label class=\"visually-hidden\" [for]=\"'check-' + row.id\">S\u00E9lectionner la ligne {{row.id}}</label>\n </td>\n }\n @for (column of columns(); track column.key) {\n @if (!column.hidden) {\n <td [class.text-end]=\"column.align === 'right'\" [class.text-center]=\"column.align === 'center'\"\n [class.td-actions]=\"column.type === 'actions'\">\n @switch (column.type) {\n @case ('link') {\n <a href=\"javascript:void(0)\" (click)=\"onCellClick(row, column)\">\n {{ column.translate ? (row[column.key] | translate) : row[column.key] }}\n </a>\n }\n @case ('badge') {\n <cw-badge\n [type]=\"getBadge(column, row[column.key]).type\"\n [label]=\"getBadge(column, row[column.key]).label ?? row[column.key]\"\n [withIcon]=\"getBadge(column, row[column.key]).withIcon\"\n [iconPosition]=\"getBadge(column, row[column.key]).iconPosition\"></cw-badge>\n }\n @case ('icon') {\n @if (isClickable(column)) {\n <a href=\"javascript:void(0)\" (click)=\"onCellClick(row, column)\" [attr.aria-label]=\"row[column.key].label\">\n <cw-icon\n [icon]=\"row[column.key].icon\"\n [label]=\"row[column.key].label\"\n [type]=\"iconType.default\"\n [iconSize]=\"iconSize['md']\"\n [iconCssClass]=\"row[column.key].iconCssClass\"\n ></cw-icon>\n </a>\n } @else {\n <cw-icon\n [icon]=\"row[column.key].icon\"\n [label]=\"row[column.key].label\"\n [type]=\"iconType.default\"\n [iconSize]=\"iconSize['md']\"\n [iconCssClass]=\"row[column.key].iconCssClass\"\n ></cw-icon>\n }\n }\n @case ('image') {\n @if (isClickable(column)) {\n <a href=\"javascript:void(0)\" (click)=\"onCellClick(row, column)\" [attr.aria-label]=\"row[column.key].label\">\n <cw-image\n [source]=\"row[column.key].source\"\n [alt]=\"row[column.key].label\"\n [isAriaHidden]=\"true\"\n [cssClass]=\"row[column.key].iconCssClass\"\n width=\"32\"\n height=\"32\"\n ></cw-image>\n </a>\n } @else {\n <cw-image\n [source]=\"row[column.key].source\"\n [alt]=\"row[column.key].label\"\n [isAriaHidden]=\"true\"\n [cssClass]=\"row[column.key].iconCssClass\"\n width=\"32\"\n height=\"32\"\n ></cw-image>\n }\n }\n @case ('check') {\n @if (isTruthy(row[column.key])) {\n <cw-icon\n [icon]=\"spriteIcon.checkCircle\"\n [label]=\"'_COMMON._PRO_SENTENCE.YES' | translate\"\n [type]=\"iconType.default\"\n iconCssClass=\"text-success\"\n [iconSize]=\"iconSize['md']\"></cw-icon>\n } @else {\n <cw-icon\n [icon]=\"spriteIcon.closeCircle\"\n [label]=\"'_COMMON._PRO_SENTENCE.NO' | translate\"\n [type]=\"iconType.default\"\n iconCssClass=\"text-danger\"\n [iconSize]=\"iconSize['md']\"></cw-icon>\n }\n }\n @case ('actions') {\n @if (usingRowActions) {\n @let actions = getResolvedActions(row);\n @if (actions.length > 0) {\n @if (!useDropdownActions()) {\n @for (action of actions; track $index) {\n <cw-button\n [type]=\"buttonType.ghost\"\n [label]=\"action.label\"\n [withIcon]=\"action.icon\"\n [link]=\"action.link\"\n [isDisabled]=\"action.disabled\"\n [cssClass]=\"actionCssClass(action)\"\n (btnAction)=\"onRowActionClick(action, row)\">\n </cw-button>\n }\n } @else {\n <cw-button\n [label]=\"'_COMMON._TABLE.ACTIONS_MENU'\"\n [withIcon]=\"spriteIcon.menuVertical\"\n [withOnlyIcon]=\"true\"\n [type]=\"buttonType.ghost\"\n [isDropdown]=\"true\"\n [hideCaret]=\"true\">\n <ul class=\"p-0 m-0\">\n @for (action of actions; track $index) {\n <li>\n @if (action.link) {\n <cw-button\n [type]=\"buttonType.ghost\"\n [label]=\"action.label\"\n [withIcon]=\"action.icon\"\n [link]=\"action.link\"\n [isDisabled]=\"action.disabled\"\n [cssClass]=\"'dropdown-item ' + actionCssClass(action)\">\n </cw-button>\n } @else {\n <cw-button\n [type]=\"buttonType.ghost\"\n [label]=\"action.label\"\n [withIcon]=\"action.icon\"\n [isDisabled]=\"action.disabled\"\n [cssClass]=\"'dropdown-item ' + actionCssClass(action)\"\n (btnAction)=\"onRowActionClick(action, row)\">\n </cw-button>\n }\n </li>\n }\n </ul>\n </cw-button>\n }\n }\n } @else {\n <ng-container\n *ngTemplateOutlet=\"actionsTemplate(); context: { $implicit: row }\">\n </ng-container>\n }\n }\n @default {\n {{ column.translate ? (row[column.key] | translate) : row[column.key] }}\n }\n }\n </td>\n }\n }\n </tr>\n }\n }\n </tbody>\n </table>\n</div>\n\n@if (pagination()) {\n <cw-pagination\n [pagination]=\"pagination()!\"\n (paginationChange)=\"paginationChange.emit($event)\">\n </cw-pagination>\n}\n" }]
|
|
762
|
+
}], ctorParameters: () => [], propDecorators: { checkbox: [{ type: i0.Input, args: [{ isSignal: true, alias: "checkbox", required: false }] }], title: [{ type: i0.Input, args: [{ isSignal: true, alias: "title", required: false }] }], columns: [{ type: i0.Input, args: [{ isSignal: true, alias: "columns", required: false }] }], data: [{ type: i0.Input, args: [{ isSignal: true, alias: "data", required: false }] }], loading: [{ type: i0.Input, args: [{ isSignal: true, alias: "loading", required: false }] }], rowClassFn: [{ type: i0.Input, args: [{ isSignal: true, alias: "rowClassFn", required: false }] }], pagination: [{ type: i0.Input, args: [{ isSignal: true, alias: "pagination", required: false }] }], bulkActions: [{ type: i0.Input, args: [{ isSignal: true, alias: "bulkActions", required: false }] }], rowActions: [{ type: i0.Input, args: [{ isSignal: true, alias: "rowActions", required: false }] }], emptyStateNoData: [{ type: i0.Input, args: [{ isSignal: true, alias: "emptyStateNoData", required: false }] }], emptyStateNoResult: [{ type: i0.Input, args: [{ isSignal: true, alias: "emptyStateNoResult", required: false }] }], isFiltered: [{ type: i0.Input, args: [{ isSignal: true, alias: "isFiltered", required: false }] }], cellClick: [{ type: i0.Output, args: ["cellClick"] }], sortChange: [{ type: i0.Output, args: ["sortChange"] }], selectionChange: [{ type: i0.Output, args: ["selectionChange"] }], paginationChange: [{ type: i0.Output, args: ["paginationChange"] }], bulkDelete: [{ type: i0.Output, args: ["bulkDelete"] }], bulkAction: [{ type: i0.Output, args: ["bulkAction"] }], actionsTemplate: [{ type: i0.ContentChild, args: ['actionsTemplate', { isSignal: true }] }] } });
|
|
753
763
|
|
|
754
764
|
const RANGE_TYPES = new Set([
|
|
755
765
|
FormFieldTypeEnum.dateToDate,
|
|
@@ -908,6 +918,58 @@ var PageHeaderActionEnum;
|
|
|
908
918
|
PageHeaderActionEnum["import"] = "import";
|
|
909
919
|
})(PageHeaderActionEnum || (PageHeaderActionEnum = {}));
|
|
910
920
|
|
|
921
|
+
// Persistance de la visibilite des colonnes de `cw-table` (pilotee par `cw-page-header`).
|
|
922
|
+
// Une SEULE cle localStorage pour N tableaux : objet indexe par `storageKey`.
|
|
923
|
+
// On ne stocke QUE les cles des colonnes MASQUEES (eviter de surcharger le localStorage).
|
|
924
|
+
//
|
|
925
|
+
// localStorage['cw-table-columns'] = {
|
|
926
|
+
// "publictransport/events": ["col1", "col2"],
|
|
927
|
+
// "users/list": ["createdAt"]
|
|
928
|
+
// }
|
|
929
|
+
const STORAGE_KEY = 'cw-table-columns';
|
|
930
|
+
/** Acces localStorage tolerant (SSR / quota / mode prive) : ne jette jamais. */
|
|
931
|
+
function readStore() {
|
|
932
|
+
try {
|
|
933
|
+
if (typeof localStorage === 'undefined')
|
|
934
|
+
return {};
|
|
935
|
+
const raw = localStorage.getItem(STORAGE_KEY);
|
|
936
|
+
const parsed = raw ? JSON.parse(raw) : {};
|
|
937
|
+
return parsed && typeof parsed === 'object' ? parsed : {};
|
|
938
|
+
}
|
|
939
|
+
catch {
|
|
940
|
+
return {};
|
|
941
|
+
}
|
|
942
|
+
}
|
|
943
|
+
/**
|
|
944
|
+
* Cles des colonnes masquees memorisees pour ce tableau.
|
|
945
|
+
* - `null` : aucune entree => l'utilisateur n'a jamais personnalise, on garde les defauts du config.
|
|
946
|
+
* - `string[]` (meme vide) : etat autoritatif memorise (`[]` = tout visible, choisi par l'utilisateur).
|
|
947
|
+
*/
|
|
948
|
+
function loadHiddenColumns(storageKey) {
|
|
949
|
+
if (!storageKey)
|
|
950
|
+
return null;
|
|
951
|
+
const entry = readStore()[storageKey];
|
|
952
|
+
return Array.isArray(entry) ? entry : null;
|
|
953
|
+
}
|
|
954
|
+
/**
|
|
955
|
+
* Memorise les cles des colonnes masquees pour ce tableau.
|
|
956
|
+
* Ecrit toujours l'entree (meme vide) : sa presence marque « personnalise par l'utilisateur ».
|
|
957
|
+
*/
|
|
958
|
+
function saveHiddenColumns(storageKey, hiddenKeys) {
|
|
959
|
+
if (!storageKey)
|
|
960
|
+
return;
|
|
961
|
+
try {
|
|
962
|
+
if (typeof localStorage === 'undefined')
|
|
963
|
+
return;
|
|
964
|
+
const store = readStore();
|
|
965
|
+
store[storageKey] = hiddenKeys;
|
|
966
|
+
localStorage.setItem(STORAGE_KEY, JSON.stringify(store));
|
|
967
|
+
}
|
|
968
|
+
catch {
|
|
969
|
+
/* localStorage indisponible : persistance silencieusement ignoree. */
|
|
970
|
+
}
|
|
971
|
+
}
|
|
972
|
+
|
|
911
973
|
class PageHeaderComponent {
|
|
912
974
|
constructor() {
|
|
913
975
|
this.location = inject(Location);
|
|
@@ -917,7 +979,16 @@ class PageHeaderComponent {
|
|
|
917
979
|
this.actions = input([], ...(ngDevMode ? [{ debugName: "actions" }] : []));
|
|
918
980
|
this.isLoading = input({}, ...(ngDevMode ? [{ debugName: "isLoading" }] : []));
|
|
919
981
|
this.isDisabled = input({}, ...(ngDevMode ? [{ debugName: "isDisabled" }] : []));
|
|
982
|
+
// --- Menu « Colonnes » -------------------------------------------------
|
|
983
|
+
/** Colonnes du tableau associe. Fourni => le dropdown « Colonnes » apparait. */
|
|
984
|
+
this.columns = input([], ...(ngDevMode ? [{ debugName: "columns" }] : []));
|
|
985
|
+
/** Identifiant stable du tableau pour la persistance localStorage (ex. 'users/list'). */
|
|
986
|
+
this.storageKey = input(...(ngDevMode ? [undefined, { debugName: "storageKey" }] : []));
|
|
987
|
+
/** Cle i18n du libelle du bouton « Colonnes ». */
|
|
988
|
+
this.columnsLabel = input('_COMMON._TABLE.COLUMNS', ...(ngDevMode ? [{ debugName: "columnsLabel" }] : []));
|
|
920
989
|
this.action = output();
|
|
990
|
+
/** Emis quand la visibilite des colonnes change (colonnes avec `hidden` a jour). */
|
|
991
|
+
this.columnsChange = output();
|
|
921
992
|
this.buttonType = BoButtonTypeEnum;
|
|
922
993
|
this.iconSize = ButtonIconSizeEnum;
|
|
923
994
|
this.spriteIcon = SpriteIconEnum;
|
|
@@ -929,6 +1000,53 @@ class PageHeaderComponent {
|
|
|
929
1000
|
this.showReset = computed(() => this.actions().includes(PageHeaderActionEnum.reset), ...(ngDevMode ? [{ debugName: "showReset" }] : []));
|
|
930
1001
|
this.showAdd = computed(() => this.actions().includes(PageHeaderActionEnum.add), ...(ngDevMode ? [{ debugName: "showAdd" }] : []));
|
|
931
1002
|
this.showSave = computed(() => this.actions().includes(PageHeaderActionEnum.save), ...(ngDevMode ? [{ debugName: "showSave" }] : []));
|
|
1003
|
+
/** Colonnes masquables (hors `actions` et hors `hideable === false`). */
|
|
1004
|
+
this.toggleableColumns = computed(() => this.columns().filter(c => c.type !== 'actions' && c.hideable !== false), ...(ngDevMode ? [{ debugName: "toggleableColumns" }] : []));
|
|
1005
|
+
/** Le dropdown « Colonnes » n'apparait que s'il existe au moins une colonne masquable. */
|
|
1006
|
+
this.showColumns = computed(() => this.toggleableColumns().length > 0, ...(ngDevMode ? [{ debugName: "showColumns" }] : []));
|
|
1007
|
+
/** Nombre de colonnes masquables actuellement visibles. */
|
|
1008
|
+
this.visibleToggleableCount = computed(() => this.toggleableColumns().filter(c => !c.hidden).length, ...(ngDevMode ? [{ debugName: "visibleToggleableCount" }] : []));
|
|
1009
|
+
// Reconciliation au 1er rendu (navigateur) : si un etat est memorise, il prime
|
|
1010
|
+
// sur les defauts du config et est emis une fois vers le parent.
|
|
1011
|
+
afterNextRender(() => this.applyStoredVisibility());
|
|
1012
|
+
}
|
|
1013
|
+
/** Une colonne visible est « la derniere » si la masquer laisserait 0 colonne visible. */
|
|
1014
|
+
isLastVisible(col) {
|
|
1015
|
+
return !col.hidden && this.visibleToggleableCount() <= 1;
|
|
1016
|
+
}
|
|
1017
|
+
/** Coche/decoche une colonne : applique le garde-fou, persiste et emet. */
|
|
1018
|
+
toggleColumn(col) {
|
|
1019
|
+
const willHide = !col.hidden;
|
|
1020
|
+
if (willHide && this.visibleToggleableCount() <= 1)
|
|
1021
|
+
return; // garde-fou : min 1 visible
|
|
1022
|
+
const updated = this.columns().map(c => (c.key === col.key ? { ...c, hidden: willHide } : c));
|
|
1023
|
+
this.persistAndEmit(updated);
|
|
1024
|
+
}
|
|
1025
|
+
applyStoredVisibility() {
|
|
1026
|
+
const key = this.storageKey();
|
|
1027
|
+
if (!key)
|
|
1028
|
+
return;
|
|
1029
|
+
const stored = loadHiddenColumns(key);
|
|
1030
|
+
if (!stored)
|
|
1031
|
+
return; // jamais personnalise -> on garde les `hidden` du config
|
|
1032
|
+
const hidden = new Set(stored);
|
|
1033
|
+
const reconciled = this.columns().map(c => c.type === 'actions' || c.hideable === false ? c : { ...c, hidden: hidden.has(c.key) });
|
|
1034
|
+
this.columnsChange.emit(this.ensureMinVisible(reconciled));
|
|
1035
|
+
}
|
|
1036
|
+
/** Garantit au moins une colonne masquable visible (re-affiche la 1re sinon). */
|
|
1037
|
+
ensureMinVisible(cols) {
|
|
1038
|
+
const toggleable = cols.filter(c => c.type !== 'actions' && c.hideable !== false);
|
|
1039
|
+
if (toggleable.length === 0 || toggleable.some(c => !c.hidden))
|
|
1040
|
+
return cols;
|
|
1041
|
+
const firstKey = toggleable[0].key;
|
|
1042
|
+
return cols.map(c => (c.key === firstKey ? { ...c, hidden: false } : c));
|
|
1043
|
+
}
|
|
1044
|
+
persistAndEmit(cols) {
|
|
1045
|
+
const hiddenKeys = cols
|
|
1046
|
+
.filter(c => c.hidden && c.type !== 'actions' && c.hideable !== false)
|
|
1047
|
+
.map(c => c.key);
|
|
1048
|
+
saveHiddenColumns(this.storageKey() ?? '', hiddenKeys);
|
|
1049
|
+
this.columnsChange.emit(cols);
|
|
932
1050
|
}
|
|
933
1051
|
goBack() {
|
|
934
1052
|
this.location.back();
|
|
@@ -943,7 +1061,7 @@ class PageHeaderComponent {
|
|
|
943
1061
|
return !!this.isDisabled()[action];
|
|
944
1062
|
}
|
|
945
1063
|
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.20", ngImport: i0, type: PageHeaderComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
|
|
946
|
-
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.20", type: PageHeaderComponent, isStandalone: true, selector: "cw-page-header", inputs: { title: { classPropertyName: "title", publicName: "title", isSignal: true, isRequired: true, transformFunction: null }, description: { classPropertyName: "description", publicName: "description", isSignal: true, isRequired: false, transformFunction: null }, showBack: { classPropertyName: "showBack", publicName: "showBack", isSignal: true, isRequired: false, transformFunction: null }, actions: { classPropertyName: "actions", publicName: "actions", isSignal: true, isRequired: false, transformFunction: null }, isLoading: { classPropertyName: "isLoading", publicName: "isLoading", isSignal: true, isRequired: false, transformFunction: null }, isDisabled: { classPropertyName: "isDisabled", publicName: "isDisabled", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { action: "action" }, ngImport: i0, template: "<div class=\"page-header d-flex-v gap-2xs\">\n @if (showBack()) {\n <cw-button [type]=\"buttonType.ghost\" [label]=\"'_COMMON._FORM.BACK'\" [withIcon]=\"spriteIcon.left1\"\n (btnAction)=\"goBack()\" />\n }\n <div class=\"d-flex-h gap-md items-start justify-between flex-wrap\">\n <div class=\"d-flex-v\">\n <h1 class=\"page-header-title\">{{ title() | translate}}</h1>\n @if (description(); as desc) {\n <p class=\"fs-md page-header-description\" [innerHTML]=\"desc | translate\"></p>\n }\n </div>\n\n <div class=\"page-header-actions d-flex-h gap-md flex-wrap items-center\">\n @if (showImport()) {\n <cw-button [type]=\"buttonType.secondary\" [label]=\"'_COMMON._ACTION.IMPORT'\"\n [isDisabled]=\"disabled(actionEnum.import)\" [isLoading]=\"loading(actionEnum.import)\"\n (btnAction)=\"emit(actionEnum.import)\">\n </cw-button>\n }\n\n @if (showReset()) {\n <cw-button [type]=\"buttonType.secondary\" [label]=\"'_COMMON._ACTION.RESET'\"\n [isDisabled]=\"disabled(actionEnum.reset)\" [isLoading]=\"loading(actionEnum.reset)\"\n (btnAction)=\"emit(actionEnum.reset)\">\n </cw-button>\n }\n\n @if (hasExport()) {\n <cw-button [type]=\"buttonType.secondary\" [label]=\"'_COMMON._ACTION.EXPORT'\" [isDropdown]=\"true\"\n [isDisabled]=\"disabled(actionEnum.exportCurrent) && disabled(actionEnum.exportAll)\">\n <ul>\n <li>\n @if (showExportCurrent()) {\n <cw-button [type]=\"buttonType.ghost\" [label]=\"'_COMMON._ACTION.EXPORT_CURRENT'\"\n [isDisabled]=\"disabled(actionEnum.exportCurrent)\" (btnAction)=\"emit(actionEnum.exportCurrent)\">\n </cw-button>\n }\n </li>\n <li>\n @if (showExportAll()) {\n <cw-button [type]=\"buttonType.ghost\" [label]=\"'_COMMON._ACTION.EXPORT_ALL'\"\n [isDisabled]=\"disabled(actionEnum.exportAll)\" (btnAction)=\"emit(actionEnum.exportAll)\">\n </cw-button>\n }\n </li>\n </ul>\n </cw-button>\n }\n\n <ng-content></ng-content>\n\n @if (showAdd()) {\n <cw-button [type]=\"buttonType.primary\" [label]=\"'_COMMON._ACTION.ADD'\" [withIcon]=\"spriteIcon.add\"\n [isDisabled]=\"disabled(actionEnum.add)\" [isLoading]=\"loading(actionEnum.add)\"\n (btnAction)=\"emit(actionEnum.add)\">\n </cw-button>\n }\n\n @if (showSave()) {\n <cw-button [type]=\"buttonType.primary\" [label]=\"'_COMMON._ACTION.SAVE'\" [isDisabled]=\"disabled(actionEnum.save)\"\n [isLoading]=\"loading(actionEnum.save)\" (btnAction)=\"emit(actionEnum.save)\">\n </cw-button>\n }\n </div>\n </div>\n</div>\n", dependencies: [{ kind: "component", type: ButtonComponent, selector: "cw-button", inputs: ["type", "label", "id", "link", "isDropdown", "hideCaret", "withIcon", "withOnlyIcon", "iconSize", "iconPosition", "dropdownPosition", "isMinWidth", "isDisabled", "isLoading", "cssClass", "dataTest", "skeletonMode", "withTooltip", "tooltipText", "tooltipTitle", "tooltipTrigger", "tooltipPosition", "tooltipType"], outputs: ["btnAction", "dropDownClicked"] }, { kind: "ngmodule", type: TranslateModule }, { kind: "pipe", type: i1$1.TranslatePipe, name: "translate" }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
|
|
1064
|
+
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.20", type: PageHeaderComponent, isStandalone: true, selector: "cw-page-header", inputs: { title: { classPropertyName: "title", publicName: "title", isSignal: true, isRequired: true, transformFunction: null }, description: { classPropertyName: "description", publicName: "description", isSignal: true, isRequired: false, transformFunction: null }, showBack: { classPropertyName: "showBack", publicName: "showBack", isSignal: true, isRequired: false, transformFunction: null }, actions: { classPropertyName: "actions", publicName: "actions", isSignal: true, isRequired: false, transformFunction: null }, isLoading: { classPropertyName: "isLoading", publicName: "isLoading", isSignal: true, isRequired: false, transformFunction: null }, isDisabled: { classPropertyName: "isDisabled", publicName: "isDisabled", isSignal: true, isRequired: false, transformFunction: null }, columns: { classPropertyName: "columns", publicName: "columns", isSignal: true, isRequired: false, transformFunction: null }, storageKey: { classPropertyName: "storageKey", publicName: "storageKey", isSignal: true, isRequired: false, transformFunction: null }, columnsLabel: { classPropertyName: "columnsLabel", publicName: "columnsLabel", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { action: "action", columnsChange: "columnsChange" }, ngImport: i0, template: "<div class=\"page-header d-flex-v gap-2xs\">\n @if (showBack()) {\n <cw-button [type]=\"buttonType.ghost\" [label]=\"'_COMMON._FORM.BACK'\" [withIcon]=\"spriteIcon.left1\"\n (btnAction)=\"goBack()\" />\n }\n <div class=\"d-flex-h gap-md items-start justify-between flex-wrap\">\n <div class=\"d-flex-v\">\n <h1 class=\"page-header-title\">{{ title() | translate}}</h1>\n @if (description(); as desc) {\n <p class=\"fs-md page-header-description\" [innerHTML]=\"desc | translate\"></p>\n }\n </div>\n\n <div class=\"page-header-actions d-flex-h gap-md flex-wrap items-center\">\n @if (showColumns()) {\n <cw-button [type]=\"buttonType.secondary\" [label]=\"columnsLabel()\" [withIcon]=\"spriteIcon.view\"\n [isDropdown]=\"true\">\n <ul class=\"page-header-columns-menu\">\n @for (col of toggleableColumns(); track col.key) {\n <li class=\"field-check\">\n <input class=\"field-check-input\" type=\"checkbox\" [id]=\"'col-toggle-' + col.key\"\n [checked]=\"!col.hidden\" [disabled]=\"isLastVisible(col)\" (change)=\"toggleColumn(col)\">\n <label class=\"field-check-label\" [for]=\"'col-toggle-' + col.key\">{{ col.label | translate }}</label>\n </li>\n }\n </ul>\n </cw-button>\n }\n\n @if (showImport()) {\n <cw-button [type]=\"buttonType.secondary\" [label]=\"'_COMMON._ACTION.IMPORT'\"\n [isDisabled]=\"disabled(actionEnum.import)\" [isLoading]=\"loading(actionEnum.import)\"\n (btnAction)=\"emit(actionEnum.import)\">\n </cw-button>\n }\n\n @if (showReset()) {\n <cw-button [type]=\"buttonType.secondary\" [label]=\"'_COMMON._ACTION.RESET'\"\n [isDisabled]=\"disabled(actionEnum.reset)\" [isLoading]=\"loading(actionEnum.reset)\"\n (btnAction)=\"emit(actionEnum.reset)\">\n </cw-button>\n }\n\n @if (hasExport()) {\n <cw-button [type]=\"buttonType.secondary\" [label]=\"'_COMMON._ACTION.EXPORT'\" [isDropdown]=\"true\"\n [isDisabled]=\"disabled(actionEnum.exportCurrent) && disabled(actionEnum.exportAll)\">\n <ul>\n <li>\n @if (showExportCurrent()) {\n <cw-button [type]=\"buttonType.ghost\" [label]=\"'_COMMON._ACTION.EXPORT_CURRENT'\"\n [isDisabled]=\"disabled(actionEnum.exportCurrent)\" (btnAction)=\"emit(actionEnum.exportCurrent)\">\n </cw-button>\n }\n </li>\n <li>\n @if (showExportAll()) {\n <cw-button [type]=\"buttonType.ghost\" [label]=\"'_COMMON._ACTION.EXPORT_ALL'\"\n [isDisabled]=\"disabled(actionEnum.exportAll)\" (btnAction)=\"emit(actionEnum.exportAll)\">\n </cw-button>\n }\n </li>\n </ul>\n </cw-button>\n }\n\n <ng-content></ng-content>\n\n @if (showAdd()) {\n <cw-button [type]=\"buttonType.primary\" [label]=\"'_COMMON._ACTION.ADD'\" [withIcon]=\"spriteIcon.add\"\n [isDisabled]=\"disabled(actionEnum.add)\" [isLoading]=\"loading(actionEnum.add)\"\n (btnAction)=\"emit(actionEnum.add)\">\n </cw-button>\n }\n\n @if (showSave()) {\n <cw-button [type]=\"buttonType.primary\" [label]=\"'_COMMON._ACTION.SAVE'\" [isDisabled]=\"disabled(actionEnum.save)\"\n [isLoading]=\"loading(actionEnum.save)\" (btnAction)=\"emit(actionEnum.save)\">\n </cw-button>\n }\n </div>\n </div>\n</div>\n", dependencies: [{ kind: "component", type: ButtonComponent, selector: "cw-button", inputs: ["type", "label", "id", "link", "isDropdown", "hideCaret", "withIcon", "withOnlyIcon", "iconSize", "iconPosition", "dropdownPosition", "isMinWidth", "isDisabled", "isLoading", "cssClass", "dataTest", "skeletonMode", "withTooltip", "tooltipText", "tooltipTitle", "tooltipTrigger", "tooltipPosition", "tooltipType"], outputs: ["btnAction", "dropDownClicked"] }, { kind: "ngmodule", type: TranslateModule }, { kind: "pipe", type: i1$1.TranslatePipe, name: "translate" }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
|
|
947
1065
|
}
|
|
948
1066
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.20", ngImport: i0, type: PageHeaderComponent, decorators: [{
|
|
949
1067
|
type: Component,
|
|
@@ -951,8 +1069,8 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.20", ngImpo
|
|
|
951
1069
|
ButtonComponent,
|
|
952
1070
|
DropdownItemDirective,
|
|
953
1071
|
TranslateModule
|
|
954
|
-
], template: "<div class=\"page-header d-flex-v gap-2xs\">\n @if (showBack()) {\n <cw-button [type]=\"buttonType.ghost\" [label]=\"'_COMMON._FORM.BACK'\" [withIcon]=\"spriteIcon.left1\"\n (btnAction)=\"goBack()\" />\n }\n <div class=\"d-flex-h gap-md items-start justify-between flex-wrap\">\n <div class=\"d-flex-v\">\n <h1 class=\"page-header-title\">{{ title() | translate}}</h1>\n @if (description(); as desc) {\n <p class=\"fs-md page-header-description\" [innerHTML]=\"desc | translate\"></p>\n }\n </div>\n\n <div class=\"page-header-actions d-flex-h gap-md flex-wrap items-center\">\n @if (showImport()) {\n <cw-button [type]=\"buttonType.secondary\" [label]=\"'_COMMON._ACTION.IMPORT'\"\n [isDisabled]=\"disabled(actionEnum.import)\" [isLoading]=\"loading(actionEnum.import)\"\n (btnAction)=\"emit(actionEnum.import)\">\n </cw-button>\n }\n\n @if (showReset()) {\n <cw-button [type]=\"buttonType.secondary\" [label]=\"'_COMMON._ACTION.RESET'\"\n [isDisabled]=\"disabled(actionEnum.reset)\" [isLoading]=\"loading(actionEnum.reset)\"\n (btnAction)=\"emit(actionEnum.reset)\">\n </cw-button>\n }\n\n @if (hasExport()) {\n <cw-button [type]=\"buttonType.secondary\" [label]=\"'_COMMON._ACTION.EXPORT'\" [isDropdown]=\"true\"\n [isDisabled]=\"disabled(actionEnum.exportCurrent) && disabled(actionEnum.exportAll)\">\n <ul>\n <li>\n @if (showExportCurrent()) {\n <cw-button [type]=\"buttonType.ghost\" [label]=\"'_COMMON._ACTION.EXPORT_CURRENT'\"\n [isDisabled]=\"disabled(actionEnum.exportCurrent)\" (btnAction)=\"emit(actionEnum.exportCurrent)\">\n </cw-button>\n }\n </li>\n <li>\n @if (showExportAll()) {\n <cw-button [type]=\"buttonType.ghost\" [label]=\"'_COMMON._ACTION.EXPORT_ALL'\"\n [isDisabled]=\"disabled(actionEnum.exportAll)\" (btnAction)=\"emit(actionEnum.exportAll)\">\n </cw-button>\n }\n </li>\n </ul>\n </cw-button>\n }\n\n <ng-content></ng-content>\n\n @if (showAdd()) {\n <cw-button [type]=\"buttonType.primary\" [label]=\"'_COMMON._ACTION.ADD'\" [withIcon]=\"spriteIcon.add\"\n [isDisabled]=\"disabled(actionEnum.add)\" [isLoading]=\"loading(actionEnum.add)\"\n (btnAction)=\"emit(actionEnum.add)\">\n </cw-button>\n }\n\n @if (showSave()) {\n <cw-button [type]=\"buttonType.primary\" [label]=\"'_COMMON._ACTION.SAVE'\" [isDisabled]=\"disabled(actionEnum.save)\"\n [isLoading]=\"loading(actionEnum.save)\" (btnAction)=\"emit(actionEnum.save)\">\n </cw-button>\n }\n </div>\n </div>\n</div>\n" }]
|
|
955
|
-
}], propDecorators: { title: [{ type: i0.Input, args: [{ isSignal: true, alias: "title", required: true }] }], description: [{ type: i0.Input, args: [{ isSignal: true, alias: "description", required: false }] }], showBack: [{ type: i0.Input, args: [{ isSignal: true, alias: "showBack", required: false }] }], actions: [{ type: i0.Input, args: [{ isSignal: true, alias: "actions", required: false }] }], isLoading: [{ type: i0.Input, args: [{ isSignal: true, alias: "isLoading", required: false }] }], isDisabled: [{ type: i0.Input, args: [{ isSignal: true, alias: "isDisabled", required: false }] }], action: [{ type: i0.Output, args: ["action"] }] } });
|
|
1072
|
+
], template: "<div class=\"page-header d-flex-v gap-2xs\">\n @if (showBack()) {\n <cw-button [type]=\"buttonType.ghost\" [label]=\"'_COMMON._FORM.BACK'\" [withIcon]=\"spriteIcon.left1\"\n (btnAction)=\"goBack()\" />\n }\n <div class=\"d-flex-h gap-md items-start justify-between flex-wrap\">\n <div class=\"d-flex-v\">\n <h1 class=\"page-header-title\">{{ title() | translate}}</h1>\n @if (description(); as desc) {\n <p class=\"fs-md page-header-description\" [innerHTML]=\"desc | translate\"></p>\n }\n </div>\n\n <div class=\"page-header-actions d-flex-h gap-md flex-wrap items-center\">\n @if (showColumns()) {\n <cw-button [type]=\"buttonType.secondary\" [label]=\"columnsLabel()\" [withIcon]=\"spriteIcon.view\"\n [isDropdown]=\"true\">\n <ul class=\"page-header-columns-menu\">\n @for (col of toggleableColumns(); track col.key) {\n <li class=\"field-check\">\n <input class=\"field-check-input\" type=\"checkbox\" [id]=\"'col-toggle-' + col.key\"\n [checked]=\"!col.hidden\" [disabled]=\"isLastVisible(col)\" (change)=\"toggleColumn(col)\">\n <label class=\"field-check-label\" [for]=\"'col-toggle-' + col.key\">{{ col.label | translate }}</label>\n </li>\n }\n </ul>\n </cw-button>\n }\n\n @if (showImport()) {\n <cw-button [type]=\"buttonType.secondary\" [label]=\"'_COMMON._ACTION.IMPORT'\"\n [isDisabled]=\"disabled(actionEnum.import)\" [isLoading]=\"loading(actionEnum.import)\"\n (btnAction)=\"emit(actionEnum.import)\">\n </cw-button>\n }\n\n @if (showReset()) {\n <cw-button [type]=\"buttonType.secondary\" [label]=\"'_COMMON._ACTION.RESET'\"\n [isDisabled]=\"disabled(actionEnum.reset)\" [isLoading]=\"loading(actionEnum.reset)\"\n (btnAction)=\"emit(actionEnum.reset)\">\n </cw-button>\n }\n\n @if (hasExport()) {\n <cw-button [type]=\"buttonType.secondary\" [label]=\"'_COMMON._ACTION.EXPORT'\" [isDropdown]=\"true\"\n [isDisabled]=\"disabled(actionEnum.exportCurrent) && disabled(actionEnum.exportAll)\">\n <ul>\n <li>\n @if (showExportCurrent()) {\n <cw-button [type]=\"buttonType.ghost\" [label]=\"'_COMMON._ACTION.EXPORT_CURRENT'\"\n [isDisabled]=\"disabled(actionEnum.exportCurrent)\" (btnAction)=\"emit(actionEnum.exportCurrent)\">\n </cw-button>\n }\n </li>\n <li>\n @if (showExportAll()) {\n <cw-button [type]=\"buttonType.ghost\" [label]=\"'_COMMON._ACTION.EXPORT_ALL'\"\n [isDisabled]=\"disabled(actionEnum.exportAll)\" (btnAction)=\"emit(actionEnum.exportAll)\">\n </cw-button>\n }\n </li>\n </ul>\n </cw-button>\n }\n\n <ng-content></ng-content>\n\n @if (showAdd()) {\n <cw-button [type]=\"buttonType.primary\" [label]=\"'_COMMON._ACTION.ADD'\" [withIcon]=\"spriteIcon.add\"\n [isDisabled]=\"disabled(actionEnum.add)\" [isLoading]=\"loading(actionEnum.add)\"\n (btnAction)=\"emit(actionEnum.add)\">\n </cw-button>\n }\n\n @if (showSave()) {\n <cw-button [type]=\"buttonType.primary\" [label]=\"'_COMMON._ACTION.SAVE'\" [isDisabled]=\"disabled(actionEnum.save)\"\n [isLoading]=\"loading(actionEnum.save)\" (btnAction)=\"emit(actionEnum.save)\">\n </cw-button>\n }\n </div>\n </div>\n</div>\n" }]
|
|
1073
|
+
}], ctorParameters: () => [], propDecorators: { title: [{ type: i0.Input, args: [{ isSignal: true, alias: "title", required: true }] }], description: [{ type: i0.Input, args: [{ isSignal: true, alias: "description", required: false }] }], showBack: [{ type: i0.Input, args: [{ isSignal: true, alias: "showBack", required: false }] }], actions: [{ type: i0.Input, args: [{ isSignal: true, alias: "actions", required: false }] }], isLoading: [{ type: i0.Input, args: [{ isSignal: true, alias: "isLoading", required: false }] }], isDisabled: [{ type: i0.Input, args: [{ isSignal: true, alias: "isDisabled", required: false }] }], columns: [{ type: i0.Input, args: [{ isSignal: true, alias: "columns", required: false }] }], storageKey: [{ type: i0.Input, args: [{ isSignal: true, alias: "storageKey", required: false }] }], columnsLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "columnsLabel", required: false }] }], action: [{ type: i0.Output, args: ["action"] }], columnsChange: [{ type: i0.Output, args: ["columnsChange"] }] } });
|
|
956
1074
|
|
|
957
1075
|
// Modele du composant `cw-progress-bar` — types alignes sur le DS (BOU)
|
|
958
1076
|
// pages Figma `Progressbar / md` et `Progressbar / sm`.
|
|
@@ -1118,5 +1236,5 @@ function buildFilterParams(filters, keyMap) {
|
|
|
1118
1236
|
* Generated bundle index. Do not edit.
|
|
1119
1237
|
*/
|
|
1120
1238
|
|
|
1121
|
-
export { ArrayAdapter, CustomListComponent, DragNDropListComponent, DragNDropNestedListComponent, FilterBarComponent, FormArrayAdapter, PageHeaderActionEnum, PageHeaderComponent, PaginationComponent, ProgressBarComponent, ProgressBarSizeEnum, ProgressBarTypeEnum, TableComponent, WizardStepComponent, WizardStepperComponent, buildFilterParams };
|
|
1239
|
+
export { ArrayAdapter, CustomListComponent, DragNDropListComponent, DragNDropNestedListComponent, FilterBarComponent, FormArrayAdapter, PageHeaderActionEnum, PageHeaderComponent, PaginationComponent, ProgressBarComponent, ProgressBarSizeEnum, ProgressBarTypeEnum, TableComponent, WizardStepComponent, WizardStepperComponent, buildFilterParams, loadHiddenColumns, saveHiddenColumns };
|
|
1122
1240
|
//# sourceMappingURL=cityway-bo-ui.mjs.map
|