@bookklik/senangstart-css 0.2.4 → 0.2.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (128) hide show
  1. package/dist/senangstart-css.js +82 -6
  2. package/dist/senangstart-css.min.js +24 -20
  3. package/dist/senangstart-tw.js +200 -52
  4. package/dist/senangstart-tw.min.js +1 -1
  5. package/docs/guide/cdn.md +1 -1
  6. package/docs/ms/guide/cdn.md +1 -1
  7. package/docs/ms/reference/layout/position.md +4 -4
  8. package/docs/ms/reference/layout/z-index.md +8 -8
  9. package/docs/ms/reference/space/gap.md +1 -1
  10. package/docs/ms/reference/space/height.md +1 -1
  11. package/docs/ms/reference/space/margin.md +1 -1
  12. package/docs/ms/reference/space/padding.md +1 -1
  13. package/docs/ms/reference/space/scale-reference.md +46 -17
  14. package/docs/ms/reference/space/width.md +1 -1
  15. package/docs/ms/reference/space.md +1 -1
  16. package/docs/ms/reference/spacing.md +103 -21
  17. package/docs/ms/reference/visual/animation-fill.md +8 -8
  18. package/docs/ms/reference/visual/backdrop-blur.md +4 -4
  19. package/docs/ms/reference/visual/backdrop-brightness.md +8 -8
  20. package/docs/ms/reference/visual/backdrop-grayscale.md +6 -6
  21. package/docs/ms/reference/visual/backdrop-sepia.md +6 -6
  22. package/docs/ms/reference/visual/background-clip.md +2 -2
  23. package/docs/ms/reference/visual/background-image.md +4 -4
  24. package/docs/ms/reference/visual/filter-brightness.md +4 -4
  25. package/docs/ms/reference/visual/filter-contrast.md +4 -4
  26. package/docs/ms/reference/visual/filter-drop-shadow.md +6 -6
  27. package/docs/ms/reference/visual/filter-grayscale.md +4 -4
  28. package/docs/ms/reference/visual/filter-hue-rotate.md +4 -4
  29. package/docs/ms/reference/visual/filter-invert.md +2 -2
  30. package/docs/ms/reference/visual/filter-saturate.md +4 -4
  31. package/docs/ms/reference/visual/filter-sepia.md +4 -4
  32. package/docs/ms/reference/visual/font-family.md +2 -2
  33. package/docs/ms/reference/visual/gradient-from.md +57 -57
  34. package/docs/ms/reference/visual/gradient-to.md +57 -57
  35. package/docs/ms/reference/visual/gradient-via.md +54 -54
  36. package/docs/ms/reference/visual/letter-spacing.md +2 -2
  37. package/docs/ms/reference/visual/line-clamp.md +2 -2
  38. package/docs/ms/reference/visual/line-height.md +2 -2
  39. package/docs/ms/reference/visual/outline.md +2 -2
  40. package/docs/ms/reference/visual/ring-color.md +29 -0
  41. package/docs/ms/reference/visual/ring-offset.md +30 -0
  42. package/docs/ms/reference/visual/ring.md +62 -0
  43. package/docs/ms/reference/visual/stroke-width.md +6 -6
  44. package/docs/ms/reference/visual/stroke.md +4 -4
  45. package/docs/ms/reference/visual/text-indent.md +2 -2
  46. package/docs/ms/reference/visual/text-overflow.md +2 -2
  47. package/docs/ms/reference/visual/text-size.md +2 -2
  48. package/docs/ms/reference/visual/text-wrap.md +2 -2
  49. package/docs/ms/reference/visual/transform-backface.md +4 -4
  50. package/docs/ms/reference/visual/transform-perspective-origin.md +6 -6
  51. package/docs/ms/reference/visual/transform-perspective.md +6 -6
  52. package/docs/ms/reference/visual/transform-rotate-3d.md +6 -6
  53. package/docs/ms/reference/visual/transform-style.md +4 -4
  54. package/docs/ms/reference/visual/transform-translate-z.md +6 -6
  55. package/docs/ms/reference/visual/transform-translate.md +2 -2
  56. package/docs/ms/reference/visual/whitespace.md +2 -2
  57. package/docs/ms/reference/visual/word-break.md +2 -2
  58. package/docs/public/assets/senangstart-css.min.js +24 -20
  59. package/docs/public/llms.txt +1718 -0
  60. package/docs/reference/layout/position.md +4 -4
  61. package/docs/reference/layout/z-index.md +8 -8
  62. package/docs/reference/space/gap.md +1 -1
  63. package/docs/reference/space/height.md +1 -1
  64. package/docs/reference/space/margin.md +1 -1
  65. package/docs/reference/space/padding.md +1 -1
  66. package/docs/reference/space/scale-reference.md +46 -17
  67. package/docs/reference/space/width.md +1 -1
  68. package/docs/reference/space.md +1 -1
  69. package/docs/reference/spacing.md +103 -21
  70. package/docs/reference/visual/animation-fill.md +8 -8
  71. package/docs/reference/visual/backdrop-blur.md +4 -4
  72. package/docs/reference/visual/backdrop-brightness.md +8 -8
  73. package/docs/reference/visual/backdrop-grayscale.md +6 -6
  74. package/docs/reference/visual/backdrop-sepia.md +6 -6
  75. package/docs/reference/visual/background-clip.md +2 -2
  76. package/docs/reference/visual/background-image.md +4 -4
  77. package/docs/reference/visual/filter-brightness.md +4 -4
  78. package/docs/reference/visual/filter-contrast.md +4 -4
  79. package/docs/reference/visual/filter-drop-shadow.md +6 -6
  80. package/docs/reference/visual/filter-grayscale.md +4 -4
  81. package/docs/reference/visual/filter-hue-rotate.md +4 -4
  82. package/docs/reference/visual/filter-invert.md +2 -2
  83. package/docs/reference/visual/filter-saturate.md +4 -4
  84. package/docs/reference/visual/filter-sepia.md +4 -4
  85. package/docs/reference/visual/font-family.md +2 -2
  86. package/docs/reference/visual/gradient-from.md +57 -57
  87. package/docs/reference/visual/gradient-to.md +57 -57
  88. package/docs/reference/visual/gradient-via.md +54 -54
  89. package/docs/reference/visual/letter-spacing.md +2 -2
  90. package/docs/reference/visual/line-clamp.md +2 -2
  91. package/docs/reference/visual/line-height.md +2 -2
  92. package/docs/reference/visual/outline.md +2 -2
  93. package/docs/reference/visual/ring-color.md +29 -0
  94. package/docs/reference/visual/ring-offset.md +30 -0
  95. package/docs/reference/visual/ring.md +62 -0
  96. package/docs/reference/visual/stroke-width.md +6 -6
  97. package/docs/reference/visual/stroke.md +4 -4
  98. package/docs/reference/visual/text-indent.md +2 -2
  99. package/docs/reference/visual/text-overflow.md +2 -2
  100. package/docs/reference/visual/text-size.md +2 -2
  101. package/docs/reference/visual/text-wrap.md +2 -2
  102. package/docs/reference/visual/transform-backface.md +4 -4
  103. package/docs/reference/visual/transform-perspective-origin.md +6 -6
  104. package/docs/reference/visual/transform-perspective.md +6 -6
  105. package/docs/reference/visual/transform-rotate-3d.md +6 -6
  106. package/docs/reference/visual/transform-style.md +4 -4
  107. package/docs/reference/visual/transform-translate-z.md +6 -6
  108. package/docs/reference/visual/transform-translate.md +2 -2
  109. package/docs/reference/visual/whitespace.md +2 -2
  110. package/docs/reference/visual/word-break.md +2 -2
  111. package/package.json +4 -2
  112. package/scripts/build-dist.js +2 -2
  113. package/scripts/bundle-jit.js +3 -3
  114. package/scripts/convert-tailwind.js +157 -2
  115. package/scripts/generate-llms-txt.js +264 -0
  116. package/src/cdn/{jit.js → senangstart-engine.js} +81 -11
  117. package/src/cdn/tw-conversion-engine.js +203 -68
  118. package/src/compiler/generators/css.js +27 -0
  119. package/src/config/defaults.js +37 -11
  120. package/src/core/constants.js +37 -8
  121. package/src/definitions/space.js +46 -5
  122. package/src/definitions/visual-borders.js +80 -1
  123. package/src/definitions/visual-transform3d.js +16 -16
  124. package/src/definitions/visual-transforms.js +1 -1
  125. package/src/definitions/visual-transitions.js +4 -4
  126. package/src/definitions/visual-typography.js +6 -6
  127. package/src/definitions/visual.js +4 -4
  128. package/tests/unit/compiler/generators/css.test.js +192 -0
