codexly-ui 0.1.20 → 0.1.22
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/assets/fonts/roboto-bold-italic.ttf +0 -0
- package/assets/fonts/roboto-bold.ttf +0 -0
- package/assets/fonts/roboto-italic.ttf +0 -0
- package/assets/fonts/roboto-light-italic.ttf +0 -0
- package/assets/fonts/roboto-light.ttf +0 -0
- package/assets/fonts/roboto-medium-italic.ttf +0 -0
- package/assets/fonts/roboto-medium.ttf +0 -0
- package/assets/fonts/roboto-regular.ttf +0 -0
- package/assets/fonts/roboto-semibold-italic.ttf +0 -0
- package/assets/fonts/roboto-semibold.ttf +0 -0
- package/assets/styles/_fonts.css +84 -3
- package/assets/styles/_globals.css +34 -43
- package/assets/styles/_safelist.css +22 -3
- package/assets/styles/_theme.css +86 -96
- package/fesm2022/codexly-ui.mjs +1317 -1674
- package/fesm2022/codexly-ui.mjs.map +1 -1
- package/package.json +1 -1
- package/types/codexly-ui.d.ts +25 -60
package/fesm2022/codexly-ui.mjs
CHANGED
|
@@ -7,7 +7,7 @@ import { toSignal, takeUntilDestroyed } from '@angular/core/rxjs-interop';
|
|
|
7
7
|
import { startWith, map, debounceTime, distinctUntilChanged, switchMap, of, catchError } from 'rxjs';
|
|
8
8
|
import * as i1$1 from '@angular/cdk/overlay';
|
|
9
9
|
import { ScrollStrategyOptions, OverlayModule } from '@angular/cdk/overlay';
|
|
10
|
-
import { ScrollingModule } from '@angular/cdk/scrolling';
|
|
10
|
+
import { ScrollingModule, CdkScrollable } from '@angular/cdk/scrolling';
|
|
11
11
|
import { Chart, LineController, BarController, PieController, DoughnutController, RadarController, PolarAreaController, CategoryScale, LinearScale, RadialLinearScale, BarElement, LineElement, PointElement, ArcElement, Filler, Tooltip, Legend } from 'chart.js';
|
|
12
12
|
import { RouterLink, RouterLinkActive } from '@angular/router';
|
|
13
13
|
|
|
@@ -165,163 +165,6 @@ const BADGE_SHAPE_FIXED = {
|
|
|
165
165
|
circle: 'rounded-full',
|
|
166
166
|
};
|
|
167
167
|
|
|
168
|
-
const CLX_FONT_CATALOG = [
|
|
169
|
-
{
|
|
170
|
-
label: 'Roboto',
|
|
171
|
-
value: 'Roboto',
|
|
172
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Roboto:ital,wght@0,300;0,400;0,500;0,600;0,700;1,300;1,400;1,500;1,600;1,700&display=swap',
|
|
173
|
-
},
|
|
174
|
-
{
|
|
175
|
-
label: 'Inter',
|
|
176
|
-
value: 'Inter',
|
|
177
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Inter:ital,wght@0,300;0,400;0,500;0,600;0,700;1,300;1,400;1,500;1,600;1,700&display=swap',
|
|
178
|
-
},
|
|
179
|
-
{
|
|
180
|
-
label: 'Poppins',
|
|
181
|
-
value: 'Poppins',
|
|
182
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Poppins:ital,wght@0,300;0,400;0,500;0,600;0,700;1,300;1,400;1,500;1,600;1,700&display=swap',
|
|
183
|
-
},
|
|
184
|
-
{
|
|
185
|
-
label: 'Plus Jakarta Sans',
|
|
186
|
-
value: 'Plus Jakarta Sans',
|
|
187
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Plus+Jakarta+Sans:ital,wght@0,300;0,400;0,500;0,600;0,700;1,300;1,400;1,500;1,600;1,700&display=swap',
|
|
188
|
-
},
|
|
189
|
-
{
|
|
190
|
-
label: 'Nunito',
|
|
191
|
-
value: 'Nunito',
|
|
192
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Nunito:ital,wght@0,300;0,400;0,500;0,600;0,700;1,300;1,400;1,500;1,600;1,700&display=swap',
|
|
193
|
-
},
|
|
194
|
-
{
|
|
195
|
-
label: 'DM Sans',
|
|
196
|
-
value: 'DM Sans',
|
|
197
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=DM+Sans:ital,wght@0,300;0,400;0,500;0,600;0,700;1,300;1,400;1,500;1,600;1,700&display=swap',
|
|
198
|
-
},
|
|
199
|
-
{
|
|
200
|
-
label: 'Geist',
|
|
201
|
-
value: 'Geist',
|
|
202
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Geist:wght@300;400;500;600;700&display=swap',
|
|
203
|
-
},
|
|
204
|
-
{
|
|
205
|
-
label: 'Lato',
|
|
206
|
-
value: 'Lato',
|
|
207
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Lato:ital,wght@0,300;0,400;0,700;1,300;1,400;1,700&display=swap',
|
|
208
|
-
},
|
|
209
|
-
{
|
|
210
|
-
label: 'Montserrat',
|
|
211
|
-
value: 'Montserrat',
|
|
212
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Montserrat:ital,wght@0,300;0,400;0,500;0,600;0,700;1,300;1,400;1,500;1,600;1,700&display=swap',
|
|
213
|
-
},
|
|
214
|
-
{
|
|
215
|
-
label: 'Open Sans',
|
|
216
|
-
value: 'Open Sans',
|
|
217
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Open+Sans:ital,wght@0,300;0,400;0,500;0,600;0,700;1,300;1,400;1,500;1,600;1,700&display=swap',
|
|
218
|
-
},
|
|
219
|
-
{
|
|
220
|
-
label: 'Work Sans',
|
|
221
|
-
value: 'Work Sans',
|
|
222
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Work+Sans:ital,wght@0,300;0,400;0,500;0,600;0,700;1,300;1,400;1,500;1,600;1,700&display=swap',
|
|
223
|
-
},
|
|
224
|
-
{
|
|
225
|
-
label: 'Manrope',
|
|
226
|
-
value: 'Manrope',
|
|
227
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Manrope:wght@300;400;500;600;700&display=swap',
|
|
228
|
-
},
|
|
229
|
-
{
|
|
230
|
-
label: 'Sora',
|
|
231
|
-
value: 'Sora',
|
|
232
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Sora:wght@300;400;500;600;700&display=swap',
|
|
233
|
-
},
|
|
234
|
-
{
|
|
235
|
-
label: 'Outfit',
|
|
236
|
-
value: 'Outfit',
|
|
237
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Outfit:wght@300;400;500;600;700&display=swap',
|
|
238
|
-
},
|
|
239
|
-
{
|
|
240
|
-
label: 'Rubik',
|
|
241
|
-
value: 'Rubik',
|
|
242
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Rubik:ital,wght@0,300;0,400;0,500;0,600;0,700;1,300;1,400;1,500;1,600;1,700&display=swap',
|
|
243
|
-
},
|
|
244
|
-
{
|
|
245
|
-
label: 'Source Sans 3',
|
|
246
|
-
value: 'Source Sans 3',
|
|
247
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Source+Sans+3:ital,wght@0,300;0,400;0,500;0,600;0,700;1,300;1,400;1,500;1,600;1,700&display=swap',
|
|
248
|
-
},
|
|
249
|
-
{
|
|
250
|
-
label: 'Space Grotesk',
|
|
251
|
-
value: 'Space Grotesk',
|
|
252
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Space+Grotesk:wght@300;400;500;600;700&display=swap',
|
|
253
|
-
},
|
|
254
|
-
{
|
|
255
|
-
label: 'Merriweather',
|
|
256
|
-
value: 'Merriweather',
|
|
257
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Merriweather:ital,wght@0,300;0,400;0,700;0,900;1,300;1,400;1,700;1,900&display=swap',
|
|
258
|
-
},
|
|
259
|
-
{
|
|
260
|
-
label: 'Playfair Display',
|
|
261
|
-
value: 'Playfair Display',
|
|
262
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Playfair+Display:ital,wght@0,400;0,500;0,600;0,700;0,800;0,900;1,400;1,500;1,600;1,700;1,800;1,900&display=swap',
|
|
263
|
-
},
|
|
264
|
-
{
|
|
265
|
-
label: 'Lora',
|
|
266
|
-
value: 'Lora',
|
|
267
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Lora:ital,wght@0,400;0,500;0,600;0,700;1,400;1,500;1,600;1,700&display=swap',
|
|
268
|
-
},
|
|
269
|
-
{
|
|
270
|
-
label: 'PT Serif',
|
|
271
|
-
value: 'PT Serif',
|
|
272
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=PT+Serif:ital,wght@0,400;0,700;1,400;1,700&display=swap',
|
|
273
|
-
},
|
|
274
|
-
{
|
|
275
|
-
label: 'Caveat',
|
|
276
|
-
value: 'Caveat',
|
|
277
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Caveat:wght@400;500;600;700&display=swap',
|
|
278
|
-
},
|
|
279
|
-
{
|
|
280
|
-
label: 'Dancing Script',
|
|
281
|
-
value: 'Dancing Script',
|
|
282
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Dancing+Script:wght@400;500;600;700&display=swap',
|
|
283
|
-
},
|
|
284
|
-
{
|
|
285
|
-
label: 'Cinzel',
|
|
286
|
-
value: 'Cinzel',
|
|
287
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Cinzel:wght@400;500;600;700;800;900&display=swap',
|
|
288
|
-
},
|
|
289
|
-
{
|
|
290
|
-
label: 'Berkshire Swash',
|
|
291
|
-
value: 'Berkshire Swash',
|
|
292
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Berkshire+Swash&display=swap',
|
|
293
|
-
},
|
|
294
|
-
{
|
|
295
|
-
label: 'JetBrains Mono',
|
|
296
|
-
value: 'JetBrains Mono',
|
|
297
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=JetBrains+Mono:ital,wght@0,400;0,500;0,600;0,700;1,400;1,500;1,600;1,700&display=swap',
|
|
298
|
-
},
|
|
299
|
-
{
|
|
300
|
-
label: 'Orbitron',
|
|
301
|
-
value: 'Orbitron',
|
|
302
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Orbitron:wght@400;500;600;700;800;900&display=swap',
|
|
303
|
-
},
|
|
304
|
-
{
|
|
305
|
-
label: 'UnifrakturMaguntia',
|
|
306
|
-
value: 'UnifrakturMaguntia',
|
|
307
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=UnifrakturMaguntia&display=swap',
|
|
308
|
-
},
|
|
309
|
-
{
|
|
310
|
-
label: 'Pirata One',
|
|
311
|
-
value: 'Pirata One',
|
|
312
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Pirata+One&display=swap',
|
|
313
|
-
},
|
|
314
|
-
{
|
|
315
|
-
label: 'Press Start 2P',
|
|
316
|
-
value: 'Press Start 2P',
|
|
317
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Press+Start+2P&display=swap',
|
|
318
|
-
},
|
|
319
|
-
{
|
|
320
|
-
label: 'Bungee',
|
|
321
|
-
value: 'Bungee',
|
|
322
|
-
googleUrl: 'https://fonts.googleapis.com/css2?family=Bungee&display=swap',
|
|
323
|
-
},
|
|
324
|
-
];
|
|
325
168
|
// ── Tailwind rounded classes per borderRadius token ───────────────────────────
|
|
326
169
|
const CLX_RADIUS_MAP = {
|
|
327
170
|
none: 'rounded-none',
|
|
@@ -351,16 +194,13 @@ function resolveContainerRadius(r) {
|
|
|
351
194
|
// ── Default theme ─────────────────────────────────────────────────────────────
|
|
352
195
|
const CLX_THEME_DEFAULTS = {
|
|
353
196
|
primaryColor: 'indigo',
|
|
354
|
-
secondaryColor: 'slate',
|
|
355
197
|
dangerColor: 'red',
|
|
356
198
|
successColor: 'green',
|
|
357
199
|
warningColor: 'amber',
|
|
358
200
|
neutralColor: 'slate',
|
|
359
|
-
textColor: 'slate',
|
|
360
201
|
borderRadius: 'md',
|
|
361
202
|
defaultSize: 'md',
|
|
362
203
|
defaultShape: 'rounded',
|
|
363
|
-
fontFamily: 'Roboto',
|
|
364
204
|
};
|
|
365
205
|
// ── Injection token ───────────────────────────────────────────────────────────
|
|
366
206
|
const CLX_THEME_CONFIG = new InjectionToken('CLX_THEME_CONFIG', { factory: () => CLX_THEME_DEFAULTS });
|
|
@@ -372,107 +212,7 @@ function provideCodexlyTheme(config) {
|
|
|
372
212
|
};
|
|
373
213
|
}
|
|
374
214
|
|
|
375
|
-
// ── Full Tailwind v4 palette (hex), all colors × all shades ──────────────────
|
|
376
|
-
// Source of truth: official Tailwind CSS v4 color values.
|
|
377
|
-
const CLX_COLOR_PALETTE = {
|
|
378
|
-
red: {
|
|
379
|
-
50: '#fef2f2', 100: '#fee2e2', 200: '#fecaca', 300: '#fca5a5', 400: '#f87171',
|
|
380
|
-
500: '#ef4444', 600: '#dc2626', 700: '#b91c1c', 800: '#991b1b', 900: '#7f1d1d', 950: '#450a0a',
|
|
381
|
-
},
|
|
382
|
-
orange: {
|
|
383
|
-
50: '#fff7ed', 100: '#ffedd5', 200: '#fed7aa', 300: '#fdba74', 400: '#fb923c',
|
|
384
|
-
500: '#f97316', 600: '#ea580c', 700: '#c2410c', 800: '#9a3412', 900: '#7c2d12', 950: '#431407',
|
|
385
|
-
},
|
|
386
|
-
amber: {
|
|
387
|
-
50: '#fffbeb', 100: '#fef3c7', 200: '#fde68a', 300: '#fcd34d', 400: '#fbbf24',
|
|
388
|
-
500: '#f59e0b', 600: '#d97706', 700: '#b45309', 800: '#92400e', 900: '#78350f', 950: '#451a03',
|
|
389
|
-
},
|
|
390
|
-
yellow: {
|
|
391
|
-
50: '#fefce8', 100: '#fef9c3', 200: '#fef08a', 300: '#fde047', 400: '#facc15',
|
|
392
|
-
500: '#eab308', 600: '#ca8a04', 700: '#a16207', 800: '#854d0e', 900: '#713f12', 950: '#422006',
|
|
393
|
-
},
|
|
394
|
-
lime: {
|
|
395
|
-
50: '#f7fee7', 100: '#ecfccb', 200: '#d9f99d', 300: '#bef264', 400: '#a3e635',
|
|
396
|
-
500: '#84cc16', 600: '#65a30d', 700: '#4d7c0f', 800: '#3f6212', 900: '#365314', 950: '#1a2e05',
|
|
397
|
-
},
|
|
398
|
-
green: {
|
|
399
|
-
50: '#f0fdf4', 100: '#dcfce7', 200: '#bbf7d0', 300: '#86efac', 400: '#4ade80',
|
|
400
|
-
500: '#22c55e', 600: '#16a34a', 700: '#15803d', 800: '#166534', 900: '#14532d', 950: '#052e16',
|
|
401
|
-
},
|
|
402
|
-
emerald: {
|
|
403
|
-
50: '#ecfdf5', 100: '#d1fae5', 200: '#a7f3d0', 300: '#6ee7b7', 400: '#34d399',
|
|
404
|
-
500: '#10b981', 600: '#059669', 700: '#047857', 800: '#065f46', 900: '#064e3b', 950: '#022c22',
|
|
405
|
-
},
|
|
406
|
-
teal: {
|
|
407
|
-
50: '#f0fdfa', 100: '#ccfbf1', 200: '#99f6e4', 300: '#5eead4', 400: '#2dd4bf',
|
|
408
|
-
500: '#14b8a6', 600: '#0d9488', 700: '#0f766e', 800: '#115e59', 900: '#134e4a', 950: '#042f2e',
|
|
409
|
-
},
|
|
410
|
-
cyan: {
|
|
411
|
-
50: '#ecfeff', 100: '#cffafe', 200: '#a5f3fc', 300: '#67e8f9', 400: '#22d3ee',
|
|
412
|
-
500: '#06b6d4', 600: '#0891b2', 700: '#0e7490', 800: '#155e75', 900: '#164e63', 950: '#083344',
|
|
413
|
-
},
|
|
414
|
-
sky: {
|
|
415
|
-
50: '#f0f9ff', 100: '#e0f2fe', 200: '#bae6fd', 300: '#7dd3fc', 400: '#38bdf8',
|
|
416
|
-
500: '#0ea5e9', 600: '#0284c7', 700: '#0369a1', 800: '#075985', 900: '#0c4a6e', 950: '#082f49',
|
|
417
|
-
},
|
|
418
|
-
blue: {
|
|
419
|
-
50: '#eff6ff', 100: '#dbeafe', 200: '#bfdbfe', 300: '#93c5fd', 400: '#60a5fa',
|
|
420
|
-
500: '#3b82f6', 600: '#2563eb', 700: '#1d4ed8', 800: '#1e40af', 900: '#1e3a8a', 950: '#172554',
|
|
421
|
-
},
|
|
422
|
-
indigo: {
|
|
423
|
-
50: '#eef2ff', 100: '#e0e7ff', 200: '#c7d2fe', 300: '#a5b4fc', 400: '#818cf8',
|
|
424
|
-
500: '#6366f1', 600: '#4f46e5', 700: '#4338ca', 800: '#3730a3', 900: '#312e81', 950: '#1e1b4b',
|
|
425
|
-
},
|
|
426
|
-
violet: {
|
|
427
|
-
50: '#f5f3ff', 100: '#ede9fe', 200: '#ddd6fe', 300: '#c4b5fd', 400: '#a78bfa',
|
|
428
|
-
500: '#8b5cf6', 600: '#7c3aed', 700: '#6d28d9', 800: '#5b21b6', 900: '#4c1d95', 950: '#2e1065',
|
|
429
|
-
},
|
|
430
|
-
purple: {
|
|
431
|
-
50: '#faf5ff', 100: '#f3e8ff', 200: '#e9d5ff', 300: '#d8b4fe', 400: '#c084fc',
|
|
432
|
-
500: '#a855f7', 600: '#9333ea', 700: '#7e22ce', 800: '#6b21a8', 900: '#581c87', 950: '#3b0764',
|
|
433
|
-
},
|
|
434
|
-
fuchsia: {
|
|
435
|
-
50: '#fdf4ff', 100: '#fae8ff', 200: '#f5d0fe', 300: '#f0abfc', 400: '#e879f9',
|
|
436
|
-
500: '#d946ef', 600: '#c026d3', 700: '#a21caf', 800: '#86198f', 900: '#701a75', 950: '#4a044e',
|
|
437
|
-
},
|
|
438
|
-
pink: {
|
|
439
|
-
50: '#fdf2f8', 100: '#fce7f3', 200: '#fbcfe8', 300: '#f9a8d4', 400: '#f472b6',
|
|
440
|
-
500: '#ec4899', 600: '#db2777', 700: '#be185d', 800: '#9d174d', 900: '#831843', 950: '#500724',
|
|
441
|
-
},
|
|
442
|
-
rose: {
|
|
443
|
-
50: '#fff1f2', 100: '#ffe4e6', 200: '#fecdd3', 300: '#fda4af', 400: '#fb7185',
|
|
444
|
-
500: '#f43f5e', 600: '#e11d48', 700: '#be123c', 800: '#9f1239', 900: '#881337', 950: '#4c0519',
|
|
445
|
-
},
|
|
446
|
-
slate: {
|
|
447
|
-
50: '#f8fafc', 100: '#f1f5f9', 200: '#e2e8f0', 300: '#cbd5e1', 400: '#94a3b8',
|
|
448
|
-
500: '#64748b', 600: '#475569', 700: '#334155', 800: '#1e293b', 900: '#0f172a', 950: '#020617',
|
|
449
|
-
},
|
|
450
|
-
gray: {
|
|
451
|
-
50: '#f9fafb', 100: '#f3f4f6', 200: '#e5e7eb', 300: '#d1d5db', 400: '#9ca3af',
|
|
452
|
-
500: '#6b7280', 600: '#4b5563', 700: '#374151', 800: '#1f2937', 900: '#111827', 950: '#030712',
|
|
453
|
-
},
|
|
454
|
-
zinc: {
|
|
455
|
-
50: '#fafafa', 100: '#f4f4f5', 200: '#e4e4e7', 300: '#d4d4d8', 400: '#a1a1aa',
|
|
456
|
-
500: '#71717a', 600: '#52525b', 700: '#3f3f46', 800: '#27272a', 900: '#18181b', 950: '#09090b',
|
|
457
|
-
},
|
|
458
|
-
neutral: {
|
|
459
|
-
50: '#fafafa', 100: '#f5f5f5', 200: '#e5e5e5', 300: '#d4d4d4', 400: '#a3a3a3',
|
|
460
|
-
500: '#737373', 600: '#525252', 700: '#404040', 800: '#262626', 900: '#171717', 950: '#0a0a0a',
|
|
461
|
-
},
|
|
462
|
-
stone: {
|
|
463
|
-
50: '#fafaf9', 100: '#f5f5f4', 200: '#e7e5e4', 300: '#d6d3d1', 400: '#a8a29e',
|
|
464
|
-
500: '#78716c', 600: '#57534e', 700: '#44403c', 800: '#292524', 900: '#1c1917', 950: '#0c0a09',
|
|
465
|
-
},
|
|
466
|
-
white: { 500: '#ffffff' },
|
|
467
|
-
};
|
|
468
|
-
/** Resolve a hex value for any Tailwind color + shade, with a safe fallback. */
|
|
469
|
-
function resolvePaletteHex(color, shade) {
|
|
470
|
-
const entry = CLX_COLOR_PALETTE[color] ?? CLX_COLOR_PALETTE.indigo;
|
|
471
|
-
return entry[shade] ?? entry[500] ?? CLX_COLOR_PALETTE.indigo[500];
|
|
472
|
-
}
|
|
473
|
-
|
|
474
215
|
const STORAGE_KEY = 'clx-theme-mode';
|
|
475
|
-
const FONT_LINK_ID = 'clx-google-font';
|
|
476
216
|
class ClxThemeService {
|
|
477
217
|
_isBrowser = isPlatformBrowser(inject(PLATFORM_ID));
|
|
478
218
|
_initial = inject(CLX_THEME_CONFIG);
|
|
@@ -489,12 +229,6 @@ class ClxThemeService {
|
|
|
489
229
|
return false;
|
|
490
230
|
return this._sysDark();
|
|
491
231
|
}, ...(ngDevMode ? [{ debugName: "isDark" }] : /* istanbul ignore next */ []));
|
|
492
|
-
/** Color to apply to clx-nav-group labels — falls back to neutralColor */
|
|
493
|
-
sidebarGroupColor = computed(() => this._config().sidebarGroupColor ?? this._config().neutralColor, ...(ngDevMode ? [{ debugName: "sidebarGroupColor" }] : /* istanbul ignore next */ []));
|
|
494
|
-
/** Color to apply to top-level clx-menu — falls back to primaryColor */
|
|
495
|
-
sidebarMenuColor = computed(() => this._config().sidebarMenuColor ?? this._config().primaryColor, ...(ngDevMode ? [{ debugName: "sidebarMenuColor" }] : /* istanbul ignore next */ []));
|
|
496
|
-
/** Color to apply to clx-menu-item — falls back to primaryColor */
|
|
497
|
-
sidebarItemColor = computed(() => this._config().sidebarItemColor ?? this._config().primaryColor, ...(ngDevMode ? [{ debugName: "sidebarItemColor" }] : /* istanbul ignore next */ []));
|
|
498
232
|
constructor() {
|
|
499
233
|
effect(() => {
|
|
500
234
|
if (!this._isBrowser)
|
|
@@ -504,15 +238,14 @@ class ClxThemeService {
|
|
|
504
238
|
effect(() => {
|
|
505
239
|
if (!this._isBrowser)
|
|
506
240
|
return;
|
|
507
|
-
const
|
|
508
|
-
|
|
509
|
-
this._applyColorVar('--clx-secondary', '--clx-secondary-light', cfg.secondaryColor);
|
|
510
|
-
this._applyTextColor(cfg.textColor, this.isDark());
|
|
511
|
-
});
|
|
512
|
-
effect(() => {
|
|
513
|
-
if (!this._isBrowser)
|
|
241
|
+
const primaryColor = this._config().primaryColor;
|
|
242
|
+
if (!primaryColor)
|
|
514
243
|
return;
|
|
515
|
-
|
|
244
|
+
const { color } = parseColorInput(primaryColor);
|
|
245
|
+
const hex500 = CLX_COLOR_HEX[color] ?? CLX_COLOR_HEX.indigo;
|
|
246
|
+
const hex100 = CLX_COLOR_HEX_100[color] ?? CLX_COLOR_HEX_100.indigo;
|
|
247
|
+
document.documentElement.style.setProperty('--clx-primary', hex500);
|
|
248
|
+
document.documentElement.style.setProperty('--clx-primary-light', hex100);
|
|
516
249
|
});
|
|
517
250
|
if (this._isBrowser) {
|
|
518
251
|
const mq = window.matchMedia('(prefers-color-scheme: dark)');
|
|
@@ -530,42 +263,6 @@ class ClxThemeService {
|
|
|
530
263
|
toggle() {
|
|
531
264
|
this.setMode(this.isDark() ? 'light' : 'dark');
|
|
532
265
|
}
|
|
533
|
-
_applyColorVar(varName, lightVarName, input) {
|
|
534
|
-
if (!input)
|
|
535
|
-
return;
|
|
536
|
-
const { color, shade } = parseColorInput(input);
|
|
537
|
-
document.documentElement.style.setProperty(varName, resolvePaletteHex(color, shade));
|
|
538
|
-
if (lightVarName) {
|
|
539
|
-
document.documentElement.style.setProperty(lightVarName, resolvePaletteHex(color, 100));
|
|
540
|
-
}
|
|
541
|
-
}
|
|
542
|
-
_applyTextColor(input, dark) {
|
|
543
|
-
if (!input)
|
|
544
|
-
return;
|
|
545
|
-
const { color } = parseColorInput(input);
|
|
546
|
-
const shades = dark
|
|
547
|
-
? { text: 100, label: 300, muted: 400, subtle: 500, faint: 600 }
|
|
548
|
-
: { text: 900, label: 600, muted: 500, subtle: 400, faint: 300 };
|
|
549
|
-
document.documentElement.style.setProperty('--clx-text', resolvePaletteHex(color, shades.text));
|
|
550
|
-
document.documentElement.style.setProperty('--clx-text-label', resolvePaletteHex(color, shades.label));
|
|
551
|
-
document.documentElement.style.setProperty('--clx-text-muted', resolvePaletteHex(color, shades.muted));
|
|
552
|
-
document.documentElement.style.setProperty('--clx-text-subtle', resolvePaletteHex(color, shades.subtle));
|
|
553
|
-
document.documentElement.style.setProperty('--clx-text-faint', resolvePaletteHex(color, shades.faint));
|
|
554
|
-
}
|
|
555
|
-
_applyFont(family) {
|
|
556
|
-
const option = CLX_FONT_CATALOG.find(f => f.value === family);
|
|
557
|
-
if (!option)
|
|
558
|
-
return;
|
|
559
|
-
let link = document.getElementById(FONT_LINK_ID);
|
|
560
|
-
if (!link) {
|
|
561
|
-
link = document.createElement('link');
|
|
562
|
-
link.id = FONT_LINK_ID;
|
|
563
|
-
link.rel = 'stylesheet';
|
|
564
|
-
document.head.appendChild(link);
|
|
565
|
-
}
|
|
566
|
-
link.href = option.googleUrl;
|
|
567
|
-
document.documentElement.style.setProperty('--clx-font-body', `'${family}', ui-sans-serif, system-ui, sans-serif`);
|
|
568
|
-
}
|
|
569
266
|
_loadMode() {
|
|
570
267
|
if (!this._isBrowser)
|
|
571
268
|
return 'system';
|
|
@@ -2938,7 +2635,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImpo
|
|
|
2938
2635
|
const CLX_LIST_CONTEXT = new InjectionToken('CLX_LIST_CONTEXT');
|
|
2939
2636
|
// ── Variant maps ──────────────────────────────────────────────────────────────
|
|
2940
2637
|
const LIST_VARIANT_SHAPE = {
|
|
2941
|
-
bordered: 'bg-
|
|
2638
|
+
bordered: 'bg-white rounded-2xl overflow-hidden',
|
|
2942
2639
|
flat: 'bg-transparent',
|
|
2943
2640
|
flush: 'bg-transparent',
|
|
2944
2641
|
};
|
|
@@ -4144,7 +3841,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImpo
|
|
|
4144
3841
|
|
|
4145
3842
|
const INPUT_STATUS_MAP = {
|
|
4146
3843
|
default: {
|
|
4147
|
-
border: 'border-
|
|
3844
|
+
border: 'border-slate-200',
|
|
4148
3845
|
ring: '',
|
|
4149
3846
|
msgCls: '',
|
|
4150
3847
|
iconName: '',
|
|
@@ -4557,18 +4254,11 @@ class ClxSelectComponent {
|
|
|
4557
4254
|
_activeColor = computed(() => this.activeColor() ?? this._themeSvc.config().primaryColor, ...(ngDevMode ? [{ debugName: "_activeColor" }] : /* istanbul ignore next */ []));
|
|
4558
4255
|
_el = inject((ElementRef));
|
|
4559
4256
|
_sso = inject(ScrollStrategyOptions);
|
|
4560
|
-
_isBrowser = isPlatformBrowser(inject(PLATFORM_ID));
|
|
4561
|
-
_loadedFonts = new Set();
|
|
4562
4257
|
_scrollStrategy = this._sso.reposition();
|
|
4563
4258
|
constructor() {
|
|
4564
4259
|
this._searchQuery = toSignal(this._searchControl.valueChanges.pipe(startWith(''), map(v => v ?? '')), { initialValue: '' });
|
|
4565
4260
|
if (this._ngControl)
|
|
4566
4261
|
this._ngControl.valueAccessor = this;
|
|
4567
|
-
effect(() => {
|
|
4568
|
-
const family = this._displayFontFamily();
|
|
4569
|
-
if (family)
|
|
4570
|
-
this._loadPreviewFont(family);
|
|
4571
|
-
});
|
|
4572
4262
|
// Async autocomplete: debounce + switchMap sobre el search control
|
|
4573
4263
|
this._searchControl.valueChanges.pipe(debounceTime(this.debounceMs()), distinctUntilChanged(), switchMap(query => {
|
|
4574
4264
|
const q = query ?? '';
|
|
@@ -4616,10 +4306,6 @@ class ClxSelectComponent {
|
|
|
4616
4306
|
const sel = this._selectedOptions();
|
|
4617
4307
|
return sel.length ? sel[0].label : this.placeholder();
|
|
4618
4308
|
}, ...(ngDevMode ? [{ debugName: "_displayValue" }] : /* istanbul ignore next */ []));
|
|
4619
|
-
_displayFontFamily = computed(() => {
|
|
4620
|
-
const sel = this._selectedOptions();
|
|
4621
|
-
return sel.length ? sel[0].previewFontFamily ?? null : null;
|
|
4622
|
-
}, ...(ngDevMode ? [{ debugName: "_displayFontFamily" }] : /* istanbul ignore next */ []));
|
|
4623
4309
|
_overlayWidth = computed(() => this._overlayWidthPx(), ...(ngDevMode ? [{ debugName: "_overlayWidth" }] : /* istanbul ignore next */ []));
|
|
4624
4310
|
_labelClass = computed(() => `${this._sizeConfig().label} ${CLX_TEXT_LABEL} leading-none`, ...(ngDevMode ? [{ debugName: "_labelClass" }] : /* istanbul ignore next */ []));
|
|
4625
4311
|
_hintClass = computed(() => `${this._sizeConfig().hint} ${CLX_TEXT_HINT}`, ...(ngDevMode ? [{ debugName: "_hintClass" }] : /* istanbul ignore next */ []));
|
|
@@ -4670,26 +4356,6 @@ class ClxSelectComponent {
|
|
|
4670
4356
|
if (!this.async())
|
|
4671
4357
|
this._searchControl.setValue('', { emitEvent: false });
|
|
4672
4358
|
this._isOpen.set(true);
|
|
4673
|
-
for (const opt of this.options()) {
|
|
4674
|
-
if (opt.previewFontFamily)
|
|
4675
|
-
this._loadPreviewFont(opt.previewFontFamily);
|
|
4676
|
-
}
|
|
4677
|
-
}
|
|
4678
|
-
_loadPreviewFont(family) {
|
|
4679
|
-
if (!this._isBrowser || this._loadedFonts.has(family))
|
|
4680
|
-
return;
|
|
4681
|
-
const option = CLX_FONT_CATALOG.find(f => f.value === family);
|
|
4682
|
-
if (!option)
|
|
4683
|
-
return;
|
|
4684
|
-
this._loadedFonts.add(family);
|
|
4685
|
-
const id = `clx-preview-font-${family.replace(/\s+/g, '-').toLowerCase()}`;
|
|
4686
|
-
if (document.getElementById(id))
|
|
4687
|
-
return;
|
|
4688
|
-
const link = document.createElement('link');
|
|
4689
|
-
link.id = id;
|
|
4690
|
-
link.rel = 'stylesheet';
|
|
4691
|
-
link.href = option.googleUrl;
|
|
4692
|
-
document.head.appendChild(link);
|
|
4693
4359
|
}
|
|
4694
4360
|
_closePanel() {
|
|
4695
4361
|
this._isOpen.set(false);
|
|
@@ -4761,145 +4427,145 @@ class ClxSelectComponent {
|
|
|
4761
4427
|
this._cvaDisabled.set(disabled);
|
|
4762
4428
|
}
|
|
4763
4429
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxSelectComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
4764
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.15", type: ClxSelectComponent, isStandalone: true, selector: "clx-select", inputs: { label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: false, transformFunction: null }, placeholder: { classPropertyName: "placeholder", publicName: "placeholder", isSignal: true, isRequired: false, transformFunction: null }, options: { classPropertyName: "options", publicName: "options", isSignal: true, isRequired: false, transformFunction: null }, multiple: { classPropertyName: "multiple", publicName: "multiple", isSignal: true, isRequired: false, transformFunction: null }, searchable: { classPropertyName: "searchable", publicName: "searchable", isSignal: true, isRequired: false, transformFunction: null }, searchPlaceholder: { classPropertyName: "searchPlaceholder", publicName: "searchPlaceholder", isSignal: true, isRequired: false, transformFunction: null }, activeColor: { classPropertyName: "activeColor", publicName: "activeColor", isSignal: true, isRequired: false, transformFunction: null }, size: { classPropertyName: "size", publicName: "size", isSignal: true, isRequired: false, transformFunction: null }, hint: { classPropertyName: "hint", publicName: "hint", isSignal: true, isRequired: false, transformFunction: null }, errorMessage: { classPropertyName: "errorMessage", publicName: "errorMessage", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null }, async: { classPropertyName: "async", publicName: "async", isSignal: true, isRequired: false, transformFunction: null }, loadOptions: { classPropertyName: "loadOptions", publicName: "loadOptions", isSignal: true, isRequired: false, transformFunction: null }, debounceMs: { classPropertyName: "debounceMs", publicName: "debounceMs", isSignal: true, isRequired: false, transformFunction: null }, minChars: { classPropertyName: "minChars", publicName: "minChars", isSignal: true, isRequired: false, transformFunction: null } }, host: { listeners: { "keydown.escape": "onEscape()" }, classAttribute: "flex flex-col gap-1.5 w-full" }, ngImport: i0, template: `
|
|
4765
|
-
@if (label()) {
|
|
4766
|
-
<span [id]="_labelId" [class]="_labelClass()">{{ label() }}</span>
|
|
4767
|
-
}
|
|
4768
|
-
|
|
4769
|
-
<!-- ── Trigger ─────────────────────────────────────────────────────────── -->
|
|
4770
|
-
<div
|
|
4771
|
-
#origin="cdkOverlayOrigin"
|
|
4772
|
-
cdkOverlayOrigin
|
|
4773
|
-
[class]="_triggerClass()"
|
|
4774
|
-
[attr.tabindex]="_disabled() ? null : '0'"
|
|
4775
|
-
role="combobox"
|
|
4776
|
-
[attr.aria-labelledby]="label() ? _labelId : null"
|
|
4777
|
-
[attr.aria-expanded]="_isOpen()"
|
|
4778
|
-
aria-haspopup="listbox"
|
|
4779
|
-
(click)="!_disabled() && _togglePanel()"
|
|
4780
|
-
(keydown)="_onTriggerKeydown($event)">
|
|
4781
|
-
|
|
4782
|
-
<!-- Multi mode: tag chips -->
|
|
4783
|
-
@if (multiple()) {
|
|
4784
|
-
<div [class]="_tagContainerClass()">
|
|
4785
|
-
@for (opt of _selectedOptions(); track opt.value) {
|
|
4786
|
-
<span
|
|
4787
|
-
clx-tag
|
|
4788
|
-
variant="soft"
|
|
4789
|
-
[color]="_activeColor()"
|
|
4790
|
-
[size]="_sizeConfig().tagSize"
|
|
4791
|
-
(onRemove)="_deselect(opt.value)">
|
|
4792
|
-
{{ opt.label }}
|
|
4793
|
-
</span>
|
|
4794
|
-
}
|
|
4795
|
-
@if (!_selectedOptions().length) {
|
|
4796
|
-
<span [class]="_placeholderClass()">{{ placeholder() }}</span>
|
|
4797
|
-
}
|
|
4798
|
-
</div>
|
|
4799
|
-
|
|
4800
|
-
<!-- Single mode: display value -->
|
|
4801
|
-
} @else {
|
|
4802
|
-
<span [class]="_singleDisplayClass()"
|
|
4803
|
-
}
|
|
4804
|
-
|
|
4805
|
-
<!-- Right controls: clear + chevron -->
|
|
4806
|
-
<div class="absolute right-2 top-1/2 -translate-y-1/2 flex items-center gap-0.5">
|
|
4807
|
-
@if (_hasValue() && !_disabled() && multiple()) {
|
|
4808
|
-
<button
|
|
4809
|
-
clx-button
|
|
4810
|
-
variant="ghost"
|
|
4811
|
-
[color]="_activeColor()"
|
|
4812
|
-
shape="circle"
|
|
4813
|
-
[size]="_sizeConfig().btnSize"
|
|
4814
|
-
icon="close"
|
|
4815
|
-
[iconOnly]="true"
|
|
4816
|
-
(mousedown)="$event.preventDefault()"
|
|
4817
|
-
(click)="$event.stopPropagation(); _clearAll()">
|
|
4818
|
-
</button>
|
|
4819
|
-
}
|
|
4820
|
-
<button
|
|
4821
|
-
clx-button
|
|
4822
|
-
variant="ghost"
|
|
4823
|
-
[color]="_activeColor()"
|
|
4824
|
-
shape="circle"
|
|
4825
|
-
[size]="_sizeConfig().btnSize"
|
|
4826
|
-
icon="keyboard_arrow_down"
|
|
4827
|
-
[iconOnly]="true"
|
|
4828
|
-
[class]="_chevronBtnClass()"
|
|
4829
|
-
(mousedown)="$event.preventDefault()">
|
|
4830
|
-
</button>
|
|
4831
|
-
</div>
|
|
4832
|
-
</div>
|
|
4833
|
-
|
|
4834
|
-
<!-- ── Overlay panel ───────────────────────────────────────────────────── -->
|
|
4835
|
-
<ng-template
|
|
4836
|
-
cdkConnectedOverlay
|
|
4837
|
-
[cdkConnectedOverlayOrigin]="origin"
|
|
4838
|
-
[cdkConnectedOverlayOpen]="_isOpen()"
|
|
4839
|
-
[cdkConnectedOverlayPositions]="_positions"
|
|
4840
|
-
[cdkConnectedOverlayScrollStrategy]="_scrollStrategy"
|
|
4841
|
-
[cdkConnectedOverlayWidth]="_overlayWidth()"
|
|
4842
|
-
[cdkConnectedOverlayPush]="true"
|
|
4843
|
-
(overlayOutsideClick)="_closePanel()"
|
|
4844
|
-
(overlayKeydown)="_onOverlayKeydown($event)">
|
|
4845
|
-
|
|
4846
|
-
<div [class]="_panelClass()" role="listbox">
|
|
4847
|
-
|
|
4848
|
-
<!-- Search / Autocomplete input -->
|
|
4849
|
-
@if (searchable() || async()) {
|
|
4850
|
-
<div class="p-2 border-b border-clx-border-soft" (click)="$event.stopPropagation()">
|
|
4851
|
-
<clx-input
|
|
4852
|
-
[formControl]="_searchControl"
|
|
4853
|
-
[placeholder]="async() ? 'Buscar...' : searchPlaceholder()"
|
|
4854
|
-
[color]="_activeColor()"
|
|
4855
|
-
[suffixIcon]="async() && _asyncLoading() ? '' : 'search'"
|
|
4856
|
-
size="sm">
|
|
4857
|
-
</clx-input>
|
|
4858
|
-
</div>
|
|
4859
|
-
}
|
|
4860
|
-
|
|
4861
|
-
<!-- Options list -->
|
|
4862
|
-
<div class="overflow-y-auto max-h-60 p-1 space-y-0.5">
|
|
4863
|
-
@if (async() && _asyncLoading()) {
|
|
4864
|
-
<div class="flex items-center justify-center py-6 gap-2 text-sm text-clx-text-subtle">
|
|
4865
|
-
<clx-spinner size="sm" [color]="_activeColor()" />
|
|
4866
|
-
Buscando...
|
|
4867
|
-
</div>
|
|
4868
|
-
} @else if (_showAsyncPlaceholder()) {
|
|
4869
|
-
<div class="px-3 py-4 text-center text-sm text-clx-text-subtle">
|
|
4870
|
-
Escribe {{ minChars() === 1 ? 'al menos 1 carácter' : 'al menos ' + minChars() + ' caracteres' }}
|
|
4871
|
-
</div>
|
|
4872
|
-
} @else if (_filteredOptions().length === 0) {
|
|
4873
|
-
<div class="px-3 py-4 text-center text-sm text-clx-text-subtle">Sin resultados</div>
|
|
4874
|
-
} @else {
|
|
4875
|
-
@for (opt of _filteredOptions(); track opt.value) {
|
|
4876
|
-
<button
|
|
4877
|
-
type="button"
|
|
4878
|
-
[class]="_optionClass(opt)"
|
|
4879
|
-
[disabled]="opt.disabled ?? false"
|
|
4880
|
-
(mousedown)="$event.preventDefault()"
|
|
4881
|
-
(click)="_selectOption(opt)">
|
|
4882
|
-
<span class="flex-1 text-left truncate"
|
|
4883
|
-
@if (_isSelected(opt.value)) {
|
|
4884
|
-
<span clx-icon name="check" size="xs" class="shrink-0"></span>
|
|
4885
|
-
}
|
|
4886
|
-
</button>
|
|
4887
|
-
}
|
|
4888
|
-
}
|
|
4889
|
-
</div>
|
|
4890
|
-
|
|
4891
|
-
</div>
|
|
4892
|
-
</ng-template>
|
|
4893
|
-
|
|
4894
|
-
<!-- ── Bottom message ─────────────────────────────────────────────────── -->
|
|
4895
|
-
@if (_isInvalid()) {
|
|
4896
|
-
<p class="text-xs text-red-500 flex items-center gap-1">
|
|
4897
|
-
<span clx-icon name="error" size="xs"></span>
|
|
4898
|
-
{{ errorMessage() }}
|
|
4899
|
-
</p>
|
|
4900
|
-
} @else if (hint()) {
|
|
4901
|
-
<p [class]="_hintClass()">{{ hint() }}</p>
|
|
4902
|
-
}
|
|
4430
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.15", type: ClxSelectComponent, isStandalone: true, selector: "clx-select", inputs: { label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: false, transformFunction: null }, placeholder: { classPropertyName: "placeholder", publicName: "placeholder", isSignal: true, isRequired: false, transformFunction: null }, options: { classPropertyName: "options", publicName: "options", isSignal: true, isRequired: false, transformFunction: null }, multiple: { classPropertyName: "multiple", publicName: "multiple", isSignal: true, isRequired: false, transformFunction: null }, searchable: { classPropertyName: "searchable", publicName: "searchable", isSignal: true, isRequired: false, transformFunction: null }, searchPlaceholder: { classPropertyName: "searchPlaceholder", publicName: "searchPlaceholder", isSignal: true, isRequired: false, transformFunction: null }, activeColor: { classPropertyName: "activeColor", publicName: "activeColor", isSignal: true, isRequired: false, transformFunction: null }, size: { classPropertyName: "size", publicName: "size", isSignal: true, isRequired: false, transformFunction: null }, hint: { classPropertyName: "hint", publicName: "hint", isSignal: true, isRequired: false, transformFunction: null }, errorMessage: { classPropertyName: "errorMessage", publicName: "errorMessage", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null }, async: { classPropertyName: "async", publicName: "async", isSignal: true, isRequired: false, transformFunction: null }, loadOptions: { classPropertyName: "loadOptions", publicName: "loadOptions", isSignal: true, isRequired: false, transformFunction: null }, debounceMs: { classPropertyName: "debounceMs", publicName: "debounceMs", isSignal: true, isRequired: false, transformFunction: null }, minChars: { classPropertyName: "minChars", publicName: "minChars", isSignal: true, isRequired: false, transformFunction: null } }, host: { listeners: { "keydown.escape": "onEscape()" }, classAttribute: "flex flex-col gap-1.5 w-full" }, ngImport: i0, template: `
|
|
4431
|
+
@if (label()) {
|
|
4432
|
+
<span [id]="_labelId" [class]="_labelClass()">{{ label() }}</span>
|
|
4433
|
+
}
|
|
4434
|
+
|
|
4435
|
+
<!-- ── Trigger ─────────────────────────────────────────────────────────── -->
|
|
4436
|
+
<div
|
|
4437
|
+
#origin="cdkOverlayOrigin"
|
|
4438
|
+
cdkOverlayOrigin
|
|
4439
|
+
[class]="_triggerClass()"
|
|
4440
|
+
[attr.tabindex]="_disabled() ? null : '0'"
|
|
4441
|
+
role="combobox"
|
|
4442
|
+
[attr.aria-labelledby]="label() ? _labelId : null"
|
|
4443
|
+
[attr.aria-expanded]="_isOpen()"
|
|
4444
|
+
aria-haspopup="listbox"
|
|
4445
|
+
(click)="!_disabled() && _togglePanel()"
|
|
4446
|
+
(keydown)="_onTriggerKeydown($event)">
|
|
4447
|
+
|
|
4448
|
+
<!-- Multi mode: tag chips -->
|
|
4449
|
+
@if (multiple()) {
|
|
4450
|
+
<div [class]="_tagContainerClass()">
|
|
4451
|
+
@for (opt of _selectedOptions(); track opt.value) {
|
|
4452
|
+
<span
|
|
4453
|
+
clx-tag
|
|
4454
|
+
variant="soft"
|
|
4455
|
+
[color]="_activeColor()"
|
|
4456
|
+
[size]="_sizeConfig().tagSize"
|
|
4457
|
+
(onRemove)="_deselect(opt.value)">
|
|
4458
|
+
{{ opt.label }}
|
|
4459
|
+
</span>
|
|
4460
|
+
}
|
|
4461
|
+
@if (!_selectedOptions().length) {
|
|
4462
|
+
<span [class]="_placeholderClass()">{{ placeholder() }}</span>
|
|
4463
|
+
}
|
|
4464
|
+
</div>
|
|
4465
|
+
|
|
4466
|
+
<!-- Single mode: display value -->
|
|
4467
|
+
} @else {
|
|
4468
|
+
<span [class]="_singleDisplayClass()">{{ _displayValue() }}</span>
|
|
4469
|
+
}
|
|
4470
|
+
|
|
4471
|
+
<!-- Right controls: clear + chevron -->
|
|
4472
|
+
<div class="absolute right-2 top-1/2 -translate-y-1/2 flex items-center gap-0.5">
|
|
4473
|
+
@if (_hasValue() && !_disabled() && multiple()) {
|
|
4474
|
+
<button
|
|
4475
|
+
clx-button
|
|
4476
|
+
variant="ghost"
|
|
4477
|
+
[color]="_activeColor()"
|
|
4478
|
+
shape="circle"
|
|
4479
|
+
[size]="_sizeConfig().btnSize"
|
|
4480
|
+
icon="close"
|
|
4481
|
+
[iconOnly]="true"
|
|
4482
|
+
(mousedown)="$event.preventDefault()"
|
|
4483
|
+
(click)="$event.stopPropagation(); _clearAll()">
|
|
4484
|
+
</button>
|
|
4485
|
+
}
|
|
4486
|
+
<button
|
|
4487
|
+
clx-button
|
|
4488
|
+
variant="ghost"
|
|
4489
|
+
[color]="_activeColor()"
|
|
4490
|
+
shape="circle"
|
|
4491
|
+
[size]="_sizeConfig().btnSize"
|
|
4492
|
+
icon="keyboard_arrow_down"
|
|
4493
|
+
[iconOnly]="true"
|
|
4494
|
+
[class]="_chevronBtnClass()"
|
|
4495
|
+
(mousedown)="$event.preventDefault()">
|
|
4496
|
+
</button>
|
|
4497
|
+
</div>
|
|
4498
|
+
</div>
|
|
4499
|
+
|
|
4500
|
+
<!-- ── Overlay panel ───────────────────────────────────────────────────── -->
|
|
4501
|
+
<ng-template
|
|
4502
|
+
cdkConnectedOverlay
|
|
4503
|
+
[cdkConnectedOverlayOrigin]="origin"
|
|
4504
|
+
[cdkConnectedOverlayOpen]="_isOpen()"
|
|
4505
|
+
[cdkConnectedOverlayPositions]="_positions"
|
|
4506
|
+
[cdkConnectedOverlayScrollStrategy]="_scrollStrategy"
|
|
4507
|
+
[cdkConnectedOverlayWidth]="_overlayWidth()"
|
|
4508
|
+
[cdkConnectedOverlayPush]="true"
|
|
4509
|
+
(overlayOutsideClick)="_closePanel()"
|
|
4510
|
+
(overlayKeydown)="_onOverlayKeydown($event)">
|
|
4511
|
+
|
|
4512
|
+
<div [class]="_panelClass()" role="listbox">
|
|
4513
|
+
|
|
4514
|
+
<!-- Search / Autocomplete input -->
|
|
4515
|
+
@if (searchable() || async()) {
|
|
4516
|
+
<div class="p-2 border-b border-clx-border-soft" (click)="$event.stopPropagation()">
|
|
4517
|
+
<clx-input
|
|
4518
|
+
[formControl]="_searchControl"
|
|
4519
|
+
[placeholder]="async() ? 'Buscar...' : searchPlaceholder()"
|
|
4520
|
+
[color]="_activeColor()"
|
|
4521
|
+
[suffixIcon]="async() && _asyncLoading() ? '' : 'search'"
|
|
4522
|
+
size="sm">
|
|
4523
|
+
</clx-input>
|
|
4524
|
+
</div>
|
|
4525
|
+
}
|
|
4526
|
+
|
|
4527
|
+
<!-- Options list -->
|
|
4528
|
+
<div class="overflow-y-auto max-h-60 p-1 space-y-0.5">
|
|
4529
|
+
@if (async() && _asyncLoading()) {
|
|
4530
|
+
<div class="flex items-center justify-center py-6 gap-2 text-sm text-clx-text-subtle">
|
|
4531
|
+
<clx-spinner size="sm" [color]="_activeColor()" />
|
|
4532
|
+
Buscando...
|
|
4533
|
+
</div>
|
|
4534
|
+
} @else if (_showAsyncPlaceholder()) {
|
|
4535
|
+
<div class="px-3 py-4 text-center text-sm text-clx-text-subtle">
|
|
4536
|
+
Escribe {{ minChars() === 1 ? 'al menos 1 carácter' : 'al menos ' + minChars() + ' caracteres' }}
|
|
4537
|
+
</div>
|
|
4538
|
+
} @else if (_filteredOptions().length === 0) {
|
|
4539
|
+
<div class="px-3 py-4 text-center text-sm text-clx-text-subtle">Sin resultados</div>
|
|
4540
|
+
} @else {
|
|
4541
|
+
@for (opt of _filteredOptions(); track opt.value) {
|
|
4542
|
+
<button
|
|
4543
|
+
type="button"
|
|
4544
|
+
[class]="_optionClass(opt)"
|
|
4545
|
+
[disabled]="opt.disabled ?? false"
|
|
4546
|
+
(mousedown)="$event.preventDefault()"
|
|
4547
|
+
(click)="_selectOption(opt)">
|
|
4548
|
+
<span class="flex-1 text-left truncate">{{ opt.label }}</span>
|
|
4549
|
+
@if (_isSelected(opt.value)) {
|
|
4550
|
+
<span clx-icon name="check" size="xs" class="shrink-0"></span>
|
|
4551
|
+
}
|
|
4552
|
+
</button>
|
|
4553
|
+
}
|
|
4554
|
+
}
|
|
4555
|
+
</div>
|
|
4556
|
+
|
|
4557
|
+
</div>
|
|
4558
|
+
</ng-template>
|
|
4559
|
+
|
|
4560
|
+
<!-- ── Bottom message ─────────────────────────────────────────────────── -->
|
|
4561
|
+
@if (_isInvalid()) {
|
|
4562
|
+
<p class="text-xs text-red-500 flex items-center gap-1">
|
|
4563
|
+
<span clx-icon name="error" size="xs"></span>
|
|
4564
|
+
{{ errorMessage() }}
|
|
4565
|
+
</p>
|
|
4566
|
+
} @else if (hint()) {
|
|
4567
|
+
<p [class]="_hintClass()">{{ hint() }}</p>
|
|
4568
|
+
}
|
|
4903
4569
|
`, isInline: true, dependencies: [{ kind: "ngmodule", type: OverlayModule }, { kind: "directive", type: i1$1.CdkConnectedOverlay, selector: "[cdk-connected-overlay], [connected-overlay], [cdkConnectedOverlay]", inputs: ["cdkConnectedOverlayOrigin", "cdkConnectedOverlayPositions", "cdkConnectedOverlayPositionStrategy", "cdkConnectedOverlayOffsetX", "cdkConnectedOverlayOffsetY", "cdkConnectedOverlayWidth", "cdkConnectedOverlayHeight", "cdkConnectedOverlayMinWidth", "cdkConnectedOverlayMinHeight", "cdkConnectedOverlayBackdropClass", "cdkConnectedOverlayPanelClass", "cdkConnectedOverlayViewportMargin", "cdkConnectedOverlayScrollStrategy", "cdkConnectedOverlayOpen", "cdkConnectedOverlayDisableClose", "cdkConnectedOverlayTransformOriginOn", "cdkConnectedOverlayHasBackdrop", "cdkConnectedOverlayLockPosition", "cdkConnectedOverlayFlexibleDimensions", "cdkConnectedOverlayGrowAfterOpen", "cdkConnectedOverlayPush", "cdkConnectedOverlayDisposeOnNavigation"], outputs: ["backdropClick", "positionChange", "attach", "detach", "overlayKeydown", "overlayOutsideClick"], exportAs: ["cdkConnectedOverlay"] }, { kind: "directive", type: i1$1.CdkOverlayOrigin, selector: "[cdk-overlay-origin], [overlay-origin], [cdkOverlayOrigin]", exportAs: ["cdkOverlayOrigin"] }, { kind: "ngmodule", type: ReactiveFormsModule }, { kind: "directive", type: i1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1.FormControlDirective, selector: "[formControl]", inputs: ["formControl", "disabled", "ngModel"], outputs: ["ngModelChange"], exportAs: ["ngForm"] }, { kind: "component", type: ClxTagComponent, selector: "span[clx-tag]", inputs: ["variant", "color", "size", "shape"], outputs: ["onRemove"] }, { kind: "component", type: ClxIconComponent, selector: "span[clx-icon]", inputs: ["name", "size", "color", "fill"] }, { kind: "component", type: ClxButtonComponent, selector: "button[clx-button], a[clx-button]", inputs: ["variant", "color", "size", "shape", "loading", "disabled", "block", "icon", "iconPosition", "iconOnly", "badge", "badgeColor"] }, { kind: "component", type: ClxInputComponent, selector: "clx-input", inputs: ["label", "placeholder", "type", "color", "hint", "prefixIcon", "suffixIcon", "prefixText", "suffixText", "status", "statusMessage", "size", "value", "disabled", "autocomplete"] }, { kind: "component", type: ClxSpinnerComponent, selector: "clx-spinner", inputs: ["size", "color", "variant"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None });
|
|
4904
4570
|
}
|
|
4905
4571
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxSelectComponent, decorators: [{
|
|
@@ -4908,145 +4574,145 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImpo
|
|
|
4908
4574
|
selector: 'clx-select',
|
|
4909
4575
|
standalone: true,
|
|
4910
4576
|
imports: [OverlayModule, ReactiveFormsModule, ClxTagComponent, ClxIconComponent, ClxButtonComponent, ClxInputComponent, ClxSpinnerComponent],
|
|
4911
|
-
template: `
|
|
4912
|
-
@if (label()) {
|
|
4913
|
-
<span [id]="_labelId" [class]="_labelClass()">{{ label() }}</span>
|
|
4914
|
-
}
|
|
4915
|
-
|
|
4916
|
-
<!-- ── Trigger ─────────────────────────────────────────────────────────── -->
|
|
4917
|
-
<div
|
|
4918
|
-
#origin="cdkOverlayOrigin"
|
|
4919
|
-
cdkOverlayOrigin
|
|
4920
|
-
[class]="_triggerClass()"
|
|
4921
|
-
[attr.tabindex]="_disabled() ? null : '0'"
|
|
4922
|
-
role="combobox"
|
|
4923
|
-
[attr.aria-labelledby]="label() ? _labelId : null"
|
|
4924
|
-
[attr.aria-expanded]="_isOpen()"
|
|
4925
|
-
aria-haspopup="listbox"
|
|
4926
|
-
(click)="!_disabled() && _togglePanel()"
|
|
4927
|
-
(keydown)="_onTriggerKeydown($event)">
|
|
4928
|
-
|
|
4929
|
-
<!-- Multi mode: tag chips -->
|
|
4930
|
-
@if (multiple()) {
|
|
4931
|
-
<div [class]="_tagContainerClass()">
|
|
4932
|
-
@for (opt of _selectedOptions(); track opt.value) {
|
|
4933
|
-
<span
|
|
4934
|
-
clx-tag
|
|
4935
|
-
variant="soft"
|
|
4936
|
-
[color]="_activeColor()"
|
|
4937
|
-
[size]="_sizeConfig().tagSize"
|
|
4938
|
-
(onRemove)="_deselect(opt.value)">
|
|
4939
|
-
{{ opt.label }}
|
|
4940
|
-
</span>
|
|
4941
|
-
}
|
|
4942
|
-
@if (!_selectedOptions().length) {
|
|
4943
|
-
<span [class]="_placeholderClass()">{{ placeholder() }}</span>
|
|
4944
|
-
}
|
|
4945
|
-
</div>
|
|
4946
|
-
|
|
4947
|
-
<!-- Single mode: display value -->
|
|
4948
|
-
} @else {
|
|
4949
|
-
<span [class]="_singleDisplayClass()"
|
|
4950
|
-
}
|
|
4951
|
-
|
|
4952
|
-
<!-- Right controls: clear + chevron -->
|
|
4953
|
-
<div class="absolute right-2 top-1/2 -translate-y-1/2 flex items-center gap-0.5">
|
|
4954
|
-
@if (_hasValue() && !_disabled() && multiple()) {
|
|
4955
|
-
<button
|
|
4956
|
-
clx-button
|
|
4957
|
-
variant="ghost"
|
|
4958
|
-
[color]="_activeColor()"
|
|
4959
|
-
shape="circle"
|
|
4960
|
-
[size]="_sizeConfig().btnSize"
|
|
4961
|
-
icon="close"
|
|
4962
|
-
[iconOnly]="true"
|
|
4963
|
-
(mousedown)="$event.preventDefault()"
|
|
4964
|
-
(click)="$event.stopPropagation(); _clearAll()">
|
|
4965
|
-
</button>
|
|
4966
|
-
}
|
|
4967
|
-
<button
|
|
4968
|
-
clx-button
|
|
4969
|
-
variant="ghost"
|
|
4970
|
-
[color]="_activeColor()"
|
|
4971
|
-
shape="circle"
|
|
4972
|
-
[size]="_sizeConfig().btnSize"
|
|
4973
|
-
icon="keyboard_arrow_down"
|
|
4974
|
-
[iconOnly]="true"
|
|
4975
|
-
[class]="_chevronBtnClass()"
|
|
4976
|
-
(mousedown)="$event.preventDefault()">
|
|
4977
|
-
</button>
|
|
4978
|
-
</div>
|
|
4979
|
-
</div>
|
|
4980
|
-
|
|
4981
|
-
<!-- ── Overlay panel ───────────────────────────────────────────────────── -->
|
|
4982
|
-
<ng-template
|
|
4983
|
-
cdkConnectedOverlay
|
|
4984
|
-
[cdkConnectedOverlayOrigin]="origin"
|
|
4985
|
-
[cdkConnectedOverlayOpen]="_isOpen()"
|
|
4986
|
-
[cdkConnectedOverlayPositions]="_positions"
|
|
4987
|
-
[cdkConnectedOverlayScrollStrategy]="_scrollStrategy"
|
|
4988
|
-
[cdkConnectedOverlayWidth]="_overlayWidth()"
|
|
4989
|
-
[cdkConnectedOverlayPush]="true"
|
|
4990
|
-
(overlayOutsideClick)="_closePanel()"
|
|
4991
|
-
(overlayKeydown)="_onOverlayKeydown($event)">
|
|
4992
|
-
|
|
4993
|
-
<div [class]="_panelClass()" role="listbox">
|
|
4994
|
-
|
|
4995
|
-
<!-- Search / Autocomplete input -->
|
|
4996
|
-
@if (searchable() || async()) {
|
|
4997
|
-
<div class="p-2 border-b border-clx-border-soft" (click)="$event.stopPropagation()">
|
|
4998
|
-
<clx-input
|
|
4999
|
-
[formControl]="_searchControl"
|
|
5000
|
-
[placeholder]="async() ? 'Buscar...' : searchPlaceholder()"
|
|
5001
|
-
[color]="_activeColor()"
|
|
5002
|
-
[suffixIcon]="async() && _asyncLoading() ? '' : 'search'"
|
|
5003
|
-
size="sm">
|
|
5004
|
-
</clx-input>
|
|
5005
|
-
</div>
|
|
5006
|
-
}
|
|
5007
|
-
|
|
5008
|
-
<!-- Options list -->
|
|
5009
|
-
<div class="overflow-y-auto max-h-60 p-1 space-y-0.5">
|
|
5010
|
-
@if (async() && _asyncLoading()) {
|
|
5011
|
-
<div class="flex items-center justify-center py-6 gap-2 text-sm text-clx-text-subtle">
|
|
5012
|
-
<clx-spinner size="sm" [color]="_activeColor()" />
|
|
5013
|
-
Buscando...
|
|
5014
|
-
</div>
|
|
5015
|
-
} @else if (_showAsyncPlaceholder()) {
|
|
5016
|
-
<div class="px-3 py-4 text-center text-sm text-clx-text-subtle">
|
|
5017
|
-
Escribe {{ minChars() === 1 ? 'al menos 1 carácter' : 'al menos ' + minChars() + ' caracteres' }}
|
|
5018
|
-
</div>
|
|
5019
|
-
} @else if (_filteredOptions().length === 0) {
|
|
5020
|
-
<div class="px-3 py-4 text-center text-sm text-clx-text-subtle">Sin resultados</div>
|
|
5021
|
-
} @else {
|
|
5022
|
-
@for (opt of _filteredOptions(); track opt.value) {
|
|
5023
|
-
<button
|
|
5024
|
-
type="button"
|
|
5025
|
-
[class]="_optionClass(opt)"
|
|
5026
|
-
[disabled]="opt.disabled ?? false"
|
|
5027
|
-
(mousedown)="$event.preventDefault()"
|
|
5028
|
-
(click)="_selectOption(opt)">
|
|
5029
|
-
<span class="flex-1 text-left truncate"
|
|
5030
|
-
@if (_isSelected(opt.value)) {
|
|
5031
|
-
<span clx-icon name="check" size="xs" class="shrink-0"></span>
|
|
5032
|
-
}
|
|
5033
|
-
</button>
|
|
5034
|
-
}
|
|
5035
|
-
}
|
|
5036
|
-
</div>
|
|
5037
|
-
|
|
5038
|
-
</div>
|
|
5039
|
-
</ng-template>
|
|
5040
|
-
|
|
5041
|
-
<!-- ── Bottom message ─────────────────────────────────────────────────── -->
|
|
5042
|
-
@if (_isInvalid()) {
|
|
5043
|
-
<p class="text-xs text-red-500 flex items-center gap-1">
|
|
5044
|
-
<span clx-icon name="error" size="xs"></span>
|
|
5045
|
-
{{ errorMessage() }}
|
|
5046
|
-
</p>
|
|
5047
|
-
} @else if (hint()) {
|
|
5048
|
-
<p [class]="_hintClass()">{{ hint() }}</p>
|
|
5049
|
-
}
|
|
4577
|
+
template: `
|
|
4578
|
+
@if (label()) {
|
|
4579
|
+
<span [id]="_labelId" [class]="_labelClass()">{{ label() }}</span>
|
|
4580
|
+
}
|
|
4581
|
+
|
|
4582
|
+
<!-- ── Trigger ─────────────────────────────────────────────────────────── -->
|
|
4583
|
+
<div
|
|
4584
|
+
#origin="cdkOverlayOrigin"
|
|
4585
|
+
cdkOverlayOrigin
|
|
4586
|
+
[class]="_triggerClass()"
|
|
4587
|
+
[attr.tabindex]="_disabled() ? null : '0'"
|
|
4588
|
+
role="combobox"
|
|
4589
|
+
[attr.aria-labelledby]="label() ? _labelId : null"
|
|
4590
|
+
[attr.aria-expanded]="_isOpen()"
|
|
4591
|
+
aria-haspopup="listbox"
|
|
4592
|
+
(click)="!_disabled() && _togglePanel()"
|
|
4593
|
+
(keydown)="_onTriggerKeydown($event)">
|
|
4594
|
+
|
|
4595
|
+
<!-- Multi mode: tag chips -->
|
|
4596
|
+
@if (multiple()) {
|
|
4597
|
+
<div [class]="_tagContainerClass()">
|
|
4598
|
+
@for (opt of _selectedOptions(); track opt.value) {
|
|
4599
|
+
<span
|
|
4600
|
+
clx-tag
|
|
4601
|
+
variant="soft"
|
|
4602
|
+
[color]="_activeColor()"
|
|
4603
|
+
[size]="_sizeConfig().tagSize"
|
|
4604
|
+
(onRemove)="_deselect(opt.value)">
|
|
4605
|
+
{{ opt.label }}
|
|
4606
|
+
</span>
|
|
4607
|
+
}
|
|
4608
|
+
@if (!_selectedOptions().length) {
|
|
4609
|
+
<span [class]="_placeholderClass()">{{ placeholder() }}</span>
|
|
4610
|
+
}
|
|
4611
|
+
</div>
|
|
4612
|
+
|
|
4613
|
+
<!-- Single mode: display value -->
|
|
4614
|
+
} @else {
|
|
4615
|
+
<span [class]="_singleDisplayClass()">{{ _displayValue() }}</span>
|
|
4616
|
+
}
|
|
4617
|
+
|
|
4618
|
+
<!-- Right controls: clear + chevron -->
|
|
4619
|
+
<div class="absolute right-2 top-1/2 -translate-y-1/2 flex items-center gap-0.5">
|
|
4620
|
+
@if (_hasValue() && !_disabled() && multiple()) {
|
|
4621
|
+
<button
|
|
4622
|
+
clx-button
|
|
4623
|
+
variant="ghost"
|
|
4624
|
+
[color]="_activeColor()"
|
|
4625
|
+
shape="circle"
|
|
4626
|
+
[size]="_sizeConfig().btnSize"
|
|
4627
|
+
icon="close"
|
|
4628
|
+
[iconOnly]="true"
|
|
4629
|
+
(mousedown)="$event.preventDefault()"
|
|
4630
|
+
(click)="$event.stopPropagation(); _clearAll()">
|
|
4631
|
+
</button>
|
|
4632
|
+
}
|
|
4633
|
+
<button
|
|
4634
|
+
clx-button
|
|
4635
|
+
variant="ghost"
|
|
4636
|
+
[color]="_activeColor()"
|
|
4637
|
+
shape="circle"
|
|
4638
|
+
[size]="_sizeConfig().btnSize"
|
|
4639
|
+
icon="keyboard_arrow_down"
|
|
4640
|
+
[iconOnly]="true"
|
|
4641
|
+
[class]="_chevronBtnClass()"
|
|
4642
|
+
(mousedown)="$event.preventDefault()">
|
|
4643
|
+
</button>
|
|
4644
|
+
</div>
|
|
4645
|
+
</div>
|
|
4646
|
+
|
|
4647
|
+
<!-- ── Overlay panel ───────────────────────────────────────────────────── -->
|
|
4648
|
+
<ng-template
|
|
4649
|
+
cdkConnectedOverlay
|
|
4650
|
+
[cdkConnectedOverlayOrigin]="origin"
|
|
4651
|
+
[cdkConnectedOverlayOpen]="_isOpen()"
|
|
4652
|
+
[cdkConnectedOverlayPositions]="_positions"
|
|
4653
|
+
[cdkConnectedOverlayScrollStrategy]="_scrollStrategy"
|
|
4654
|
+
[cdkConnectedOverlayWidth]="_overlayWidth()"
|
|
4655
|
+
[cdkConnectedOverlayPush]="true"
|
|
4656
|
+
(overlayOutsideClick)="_closePanel()"
|
|
4657
|
+
(overlayKeydown)="_onOverlayKeydown($event)">
|
|
4658
|
+
|
|
4659
|
+
<div [class]="_panelClass()" role="listbox">
|
|
4660
|
+
|
|
4661
|
+
<!-- Search / Autocomplete input -->
|
|
4662
|
+
@if (searchable() || async()) {
|
|
4663
|
+
<div class="p-2 border-b border-clx-border-soft" (click)="$event.stopPropagation()">
|
|
4664
|
+
<clx-input
|
|
4665
|
+
[formControl]="_searchControl"
|
|
4666
|
+
[placeholder]="async() ? 'Buscar...' : searchPlaceholder()"
|
|
4667
|
+
[color]="_activeColor()"
|
|
4668
|
+
[suffixIcon]="async() && _asyncLoading() ? '' : 'search'"
|
|
4669
|
+
size="sm">
|
|
4670
|
+
</clx-input>
|
|
4671
|
+
</div>
|
|
4672
|
+
}
|
|
4673
|
+
|
|
4674
|
+
<!-- Options list -->
|
|
4675
|
+
<div class="overflow-y-auto max-h-60 p-1 space-y-0.5">
|
|
4676
|
+
@if (async() && _asyncLoading()) {
|
|
4677
|
+
<div class="flex items-center justify-center py-6 gap-2 text-sm text-clx-text-subtle">
|
|
4678
|
+
<clx-spinner size="sm" [color]="_activeColor()" />
|
|
4679
|
+
Buscando...
|
|
4680
|
+
</div>
|
|
4681
|
+
} @else if (_showAsyncPlaceholder()) {
|
|
4682
|
+
<div class="px-3 py-4 text-center text-sm text-clx-text-subtle">
|
|
4683
|
+
Escribe {{ minChars() === 1 ? 'al menos 1 carácter' : 'al menos ' + minChars() + ' caracteres' }}
|
|
4684
|
+
</div>
|
|
4685
|
+
} @else if (_filteredOptions().length === 0) {
|
|
4686
|
+
<div class="px-3 py-4 text-center text-sm text-clx-text-subtle">Sin resultados</div>
|
|
4687
|
+
} @else {
|
|
4688
|
+
@for (opt of _filteredOptions(); track opt.value) {
|
|
4689
|
+
<button
|
|
4690
|
+
type="button"
|
|
4691
|
+
[class]="_optionClass(opt)"
|
|
4692
|
+
[disabled]="opt.disabled ?? false"
|
|
4693
|
+
(mousedown)="$event.preventDefault()"
|
|
4694
|
+
(click)="_selectOption(opt)">
|
|
4695
|
+
<span class="flex-1 text-left truncate">{{ opt.label }}</span>
|
|
4696
|
+
@if (_isSelected(opt.value)) {
|
|
4697
|
+
<span clx-icon name="check" size="xs" class="shrink-0"></span>
|
|
4698
|
+
}
|
|
4699
|
+
</button>
|
|
4700
|
+
}
|
|
4701
|
+
}
|
|
4702
|
+
</div>
|
|
4703
|
+
|
|
4704
|
+
</div>
|
|
4705
|
+
</ng-template>
|
|
4706
|
+
|
|
4707
|
+
<!-- ── Bottom message ─────────────────────────────────────────────────── -->
|
|
4708
|
+
@if (_isInvalid()) {
|
|
4709
|
+
<p class="text-xs text-red-500 flex items-center gap-1">
|
|
4710
|
+
<span clx-icon name="error" size="xs"></span>
|
|
4711
|
+
{{ errorMessage() }}
|
|
4712
|
+
</p>
|
|
4713
|
+
} @else if (hint()) {
|
|
4714
|
+
<p [class]="_hintClass()">{{ hint() }}</p>
|
|
4715
|
+
}
|
|
5050
4716
|
`,
|
|
5051
4717
|
encapsulation: ViewEncapsulation.None,
|
|
5052
4718
|
changeDetection: ChangeDetectionStrategy.OnPush,
|
|
@@ -5471,7 +5137,6 @@ class ClxAlertComponent {
|
|
|
5471
5137
|
_resolve = inject(CLX_ALERT_RESOLVE);
|
|
5472
5138
|
_animate = inject(ClxAnimateService);
|
|
5473
5139
|
_el = inject((ElementRef));
|
|
5474
|
-
_themeSvc = inject(ClxThemeService);
|
|
5475
5140
|
_zone;
|
|
5476
5141
|
constructor() {
|
|
5477
5142
|
const zone = inject(NgZone, { optional: true });
|
|
@@ -5479,36 +5144,17 @@ class ClxAlertComponent {
|
|
|
5479
5144
|
}
|
|
5480
5145
|
// ─── Resolved options ─────────────────────────────────────────────────────
|
|
5481
5146
|
get _type() { return this._opts.type ?? 'info'; }
|
|
5482
|
-
get _isConfirm() { return this._type === 'confirm'; }
|
|
5483
5147
|
_icon = signal(ALERT_ICON_MAP[this._type], ...(ngDevMode ? [{ debugName: "_icon" }] : /* istanbul ignore next */ []));
|
|
5148
|
+
_iconBg = signal(ALERT_ICON_BG_MAP[this._type], ...(ngDevMode ? [{ debugName: "_iconBg" }] : /* istanbul ignore next */ []));
|
|
5149
|
+
_iconColor = signal(ALERT_ICON_COLOR_MAP[this._type], ...(ngDevMode ? [{ debugName: "_iconColor" }] : /* istanbul ignore next */ []));
|
|
5150
|
+
_progressColor = signal(ALERT_PROGRESS_COLOR_MAP[this._type], ...(ngDevMode ? [{ debugName: "_progressColor" }] : /* istanbul ignore next */ []));
|
|
5484
5151
|
_title = signal(this._opts.title ?? '', ...(ngDevMode ? [{ debugName: "_title" }] : /* istanbul ignore next */ []));
|
|
5485
5152
|
_message = signal(this._opts.message ?? '', ...(ngDevMode ? [{ debugName: "_message" }] : /* istanbul ignore next */ []));
|
|
5486
5153
|
_showCancel = signal(this._opts.showCancelButton ?? this._opts.type === 'confirm', ...(ngDevMode ? [{ debugName: "_showCancel" }] : /* istanbul ignore next */ []));
|
|
5487
|
-
_iconBg = computed(() => {
|
|
5488
|
-
if (!this._isConfirm)
|
|
5489
|
-
return ALERT_ICON_BG_MAP[this._type];
|
|
5490
|
-
return resolveColor(this._themeSvc.config().primaryColor).bgSubtle;
|
|
5491
|
-
}, ...(ngDevMode ? [{ debugName: "_iconBg" }] : /* istanbul ignore next */ []));
|
|
5492
|
-
_iconColor = computed(() => {
|
|
5493
|
-
if (!this._isConfirm)
|
|
5494
|
-
return ALERT_ICON_COLOR_MAP[this._type];
|
|
5495
|
-
return resolveColor(this._themeSvc.config().primaryColor).textSubtle;
|
|
5496
|
-
}, ...(ngDevMode ? [{ debugName: "_iconColor" }] : /* istanbul ignore next */ []));
|
|
5497
|
-
_progressColor = computed(() => {
|
|
5498
|
-
if (!this._isConfirm)
|
|
5499
|
-
return ALERT_PROGRESS_COLOR_MAP[this._type];
|
|
5500
|
-
return resolveColor(this._themeSvc.config().primaryColor).bg;
|
|
5501
|
-
}, ...(ngDevMode ? [{ debugName: "_progressColor" }] : /* istanbul ignore next */ []));
|
|
5502
5154
|
_confirmText = signal(this._opts.confirmButton?.text ?? 'Aceptar', ...(ngDevMode ? [{ debugName: "_confirmText" }] : /* istanbul ignore next */ []));
|
|
5503
|
-
_confirmColor =
|
|
5504
|
-
if (this._opts.confirmButton?.color)
|
|
5505
|
-
return this._opts.confirmButton.color;
|
|
5506
|
-
if (this._isConfirm)
|
|
5507
|
-
return this._themeSvc.config().primaryColor;
|
|
5508
|
-
return ALERT_CONFIRM_COLOR_MAP[this._type];
|
|
5509
|
-
}, ...(ngDevMode ? [{ debugName: "_confirmColor" }] : /* istanbul ignore next */ []));
|
|
5155
|
+
_confirmColor = signal(this._opts.confirmButton?.color ?? ALERT_CONFIRM_COLOR_MAP[this._type], ...(ngDevMode ? [{ debugName: "_confirmColor" }] : /* istanbul ignore next */ []));
|
|
5510
5156
|
_cancelText = signal(this._opts.cancelButton?.text ?? 'Cancelar', ...(ngDevMode ? [{ debugName: "_cancelText" }] : /* istanbul ignore next */ []));
|
|
5511
|
-
_cancelColor =
|
|
5157
|
+
_cancelColor = signal(this._opts.cancelButton?.color ?? 'slate', ...(ngDevMode ? [{ debugName: "_cancelColor" }] : /* istanbul ignore next */ []));
|
|
5512
5158
|
_cancelVariant = signal(this._opts.cancelButton?.variant ?? 'ghost', ...(ngDevMode ? [{ debugName: "_cancelVariant" }] : /* istanbul ignore next */ []));
|
|
5513
5159
|
// ─── Timer state ─────────────────────────────────────────────────────────
|
|
5514
5160
|
_timerTotal = signal(this._opts.timer ?? 0, ...(ngDevMode ? [{ debugName: "_timerTotal" }] : /* istanbul ignore next */ []));
|
|
@@ -5575,142 +5221,146 @@ class ClxAlertComponent {
|
|
|
5575
5221
|
}
|
|
5576
5222
|
}
|
|
5577
5223
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxAlertComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
5578
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.15", type: ClxAlertComponent, isStandalone: true, selector: "clx-alert", ngImport: i0, template: `
|
|
5579
|
-
<!-- Dialog card -->
|
|
5580
|
-
<div
|
|
5581
|
-
#card
|
|
5582
|
-
class="clx-alert-card relative w-full max-w-sm mx-auto bg-clx-surface rounded-3xl shadow-2xl overflow-hidden flex flex-col items-center text-center px-8 pt-8 pb-6 gap-4"
|
|
5583
|
-
>
|
|
5584
|
-
<!-- Icon circle -->
|
|
5585
|
-
<div class="w-20 h-20 rounded-full flex items-center justify-center shrink-0"
|
|
5586
|
-
[class]="_iconBg()">
|
|
5587
|
-
<span clx-icon [name]="_icon()" size="xl" [class]="_iconColor()"></span>
|
|
5588
|
-
</div>
|
|
5589
|
-
|
|
5590
|
-
<!-- Title -->
|
|
5591
|
-
@if (_title()) {
|
|
5592
|
-
<h2
|
|
5593
|
-
class="text-lg font-bold text-clx-text-label leading-snug"
|
|
5594
|
-
[innerHTML]="_title()">
|
|
5595
|
-
</h2>
|
|
5596
|
-
}
|
|
5597
|
-
|
|
5598
|
-
<!-- Message -->
|
|
5599
|
-
@if (_message()) {
|
|
5600
|
-
<p
|
|
5601
|
-
class="text-sm text-clx-text-subtle leading-relaxed"
|
|
5602
|
-
[innerHTML]="_message()">
|
|
5603
|
-
</p>
|
|
5604
|
-
}
|
|
5605
|
-
|
|
5606
|
-
<!-- Buttons -->
|
|
5607
|
-
<div class="flex items-center justify-center gap-3 w-full mt-1">
|
|
5608
|
-
|
|
5609
|
-
@if (_showCancel()) {
|
|
5610
|
-
<button
|
|
5611
|
-
clx-button
|
|
5612
|
-
[color]="_cancelColor()"
|
|
5613
|
-
[variant]="_cancelVariant()"
|
|
5614
|
-
size="md"
|
|
5615
|
-
|
|
5616
|
-
|
|
5617
|
-
|
|
5618
|
-
|
|
5619
|
-
|
|
5620
|
-
|
|
5621
|
-
|
|
5622
|
-
|
|
5623
|
-
|
|
5624
|
-
|
|
5625
|
-
|
|
5626
|
-
|
|
5627
|
-
|
|
5628
|
-
|
|
5629
|
-
|
|
5630
|
-
|
|
5631
|
-
|
|
5632
|
-
|
|
5633
|
-
|
|
5634
|
-
|
|
5635
|
-
|
|
5636
|
-
|
|
5637
|
-
|
|
5638
|
-
|
|
5639
|
-
|
|
5640
|
-
|
|
5641
|
-
|
|
5642
|
-
|
|
5643
|
-
|
|
5224
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.15", type: ClxAlertComponent, isStandalone: true, selector: "clx-alert", ngImport: i0, template: `
|
|
5225
|
+
<!-- Dialog card -->
|
|
5226
|
+
<div
|
|
5227
|
+
#card
|
|
5228
|
+
class="clx-alert-card relative w-full max-w-sm mx-auto bg-clx-surface rounded-3xl shadow-2xl overflow-hidden flex flex-col items-center text-center px-8 pt-8 pb-6 gap-4"
|
|
5229
|
+
>
|
|
5230
|
+
<!-- Icon circle -->
|
|
5231
|
+
<div class="w-20 h-20 rounded-full flex items-center justify-center shrink-0"
|
|
5232
|
+
[class]="_iconBg()">
|
|
5233
|
+
<span clx-icon [name]="_icon()" size="xl" [class]="_iconColor()"></span>
|
|
5234
|
+
</div>
|
|
5235
|
+
|
|
5236
|
+
<!-- Title -->
|
|
5237
|
+
@if (_title()) {
|
|
5238
|
+
<h2
|
|
5239
|
+
class="text-lg font-bold text-clx-text-label leading-snug"
|
|
5240
|
+
[innerHTML]="_title()">
|
|
5241
|
+
</h2>
|
|
5242
|
+
}
|
|
5243
|
+
|
|
5244
|
+
<!-- Message -->
|
|
5245
|
+
@if (_message()) {
|
|
5246
|
+
<p
|
|
5247
|
+
class="text-sm text-clx-text-subtle leading-relaxed"
|
|
5248
|
+
[innerHTML]="_message()">
|
|
5249
|
+
</p>
|
|
5250
|
+
}
|
|
5251
|
+
|
|
5252
|
+
<!-- Buttons -->
|
|
5253
|
+
<div class="flex items-center justify-center gap-3 w-full mt-1">
|
|
5254
|
+
|
|
5255
|
+
@if (_showCancel()) {
|
|
5256
|
+
<button
|
|
5257
|
+
clx-button
|
|
5258
|
+
[color]="_cancelColor()"
|
|
5259
|
+
[variant]="_cancelVariant()"
|
|
5260
|
+
size="md"
|
|
5261
|
+
shape="pill"
|
|
5262
|
+
(click)="dismiss()"
|
|
5263
|
+
>
|
|
5264
|
+
{{ _cancelText() }}
|
|
5265
|
+
</button>
|
|
5266
|
+
}
|
|
5267
|
+
|
|
5268
|
+
<button
|
|
5269
|
+
clx-button
|
|
5270
|
+
[color]="_confirmColor()"
|
|
5271
|
+
variant="solid"
|
|
5272
|
+
size="md"
|
|
5273
|
+
shape="pill"
|
|
5274
|
+
(click)="confirm()"
|
|
5275
|
+
>
|
|
5276
|
+
{{ _confirmText() }}
|
|
5277
|
+
</button>
|
|
5278
|
+
|
|
5279
|
+
</div>
|
|
5280
|
+
|
|
5281
|
+
<!-- Timer progress bar -->
|
|
5282
|
+
@if (_timerTotal() > 0) {
|
|
5283
|
+
<div class="absolute bottom-0 left-0 right-0 h-1 bg-clx-surface-2 rounded-b-3xl overflow-hidden">
|
|
5284
|
+
<div
|
|
5285
|
+
class="h-full transition-none rounded-b-3xl"
|
|
5286
|
+
[class]="_progressColor()"
|
|
5287
|
+
[ngStyle]="{ width: _progressPct() + '%' }">
|
|
5288
|
+
</div>
|
|
5289
|
+
</div>
|
|
5290
|
+
}
|
|
5291
|
+
</div>
|
|
5644
5292
|
`, isInline: true, styles: ["clx-alert{display:flex;align-items:center;justify-content:center;width:100%}.clx-alert-card{will-change:transform,opacity}\n"], dependencies: [{ kind: "component", type: ClxIconComponent, selector: "span[clx-icon]", inputs: ["name", "size", "color", "fill"] }, { kind: "component", type: ClxButtonComponent, selector: "button[clx-button], a[clx-button]", inputs: ["variant", "color", "size", "shape", "loading", "disabled", "block", "icon", "iconPosition", "iconOnly", "badge", "badgeColor"] }, { kind: "directive", type: NgStyle, selector: "[ngStyle]", inputs: ["ngStyle"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None });
|
|
5645
5293
|
}
|
|
5646
5294
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxAlertComponent, decorators: [{
|
|
5647
5295
|
type: Component,
|
|
5648
|
-
args: [{ selector: 'clx-alert', standalone: true, imports: [ClxIconComponent, ClxButtonComponent, NgStyle], encapsulation: ViewEncapsulation.None, changeDetection: ChangeDetectionStrategy.OnPush, template: `
|
|
5649
|
-
<!-- Dialog card -->
|
|
5650
|
-
<div
|
|
5651
|
-
#card
|
|
5652
|
-
class="clx-alert-card relative w-full max-w-sm mx-auto bg-clx-surface rounded-3xl shadow-2xl overflow-hidden flex flex-col items-center text-center px-8 pt-8 pb-6 gap-4"
|
|
5653
|
-
>
|
|
5654
|
-
<!-- Icon circle -->
|
|
5655
|
-
<div class="w-20 h-20 rounded-full flex items-center justify-center shrink-0"
|
|
5656
|
-
[class]="_iconBg()">
|
|
5657
|
-
<span clx-icon [name]="_icon()" size="xl" [class]="_iconColor()"></span>
|
|
5658
|
-
</div>
|
|
5659
|
-
|
|
5660
|
-
<!-- Title -->
|
|
5661
|
-
@if (_title()) {
|
|
5662
|
-
<h2
|
|
5663
|
-
class="text-lg font-bold text-clx-text-label leading-snug"
|
|
5664
|
-
[innerHTML]="_title()">
|
|
5665
|
-
</h2>
|
|
5666
|
-
}
|
|
5667
|
-
|
|
5668
|
-
<!-- Message -->
|
|
5669
|
-
@if (_message()) {
|
|
5670
|
-
<p
|
|
5671
|
-
class="text-sm text-clx-text-subtle leading-relaxed"
|
|
5672
|
-
[innerHTML]="_message()">
|
|
5673
|
-
</p>
|
|
5674
|
-
}
|
|
5675
|
-
|
|
5676
|
-
<!-- Buttons -->
|
|
5677
|
-
<div class="flex items-center justify-center gap-3 w-full mt-1">
|
|
5678
|
-
|
|
5679
|
-
@if (_showCancel()) {
|
|
5680
|
-
<button
|
|
5681
|
-
clx-button
|
|
5682
|
-
[color]="_cancelColor()"
|
|
5683
|
-
[variant]="_cancelVariant()"
|
|
5684
|
-
size="md"
|
|
5685
|
-
|
|
5686
|
-
|
|
5687
|
-
|
|
5688
|
-
|
|
5689
|
-
|
|
5690
|
-
|
|
5691
|
-
|
|
5692
|
-
|
|
5693
|
-
|
|
5694
|
-
|
|
5695
|
-
|
|
5696
|
-
|
|
5697
|
-
|
|
5698
|
-
|
|
5699
|
-
|
|
5700
|
-
|
|
5701
|
-
|
|
5702
|
-
|
|
5703
|
-
|
|
5704
|
-
|
|
5705
|
-
|
|
5706
|
-
|
|
5707
|
-
|
|
5708
|
-
|
|
5709
|
-
|
|
5710
|
-
|
|
5711
|
-
|
|
5712
|
-
|
|
5713
|
-
|
|
5296
|
+
args: [{ selector: 'clx-alert', standalone: true, imports: [ClxIconComponent, ClxButtonComponent, NgStyle], encapsulation: ViewEncapsulation.None, changeDetection: ChangeDetectionStrategy.OnPush, template: `
|
|
5297
|
+
<!-- Dialog card -->
|
|
5298
|
+
<div
|
|
5299
|
+
#card
|
|
5300
|
+
class="clx-alert-card relative w-full max-w-sm mx-auto bg-clx-surface rounded-3xl shadow-2xl overflow-hidden flex flex-col items-center text-center px-8 pt-8 pb-6 gap-4"
|
|
5301
|
+
>
|
|
5302
|
+
<!-- Icon circle -->
|
|
5303
|
+
<div class="w-20 h-20 rounded-full flex items-center justify-center shrink-0"
|
|
5304
|
+
[class]="_iconBg()">
|
|
5305
|
+
<span clx-icon [name]="_icon()" size="xl" [class]="_iconColor()"></span>
|
|
5306
|
+
</div>
|
|
5307
|
+
|
|
5308
|
+
<!-- Title -->
|
|
5309
|
+
@if (_title()) {
|
|
5310
|
+
<h2
|
|
5311
|
+
class="text-lg font-bold text-clx-text-label leading-snug"
|
|
5312
|
+
[innerHTML]="_title()">
|
|
5313
|
+
</h2>
|
|
5314
|
+
}
|
|
5315
|
+
|
|
5316
|
+
<!-- Message -->
|
|
5317
|
+
@if (_message()) {
|
|
5318
|
+
<p
|
|
5319
|
+
class="text-sm text-clx-text-subtle leading-relaxed"
|
|
5320
|
+
[innerHTML]="_message()">
|
|
5321
|
+
</p>
|
|
5322
|
+
}
|
|
5323
|
+
|
|
5324
|
+
<!-- Buttons -->
|
|
5325
|
+
<div class="flex items-center justify-center gap-3 w-full mt-1">
|
|
5326
|
+
|
|
5327
|
+
@if (_showCancel()) {
|
|
5328
|
+
<button
|
|
5329
|
+
clx-button
|
|
5330
|
+
[color]="_cancelColor()"
|
|
5331
|
+
[variant]="_cancelVariant()"
|
|
5332
|
+
size="md"
|
|
5333
|
+
shape="pill"
|
|
5334
|
+
(click)="dismiss()"
|
|
5335
|
+
>
|
|
5336
|
+
{{ _cancelText() }}
|
|
5337
|
+
</button>
|
|
5338
|
+
}
|
|
5339
|
+
|
|
5340
|
+
<button
|
|
5341
|
+
clx-button
|
|
5342
|
+
[color]="_confirmColor()"
|
|
5343
|
+
variant="solid"
|
|
5344
|
+
size="md"
|
|
5345
|
+
shape="pill"
|
|
5346
|
+
(click)="confirm()"
|
|
5347
|
+
>
|
|
5348
|
+
{{ _confirmText() }}
|
|
5349
|
+
</button>
|
|
5350
|
+
|
|
5351
|
+
</div>
|
|
5352
|
+
|
|
5353
|
+
<!-- Timer progress bar -->
|
|
5354
|
+
@if (_timerTotal() > 0) {
|
|
5355
|
+
<div class="absolute bottom-0 left-0 right-0 h-1 bg-clx-surface-2 rounded-b-3xl overflow-hidden">
|
|
5356
|
+
<div
|
|
5357
|
+
class="h-full transition-none rounded-b-3xl"
|
|
5358
|
+
[class]="_progressColor()"
|
|
5359
|
+
[ngStyle]="{ width: _progressPct() + '%' }">
|
|
5360
|
+
</div>
|
|
5361
|
+
</div>
|
|
5362
|
+
}
|
|
5363
|
+
</div>
|
|
5714
5364
|
`, styles: ["clx-alert{display:flex;align-items:center;justify-content:center;width:100%}.clx-alert-card{will-change:transform,opacity}\n"] }]
|
|
5715
5365
|
}], ctorParameters: () => [] });
|
|
5716
5366
|
|
|
@@ -5721,7 +5371,7 @@ const MODAL_SIZE_MAP = {
|
|
|
5721
5371
|
xl: 'w-full',
|
|
5722
5372
|
full: 'w-full h-screen rounded-none',
|
|
5723
5373
|
};
|
|
5724
|
-
const MODAL_CONTAINER_CLASS = 'flex flex-col bg-
|
|
5374
|
+
const MODAL_CONTAINER_CLASS = 'flex flex-col bg-white rounded-2xl shadow-2xl overflow-hidden';
|
|
5725
5375
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
5726
5376
|
const CLX_MODAL_DATA = new InjectionToken('CLX_MODAL_DATA');
|
|
5727
5377
|
const CLX_MODAL_SIZE = new InjectionToken('CLX_MODAL_SIZE');
|
|
@@ -5744,7 +5394,7 @@ const DRAWER_WIDTH_MAP = {
|
|
|
5744
5394
|
md: '420px',
|
|
5745
5395
|
lg: '560px',
|
|
5746
5396
|
};
|
|
5747
|
-
const DRAWER_CONTAINER_CLASS = 'flex flex-col bg-
|
|
5397
|
+
const DRAWER_CONTAINER_CLASS = 'flex flex-col bg-white shadow-2xl overflow-hidden h-screen';
|
|
5748
5398
|
const CLX_DRAWER_SIZE = new InjectionToken('CLX_DRAWER_SIZE');
|
|
5749
5399
|
|
|
5750
5400
|
class ClxDrawerComponent {
|
|
@@ -5771,57 +5421,59 @@ class ClxDrawerComponent {
|
|
|
5771
5421
|
this._modalRef?.close();
|
|
5772
5422
|
}
|
|
5773
5423
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxDrawerComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
5774
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.15", type: ClxDrawerComponent, isStandalone: true, selector: "clx-drawer", inputs: { size: { classPropertyName: "size", publicName: "size", isSignal: true, isRequired: false, transformFunction: null }, showClose: { classPropertyName: "showClose", publicName: "showClose", isSignal: true, isRequired: false, transformFunction: null }, confirmButton: { classPropertyName: "confirmButton", publicName: "confirmButton", isSignal: true, isRequired: false, transformFunction: null }, cancelButton: { classPropertyName: "cancelButton", publicName: "cancelButton", isSignal: true, isRequired: false, transformFunction: null }, showCancelButton: { classPropertyName: "showCancelButton", publicName: "showCancelButton", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { confirmClick: "confirmClick", cancelClick: "cancelClick" }, host: { properties: { "class": "_hostClass()" } }, ngImport: i0, template: `
|
|
5775
|
-
<!-- Header -->
|
|
5776
|
-
<div class="flex items-center gap-3 px-6 py-4 border-b border-clx-border-soft shrink-0">
|
|
5777
|
-
<div class="flex-1 min-w-0">
|
|
5778
|
-
<ng-content select="[clx-drawer-title]" />
|
|
5779
|
-
</div>
|
|
5780
|
-
@if (showClose()) {
|
|
5781
|
-
<button
|
|
5782
|
-
clx-button
|
|
5783
|
-
variant="ghost"
|
|
5784
|
-
color="zinc"
|
|
5785
|
-
shape="circle"
|
|
5786
|
-
size="sm"
|
|
5787
|
-
icon="close"
|
|
5788
|
-
[iconOnly]="true"
|
|
5789
|
-
class="shrink-0 -mr-1"
|
|
5790
|
-
(click)="_close()">
|
|
5791
|
-
</button>
|
|
5792
|
-
}
|
|
5793
|
-
</div>
|
|
5794
|
-
|
|
5795
|
-
<!-- Body -->
|
|
5796
|
-
<div class="flex-1 overflow-y-auto px-6 py-5">
|
|
5797
|
-
<ng-content />
|
|
5798
|
-
</div>
|
|
5799
|
-
|
|
5800
|
-
<!-- Footer -->
|
|
5801
|
-
<div class="flex items-center justify-end gap-3 px-6 py-4 border-t border-clx-border-soft shrink-0">
|
|
5802
|
-
@if (_hasBuiltInButtons()) {
|
|
5803
|
-
@if (showCancelButton()) {
|
|
5804
|
-
<button
|
|
5805
|
-
clx-button
|
|
5806
|
-
[color]="_cancelColor()"
|
|
5807
|
-
[variant]="_cancelVariant()"
|
|
5808
|
-
size="md"
|
|
5809
|
-
|
|
5810
|
-
|
|
5811
|
-
|
|
5812
|
-
|
|
5813
|
-
|
|
5814
|
-
|
|
5815
|
-
|
|
5816
|
-
[
|
|
5817
|
-
|
|
5818
|
-
|
|
5819
|
-
|
|
5820
|
-
|
|
5821
|
-
|
|
5822
|
-
|
|
5823
|
-
}
|
|
5824
|
-
|
|
5424
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.15", type: ClxDrawerComponent, isStandalone: true, selector: "clx-drawer", inputs: { size: { classPropertyName: "size", publicName: "size", isSignal: true, isRequired: false, transformFunction: null }, showClose: { classPropertyName: "showClose", publicName: "showClose", isSignal: true, isRequired: false, transformFunction: null }, confirmButton: { classPropertyName: "confirmButton", publicName: "confirmButton", isSignal: true, isRequired: false, transformFunction: null }, cancelButton: { classPropertyName: "cancelButton", publicName: "cancelButton", isSignal: true, isRequired: false, transformFunction: null }, showCancelButton: { classPropertyName: "showCancelButton", publicName: "showCancelButton", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { confirmClick: "confirmClick", cancelClick: "cancelClick" }, host: { properties: { "class": "_hostClass()" } }, ngImport: i0, template: `
|
|
5425
|
+
<!-- Header -->
|
|
5426
|
+
<div class="flex items-center gap-3 px-6 py-4 border-b border-clx-border-soft shrink-0">
|
|
5427
|
+
<div class="flex-1 min-w-0">
|
|
5428
|
+
<ng-content select="[clx-drawer-title]" />
|
|
5429
|
+
</div>
|
|
5430
|
+
@if (showClose()) {
|
|
5431
|
+
<button
|
|
5432
|
+
clx-button
|
|
5433
|
+
variant="ghost"
|
|
5434
|
+
color="zinc"
|
|
5435
|
+
shape="circle"
|
|
5436
|
+
size="sm"
|
|
5437
|
+
icon="close"
|
|
5438
|
+
[iconOnly]="true"
|
|
5439
|
+
class="shrink-0 -mr-1"
|
|
5440
|
+
(click)="_close()">
|
|
5441
|
+
</button>
|
|
5442
|
+
}
|
|
5443
|
+
</div>
|
|
5444
|
+
|
|
5445
|
+
<!-- Body -->
|
|
5446
|
+
<div class="flex-1 overflow-y-auto px-6 py-5">
|
|
5447
|
+
<ng-content />
|
|
5448
|
+
</div>
|
|
5449
|
+
|
|
5450
|
+
<!-- Footer -->
|
|
5451
|
+
<div class="flex items-center justify-end gap-3 px-6 py-4 border-t border-clx-border-soft shrink-0 bg-clx-surface-2">
|
|
5452
|
+
@if (_hasBuiltInButtons()) {
|
|
5453
|
+
@if (showCancelButton()) {
|
|
5454
|
+
<button
|
|
5455
|
+
clx-button
|
|
5456
|
+
[color]="_cancelColor()"
|
|
5457
|
+
[variant]="_cancelVariant()"
|
|
5458
|
+
size="md"
|
|
5459
|
+
shape="pill"
|
|
5460
|
+
(click)="cancelClick.emit()">
|
|
5461
|
+
{{ _cancelText() }}
|
|
5462
|
+
</button>
|
|
5463
|
+
}
|
|
5464
|
+
<button
|
|
5465
|
+
clx-button
|
|
5466
|
+
[color]="_confirmColor()"
|
|
5467
|
+
[variant]="_confirmVariant()"
|
|
5468
|
+
size="md"
|
|
5469
|
+
shape="pill"
|
|
5470
|
+
(click)="confirmClick.emit()">
|
|
5471
|
+
{{ _confirmText() }}
|
|
5472
|
+
</button>
|
|
5473
|
+
} @else {
|
|
5474
|
+
<ng-content select="[clx-drawer-footer]" />
|
|
5475
|
+
}
|
|
5476
|
+
</div>
|
|
5825
5477
|
`, isInline: true, dependencies: [{ kind: "component", type: ClxButtonComponent, selector: "button[clx-button], a[clx-button]", inputs: ["variant", "color", "size", "shape", "loading", "disabled", "block", "icon", "iconPosition", "iconOnly", "badge", "badgeColor"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None });
|
|
5826
5478
|
}
|
|
5827
5479
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxDrawerComponent, decorators: [{
|
|
@@ -5830,57 +5482,59 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImpo
|
|
|
5830
5482
|
selector: 'clx-drawer',
|
|
5831
5483
|
standalone: true,
|
|
5832
5484
|
imports: [ClxButtonComponent],
|
|
5833
|
-
template: `
|
|
5834
|
-
<!-- Header -->
|
|
5835
|
-
<div class="flex items-center gap-3 px-6 py-4 border-b border-clx-border-soft shrink-0">
|
|
5836
|
-
<div class="flex-1 min-w-0">
|
|
5837
|
-
<ng-content select="[clx-drawer-title]" />
|
|
5838
|
-
</div>
|
|
5839
|
-
@if (showClose()) {
|
|
5840
|
-
<button
|
|
5841
|
-
clx-button
|
|
5842
|
-
variant="ghost"
|
|
5843
|
-
color="zinc"
|
|
5844
|
-
shape="circle"
|
|
5845
|
-
size="sm"
|
|
5846
|
-
icon="close"
|
|
5847
|
-
[iconOnly]="true"
|
|
5848
|
-
class="shrink-0 -mr-1"
|
|
5849
|
-
(click)="_close()">
|
|
5850
|
-
</button>
|
|
5851
|
-
}
|
|
5852
|
-
</div>
|
|
5853
|
-
|
|
5854
|
-
<!-- Body -->
|
|
5855
|
-
<div class="flex-1 overflow-y-auto px-6 py-5">
|
|
5856
|
-
<ng-content />
|
|
5857
|
-
</div>
|
|
5858
|
-
|
|
5859
|
-
<!-- Footer -->
|
|
5860
|
-
<div class="flex items-center justify-end gap-3 px-6 py-4 border-t border-clx-border-soft shrink-0">
|
|
5861
|
-
@if (_hasBuiltInButtons()) {
|
|
5862
|
-
@if (showCancelButton()) {
|
|
5863
|
-
<button
|
|
5864
|
-
clx-button
|
|
5865
|
-
[color]="_cancelColor()"
|
|
5866
|
-
[variant]="_cancelVariant()"
|
|
5867
|
-
size="md"
|
|
5868
|
-
|
|
5869
|
-
|
|
5870
|
-
|
|
5871
|
-
|
|
5872
|
-
|
|
5873
|
-
|
|
5874
|
-
|
|
5875
|
-
[
|
|
5876
|
-
|
|
5877
|
-
|
|
5878
|
-
|
|
5879
|
-
|
|
5880
|
-
|
|
5881
|
-
|
|
5882
|
-
}
|
|
5883
|
-
|
|
5485
|
+
template: `
|
|
5486
|
+
<!-- Header -->
|
|
5487
|
+
<div class="flex items-center gap-3 px-6 py-4 border-b border-clx-border-soft shrink-0">
|
|
5488
|
+
<div class="flex-1 min-w-0">
|
|
5489
|
+
<ng-content select="[clx-drawer-title]" />
|
|
5490
|
+
</div>
|
|
5491
|
+
@if (showClose()) {
|
|
5492
|
+
<button
|
|
5493
|
+
clx-button
|
|
5494
|
+
variant="ghost"
|
|
5495
|
+
color="zinc"
|
|
5496
|
+
shape="circle"
|
|
5497
|
+
size="sm"
|
|
5498
|
+
icon="close"
|
|
5499
|
+
[iconOnly]="true"
|
|
5500
|
+
class="shrink-0 -mr-1"
|
|
5501
|
+
(click)="_close()">
|
|
5502
|
+
</button>
|
|
5503
|
+
}
|
|
5504
|
+
</div>
|
|
5505
|
+
|
|
5506
|
+
<!-- Body -->
|
|
5507
|
+
<div class="flex-1 overflow-y-auto px-6 py-5">
|
|
5508
|
+
<ng-content />
|
|
5509
|
+
</div>
|
|
5510
|
+
|
|
5511
|
+
<!-- Footer -->
|
|
5512
|
+
<div class="flex items-center justify-end gap-3 px-6 py-4 border-t border-clx-border-soft shrink-0 bg-clx-surface-2">
|
|
5513
|
+
@if (_hasBuiltInButtons()) {
|
|
5514
|
+
@if (showCancelButton()) {
|
|
5515
|
+
<button
|
|
5516
|
+
clx-button
|
|
5517
|
+
[color]="_cancelColor()"
|
|
5518
|
+
[variant]="_cancelVariant()"
|
|
5519
|
+
size="md"
|
|
5520
|
+
shape="pill"
|
|
5521
|
+
(click)="cancelClick.emit()">
|
|
5522
|
+
{{ _cancelText() }}
|
|
5523
|
+
</button>
|
|
5524
|
+
}
|
|
5525
|
+
<button
|
|
5526
|
+
clx-button
|
|
5527
|
+
[color]="_confirmColor()"
|
|
5528
|
+
[variant]="_confirmVariant()"
|
|
5529
|
+
size="md"
|
|
5530
|
+
shape="pill"
|
|
5531
|
+
(click)="confirmClick.emit()">
|
|
5532
|
+
{{ _confirmText() }}
|
|
5533
|
+
</button>
|
|
5534
|
+
} @else {
|
|
5535
|
+
<ng-content select="[clx-drawer-footer]" />
|
|
5536
|
+
}
|
|
5537
|
+
</div>
|
|
5884
5538
|
`,
|
|
5885
5539
|
encapsulation: ViewEncapsulation.None,
|
|
5886
5540
|
changeDetection: ChangeDetectionStrategy.OnPush,
|
|
@@ -5895,133 +5549,137 @@ class ClxModalComponent {
|
|
|
5895
5549
|
cancelButton = input(undefined, ...(ngDevMode ? [{ debugName: "cancelButton" }] : /* istanbul ignore next */ []));
|
|
5896
5550
|
showCancelButton = input(false, ...(ngDevMode ? [{ debugName: "showCancelButton" }] : /* istanbul ignore next */ []));
|
|
5897
5551
|
confirmClick = output();
|
|
5898
|
-
cancelClick = output();
|
|
5899
|
-
_modalRef = inject(CLX_MODAL_REF, { optional: true });
|
|
5900
|
-
_sizeToken = inject(CLX_MODAL_SIZE, { optional: true });
|
|
5901
|
-
_themeSvc = inject(ClxThemeService);
|
|
5902
|
-
_resolvedSize = computed(() => this.size() ?? this._sizeToken ?? 'md', ...(ngDevMode ? [{ debugName: "_resolvedSize" }] : /* istanbul ignore next */ []));
|
|
5903
|
-
_hostClass = computed(() => `${MODAL_CONTAINER_CLASS} ${MODAL_SIZE_MAP[this._resolvedSize()]} max-h-[90vh]`, ...(ngDevMode ? [{ debugName: "_hostClass" }] : /* istanbul ignore next */ []));
|
|
5904
|
-
_hasBuiltInButtons = computed(() => !!this.confirmButton(), ...(ngDevMode ? [{ debugName: "_hasBuiltInButtons" }] : /* istanbul ignore next */ []));
|
|
5905
|
-
_confirmText = computed(() => this.confirmButton()?.text ?? 'Aceptar', ...(ngDevMode ? [{ debugName: "_confirmText" }] : /* istanbul ignore next */ []));
|
|
5906
|
-
_confirmColor = computed(() => this.confirmButton()?.color ?? this._themeSvc.config().primaryColor, ...(ngDevMode ? [{ debugName: "_confirmColor" }] : /* istanbul ignore next */ []));
|
|
5907
|
-
_confirmVariant = computed(() => this.confirmButton()?.variant ?? 'solid', ...(ngDevMode ? [{ debugName: "_confirmVariant" }] : /* istanbul ignore next */ []));
|
|
5908
|
-
_cancelText = computed(() => this.cancelButton()?.text ?? 'Cancelar', ...(ngDevMode ? [{ debugName: "_cancelText" }] : /* istanbul ignore next */ []));
|
|
5909
|
-
_cancelColor = computed(() => this.cancelButton()?.color ?? 'slate', ...(ngDevMode ? [{ debugName: "_cancelColor" }] : /* istanbul ignore next */ []));
|
|
5910
|
-
_cancelVariant = computed(() => this.cancelButton()?.variant ?? 'ghost', ...(ngDevMode ? [{ debugName: "_cancelVariant" }] : /* istanbul ignore next */ []));
|
|
5911
|
-
_close() {
|
|
5912
|
-
this._modalRef?.close();
|
|
5913
|
-
}
|
|
5914
|
-
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxModalComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
5915
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.15", type: ClxModalComponent, isStandalone: true, selector: "clx-modal", inputs: { size: { classPropertyName: "size", publicName: "size", isSignal: true, isRequired: false, transformFunction: null }, showClose: { classPropertyName: "showClose", publicName: "showClose", isSignal: true, isRequired: false, transformFunction: null }, confirmButton: { classPropertyName: "confirmButton", publicName: "confirmButton", isSignal: true, isRequired: false, transformFunction: null }, cancelButton: { classPropertyName: "cancelButton", publicName: "cancelButton", isSignal: true, isRequired: false, transformFunction: null }, showCancelButton: { classPropertyName: "showCancelButton", publicName: "showCancelButton", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { confirmClick: "confirmClick", cancelClick: "cancelClick" }, host: { properties: { "class": "_hostClass()" } }, ngImport: i0, template: `
|
|
5916
|
-
<!-- Header -->
|
|
5917
|
-
<div class="flex items-center gap-3 px-6 py-4 border-b border-clx-border-soft shrink-0">
|
|
5918
|
-
<div class="flex-1 min-w-0
|
|
5919
|
-
<ng-content select="[clx-modal-title]" />
|
|
5920
|
-
</div>
|
|
5921
|
-
@if (showClose()) {
|
|
5922
|
-
<button
|
|
5923
|
-
clx-button
|
|
5924
|
-
variant="ghost"
|
|
5925
|
-
color="zinc"
|
|
5926
|
-
shape="circle"
|
|
5927
|
-
size="md"
|
|
5928
|
-
icon="close"
|
|
5929
|
-
[iconOnly]="true"
|
|
5930
|
-
class="shrink-0 -mr-1"
|
|
5931
|
-
(click)="_close()">
|
|
5932
|
-
</button>
|
|
5933
|
-
}
|
|
5934
|
-
</div>
|
|
5935
|
-
|
|
5936
|
-
<!-- Body -->
|
|
5937
|
-
<div cdkScrollable class="flex-1 min-h-0 overflow-y-auto px-6 py-5">
|
|
5938
|
-
<ng-content />
|
|
5939
|
-
</div>
|
|
5940
|
-
|
|
5941
|
-
<!-- Footer -->
|
|
5942
|
-
<div class="flex items-center justify-end gap-3 px-6 py-4 border-t border-clx-border-soft shrink-0">
|
|
5943
|
-
@if (_hasBuiltInButtons()) {
|
|
5944
|
-
@if (showCancelButton()) {
|
|
5945
|
-
<button
|
|
5946
|
-
clx-button
|
|
5947
|
-
[color]="_cancelColor()"
|
|
5948
|
-
[variant]="_cancelVariant()"
|
|
5949
|
-
size="md"
|
|
5950
|
-
|
|
5951
|
-
|
|
5952
|
-
|
|
5953
|
-
|
|
5954
|
-
|
|
5955
|
-
|
|
5956
|
-
|
|
5957
|
-
[
|
|
5958
|
-
|
|
5959
|
-
|
|
5960
|
-
|
|
5961
|
-
|
|
5962
|
-
|
|
5963
|
-
|
|
5964
|
-
}
|
|
5965
|
-
|
|
5966
|
-
|
|
5967
|
-
|
|
5968
|
-
|
|
5969
|
-
|
|
5970
|
-
|
|
5971
|
-
|
|
5972
|
-
|
|
5973
|
-
|
|
5974
|
-
|
|
5975
|
-
|
|
5976
|
-
|
|
5977
|
-
|
|
5978
|
-
|
|
5979
|
-
|
|
5980
|
-
|
|
5981
|
-
|
|
5982
|
-
|
|
5983
|
-
|
|
5984
|
-
|
|
5985
|
-
|
|
5986
|
-
|
|
5987
|
-
|
|
5988
|
-
|
|
5989
|
-
|
|
5990
|
-
|
|
5991
|
-
|
|
5992
|
-
|
|
5993
|
-
|
|
5994
|
-
|
|
5995
|
-
|
|
5996
|
-
|
|
5997
|
-
|
|
5998
|
-
|
|
5999
|
-
|
|
6000
|
-
|
|
6001
|
-
|
|
6002
|
-
|
|
6003
|
-
|
|
6004
|
-
|
|
6005
|
-
|
|
6006
|
-
|
|
6007
|
-
|
|
6008
|
-
|
|
6009
|
-
|
|
6010
|
-
|
|
6011
|
-
|
|
6012
|
-
|
|
6013
|
-
|
|
6014
|
-
|
|
6015
|
-
|
|
6016
|
-
|
|
6017
|
-
|
|
6018
|
-
|
|
6019
|
-
|
|
6020
|
-
|
|
6021
|
-
|
|
6022
|
-
|
|
6023
|
-
|
|
6024
|
-
|
|
5552
|
+
cancelClick = output();
|
|
5553
|
+
_modalRef = inject(CLX_MODAL_REF, { optional: true });
|
|
5554
|
+
_sizeToken = inject(CLX_MODAL_SIZE, { optional: true });
|
|
5555
|
+
_themeSvc = inject(ClxThemeService);
|
|
5556
|
+
_resolvedSize = computed(() => this.size() ?? this._sizeToken ?? 'md', ...(ngDevMode ? [{ debugName: "_resolvedSize" }] : /* istanbul ignore next */ []));
|
|
5557
|
+
_hostClass = computed(() => `${MODAL_CONTAINER_CLASS} ${MODAL_SIZE_MAP[this._resolvedSize()]} max-h-[90vh]`, ...(ngDevMode ? [{ debugName: "_hostClass" }] : /* istanbul ignore next */ []));
|
|
5558
|
+
_hasBuiltInButtons = computed(() => !!this.confirmButton(), ...(ngDevMode ? [{ debugName: "_hasBuiltInButtons" }] : /* istanbul ignore next */ []));
|
|
5559
|
+
_confirmText = computed(() => this.confirmButton()?.text ?? 'Aceptar', ...(ngDevMode ? [{ debugName: "_confirmText" }] : /* istanbul ignore next */ []));
|
|
5560
|
+
_confirmColor = computed(() => this.confirmButton()?.color ?? this._themeSvc.config().primaryColor, ...(ngDevMode ? [{ debugName: "_confirmColor" }] : /* istanbul ignore next */ []));
|
|
5561
|
+
_confirmVariant = computed(() => this.confirmButton()?.variant ?? 'solid', ...(ngDevMode ? [{ debugName: "_confirmVariant" }] : /* istanbul ignore next */ []));
|
|
5562
|
+
_cancelText = computed(() => this.cancelButton()?.text ?? 'Cancelar', ...(ngDevMode ? [{ debugName: "_cancelText" }] : /* istanbul ignore next */ []));
|
|
5563
|
+
_cancelColor = computed(() => this.cancelButton()?.color ?? 'slate', ...(ngDevMode ? [{ debugName: "_cancelColor" }] : /* istanbul ignore next */ []));
|
|
5564
|
+
_cancelVariant = computed(() => this.cancelButton()?.variant ?? 'ghost', ...(ngDevMode ? [{ debugName: "_cancelVariant" }] : /* istanbul ignore next */ []));
|
|
5565
|
+
_close() {
|
|
5566
|
+
this._modalRef?.close();
|
|
5567
|
+
}
|
|
5568
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxModalComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
5569
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.15", type: ClxModalComponent, isStandalone: true, selector: "clx-modal", inputs: { size: { classPropertyName: "size", publicName: "size", isSignal: true, isRequired: false, transformFunction: null }, showClose: { classPropertyName: "showClose", publicName: "showClose", isSignal: true, isRequired: false, transformFunction: null }, confirmButton: { classPropertyName: "confirmButton", publicName: "confirmButton", isSignal: true, isRequired: false, transformFunction: null }, cancelButton: { classPropertyName: "cancelButton", publicName: "cancelButton", isSignal: true, isRequired: false, transformFunction: null }, showCancelButton: { classPropertyName: "showCancelButton", publicName: "showCancelButton", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { confirmClick: "confirmClick", cancelClick: "cancelClick" }, host: { properties: { "class": "_hostClass()" } }, ngImport: i0, template: `
|
|
5570
|
+
<!-- Header -->
|
|
5571
|
+
<div class="flex items-center gap-3 px-6 py-4 border-b border-clx-border-soft shrink-0">
|
|
5572
|
+
<div class="flex-1 min-w-0">
|
|
5573
|
+
<ng-content select="[clx-modal-title]" />
|
|
5574
|
+
</div>
|
|
5575
|
+
@if (showClose()) {
|
|
5576
|
+
<button
|
|
5577
|
+
clx-button
|
|
5578
|
+
variant="ghost"
|
|
5579
|
+
color="zinc"
|
|
5580
|
+
shape="circle"
|
|
5581
|
+
size="md"
|
|
5582
|
+
icon="close"
|
|
5583
|
+
[iconOnly]="true"
|
|
5584
|
+
class="shrink-0 -mr-1"
|
|
5585
|
+
(click)="_close()">
|
|
5586
|
+
</button>
|
|
5587
|
+
}
|
|
5588
|
+
</div>
|
|
5589
|
+
|
|
5590
|
+
<!-- Body -->
|
|
5591
|
+
<div cdkScrollable class="flex-1 min-h-0 overflow-y-auto px-6 py-5">
|
|
5592
|
+
<ng-content />
|
|
5593
|
+
</div>
|
|
5594
|
+
|
|
5595
|
+
<!-- Footer -->
|
|
5596
|
+
<div class="flex items-center justify-end gap-3 px-6 py-4 border-t border-clx-border-soft shrink-0 bg-clx-surface-2">
|
|
5597
|
+
@if (_hasBuiltInButtons()) {
|
|
5598
|
+
@if (showCancelButton()) {
|
|
5599
|
+
<button
|
|
5600
|
+
clx-button
|
|
5601
|
+
[color]="_cancelColor()"
|
|
5602
|
+
[variant]="_cancelVariant()"
|
|
5603
|
+
size="md"
|
|
5604
|
+
shape="pill"
|
|
5605
|
+
(click)="cancelClick.emit()">
|
|
5606
|
+
{{ _cancelText() }}
|
|
5607
|
+
</button>
|
|
5608
|
+
}
|
|
5609
|
+
<button
|
|
5610
|
+
clx-button
|
|
5611
|
+
[color]="_confirmColor()"
|
|
5612
|
+
[variant]="_confirmVariant()"
|
|
5613
|
+
size="md"
|
|
5614
|
+
shape="pill"
|
|
5615
|
+
(click)="confirmClick.emit()">
|
|
5616
|
+
{{ _confirmText() }}
|
|
5617
|
+
</button>
|
|
5618
|
+
} @else {
|
|
5619
|
+
<ng-content select="[clx-modal-footer]" />
|
|
5620
|
+
}
|
|
5621
|
+
</div>
|
|
5622
|
+
`, isInline: true, dependencies: [{ kind: "component", type: ClxButtonComponent, selector: "button[clx-button], a[clx-button]", inputs: ["variant", "color", "size", "shape", "loading", "disabled", "block", "icon", "iconPosition", "iconOnly", "badge", "badgeColor"] }, { kind: "ngmodule", type: ScrollingModule }, { kind: "directive", type: i1$1.CdkScrollable, selector: "[cdk-scrollable], [cdkScrollable]" }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None });
|
|
5623
|
+
}
|
|
5624
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxModalComponent, decorators: [{
|
|
5625
|
+
type: Component,
|
|
5626
|
+
args: [{
|
|
5627
|
+
selector: 'clx-modal',
|
|
5628
|
+
standalone: true,
|
|
5629
|
+
imports: [ClxButtonComponent, ScrollingModule],
|
|
5630
|
+
template: `
|
|
5631
|
+
<!-- Header -->
|
|
5632
|
+
<div class="flex items-center gap-3 px-6 py-4 border-b border-clx-border-soft shrink-0">
|
|
5633
|
+
<div class="flex-1 min-w-0">
|
|
5634
|
+
<ng-content select="[clx-modal-title]" />
|
|
5635
|
+
</div>
|
|
5636
|
+
@if (showClose()) {
|
|
5637
|
+
<button
|
|
5638
|
+
clx-button
|
|
5639
|
+
variant="ghost"
|
|
5640
|
+
color="zinc"
|
|
5641
|
+
shape="circle"
|
|
5642
|
+
size="md"
|
|
5643
|
+
icon="close"
|
|
5644
|
+
[iconOnly]="true"
|
|
5645
|
+
class="shrink-0 -mr-1"
|
|
5646
|
+
(click)="_close()">
|
|
5647
|
+
</button>
|
|
5648
|
+
}
|
|
5649
|
+
</div>
|
|
5650
|
+
|
|
5651
|
+
<!-- Body -->
|
|
5652
|
+
<div cdkScrollable class="flex-1 min-h-0 overflow-y-auto px-6 py-5">
|
|
5653
|
+
<ng-content />
|
|
5654
|
+
</div>
|
|
5655
|
+
|
|
5656
|
+
<!-- Footer -->
|
|
5657
|
+
<div class="flex items-center justify-end gap-3 px-6 py-4 border-t border-clx-border-soft shrink-0 bg-clx-surface-2">
|
|
5658
|
+
@if (_hasBuiltInButtons()) {
|
|
5659
|
+
@if (showCancelButton()) {
|
|
5660
|
+
<button
|
|
5661
|
+
clx-button
|
|
5662
|
+
[color]="_cancelColor()"
|
|
5663
|
+
[variant]="_cancelVariant()"
|
|
5664
|
+
size="md"
|
|
5665
|
+
shape="pill"
|
|
5666
|
+
(click)="cancelClick.emit()">
|
|
5667
|
+
{{ _cancelText() }}
|
|
5668
|
+
</button>
|
|
5669
|
+
}
|
|
5670
|
+
<button
|
|
5671
|
+
clx-button
|
|
5672
|
+
[color]="_confirmColor()"
|
|
5673
|
+
[variant]="_confirmVariant()"
|
|
5674
|
+
size="md"
|
|
5675
|
+
shape="pill"
|
|
5676
|
+
(click)="confirmClick.emit()">
|
|
5677
|
+
{{ _confirmText() }}
|
|
5678
|
+
</button>
|
|
5679
|
+
} @else {
|
|
5680
|
+
<ng-content select="[clx-modal-footer]" />
|
|
5681
|
+
}
|
|
5682
|
+
</div>
|
|
6025
5683
|
`,
|
|
6026
5684
|
encapsulation: ViewEncapsulation.None,
|
|
6027
5685
|
changeDetection: ChangeDetectionStrategy.OnPush,
|
|
@@ -11778,9 +11436,8 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImpo
|
|
|
11778
11436
|
}] } });
|
|
11779
11437
|
|
|
11780
11438
|
class ClxAppLayoutComponent {
|
|
11781
|
-
_zone
|
|
11782
|
-
_document
|
|
11783
|
-
_el = inject(ElementRef);
|
|
11439
|
+
_zone;
|
|
11440
|
+
_document;
|
|
11784
11441
|
activeColor = input(undefined, ...(ngDevMode ? [{ debugName: "activeColor" }] : /* istanbul ignore next */ []));
|
|
11785
11442
|
_sidebarOpen = signal(false, ...(ngDevMode ? [{ debugName: "_sidebarOpen" }] : /* istanbul ignore next */ []));
|
|
11786
11443
|
collapsed = signal(false, ...(ngDevMode ? [{ debugName: "collapsed" }] : /* istanbul ignore next */ []));
|
|
@@ -11788,31 +11445,38 @@ class ClxAppLayoutComponent {
|
|
|
11788
11445
|
_isMobile = signal(true, ...(ngDevMode ? [{ debugName: "_isMobile" }] : /* istanbul ignore next */ []));
|
|
11789
11446
|
collapsedChange = output();
|
|
11790
11447
|
expandedChange = output();
|
|
11448
|
+
constructor() {
|
|
11449
|
+
const zone = inject(NgZone, { optional: true });
|
|
11450
|
+
this._zone = zone ?? { run: (fn) => fn(), runOutsideAngular: (fn) => fn() };
|
|
11451
|
+
this._document = inject(DOCUMENT);
|
|
11452
|
+
}
|
|
11791
11453
|
_showBackdrop = computed(() => this._sidebarOpen() && this._isMobile(), ...(ngDevMode ? [{ debugName: "_showBackdrop" }] : /* istanbul ignore next */ []));
|
|
11792
11454
|
_isExpanded = computed(() => !this.collapsed() || this._hovered(), ...(ngDevMode ? [{ debugName: "_isExpanded" }] : /* istanbul ignore next */ []));
|
|
11793
11455
|
_sidebarCls = computed(() => {
|
|
11794
|
-
const
|
|
11795
|
-
const open = this._sidebarOpen();
|
|
11796
|
-
const collapsed = this.collapsed();
|
|
11456
|
+
const isDesktopCollapsed = this.collapsed() && !this._isMobile();
|
|
11797
11457
|
const hovered = this._hovered();
|
|
11798
|
-
|
|
11799
|
-
if (
|
|
11800
|
-
|
|
11801
|
-
|
|
11802
|
-
|
|
11803
|
-
|
|
11804
|
-
|
|
11805
|
-
|
|
11806
|
-
|
|
11807
|
-
|
|
11458
|
+
let width;
|
|
11459
|
+
if (isDesktopCollapsed && hovered) {
|
|
11460
|
+
width = 'w-72';
|
|
11461
|
+
}
|
|
11462
|
+
else if (isDesktopCollapsed) {
|
|
11463
|
+
width = 'w-20';
|
|
11464
|
+
}
|
|
11465
|
+
else {
|
|
11466
|
+
width = 'w-72';
|
|
11467
|
+
}
|
|
11468
|
+
const isOverlay = isDesktopCollapsed && hovered;
|
|
11469
|
+
return [
|
|
11470
|
+
`fixed inset-y-0 left-0 z-30 ${width} flex flex-col`,
|
|
11471
|
+
'bg-clx-surface border-r border-clx-border overflow-hidden shrink-0',
|
|
11472
|
+
'transition-[width,transform] duration-300 ease-in-out',
|
|
11473
|
+
isOverlay ? 'shadow-2xl' : '',
|
|
11474
|
+
'lg:transition-[width] lg:relative lg:inset-auto lg:z-30 lg:translate-x-0',
|
|
11475
|
+
(!this._isMobile() || this._sidebarOpen()) ? 'translate-x-0' : '-translate-x-full',
|
|
11476
|
+
].join(' ');
|
|
11808
11477
|
}, ...(ngDevMode ? [{ debugName: "_sidebarCls" }] : /* istanbul ignore next */ []));
|
|
11809
11478
|
_mql;
|
|
11810
11479
|
_mqlListener;
|
|
11811
|
-
_resizeTimer = null;
|
|
11812
|
-
_resizeListener;
|
|
11813
|
-
_mouseEnterFn;
|
|
11814
|
-
_mouseLeaveFn;
|
|
11815
|
-
_sidebarEl = null;
|
|
11816
11480
|
ngOnInit() {
|
|
11817
11481
|
const win = this._document.defaultView;
|
|
11818
11482
|
if (!win)
|
|
@@ -11835,58 +11499,9 @@ class ClxAppLayoutComponent {
|
|
|
11835
11499
|
});
|
|
11836
11500
|
};
|
|
11837
11501
|
this._mql.addEventListener('change', this._mqlListener);
|
|
11838
|
-
this._zone.runOutsideAngular(() => {
|
|
11839
|
-
// Suppress all transitions during resize
|
|
11840
|
-
this._resizeListener = () => {
|
|
11841
|
-
this._document.documentElement.classList.add('clx-resizing');
|
|
11842
|
-
if (this._resizeTimer !== null)
|
|
11843
|
-
clearTimeout(this._resizeTimer);
|
|
11844
|
-
this._resizeTimer = setTimeout(() => {
|
|
11845
|
-
this._document.documentElement.classList.remove('clx-resizing');
|
|
11846
|
-
this._resizeTimer = null;
|
|
11847
|
-
}, 150);
|
|
11848
|
-
};
|
|
11849
|
-
win.addEventListener('resize', this._resizeListener, { passive: true });
|
|
11850
|
-
// Sidebar hover outside NgZone — only enters zone when state actually changes
|
|
11851
|
-
this._mouseEnterFn = () => {
|
|
11852
|
-
if (!this.collapsed() || this._isMobile())
|
|
11853
|
-
return;
|
|
11854
|
-
if (!this._hovered()) {
|
|
11855
|
-
this._zone.run(() => {
|
|
11856
|
-
this._hovered.set(true);
|
|
11857
|
-
this.expandedChange.emit(true);
|
|
11858
|
-
});
|
|
11859
|
-
}
|
|
11860
|
-
};
|
|
11861
|
-
this._mouseLeaveFn = () => {
|
|
11862
|
-
if (this._hovered()) {
|
|
11863
|
-
this._zone.run(() => {
|
|
11864
|
-
this._hovered.set(false);
|
|
11865
|
-
this.expandedChange.emit(false);
|
|
11866
|
-
});
|
|
11867
|
-
}
|
|
11868
|
-
};
|
|
11869
|
-
// Attach after a tick so the aside is rendered
|
|
11870
|
-
setTimeout(() => {
|
|
11871
|
-
const host = this._el.nativeElement;
|
|
11872
|
-
this._sidebarEl = host.querySelector('aside');
|
|
11873
|
-
if (this._sidebarEl) {
|
|
11874
|
-
this._sidebarEl.addEventListener('mouseenter', this._mouseEnterFn, { passive: true });
|
|
11875
|
-
this._sidebarEl.addEventListener('mouseleave', this._mouseLeaveFn, { passive: true });
|
|
11876
|
-
}
|
|
11877
|
-
}, 0);
|
|
11878
|
-
});
|
|
11879
11502
|
}
|
|
11880
11503
|
ngOnDestroy() {
|
|
11881
11504
|
this._mql?.removeEventListener('change', this._mqlListener);
|
|
11882
|
-
const win = this._document.defaultView;
|
|
11883
|
-
win?.removeEventListener('resize', this._resizeListener);
|
|
11884
|
-
if (this._resizeTimer !== null)
|
|
11885
|
-
clearTimeout(this._resizeTimer);
|
|
11886
|
-
if (this._sidebarEl) {
|
|
11887
|
-
this._sidebarEl.removeEventListener('mouseenter', this._mouseEnterFn);
|
|
11888
|
-
this._sidebarEl.removeEventListener('mouseleave', this._mouseLeaveFn);
|
|
11889
|
-
}
|
|
11890
11505
|
}
|
|
11891
11506
|
_toggleCollapsed() {
|
|
11892
11507
|
const next = !this.collapsed();
|
|
@@ -11894,122 +11509,144 @@ class ClxAppLayoutComponent {
|
|
|
11894
11509
|
this._hovered.set(false);
|
|
11895
11510
|
this.collapsedChange.emit(next);
|
|
11896
11511
|
}
|
|
11512
|
+
_onSidebarEnter() {
|
|
11513
|
+
if (this.collapsed() && !this._isMobile()) {
|
|
11514
|
+
this._hovered.set(true);
|
|
11515
|
+
this.expandedChange.emit(true);
|
|
11516
|
+
}
|
|
11517
|
+
}
|
|
11518
|
+
_onSidebarLeave() {
|
|
11519
|
+
if (this._hovered()) {
|
|
11520
|
+
this._hovered.set(false);
|
|
11521
|
+
this.expandedChange.emit(false);
|
|
11522
|
+
}
|
|
11523
|
+
}
|
|
11897
11524
|
toggleSidebar() { this._sidebarOpen.update(v => !v); }
|
|
11898
11525
|
openSidebar() { this._sidebarOpen.set(true); }
|
|
11899
11526
|
closeSidebar() { this._sidebarOpen.set(false); }
|
|
11900
11527
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxAppLayoutComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
11901
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.15", type: ClxAppLayoutComponent, isStandalone: true, selector: "clx-app-layout", inputs: { activeColor: { classPropertyName: "activeColor", publicName: "activeColor", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { collapsedChange: "collapsedChange", expandedChange: "expandedChange" }, host: { classAttribute: "flex h-screen overflow-hidden" }, ngImport: i0, template: `
|
|
11902
|
-
<!-- Mobile backdrop -->
|
|
11903
|
-
@if (_showBackdrop()) {
|
|
11904
|
-
<div
|
|
11905
|
-
class="fixed inset-0 z-20 bg-slate-900/60"
|
|
11906
|
-
aria-hidden="true"
|
|
11907
|
-
(click)="closeSidebar()">
|
|
11908
|
-
</div>
|
|
11909
|
-
}
|
|
11910
|
-
|
|
11911
|
-
<!-- Sidebar -->
|
|
11912
|
-
<aside
|
|
11913
|
-
[class]="_sidebarCls()"
|
|
11914
|
-
|
|
11915
|
-
|
|
11916
|
-
|
|
11917
|
-
|
|
11918
|
-
|
|
11919
|
-
|
|
11920
|
-
|
|
11921
|
-
|
|
11922
|
-
|
|
11923
|
-
|
|
11924
|
-
|
|
11925
|
-
|
|
11926
|
-
|
|
11927
|
-
|
|
11928
|
-
|
|
11929
|
-
|
|
11930
|
-
|
|
11931
|
-
|
|
11932
|
-
|
|
11933
|
-
|
|
11934
|
-
|
|
11935
|
-
|
|
11936
|
-
|
|
11937
|
-
|
|
11938
|
-
|
|
11939
|
-
|
|
11940
|
-
|
|
11941
|
-
|
|
11942
|
-
|
|
11943
|
-
|
|
11944
|
-
|
|
11945
|
-
|
|
11946
|
-
|
|
11947
|
-
|
|
11948
|
-
|
|
11949
|
-
|
|
11950
|
-
|
|
11528
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.15", type: ClxAppLayoutComponent, isStandalone: true, selector: "clx-app-layout", inputs: { activeColor: { classPropertyName: "activeColor", publicName: "activeColor", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { collapsedChange: "collapsedChange", expandedChange: "expandedChange" }, host: { classAttribute: "flex h-screen overflow-hidden" }, ngImport: i0, template: `
|
|
11529
|
+
<!-- Mobile backdrop -->
|
|
11530
|
+
@if (_showBackdrop()) {
|
|
11531
|
+
<div
|
|
11532
|
+
class="fixed inset-0 z-20 bg-slate-900/60"
|
|
11533
|
+
aria-hidden="true"
|
|
11534
|
+
(click)="closeSidebar()">
|
|
11535
|
+
</div>
|
|
11536
|
+
}
|
|
11537
|
+
|
|
11538
|
+
<!-- Sidebar -->
|
|
11539
|
+
<aside
|
|
11540
|
+
[class]="_sidebarCls()"
|
|
11541
|
+
(mouseenter)="_onSidebarEnter()"
|
|
11542
|
+
(mouseleave)="_onSidebarLeave()"
|
|
11543
|
+
aria-label="Navegación principal">
|
|
11544
|
+
|
|
11545
|
+
<!-- Brand slot -->
|
|
11546
|
+
<div class="border-b border-slate-700/50 shrink-0 overflow-hidden">
|
|
11547
|
+
<ng-content select="clx-brand"></ng-content>
|
|
11548
|
+
</div>
|
|
11549
|
+
|
|
11550
|
+
<div class="flex flex-col flex-1 min-h-0">
|
|
11551
|
+
<ng-content select="[clx-sidebar]"></ng-content>
|
|
11552
|
+
</div>
|
|
11553
|
+
</aside>
|
|
11554
|
+
|
|
11555
|
+
<!-- Right panel -->
|
|
11556
|
+
<div class="flex-1 flex flex-col overflow-hidden min-w-0">
|
|
11557
|
+
|
|
11558
|
+
<header class="h-16 shrink-0 bg-clx-surface border-b border-clx-border flex items-center z-10 px-4 gap-3">
|
|
11559
|
+
<!-- Toggle button desktop -->
|
|
11560
|
+
<button
|
|
11561
|
+
type="button"
|
|
11562
|
+
class="hidden lg:flex items-center justify-center w-8 h-8 rounded-md text-clx-text-subtle hover:text-clx-text-label hover:bg-clx-surface-2 transition-colors shrink-0"
|
|
11563
|
+
(click)="_toggleCollapsed()">
|
|
11564
|
+
<span clx-icon [name]="collapsed() ? 'menu_open' : 'menu'" size="sm"></span>
|
|
11565
|
+
</button>
|
|
11566
|
+
<!-- Toggle button mobile -->
|
|
11567
|
+
<button
|
|
11568
|
+
type="button"
|
|
11569
|
+
class="flex lg:hidden items-center justify-center w-8 h-8 rounded-md text-clx-text-subtle hover:text-clx-text-label hover:bg-clx-surface-2 transition-colors shrink-0"
|
|
11570
|
+
(click)="toggleSidebar()">
|
|
11571
|
+
<span clx-icon name="menu" size="sm"></span>
|
|
11572
|
+
</button>
|
|
11573
|
+
|
|
11574
|
+
<ng-content select="[clx-header]"></ng-content>
|
|
11575
|
+
</header>
|
|
11576
|
+
|
|
11577
|
+
<main cdkScrollable class="flex-1 overflow-y-auto bg-clx-bg">
|
|
11578
|
+
<ng-content></ng-content>
|
|
11579
|
+
</main>
|
|
11580
|
+
|
|
11581
|
+
</div>
|
|
11582
|
+
`, isInline: true, dependencies: [{ kind: "component", type: ClxIconComponent, selector: "span[clx-icon]", inputs: ["name", "size", "color", "fill"] }, { kind: "directive", type: CdkScrollable, selector: "[cdk-scrollable], [cdkScrollable]" }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None });
|
|
11951
11583
|
}
|
|
11952
11584
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxAppLayoutComponent, decorators: [{
|
|
11953
11585
|
type: Component,
|
|
11954
11586
|
args: [{
|
|
11955
11587
|
selector: 'clx-app-layout',
|
|
11956
11588
|
standalone: true,
|
|
11957
|
-
imports: [ClxIconComponent],
|
|
11958
|
-
template: `
|
|
11959
|
-
<!-- Mobile backdrop -->
|
|
11960
|
-
@if (_showBackdrop()) {
|
|
11961
|
-
<div
|
|
11962
|
-
class="fixed inset-0 z-20 bg-slate-900/60"
|
|
11963
|
-
aria-hidden="true"
|
|
11964
|
-
(click)="closeSidebar()">
|
|
11965
|
-
</div>
|
|
11966
|
-
}
|
|
11967
|
-
|
|
11968
|
-
<!-- Sidebar -->
|
|
11969
|
-
<aside
|
|
11970
|
-
[class]="_sidebarCls()"
|
|
11971
|
-
|
|
11972
|
-
|
|
11973
|
-
|
|
11974
|
-
|
|
11975
|
-
|
|
11976
|
-
|
|
11977
|
-
|
|
11978
|
-
|
|
11979
|
-
|
|
11980
|
-
|
|
11981
|
-
|
|
11982
|
-
|
|
11983
|
-
|
|
11984
|
-
|
|
11985
|
-
|
|
11986
|
-
|
|
11987
|
-
|
|
11988
|
-
|
|
11989
|
-
|
|
11990
|
-
|
|
11991
|
-
|
|
11992
|
-
|
|
11993
|
-
|
|
11994
|
-
|
|
11995
|
-
|
|
11996
|
-
|
|
11997
|
-
|
|
11998
|
-
|
|
11999
|
-
|
|
12000
|
-
|
|
12001
|
-
|
|
12002
|
-
|
|
12003
|
-
|
|
12004
|
-
|
|
12005
|
-
|
|
12006
|
-
|
|
11589
|
+
imports: [ClxIconComponent, CdkScrollable],
|
|
11590
|
+
template: `
|
|
11591
|
+
<!-- Mobile backdrop -->
|
|
11592
|
+
@if (_showBackdrop()) {
|
|
11593
|
+
<div
|
|
11594
|
+
class="fixed inset-0 z-20 bg-slate-900/60"
|
|
11595
|
+
aria-hidden="true"
|
|
11596
|
+
(click)="closeSidebar()">
|
|
11597
|
+
</div>
|
|
11598
|
+
}
|
|
11599
|
+
|
|
11600
|
+
<!-- Sidebar -->
|
|
11601
|
+
<aside
|
|
11602
|
+
[class]="_sidebarCls()"
|
|
11603
|
+
(mouseenter)="_onSidebarEnter()"
|
|
11604
|
+
(mouseleave)="_onSidebarLeave()"
|
|
11605
|
+
aria-label="Navegación principal">
|
|
11606
|
+
|
|
11607
|
+
<!-- Brand slot -->
|
|
11608
|
+
<div class="border-b border-slate-700/50 shrink-0 overflow-hidden">
|
|
11609
|
+
<ng-content select="clx-brand"></ng-content>
|
|
11610
|
+
</div>
|
|
11611
|
+
|
|
11612
|
+
<div class="flex flex-col flex-1 min-h-0">
|
|
11613
|
+
<ng-content select="[clx-sidebar]"></ng-content>
|
|
11614
|
+
</div>
|
|
11615
|
+
</aside>
|
|
11616
|
+
|
|
11617
|
+
<!-- Right panel -->
|
|
11618
|
+
<div class="flex-1 flex flex-col overflow-hidden min-w-0">
|
|
11619
|
+
|
|
11620
|
+
<header class="h-16 shrink-0 bg-clx-surface border-b border-clx-border flex items-center z-10 px-4 gap-3">
|
|
11621
|
+
<!-- Toggle button desktop -->
|
|
11622
|
+
<button
|
|
11623
|
+
type="button"
|
|
11624
|
+
class="hidden lg:flex items-center justify-center w-8 h-8 rounded-md text-clx-text-subtle hover:text-clx-text-label hover:bg-clx-surface-2 transition-colors shrink-0"
|
|
11625
|
+
(click)="_toggleCollapsed()">
|
|
11626
|
+
<span clx-icon [name]="collapsed() ? 'menu_open' : 'menu'" size="sm"></span>
|
|
11627
|
+
</button>
|
|
11628
|
+
<!-- Toggle button mobile -->
|
|
11629
|
+
<button
|
|
11630
|
+
type="button"
|
|
11631
|
+
class="flex lg:hidden items-center justify-center w-8 h-8 rounded-md text-clx-text-subtle hover:text-clx-text-label hover:bg-clx-surface-2 transition-colors shrink-0"
|
|
11632
|
+
(click)="toggleSidebar()">
|
|
11633
|
+
<span clx-icon name="menu" size="sm"></span>
|
|
11634
|
+
</button>
|
|
11635
|
+
|
|
11636
|
+
<ng-content select="[clx-header]"></ng-content>
|
|
11637
|
+
</header>
|
|
11638
|
+
|
|
11639
|
+
<main cdkScrollable class="flex-1 overflow-y-auto bg-clx-bg">
|
|
11640
|
+
<ng-content></ng-content>
|
|
11641
|
+
</main>
|
|
11642
|
+
|
|
11643
|
+
</div>
|
|
12007
11644
|
`,
|
|
12008
11645
|
encapsulation: ViewEncapsulation.None,
|
|
12009
11646
|
changeDetection: ChangeDetectionStrategy.OnPush,
|
|
12010
11647
|
host: { class: 'flex h-screen overflow-hidden' },
|
|
12011
11648
|
}]
|
|
12012
|
-
}], propDecorators: { activeColor: [{ type: i0.Input, args: [{ isSignal: true, alias: "activeColor", required: false }] }], collapsedChange: [{ type: i0.Output, args: ["collapsedChange"] }], expandedChange: [{ type: i0.Output, args: ["expandedChange"] }] } });
|
|
11649
|
+
}], ctorParameters: () => [], propDecorators: { activeColor: [{ type: i0.Input, args: [{ isSignal: true, alias: "activeColor", required: false }] }], collapsedChange: [{ type: i0.Output, args: ["collapsedChange"] }], expandedChange: [{ type: i0.Output, args: ["expandedChange"] }] } });
|
|
12013
11650
|
|
|
12014
11651
|
class ClxBrandComponent {
|
|
12015
11652
|
logo = input.required(...(ngDevMode ? [{ debugName: "logo" }] : /* istanbul ignore next */ []));
|
|
@@ -12056,7 +11693,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImpo
|
|
|
12056
11693
|
}], propDecorators: { logo: [{ type: i0.Input, args: [{ isSignal: true, alias: "logo", required: true }] }], name: [{ type: i0.Input, args: [{ isSignal: true, alias: "name", required: true }] }], description: [{ type: i0.Input, args: [{ isSignal: true, alias: "description", required: false }] }], collapsed: [{ type: i0.Input, args: [{ isSignal: true, alias: "collapsed", required: false }] }] } });
|
|
12057
11694
|
|
|
12058
11695
|
// ── Item geometry ──────────────────────────────────────────────────────────────
|
|
12059
|
-
const NAV_ITEM_BASE = 'flex items-center gap-3 w-full text-sm font-medium cursor-pointer select-none';
|
|
11696
|
+
const NAV_ITEM_BASE = 'flex items-center gap-3 w-full text-sm font-medium transition-colors duration-150 cursor-pointer select-none';
|
|
12060
11697
|
const NAV_ITEM_L1 = 'px-6 py-3';
|
|
12061
11698
|
const NAV_ITEM_L2 = 'pl-4 pr-3 py-2';
|
|
12062
11699
|
const NAV_ITEM_IDLE = 'text-clx-text-subtle';
|
|
@@ -12076,7 +11713,9 @@ class ClxMenuItemComponent {
|
|
|
12076
11713
|
routerLink = input('', ...(ngDevMode ? [{ debugName: "routerLink" }] : /* istanbul ignore next */ []));
|
|
12077
11714
|
routerLinkActiveOptions = input({ exact: false }, ...(ngDevMode ? [{ debugName: "routerLinkActiveOptions" }] : /* istanbul ignore next */ []));
|
|
12078
11715
|
itemClick = output();
|
|
12079
|
-
|
|
11716
|
+
_inheritedColor = signal(null, ...(ngDevMode ? [{ debugName: "_inheritedColor" }] : /* istanbul ignore next */ []));
|
|
11717
|
+
_resolvedColor = computed(() => this._inheritedColor() ?? this.color() ?? this._themeSvc.config().primaryColor, ...(ngDevMode ? [{ debugName: "_resolvedColor" }] : /* istanbul ignore next */ []));
|
|
11718
|
+
inheritColor(c) { this._inheritedColor.set(c); }
|
|
12080
11719
|
_geom = computed(() => {
|
|
12081
11720
|
if (this.collapsed())
|
|
12082
11721
|
return 'w-full py-3 px-0 justify-center';
|
|
@@ -12084,8 +11723,8 @@ class ClxMenuItemComponent {
|
|
|
12084
11723
|
}, ...(ngDevMode ? [{ debugName: "_geom" }] : /* istanbul ignore next */ []));
|
|
12085
11724
|
_iconCls = computed(() => resolveColor(this._resolvedColor()).textSubtle, ...(ngDevMode ? [{ debugName: "_iconCls" }] : /* istanbul ignore next */ []));
|
|
12086
11725
|
_idleCls = computed(() => {
|
|
12087
|
-
const
|
|
12088
|
-
return `${NAV_ITEM_BASE} ${this._geom()} ${
|
|
11726
|
+
const t = resolveColor(this._resolvedColor());
|
|
11727
|
+
return `${NAV_ITEM_BASE} ${this._geom()} ${NAV_ITEM_IDLE} ${t.hoverBgMuted}`;
|
|
12089
11728
|
}, ...(ngDevMode ? [{ debugName: "_idleCls" }] : /* istanbul ignore next */ []));
|
|
12090
11729
|
_activeCls = computed(() => {
|
|
12091
11730
|
const t = resolveColor(this._resolvedColor());
|
|
@@ -12095,36 +11734,36 @@ class ClxMenuItemComponent {
|
|
|
12095
11734
|
return `${NAV_ITEM_BASE} ${this._geom()} ${t.textSubtle} font-semibold border-l-2 ${t.borderLight} !pl-[22px] ${t.hoverBgMuted}`;
|
|
12096
11735
|
}, ...(ngDevMode ? [{ debugName: "_activeCls" }] : /* istanbul ignore next */ []));
|
|
12097
11736
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxMenuItemComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
12098
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.15", type: ClxMenuItemComponent, isStandalone: true, selector: "clx-menu-item", inputs: { label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: true, transformFunction: null }, icon: { classPropertyName: "icon", publicName: "icon", isSignal: true, isRequired: false, transformFunction: null }, active: { classPropertyName: "active", publicName: "active", isSignal: true, isRequired: false, transformFunction: null }, color: { classPropertyName: "color", publicName: "color", isSignal: true, isRequired: false, transformFunction: null }, nested: { classPropertyName: "nested", publicName: "nested", isSignal: true, isRequired: false, transformFunction: null }, collapsed: { classPropertyName: "collapsed", publicName: "collapsed", isSignal: true, isRequired: false, transformFunction: null }, routerLink: { classPropertyName: "routerLink", publicName: "routerLink", isSignal: true, isRequired: false, transformFunction: null }, routerLinkActiveOptions: { classPropertyName: "routerLinkActiveOptions", publicName: "routerLinkActiveOptions", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { itemClick: "itemClick" }, host: { classAttribute: "block" }, ngImport: i0, template: `
|
|
12099
|
-
@if (routerLink()) {
|
|
12100
|
-
<a
|
|
12101
|
-
[routerLink]="routerLink()"
|
|
12102
|
-
routerLinkActive
|
|
12103
|
-
#rla="routerLinkActive"
|
|
12104
|
-
[routerLinkActiveOptions]="routerLinkActiveOptions()"
|
|
12105
|
-
[class]="rla.isActive ? _activeCls() : _idleCls()"
|
|
12106
|
-
[title]="collapsed() ? label() : ''">
|
|
12107
|
-
@if (icon()) {
|
|
12108
|
-
<span clx-icon [name]="icon()" size="sm" [class]="_iconCls()"></span>
|
|
12109
|
-
}
|
|
12110
|
-
@if (!collapsed()) {
|
|
12111
|
-
<span class="flex-1 text-left truncate"
|
|
12112
|
-
}
|
|
12113
|
-
</a>
|
|
12114
|
-
} @else {
|
|
12115
|
-
<button
|
|
12116
|
-
type="button"
|
|
12117
|
-
[class]="active() ? _activeCls() : _idleCls()"
|
|
12118
|
-
[title]="collapsed() ? label() : ''"
|
|
12119
|
-
(click)="itemClick.emit()">
|
|
12120
|
-
@if (icon()) {
|
|
12121
|
-
<span clx-icon [name]="icon()" size="sm" [class]="_iconCls()"></span>
|
|
12122
|
-
}
|
|
12123
|
-
@if (!collapsed()) {
|
|
12124
|
-
<span class="flex-1 text-left truncate"
|
|
12125
|
-
}
|
|
12126
|
-
</button>
|
|
12127
|
-
}
|
|
11737
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.15", type: ClxMenuItemComponent, isStandalone: true, selector: "clx-menu-item", inputs: { label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: true, transformFunction: null }, icon: { classPropertyName: "icon", publicName: "icon", isSignal: true, isRequired: false, transformFunction: null }, active: { classPropertyName: "active", publicName: "active", isSignal: true, isRequired: false, transformFunction: null }, color: { classPropertyName: "color", publicName: "color", isSignal: true, isRequired: false, transformFunction: null }, nested: { classPropertyName: "nested", publicName: "nested", isSignal: true, isRequired: false, transformFunction: null }, collapsed: { classPropertyName: "collapsed", publicName: "collapsed", isSignal: true, isRequired: false, transformFunction: null }, routerLink: { classPropertyName: "routerLink", publicName: "routerLink", isSignal: true, isRequired: false, transformFunction: null }, routerLinkActiveOptions: { classPropertyName: "routerLinkActiveOptions", publicName: "routerLinkActiveOptions", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { itemClick: "itemClick" }, host: { classAttribute: "block" }, ngImport: i0, template: `
|
|
11738
|
+
@if (routerLink()) {
|
|
11739
|
+
<a
|
|
11740
|
+
[routerLink]="routerLink()"
|
|
11741
|
+
routerLinkActive
|
|
11742
|
+
#rla="routerLinkActive"
|
|
11743
|
+
[routerLinkActiveOptions]="routerLinkActiveOptions()"
|
|
11744
|
+
[class]="rla.isActive ? _activeCls() : _idleCls()"
|
|
11745
|
+
[title]="collapsed() ? label() : ''">
|
|
11746
|
+
@if (icon()) {
|
|
11747
|
+
<span clx-icon [name]="icon()" size="sm" [class]="rla.isActive ? _iconCls() : 'text-clx-text-subtle'"></span>
|
|
11748
|
+
}
|
|
11749
|
+
@if (!collapsed()) {
|
|
11750
|
+
<span class="flex-1 text-left truncate">{{ label() }}</span>
|
|
11751
|
+
}
|
|
11752
|
+
</a>
|
|
11753
|
+
} @else {
|
|
11754
|
+
<button
|
|
11755
|
+
type="button"
|
|
11756
|
+
[class]="active() ? _activeCls() : _idleCls()"
|
|
11757
|
+
[title]="collapsed() ? label() : ''"
|
|
11758
|
+
(click)="itemClick.emit()">
|
|
11759
|
+
@if (icon()) {
|
|
11760
|
+
<span clx-icon [name]="icon()" size="sm" [class]="active() ? _iconCls() : 'text-clx-text-subtle'"></span>
|
|
11761
|
+
}
|
|
11762
|
+
@if (!collapsed()) {
|
|
11763
|
+
<span class="flex-1 text-left truncate">{{ label() }}</span>
|
|
11764
|
+
}
|
|
11765
|
+
</button>
|
|
11766
|
+
}
|
|
12128
11767
|
`, isInline: true, dependencies: [{ kind: "component", type: ClxIconComponent, selector: "span[clx-icon]", inputs: ["name", "size", "color", "fill"] }, { kind: "directive", type: RouterLink, selector: "[routerLink]", inputs: ["target", "queryParams", "fragment", "queryParamsHandling", "state", "info", "relativeTo", "preserveFragment", "skipLocationChange", "replaceUrl", "routerLink"] }, { kind: "directive", type: RouterLinkActive, selector: "[routerLinkActive]", inputs: ["routerLinkActiveOptions", "ariaCurrentWhenActive", "routerLinkActive"], outputs: ["isActiveChange"], exportAs: ["routerLinkActive"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None });
|
|
12129
11768
|
}
|
|
12130
11769
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxMenuItemComponent, decorators: [{
|
|
@@ -12133,36 +11772,36 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImpo
|
|
|
12133
11772
|
selector: 'clx-menu-item',
|
|
12134
11773
|
standalone: true,
|
|
12135
11774
|
imports: [ClxIconComponent, RouterLink, RouterLinkActive],
|
|
12136
|
-
template: `
|
|
12137
|
-
@if (routerLink()) {
|
|
12138
|
-
<a
|
|
12139
|
-
[routerLink]="routerLink()"
|
|
12140
|
-
routerLinkActive
|
|
12141
|
-
#rla="routerLinkActive"
|
|
12142
|
-
[routerLinkActiveOptions]="routerLinkActiveOptions()"
|
|
12143
|
-
[class]="rla.isActive ? _activeCls() : _idleCls()"
|
|
12144
|
-
[title]="collapsed() ? label() : ''">
|
|
12145
|
-
@if (icon()) {
|
|
12146
|
-
<span clx-icon [name]="icon()" size="sm" [class]="_iconCls()"></span>
|
|
12147
|
-
}
|
|
12148
|
-
@if (!collapsed()) {
|
|
12149
|
-
<span class="flex-1 text-left truncate"
|
|
12150
|
-
}
|
|
12151
|
-
</a>
|
|
12152
|
-
} @else {
|
|
12153
|
-
<button
|
|
12154
|
-
type="button"
|
|
12155
|
-
[class]="active() ? _activeCls() : _idleCls()"
|
|
12156
|
-
[title]="collapsed() ? label() : ''"
|
|
12157
|
-
(click)="itemClick.emit()">
|
|
12158
|
-
@if (icon()) {
|
|
12159
|
-
<span clx-icon [name]="icon()" size="sm" [class]="_iconCls()"></span>
|
|
12160
|
-
}
|
|
12161
|
-
@if (!collapsed()) {
|
|
12162
|
-
<span class="flex-1 text-left truncate"
|
|
12163
|
-
}
|
|
12164
|
-
</button>
|
|
12165
|
-
}
|
|
11775
|
+
template: `
|
|
11776
|
+
@if (routerLink()) {
|
|
11777
|
+
<a
|
|
11778
|
+
[routerLink]="routerLink()"
|
|
11779
|
+
routerLinkActive
|
|
11780
|
+
#rla="routerLinkActive"
|
|
11781
|
+
[routerLinkActiveOptions]="routerLinkActiveOptions()"
|
|
11782
|
+
[class]="rla.isActive ? _activeCls() : _idleCls()"
|
|
11783
|
+
[title]="collapsed() ? label() : ''">
|
|
11784
|
+
@if (icon()) {
|
|
11785
|
+
<span clx-icon [name]="icon()" size="sm" [class]="rla.isActive ? _iconCls() : 'text-clx-text-subtle'"></span>
|
|
11786
|
+
}
|
|
11787
|
+
@if (!collapsed()) {
|
|
11788
|
+
<span class="flex-1 text-left truncate">{{ label() }}</span>
|
|
11789
|
+
}
|
|
11790
|
+
</a>
|
|
11791
|
+
} @else {
|
|
11792
|
+
<button
|
|
11793
|
+
type="button"
|
|
11794
|
+
[class]="active() ? _activeCls() : _idleCls()"
|
|
11795
|
+
[title]="collapsed() ? label() : ''"
|
|
11796
|
+
(click)="itemClick.emit()">
|
|
11797
|
+
@if (icon()) {
|
|
11798
|
+
<span clx-icon [name]="icon()" size="sm" [class]="active() ? _iconCls() : 'text-clx-text-subtle'"></span>
|
|
11799
|
+
}
|
|
11800
|
+
@if (!collapsed()) {
|
|
11801
|
+
<span class="flex-1 text-left truncate">{{ label() }}</span>
|
|
11802
|
+
}
|
|
11803
|
+
</button>
|
|
11804
|
+
}
|
|
12166
11805
|
`,
|
|
12167
11806
|
encapsulation: ViewEncapsulation.None,
|
|
12168
11807
|
changeDetection: ChangeDetectionStrategy.OnPush,
|
|
@@ -12175,13 +11814,14 @@ class ClxMenuComponent {
|
|
|
12175
11814
|
label = input.required(...(ngDevMode ? [{ debugName: "label" }] : /* istanbul ignore next */ []));
|
|
12176
11815
|
icon = input('', ...(ngDevMode ? [{ debugName: "icon" }] : /* istanbul ignore next */ []));
|
|
12177
11816
|
color = input(undefined, ...(ngDevMode ? [{ debugName: "color" }] : /* istanbul ignore next */ []));
|
|
12178
|
-
_color = computed(() => this.color() ?? this._themeSvc.
|
|
11817
|
+
_color = computed(() => this.color() ?? this._themeSvc.config().primaryColor, ...(ngDevMode ? [{ debugName: "_color" }] : /* istanbul ignore next */ []));
|
|
12179
11818
|
collapsed = input(false, ...(ngDevMode ? [{ debugName: "collapsed" }] : /* istanbul ignore next */ []));
|
|
12180
11819
|
active = input(false, ...(ngDevMode ? [{ debugName: "active" }] : /* istanbul ignore next */ []));
|
|
12181
11820
|
routerLink = input('', ...(ngDevMode ? [{ debugName: "routerLink" }] : /* istanbul ignore next */ []));
|
|
12182
11821
|
routerLinkActiveOptions = input({ exact: false }, ...(ngDevMode ? [{ debugName: "routerLinkActiveOptions" }] : /* istanbul ignore next */ []));
|
|
12183
11822
|
_isExpanded = signal(false, ...(ngDevMode ? [{ debugName: "_isExpanded" }] : /* istanbul ignore next */ []));
|
|
12184
11823
|
_rla;
|
|
11824
|
+
_childItems;
|
|
12185
11825
|
_destroyRef = inject(DestroyRef);
|
|
12186
11826
|
constructor() {
|
|
12187
11827
|
effect(() => { if (this.active())
|
|
@@ -12209,70 +11849,80 @@ class ClxMenuComponent {
|
|
|
12209
11849
|
return `${base} ${t.textSubtle} font-semibold`;
|
|
12210
11850
|
return `${base} ${t.textSubtle} font-semibold border-l-2 ${t.borderLight} !pl-[22px]`;
|
|
12211
11851
|
}
|
|
12212
|
-
return `${base} ${t.hoverBgMuted}`;
|
|
11852
|
+
return `${base} ${NAV_ITEM_IDLE} ${t.hoverBgMuted}`;
|
|
12213
11853
|
}
|
|
12214
11854
|
NAV_CHILDREN_WRAPPER = NAV_CHILDREN_WRAPPER;
|
|
12215
11855
|
NAV_CHILDREN_INNER = NAV_CHILDREN_INNER;
|
|
12216
11856
|
NAV_CHILDREN_LIST = NAV_CHILDREN_LIST;
|
|
11857
|
+
ngAfterContentInit() {
|
|
11858
|
+
this._syncChildren();
|
|
11859
|
+
this._childItems.changes
|
|
11860
|
+
.pipe(takeUntilDestroyed(this._destroyRef))
|
|
11861
|
+
.subscribe(() => this._syncChildren());
|
|
11862
|
+
}
|
|
11863
|
+
_syncChildren() {
|
|
11864
|
+
const color = this._color();
|
|
11865
|
+
this._childItems.forEach(c => c.inheritColor(color));
|
|
11866
|
+
}
|
|
12217
11867
|
_toggle() {
|
|
12218
11868
|
this._isExpanded.update(v => !v);
|
|
12219
11869
|
}
|
|
12220
11870
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxMenuComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
12221
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.15", type: ClxMenuComponent, isStandalone: true, selector: "clx-menu", inputs: { label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: true, transformFunction: null }, icon: { classPropertyName: "icon", publicName: "icon", isSignal: true, isRequired: false, transformFunction: null }, color: { classPropertyName: "color", publicName: "color", isSignal: true, isRequired: false, transformFunction: null }, collapsed: { classPropertyName: "collapsed", publicName: "collapsed", isSignal: true, isRequired: false, transformFunction: null }, active: { classPropertyName: "active", publicName: "active", isSignal: true, isRequired: false, transformFunction: null }, routerLink: { classPropertyName: "routerLink", publicName: "routerLink", isSignal: true, isRequired: false, transformFunction: null }, routerLinkActiveOptions: { classPropertyName: "routerLinkActiveOptions", publicName: "routerLinkActiveOptions", isSignal: true, isRequired: false, transformFunction: null } }, host: { classAttribute: "block" }, viewQueries: [{ propertyName: "_rla", first: true, predicate: RouterLinkActive, descendants: true }], ngImport: i0, template: `
|
|
12222
|
-
@if (routerLink()) {
|
|
12223
|
-
<a
|
|
12224
|
-
[routerLink]="routerLink()"
|
|
12225
|
-
routerLinkActive
|
|
12226
|
-
#rla="routerLinkActive"
|
|
12227
|
-
[routerLinkActiveOptions]="routerLinkActiveOptions()"
|
|
12228
|
-
[class]="_buttonCls(rla.isActive)"
|
|
12229
|
-
[title]="collapsed() ? label() : ''"
|
|
12230
|
-
(click)="$event.preventDefault(); !collapsed() && _toggle()">
|
|
12231
|
-
@if (icon()) {
|
|
12232
|
-
<span clx-icon [name]="icon()" size="sm" [class]="_iconCls()"></span>
|
|
12233
|
-
}
|
|
12234
|
-
@if (!collapsed()) {
|
|
12235
|
-
<span class="flex-1 text-left truncate"
|
|
12236
|
-
<span
|
|
12237
|
-
clx-icon
|
|
12238
|
-
name="expand_more"
|
|
12239
|
-
size="sm"
|
|
12240
|
-
class="shrink-0 transition-transform duration-300"
|
|
12241
|
-
[style.transform]="_isExpanded() ? 'rotate(180deg)' : 'rotate(0deg)'">
|
|
12242
|
-
</span>
|
|
12243
|
-
}
|
|
12244
|
-
</a>
|
|
12245
|
-
} @else {
|
|
12246
|
-
<button
|
|
12247
|
-
type="button"
|
|
12248
|
-
[class]="_buttonCls(active())"
|
|
12249
|
-
[title]="collapsed() ? label() : ''"
|
|
12250
|
-
(click)="!collapsed() && _toggle()">
|
|
12251
|
-
@if (icon()) {
|
|
12252
|
-
<span clx-icon [name]="icon()" size="sm" [class]="_iconCls()"></span>
|
|
12253
|
-
}
|
|
12254
|
-
@if (!collapsed()) {
|
|
12255
|
-
<span class="flex-1 text-left truncate"
|
|
12256
|
-
<span
|
|
12257
|
-
clx-icon
|
|
12258
|
-
name="expand_more"
|
|
12259
|
-
size="sm"
|
|
12260
|
-
class="shrink-0 transition-transform duration-300"
|
|
12261
|
-
[style.transform]="_isExpanded() ? 'rotate(180deg)' : 'rotate(0deg)'">
|
|
12262
|
-
</span>
|
|
12263
|
-
}
|
|
12264
|
-
</button>
|
|
12265
|
-
}
|
|
12266
|
-
|
|
12267
|
-
<div
|
|
12268
|
-
[class]="NAV_CHILDREN_WRAPPER"
|
|
12269
|
-
[style.grid-template-rows]="(!collapsed() && _isExpanded()) ? '1fr' : '0fr'">
|
|
12270
|
-
<div [class]="NAV_CHILDREN_INNER">
|
|
12271
|
-
<div [class]="NAV_CHILDREN_LIST">
|
|
12272
|
-
<ng-content></ng-content>
|
|
12273
|
-
</div>
|
|
12274
|
-
</div>
|
|
12275
|
-
</div>
|
|
11871
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.15", type: ClxMenuComponent, isStandalone: true, selector: "clx-menu", inputs: { label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: true, transformFunction: null }, icon: { classPropertyName: "icon", publicName: "icon", isSignal: true, isRequired: false, transformFunction: null }, color: { classPropertyName: "color", publicName: "color", isSignal: true, isRequired: false, transformFunction: null }, collapsed: { classPropertyName: "collapsed", publicName: "collapsed", isSignal: true, isRequired: false, transformFunction: null }, active: { classPropertyName: "active", publicName: "active", isSignal: true, isRequired: false, transformFunction: null }, routerLink: { classPropertyName: "routerLink", publicName: "routerLink", isSignal: true, isRequired: false, transformFunction: null }, routerLinkActiveOptions: { classPropertyName: "routerLinkActiveOptions", publicName: "routerLinkActiveOptions", isSignal: true, isRequired: false, transformFunction: null } }, host: { classAttribute: "block" }, queries: [{ propertyName: "_childItems", predicate: ClxMenuItemComponent, descendants: true }], viewQueries: [{ propertyName: "_rla", first: true, predicate: RouterLinkActive, descendants: true }], ngImport: i0, template: `
|
|
11872
|
+
@if (routerLink()) {
|
|
11873
|
+
<a
|
|
11874
|
+
[routerLink]="routerLink()"
|
|
11875
|
+
routerLinkActive
|
|
11876
|
+
#rla="routerLinkActive"
|
|
11877
|
+
[routerLinkActiveOptions]="routerLinkActiveOptions()"
|
|
11878
|
+
[class]="_buttonCls(rla.isActive)"
|
|
11879
|
+
[title]="collapsed() ? label() : ''"
|
|
11880
|
+
(click)="$event.preventDefault(); !collapsed() && _toggle()">
|
|
11881
|
+
@if (icon()) {
|
|
11882
|
+
<span clx-icon [name]="icon()" size="sm" [class]="_iconCls()"></span>
|
|
11883
|
+
}
|
|
11884
|
+
@if (!collapsed()) {
|
|
11885
|
+
<span class="flex-1 text-left truncate">{{ label() }}</span>
|
|
11886
|
+
<span
|
|
11887
|
+
clx-icon
|
|
11888
|
+
name="expand_more"
|
|
11889
|
+
size="sm"
|
|
11890
|
+
class="shrink-0 transition-transform duration-300"
|
|
11891
|
+
[style.transform]="_isExpanded() ? 'rotate(180deg)' : 'rotate(0deg)'">
|
|
11892
|
+
</span>
|
|
11893
|
+
}
|
|
11894
|
+
</a>
|
|
11895
|
+
} @else {
|
|
11896
|
+
<button
|
|
11897
|
+
type="button"
|
|
11898
|
+
[class]="_buttonCls(active())"
|
|
11899
|
+
[title]="collapsed() ? label() : ''"
|
|
11900
|
+
(click)="!collapsed() && _toggle()">
|
|
11901
|
+
@if (icon()) {
|
|
11902
|
+
<span clx-icon [name]="icon()" size="sm" [class]="_iconCls()"></span>
|
|
11903
|
+
}
|
|
11904
|
+
@if (!collapsed()) {
|
|
11905
|
+
<span class="flex-1 text-left truncate">{{ label() }}</span>
|
|
11906
|
+
<span
|
|
11907
|
+
clx-icon
|
|
11908
|
+
name="expand_more"
|
|
11909
|
+
size="sm"
|
|
11910
|
+
class="shrink-0 transition-transform duration-300"
|
|
11911
|
+
[style.transform]="_isExpanded() ? 'rotate(180deg)' : 'rotate(0deg)'">
|
|
11912
|
+
</span>
|
|
11913
|
+
}
|
|
11914
|
+
</button>
|
|
11915
|
+
}
|
|
11916
|
+
|
|
11917
|
+
<div
|
|
11918
|
+
[class]="NAV_CHILDREN_WRAPPER"
|
|
11919
|
+
[style.grid-template-rows]="(!collapsed() && _isExpanded()) ? '1fr' : '0fr'">
|
|
11920
|
+
<div [class]="NAV_CHILDREN_INNER">
|
|
11921
|
+
<div [class]="NAV_CHILDREN_LIST">
|
|
11922
|
+
<ng-content></ng-content>
|
|
11923
|
+
</div>
|
|
11924
|
+
</div>
|
|
11925
|
+
</div>
|
|
12276
11926
|
`, isInline: true, dependencies: [{ kind: "component", type: ClxIconComponent, selector: "span[clx-icon]", inputs: ["name", "size", "color", "fill"] }, { kind: "directive", type: RouterLink, selector: "[routerLink]", inputs: ["target", "queryParams", "fragment", "queryParamsHandling", "state", "info", "relativeTo", "preserveFragment", "skipLocationChange", "replaceUrl", "routerLink"] }, { kind: "directive", type: RouterLinkActive, selector: "[routerLinkActive]", inputs: ["routerLinkActiveOptions", "ariaCurrentWhenActive", "routerLinkActive"], outputs: ["isActiveChange"], exportAs: ["routerLinkActive"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None });
|
|
12277
11927
|
}
|
|
12278
11928
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxMenuComponent, decorators: [{
|
|
@@ -12281,61 +11931,61 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImpo
|
|
|
12281
11931
|
selector: 'clx-menu',
|
|
12282
11932
|
standalone: true,
|
|
12283
11933
|
imports: [ClxIconComponent, RouterLink, RouterLinkActive],
|
|
12284
|
-
template: `
|
|
12285
|
-
@if (routerLink()) {
|
|
12286
|
-
<a
|
|
12287
|
-
[routerLink]="routerLink()"
|
|
12288
|
-
routerLinkActive
|
|
12289
|
-
#rla="routerLinkActive"
|
|
12290
|
-
[routerLinkActiveOptions]="routerLinkActiveOptions()"
|
|
12291
|
-
[class]="_buttonCls(rla.isActive)"
|
|
12292
|
-
[title]="collapsed() ? label() : ''"
|
|
12293
|
-
(click)="$event.preventDefault(); !collapsed() && _toggle()">
|
|
12294
|
-
@if (icon()) {
|
|
12295
|
-
<span clx-icon [name]="icon()" size="sm" [class]="_iconCls()"></span>
|
|
12296
|
-
}
|
|
12297
|
-
@if (!collapsed()) {
|
|
12298
|
-
<span class="flex-1 text-left truncate"
|
|
12299
|
-
<span
|
|
12300
|
-
clx-icon
|
|
12301
|
-
name="expand_more"
|
|
12302
|
-
size="sm"
|
|
12303
|
-
class="shrink-0 transition-transform duration-300"
|
|
12304
|
-
[style.transform]="_isExpanded() ? 'rotate(180deg)' : 'rotate(0deg)'">
|
|
12305
|
-
</span>
|
|
12306
|
-
}
|
|
12307
|
-
</a>
|
|
12308
|
-
} @else {
|
|
12309
|
-
<button
|
|
12310
|
-
type="button"
|
|
12311
|
-
[class]="_buttonCls(active())"
|
|
12312
|
-
[title]="collapsed() ? label() : ''"
|
|
12313
|
-
(click)="!collapsed() && _toggle()">
|
|
12314
|
-
@if (icon()) {
|
|
12315
|
-
<span clx-icon [name]="icon()" size="sm" [class]="_iconCls()"></span>
|
|
12316
|
-
}
|
|
12317
|
-
@if (!collapsed()) {
|
|
12318
|
-
<span class="flex-1 text-left truncate"
|
|
12319
|
-
<span
|
|
12320
|
-
clx-icon
|
|
12321
|
-
name="expand_more"
|
|
12322
|
-
size="sm"
|
|
12323
|
-
class="shrink-0 transition-transform duration-300"
|
|
12324
|
-
[style.transform]="_isExpanded() ? 'rotate(180deg)' : 'rotate(0deg)'">
|
|
12325
|
-
</span>
|
|
12326
|
-
}
|
|
12327
|
-
</button>
|
|
12328
|
-
}
|
|
12329
|
-
|
|
12330
|
-
<div
|
|
12331
|
-
[class]="NAV_CHILDREN_WRAPPER"
|
|
12332
|
-
[style.grid-template-rows]="(!collapsed() && _isExpanded()) ? '1fr' : '0fr'">
|
|
12333
|
-
<div [class]="NAV_CHILDREN_INNER">
|
|
12334
|
-
<div [class]="NAV_CHILDREN_LIST">
|
|
12335
|
-
<ng-content></ng-content>
|
|
12336
|
-
</div>
|
|
12337
|
-
</div>
|
|
12338
|
-
</div>
|
|
11934
|
+
template: `
|
|
11935
|
+
@if (routerLink()) {
|
|
11936
|
+
<a
|
|
11937
|
+
[routerLink]="routerLink()"
|
|
11938
|
+
routerLinkActive
|
|
11939
|
+
#rla="routerLinkActive"
|
|
11940
|
+
[routerLinkActiveOptions]="routerLinkActiveOptions()"
|
|
11941
|
+
[class]="_buttonCls(rla.isActive)"
|
|
11942
|
+
[title]="collapsed() ? label() : ''"
|
|
11943
|
+
(click)="$event.preventDefault(); !collapsed() && _toggle()">
|
|
11944
|
+
@if (icon()) {
|
|
11945
|
+
<span clx-icon [name]="icon()" size="sm" [class]="_iconCls()"></span>
|
|
11946
|
+
}
|
|
11947
|
+
@if (!collapsed()) {
|
|
11948
|
+
<span class="flex-1 text-left truncate">{{ label() }}</span>
|
|
11949
|
+
<span
|
|
11950
|
+
clx-icon
|
|
11951
|
+
name="expand_more"
|
|
11952
|
+
size="sm"
|
|
11953
|
+
class="shrink-0 transition-transform duration-300"
|
|
11954
|
+
[style.transform]="_isExpanded() ? 'rotate(180deg)' : 'rotate(0deg)'">
|
|
11955
|
+
</span>
|
|
11956
|
+
}
|
|
11957
|
+
</a>
|
|
11958
|
+
} @else {
|
|
11959
|
+
<button
|
|
11960
|
+
type="button"
|
|
11961
|
+
[class]="_buttonCls(active())"
|
|
11962
|
+
[title]="collapsed() ? label() : ''"
|
|
11963
|
+
(click)="!collapsed() && _toggle()">
|
|
11964
|
+
@if (icon()) {
|
|
11965
|
+
<span clx-icon [name]="icon()" size="sm" [class]="_iconCls()"></span>
|
|
11966
|
+
}
|
|
11967
|
+
@if (!collapsed()) {
|
|
11968
|
+
<span class="flex-1 text-left truncate">{{ label() }}</span>
|
|
11969
|
+
<span
|
|
11970
|
+
clx-icon
|
|
11971
|
+
name="expand_more"
|
|
11972
|
+
size="sm"
|
|
11973
|
+
class="shrink-0 transition-transform duration-300"
|
|
11974
|
+
[style.transform]="_isExpanded() ? 'rotate(180deg)' : 'rotate(0deg)'">
|
|
11975
|
+
</span>
|
|
11976
|
+
}
|
|
11977
|
+
</button>
|
|
11978
|
+
}
|
|
11979
|
+
|
|
11980
|
+
<div
|
|
11981
|
+
[class]="NAV_CHILDREN_WRAPPER"
|
|
11982
|
+
[style.grid-template-rows]="(!collapsed() && _isExpanded()) ? '1fr' : '0fr'">
|
|
11983
|
+
<div [class]="NAV_CHILDREN_INNER">
|
|
11984
|
+
<div [class]="NAV_CHILDREN_LIST">
|
|
11985
|
+
<ng-content></ng-content>
|
|
11986
|
+
</div>
|
|
11987
|
+
</div>
|
|
11988
|
+
</div>
|
|
12339
11989
|
`,
|
|
12340
11990
|
encapsulation: ViewEncapsulation.None,
|
|
12341
11991
|
changeDetection: ChangeDetectionStrategy.OnPush,
|
|
@@ -12344,25 +11994,23 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImpo
|
|
|
12344
11994
|
}], ctorParameters: () => [], propDecorators: { label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: true }] }], icon: [{ type: i0.Input, args: [{ isSignal: true, alias: "icon", required: false }] }], color: [{ type: i0.Input, args: [{ isSignal: true, alias: "color", required: false }] }], collapsed: [{ type: i0.Input, args: [{ isSignal: true, alias: "collapsed", required: false }] }], active: [{ type: i0.Input, args: [{ isSignal: true, alias: "active", required: false }] }], routerLink: [{ type: i0.Input, args: [{ isSignal: true, alias: "routerLink", required: false }] }], routerLinkActiveOptions: [{ type: i0.Input, args: [{ isSignal: true, alias: "routerLinkActiveOptions", required: false }] }], _rla: [{
|
|
12345
11995
|
type: ViewChild,
|
|
12346
11996
|
args: [RouterLinkActive]
|
|
11997
|
+
}], _childItems: [{
|
|
11998
|
+
type: ContentChildren,
|
|
11999
|
+
args: [ClxMenuItemComponent, { descendants: true }]
|
|
12347
12000
|
}] } });
|
|
12348
12001
|
|
|
12349
12002
|
class ClxNavGroupComponent {
|
|
12350
12003
|
label = input.required(...(ngDevMode ? [{ debugName: "label" }] : /* istanbul ignore next */ []));
|
|
12351
12004
|
collapsed = input(false, ...(ngDevMode ? [{ debugName: "collapsed" }] : /* istanbul ignore next */ []));
|
|
12352
|
-
color = input(undefined, ...(ngDevMode ? [{ debugName: "color" }] : /* istanbul ignore next */ []));
|
|
12353
|
-
labelClass = computed(() => {
|
|
12354
|
-
const c = this.color();
|
|
12355
|
-
return c ? resolveColor(c).textSubtle : 'text-clx-text-subtle';
|
|
12356
|
-
}, ...(ngDevMode ? [{ debugName: "labelClass" }] : /* istanbul ignore next */ []));
|
|
12357
12005
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxNavGroupComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
12358
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.15", type: ClxNavGroupComponent, isStandalone: true, selector: "clx-nav-group", inputs: { label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: true, transformFunction: null }, collapsed: { classPropertyName: "collapsed", publicName: "collapsed", isSignal: true, isRequired: false, transformFunction: null }
|
|
12359
|
-
@if (!collapsed()) {
|
|
12360
|
-
<span class="block px-6 pt-5 pb-1 text-[10px] font-bold uppercase tracking-widest select-none"
|
|
12361
|
-
} @else {
|
|
12362
|
-
<span class="flex items-center justify-center w-full py-3">
|
|
12363
|
-
<span class="w-1.5 h-1.5 rounded-full bg-clx-border"></span>
|
|
12364
|
-
</span>
|
|
12365
|
-
}
|
|
12006
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.15", type: ClxNavGroupComponent, isStandalone: true, selector: "clx-nav-group", inputs: { label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: true, transformFunction: null }, collapsed: { classPropertyName: "collapsed", publicName: "collapsed", isSignal: true, isRequired: false, transformFunction: null } }, host: { classAttribute: "block" }, ngImport: i0, template: `
|
|
12007
|
+
@if (!collapsed()) {
|
|
12008
|
+
<span class="block px-6 pt-5 pb-1 text-[10px] font-bold uppercase tracking-widest text-clx-text-subtle select-none">{{ label() }}</span>
|
|
12009
|
+
} @else {
|
|
12010
|
+
<span class="flex items-center justify-center w-full py-3">
|
|
12011
|
+
<span class="w-1.5 h-1.5 rounded-full bg-clx-border"></span>
|
|
12012
|
+
</span>
|
|
12013
|
+
}
|
|
12366
12014
|
`, isInline: true, changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None });
|
|
12367
12015
|
}
|
|
12368
12016
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxNavGroupComponent, decorators: [{
|
|
@@ -12370,20 +12018,20 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImpo
|
|
|
12370
12018
|
args: [{
|
|
12371
12019
|
selector: 'clx-nav-group',
|
|
12372
12020
|
standalone: true,
|
|
12373
|
-
template: `
|
|
12374
|
-
@if (!collapsed()) {
|
|
12375
|
-
<span class="block px-6 pt-5 pb-1 text-[10px] font-bold uppercase tracking-widest select-none"
|
|
12376
|
-
} @else {
|
|
12377
|
-
<span class="flex items-center justify-center w-full py-3">
|
|
12378
|
-
<span class="w-1.5 h-1.5 rounded-full bg-clx-border"></span>
|
|
12379
|
-
</span>
|
|
12380
|
-
}
|
|
12021
|
+
template: `
|
|
12022
|
+
@if (!collapsed()) {
|
|
12023
|
+
<span class="block px-6 pt-5 pb-1 text-[10px] font-bold uppercase tracking-widest text-clx-text-subtle select-none">{{ label() }}</span>
|
|
12024
|
+
} @else {
|
|
12025
|
+
<span class="flex items-center justify-center w-full py-3">
|
|
12026
|
+
<span class="w-1.5 h-1.5 rounded-full bg-clx-border"></span>
|
|
12027
|
+
</span>
|
|
12028
|
+
}
|
|
12381
12029
|
`,
|
|
12382
12030
|
encapsulation: ViewEncapsulation.None,
|
|
12383
12031
|
changeDetection: ChangeDetectionStrategy.OnPush,
|
|
12384
12032
|
host: { class: 'block' },
|
|
12385
12033
|
}]
|
|
12386
|
-
}], propDecorators: { label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: true }] }], collapsed: [{ type: i0.Input, args: [{ isSignal: true, alias: "collapsed", required: false }] }]
|
|
12034
|
+
}], propDecorators: { label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: true }] }], collapsed: [{ type: i0.Input, args: [{ isSignal: true, alias: "collapsed", required: false }] }] } });
|
|
12387
12035
|
|
|
12388
12036
|
class ClxProfileComponent {
|
|
12389
12037
|
// ── Inputs ──────────────────────────────────────────────────────────────────
|
|
@@ -12604,7 +12252,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImpo
|
|
|
12604
12252
|
// ── Base classes ─────────────────────────────────────────────────────────────
|
|
12605
12253
|
const TABLE_BASE_CLASS = 'w-full text-left border-collapse text-sm';
|
|
12606
12254
|
const TABLE_HEADER_CELL_CLASS = 'px-4 py-3 font-semibold whitespace-nowrap';
|
|
12607
|
-
const TABLE_CELL_CLASS = 'px-4 py-3 border-b border-
|
|
12255
|
+
const TABLE_CELL_CLASS = 'px-4 py-3 border-b border-slate-100 text-slate-700';
|
|
12608
12256
|
const TABLE_ROW_CLASS = '';
|
|
12609
12257
|
// ── Alignment ────────────────────────────────────────────────────────────────
|
|
12610
12258
|
const TABLE_ALIGN_MAP = {
|
|
@@ -12864,25 +12512,20 @@ class ClxTableComponent {
|
|
|
12864
12512
|
_isSelected(item) {
|
|
12865
12513
|
return this.selectedItems().some(s => s === item);
|
|
12866
12514
|
}
|
|
12867
|
-
|
|
12868
|
-
|
|
12869
|
-
|
|
12870
|
-
|
|
12871
|
-
|
|
12872
|
-
|
|
12873
|
-
|
|
12874
|
-
}
|
|
12875
|
-
|
|
12876
|
-
|
|
12877
|
-
|
|
12878
|
-
const
|
|
12879
|
-
|
|
12880
|
-
|
|
12881
|
-
const extra = col.cellClass || '';
|
|
12882
|
-
map.set(col.key, `${TABLE_CELL_CLASS} ${align} ${extra}`.trim());
|
|
12883
|
-
}
|
|
12884
|
-
return map;
|
|
12885
|
-
}, ...(ngDevMode ? [{ debugName: "_dataCellClassMap" }] : /* istanbul ignore next */ []));
|
|
12515
|
+
_getAlignClass(align) {
|
|
12516
|
+
return TABLE_ALIGN_MAP[align];
|
|
12517
|
+
}
|
|
12518
|
+
_getHeaderCellClass(col) {
|
|
12519
|
+
const align = this._getAlignClass(col.align || 'left');
|
|
12520
|
+
const cursor = col.sortable ? 'cursor-pointer select-none' : '';
|
|
12521
|
+
const extra = col.headerClass || '';
|
|
12522
|
+
return `${TABLE_HEADER_CELL_CLASS} ${align} ${cursor} ${extra}`.trim();
|
|
12523
|
+
}
|
|
12524
|
+
_getDataCellClass(col) {
|
|
12525
|
+
const align = this._getAlignClass(col.align || 'left');
|
|
12526
|
+
const extra = col.cellClass || '';
|
|
12527
|
+
return `${TABLE_CELL_CLASS} ${align} ${extra}`.trim();
|
|
12528
|
+
}
|
|
12886
12529
|
_getCellValue(item, key) {
|
|
12887
12530
|
return item[key];
|
|
12888
12531
|
}
|
|
@@ -12924,143 +12567,143 @@ class ClxTableComponent {
|
|
|
12924
12567
|
this.selectionChange.emit({ selected: this.selectedItems(), allSelected: false });
|
|
12925
12568
|
}
|
|
12926
12569
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxTableComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
12927
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.15", type: ClxTableComponent, isStandalone: true, selector: "clx-table", inputs: { data: { classPropertyName: "data", publicName: "data", isSignal: true, isRequired: true, transformFunction: null }, columns: { classPropertyName: "columns", publicName: "columns", isSignal: true, isRequired: false, transformFunction: null }, loading: { classPropertyName: "loading", publicName: "loading", isSignal: true, isRequired: false, transformFunction: null }, selectable: { classPropertyName: "selectable", publicName: "selectable", isSignal: true, isRequired: false, transformFunction: null }, singleSelect: { classPropertyName: "singleSelect", publicName: "singleSelect", isSignal: true, isRequired: false, transformFunction: null }, searchable: { classPropertyName: "searchable", publicName: "searchable", isSignal: true, isRequired: false, transformFunction: null }, pagination: { classPropertyName: "pagination", publicName: "pagination", isSignal: true, isRequired: false, transformFunction: null }, color: { classPropertyName: "color", publicName: "color", isSignal: true, isRequired: false, transformFunction: null }, emptyIcon: { classPropertyName: "emptyIcon", publicName: "emptyIcon", isSignal: true, isRequired: false, transformFunction: null }, emptyTitle: { classPropertyName: "emptyTitle", publicName: "emptyTitle", isSignal: true, isRequired: false, transformFunction: null }, emptyDescription: { classPropertyName: "emptyDescription", publicName: "emptyDescription", isSignal: true, isRequired: false, transformFunction: null }, sortKey: { classPropertyName: "sortKey", publicName: "sortKey", isSignal: true, isRequired: false, transformFunction: null }, sortDir: { classPropertyName: "sortDir", publicName: "sortDir", isSignal: true, isRequired: false, transformFunction: null }, pageIndex: { classPropertyName: "pageIndex", publicName: "pageIndex", isSignal: true, isRequired: false, transformFunction: null }, pageSize: { classPropertyName: "pageSize", publicName: "pageSize", isSignal: true, isRequired: false, transformFunction: null }, _currentPage: { classPropertyName: "_currentPage", publicName: "_currentPage", isSignal: true, isRequired: false, transformFunction: null }, searchQuery: { classPropertyName: "searchQuery", publicName: "searchQuery", isSignal: true, isRequired: false, transformFunction: null }, selectedItems: { classPropertyName: "selectedItems", publicName: "selectedItems", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { sortKey: "sortKeyChange", sortDir: "sortDirChange", pageIndex: "pageIndexChange", pageSize: "pageSizeChange", _currentPage: "_currentPageChange", searchQuery: "searchQueryChange", selectedItems: "selectedItemsChange", sortChange: "sortChange", pageChange: "pageChange", selectionChange: "selectionChange" }, host: { classAttribute: "block" }, queries: [{ propertyName: "_columnDefs", predicate: ClxColumnDefDirective, isSignal: true }], ngImport: i0, template: `
|
|
12928
|
-
<!-- ── Toolbar: búsqueda ──────────────────────────────────────────────── -->
|
|
12929
|
-
@if (searchable() && !loading() && _filteredData().length > 0) {
|
|
12930
|
-
<div class="mb-3 max-w-80 min-w-40">
|
|
12931
|
-
<clx-input
|
|
12932
|
-
placeholder="Buscar..."
|
|
12933
|
-
size="sm"
|
|
12934
|
-
suffixIcon="search"
|
|
12935
|
-
[color]="_color()"
|
|
12936
|
-
[(ngModel)]="searchQuery">
|
|
12937
|
-
</clx-input>
|
|
12938
|
-
</div>
|
|
12939
|
-
}
|
|
12940
|
-
|
|
12941
|
-
@if (loading()) {
|
|
12942
|
-
<!-- ── Loading State ───────────────────────────────────────────────── -->
|
|
12943
|
-
<div class="space-y-3">
|
|
12944
|
-
@for (row of [1, 2, 3, 4, 5]; track row) {
|
|
12945
|
-
<div class="flex items-center gap-4">
|
|
12946
|
-
@if (selectable()) {
|
|
12947
|
-
<clx-skeleton variant="circular" size="xs"></clx-skeleton>
|
|
12948
|
-
}
|
|
12949
|
-
@for (col of columns(); track col.key) {
|
|
12950
|
-
<clx-skeleton variant="text" size="md" [style.flex]="'1'"></clx-skeleton>
|
|
12951
|
-
}
|
|
12952
|
-
</div>
|
|
12953
|
-
}
|
|
12954
|
-
</div>
|
|
12955
|
-
} @else if (_filteredData().length === 0) {
|
|
12956
|
-
<!-- ── Empty State ─────────────────────────────────────────────────── -->
|
|
12957
|
-
<div class="py-10">
|
|
12958
|
-
<clx-page-empty
|
|
12959
|
-
size="sm"
|
|
12960
|
-
[icon]="emptyIcon()"
|
|
12961
|
-
[title]="_emptyTitle()"
|
|
12962
|
-
[description]="_emptyDescription()" />
|
|
12963
|
-
</div>
|
|
12964
|
-
} @else {
|
|
12965
|
-
<!-- ── Tabla ───────────────────────────────────────────────────────── -->
|
|
12966
|
-
<div class="overflow-x-auto">
|
|
12967
|
-
<table [class]="_tableClass()">
|
|
12968
|
-
<thead>
|
|
12969
|
-
<tr [class]="_headerClass()">
|
|
12970
|
-
@if (selectable()) {
|
|
12971
|
-
<th [class]="_headerCellClass()"
|
|
12972
|
-
[class.rounded-tl-lg]="true"
|
|
12973
|
-
[class.rounded-bl-lg]="true"
|
|
12974
|
-
class="w-10 text-center">
|
|
12975
|
-
@if (!singleSelect()) {
|
|
12976
|
-
<clx-checkbox
|
|
12977
|
-
[color]="_color()"
|
|
12978
|
-
[ngModel]="_allSelected()"
|
|
12979
|
-
(ngModelChange)="_handleSelectAll($event)">
|
|
12980
|
-
</clx-checkbox>
|
|
12981
|
-
}
|
|
12982
|
-
</th>
|
|
12983
|
-
}
|
|
12984
|
-
|
|
12985
|
-
@for (col of columns(); track col.key; let first = $first; let last = $last) {
|
|
12986
|
-
<th
|
|
12987
|
-
[class]="
|
|
12988
|
-
[class.rounded-tl-lg]="first && !selectable()"
|
|
12989
|
-
[class.rounded-bl-lg]="first && !selectable()"
|
|
12990
|
-
[class.rounded-tr-lg]="last"
|
|
12991
|
-
[class.rounded-br-lg]="last"
|
|
12992
|
-
[style.width]="col.width"
|
|
12993
|
-
(click)="col.sortable && _handleSort(col.key)">
|
|
12994
|
-
<div class="flex items-center gap-1.5"
|
|
12995
|
-
[class.justify-end]="col.align === 'right'"
|
|
12996
|
-
[class.justify-center]="col.align === 'center'">
|
|
12997
|
-
@if (_getColumnDef(col.key)?.headerCell()?.templateRef; as tpl) {
|
|
12998
|
-
<ng-container [ngTemplateOutlet]="tpl"></ng-container>
|
|
12999
|
-
} @else {
|
|
13000
|
-
<span>{{ col.header || col.key }}</span>
|
|
13001
|
-
}
|
|
13002
|
-
@if (col.sortable) {
|
|
13003
|
-
<span class="opacity-50">
|
|
13004
|
-
@if (sortKey() === col.key && sortDir() === 'asc') {
|
|
13005
|
-
<span clx-icon name="arrow_upward" size="xs"></span>
|
|
13006
|
-
} @else if (sortKey() === col.key && sortDir() === 'desc') {
|
|
13007
|
-
<span clx-icon name="arrow_downward" size="xs"></span>
|
|
13008
|
-
} @else {
|
|
13009
|
-
<span clx-icon name="swap_vert" size="xs"></span>
|
|
13010
|
-
}
|
|
13011
|
-
</span>
|
|
13012
|
-
}
|
|
13013
|
-
</div>
|
|
13014
|
-
</th>
|
|
13015
|
-
}
|
|
13016
|
-
</tr>
|
|
13017
|
-
</thead>
|
|
13018
|
-
|
|
13019
|
-
<tbody>
|
|
13020
|
-
@for (item of _paginatedData(); track i; let i = $index) {
|
|
13021
|
-
<tr [class]="_rowClass()">
|
|
13022
|
-
@if (selectable()) {
|
|
13023
|
-
<td [class]="_cellClass()" class="text-center">
|
|
13024
|
-
<clx-checkbox
|
|
13025
|
-
[color]="_color()"
|
|
13026
|
-
[ngModel]="_isSelected(item)"
|
|
13027
|
-
(ngModelChange)="_handleSelectItem(item, $event)">
|
|
13028
|
-
</clx-checkbox>
|
|
13029
|
-
</td>
|
|
13030
|
-
}
|
|
13031
|
-
|
|
13032
|
-
@for (col of columns(); track col.key) {
|
|
13033
|
-
<td [class]="
|
|
13034
|
-
@if (_getColumnDef(col.key)?.cell()?.templateRef; as tpl) {
|
|
13035
|
-
<ng-container
|
|
13036
|
-
[ngTemplateOutlet]="tpl"
|
|
13037
|
-
[ngTemplateOutletContext]="{ $implicit: item, index: i }">
|
|
13038
|
-
</ng-container>
|
|
13039
|
-
} @else {
|
|
13040
|
-
{{ _getCellValue(item, col.key) }}
|
|
13041
|
-
}
|
|
13042
|
-
</td>
|
|
13043
|
-
}
|
|
13044
|
-
</tr>
|
|
13045
|
-
}
|
|
13046
|
-
</tbody>
|
|
13047
|
-
</table>
|
|
13048
|
-
</div>
|
|
13049
|
-
|
|
13050
|
-
<!-- ── Footer: clx-pagination ────────────────────────────────────────── -->
|
|
13051
|
-
@if (pagination()) {
|
|
13052
|
-
<div class="border-t border-clx-border-soft pt-3">
|
|
13053
|
-
<clx-pagination
|
|
13054
|
-
size="sm"
|
|
13055
|
-
[totalItems]="_totalItems()"
|
|
13056
|
-
[color]="_color()"
|
|
13057
|
-
[(currentPage)]="_currentPage"
|
|
13058
|
-
[(pageSize)]="pageSize"
|
|
13059
|
-
(pageChange)="_onPaginationPageChange($event.page)">
|
|
13060
|
-
</clx-pagination>
|
|
13061
|
-
</div>
|
|
13062
|
-
}
|
|
13063
|
-
}
|
|
12570
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.15", type: ClxTableComponent, isStandalone: true, selector: "clx-table", inputs: { data: { classPropertyName: "data", publicName: "data", isSignal: true, isRequired: true, transformFunction: null }, columns: { classPropertyName: "columns", publicName: "columns", isSignal: true, isRequired: false, transformFunction: null }, loading: { classPropertyName: "loading", publicName: "loading", isSignal: true, isRequired: false, transformFunction: null }, selectable: { classPropertyName: "selectable", publicName: "selectable", isSignal: true, isRequired: false, transformFunction: null }, singleSelect: { classPropertyName: "singleSelect", publicName: "singleSelect", isSignal: true, isRequired: false, transformFunction: null }, searchable: { classPropertyName: "searchable", publicName: "searchable", isSignal: true, isRequired: false, transformFunction: null }, pagination: { classPropertyName: "pagination", publicName: "pagination", isSignal: true, isRequired: false, transformFunction: null }, color: { classPropertyName: "color", publicName: "color", isSignal: true, isRequired: false, transformFunction: null }, emptyIcon: { classPropertyName: "emptyIcon", publicName: "emptyIcon", isSignal: true, isRequired: false, transformFunction: null }, emptyTitle: { classPropertyName: "emptyTitle", publicName: "emptyTitle", isSignal: true, isRequired: false, transformFunction: null }, emptyDescription: { classPropertyName: "emptyDescription", publicName: "emptyDescription", isSignal: true, isRequired: false, transformFunction: null }, sortKey: { classPropertyName: "sortKey", publicName: "sortKey", isSignal: true, isRequired: false, transformFunction: null }, sortDir: { classPropertyName: "sortDir", publicName: "sortDir", isSignal: true, isRequired: false, transformFunction: null }, pageIndex: { classPropertyName: "pageIndex", publicName: "pageIndex", isSignal: true, isRequired: false, transformFunction: null }, pageSize: { classPropertyName: "pageSize", publicName: "pageSize", isSignal: true, isRequired: false, transformFunction: null }, _currentPage: { classPropertyName: "_currentPage", publicName: "_currentPage", isSignal: true, isRequired: false, transformFunction: null }, searchQuery: { classPropertyName: "searchQuery", publicName: "searchQuery", isSignal: true, isRequired: false, transformFunction: null }, selectedItems: { classPropertyName: "selectedItems", publicName: "selectedItems", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { sortKey: "sortKeyChange", sortDir: "sortDirChange", pageIndex: "pageIndexChange", pageSize: "pageSizeChange", _currentPage: "_currentPageChange", searchQuery: "searchQueryChange", selectedItems: "selectedItemsChange", sortChange: "sortChange", pageChange: "pageChange", selectionChange: "selectionChange" }, host: { classAttribute: "block" }, queries: [{ propertyName: "_columnDefs", predicate: ClxColumnDefDirective, isSignal: true }], ngImport: i0, template: `
|
|
12571
|
+
<!-- ── Toolbar: búsqueda ──────────────────────────────────────────────── -->
|
|
12572
|
+
@if (searchable() && !loading() && _filteredData().length > 0) {
|
|
12573
|
+
<div class="mb-3 max-w-80 min-w-40">
|
|
12574
|
+
<clx-input
|
|
12575
|
+
placeholder="Buscar..."
|
|
12576
|
+
size="sm"
|
|
12577
|
+
suffixIcon="search"
|
|
12578
|
+
[color]="_color()"
|
|
12579
|
+
[(ngModel)]="searchQuery">
|
|
12580
|
+
</clx-input>
|
|
12581
|
+
</div>
|
|
12582
|
+
}
|
|
12583
|
+
|
|
12584
|
+
@if (loading()) {
|
|
12585
|
+
<!-- ── Loading State ───────────────────────────────────────────────── -->
|
|
12586
|
+
<div class="space-y-3">
|
|
12587
|
+
@for (row of [1, 2, 3, 4, 5]; track row) {
|
|
12588
|
+
<div class="flex items-center gap-4">
|
|
12589
|
+
@if (selectable()) {
|
|
12590
|
+
<clx-skeleton variant="circular" size="xs"></clx-skeleton>
|
|
12591
|
+
}
|
|
12592
|
+
@for (col of columns(); track col.key) {
|
|
12593
|
+
<clx-skeleton variant="text" size="md" [style.flex]="'1'"></clx-skeleton>
|
|
12594
|
+
}
|
|
12595
|
+
</div>
|
|
12596
|
+
}
|
|
12597
|
+
</div>
|
|
12598
|
+
} @else if (_filteredData().length === 0) {
|
|
12599
|
+
<!-- ── Empty State ─────────────────────────────────────────────────── -->
|
|
12600
|
+
<div class="py-10">
|
|
12601
|
+
<clx-page-empty
|
|
12602
|
+
size="sm"
|
|
12603
|
+
[icon]="emptyIcon()"
|
|
12604
|
+
[title]="_emptyTitle()"
|
|
12605
|
+
[description]="_emptyDescription()" />
|
|
12606
|
+
</div>
|
|
12607
|
+
} @else {
|
|
12608
|
+
<!-- ── Tabla ───────────────────────────────────────────────────────── -->
|
|
12609
|
+
<div class="overflow-x-auto">
|
|
12610
|
+
<table [class]="_tableClass()">
|
|
12611
|
+
<thead>
|
|
12612
|
+
<tr [class]="_headerClass()">
|
|
12613
|
+
@if (selectable()) {
|
|
12614
|
+
<th [class]="_headerCellClass()"
|
|
12615
|
+
[class.rounded-tl-lg]="true"
|
|
12616
|
+
[class.rounded-bl-lg]="true"
|
|
12617
|
+
class="w-10 text-center">
|
|
12618
|
+
@if (!singleSelect()) {
|
|
12619
|
+
<clx-checkbox
|
|
12620
|
+
[color]="_color()"
|
|
12621
|
+
[ngModel]="_allSelected()"
|
|
12622
|
+
(ngModelChange)="_handleSelectAll($event)">
|
|
12623
|
+
</clx-checkbox>
|
|
12624
|
+
}
|
|
12625
|
+
</th>
|
|
12626
|
+
}
|
|
12627
|
+
|
|
12628
|
+
@for (col of columns(); track col.key; let first = $first; let last = $last) {
|
|
12629
|
+
<th
|
|
12630
|
+
[class]="_getHeaderCellClass(col)"
|
|
12631
|
+
[class.rounded-tl-lg]="first && !selectable()"
|
|
12632
|
+
[class.rounded-bl-lg]="first && !selectable()"
|
|
12633
|
+
[class.rounded-tr-lg]="last"
|
|
12634
|
+
[class.rounded-br-lg]="last"
|
|
12635
|
+
[style.width]="col.width"
|
|
12636
|
+
(click)="col.sortable && _handleSort(col.key)">
|
|
12637
|
+
<div class="flex items-center gap-1.5"
|
|
12638
|
+
[class.justify-end]="col.align === 'right'"
|
|
12639
|
+
[class.justify-center]="col.align === 'center'">
|
|
12640
|
+
@if (_getColumnDef(col.key)?.headerCell()?.templateRef; as tpl) {
|
|
12641
|
+
<ng-container [ngTemplateOutlet]="tpl"></ng-container>
|
|
12642
|
+
} @else {
|
|
12643
|
+
<span>{{ col.header || col.key }}</span>
|
|
12644
|
+
}
|
|
12645
|
+
@if (col.sortable) {
|
|
12646
|
+
<span class="opacity-50">
|
|
12647
|
+
@if (sortKey() === col.key && sortDir() === 'asc') {
|
|
12648
|
+
<span clx-icon name="arrow_upward" size="xs"></span>
|
|
12649
|
+
} @else if (sortKey() === col.key && sortDir() === 'desc') {
|
|
12650
|
+
<span clx-icon name="arrow_downward" size="xs"></span>
|
|
12651
|
+
} @else {
|
|
12652
|
+
<span clx-icon name="swap_vert" size="xs"></span>
|
|
12653
|
+
}
|
|
12654
|
+
</span>
|
|
12655
|
+
}
|
|
12656
|
+
</div>
|
|
12657
|
+
</th>
|
|
12658
|
+
}
|
|
12659
|
+
</tr>
|
|
12660
|
+
</thead>
|
|
12661
|
+
|
|
12662
|
+
<tbody>
|
|
12663
|
+
@for (item of _paginatedData(); track i; let i = $index) {
|
|
12664
|
+
<tr [class]="_rowClass()">
|
|
12665
|
+
@if (selectable()) {
|
|
12666
|
+
<td [class]="_cellClass()" class="text-center">
|
|
12667
|
+
<clx-checkbox
|
|
12668
|
+
[color]="_color()"
|
|
12669
|
+
[ngModel]="_isSelected(item)"
|
|
12670
|
+
(ngModelChange)="_handleSelectItem(item, $event)">
|
|
12671
|
+
</clx-checkbox>
|
|
12672
|
+
</td>
|
|
12673
|
+
}
|
|
12674
|
+
|
|
12675
|
+
@for (col of columns(); track col.key) {
|
|
12676
|
+
<td [class]="_getDataCellClass(col)">
|
|
12677
|
+
@if (_getColumnDef(col.key)?.cell()?.templateRef; as tpl) {
|
|
12678
|
+
<ng-container
|
|
12679
|
+
[ngTemplateOutlet]="tpl"
|
|
12680
|
+
[ngTemplateOutletContext]="{ $implicit: item, index: i }">
|
|
12681
|
+
</ng-container>
|
|
12682
|
+
} @else {
|
|
12683
|
+
{{ _getCellValue(item, col.key) }}
|
|
12684
|
+
}
|
|
12685
|
+
</td>
|
|
12686
|
+
}
|
|
12687
|
+
</tr>
|
|
12688
|
+
}
|
|
12689
|
+
</tbody>
|
|
12690
|
+
</table>
|
|
12691
|
+
</div>
|
|
12692
|
+
|
|
12693
|
+
<!-- ── Footer: clx-pagination ────────────────────────────────────────── -->
|
|
12694
|
+
@if (pagination()) {
|
|
12695
|
+
<div class="border-t border-clx-border-soft pt-3">
|
|
12696
|
+
<clx-pagination
|
|
12697
|
+
size="sm"
|
|
12698
|
+
[totalItems]="_totalItems()"
|
|
12699
|
+
[color]="_color()"
|
|
12700
|
+
[(currentPage)]="_currentPage"
|
|
12701
|
+
[(pageSize)]="pageSize"
|
|
12702
|
+
(pageChange)="_onPaginationPageChange($event.page)">
|
|
12703
|
+
</clx-pagination>
|
|
12704
|
+
</div>
|
|
12705
|
+
}
|
|
12706
|
+
}
|
|
13064
12707
|
`, isInline: true, dependencies: [{ kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "directive", type: NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "component", type: ClxCheckboxComponent, selector: "clx-checkbox", inputs: ["color", "variant", "size", "label", "value", "disabled"] }, { kind: "component", type: ClxInputComponent, selector: "clx-input", inputs: ["label", "placeholder", "type", "color", "hint", "prefixIcon", "suffixIcon", "prefixText", "suffixText", "status", "statusMessage", "size", "value", "disabled", "autocomplete"] }, { kind: "component", type: ClxSkeletonComponent, selector: "clx-skeleton", inputs: ["variant", "size", "width", "height"] }, { kind: "component", type: ClxIconComponent, selector: "span[clx-icon]", inputs: ["name", "size", "color", "fill"] }, { kind: "component", type: ClxPaginationComponent, selector: "clx-pagination", inputs: ["totalItems", "color", "size", "showPageSize", "pageSizeOptions", "currentPage", "pageSize"], outputs: ["currentPageChange", "pageSizeChange", "pageChange", "sizeChange"] }, { kind: "component", type: ClxPageEmptyComponent, selector: "clx-page-empty", inputs: ["icon", "title", "description", "ctaLabel", "ctaIcon", "ctaColor", "size"], outputs: ["cta"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None });
|
|
13065
12708
|
}
|
|
13066
12709
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImport: i0, type: ClxTableComponent, decorators: [{
|
|
@@ -13078,143 +12721,143 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImpo
|
|
|
13078
12721
|
ClxPaginationComponent,
|
|
13079
12722
|
ClxPageEmptyComponent,
|
|
13080
12723
|
],
|
|
13081
|
-
template: `
|
|
13082
|
-
<!-- ── Toolbar: búsqueda ──────────────────────────────────────────────── -->
|
|
13083
|
-
@if (searchable() && !loading() && _filteredData().length > 0) {
|
|
13084
|
-
<div class="mb-3 max-w-80 min-w-40">
|
|
13085
|
-
<clx-input
|
|
13086
|
-
placeholder="Buscar..."
|
|
13087
|
-
size="sm"
|
|
13088
|
-
suffixIcon="search"
|
|
13089
|
-
[color]="_color()"
|
|
13090
|
-
[(ngModel)]="searchQuery">
|
|
13091
|
-
</clx-input>
|
|
13092
|
-
</div>
|
|
13093
|
-
}
|
|
13094
|
-
|
|
13095
|
-
@if (loading()) {
|
|
13096
|
-
<!-- ── Loading State ───────────────────────────────────────────────── -->
|
|
13097
|
-
<div class="space-y-3">
|
|
13098
|
-
@for (row of [1, 2, 3, 4, 5]; track row) {
|
|
13099
|
-
<div class="flex items-center gap-4">
|
|
13100
|
-
@if (selectable()) {
|
|
13101
|
-
<clx-skeleton variant="circular" size="xs"></clx-skeleton>
|
|
13102
|
-
}
|
|
13103
|
-
@for (col of columns(); track col.key) {
|
|
13104
|
-
<clx-skeleton variant="text" size="md" [style.flex]="'1'"></clx-skeleton>
|
|
13105
|
-
}
|
|
13106
|
-
</div>
|
|
13107
|
-
}
|
|
13108
|
-
</div>
|
|
13109
|
-
} @else if (_filteredData().length === 0) {
|
|
13110
|
-
<!-- ── Empty State ─────────────────────────────────────────────────── -->
|
|
13111
|
-
<div class="py-10">
|
|
13112
|
-
<clx-page-empty
|
|
13113
|
-
size="sm"
|
|
13114
|
-
[icon]="emptyIcon()"
|
|
13115
|
-
[title]="_emptyTitle()"
|
|
13116
|
-
[description]="_emptyDescription()" />
|
|
13117
|
-
</div>
|
|
13118
|
-
} @else {
|
|
13119
|
-
<!-- ── Tabla ───────────────────────────────────────────────────────── -->
|
|
13120
|
-
<div class="overflow-x-auto">
|
|
13121
|
-
<table [class]="_tableClass()">
|
|
13122
|
-
<thead>
|
|
13123
|
-
<tr [class]="_headerClass()">
|
|
13124
|
-
@if (selectable()) {
|
|
13125
|
-
<th [class]="_headerCellClass()"
|
|
13126
|
-
[class.rounded-tl-lg]="true"
|
|
13127
|
-
[class.rounded-bl-lg]="true"
|
|
13128
|
-
class="w-10 text-center">
|
|
13129
|
-
@if (!singleSelect()) {
|
|
13130
|
-
<clx-checkbox
|
|
13131
|
-
[color]="_color()"
|
|
13132
|
-
[ngModel]="_allSelected()"
|
|
13133
|
-
(ngModelChange)="_handleSelectAll($event)">
|
|
13134
|
-
</clx-checkbox>
|
|
13135
|
-
}
|
|
13136
|
-
</th>
|
|
13137
|
-
}
|
|
13138
|
-
|
|
13139
|
-
@for (col of columns(); track col.key; let first = $first; let last = $last) {
|
|
13140
|
-
<th
|
|
13141
|
-
[class]="
|
|
13142
|
-
[class.rounded-tl-lg]="first && !selectable()"
|
|
13143
|
-
[class.rounded-bl-lg]="first && !selectable()"
|
|
13144
|
-
[class.rounded-tr-lg]="last"
|
|
13145
|
-
[class.rounded-br-lg]="last"
|
|
13146
|
-
[style.width]="col.width"
|
|
13147
|
-
(click)="col.sortable && _handleSort(col.key)">
|
|
13148
|
-
<div class="flex items-center gap-1.5"
|
|
13149
|
-
[class.justify-end]="col.align === 'right'"
|
|
13150
|
-
[class.justify-center]="col.align === 'center'">
|
|
13151
|
-
@if (_getColumnDef(col.key)?.headerCell()?.templateRef; as tpl) {
|
|
13152
|
-
<ng-container [ngTemplateOutlet]="tpl"></ng-container>
|
|
13153
|
-
} @else {
|
|
13154
|
-
<span>{{ col.header || col.key }}</span>
|
|
13155
|
-
}
|
|
13156
|
-
@if (col.sortable) {
|
|
13157
|
-
<span class="opacity-50">
|
|
13158
|
-
@if (sortKey() === col.key && sortDir() === 'asc') {
|
|
13159
|
-
<span clx-icon name="arrow_upward" size="xs"></span>
|
|
13160
|
-
} @else if (sortKey() === col.key && sortDir() === 'desc') {
|
|
13161
|
-
<span clx-icon name="arrow_downward" size="xs"></span>
|
|
13162
|
-
} @else {
|
|
13163
|
-
<span clx-icon name="swap_vert" size="xs"></span>
|
|
13164
|
-
}
|
|
13165
|
-
</span>
|
|
13166
|
-
}
|
|
13167
|
-
</div>
|
|
13168
|
-
</th>
|
|
13169
|
-
}
|
|
13170
|
-
</tr>
|
|
13171
|
-
</thead>
|
|
13172
|
-
|
|
13173
|
-
<tbody>
|
|
13174
|
-
@for (item of _paginatedData(); track i; let i = $index) {
|
|
13175
|
-
<tr [class]="_rowClass()">
|
|
13176
|
-
@if (selectable()) {
|
|
13177
|
-
<td [class]="_cellClass()" class="text-center">
|
|
13178
|
-
<clx-checkbox
|
|
13179
|
-
[color]="_color()"
|
|
13180
|
-
[ngModel]="_isSelected(item)"
|
|
13181
|
-
(ngModelChange)="_handleSelectItem(item, $event)">
|
|
13182
|
-
</clx-checkbox>
|
|
13183
|
-
</td>
|
|
13184
|
-
}
|
|
13185
|
-
|
|
13186
|
-
@for (col of columns(); track col.key) {
|
|
13187
|
-
<td [class]="
|
|
13188
|
-
@if (_getColumnDef(col.key)?.cell()?.templateRef; as tpl) {
|
|
13189
|
-
<ng-container
|
|
13190
|
-
[ngTemplateOutlet]="tpl"
|
|
13191
|
-
[ngTemplateOutletContext]="{ $implicit: item, index: i }">
|
|
13192
|
-
</ng-container>
|
|
13193
|
-
} @else {
|
|
13194
|
-
{{ _getCellValue(item, col.key) }}
|
|
13195
|
-
}
|
|
13196
|
-
</td>
|
|
13197
|
-
}
|
|
13198
|
-
</tr>
|
|
13199
|
-
}
|
|
13200
|
-
</tbody>
|
|
13201
|
-
</table>
|
|
13202
|
-
</div>
|
|
13203
|
-
|
|
13204
|
-
<!-- ── Footer: clx-pagination ────────────────────────────────────────── -->
|
|
13205
|
-
@if (pagination()) {
|
|
13206
|
-
<div class="border-t border-clx-border-soft pt-3">
|
|
13207
|
-
<clx-pagination
|
|
13208
|
-
size="sm"
|
|
13209
|
-
[totalItems]="_totalItems()"
|
|
13210
|
-
[color]="_color()"
|
|
13211
|
-
[(currentPage)]="_currentPage"
|
|
13212
|
-
[(pageSize)]="pageSize"
|
|
13213
|
-
(pageChange)="_onPaginationPageChange($event.page)">
|
|
13214
|
-
</clx-pagination>
|
|
13215
|
-
</div>
|
|
13216
|
-
}
|
|
13217
|
-
}
|
|
12724
|
+
template: `
|
|
12725
|
+
<!-- ── Toolbar: búsqueda ──────────────────────────────────────────────── -->
|
|
12726
|
+
@if (searchable() && !loading() && _filteredData().length > 0) {
|
|
12727
|
+
<div class="mb-3 max-w-80 min-w-40">
|
|
12728
|
+
<clx-input
|
|
12729
|
+
placeholder="Buscar..."
|
|
12730
|
+
size="sm"
|
|
12731
|
+
suffixIcon="search"
|
|
12732
|
+
[color]="_color()"
|
|
12733
|
+
[(ngModel)]="searchQuery">
|
|
12734
|
+
</clx-input>
|
|
12735
|
+
</div>
|
|
12736
|
+
}
|
|
12737
|
+
|
|
12738
|
+
@if (loading()) {
|
|
12739
|
+
<!-- ── Loading State ───────────────────────────────────────────────── -->
|
|
12740
|
+
<div class="space-y-3">
|
|
12741
|
+
@for (row of [1, 2, 3, 4, 5]; track row) {
|
|
12742
|
+
<div class="flex items-center gap-4">
|
|
12743
|
+
@if (selectable()) {
|
|
12744
|
+
<clx-skeleton variant="circular" size="xs"></clx-skeleton>
|
|
12745
|
+
}
|
|
12746
|
+
@for (col of columns(); track col.key) {
|
|
12747
|
+
<clx-skeleton variant="text" size="md" [style.flex]="'1'"></clx-skeleton>
|
|
12748
|
+
}
|
|
12749
|
+
</div>
|
|
12750
|
+
}
|
|
12751
|
+
</div>
|
|
12752
|
+
} @else if (_filteredData().length === 0) {
|
|
12753
|
+
<!-- ── Empty State ─────────────────────────────────────────────────── -->
|
|
12754
|
+
<div class="py-10">
|
|
12755
|
+
<clx-page-empty
|
|
12756
|
+
size="sm"
|
|
12757
|
+
[icon]="emptyIcon()"
|
|
12758
|
+
[title]="_emptyTitle()"
|
|
12759
|
+
[description]="_emptyDescription()" />
|
|
12760
|
+
</div>
|
|
12761
|
+
} @else {
|
|
12762
|
+
<!-- ── Tabla ───────────────────────────────────────────────────────── -->
|
|
12763
|
+
<div class="overflow-x-auto">
|
|
12764
|
+
<table [class]="_tableClass()">
|
|
12765
|
+
<thead>
|
|
12766
|
+
<tr [class]="_headerClass()">
|
|
12767
|
+
@if (selectable()) {
|
|
12768
|
+
<th [class]="_headerCellClass()"
|
|
12769
|
+
[class.rounded-tl-lg]="true"
|
|
12770
|
+
[class.rounded-bl-lg]="true"
|
|
12771
|
+
class="w-10 text-center">
|
|
12772
|
+
@if (!singleSelect()) {
|
|
12773
|
+
<clx-checkbox
|
|
12774
|
+
[color]="_color()"
|
|
12775
|
+
[ngModel]="_allSelected()"
|
|
12776
|
+
(ngModelChange)="_handleSelectAll($event)">
|
|
12777
|
+
</clx-checkbox>
|
|
12778
|
+
}
|
|
12779
|
+
</th>
|
|
12780
|
+
}
|
|
12781
|
+
|
|
12782
|
+
@for (col of columns(); track col.key; let first = $first; let last = $last) {
|
|
12783
|
+
<th
|
|
12784
|
+
[class]="_getHeaderCellClass(col)"
|
|
12785
|
+
[class.rounded-tl-lg]="first && !selectable()"
|
|
12786
|
+
[class.rounded-bl-lg]="first && !selectable()"
|
|
12787
|
+
[class.rounded-tr-lg]="last"
|
|
12788
|
+
[class.rounded-br-lg]="last"
|
|
12789
|
+
[style.width]="col.width"
|
|
12790
|
+
(click)="col.sortable && _handleSort(col.key)">
|
|
12791
|
+
<div class="flex items-center gap-1.5"
|
|
12792
|
+
[class.justify-end]="col.align === 'right'"
|
|
12793
|
+
[class.justify-center]="col.align === 'center'">
|
|
12794
|
+
@if (_getColumnDef(col.key)?.headerCell()?.templateRef; as tpl) {
|
|
12795
|
+
<ng-container [ngTemplateOutlet]="tpl"></ng-container>
|
|
12796
|
+
} @else {
|
|
12797
|
+
<span>{{ col.header || col.key }}</span>
|
|
12798
|
+
}
|
|
12799
|
+
@if (col.sortable) {
|
|
12800
|
+
<span class="opacity-50">
|
|
12801
|
+
@if (sortKey() === col.key && sortDir() === 'asc') {
|
|
12802
|
+
<span clx-icon name="arrow_upward" size="xs"></span>
|
|
12803
|
+
} @else if (sortKey() === col.key && sortDir() === 'desc') {
|
|
12804
|
+
<span clx-icon name="arrow_downward" size="xs"></span>
|
|
12805
|
+
} @else {
|
|
12806
|
+
<span clx-icon name="swap_vert" size="xs"></span>
|
|
12807
|
+
}
|
|
12808
|
+
</span>
|
|
12809
|
+
}
|
|
12810
|
+
</div>
|
|
12811
|
+
</th>
|
|
12812
|
+
}
|
|
12813
|
+
</tr>
|
|
12814
|
+
</thead>
|
|
12815
|
+
|
|
12816
|
+
<tbody>
|
|
12817
|
+
@for (item of _paginatedData(); track i; let i = $index) {
|
|
12818
|
+
<tr [class]="_rowClass()">
|
|
12819
|
+
@if (selectable()) {
|
|
12820
|
+
<td [class]="_cellClass()" class="text-center">
|
|
12821
|
+
<clx-checkbox
|
|
12822
|
+
[color]="_color()"
|
|
12823
|
+
[ngModel]="_isSelected(item)"
|
|
12824
|
+
(ngModelChange)="_handleSelectItem(item, $event)">
|
|
12825
|
+
</clx-checkbox>
|
|
12826
|
+
</td>
|
|
12827
|
+
}
|
|
12828
|
+
|
|
12829
|
+
@for (col of columns(); track col.key) {
|
|
12830
|
+
<td [class]="_getDataCellClass(col)">
|
|
12831
|
+
@if (_getColumnDef(col.key)?.cell()?.templateRef; as tpl) {
|
|
12832
|
+
<ng-container
|
|
12833
|
+
[ngTemplateOutlet]="tpl"
|
|
12834
|
+
[ngTemplateOutletContext]="{ $implicit: item, index: i }">
|
|
12835
|
+
</ng-container>
|
|
12836
|
+
} @else {
|
|
12837
|
+
{{ _getCellValue(item, col.key) }}
|
|
12838
|
+
}
|
|
12839
|
+
</td>
|
|
12840
|
+
}
|
|
12841
|
+
</tr>
|
|
12842
|
+
}
|
|
12843
|
+
</tbody>
|
|
12844
|
+
</table>
|
|
12845
|
+
</div>
|
|
12846
|
+
|
|
12847
|
+
<!-- ── Footer: clx-pagination ────────────────────────────────────────── -->
|
|
12848
|
+
@if (pagination()) {
|
|
12849
|
+
<div class="border-t border-clx-border-soft pt-3">
|
|
12850
|
+
<clx-pagination
|
|
12851
|
+
size="sm"
|
|
12852
|
+
[totalItems]="_totalItems()"
|
|
12853
|
+
[color]="_color()"
|
|
12854
|
+
[(currentPage)]="_currentPage"
|
|
12855
|
+
[(pageSize)]="pageSize"
|
|
12856
|
+
(pageChange)="_onPaginationPageChange($event.page)">
|
|
12857
|
+
</clx-pagination>
|
|
12858
|
+
</div>
|
|
12859
|
+
}
|
|
12860
|
+
}
|
|
13218
12861
|
`,
|
|
13219
12862
|
encapsulation: ViewEncapsulation.None,
|
|
13220
12863
|
changeDetection: ChangeDetectionStrategy.OnPush,
|
|
@@ -15230,5 +14873,5 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.15", ngImpo
|
|
|
15230
14873
|
* Generated bundle index. Do not edit.
|
|
15231
14874
|
*/
|
|
15232
14875
|
|
|
15233
|
-
export { CLX_ADDON_BORDER, CLX_ADDON_TEXT, CLX_ALERT_OPTIONS, CLX_ALERT_RESOLVE, CLX_BG_ADDON, CLX_BG_DISABLED, CLX_BG_ICON_WRAP, CLX_BG_SECTION, CLX_BG_SURFACE, CLX_BORDER_DEFAULT, CLX_BORDER_DISABLED, CLX_BORDER_MEDIUM, CLX_COLOR_HEX, CLX_COLOR_HEX_100, CLX_COLOR_MAP,
|
|
14876
|
+
export { CLX_ADDON_BORDER, CLX_ADDON_TEXT, CLX_ALERT_OPTIONS, CLX_ALERT_RESOLVE, CLX_BG_ADDON, CLX_BG_DISABLED, CLX_BG_ICON_WRAP, CLX_BG_SECTION, CLX_BG_SURFACE, CLX_BORDER_DEFAULT, CLX_BORDER_DISABLED, CLX_BORDER_MEDIUM, CLX_COLOR_HEX, CLX_COLOR_HEX_100, CLX_COLOR_MAP, CLX_MODAL_ANIM_CONFIG, CLX_MODAL_DATA, CLX_MODAL_REF, CLX_OPTION_DISABLED, CLX_PLACEHOLDER, CLX_RADIO_GROUP, CLX_RADIUS_MAP, CLX_TEXT_BODY, CLX_TEXT_DISABLED, CLX_TEXT_HEADING, CLX_TEXT_HINT, CLX_TEXT_IDLE, CLX_TEXT_INPUT, CLX_TEXT_LABEL, CLX_TEXT_OPTION, CLX_TEXT_SUBTITLE, CLX_TEXT_TITLE, CLX_THEME_CONFIG, CLX_THEME_DEFAULTS, CLX_TOAST_DEFAULTS, ClxAlertComponent, ClxAlertService, ClxAnimateDirective, ClxAnimateGroupDirective, ClxAnimateService, ClxAppLayoutComponent, ClxAvatarComponent, ClxBadgeComponent, ClxBrandComponent, ClxButtonComponent, ClxButtonGroupComponent, ClxCardBodyDirective, ClxCardComponent, ClxCardFooterDirective, ClxCardHeaderDirective, ClxCarouselComponent, ClxCarouselDirective, ClxCartComponent, ClxCartSummaryDrawer, ClxCellDirective, ClxChartComponent, ClxCheckboxComponent, ClxColorPickerComponent, ClxColumnDefDirective, ClxDateRangePickerComponent, ClxDatepickerComponent, ClxDrawerComponent, ClxDrawerService, ClxEditorComponent, ClxEditorLinkModalComponent, ClxFilterPanelComponent, ClxHeaderCellDirective, ClxIconComponent, ClxInputComponent, ClxListComponent, ClxListItemComponent, ClxMenuComponent, ClxMenuItemComponent, ClxModalComponent, ClxModalService, ClxNavGroupComponent, ClxNumberComponent, ClxPageEmptyComponent, ClxPageNotFoundComponent, ClxPageServerErrorComponent, ClxPageUnauthorizedComponent, ClxPaginationComponent, ClxProductComponent, ClxProductDetailComponent, ClxProfileComponent, ClxProgressBarComponent, ClxRadioComponent, ClxRadioGroupComponent, ClxRatingComponent, ClxSelectComponent, ClxSkeletonComponent, ClxSliderComponent, ClxSpinnerComponent, ClxStatCardComponent, ClxStepComponent, ClxStepperComponent, ClxSwitchComponent, ClxTabDirective, ClxTableComponent, ClxTabsComponent, ClxTagComponent, ClxTextareaComponent, ClxThemeService, ClxTimelineComponent, ClxTimelineItemComponent, ClxTimepickerComponent, ClxToastComponent, ClxToastContainerComponent, ClxToastService, ClxTooltipComponent, ClxTooltipDirective, ClxTreeComponent, ClxUploadComponent, ClxWishlistComponent, ClxWizardComponent, TIMEPICKER_SIZE_MAP, parseColorInput, provideCodexlyTheme, resolveColor, resolveContainerRadius, resolveRadius };
|
|
15234
14877
|
//# sourceMappingURL=codexly-ui.mjs.map
|