tailjng 0.1.1 → 0.1.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -43,7 +43,8 @@ El CLI instala **dependencias transitivas** automáticamente (ej. `button` → `
43
43
 
44
44
  - Angular **19.2+** (19.x dentro del mismo major; no Angular 20/21 aún)
45
45
  - Tailwind CSS **4.x** (incluido si eliges Tailwind al crear el proyecto con `ng new`)
46
- - Peers: `lucide-angular`, `date-fns`, `exceljs`, `xlsx` (el CLI los instala con `init:app` si faltan)
46
+ -{
47
+ - Peers: `lucide-angular`, `date-fns`, `exceljs`, `xlsx`, `file-saver` (el CLI los instala con `init:app` si faltan)
47
48
  - Estilos globales en **CSS o SCSS** — `init:app` detecta cuál usa tu app
48
49
 
49
50
  ---
@@ -133,13 +134,39 @@ import { JAlertToastComponent } from './tailjng/alert/alert-toast/toast-alert.co
133
134
  <JButton [text]="'Guardar'" classes="primary" [icon]="icons.save" (clicked)="save()" />
134
135
  ```
135
136
 
136
- ### Colores — `JColorsService` (solo npm)
137
+ ### Colores — `JColorsService` + safelist Tailwind
137
138
 
138
- No uses `npx tailjng add color`. Las variantes vienen del servicio:
139
+ Las variantes (`primary`, `success_soft`, …) las resuelve **`JColorsService`** en runtime. Tailwind v4 **no ve** esas clases en el HTML estático, así que el paquete incluye `node_modules/tailjng/src/colors.safelist.css` con `@source inline(...)`.
140
+
141
+ `init:app` importa ese archivo en tu `styles.css` / `styles.scss` automáticamente.
142
+
143
+ **Variantes personalizadas del proyecto:**
144
+
145
+ ```powershell
146
+ npx tailjng add colors-config
147
+ ```
148
+
149
+ Copia `src/app/tailjng/colors/` con:
150
+
151
+ - `colors.config.ts` — define variantes extra (`TAILJNG_COLORS_CONFIG`)
152
+ - `colors.safelist.css` — añade tus clases Tailwind al `@source inline` para que el build las genere
153
+
154
+ Registra el provider en `app.config.ts`:
155
+
156
+ ```typescript
157
+ import { tailjngColorsProvider } from './tailjng/colors/colors.config';
158
+
159
+ providers: [
160
+ tailjngColorsProvider,
161
+ // ...
162
+ ],
163
+ ```
164
+
165
+ Uso en componentes (igual que siempre):
139
166
 
140
167
  ```html
141
- <JButton classes="success" … />
142
- <JBadge classes="warning_soft" … />
168
+ <JButton classes="primary" … />
169
+ <JButton classes="brand" … />
143
170
  ```
144
171
 
145
172
  ### Select con datos estáticos
@@ -23,6 +23,10 @@ const {
23
23
  resolveRuntimePackages,
24
24
  resolveDevPackages,
25
25
  hasTailwindSetup,
26
+ getTailjngSafelistCssImport,
27
+ ensureTailjngSafelistImport,
28
+ alignAngularAnimationsInPackageJson,
29
+ resolveStyleFilePath,
26
30
  fileExists,
27
31
  } = require('../settings/project-utils');
28
32
 
@@ -32,6 +36,7 @@ const RUNTIME_PACKAGES = {
32
36
  'date-fns': '^4.1.0',
33
37
  'exceljs': '^4.4.0',
34
38
  'xlsx': '^0.18.5',
39
+ 'file-saver': '^2.0.5',
35
40
  };
36
41
 
37
42
  const DEV_PACKAGES = {
@@ -92,12 +97,7 @@ function installPackages(workspaceRoot, packages, isDev = false) {
92
97
  });
93
98
  };
94
99
 
95
- try {
96
- run();
97
- } catch {
98
- console.log(`${COLORS.yellow}[tailjng CLI] Retrying with --legacy-peer-deps...${COLORS.reset}`);
99
- run('--legacy-peer-deps');
100
- }
100
+ run('--legacy-peer-deps');
101
101
  }
102
102
 