@@ -7,83 +7,105 @@
7
7
  // MAPPING SCALES
8
8
  // ============================
9
9
 
10
+ // Spacing scale mapping Tailwind values to SenangStart semantic values
11
+ // Engine native values: none(0px), thin(1px), regular(2px), thick(3px), tiny(4px), tiny-2x(6px),
12
+ // small(8px), small-2x(10px), small-3x(12px), small-4x(14px),
13
+ // medium(16px), medium-2x(20px), medium-3x(24px), medium-4x(28px),
14
+ // large(32px), large-2x(36px), large-3x(40px), large-4x(44px),
15
+ // big(48px), big-2x(56px), big-3x(64px), big-4x(80px),
16
+ // giant(96px), giant-2x(112px), giant-3x(128px), giant-4x(144px),
17
+ // vast(160px), vast-2x(176px), vast-3x(192px), vast-4x(208px),
18
+ // vast-5x(224px), vast-6x(240px), vast-7x(256px), vast-8x(288px),
19
+ // vast-9x(320px), vast-10x(384px)
20
+ // Tailwind base: 4px per unit (1 = 0.25rem = 4px)
10
21
  const spacingScale = {
11
- 0: "none",
12
- px: "[1px]",
13
- 0.5: "tiny",
14
- 1: "tiny",
15
- 1.5: "tiny",
16
- 2: "tiny",
17
- 2.5: "small",
18
- 3: "small",
19
- 3.5: "small",
20
- 4: "small",
21
- 5: "medium",
22
- 6: "medium",
23
- 7: "medium",
24
- 8: "big",
25
- 9: "big",
26
- 10: "big",
27
- 11: "big",
28
- 12: "giant",
29
- 14: "giant",
30
- 16: "giant",
31
- 20: "vast",
32
- 24: "vast",
33
- 28: "vast",
34
- 32: "vast",
35
- 36: "vast",
36
- 40: "vast",
37
- 44: "vast",
38
- 48: "vast",
39
- 52: "vast",
40
- 56: "vast",
41
- 60: "vast",
42
- 64: "vast",
43
- 72: "vast",
44
- 80: "vast",
45
- 96: "vast",
22
+ 0: "none", // 0px → none
23
+ px: "thin", // 1px → thin
24
+ 0.5: "regular", // 2px → regular
25
+ 1: "tiny", // 4px → tiny
26
+ 1.5: "tiny-2x", // 6px → tiny-2x
27
+ 2: "small", // 8px → small
28
+ 2.5: "small-2x", // 10px → small-2x
29
+ 3: "small-3x", // 12px → small-3x
30
+ 3.5: "small-4x", // 14px → small-4x
31
+ 4: "medium", // 16px → medium
32
+ 5: "medium-2x", // 20px → medium-2x
33
+ 6: "medium-3x", // 24px → medium-3x
34
+ 7: "medium-4x", // 28px → medium-4x
35
+ 8: "large", // 32px → large
36
+ 9: "large-2x", // 36px → large-2x
37
+ 10: "large-3x", // 40px → large-3x
38
+ 11: "large-4x", // 44px → large-4x
39
+ 12: "big", // 48px → big
40
+ 14: "big-2x", // 56px → big-2x
41
+ 16: "big-3x", // 64px → big-3x
42
+ 20: "big-4x", // 80px → big-4x
43
+ 24: "giant", // 96px → giant
44
+ 28: "giant-2x", // 112px → giant-2x
45
+ 32: "giant-3x", // 128px → giant-3x
46
+ 36: "giant-4x", // 144px → giant-4x
47
+ 40: "vast", // 160px → vast
48
+ 44: "vast-2x", // 176px → vast-2x
49
+ 48: "vast-3x", // 192px → vast-3x
50
+ 52: "vast-4x", // 208px → vast-4x
51
+ 56: "vast-5x", // 224px → vast-5x
52
+ 60: "vast-6x", // 240px → vast-6x
53
+ 64: "vast-7x", // 256px → vast-7x
54
+ 72: "vast-8x", // 288px → vast-8x
55
+ 80: "vast-9x", // 320px → vast-9x
56
+ 96: "vast-10x", // 384px → vast-10x
46
57
  full: "[100%]",
47
58
  screen: "[100vw]",
48
59
  auto: "auto",
49
60
  };
