@joanroucoux/cairn-ui 0.8.2 → 0.9.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (124) hide show
  1. package/CHANGELOG.md +99 -0
  2. package/fesm2022/joanroucoux-cairn-ui-action-bar.mjs +57 -53
  3. package/fesm2022/joanroucoux-cairn-ui-action-bar.mjs.map +1 -1
  4. package/fesm2022/joanroucoux-cairn-ui-alert.mjs +155 -47
  5. package/fesm2022/joanroucoux-cairn-ui-alert.mjs.map +1 -1
  6. package/fesm2022/joanroucoux-cairn-ui-amount.mjs +220 -110
  7. package/fesm2022/joanroucoux-cairn-ui-amount.mjs.map +1 -1
  8. package/fesm2022/joanroucoux-cairn-ui-async.mjs +392 -216
  9. package/fesm2022/joanroucoux-cairn-ui-async.mjs.map +1 -1
  10. package/fesm2022/joanroucoux-cairn-ui-avatar.mjs +145 -68
  11. package/fesm2022/joanroucoux-cairn-ui-avatar.mjs.map +1 -1
  12. package/fesm2022/joanroucoux-cairn-ui-back-link.mjs +87 -47
  13. package/fesm2022/joanroucoux-cairn-ui-back-link.mjs.map +1 -1
  14. package/fesm2022/joanroucoux-cairn-ui-badge.mjs +83 -43
  15. package/fesm2022/joanroucoux-cairn-ui-badge.mjs.map +1 -1
  16. package/fesm2022/joanroucoux-cairn-ui-button.mjs +184 -104
  17. package/fesm2022/joanroucoux-cairn-ui-button.mjs.map +1 -1
  18. package/fesm2022/joanroucoux-cairn-ui-card.mjs +232 -137
  19. package/fesm2022/joanroucoux-cairn-ui-card.mjs.map +1 -1
  20. package/fesm2022/joanroucoux-cairn-ui-choice-chips.mjs +298 -102
  21. package/fesm2022/joanroucoux-cairn-ui-choice-chips.mjs.map +1 -1
  22. package/fesm2022/joanroucoux-cairn-ui-control.mjs +4 -17
  23. package/fesm2022/joanroucoux-cairn-ui-control.mjs.map +1 -1
  24. package/fesm2022/joanroucoux-cairn-ui-delta.mjs +150 -83
  25. package/fesm2022/joanroucoux-cairn-ui-delta.mjs.map +1 -1
  26. package/fesm2022/joanroucoux-cairn-ui-dialog.mjs +508 -471
  27. package/fesm2022/joanroucoux-cairn-ui-dialog.mjs.map +1 -1
  28. package/fesm2022/joanroucoux-cairn-ui-donut.mjs +255 -157
  29. package/fesm2022/joanroucoux-cairn-ui-donut.mjs.map +1 -1
  30. package/fesm2022/joanroucoux-cairn-ui-drawer.mjs +303 -0
  31. package/fesm2022/joanroucoux-cairn-ui-drawer.mjs.map +1 -0
  32. package/fesm2022/joanroucoux-cairn-ui-empty.mjs +76 -35
  33. package/fesm2022/joanroucoux-cairn-ui-empty.mjs.map +1 -1
  34. package/fesm2022/joanroucoux-cairn-ui-external-link.mjs +40 -31
  35. package/fesm2022/joanroucoux-cairn-ui-external-link.mjs.map +1 -1
  36. package/fesm2022/joanroucoux-cairn-ui-fact.mjs +188 -79
  37. package/fesm2022/joanroucoux-cairn-ui-fact.mjs.map +1 -1
  38. package/fesm2022/joanroucoux-cairn-ui-field.mjs +309 -173
  39. package/fesm2022/joanroucoux-cairn-ui-field.mjs.map +1 -1
  40. package/fesm2022/joanroucoux-cairn-ui-filter-chips.mjs +165 -87
  41. package/fesm2022/joanroucoux-cairn-ui-filter-chips.mjs.map +1 -1
  42. package/fesm2022/joanroucoux-cairn-ui-group-header.mjs +269 -0
  43. package/fesm2022/joanroucoux-cairn-ui-group-header.mjs.map +1 -0
  44. package/fesm2022/joanroucoux-cairn-ui-input.mjs +205 -85
  45. package/fesm2022/joanroucoux-cairn-ui-input.mjs.map +1 -1
  46. package/fesm2022/joanroucoux-cairn-ui-line-chart.mjs +838 -512
  47. package/fesm2022/joanroucoux-cairn-ui-line-chart.mjs.map +1 -1
  48. package/fesm2022/joanroucoux-cairn-ui-menu.mjs +401 -225
  49. package/fesm2022/joanroucoux-cairn-ui-menu.mjs.map +1 -1
  50. package/fesm2022/joanroucoux-cairn-ui-meter.mjs +143 -57
  51. package/fesm2022/joanroucoux-cairn-ui-meter.mjs.map +1 -1
  52. package/fesm2022/joanroucoux-cairn-ui-motion.mjs +367 -399
  53. package/fesm2022/joanroucoux-cairn-ui-motion.mjs.map +1 -1
  54. package/fesm2022/joanroucoux-cairn-ui-nav-item.mjs +73 -44
  55. package/fesm2022/joanroucoux-cairn-ui-nav-item.mjs.map +1 -1
  56. package/fesm2022/joanroucoux-cairn-ui-result-group.mjs +191 -0
  57. package/fesm2022/joanroucoux-cairn-ui-result-group.mjs.map +1 -0
  58. package/fesm2022/joanroucoux-cairn-ui-row.mjs +376 -146
  59. package/fesm2022/joanroucoux-cairn-ui-row.mjs.map +1 -1
  60. package/fesm2022/joanroucoux-cairn-ui-segmented.mjs +183 -81
  61. package/fesm2022/joanroucoux-cairn-ui-segmented.mjs.map +1 -1
  62. package/fesm2022/joanroucoux-cairn-ui-select-pill.mjs +233 -0
  63. package/fesm2022/joanroucoux-cairn-ui-select-pill.mjs.map +1 -0
  64. package/fesm2022/joanroucoux-cairn-ui-select.mjs +121 -67
  65. package/fesm2022/joanroucoux-cairn-ui-select.mjs.map +1 -1
  66. package/fesm2022/joanroucoux-cairn-ui-skeleton.mjs +129 -51
  67. package/fesm2022/joanroucoux-cairn-ui-skeleton.mjs.map +1 -1
  68. package/fesm2022/joanroucoux-cairn-ui-stale-link.mjs +80 -39
  69. package/fesm2022/joanroucoux-cairn-ui-stale-link.mjs.map +1 -1
  70. package/fesm2022/joanroucoux-cairn-ui-stat.mjs +85 -55
  71. package/fesm2022/joanroucoux-cairn-ui-stat.mjs.map +1 -1
  72. package/fesm2022/joanroucoux-cairn-ui-switch.mjs +48 -35
  73. package/fesm2022/joanroucoux-cairn-ui-switch.mjs.map +1 -1
  74. package/fesm2022/joanroucoux-cairn-ui-tab-bar.mjs +113 -69
  75. package/fesm2022/joanroucoux-cairn-ui-tab-bar.mjs.map +1 -1
  76. package/fesm2022/joanroucoux-cairn-ui-table.mjs +1036 -310
  77. package/fesm2022/joanroucoux-cairn-ui-table.mjs.map +1 -1
  78. package/fesm2022/joanroucoux-cairn-ui-toast.mjs +240 -127
  79. package/fesm2022/joanroucoux-cairn-ui-toast.mjs.map +1 -1
  80. package/fesm2022/joanroucoux-cairn-ui.mjs +0 -4
  81. package/package.json +17 -1
  82. package/styles/motion.css +1 -13
  83. package/styles/tokens.css +35 -64
  84. package/types/joanroucoux-cairn-ui-action-bar.d.ts +9 -14
  85. package/types/joanroucoux-cairn-ui-alert.d.ts +29 -15
  86. package/types/joanroucoux-cairn-ui-amount.d.ts +64 -32
  87. package/types/joanroucoux-cairn-ui-async.d.ts +85 -38
  88. package/types/joanroucoux-cairn-ui-avatar.d.ts +34 -22
  89. package/types/joanroucoux-cairn-ui-back-link.d.ts +20 -15
  90. package/types/joanroucoux-cairn-ui-badge.d.ts +22 -14
  91. package/types/joanroucoux-cairn-ui-button.d.ts +36 -18
  92. package/types/joanroucoux-cairn-ui-card.d.ts +48 -23
  93. package/types/joanroucoux-cairn-ui-choice-chips.d.ts +91 -35
  94. package/types/joanroucoux-cairn-ui-control.d.ts +9 -18
  95. package/types/joanroucoux-cairn-ui-delta.d.ts +46 -24
  96. package/types/joanroucoux-cairn-ui-dialog.d.ts +124 -57
  97. package/types/joanroucoux-cairn-ui-donut.d.ts +83 -46
  98. package/types/joanroucoux-cairn-ui-drawer.d.ts +73 -0
  99. package/types/joanroucoux-cairn-ui-empty.d.ts +20 -13
  100. package/types/joanroucoux-cairn-ui-external-link.d.ts +6 -10
  101. package/types/joanroucoux-cairn-ui-fact.d.ts +49 -25
  102. package/types/joanroucoux-cairn-ui-field.d.ts +72 -49
  103. package/types/joanroucoux-cairn-ui-filter-chips.d.ts +35 -20
  104. package/types/joanroucoux-cairn-ui-group-header.d.ts +58 -0
  105. package/types/joanroucoux-cairn-ui-input.d.ts +59 -37
  106. package/types/joanroucoux-cairn-ui-line-chart.d.ts +199 -89
  107. package/types/joanroucoux-cairn-ui-menu.d.ts +81 -44
  108. package/types/joanroucoux-cairn-ui-meter.d.ts +44 -22
  109. package/types/joanroucoux-cairn-ui-motion.d.ts +61 -75
  110. package/types/joanroucoux-cairn-ui-nav-item.d.ts +15 -13
  111. package/types/joanroucoux-cairn-ui-result-group.d.ts +52 -0
  112. package/types/joanroucoux-cairn-ui-row.d.ts +79 -37
  113. package/types/joanroucoux-cairn-ui-segmented.d.ts +51 -27
  114. package/types/joanroucoux-cairn-ui-select-pill.d.ts +52 -0
  115. package/types/joanroucoux-cairn-ui-select.d.ts +28 -18
  116. package/types/joanroucoux-cairn-ui-skeleton.d.ts +35 -18
  117. package/types/joanroucoux-cairn-ui-stale-link.d.ts +23 -16
  118. package/types/joanroucoux-cairn-ui-stat.d.ts +26 -21
  119. package/types/joanroucoux-cairn-ui-switch.d.ts +7 -11
  120. package/types/joanroucoux-cairn-ui-tab-bar.d.ts +20 -17
  121. package/types/joanroucoux-cairn-ui-table.d.ts +251 -89
  122. package/types/joanroucoux-cairn-ui-toast.d.ts +46 -36
  123. package/types/joanroucoux-cairn-ui.d.ts +1 -2
  124. package/fesm2022/joanroucoux-cairn-ui.mjs.map +0 -1