103
103
  function resolveTargetPath(workspaceRoot, appProject, relativePath, appRootRelative = false) {
@@ -176,15 +176,22 @@ async function runInitApp() {
176
176
  console.log(`${COLORS.yellow}Install it first: npm install tailjng${COLORS.reset}`);
177
177
  }
178
178
 
179
+ // Siempre alinear @angular/animations con la versión real de @angular/core del proyecto
180
+ const animationsAligned = alignAngularAnimationsInPackageJson(workspaceRoot);
181
+ if (animationsAligned.changed) {
182
+ console.log(`${COLORS.cyan}[tailjng CLI] Aligned @angular/animations → ${animationsAligned.version} (same as @angular/core)${COLORS.reset}`);
183
+ Object.assign(packageJson, readJson(packageJsonPath));
184
+ }
185
+
179
186
  if (installDeps) {
180
187
  if (tailwindReady) {
181
188
  console.log(`${COLORS.cyan}[tailjng CLI] Tailwind already configured — skipping Tailwind/PostCSS packages and .postcssrc.json${COLORS.reset}`);
182
189
  }
183
190
 
184
- const runtimePackages = resolveRuntimePackages(packageJson, RUNTIME_PACKAGES);
191
+ const runtimePackages = resolveRuntimePackages(packageJson, RUNTIME_PACKAGES, workspaceRoot);
185
192
  const devPackages = resolveDevPackages(packageJson, DEV_PACKAGES, tailwindReady);
186
- const missingRuntime = Object.fromEntries(getMissingPackages(packageJson, runtimePackages));
187
- const missingDev = Object.fromEntries(getMissingPackages(packageJson, devPackages));
193
+ const missingRuntime = Object.fromEntries(getMissingPackages(packageJson, runtimePackages, workspaceRoot));
194
+ const missingDev = Object.fromEntries(getMissingPackages(packageJson, devPackages, workspaceRoot));
188
195
 
189
196
  if (missingRuntime['@angular/animations']) {
190
197
  console.log(`${COLORS.dim}[tailjng CLI] Adding @angular/animations aligned with @angular/core${COLORS.reset}`);
@@ -195,6 +202,8 @@ async function runInitApp() {
195
202
  }
196
203
 
197
204
  const hasAppConfig = fileExists(appConfigPath);
205
+ const safelistImport = getTailjngSafelistCssImport(workspaceRoot, primaryStylePath, selectedApp);
206
+ const primaryStyleFullPath = resolveStyleFilePath(workspaceRoot, primaryStylePath, selectedApp);
198
207
  const files = buildInitFiles({
199
208
  styleLanguage,
200
209
  primaryStylePath,
@@ -203,6 +212,7 @@ async function runInitApp() {
203
212
  componentsPath,
204
213
  overwrite,
205
214
  hasAppConfig,
215
+ safelistImport,
206
216
  });
207
217
 
208
218
  let created = 0;
@@ -251,6 +261,11 @@ async function runInitApp() {
251
261
  console.log(`${COLORS.green}✔ Added node_modules/tailjng/src/styles.css to angular.json${COLORS.reset}`);
252
262
  }
253
263
 
264
+ const safelistPatched = ensureTailjngSafelistImport(primaryStyleFullPath, safelistImport);
265
+ if (safelistPatched.changed) {
266
+ console.log(`${COLORS.green}✔ Added tailjng colors safelist to ${path.relative(workspaceRoot, primaryStyleFullPath)}${COLORS.reset}`);
267
+ }
268
+
254
269
  if (installComponents) {
255
270
  const previousCwd = process.cwd();
256
271
  process.chdir(appRoot);
@@ -272,8 +287,8 @@ async function runInitApp() {
272
287
  console.log(`\n${COLORS.greenBright}${COLORS.bright}[tailjng CLI] init:app completed.${COLORS.reset}`);
273
288
  console.log(`${COLORS.dim}Created: ${created} | Skipped: ${skipped}${COLORS.reset}`);
274
289
  console.log(`\n${COLORS.cyan}Project ready. Install components when you need them:${COLORS.reset}`);
275
- console.log(` ${COLORS.dim}One by one:${COLORS.reset} cd ${path.relative(workspaceRoot, appRoot)} && npx tailjng add button`);
276
- console.log(` ${COLORS.dim}All at once:${COLORS.reset} cd ${path.relative(workspaceRoot, appRoot)} && npx tailjng install-all`);
290
+ console.log(` ${COLORS.dim}One by one:${COLORS.reset} npx tailjng add button`);
291
+ console.log(` ${COLORS.dim}All at once:${COLORS.reset} npx tailjng install-all`);
277
292
  console.log(` ${COLORS.dim}List:${COLORS.reset} npx tailjng list`);
278
293
  console.log(`\n${COLORS.cyan}Then run:${COLORS.reset} ng serve ${selectedApp.name} -o\n`);
279
294
  }
@@ -70,6 +70,38 @@ function writeFileSafe(filePath, content, overwrite = false) {
70
70
  return true;
71
71
  }
72
72
 
73
+ function resolveStyleFilePath(workspaceRoot, styleEntry, appProject) {
74
+ if (path.isAbsolute(styleEntry)) return styleEntry;
75
+ if (styleEntry.startsWith('projects/')) return path.join(workspaceRoot, styleEntry);
76
+ return path.join(workspaceRoot, appProject.root || '', styleEntry);
77
+ }
78
+
79
+ function getTailjngSafelistCssImport(workspaceRoot, styleEntry, appProject) {
80
+ const stylePath = resolveStyleFilePath(workspaceRoot, styleEntry, appProject);
81
+ const safelistPath = path.join(workspaceRoot, 'node_modules', 'tailjng', 'src', 'colors.safelist.css');
82
+ let rel = path.relative(path.dirname(stylePath), safelistPath).split(path.sep).join('/');
83
+ if (!rel.startsWith('.')) rel = `./${rel}`;
84
+ return `@import "${rel}";`;
85
+ }
86
+
87
+ function ensureTailjngSafelistImport(styleFilePath, importLine) {
88
+ if (!fs.existsSync(styleFilePath)) return { changed: false };
89
+
90
+ let content = fs.readFileSync(styleFilePath, 'utf8');
91
+ if (content.includes('colors.safelist.css')) return { changed: false };
92
+
93
+ const tailwindMatch = content.match(/@(?:import|use)\s+"tailwindcss";?/);
94
+ if (tailwindMatch) {
95
+ const insertAt = tailwindMatch.index + tailwindMatch[0].length;
96
+ content = `${content.slice(0, insertAt)}\n${importLine}\n${content.slice(insertAt)}`;
97
+ } else {
98
+ content = `${importLine}\n${content}`;
99
+ }
100
+
101
+ fs.writeFileSync(styleFilePath, content, 'utf8');
102
+ return { changed: true };
103
+ }
104
+
73
105
  function ensureTailjngStylesInAngularJson(angularJsonPath, projectName, styleLanguage) {
74
106
  const angularJson = readJson(angularJsonPath);
75
107
  const buildOptions = getBuildOptions(angularJson, projectName);
@@ -196,24 +228,72 @@ function patchAppComponentForAlerts(appComponentTsPath, appComponentHtmlPath) {
196
228
  return { changed };
197
229
  }
198
230
 
199
- function getMissingPackages(packageJson, packages) {
231
+ function getMissingPackages(packageJson, packages, workspaceRoot = null) {
200
232
  const deps = { ...packageJson.dependencies, ...packageJson.devDependencies };
201
- return Object.entries(packages).filter(([name]) => !deps[name]);
233
+ return Object.entries(packages).filter(([name]) => {
234
+ if (deps[name]) return false;
235
+ if (workspaceRoot && name.startsWith('@angular/')) {
236
+ const installed = path.join(workspaceRoot, 'node_modules', ...name.split('/'), 'package.json');
237
+ if (fs.existsSync(installed)) return false;
238
+ }
239
+ return true;
240
+ });
202
241
  }
203
242
 
204
243
  function getMergedDependencies(packageJson) {
205
244
  return { ...packageJson.dependencies, ...packageJson.devDependencies };
206
245
  }
207
246
 
208
- /** Alinea @angular/animations con la línea de @angular/core del proyecto (evita ERESOLVE 19.2.0 vs 19.2.25). */
209
- function resolveRuntimePackages(packageJson, basePackages) {
247
+ function getInstalledPackageVersion(workspaceRoot, name) {
248
+ const pkgPath = path.join(workspaceRoot, 'node_modules', ...name.split('/'), 'package.json');
249
+ if (!fs.existsSync(pkgPath)) return null;
250
+ try {
251
+ return JSON.parse(fs.readFileSync(pkgPath, 'utf8')).version;
252
+ } catch {
253
+ return null;
254
+ }
255
+ }
256
+
257
+ function resolveAngularAnimationsSpec(packageJson, workspaceRoot) {
258
+ const deps = getMergedDependencies(packageJson);
259
+ const coreInstalled = workspaceRoot ? getInstalledPackageVersion(workspaceRoot, '@angular/core') : null;
260
+ if (coreInstalled) return `^${coreInstalled}`;
261
+ if (deps['@angular/core']) return deps['@angular/core'];
262
+ return '^19.2.0';
263
+ }
264
+
265
+ /** Corrige @angular/animations para usar la misma versión que @angular/core del proyecto. */
266
+ function alignAngularAnimationsInPackageJson(workspaceRoot) {
267
+ const pkgPath = path.join(workspaceRoot, 'package.json');
268
+ if (!fs.existsSync(pkgPath)) return { changed: false };
269
+
270
+ const pkg = readJson(pkgPath);
271
+ const deps = pkg.dependencies || {};
272
+ const coreInstalled = getInstalledPackageVersion(workspaceRoot, '@angular/core');
273
+ const coreSpec = deps['@angular/core'];
274
+
275
+ // Preferir versión instalada (ej. 19.2.25); si no, la misma entrada que core en package.json
276
+ const aligned = coreInstalled ? `^${coreInstalled}` : coreSpec;
277
+ if (!aligned) return { changed: false };
278
+
279
+ if (!deps['@angular/animations']) return { changed: false };
280
+ if (deps['@angular/animations'] === aligned) return { changed: false };
281
+
282
+ deps['@angular/animations'] = aligned;
283
+ pkg.dependencies = deps;
284
+ writeJson(pkgPath, pkg);
285
+ return { changed: true, version: aligned };
286
+ }
287
+
288
+ /** Alinea @angular/animations con la versión instalada de @angular/core (evita ERESOLVE 19.2.0 vs 19.2.25). */
289
+ function resolveRuntimePackages(packageJson, basePackages, workspaceRoot = null) {
210
290
  const packages = { ...basePackages };
211
291
  const deps = getMergedDependencies(packageJson);
212
292
 
213
293
  if (deps['@angular/animations']) {
214
294
  delete packages['@angular/animations'];
215
- } else if (deps['@angular/core']) {
216
- packages['@angular/animations'] = deps['@angular/core'];
295
+ } else if (deps['@angular/core'] || (workspaceRoot && getInstalledPackageVersion(workspaceRoot, '@angular/core'))) {
296
+ packages['@angular/animations'] = resolveAngularAnimationsSpec(packageJson, workspaceRoot);
217
297
  }
218
298
 
219
299
  return packages;
@@ -278,6 +358,9 @@ module.exports = {
278
358
  getPrimaryStyleEntry,
279
359
  writeFileSafe,
280
360
  ensureTailjngStylesInAngularJson,
361
+ resolveStyleFilePath,
362
+ getTailjngSafelistCssImport,
363
+ ensureTailjngSafelistImport,
281
364
  patchIndexHtml,
282
365
  patchAppConfig,
283
366
  patchAppComponentForAlerts,
@@ -285,6 +368,7 @@ module.exports = {
285
368
  getMergedDependencies,
286
369
  resolveRuntimePackages,
287
370
  resolveDevPackages,
371
+ alignAngularAnimationsInPackageJson,
288
372
  hasTailwindSetup,
289
373
  fileExists,
290
374
  };
@@ -44,9 +44,9 @@ function buildDefaultThemeBlock() {
44
44
  }`;
45
45
  }
46
46
 
47
- function buildStylesCss() {
47
+ function buildStylesCss(safelistImport = '') {
48
48
  return `@import "tailwindcss";
49
-
49
+ ${safelistImport ? `${safelistImport}\n` : ''}
50
50
  html,
51
51
  body {
52
52
  font-family: 'Arial', sans-serif;
@@ -75,9 +75,9 @@ ${buildDefaultThemeBlock()}
75
75
  `;
76
76
  }
77
77
 
78
- function buildStylesScss() {
78
+ function buildStylesScss(safelistImport = '') {
79
79
  return `@use "tailwindcss";
80
-
80
+ ${safelistImport ? `${safelistImport}\n` : ''}
81
81
  @use "./scss/scroll";
82
82
  @use "./scss/input";
83
83
 
@@ -318,6 +318,7 @@ function buildInitFiles(options) {
318
318
  socketUrl,
319
319
  componentsPath,
320
320
  overwrite,
321
+ safelistImport = '',
321
322
  } = options;
322
323
 
323
324
  const files = [
@@ -349,7 +350,7 @@ function buildInitFiles(options) {
349
350
  if (styleLanguage === 'scss') {
350
351
  files.push({
351
352
  relativePath: primaryStylePath,
352
- content: buildStylesScss(),
353
+ content: buildStylesScss(safelistImport),
353
354
  });
354
355
  files.push({
355
356
  relativePath: 'src/scss/_scroll.scss',
@@ -362,7 +363,7 @@ function buildInitFiles(options) {
362
363
  } else {
363
364
  files.push({
364
365
  relativePath: primaryStylePath,
365
- content: buildStylesCss(),
366
+ content: buildStylesCss(safelistImport),
366
367
  });
367
368
  }
368
369
 
@@ -1,5 +1,5 @@
1
1
  import * as i0 from '@angular/core';
2
- import { InjectionToken, signal, computed, Injectable, Inject } from '@angular/core';
2
+ import { InjectionToken, signal, computed, Injectable, Inject, inject } from '@angular/core';
3
3
  import { CurrencyPipe } from '@angular/common';
4
4
  import { formatDistanceToNowStrict } from 'date-fns';
5
5
  import { es } from 'date-fns/locale';
@@ -23,6 +23,8 @@ const TAILJNG_CONFIG = new InjectionToken('TAILJNG_CONFIG');
23
23
  // }
24
24
  // ]
25
25
 
26
+ const TAILJNG_COLORS_CONFIG = new InjectionToken('TAILJNG_COLORS_CONFIG');
27
+
26
28
  // ======================================================
27
29
  // Table Column Interface
28
30
  // This interface defines the structure of a table column in a CRUD application.
@@ -1353,86 +1355,90 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.25", ngImpo
1353
1355
  args: [{ providedIn: 'root' }]
1354
1356
  }], ctorParameters: () => [] });
1355
1357
 
1358
+ const JCOLORS_DEFAULT_VARIANTS = {
1359
+ primary: 'bg-primary dark:bg-input text-white dark:text-white hover:bg-primary/80 dark:hover:bg-input/60 dark:hover:text-white shadow-md border border-dark-border dark:border-border',
1360
+ primary_soft: 'bg-primary/10 dark:bg-input/15 text-primary dark:text-input hover:bg-primary/20 dark:hover:bg-input/25 border border-primary/20 dark:border-input/30 shadow-sm',
1361
+ primary_outline: 'bg-transparent text-primary dark:text-input border border-primary dark:border-input hover:bg-primary/10 dark:hover:bg-input/15 shadow-sm',
1362
+ primary_ghost: 'bg-transparent text-primary dark:text-input hover:bg-primary/10 dark:hover:bg-input/15 border border-transparent dark:border-transparent',
1363
+ primary_light: 'bg-primary/80 dark:bg-input/80 text-white hover:bg-primary dark:hover:bg-input border border-primary/30 dark:border-input/40 shadow-md',
1364
+ primary_dark: 'bg-primary text-white dark:bg-input hover:bg-primary/80 dark:hover:bg-input/80 border border-dark-border dark:border-border shadow-md',
1365
+ primary_secondary: 'bg-none text-dark-border dark:text-border border border-dark-border dark:border-border hover:bg-dark-border/10 dark:hover:bg-border/10 shadow-md',
1366
+ secondary: 'bg-background dark:bg-dark-background text-black border border-dark-border dark:border-border dark:text-white hover:bg-accent dark:hover:bg-dark-accent/50',
1367
+ secondary_soft: 'bg-accent/40 dark:bg-dark-accent/30 text-black dark:text-white border border-border dark:border-dark-border hover:bg-accent/70 dark:hover:bg-dark-accent/50 shadow-sm',
1368
+ secondary_outline: 'bg-transparent text-black dark:text-white border border-border dark:border-dark-border hover:bg-accent dark:hover:bg-dark-accent/40 shadow-sm',
1369
+ secondary_ghost: 'bg-transparent text-black dark:text-white hover:bg-accent/60 dark:hover:bg-dark-accent/40 border border-transparent dark:border-transparent',
1370
+ secondary_light: 'bg-background/80 dark:bg-dark-background/80 text-black dark:text-white border border-border dark:border-dark-border hover:bg-background dark:hover:bg-dark-background shadow-sm',
1371
+ secondary_dark: 'bg-dark-background text-white border border-dark-border hover:bg-dark-accent/50 shadow-md',
1372
+ success: 'bg-green-500 hover:bg-green-600 text-white border border-green-300 dark:border-green-300 shadow-md',
1373
+ success_secondary: 'bg-none text-green-500 border border-green-500 dark:border-green-600 hover:bg-green-500/10 dark:hover:bg-green-600/10 shadow-md',
1374
+ success_soft: 'bg-green-500/10 text-green-600 dark:text-green-400 border border-green-500/20 hover:bg-green-500/20 dark:hover:bg-green-500/15 shadow-sm',
1375
+ success_outline: 'bg-transparent text-green-500 border border-green-500 hover:bg-green-500/10 shadow-sm',
1376
+ success_ghost: 'bg-transparent text-green-500 hover:bg-green-500/10 border border-transparent dark:border-transparent',
1377
+ info: 'bg-blue-500 hover:bg-blue-600 text-white border border-blue-300 dark:border-blue-300 shadow-md',
1378
+ info_secondary: 'bg-none text-blue-500 border border-blue-500 dark:border-blue-600 hover:bg-blue-500/10 dark:hover:bg-blue-600/10 shadow-md',
1379
+ info_soft: 'bg-blue-500/10 text-blue-600 dark:text-blue-400 border border-blue-500/20 hover:bg-blue-500/20 dark:hover:bg-blue-500/15 shadow-sm',
1380
+ info_outline: 'bg-transparent text-blue-500 border border-blue-500 hover:bg-blue-500/10 shadow-sm',
1381
+ info_ghost: 'bg-transparent text-blue-500 hover:bg-blue-500/10 border border-transparent dark:border-transparent',
1382
+ warning: 'bg-yellow-600 hover:bg-yellow-700 text-white border border-yellow-500 dark:border-yellow-500 shadow-md',
1383
+ warning_secondary: 'bg-none text-yellow-600 border border-yellow-600 dark:border-yellow-700 hover:bg-yellow-600/10 dark:hover:bg-yellow-700/10 shadow-md',
1384
+ warning_soft: 'bg-yellow-600/10 text-yellow-700 dark:text-yellow-400 border border-yellow-600/20 hover:bg-yellow-600/20 dark:hover:bg-yellow-600/15 shadow-sm',
1385
+ warning_outline: 'bg-transparent text-yellow-600 border border-yellow-600 hover:bg-yellow-600/10 shadow-sm',
1386
+ warning_ghost: 'bg-transparent text-yellow-600 hover:bg-yellow-600/10 border border-transparent dark:border-transparent',
1387
+ question: 'bg-purple-500 hover:bg-purple-600 text-white border border-purple-400 dark:border-purple-400 shadow-md',
1388
+ question_secondary: 'bg-none text-purple-500 border border-purple-500 dark:border-purple-600 hover:bg-purple-500/10 dark:hover:bg-purple-600/10 shadow-md',
1389
+ question_soft: 'bg-purple-500/10 text-purple-600 dark:text-purple-400 border border-purple-500/20 hover:bg-purple-500/20 dark:hover:bg-purple-500/15 shadow-sm',
1390
+ question_outline: 'bg-transparent text-purple-500 border border-purple-500 hover:bg-purple-500/10 shadow-sm',
1391
+ question_ghost: 'bg-transparent text-purple-500 hover:bg-purple-500/10 border border-transparent dark:border-transparent',
1392
+ error: 'bg-red-500 hover:bg-red-600 text-white border border-red-400 dark:border-red-400 shadow-md',
1393
+ error_secondary: 'bg-none text-red-500 border border-red-500 dark:border-red-600 hover:bg-red-500/10 dark:hover:bg-red-600/10 shadow-md',
1394
+ error_soft: 'bg-red-500/10 text-red-600 dark:text-red-400 border border-red-500/20 hover:bg-red-500/20 dark:hover:bg-red-500/15 shadow-sm',
1395
+ error_outline: 'bg-transparent text-red-500 border border-red-500 hover:bg-red-500/10 shadow-sm',
1396
+ error_ghost: 'bg-transparent text-red-500 hover:bg-red-500/10 border border-transparent dark:border-transparent',
1397
+ loading: 'bg-gray-500 hover:bg-gray-600 text-white border border-gray-400 dark:border-gray-400 shadow-md',
1398
+ loading_secondary: 'bg-none text-gray-500 border border-gray-500 dark:border-gray-600 hover:bg-gray-500/10 dark:hover:bg-gray-600/10 shadow-md',
1399
+ loading_soft: 'bg-gray-500/10 text-gray-600 dark:text-gray-400 border border-gray-500/20 hover:bg-gray-500/20 dark:hover:bg-gray-500/15 shadow-sm',
1400
+ loading_outline: 'bg-transparent text-gray-500 border border-gray-500 hover:bg-gray-500/10 shadow-sm',
1401
+ loading_ghost: 'bg-transparent text-gray-500 hover:bg-gray-500/10 border border-transparent dark:border-transparent',
1402
+ orange: 'bg-orange-500 hover:bg-orange-600 text-white border border-orange-300 dark:border-orange-300 shadow-md',
1403
+ orange_secondary: 'bg-none text-orange-500 border border-orange-500 dark:border-orange-600 hover:bg-orange-500/10 dark:hover:bg-orange-600/10 shadow-md',
1404
+ orange_soft: 'bg-orange-500/10 text-orange-600 dark:text-orange-400 border border-orange-500/20 hover:bg-orange-500/20 dark:hover:bg-orange-500/15 shadow-sm',
1405
+ orange_outline: 'bg-transparent text-orange-500 border border-orange-500 hover:bg-orange-500/10 shadow-sm',
1406
+ orange_ghost: 'bg-transparent text-orange-500 hover:bg-orange-500/10 border border-transparent dark:border-transparent',
1407
+ cyan: 'bg-cyan-500 hover:bg-cyan-600 text-white border border-cyan-300 dark:border-cyan-300 shadow-md',
1408
+ cyan_secondary: 'bg-none text-cyan-500 border border-cyan-500 dark:border-cyan-600 hover:bg-cyan-500/10 dark:hover:bg-cyan-600/10 shadow-md',
1409
+ cyan_soft: 'bg-cyan-500/10 text-cyan-600 dark:text-cyan-400 border border-cyan-500/20 hover:bg-cyan-500/20 dark:hover:bg-cyan-500/15 shadow-sm',
1410
+ cyan_outline: 'bg-transparent text-cyan-500 border border-cyan-500 hover:bg-cyan-500/10 shadow-sm',
1411
+ cyan_ghost: 'bg-transparent text-cyan-500 hover:bg-cyan-500/10 border border-transparent dark:border-transparent',
1412
+ purple: 'bg-purple-500 hover:bg-purple-600 text-white border border-purple-300 dark:border-purple-300 shadow-md',
1413
+ purple_secondary: 'bg-none text-purple-500 border border-purple-500 dark:border-purple-600 hover:bg-purple-500/10 dark:hover:bg-purple-600/10 shadow-md',
1414
+ purple_soft: 'bg-purple-500/10 text-purple-600 dark:text-purple-400 border border-purple-500/20 hover:bg-purple-500/20 dark:hover:bg-purple-500/15 shadow-sm',
1415
+ purple_outline: 'bg-transparent text-purple-500 border border-purple-500 hover:bg-purple-500/10 shadow-sm',
1416
+ purple_ghost: 'bg-transparent text-purple-500 hover:bg-purple-500/10 border border-transparent dark:border-transparent',
1417
+ teal: 'bg-teal-500 hover:bg-teal-600 text-white border border-teal-300 dark:border-teal-300 shadow-md',
1418
+ teal_secondary: 'bg-none text-teal-500 border border-teal-500 dark:border-teal-600 hover:bg-teal-500/10 dark:hover:bg-teal-600/10 shadow-md',
1419
+ teal_soft: 'bg-teal-500/10 text-teal-600 dark:text-teal-400 border border-teal-500/20 hover:bg-teal-500/20 dark:hover:bg-teal-500/15 shadow-sm',
1420
+ teal_outline: 'bg-transparent text-teal-500 border border-teal-500 hover:bg-teal-500/10 shadow-sm',
1421
+ teal_ghost: 'bg-transparent text-teal-500 hover:bg-teal-500/10 border border-transparent dark:border-transparent',
1422
+ pink: 'bg-pink-500 hover:bg-pink-600 text-white border border-pink-300 dark:border-pink-300 shadow-md',
1423
+ pink_secondary: 'bg-none text-pink-500 border border-pink-500 dark:border-pink-600 hover:bg-pink-500/10 dark:hover:bg-pink-600/10 shadow-md',
1424
+ pink_soft: 'bg-pink-500/10 text-pink-600 dark:text-pink-400 border border-pink-500/20 hover:bg-pink-500/20 dark:hover:bg-pink-500/15 shadow-sm',
1425
+ pink_outline: 'bg-transparent text-pink-500 border border-pink-500 hover:bg-pink-500/10 shadow-sm',
1426
+ pink_ghost: 'bg-transparent text-pink-500 hover:bg-pink-500/10 border border-transparent dark:border-transparent',
1427
+ green: 'bg-green-500 hover:bg-green-600 text-white border border-green-300 dark:border-green-300 shadow-md',
1428
+ green_secondary: 'bg-none text-green-500 border border-green-500 dark:border-green-600 hover:bg-green-500/10 dark:hover:bg-green-600/10 shadow-md',
1429
+ green_soft: 'bg-green-500/10 text-green-600 dark:text-green-400 border border-green-500/20 hover:bg-green-500/20 dark:hover:bg-green-500/15 shadow-sm',
1430
+ green_outline: 'bg-transparent text-green-500 border border-green-500 hover:bg-green-500/10 shadow-sm',
1431
+ green_ghost: 'bg-transparent text-green-500 hover:bg-green-500/10 border border-transparent dark:border-transparent',
1432
+ default: 'text-black dark:text-white shadow-md border border-dark-border dark:border-border',
1433
+ default_soft: 'bg-black/5 dark:bg-white/10 text-black dark:text-white border border-dark-border/20 dark:border-border/20 hover:bg-black/10 dark:hover:bg-white/15 shadow-sm',
1434
+ default_outline: 'bg-transparent text-black dark:text-white border border-dark-border dark:border-border hover:bg-black/5 dark:hover:bg-white/10 shadow-sm',
1435
+ default_ghost: 'bg-transparent text-black dark:text-white hover:bg-black/5 dark:hover:bg-white/10 border border-transparent dark:border-transparent',
1436
+ };
1356
1437
  class JColorsService {
1357
- // Variants
1438
+ colorsConfig = inject(TAILJNG_COLORS_CONFIG, { optional: true });
1358
1439
  variants = {
1359
- primary: 'bg-primary dark:bg-input text-white dark:text-white hover:bg-primary/80 dark:hover:bg-input/60 dark:hover:text-white shadow-md border border-dark-border dark:border-border',
1360
- primary_soft: 'bg-primary/10 dark:bg-input/15 text-primary dark:text-input hover:bg-primary/20 dark:hover:bg-input/25 border border-primary/20 dark:border-input/30 shadow-sm',
1361
- primary_outline: 'bg-transparent text-primary dark:text-input border border-primary dark:border-input hover:bg-primary/10 dark:hover:bg-input/15 shadow-sm',
1362
- primary_ghost: 'bg-transparent text-primary dark:text-input hover:bg-primary/10 dark:hover:bg-input/15 border border-transparent dark:border-transparent',
1363
- primary_light: 'bg-primary/80 dark:bg-input/80 text-white hover:bg-primary dark:hover:bg-input border border-primary/30 dark:border-input/40 shadow-md',
1364
- primary_dark: 'bg-primary text-white dark:bg-input hover:bg-primary/80 dark:hover:bg-input/80 border border-dark-border dark:border-border shadow-md',
1365
- primary_secondary: 'bg-none text-dark-border dark:text-border border border-dark-border dark:border-border hover:bg-dark-border/10 dark:hover:bg-border/10 shadow-md',
1366
- secondary: 'bg-background dark:bg-dark-background text-black border border-dark-border dark:border-border dark:text-white hover:bg-accent dark:hover:bg-dark-accent/50',
1367
- secondary_soft: 'bg-accent/40 dark:bg-dark-accent/30 text-black dark:text-white border border-border dark:border-dark-border hover:bg-accent/70 dark:hover:bg-dark-accent/50 shadow-sm',
1368
- secondary_outline: 'bg-transparent text-black dark:text-white border border-border dark:border-dark-border hover:bg-accent dark:hover:bg-dark-accent/40 shadow-sm',
1369
- secondary_ghost: 'bg-transparent text-black dark:text-white hover:bg-accent/60 dark:hover:bg-dark-accent/40 border border-transparent dark:border-transparent',
1370
- secondary_light: 'bg-background/80 dark:bg-dark-background/80 text-black dark:text-white border border-border dark:border-dark-border hover:bg-background dark:hover:bg-dark-background shadow-sm',
1371
- secondary_dark: 'bg-dark-background text-white border border-dark-border hover:bg-dark-accent/50 shadow-md',
1372
- success: 'bg-green-500 hover:bg-green-600 text-white border border-green-300 dark:border-green-300 shadow-md',
1373
- success_secondary: 'bg-none text-green-500 border border-green-500 dark:border-green-600 hover:bg-green-500/10 dark:hover:bg-green-600/10 shadow-md',
1374
- success_soft: 'bg-green-500/10 text-green-600 dark:text-green-400 border border-green-500/20 hover:bg-green-500/20 dark:hover:bg-green-500/15 shadow-sm',
1375
- success_outline: 'bg-transparent text-green-500 border border-green-500 hover:bg-green-500/10 shadow-sm',
1376
- success_ghost: 'bg-transparent text-green-500 hover:bg-green-500/10 border border-transparent dark:border-transparent',
1377
- info: 'bg-blue-500 hover:bg-blue-600 text-white border border-blue-300 dark:border-blue-300 shadow-md',
1378
- info_secondary: 'bg-none text-blue-500 border border-blue-500 dark:border-blue-600 hover:bg-blue-500/10 dark:hover:bg-blue-600/10 shadow-md',
1379
- info_soft: 'bg-blue-500/10 text-blue-600 dark:text-blue-400 border border-blue-500/20 hover:bg-blue-500/20 dark:hover:bg-blue-500/15 shadow-sm',
1380
- info_outline: 'bg-transparent text-blue-500 border border-blue-500 hover:bg-blue-500/10 shadow-sm',
1381
- info_ghost: 'bg-transparent text-blue-500 hover:bg-blue-500/10 border border-transparent dark:border-transparent',
1382
- warning: 'bg-yellow-600 hover:bg-yellow-700 text-white border border-yellow-500 dark:border-yellow-500 shadow-md',
1383
- warning_secondary: 'bg-none text-yellow-600 border border-yellow-600 dark:border-yellow-700 hover:bg-yellow-600/10 dark:hover:bg-yellow-700/10 shadow-md',
1384
- warning_soft: 'bg-yellow-600/10 text-yellow-700 dark:text-yellow-400 border border-yellow-600/20 hover:bg-yellow-600/20 dark:hover:bg-yellow-600/15 shadow-sm',
1385
- warning_outline: 'bg-transparent text-yellow-600 border border-yellow-600 hover:bg-yellow-600/10 shadow-sm',
1386
- warning_ghost: 'bg-transparent text-yellow-600 hover:bg-yellow-600/10 border border-transparent dark:border-transparent',
1387
- question: 'bg-purple-500 hover:bg-purple-600 text-white border border-purple-400 dark:border-purple-400 shadow-md',
1388
- question_secondary: 'bg-none text-purple-500 border border-purple-500 dark:border-purple-600 hover:bg-purple-500/10 dark:hover:bg-purple-600/10 shadow-md',
1389
- question_soft: 'bg-purple-500/10 text-purple-600 dark:text-purple-400 border border-purple-500/20 hover:bg-purple-500/20 dark:hover:bg-purple-500/15 shadow-sm',
1390
- question_outline: 'bg-transparent text-purple-500 border border-purple-500 hover:bg-purple-500/10 shadow-sm',
1391
- question_ghost: 'bg-transparent text-purple-500 hover:bg-purple-500/10 border border-transparent dark:border-transparent',
1392
- error: 'bg-red-500 hover:bg-red-600 text-white border border-red-400 dark:border-red-400 shadow-md',
1393
- error_secondary: 'bg-none text-red-500 border border-red-500 dark:border-red-600 hover:bg-red-500/10 dark:hover:bg-red-600/10 shadow-md',
1394
- error_soft: 'bg-red-500/10 text-red-600 dark:text-red-400 border border-red-500/20 hover:bg-red-500/20 dark:hover:bg-red-500/15 shadow-sm',
1395
- error_outline: 'bg-transparent text-red-500 border border-red-500 hover:bg-red-500/10 shadow-sm',
1396
- error_ghost: 'bg-transparent text-red-500 hover:bg-red-500/10 border border-transparent dark:border-transparent',
1397
- loading: 'bg-gray-500 hover:bg-gray-600 text-white border border-gray-400 dark:border-gray-400 shadow-md',
1398
- loading_secondary: 'bg-none text-gray-500 border border-gray-500 dark:border-gray-600 hover:bg-gray-500/10 dark:hover:bg-gray-600/10 shadow-md',
1399
- loading_soft: 'bg-gray-500/10 text-gray-600 dark:text-gray-400 border border-gray-500/20 hover:bg-gray-500/20 dark:hover:bg-gray-500/15 shadow-sm',
1400
- loading_outline: 'bg-transparent text-gray-500 border border-gray-500 hover:bg-gray-500/10 shadow-sm',
1401
- loading_ghost: 'bg-transparent text-gray-500 hover:bg-gray-500/10 border border-transparent dark:border-transparent',
1402
- orange: 'bg-orange-500 hover:bg-orange-600 text-white border border-orange-300 dark:border-orange-300 shadow-md',
1403
- orange_secondary: 'bg-none text-orange-500 border border-orange-500 dark:border-orange-600 hover:bg-orange-500/10 dark:hover:bg-orange-600/10 shadow-md',
1404
- orange_soft: 'bg-orange-500/10 text-orange-600 dark:text-orange-400 border border-orange-500/20 hover:bg-orange-500/20 dark:hover:bg-orange-500/15 shadow-sm',
1405
- orange_outline: 'bg-transparent text-orange-500 border border-orange-500 hover:bg-orange-500/10 shadow-sm',
1406
- orange_ghost: 'bg-transparent text-orange-500 hover:bg-orange-500/10 border border-transparent dark:border-transparent',
1407
- cyan: 'bg-cyan-500 hover:bg-cyan-600 text-white border border-cyan-300 dark:border-cyan-300 shadow-md',
1408
- cyan_secondary: 'bg-none text-cyan-500 border border-cyan-500 dark:border-cyan-600 hover:bg-cyan-500/10 dark:hover:bg-cyan-600/10 shadow-md',
1409
- cyan_soft: 'bg-cyan-500/10 text-cyan-600 dark:text-cyan-400 border border-cyan-500/20 hover:bg-cyan-500/20 dark:hover:bg-cyan-500/15 shadow-sm',
1410
- cyan_outline: 'bg-transparent text-cyan-500 border border-cyan-500 hover:bg-cyan-500/10 shadow-sm',
1411
- cyan_ghost: 'bg-transparent text-cyan-500 hover:bg-cyan-500/10 border border-transparent dark:border-transparent',
1412
- purple: 'bg-purple-500 hover:bg-purple-600 text-white border border-purple-300 dark:border-purple-300 shadow-md',
1413
- purple_secondary: 'bg-none text-purple-500 border border-purple-500 dark:border-purple-600 hover:bg-purple-500/10 dark:hover:bg-purple-600/10 shadow-md',
1414
- purple_soft: 'bg-purple-500/10 text-purple-600 dark:text-purple-400 border border-purple-500/20 hover:bg-purple-500/20 dark:hover:bg-purple-500/15 shadow-sm',
1415
- purple_outline: 'bg-transparent text-purple-500 border border-purple-500 hover:bg-purple-500/10 shadow-sm',
1416
- purple_ghost: 'bg-transparent text-purple-500 hover:bg-purple-500/10 border border-transparent dark:border-transparent',
1417
- teal: 'bg-teal-500 hover:bg-teal-600 text-white border border-teal-300 dark:border-teal-300 shadow-md',
1418
- teal_secondary: 'bg-none text-teal-500 border border-teal-500 dark:border-teal-600 hover:bg-teal-500/10 dark:hover:bg-teal-600/10 shadow-md',
1419
- teal_soft: 'bg-teal-500/10 text-teal-600 dark:text-teal-400 border border-teal-500/20 hover:bg-teal-500/20 dark:hover:bg-teal-500/15 shadow-sm',
1420
- teal_outline: 'bg-transparent text-teal-500 border border-teal-500 hover:bg-teal-500/10 shadow-sm',
1421
- teal_ghost: 'bg-transparent text-teal-500 hover:bg-teal-500/10 border border-transparent dark:border-transparent',
1422
- pink: 'bg-pink-500 hover:bg-pink-600 text-white border border-pink-300 dark:border-pink-300 shadow-md',
1423
- pink_secondary: 'bg-none text-pink-500 border border-pink-500 dark:border-pink-600 hover:bg-pink-500/10 dark:hover:bg-pink-600/10 shadow-md',
1424
- pink_soft: 'bg-pink-500/10 text-pink-600 dark:text-pink-400 border border-pink-500/20 hover:bg-pink-500/20 dark:hover:bg-pink-500/15 shadow-sm',
1425
- pink_outline: 'bg-transparent text-pink-500 border border-pink-500 hover:bg-pink-500/10 shadow-sm',
1426
- pink_ghost: 'bg-transparent text-pink-500 hover:bg-pink-500/10 border border-transparent dark:border-transparent',
1427
- green: 'bg-green-500 hover:bg-green-600 text-white border border-green-300 dark:border-green-300 shadow-md',
1428
- green_secondary: 'bg-none text-green-500 border border-green-500 dark:border-green-600 hover:bg-green-500/10 dark:hover:bg-green-600/10 shadow-md',
1429
- green_soft: 'bg-green-500/10 text-green-600 dark:text-green-400 border border-green-500/20 hover:bg-green-500/20 dark:hover:bg-green-500/15 shadow-sm',
1430
- green_outline: 'bg-transparent text-green-500 border border-green-500 hover:bg-green-500/10 shadow-sm',
1431
- green_ghost: 'bg-transparent text-green-500 hover:bg-green-500/10 border border-transparent dark:border-transparent',
1432
- default: 'text-black dark:text-white shadow-md border border-dark-border dark:border-border',
1433
- default_soft: 'bg-black/5 dark:bg-white/10 text-black dark:text-white border border-dark-border/20 dark:border-border/20 hover:bg-black/10 dark:hover:bg-white/15 shadow-sm',
1434
- default_outline: 'bg-transparent text-black dark:text-white border border-dark-border dark:border-border hover:bg-black/5 dark:hover:bg-white/10 shadow-sm',
1435
- default_ghost: 'bg-transparent text-black dark:text-white hover:bg-black/5 dark:hover:bg-white/10 border border-transparent dark:border-transparent',
1440
+ ...JCOLORS_DEFAULT_VARIANTS,
1441
+ ...(this.colorsConfig?.variants ?? {}),
1436
1442
  };
1437
1443
  // Function to get variant with optional border and shadow
1438
1444
  getVariantClass(type, hasShadow = true, hasBorder = true) {
@@ -2290,5 +2296,5 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.25", ngImpo
2290
2296
  * Generated bundle index. Do not edit.
2291
2297
  */
2292
2298
 
2293
- export { JAlertDialogService, JAlertToastService, JCalendarService, JColorsService, JConverterCrudService, JDialogShared, JErrorHandlerHttpService, JExcelFilterService, JExcelService, JFileHttpService, JFormShared, JGenericCrudService, JIconsService, JParamsHttpService, JThemeService, JTransformService, JUploadFilterService, TAILJNG_CONFIG };
2299
+ export { JAlertDialogService, JAlertToastService, JCOLORS_DEFAULT_VARIANTS, JCalendarService, JColorsService, JConverterCrudService, JDialogShared, JErrorHandlerHttpService, JExcelFilterService, JExcelService, JFileHttpService, JFormShared, JGenericCrudService, JIconsService, JParamsHttpService, JThemeService, JTransformService, JUploadFilterService, TAILJNG_COLORS_CONFIG, TAILJNG_CONFIG };
2294
2300
  //# sourceMappingURL=tailjng.mjs.map