50
61
 
62
+ // Radius scale mapping Tailwind values to SenangStart semantic values
63
+ // Engine native values: none(0px), small(4px), medium(8px), big(16px), round(9999px)
64
+ // Tailwind: none(0), sm(0.125rem=2px), DEFAULT(0.25rem=4px), md(0.375rem=6px),
65
+ // lg(0.5rem=8px), xl(0.75rem=12px), 2xl(1rem=16px), 3xl(1.5rem=24px), full(9999px)
51
66
  const radiusScale = {
52
- none: "none",
53
- sm: "small",
54
- "": "small",
55
- md: "medium",
56
- lg: "medium",
57
- xl: "big",
58
- "2xl": "big",
59
- "3xl": "big",
60
- full: "round",
67
+ none: "none", // 0px → none
68
+ sm: "small", // 2px → small (closest to 4px)
69
+ "": "small", // 4px → small (Tailwind DEFAULT)
70
+ md: "small", // 6px → small (closest to 4px)
71
+ lg: "medium", // 8px → medium
72
+ xl: "medium", // 12px → medium (closest to 8px)
73
+ "2xl": "big", // 16px → big
74
+ "3xl": "big", // 24px → big (closest to 16px)
75
+ full: "round", // 9999px → round
61
76
  };
62
77
 
78
+ // Shadow scale mapping Tailwind values to SenangStart semantic values
79
+ // Engine native values: none, small, medium, big, giant
63
80
  const shadowScale = {
64
- sm: "small",
65
- "": "small",
66
- md: "medium",
67
- lg: "big",
68
- xl: "giant",
69
- "2xl": "giant",
70
- none: "none",
81
+ none: "none", // none → none
82
+ sm: "small", // small shadow → small
83
+ "": "small", // DEFAULT shadow → small
84
+ md: "medium", // medium shadow → medium
85
+ lg: "big", // large shadow → big
86
+ xl: "giant", // xl shadow → giant
87
+ "2xl": "giant", // 2xl shadow → giant
88
+ inner: "none", // inner shadow not directly supported
71
89
  };