@@ -1,89 +1,167 @@
1
- import * as i0 from '@angular/core';
2
- import { input, model, Component } from '@angular/core';
3
-
4
- const CHIP_CLASSES = 'flex-none flex h-11 items-center rounded-pill border-0 bg-transparent p-0 font-[inherit] cursor-pointer transition-transform duration-(--duration-press) ease-out active:scale-(--press-scale) focus-visible:outline-2 focus-visible:-outline-offset-2 focus-visible:outline-(--ring) pointer-fine:h-8 pointer-fine:focus-visible:outline-offset-2';
5
- const PILL_CLASSES = 'flex h-[34px] items-center gap-1.5 rounded-pill px-3.5 text-label font-medium whitespace-nowrap pointer-fine:h-8 pointer-fine:px-3 pointer-fine:group-hover/chip:shadow-[inset_0_0_0_1px_var(--muted-foreground)]';
6
- const SELECTED_PILL_CLASSES = 'bg-(--primary) text-(--primary-foreground)';
7
- const UNSELECTED_PILL_CLASSES = 'bg-(--card) text-(--foreground) shadow-[inset_0_0_0_1px_var(--border)]';
8
- /**
9
- * A row of single-choice filter pills, each with an optional count, that narrows a list in place:
10
- * an asset class, a status. On touch it scrolls on one line, bleeding to the screen edges; with a
11
- * fine pointer it wraps.
12
- *
13
- * @example
14
- * <ui-filter-chips ariaLabel="Filter by class" [options]="classes()" [(value)]="selectedClass" />
15
- */
16
- class UiFilterChips {
17
- options = input.required(/* @ts-ignore */
18
- ...(ngDevMode ? [{ debugName: "options" }] : /* istanbul ignore next */ []));
19
- value = model.required(/* @ts-ignore */
20
- ...(ngDevMode ? [{ debugName: "value" }] : /* istanbul ignore next */ []));
21
- ariaLabel = input.required(/* @ts-ignore */
22
- ...(ngDevMode ? [{ debugName: "ariaLabel" }] : /* istanbul ignore next */ []));
23
- chipClasses = CHIP_CLASSES;
24
- pillClasses(optionValue) {
25
- return `${PILL_CLASSES} ${optionValue === this.value() ? SELECTED_PILL_CLASSES : UNSELECTED_PILL_CLASSES}`;
26
- }
27
- countClasses(optionValue) {
28
- return optionValue === this.value() ? 'text-(--primary-foreground)' : 'text-(--subtle-foreground)';
29
- }
30
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.1.7", ngImport: i0, type: UiFilterChips, deps: [], target: i0.ɵɵFactoryTarget.Component });
31
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.1.7", type: UiFilterChips, isStandalone: true, selector: "ui-filter-chips", inputs: { options: { classPropertyName: "options", publicName: "options", isSignal: true, isRequired: true, transformFunction: null }, value: { classPropertyName: "value", publicName: "value", isSignal: true, isRequired: true, transformFunction: null }, ariaLabel: { classPropertyName: "ariaLabel", publicName: "ariaLabel", isSignal: true, isRequired: true, transformFunction: null } }, outputs: { value: "valueChange" }, host: { attributes: { "role": "group" }, properties: { "attr.aria-label": "ariaLabel()" }, classAttribute: "flex gap-2 overflow-x-auto [scrollbar-width:none] -mt-1 -mx-(--gutter) px-(--gutter) pointer-fine:m-0 pointer-fine:flex-wrap pointer-fine:overflow-visible pointer-fine:p-0" }, ngImport: i0, template: `
32
- @for (option of options(); track option.value) {
33
- <button
34
- class="group/chip"
35
- type="button"
36
- [attr.aria-pressed]="option.value === value()"
37
- [class]="chipClasses"
38
- (click)="value.set(option.value)"
39
- >
40
- <span data-chip [class]="pillClasses(option.value)"
41
- >{{ option.label }}
42
- @if (option.count !== undefined && option.count !== null) {
43
- &ngsp;<span class="[font-variant-numeric:var(--numeric)]" data-count [class]="countClasses(option.value)">{{
44
- option.count
45
- }}</span>
46
- }
47
- </span>
48
- </button>
49
- }
50
- `, isInline: true });
51
- }
52
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.7", ngImport: i0, type: UiFilterChips, decorators: [{
53
- type: Component,
54
- args: [{
55
- selector: 'ui-filter-chips',
56
- template: `
57
- @for (option of options(); track option.value) {
58
- <button
59
- class="group/chip"
60
- type="button"
61
- [attr.aria-pressed]="option.value === value()"
62
- [class]="chipClasses"
63
- (click)="value.set(option.value)"
64
- >
65
- <span data-chip [class]="pillClasses(option.value)"
66
- >{{ option.label }}
67
- @if (option.count !== undefined && option.count !== null) {
68
- &ngsp;<span class="[font-variant-numeric:var(--numeric)]" data-count [class]="countClasses(option.value)">{{
69
- option.count
70
- }}</span>
71
- }
72
- </span>
73
- </button>
74
- }
1
+ import * as i0 from "@angular/core";
2
+ import { Component, input, model } from "@angular/core";
3
+ const CHIP_CLASSES = "flex-none flex h-11 items-center rounded-pill border-0 bg-transparent p-0 font-[inherit] cursor-pointer transition-transform duration-(--duration-press) ease-out active:scale-(--press-scale) focus-visible:outline-2 focus-visible:-outline-offset-2 focus-visible:outline-(--ring) pointer-fine:h-8 pointer-fine:focus-visible:outline-offset-2";
4
+ const PILL_CLASSES = "flex h-[34px] items-center gap-1.5 rounded-pill px-3.5 text-label font-medium whitespace-nowrap pointer-fine:h-8 pointer-fine:px-3 pointer-fine:group-hover/chip:shadow-[inset_0_0_0_1px_var(--muted-foreground)]";
5
+ const SELECTED_PILL_CLASSES = "bg-(--primary) text-(--primary-foreground)";
6
+ const UNSELECTED_PILL_CLASSES = "bg-(--card) text-(--foreground) shadow-[inset_0_0_0_1px_var(--border)]";
7
+ var UiFilterChips = class UiFilterChips {
8
+ options = input.required(...ngDevMode ? [{ debugName: "options" }] : /* istanbul ignore next */ []);
9
+ value = model.required(...ngDevMode ? [{ debugName: "value" }] : /* istanbul ignore next */ []);
10
+ ariaLabel = input.required(...ngDevMode ? [{ debugName: "ariaLabel" }] : /* istanbul ignore next */ []);
11
+ chipClasses = CHIP_CLASSES;
12
+ pillClasses(optionValue) {
13
+ return `${PILL_CLASSES} ${optionValue === this.value() ? SELECTED_PILL_CLASSES : UNSELECTED_PILL_CLASSES}`;
14
+ }
15
+ countClasses(optionValue) {
16
+ return optionValue === this.value() ? "text-(--primary-foreground)" : "text-(--subtle-foreground)";
17
+ }
18
+ static ɵfac = i0.ɵɵngDeclareFactory({
19
+ minVersion: "12.0.0",
20
+ version: "22.2.0",
21
+ ngImport: i0,
22
+ type: UiFilterChips,
23
+ deps: [],
24
+ target: i0.ɵɵFactoryTarget.Component
25
+ });
26
+ static ɵcmp = i0.ɵɵngDeclareComponent({
27
+ minVersion: "17.0.0",
28
+ version: "22.2.0",
29
+ type: UiFilterChips,
30
+ isStandalone: true,
31
+ selector: "ui-filter-chips",
32
+ inputs: {
33
+ options: {
34
+ classPropertyName: "options",
35
+ publicName: "options",
36
+ isSignal: true,
37
+ isRequired: true,
38
+ transformFunction: null
39
+ },
40
+ value: {
41
+ classPropertyName: "value",
42
+ publicName: "value",
43
+ isSignal: true,
44
+ isRequired: true,
45
+ transformFunction: null
46
+ },
47
+ ariaLabel: {
48
+ classPropertyName: "ariaLabel",
49
+ publicName: "ariaLabel",
50
+ isSignal: true,
51
+ isRequired: true,
52
+ transformFunction: null
53
+ }
54
+ },
55
+ outputs: { value: "valueChange" },
56
+ host: { classAttribute: "flex gap-2 overflow-x-auto [scrollbar-width:none] -mt-1 -mx-(--gutter) px-(--gutter) pointer-fine:m-0 pointer-fine:flex-wrap pointer-fine:overflow-visible pointer-fine:p-0" },
57
+ ngImport: i0,
58
+ template: `
59
+ <ng-content select="[uiChipsLeading]" />
60
+ <span
61
+ aria-hidden="true"
62
+ class="hidden h-5 w-px flex-none self-center bg-(--border) [[uiChipsLeading]+&]:block"
63
+ data-chips-rule
64
+ ></span>
65
+ <div class="contents" role="group" [attr.aria-label]="ariaLabel()">
66
+ @for (option of options(); track option.value) {
67
+ <button
68
+ class="group/chip"
69
+ type="button"
70
+ [attr.aria-pressed]="option.value === value()"
71
+ [class]="chipClasses"
72
+ (click)="value.set(option.value)"
73
+ >
74
+ <span data-chip [class]="pillClasses(option.value)"
75
+ >{{ option.label }}
76
+ @if (option.count !== undefined && option.count !== null) {
77
+ &ngsp;<span
78
+ class="[font-variant-numeric:var(--numeric)]"
79
+ data-count
80
+ [class]="countClasses(option.value)"
81
+ >{{ option.count }}</span
82
+ >
83
+ }
84
+ </span>
85
+ </button>
86
+ }
87
+ </div>
75
88
  `,
76
- host: {
77
- role: 'group',
78
- class: 'flex gap-2 overflow-x-auto [scrollbar-width:none] -mt-1 -mx-(--gutter) px-(--gutter) pointer-fine:m-0 pointer-fine:flex-wrap pointer-fine:overflow-visible pointer-fine:p-0',
79
- '[attr.aria-label]': 'ariaLabel()',
80
- },
81
- }]
82
- }], propDecorators: { options: [{ type: i0.Input, args: [{ isSignal: true, alias: "options", required: true }] }], value: [{ type: i0.Input, args: [{ isSignal: true, alias: "value", required: true }] }, { type: i0.Output, args: ["valueChange"] }], ariaLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "ariaLabel", required: true }] }] } });
83
-
84
- /**
85
- * Generated bundle index. Do not edit.
86
- */
87
-
89
+ isInline: true
90
+ });
91
+ };
92
+ i0.ɵɵngDeclareClassMetadata({
93
+ minVersion: "12.0.0",
94
+ version: "22.2.0",
95
+ ngImport: i0,
96
+ type: UiFilterChips,
97
+ decorators: [{
98
+ type: Component,
99
+ args: [{
100
+ selector: "ui-filter-chips",
101
+ template: `
102
+ <ng-content select="[uiChipsLeading]" />
103
+ <span
104
+ aria-hidden="true"
105
+ class="hidden h-5 w-px flex-none self-center bg-(--border) [[uiChipsLeading]+&]:block"
106
+ data-chips-rule
107
+ ></span>
108
+ <div class="contents" role="group" [attr.aria-label]="ariaLabel()">
109
+ @for (option of options(); track option.value) {
110
+ <button
111
+ class="group/chip"
112
+ type="button"
113
+ [attr.aria-pressed]="option.value === value()"
114
+ [class]="chipClasses"
115
+ (click)="value.set(option.value)"
116
+ >
117
+ <span data-chip [class]="pillClasses(option.value)"
118
+ >{{ option.label }}
119
+ @if (option.count !== undefined && option.count !== null) {
120
+ &ngsp;<span
121
+ class="[font-variant-numeric:var(--numeric)]"
122
+ data-count
123
+ [class]="countClasses(option.value)"
124
+ >{{ option.count }}</span
125
+ >
126
+ }
127
+ </span>
128
+ </button>
129
+ }
130
+ </div>
131
+ `,
132
+ host: { class: "flex gap-2 overflow-x-auto [scrollbar-width:none] -mt-1 -mx-(--gutter) px-(--gutter) pointer-fine:m-0 pointer-fine:flex-wrap pointer-fine:overflow-visible pointer-fine:p-0" }
133
+ }]
134
+ }],
135
+ propDecorators: {
136
+ options: [{
137
+ type: i0.Input,
138
+ args: [{
139
+ isSignal: true,
140
+ alias: "options",
141
+ required: true
142
+ }]
143
+ }],
144
+ value: [{
145
+ type: i0.Input,
146
+ args: [{
147
+ isSignal: true,
148
+ alias: "value",
149
+ required: true
150
+ }]
151
+ }, {
152
+ type: i0.Output,
153
+ args: ["valueChange"]
154
+ }],
155
+ ariaLabel: [{
156
+ type: i0.Input,
157
+ args: [{
158
+ isSignal: true,
159
+ alias: "ariaLabel",
160
+ required: true
161
+ }]
162
+ }]
163
+ }
164
+ });
88
165
  export { UiFilterChips };
89
- //# sourceMappingURL=joanroucoux-cairn-ui-filter-chips.mjs.map
166
+
167
+ //# sourceMappingURL=joanroucoux-cairn-ui-filter-chips.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"joanroucoux-cairn-ui-filter-chips.mjs","sources":["../../../projects/ui/filter-chips/filter-chips.ts","../../../projects/ui/filter-chips/joanroucoux-cairn-ui-filter-chips.ts"],"sourcesContent":["import { Component, input, model } from '@angular/core';\n\nexport type FilterChipOption = {\n value: string;\n label: string;\n count?: number | string | null;\n};\n\nconst CHIP_CLASSES =\n 'flex-none flex h-11 items-center rounded-pill border-0 bg-transparent p-0 font-[inherit] cursor-pointer transition-transform duration-(--duration-press) ease-out active:scale-(--press-scale) focus-visible:outline-2 focus-visible:-outline-offset-2 focus-visible:outline-(--ring) pointer-fine:h-8 pointer-fine:focus-visible:outline-offset-2';\n\nconst PILL_CLASSES =\n 'flex h-[34px] items-center gap-1.5 rounded-pill px-3.5 text-label font-medium whitespace-nowrap pointer-fine:h-8 pointer-fine:px-3 pointer-fine:group-hover/chip:shadow-[inset_0_0_0_1px_var(--muted-foreground)]';\n\nconst SELECTED_PILL_CLASSES = 'bg-(--primary) text-(--primary-foreground)';\n\nconst UNSELECTED_PILL_CLASSES = 'bg-(--card) text-(--foreground) shadow-[inset_0_0_0_1px_var(--border)]';\n\n/**\n * A row of single-choice filter pills, each with an optional count, that narrows a list in place:\n * an asset class, a status. On touch it scrolls on one line, bleeding to the screen edges; with a\n * fine pointer it wraps.\n *\n * @example\n * <ui-filter-chips ariaLabel=\"Filter by class\" [options]=\"classes()\" [(value)]=\"selectedClass\" />\n */\n@Component({\n selector: 'ui-filter-chips',\n template: `\n @for (option of options(); track option.value) {\n <button\n class=\"group/chip\"\n type=\"button\"\n [attr.aria-pressed]=\"option.value === value()\"\n [class]=\"chipClasses\"\n (click)=\"value.set(option.value)\"\n >\n <span data-chip [class]=\"pillClasses(option.value)\"\n >{{ option.label }}\n @if (option.count !== undefined && option.count !== null) {\n &ngsp;<span class=\"[font-variant-numeric:var(--numeric)]\" data-count [class]=\"countClasses(option.value)\">{{\n option.count\n }}</span>\n }\n </span>\n </button>\n }\n `,\n host: {\n role: 'group',\n class:\n 'flex gap-2 overflow-x-auto [scrollbar-width:none] -mt-1 -mx-(--gutter) px-(--gutter) pointer-fine:m-0 pointer-fine:flex-wrap pointer-fine:overflow-visible pointer-fine:p-0',\n '[attr.aria-label]': 'ariaLabel()',\n },\n})\nexport class UiFilterChips {\n readonly options = input.required<FilterChipOption[]>();\n readonly value = model.required<string>();\n readonly ariaLabel = input.required<string>();\n\n protected readonly chipClasses = CHIP_CLASSES;\n\n protected pillClasses(optionValue: string): string {\n return `${PILL_CLASSES} ${optionValue === this.value() ? SELECTED_PILL_CLASSES : UNSELECTED_PILL_CLASSES}`;\n }\n\n protected countClasses(optionValue: string): string {\n return optionValue === this.value() ? 'text-(--primary-foreground)' : 'text-(--subtle-foreground)';\n }\n}\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './index';\n"],"names":[],"mappings":";;;AAQA,MAAM,YAAY,GAChB,oVAAoV;AAEtV,MAAM,YAAY,GAChB,mNAAmN;AAErN,MAAM,qBAAqB,GAAG,4CAA4C;AAE1E,MAAM,uBAAuB,GAAG,wEAAwE;AAExG;;;;;;;AAOG;MA8BU,aAAa,CAAA;IACf,OAAO,GAAG,KAAK,CAAC,QAAQ;gFAAsB;IAC9C,KAAK,GAAG,KAAK,CAAC,QAAQ;8EAAU;IAChC,SAAS,GAAG,KAAK,CAAC,QAAQ;kFAAU;IAE1B,WAAW,GAAG,YAAY;AAEnC,IAAA,WAAW,CAAC,WAAmB,EAAA;AACvC,QAAA,OAAO,GAAG,YAAY,CAAA,CAAA,EAAI,WAAW,KAAK,IAAI,CAAC,KAAK,EAAE,GAAG,qBAAqB,GAAG,uBAAuB,EAAE;IAC5G;AAEU,IAAA,YAAY,CAAC,WAAmB,EAAA;AACxC,QAAA,OAAO,WAAW,KAAK,IAAI,CAAC,KAAK,EAAE,GAAG,6BAA6B,GAAG,4BAA4B;IACpG;uGAbW,aAAa,EAAA,IAAA,EAAA,EAAA,EAAA,MAAA,EAAA,EAAA,CAAA,eAAA,CAAA,SAAA,EAAA,CAAA;AAAb,IAAA,OAAA,IAAA,GAAA,EAAA,CAAA,oBAAA,CAAA,EAAA,UAAA,EAAA,QAAA,EAAA,OAAA,EAAA,QAAA,EAAA,IAAA,EAAA,aAAa,EAAA,YAAA,EAAA,IAAA,EAAA,QAAA,EAAA,iBAAA,EAAA,MAAA,EAAA,EAAA,OAAA,EAAA,EAAA,iBAAA,EAAA,SAAA,EAAA,UAAA,EAAA,SAAA,EAAA,QAAA,EAAA,IAAA,EAAA,UAAA,EAAA,IAAA,EAAA,iBAAA,EAAA,IAAA,EAAA,EAAA,KAAA,EAAA,EAAA,iBAAA,EAAA,OAAA,EAAA,UAAA,EAAA,OAAA,EAAA,QAAA,EAAA,IAAA,EAAA,UAAA,EAAA,IAAA,EAAA,iBAAA,EAAA,IAAA,EAAA,EAAA,SAAA,EAAA,EAAA,iBAAA,EAAA,WAAA,EAAA,UAAA,EAAA,WAAA,EAAA,QAAA,EAAA,IAAA,EAAA,UAAA,EAAA,IAAA,EAAA,iBAAA,EAAA,IAAA,EAAA,EAAA,EAAA,OAAA,EAAA,EAAA,KAAA,EAAA,aAAA,EAAA,EAAA,IAAA,EAAA,EAAA,UAAA,EAAA,EAAA,MAAA,EAAA,OAAA,EAAA,EAAA,UAAA,EAAA,EAAA,iBAAA,EAAA,aAAA,EAAA,EAAA,cAAA,EAAA,6KAAA,EAAA,EAAA,QAAA,EAAA,EAAA,EAAA,QAAA,EA3Bd;;;;;;;;;;;;;;;;;;;AAmBT,EAAA,CAAA,EAAA,QAAA,EAAA,IAAA,EAAA,CAAA;;2FAQU,aAAa,EAAA,UAAA,EAAA,CAAA;kBA7BzB,SAAS;AAAC,YAAA,IAAA,EAAA,CAAA;AACT,oBAAA,QAAQ,EAAE,iBAAiB;AAC3B,oBAAA,QAAQ,EAAE;;;;;;;;;;;;;;;;;;;AAmBT,EAAA,CAAA;AACD,oBAAA,IAAI,EAAE;AACJ,wBAAA,IAAI,EAAE,OAAO;AACb,wBAAA,KAAK,EACH,6KAA6K;AAC/K,wBAAA,mBAAmB,EAAE,aAAa;AACnC,qBAAA;AACF,iBAAA;;;ACtDD;;AAEG;;;;"}
1
+ {"version":3,"file":"joanroucoux-cairn-ui-filter-chips.mjs","names":[],"sources":["../../../projects/ui/filter-chips/filter-chips.ts"],"sourcesContent":["import { Component, input, model } from '@angular/core';\n\nexport type FilterChipOption = {\n value: string;\n label: string;\n count?: number | string | null;\n};\n\nconst CHIP_CLASSES =\n 'flex-none flex h-11 items-center rounded-pill border-0 bg-transparent p-0 font-[inherit] cursor-pointer transition-transform duration-(--duration-press) ease-out active:scale-(--press-scale) focus-visible:outline-2 focus-visible:-outline-offset-2 focus-visible:outline-(--ring) pointer-fine:h-8 pointer-fine:focus-visible:outline-offset-2';\n\nconst PILL_CLASSES =\n 'flex h-[34px] items-center gap-1.5 rounded-pill px-3.5 text-label font-medium whitespace-nowrap pointer-fine:h-8 pointer-fine:px-3 pointer-fine:group-hover/chip:shadow-[inset_0_0_0_1px_var(--muted-foreground)]';\n\nconst SELECTED_PILL_CLASSES = 'bg-(--primary) text-(--primary-foreground)';\n\nconst UNSELECTED_PILL_CLASSES = 'bg-(--card) text-(--foreground) shadow-[inset_0_0_0_1px_var(--border)]';\n\n/**\n * A row of single-choice filter pills, each with an optional count, that narrows a list in place.\n * On touch it scrolls on one line; with a fine pointer it wraps. An element marked `uiChipsLeading` is\n * projected first, outside the chips' group, followed by a vertical rule.\n *\n * @example\n * <ui-filter-chips ariaLabel=\"Filter by class\" [options]=\"classes()\" [(value)]=\"selectedClass\" />\n */\n@Component({\n selector: 'ui-filter-chips',\n template: `\n <ng-content select=\"[uiChipsLeading]\" />\n <span\n aria-hidden=\"true\"\n class=\"hidden h-5 w-px flex-none self-center bg-(--border) [[uiChipsLeading]+&]:block\"\n data-chips-rule\n ></span>\n <div class=\"contents\" role=\"group\" [attr.aria-label]=\"ariaLabel()\">\n @for (option of options(); track option.value) {\n <button\n class=\"group/chip\"\n type=\"button\"\n [attr.aria-pressed]=\"option.value === value()\"\n [class]=\"chipClasses\"\n (click)=\"value.set(option.value)\"\n >\n <span data-chip [class]=\"pillClasses(option.value)\"\n >{{ option.label }}\n @if (option.count !== undefined && option.count !== null) {\n &ngsp;<span\n class=\"[font-variant-numeric:var(--numeric)]\"\n data-count\n [class]=\"countClasses(option.value)\"\n >{{ option.count }}</span\n >\n }\n </span>\n </button>\n }\n </div>\n `,\n host: {\n class:\n 'flex gap-2 overflow-x-auto [scrollbar-width:none] -mt-1 -mx-(--gutter) px-(--gutter) pointer-fine:m-0 pointer-fine:flex-wrap pointer-fine:overflow-visible pointer-fine:p-0',\n },\n})\nexport class UiFilterChips {\n readonly options = input.required<FilterChipOption[]>();\n readonly value = model.required<string>();\n readonly ariaLabel = input.required<string>();\n\n protected readonly chipClasses = CHIP_CLASSES;\n\n protected pillClasses(optionValue: string): string {\n return `${PILL_CLASSES} ${optionValue === this.value() ? SELECTED_PILL_CLASSES : UNSELECTED_PILL_CLASSES}`;\n }\n\n protected countClasses(optionValue: string): string {\n return optionValue === this.value() ? 'text-(--primary-foreground)' : 'text-(--subtle-foreground)';\n }\n}\n"],"mappings":";;AAQA,MAAM,eACJ;AAEF,MAAM,eACJ;AAEF,MAAM,wBAAwB;AAE9B,MAAM,0BAA0B;AAgDhC,IAAa,gBAAb,MAAa,cAAa;CACf,UAAU,MAAM,SAA8B,GAAA,YAAA,CAAA,EAAA,WAAA,UAAA,CAAA,+BAAA,CAAA,CAAA;CAC9C,QAAQ,MAAM,SAAkB,GAAA,YAAA,CAAA,EAAA,WAAA,QAAA,CAAA,+BAAA,CAAA,CAAA;CAChC,YAAY,MAAM,SAAkB,GAAA,YAAA,CAAA,EAAA,WAAA,YAAA,CAAA,+BAAA,CAAA,CAAA;CAE1B,cAAc;CAEvB,YAAY,aAAmB;EACvC,OAAO,GAAG,aAAY,GAAI,gBAAgB,KAAK,MAAK,IAAK,wBAAwB;CACnF;CAEU,aAAa,aAAmB;EACxC,OAAO,gBAAgB,KAAK,MAAK,IAAK,gCAAgC;CACxE;CAbW,OAAA,OAAA,GAAA,mBAAA;EAAA,YAAA;EAAA,SAAA;EAAA,UAAA;EAAA,MAAA;EAAa,MAAA,CAAA;EAAA,QAAA,GAAA,gBAAA;CAAA,CAAA;CAAb,OAAA,OAAA,GAAA,qBAAA;EAAA,YAAA;EAAA,SAAA;EAAA,MAAA;EAAa,cAAA;EAAA,UAAA;EAAA,QAAA;GAAA,SAAA;IAAA,mBAAA;IAAA,YAAA;IAAA,UAAA;IAAA,YAAA;IAAA,mBAAA;GAAA;GAAA,OAAA;IAAA,mBAAA;IAAA,YAAA;IAAA,UAAA;IAAA,YAAA;IAAA,mBAAA;GAAA;GAAA,WAAA;IAAA,mBAAA;IAAA,YAAA;IAAA,UAAA;IAAA,YAAA;IAAA,mBAAA;GAAA;EAAA;EAAA,SAAA,EAAA,OAAA,cAAA;EAAA,MAAA,EAAA,gBAAA,8KAAA;EAAA,UAAA;EAAA,UApCd;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EA8BT,UAAA;CAAA,CAAA;;AAMU,GAAA,yBAAA;CAAA,YAAA;CAAA,SAAA;CAAA,UAAA;CAAA,MAAA;CAAa,YAAA,CAAA;EAtCzB,MAAA;EAAU,MAAA,CAAA;GACT,UAAU;GACV,UAAU;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA+BV,MAAM,EACJ,OACE,8KACH;EACF,CAAA"}
@@ -0,0 +1,269 @@
1
+ import { NgTemplateOutlet } from "@angular/common";
2
+ import * as i0 from "@angular/core";
3
+ import { Component, booleanAttribute, input, model } from "@angular/core";
4
+ var UiGroupHeader = class UiGroupHeader {
5
+ name = input.required(...ngDevMode ? [{ debugName: "name" }] : /* istanbul ignore next */ []);
6
+ meta = input(...ngDevMode ? [void 0, { debugName: "meta" }] : /* istanbul ignore next */ []);
7
+ collapsible = input(false, {
8
+ ...ngDevMode ? { debugName: "collapsible" } : /* istanbul ignore next */ {},
9
+ transform: booleanAttribute
10
+ });
11
+ expanded = model(true, ...ngDevMode ? [{ debugName: "expanded" }] : /* istanbul ignore next */ []);
12
+ toggleDisabled = input(false, {
13
+ ...ngDevMode ? { debugName: "toggleDisabled" } : /* istanbul ignore next */ {},
14
+ transform: booleanAttribute
15
+ });
16
+ controls = input(...ngDevMode ? [void 0, { debugName: "controls" }] : /* istanbul ignore next */ []);
17
+ toggle() {
18
+ if (!this.toggleDisabled()) this.expanded.update((expanded) => !expanded);
19
+ }
20
+ static ɵfac = i0.ɵɵngDeclareFactory({
21
+ minVersion: "12.0.0",
22
+ version: "22.2.0",
23
+ ngImport: i0,
24
+ type: UiGroupHeader,
25
+ deps: [],
26
+ target: i0.ɵɵFactoryTarget.Component
27
+ });
28
+ static ɵcmp = i0.ɵɵngDeclareComponent({
29
+ minVersion: "17.0.0",
30
+ version: "22.2.0",
31
+ type: UiGroupHeader,
32
+ isStandalone: true,
33
+ selector: "ui-group-header",
34
+ inputs: {
35
+ name: {
36
+ classPropertyName: "name",
37
+ publicName: "name",
38
+ isSignal: true,
39
+ isRequired: true,
40
+ transformFunction: null
41
+ },
42
+ meta: {
43
+ classPropertyName: "meta",
44
+ publicName: "meta",
45
+ isSignal: true,
46
+ isRequired: false,
47
+ transformFunction: null
48
+ },
49
+ collapsible: {
50
+ classPropertyName: "collapsible",
51
+ publicName: "collapsible",
52
+ isSignal: true,
53
+ isRequired: false,
54
+ transformFunction: null
55
+ },
56
+ expanded: {
57
+ classPropertyName: "expanded",
58
+ publicName: "expanded",
59
+ isSignal: true,
60
+ isRequired: false,
61
+ transformFunction: null
62
+ },
63
+ toggleDisabled: {
64
+ classPropertyName: "toggleDisabled",
65
+ publicName: "toggleDisabled",
66
+ isSignal: true,
67
+ isRequired: false,
68
+ transformFunction: null
69
+ },
70
+ controls: {
71
+ classPropertyName: "controls",
72
+ publicName: "controls",
73
+ isSignal: true,
74
+ isRequired: false,
75
+ transformFunction: null
76
+ }
77
+ },
78
+ outputs: { expanded: "expandedChange" },
79
+ host: { classAttribute: "block" },
80
+ ngImport: i0,
81
+ template: `
82
+ <ng-template #total><ng-content /></ng-template>
83
+ @if (collapsible()) {
84
+ <h2 class="m-0 font-normal">
85
+ <button
86
+ class="rounded-control flex min-h-11 w-full items-end justify-between gap-3 px-1 pt-3 text-left transition-transform [transition-duration:var(--duration-press)] ease-out not-aria-disabled:cursor-pointer focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-(--ring) not-aria-disabled:active:scale-(--press-scale)"
87
+ type="button"
88
+ [attr.aria-controls]="controls() || null"
89
+ [attr.aria-disabled]="toggleDisabled() ? 'true' : null"
90
+ [attr.aria-expanded]="expanded()"
91
+ (click)="toggle()"
92
+ >
93
+ <span class="flex min-w-0 items-center gap-2">
94
+ <svg
95
+ aria-hidden="true"
96
+ class="flex-none stroke-(--muted-foreground) transition-transform duration-(--duration-fast) ease-out"
97
+ fill="none"
98
+ height="20"
99
+ stroke-linecap="round"
100
+ stroke-linejoin="round"
101
+ stroke-width="1.75"
102
+ viewBox="0 0 24 24"
103
+ width="20"
104
+ [class.-rotate-90]="!expanded()"
105
+ >
106
+ <path d="m6 9 6 6 6-6" />
107
+ </svg>
108
+ <span class="flex min-w-0 flex-col">
109
+ <span class="text-title font-semibold">{{ name() }}</span>
110
+ @if (meta()) {
111
+ <span class="text-label text-(--muted-foreground)">{{ meta() }}</span>
112
+ }
113
+ </span>
114
+ </span>
115
+ <span class="text-title font-semibold whitespace-nowrap tabular-nums">
116
+ <ng-container [ngTemplateOutlet]="total" />
117
+ </span>
118
+ </button>
119
+ </h2>
120
+ } @else {
121
+ <div class="flex min-h-11 w-full items-end justify-between gap-3 px-1 pt-3">
122
+ <div class="flex min-w-0 flex-col">
123
+ <h2 class="text-title m-0 font-semibold">{{ name() }}</h2>
124
+ @if (meta()) {
125
+ <span class="text-label text-(--muted-foreground)">{{ meta() }}</span>
126
+ }
127
+ </div>
128
+ <span class="text-title font-semibold whitespace-nowrap tabular-nums">
129
+ <ng-container [ngTemplateOutlet]="total" />
130
+ </span>
131
+ </div>
132
+ }
133
+ `,
134
+ isInline: true,
135
+ dependencies: [{
136
+ kind: "directive",
137
+ type: NgTemplateOutlet,
138
+ selector: "[ngTemplateOutlet]",
139
+ inputs: [
140
+ "ngTemplateOutletContext",
141
+ "ngTemplateOutlet",
142
+ "ngTemplateOutletInjector"
143
+ ]
144
+ }]
145
+ });
146
+ };
147
+ i0.ɵɵngDeclareClassMetadata({
148
+ minVersion: "12.0.0",
149
+ version: "22.2.0",
150
+ ngImport: i0,
151
+ type: UiGroupHeader,
152
+ decorators: [{
153
+ type: Component,
154
+ args: [{
155
+ selector: "ui-group-header",
156
+ imports: [NgTemplateOutlet],
157
+ host: { class: "block" },
158
+ template: `
159
+ <ng-template #total><ng-content /></ng-template>
160
+ @if (collapsible()) {
161
+ <h2 class="m-0 font-normal">
162
+ <button
163
+ class="rounded-control flex min-h-11 w-full items-end justify-between gap-3 px-1 pt-3 text-left transition-transform [transition-duration:var(--duration-press)] ease-out not-aria-disabled:cursor-pointer focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-(--ring) not-aria-disabled:active:scale-(--press-scale)"
164
+ type="button"
165
+ [attr.aria-controls]="controls() || null"
166
+ [attr.aria-disabled]="toggleDisabled() ? 'true' : null"
167
+ [attr.aria-expanded]="expanded()"
168
+ (click)="toggle()"
169
+ >
170
+ <span class="flex min-w-0 items-center gap-2">
171
+ <svg
172
+ aria-hidden="true"
173
+ class="flex-none stroke-(--muted-foreground) transition-transform duration-(--duration-fast) ease-out"
174
+ fill="none"
175
+ height="20"
176
+ stroke-linecap="round"
177
+ stroke-linejoin="round"
178
+ stroke-width="1.75"
179
+ viewBox="0 0 24 24"
180
+ width="20"
181
+ [class.-rotate-90]="!expanded()"
182
+ >
183
+ <path d="m6 9 6 6 6-6" />
184
+ </svg>
185
+ <span class="flex min-w-0 flex-col">
186
+ <span class="text-title font-semibold">{{ name() }}</span>
187
+ @if (meta()) {
188
+ <span class="text-label text-(--muted-foreground)">{{ meta() }}</span>
189
+ }
190
+ </span>
191
+ </span>
192
+ <span class="text-title font-semibold whitespace-nowrap tabular-nums">
193
+ <ng-container [ngTemplateOutlet]="total" />
194
+ </span>
195
+ </button>
196
+ </h2>
197
+ } @else {
198
+ <div class="flex min-h-11 w-full items-end justify-between gap-3 px-1 pt-3">
199
+ <div class="flex min-w-0 flex-col">
200
+ <h2 class="text-title m-0 font-semibold">{{ name() }}</h2>
201
+ @if (meta()) {
202
+ <span class="text-label text-(--muted-foreground)">{{ meta() }}</span>
203
+ }
204
+ </div>
205
+ <span class="text-title font-semibold whitespace-nowrap tabular-nums">
206
+ <ng-container [ngTemplateOutlet]="total" />
207
+ </span>
208
+ </div>
209
+ }
210
+ `
211
+ }]
212
+ }],
213
+ propDecorators: {
214
+ name: [{
215
+ type: i0.Input,
216
+ args: [{
217
+ isSignal: true,
218
+ alias: "name",
219
+ required: true
220
+ }]
221
+ }],
222
+ meta: [{
223
+ type: i0.Input,
224
+ args: [{
225
+ isSignal: true,
226
+ alias: "meta",
227
+ required: false
228
+ }]
229
+ }],
230
+ collapsible: [{
231
+ type: i0.Input,
232
+ args: [{
233
+ isSignal: true,
234
+ alias: "collapsible",
235
+ required: false
236
+ }]
237
+ }],
238
+ expanded: [{
239
+ type: i0.Input,
240
+ args: [{
241
+ isSignal: true,
242
+ alias: "expanded",
243
+ required: false
244
+ }]
245
+ }, {
246
+ type: i0.Output,
247
+ args: ["expandedChange"]
248
+ }],
249
+ toggleDisabled: [{
250
+ type: i0.Input,
251
+ args: [{
252
+ isSignal: true,
253
+ alias: "toggleDisabled",
254
+ required: false
255
+ }]
256
+ }],
257
+ controls: [{
258
+ type: i0.Input,
259
+ args: [{
260
+ isSignal: true,
261
+ alias: "controls",
262
+ required: false
263
+ }]
264
+ }]
265
+ }
266
+ });
267
+ export { UiGroupHeader };
268
+
269
+ //# sourceMappingURL=joanroucoux-cairn-ui-group-header.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"joanroucoux-cairn-ui-group-header.mjs","names":[],"sources":["../../../projects/ui/group-header/group-header.ts"],"sourcesContent":["import { NgTemplateOutlet } from '@angular/common';\nimport { Component, booleanAttribute, input, model } from '@angular/core';\n\n/**\n * Header of a card on a phone: the name, its meta underneath, the projected total on the right.\n *\n * With `collapsible` the header is a button inside the heading, with a chevron that turns when the\n * group is folded and a press scale. `expanded` is a model: the page keeps the fold memory and hides\n * the card body itself. `toggleDisabled` keeps the button focusable and announced, but a click\n * changes nothing (a filter holds the group open). `controls` is the id of the body it folds.\n *\n * @example\n * <ui-group-header name=\"Northwind PEA\" meta=\"PEA · 3 lignes\" collapsible [(expanded)]=\"open\">\n * <ui-amount [value]=\"total\" />\n * </ui-group-header>\n */\n@Component({\n selector: 'ui-group-header',\n imports: [NgTemplateOutlet],\n host: { class: 'block' },\n template: `\n <ng-template #total><ng-content /></ng-template>\n @if (collapsible()) {\n <h2 class=\"m-0 font-normal\">\n <button\n class=\"rounded-control flex min-h-11 w-full items-end justify-between gap-3 px-1 pt-3 text-left transition-transform [transition-duration:var(--duration-press)] ease-out not-aria-disabled:cursor-pointer focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-(--ring) not-aria-disabled:active:scale-(--press-scale)\"\n type=\"button\"\n [attr.aria-controls]=\"controls() || null\"\n [attr.aria-disabled]=\"toggleDisabled() ? 'true' : null\"\n [attr.aria-expanded]=\"expanded()\"\n (click)=\"toggle()\"\n >\n <span class=\"flex min-w-0 items-center gap-2\">\n <svg\n aria-hidden=\"true\"\n class=\"flex-none stroke-(--muted-foreground) transition-transform duration-(--duration-fast) ease-out\"\n fill=\"none\"\n height=\"20\"\n stroke-linecap=\"round\"\n stroke-linejoin=\"round\"\n stroke-width=\"1.75\"\n viewBox=\"0 0 24 24\"\n width=\"20\"\n [class.-rotate-90]=\"!expanded()\"\n >\n <path d=\"m6 9 6 6 6-6\" />\n </svg>\n <span class=\"flex min-w-0 flex-col\">\n <span class=\"text-title font-semibold\">{{ name() }}</span>\n @if (meta()) {\n <span class=\"text-label text-(--muted-foreground)\">{{ meta() }}</span>\n }\n </span>\n </span>\n <span class=\"text-title font-semibold whitespace-nowrap tabular-nums\">\n <ng-container [ngTemplateOutlet]=\"total\" />\n </span>\n </button>\n </h2>\n } @else {\n <div class=\"flex min-h-11 w-full items-end justify-between gap-3 px-1 pt-3\">\n <div class=\"flex min-w-0 flex-col\">\n <h2 class=\"text-title m-0 font-semibold\">{{ name() }}</h2>\n @if (meta()) {\n <span class=\"text-label text-(--muted-foreground)\">{{ meta() }}</span>\n }\n </div>\n <span class=\"text-title font-semibold whitespace-nowrap tabular-nums\">\n <ng-container [ngTemplateOutlet]=\"total\" />\n </span>\n </div>\n }\n `,\n})\nexport class UiGroupHeader {\n readonly name = input.required<string>();\n readonly meta = input<string>();\n readonly collapsible = input(false, { transform: booleanAttribute });\n readonly expanded = model(true);\n readonly toggleDisabled = input(false, { transform: booleanAttribute });\n readonly controls = input<string>();\n\n protected toggle(): void {\n if (!this.toggleDisabled()) {\n this.expanded.update((expanded) => !expanded);\n }\n }\n}\n"],"mappings":";;;AA0EA,IAAa,gBAAb,MAAa,cAAa;CACf,OAAO,MAAM,SAAkB,GAAA,YAAA,CAAA,EAAA,WAAA,OAAA,CAAA,+BAAA,CAAA,CAAA;CAC/B,OAAO,MAAe,GAAA,YAAA,CAAA,QAAA,EAAA,WAAA,OAAA,CAAA,+BAAA,CAAA,CAAA;CACtB,cAAc,MAAM,OAAK;EAAA,GAAA,YAAA,EAAA,WAAA,cAAA,+BAAA,CAAA;EAAI,WAAW;CAAgB,CAAA;CACxD,WAAW,MAAM,MAAK,GAAA,YAAA,CAAA,EAAA,WAAA,WAAA,CAAA,+BAAA,CAAA,CAAA;CACtB,iBAAiB,MAAM,OAAK;EAAA,GAAA,YAAA,EAAA,WAAA,iBAAA,+BAAA,CAAA;EAAI,WAAW;CAAgB,CAAA;CAC3D,WAAW,MAAe,GAAA,YAAA,CAAA,QAAA,EAAA,WAAA,WAAA,CAAA,+BAAA,CAAA,CAAA;CAEzB,SAAM;EACd,IAAI,CAAC,KAAK,eAAc,GACtB,KAAK,SAAS,QAAQ,aAAa,CAAC,QAAQ;CAEhD;CAZW,OAAA,OAAA,GAAA,mBAAA;EAAA,YAAA;EAAA,SAAA;EAAA,UAAA;EAAA,MAAA;EAAa,MAAA,CAAA;EAAA,QAAA,GAAA,gBAAA;CAAA,CAAA;CAAb,OAAA,OAAA,GAAA,qBAAA;EAAA,YAAA;EAAA,SAAA;EAAA,MAAA;EAAa,cAAA;EAAA,UAAA;EAAA,QAAA;GAAA,MAAA;IAAA,mBAAA;IAAA,YAAA;IAAA,UAAA;IAAA,YAAA;IAAA,mBAAA;GAAA;GAAA,MAAA;IAAA,mBAAA;IAAA,YAAA;IAAA,UAAA;IAAA,YAAA;IAAA,mBAAA;GAAA;GAAA,aAAA;IAAA,mBAAA;IAAA,YAAA;IAAA,UAAA;IAAA,YAAA;IAAA,mBAAA;GAAA;GAAA,UAAA;IAAA,mBAAA;IAAA,YAAA;IAAA,UAAA;IAAA,YAAA;IAAA,mBAAA;GAAA;GAAA,gBAAA;IAAA,mBAAA;IAAA,YAAA;IAAA,UAAA;IAAA,YAAA;IAAA,mBAAA;GAAA;GAAA,UAAA;IAAA,mBAAA;IAAA,YAAA;IAAA,UAAA;IAAA,YAAA;IAAA,mBAAA;GAAA;EAAA;EAAA,SAAA,EAAA,UAAA,iBAAA;EAAA,MAAA,EAAA,gBAAA,QAAA;EAAA,UAAA;EAAA,UAtDd;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EAoDT,UAAA;EAAA,cAAA,CAAA;GAAA,MAAA;GAAA,MAtDS;GAAgB,UAAA;GAAA,QAAA;IAAA;IAAA;IAAA;GAAA;EAAA,CAAA;CAAA,CAAA;;AAwDf,GAAA,yBAAA;CAAA,YAAA;CAAA,SAAA;CAAA,UAAA;CAAA,MAAA;CAAa,YAAA,CAAA;EA1DzB,MAAA;EAAU,MAAA,CAAA;GACT,UAAU;GACV,SAAS,CAAC,gBAAgB;GAC1B,MAAM,EAAE,OAAO,QAAO;GACtB,UAAU;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EAqDX,CAAA"}