72
90
 
91
+ // Font size scale mapping Tailwind values to SenangStart semantic values
92
+ // Engine native values: mini(0.75rem), small(0.875rem), base(1rem), large(1.125rem),
93
+ // big(1.25rem), huge(1.5rem), grand(1.875rem), giant(2.25rem),
94
+ // mount(3rem), mega(3.75rem), giga(4.5rem), tera(6rem), hero(8rem)
73
95
  const fontSizeScale = {
74
- xs: "mini", // 0.75rem
75
- sm: "small", // 0.875rem
76
- base: "base", // 1rem
77
- lg: "large", // 1.125rem
78
- xl: "big", // 1.25rem
79
- "2xl": "huge", // 1.5rem
80
- "3xl": "grand", // 1.875rem
81
- "4xl": "giant", // 2.25rem
82
- "5xl": "mount", // 3rem
83
- "6xl": "mega", // 3.75rem
84
- "7xl": "giga", // 4.5rem
85
- "8xl": "tera", // 6rem
86
- "9xl": "hero", // 8rem
96
+ xs: "mini", // 0.75rem → mini
97
+ sm: "small", // 0.875rem → small
98
+ base: "base", // 1rem → base
99
+ lg: "large", // 1.125rem → large
100
+ xl: "big", // 1.25rem → big
101
+ "2xl": "huge", // 1.5rem → huge
102
+ "3xl": "grand", // 1.875rem → grand
103
+ "4xl": "giant", // 2.25rem → giant
104
+ "5xl": "mount", // 3rem → mount
105
+ "6xl": "mega", // 3.75rem → mega
106
+ "7xl": "giga", // 4.5rem → giga
107
+ "8xl": "tera", // 6rem → tera
108
+ "9xl": "hero", // 8rem → hero
87
109
  };
88
110
 
89
111
  const layoutMappings = {
@@ -171,6 +193,10 @@ const visualKeywords = {
171
193
  // ============================
172
194
 
173
195
  function getSpacing(value, exact) {
196
+ // Check if it's already an arbitrary value with brackets
197
+ if (value.startsWith('[') && value.endsWith(']')) {
198
+ return value; // Return as-is, don't double-wrap
199
+ }
174
200
  if (exact) {
175
201
  if (["full", "screen", "auto"].includes(value))
176
202
  return spacingScale[value] || `[${value}]`;
@@ -179,6 +205,24 @@ function getSpacing(value, exact) {
179
205
  return spacingScale[value] || `[${value}]`;
180
206
  }
181
207
 
208
+ // Border width scale mapping Tailwind values to SenangStart semantic values
209
+ // Engine native values: none(0), thin(1px), regular(2px), thick(3px)
210
+ const borderWidthScale = {
211
+ 0: "none",
212
+ 1: "thin", // 1px → thin (was [1px])
213
+ 2: "regular", // 2px → regular
214
+ 3: "thick", // 3px → thick
215
+ 4: "tiny", // 4px → tiny
216
+ 8: "small", // 8px → small
217
+ };
218
+
219
+ function getBorderWidth(value, exact) {
220
+ if (exact) {
221
+ return `tw-${value}`;
222
+ }
223
+ return borderWidthScale[value] || `[${value}px]`;
224
+ }
225
+
182
226
  // ============================
183
227
  // CONVERSION FUNCTIONS
184
228
  // ============================
@@ -186,7 +230,7 @@ function getSpacing(value, exact) {
186
230
  function convertClass(twClass, exact) {
187
231
  // Handle prefixes (hover:, sm:, md:, etc.)
188
232
  const prefixMatch = twClass.match(
189
- /^(sm:|md:|lg:|xl:|2xl:|hover:|focus:|active:|disabled:|dark:)(.+)$/
233
+ /^(sm:|md:|lg:|xl:|2xl:|hover:|focus:|focus-visible:|active:|disabled:|dark:)(.+)$/
190
234
  );
191
235
  let prefix = "",
192
236
  baseClass = twClass;
@@ -239,9 +283,22 @@ function convertClass(twClass, exact) {
239
283
 
240
284
  // Background color
241
285
  const bgMatch = baseClass.match(
242
- /^bg-((?:slate|gray|zinc|neutral|stone|red|orange|amber|yellow|lime|green|emerald|teal|cyan|sky|blue|indigo|violet|purple|fuchsia|pink|rose|white|black)(?:-\d+)?)$/
286
+ /^bg-((?:slate|gray|zinc|neutral|stone|red|orange|amber|yellow|lime|green|emerald|teal|cyan|sky|blue|indigo|violet|purple|fuchsia|pink|rose|white|black)(?:-\d+)?|transparent|current|inherit)$/
243
287
  );
244
- if (bgMatch) return { cat: "visual", val: prefix + "bg:" + bgMatch[1] };
288
+ if (bgMatch) {
289
+ const colorVal = bgMatch[1];
290
+ // Handle special values
291
+ if (colorVal === 'transparent') {
292
+ return { cat: "visual", val: prefix + "bg:[transparent]" };
293
+ }
294
+ if (colorVal === 'current') {
295
+ return { cat: "visual", val: prefix + "bg:[currentColor]" };
296
+ }
297
+ if (colorVal === 'inherit') {
298
+ return { cat: "visual", val: prefix + "bg:[inherit]" };
299
+ }
300
+ return { cat: "visual", val: prefix + "bg:" + colorVal };
301
+ }
245
302
 
246
303
  // Border color
247
304
  const borderColorMatch = baseClass.match(
@@ -350,10 +407,31 @@ function convertClass(twClass, exact) {
350
407
  const width = borderWidthMatch[2] || "1";
351
408
  return {
352
409
  cat: "visual",
353
- val: prefix + "border" + side + ":[" + width + "px]",
410
+ val: prefix + "border" + side + ":" + getBorderWidth(width, exact),
354
411
  };
355
412
  }
356
413
 
414
+ // Positional properties (top-0, right-0, bottom-0, left-0, inset-0, etc.)
415
+ const positionMatch = baseClass.match(/^(top|right|bottom|left|inset|inset-x|inset-y)-(\d+|px|auto|full|\[.+\])$/);
416
+ if (positionMatch) {
417
+ const prop = positionMatch[1];
418
+ let val = positionMatch[2];
419
+ // Handle 0 specially
420
+ if (val === '0') {
421
+ val = 'none';
422
+ } else if (val.startsWith('[') && val.endsWith(']')) {
423
+ // Keep arbitrary values as-is
424
+ } else {
425
+ val = getSpacing(val, exact);
426
+ }
427
+ return { cat: "layout", val: prefix + prop + ":" + val };
428
+ }
429
+
430
+ // Outline none
431
+ if (baseClass === 'outline-none') {
432
+ return { cat: "visual", val: prefix + "outline:none" };
433
+ }
434
+
357
435
  // Order
358
436
  const orderMatch = baseClass.match(/^order-(\d+|first|last|none)$/);
359
437
  if (orderMatch) {
@@ -414,6 +492,63 @@ function convertClass(twClass, exact) {
414
492
  return { cat: "visual", val: prefix + "to:" + toMatch[1] };
415
493
  }
416
494
 
495
+ // Transition utilities
496
+ const transitionMatch = baseClass.match(/^transition(?:-(all|colors|opacity|shadow|transform|none))?$/);
497
+ if (transitionMatch) {
498
+ const type = transitionMatch[1] || 'all';
499
+ return { cat: "visual", val: prefix + "transition:" + type };
500
+ }
501
+
502
+ // Duration utilities
503
+ const durationMatch = baseClass.match(/^duration-(\d+)$/);
504
+ if (durationMatch) {
505
+ // Map Tailwind duration (ms) to SenangStart semantic values
506
+ const ms = parseInt(durationMatch[1]);
507
+ let durationVal;
508
+ if (ms <= 75) durationVal = 'instant';
509
+ else if (ms <= 100) durationVal = 'quick';
510
+ else if (ms <= 150) durationVal = 'fast';
511
+ else if (ms <= 200) durationVal = 'normal';
512
+ else if (ms <= 300) durationVal = 'slow';
513
+ else if (ms <= 500) durationVal = 'slower';
514
+ else durationVal = 'lazy';
515
+ return { cat: "visual", val: prefix + "duration:" + durationVal };
516
+ }
517
+
518
+ // Ease utilities
519
+ const easeMatch = baseClass.match(/^ease-(linear|in|out|in-out)$/);
520
+ if (easeMatch) {
521
+ return { cat: "visual", val: prefix + "ease:" + easeMatch[1] };
522
+ }
523
+
524
+ // Ring utilities - Convert to native ring utilities
525
+ // Tailwind ring-4 generates: box-shadow: 0 0 0 4px var(--tw-ring-color)
526
+ const ringMatch = baseClass.match(/^ring(?:-(\d+))?$/);
527
+ if (ringMatch) {
528
+ const width = ringMatch[1] || '3';
529
+ if (width === '0') {
530
+ return { cat: "visual", val: prefix + "ring:none" };
531
+ }
532
+ // Map Tailwind ring widths to SenangStart semantic values
533
+ const ringScale = {
534
+ '1': 'thin', '2': 'regular', '3': 'small', '4': 'medium', '8': 'big'
535
+ };
536
+ const scale = ringScale[width] || `[${width}px]`;
537
+ return { cat: "visual", val: prefix + "ring:" + scale };
538
+ }
539
+
540
+ // Ring offset - converts to native ring-offset utility
541
+ const ringOffsetMatch = baseClass.match(/^ring-offset-(\d+)$/);
542
+ if (ringOffsetMatch) {
543
+ return { cat: "visual", val: prefix + "ring-offset:" + ringOffsetMatch[1] };
544
+ }
545
+
546
+ // Ring color - converts to native ring-color utility
547
+ const ringColorMatch = baseClass.match(/^ring-((?:slate|gray|zinc|neutral|stone|red|orange|amber|yellow|lime|green|emerald|teal|cyan|sky|blue|indigo|violet|purple|fuchsia|pink|rose|white|black)(?:-\d+)?)$/);
548
+ if (ringColorMatch) {
549
+ return { cat: "visual", val: prefix + "ring-color:" + ringColorMatch[1] };
550
+ }
551
+
417
552
  return null;
418
553
  }
419
554
 
@@ -1577,6 +1577,33 @@ function generateVisualRule(token, config) {
1577
1577
  return `transform: skewY(${cssValue});`;
1578
1578
  },
1579
1579
 
1580
+ // 3D Rotation (Rotate X/Y/Z)
1581
+ 'rotate-x': () => {
1582
+ const cssValue = isArbitrary ? value : `${value}deg`;
1583
+ return `transform: rotateX(${cssValue});`;
1584
+ },
1585
+
1586
+ 'rotate-y': () => {
1587
+ const cssValue = isArbitrary ? value : `${value}deg`;
1588
+ return `transform: rotateY(${cssValue});`;
1589
+ },
1590
+
1591
+ 'rotate-z': () => {
1592
+ const cssValue = isArbitrary ? value : `${value}deg`;
1593
+ return `transform: rotateZ(${cssValue});`;
1594
+ },
1595
+
1596
+ // 3D Translation (Translate Z)
1597
+ 'translate-z': () => {
1598
+ const translatePresets = {
1599
+ 'near': '50px',
1600
+ 'far': '-50px',
1601
+ '0': '0'
1602
+ };
1603
+ const cssValue = isArbitrary ? value : (translatePresets[value] || `var(--s-${value})`);
1604
+ return `transform: translateZ(${cssValue});`;
1605
+ },
1606
+
1580
1607
  // Transform Origin
1581
1608
  'origin': () => {
1582
1609
  const originMap = {
@@ -32,19 +32,45 @@ export const defaultConfig = {
32
32
  preflight: true,
33
33
 
34
34
  theme: {
35
- // 1. SPACING: The "Natural Object" Scale
35
+ // 1. SPACING: The "Natural Object" Scale with multiplier variants
36
36
  // Logic: How big is the object/gap physically?
37
37
  spacing: {
38
- 'none': '0px', // No space
39
- 'thin': '1px', // Hairline (for borders)
40
- 'regular': '2px', // Standard border
41
- 'thick': '3px', // Bold border
42
- 'tiny': '4px', // Pebble (Small offsets)
43
- 'small': '8px', // Matchbox (Grouping inside components)
44
- 'medium': '16px', // Smartphone (Standard default)
45
- 'big': '32px', // Laptop (Separation between groups)
46
- 'giant': '64px', // Door (Layout sections)
47
- 'vast': '128px' // House (Hero sections)
38
+ 'none': '0px', // No space
39
+ 'thin': '1px', // Hairline (for borders)
40
+ 'regular': '2px', // Standard border
41
+ 'thick': '3px', // Bold border
42
+ 'tiny': '4px', // Small offsets
43
+ 'tiny-2x': '6px', // Tiny multiplied
44
+ 'small': '8px', // Grouping inside components
45
+ 'small-2x': '10px', //
46
+ 'small-3x': '12px', //
47
+ 'small-4x': '14px', //
48
+ 'medium': '16px', // Standard default
49
+ 'medium-2x': '20px', //
50
+ 'medium-3x': '24px', //
51
+ 'medium-4x': '28px', //
52
+ 'large': '32px', // Separation between groups
53
+ 'large-2x': '36px', //
54
+ 'large-3x': '40px', //
55
+ 'large-4x': '44px', //
56
+ 'big': '48px', // Layout sections
57
+ 'big-2x': '56px', //
58
+ 'big-3x': '64px', //
59
+ 'big-4x': '80px', //
60
+ 'giant': '96px', // Hero sections
61
+ 'giant-2x': '112px', //
62
+ 'giant-3x': '128px', //
63
+ 'giant-4x': '144px', //
64
+ 'vast': '160px', // Page-level spacing
65
+ 'vast-2x': '176px', //
66
+ 'vast-3x': '192px', //
67
+ 'vast-4x': '208px', //
68
+ 'vast-5x': '224px', //
69
+ 'vast-6x': '240px', //
70
+ 'vast-7x': '256px', //
71
+ 'vast-8x': '288px', //
72
+ 'vast-9x': '320px', //
73
+ 'vast-10x': '384px', //
48
74
  },
49
75
 
50
76
  // 2. RADIUS: Tactile Feel
@@ -7,7 +7,7 @@
7
7
  export const BREAKPOINTS = ['mob', 'tab', 'lap', 'desk', 'tw-sm', 'tw-md', 'tw-lg', 'tw-xl', 'tw-2xl'];
8
8
 
9
9
  // State prefixes
10
- export const STATES = ['hover', 'focus', 'active', 'disabled', 'dark'];
10
+ export const STATES = ['hover', 'focus', 'focus-visible', 'active', 'disabled', 'dark'];
11
11
 
12
12
  // Layout keywords (no colon syntax)
13
13
  export const LAYOUT_KEYWORDS = [
@@ -204,13 +204,42 @@ export const TYPOGRAPHY_KEYWORDS = {
204
204
  // Default theme configuration
205
205
  export const DEFAULT_THEME = {
206
206
  spacing: {
207
- 'none': '0px',
208
- 'tiny': '4px',
209
- 'small': '8px',
210
- 'medium': '16px',
211
- 'big': '32px',
212
- 'giant': '64px',
213
- 'vast': '128px'
207
+ 'none': '0px',
208
+ 'thin': '1px',
209
+ 'regular': '2px',
210
+ 'thick': '3px',
211
+ 'tiny': '4px',
212
+ 'tiny-2x': '6px',
213
+ 'small': '8px',
214
+ 'small-2x': '10px',
215
+ 'small-3x': '12px',
216
+ 'small-4x': '14px',
217
+ 'medium': '16px',
218
+ 'medium-2x': '20px',
219
+ 'medium-3x': '24px',
220
+ 'medium-4x': '28px',
221
+ 'large': '32px',
222
+ 'large-2x': '36px',
223
+ 'large-3x': '40px',
224
+ 'large-4x': '44px',
225
+ 'big': '48px',
226
+ 'big-2x': '56px',
227
+ 'big-3x': '64px',
228
+ 'big-4x': '80px',
229
+ 'giant': '96px',
230
+ 'giant-2x': '112px',
231
+ 'giant-3x': '128px',
232
+ 'giant-4x': '144px',
233
+ 'vast': '160px',
234
+ 'vast-2x': '176px',
235
+ 'vast-3x': '192px',
236
+ 'vast-4x': '208px',
237
+ 'vast-5x': '224px',
238
+ 'vast-6x': '240px',
239
+ 'vast-7x': '256px',
240
+ 'vast-8x': '288px',
241
+ 'vast-9x': '320px',
242
+ 'vast-10x': '384px'
214
243
  },
215
244
  radius: {
216
245
  'none': '0px',
@@ -24,7 +24,15 @@ export const padding = {
24
24
  { property: 'p-x', css: 'padding-left: var(--s-{value}); padding-right: var(--s-{value});', description: 'Horizontal', descriptionMs: 'Mendatar' },
25
25
  { property: 'p-y', css: 'padding-top: var(--s-{value}); padding-bottom: var(--s-{value});', description: 'Vertical', descriptionMs: 'Menegak' }
26
26
  ],
27
- scaleValues: ['none', 'tiny', 'small', 'medium', 'big', 'giant', 'vast'],
27
+ scaleValues: [
28
+ 'none', 'thin', 'regular', 'thick', 'tiny', 'tiny-2x',
29
+ 'small', 'small-2x', 'small-3x', 'small-4x',
30
+ 'medium', 'medium-2x', 'medium-3x', 'medium-4x',
31
+ 'large', 'large-2x', 'large-3x', 'large-4x',
32
+ 'big', 'big-2x', 'big-3x', 'big-4x',
33
+ 'giant', 'giant-2x', 'giant-3x', 'giant-4x',
34
+ 'vast', 'vast-2x', 'vast-3x', 'vast-4x', 'vast-5x', 'vast-6x', 'vast-7x', 'vast-8x', 'vast-9x', 'vast-10x'
35
+ ],
28
36
  supportsArbitrary: true,
29
37
  examples: [
30
38
  { code: '<div space="p:medium">Padding all sides</div>', description: 'Medium padding' },
@@ -89,7 +97,16 @@ export const margin = {
89
97
  { property: 'm-x', css: 'margin-left: var(--s-{value}); margin-right: var(--s-{value});', description: 'Horizontal', descriptionMs: 'Mendatar' },
90
98
  { property: 'm-y', css: 'margin-top: var(--s-{value}); margin-bottom: var(--s-{value});', description: 'Vertical', descriptionMs: 'Menegak' }
91
99
  ],
92
- scaleValues: ['none', 'tiny', 'small', 'medium', 'big', 'giant', 'vast', 'auto'],
100
+ scaleValues: [
101
+ 'none', 'thin', 'regular', 'thick', 'tiny', 'tiny-2x',
102
+ 'small', 'small-2x', 'small-3x', 'small-4x',
103
+ 'medium', 'medium-2x', 'medium-3x', 'medium-4x',
104
+ 'large', 'large-2x', 'large-3x', 'large-4x',
105
+ 'big', 'big-2x', 'big-3x', 'big-4x',
106
+ 'giant', 'giant-2x', 'giant-3x', 'giant-4x',
107
+ 'vast', 'vast-2x', 'vast-3x', 'vast-4x', 'vast-5x', 'vast-6x', 'vast-7x', 'vast-8x', 'vast-9x', 'vast-10x',
108
+ 'auto'
109
+ ],
93
110
  supportsArbitrary: true,
94
111
  examples: [
95
112
  { code: '<div space="m:medium">Margin all sides</div>', description: 'Medium margin' },
@@ -148,7 +165,15 @@ export const gap = {
148
165
  { property: 'g-x', css: 'column-gap: var(--s-{value});', description: 'Column gap', descriptionMs: 'Ruang lajur' },
149
166
  { property: 'g-y', css: 'row-gap: var(--s-{value});', description: 'Row gap', descriptionMs: 'Ruang baris' }
150
167
  ],
151
- scaleValues: ['none', 'tiny', 'small', 'medium', 'big', 'giant', 'vast'],
168
+ scaleValues: [
169
+ 'none', 'thin', 'regular', 'thick', 'tiny', 'tiny-2x',
170
+ 'small', 'small-2x', 'small-3x', 'small-4x',
171
+ 'medium', 'medium-2x', 'medium-3x', 'medium-4x',
172
+ 'large', 'large-2x', 'large-3x', 'large-4x',
173
+ 'big', 'big-2x', 'big-3x', 'big-4x',
174
+ 'giant', 'giant-2x', 'giant-3x', 'giant-4x',
175
+ 'vast', 'vast-2x', 'vast-3x', 'vast-4x', 'vast-5x', 'vast-6x', 'vast-7x', 'vast-8x', 'vast-9x', 'vast-10x'
176
+ ],
152
177
  supportsArbitrary: true,
153
178
  examples: [
154
179
  { code: '<div layout="flex" space="g:medium">Gap between items</div>', description: 'Flex gap' },
@@ -211,7 +236,15 @@ export const width = {
211
236
  { property: 'min-w', css: 'min-width: var(--s-{value});', description: 'Minimum width', descriptionMs: 'Lebar minimum' },
212
237
  { property: 'max-w', css: 'max-width: var(--s-{value});', description: 'Maximum width', descriptionMs: 'Lebar maksimum' }
213
238
  ],
214
- scaleValues: ['none', 'tiny', 'small', 'medium', 'big', 'giant', 'vast'],
239
+ scaleValues: [
240
+ 'none', 'thin', 'regular', 'thick', 'tiny', 'tiny-2x',
241
+ 'small', 'small-2x', 'small-3x', 'small-4x',
242
+ 'medium', 'medium-2x', 'medium-3x', 'medium-4x',
243
+ 'large', 'large-2x', 'large-3x', 'large-4x',
244
+ 'big', 'big-2x', 'big-3x', 'big-4x',
245
+ 'giant', 'giant-2x', 'giant-3x', 'giant-4x',
246
+ 'vast', 'vast-2x', 'vast-3x', 'vast-4x', 'vast-5x', 'vast-6x', 'vast-7x', 'vast-8x', 'vast-9x', 'vast-10x'
247
+ ],
215
248
  supportsArbitrary: true,
216
249
  examples: [
217
250
  { code: '<div space="w:[100%]">Full width</div>', description: 'Full width' },
@@ -270,7 +303,15 @@ export const height = {
270
303
  { property: 'min-h', css: 'min-height: var(--s-{value});', description: 'Minimum height', descriptionMs: 'Tinggi minimum' },
271
304
  { property: 'max-h', css: 'max-height: var(--s-{value});', description: 'Maximum height', descriptionMs: 'Tinggi maksimum' }
272
305
  ],
273
- scaleValues: ['none', 'tiny', 'small', 'medium', 'big', 'giant', 'vast'],
306
+ scaleValues: [
307
+ 'none', 'thin', 'regular', 'thick', 'tiny', 'tiny-2x',
308
+ 'small', 'small-2x', 'small-3x', 'small-4x',
309
+ 'medium', 'medium-2x', 'medium-3x', 'medium-4x',
310
+ 'large', 'large-2x', 'large-3x', 'large-4x',
311
+ 'big', 'big-2x', 'big-3x', 'big-4x',
312
+ 'giant', 'giant-2x', 'giant-3x', 'giant-4x',
313
+ 'vast', 'vast-2x', 'vast-3x', 'vast-4x', 'vast-5x', 'vast-6x', 'vast-7x', 'vast-8x', 'vast-9x', 'vast-10x'
314
+ ],
274
315
  supportsArbitrary: true,
275
316
  examples: [
276
317
  { code: '<div space="h:[100vh]">Full viewport height</div>', description: 'Full height' },