dispersa 0.1.3 → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +21 -5
- package/dist/builders.cjs +1835 -66
- package/dist/builders.cjs.map +1 -1
- package/dist/builders.d.cts +151 -2
- package/dist/builders.d.ts +151 -2
- package/dist/builders.js +1834 -68
- package/dist/builders.js.map +1 -1
- package/dist/cli/cli.d.ts +11 -0
- package/dist/cli/cli.js +201 -0
- package/dist/cli/cli.js.map +1 -0
- package/dist/cli/config.d.ts +8 -0
- package/dist/cli/config.js +8 -0
- package/dist/cli/config.js.map +1 -0
- package/dist/cli/index.d.ts +1 -0
- package/dist/cli/index.js +203 -0
- package/dist/cli/index.js.map +1 -0
- package/dist/filters.cjs +8 -7
- package/dist/filters.cjs.map +1 -1
- package/dist/filters.js +8 -7
- package/dist/filters.js.map +1 -1
- package/dist/{index-CPB9Ea9U.d.ts → index-BP52gB00.d.ts} +179 -56
- package/dist/{index-DKf9WMQG.d.cts → index-CePv_bgv.d.cts} +179 -56
- package/dist/index.cjs +2029 -241
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +3 -3
- package/dist/index.d.ts +3 -3
- package/dist/index.js +2028 -243
- package/dist/index.js.map +1 -1
- package/dist/preprocessors.cjs.map +1 -1
- package/dist/preprocessors.js.map +1 -1
- package/dist/renderers.cjs.map +1 -1
- package/dist/renderers.d.cts +2 -2
- package/dist/renderers.d.ts +2 -2
- package/dist/renderers.js.map +1 -1
- package/dist/transforms.cjs +5 -5
- package/dist/transforms.cjs.map +1 -1
- package/dist/transforms.js +5 -5
- package/dist/transforms.js.map +1 -1
- package/package.json +18 -1
package/dist/index.js
CHANGED
|
@@ -4,7 +4,7 @@ import { constants } from 'fs';
|
|
|
4
4
|
import { mkdir, writeFile, access, readFile } from 'fs/promises';
|
|
5
5
|
import * as path from 'path';
|
|
6
6
|
import { JsonPointer } from 'json-ptr';
|
|
7
|
-
import { formatHex8, formatHex } from 'culori';
|
|
7
|
+
import { converter, formatHex8, formatHex } from 'culori';
|
|
8
8
|
import prettier from 'prettier';
|
|
9
9
|
|
|
10
10
|
var __defProp = Object.defineProperty;
|
|
@@ -159,10 +159,55 @@ var init_errors = __esm({
|
|
|
159
159
|
}
|
|
160
160
|
});
|
|
161
161
|
|
|
162
|
-
// src/
|
|
162
|
+
// src/shared/utils/validation-handler.ts
|
|
163
|
+
var ValidationHandler;
|
|
164
|
+
var init_validation_handler = __esm({
|
|
165
|
+
"src/shared/utils/validation-handler.ts"() {
|
|
166
|
+
ValidationHandler = class {
|
|
167
|
+
mode;
|
|
168
|
+
constructor(options) {
|
|
169
|
+
this.mode = options?.mode ?? "error";
|
|
170
|
+
}
|
|
171
|
+
/**
|
|
172
|
+
* Whether validation checks should run (mode is not 'off')
|
|
173
|
+
*/
|
|
174
|
+
shouldValidate() {
|
|
175
|
+
return this.mode !== "off";
|
|
176
|
+
}
|
|
177
|
+
/**
|
|
178
|
+
* Whether the current mode is 'error' (strictest)
|
|
179
|
+
*/
|
|
180
|
+
isStrict() {
|
|
181
|
+
return this.mode === "error";
|
|
182
|
+
}
|
|
183
|
+
/**
|
|
184
|
+
* Handle a validation issue: throw in 'error' mode, warn in 'warn' mode, ignore in 'off' mode
|
|
185
|
+
*/
|
|
186
|
+
handleIssue(error) {
|
|
187
|
+
if (this.mode === "error") {
|
|
188
|
+
throw error;
|
|
189
|
+
}
|
|
190
|
+
if (this.mode === "warn") {
|
|
191
|
+
console.warn(error.message);
|
|
192
|
+
}
|
|
193
|
+
}
|
|
194
|
+
/**
|
|
195
|
+
* Emit a warning (in 'error' and 'warn' modes, skip in 'off')
|
|
196
|
+
*/
|
|
197
|
+
warn(message) {
|
|
198
|
+
if (this.mode === "off") {
|
|
199
|
+
return;
|
|
200
|
+
}
|
|
201
|
+
console.warn(message);
|
|
202
|
+
}
|
|
203
|
+
};
|
|
204
|
+
}
|
|
205
|
+
});
|
|
206
|
+
|
|
207
|
+
// src/validation/dtcg-schemas/2025.10/format/group.json
|
|
163
208
|
var group_default;
|
|
164
209
|
var init_group = __esm({
|
|
165
|
-
"src/
|
|
210
|
+
"src/validation/dtcg-schemas/2025.10/format/group.json"() {
|
|
166
211
|
group_default = {
|
|
167
212
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
168
213
|
$id: "https://www.designtokens.org/schemas/2025.10/format/group.json",
|
|
@@ -220,10 +265,10 @@ var init_group = __esm({
|
|
|
220
265
|
}
|
|
221
266
|
});
|
|
222
267
|
|
|
223
|
-
// src/
|
|
268
|
+
// src/validation/dtcg-schemas/2025.10/format/groupOrToken.json
|
|
224
269
|
var groupOrToken_default;
|
|
225
270
|
var init_groupOrToken = __esm({
|
|
226
|
-
"src/
|
|
271
|
+
"src/validation/dtcg-schemas/2025.10/format/groupOrToken.json"() {
|
|
227
272
|
groupOrToken_default = {
|
|
228
273
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
229
274
|
$id: "https://www.designtokens.org/schemas/2025.10/format/groupOrToken.json",
|
|
@@ -241,10 +286,10 @@ var init_groupOrToken = __esm({
|
|
|
241
286
|
}
|
|
242
287
|
});
|
|
243
288
|
|
|
244
|
-
// src/
|
|
289
|
+
// src/validation/dtcg-schemas/2025.10/format/token.json
|
|
245
290
|
var token_default;
|
|
246
291
|
var init_token = __esm({
|
|
247
|
-
"src/
|
|
292
|
+
"src/validation/dtcg-schemas/2025.10/format/token.json"() {
|
|
248
293
|
token_default = {
|
|
249
294
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
250
295
|
$id: "https://www.designtokens.org/schemas/2025.10/format/token.json",
|
|
@@ -672,10 +717,10 @@ var init_token = __esm({
|
|
|
672
717
|
}
|
|
673
718
|
});
|
|
674
719
|
|
|
675
|
-
// src/
|
|
720
|
+
// src/validation/dtcg-schemas/2025.10/format/tokenType.json
|
|
676
721
|
var tokenType_default;
|
|
677
722
|
var init_tokenType = __esm({
|
|
678
|
-
"src/
|
|
723
|
+
"src/validation/dtcg-schemas/2025.10/format/tokenType.json"() {
|
|
679
724
|
tokenType_default = {
|
|
680
725
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
681
726
|
$id: "https://www.designtokens.org/schemas/2025.10/format/tokenType.json",
|
|
@@ -701,10 +746,10 @@ var init_tokenType = __esm({
|
|
|
701
746
|
}
|
|
702
747
|
});
|
|
703
748
|
|
|
704
|
-
// src/
|
|
749
|
+
// src/validation/dtcg-schemas/2025.10/format/values/border.json
|
|
705
750
|
var border_default;
|
|
706
751
|
var init_border = __esm({
|
|
707
|
-
"src/
|
|
752
|
+
"src/validation/dtcg-schemas/2025.10/format/values/border.json"() {
|
|
708
753
|
border_default = {
|
|
709
754
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
710
755
|
$id: "https://www.designtokens.org/schemas/2025.10/format/values/border.json",
|
|
@@ -752,10 +797,10 @@ var init_border = __esm({
|
|
|
752
797
|
}
|
|
753
798
|
});
|
|
754
799
|
|
|
755
|
-
// src/
|
|
800
|
+
// src/validation/dtcg-schemas/2025.10/format/values/color.json
|
|
756
801
|
var color_default;
|
|
757
802
|
var init_color = __esm({
|
|
758
|
-
"src/
|
|
803
|
+
"src/validation/dtcg-schemas/2025.10/format/values/color.json"() {
|
|
759
804
|
color_default = {
|
|
760
805
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
761
806
|
$id: "https://www.designtokens.org/schemas/2025.10/format/values/color.json",
|
|
@@ -1273,10 +1318,10 @@ var init_color = __esm({
|
|
|
1273
1318
|
}
|
|
1274
1319
|
});
|
|
1275
1320
|
|
|
1276
|
-
// src/
|
|
1321
|
+
// src/validation/dtcg-schemas/2025.10/format/values/cubicBezier.json
|
|
1277
1322
|
var cubicBezier_default;
|
|
1278
1323
|
var init_cubicBezier = __esm({
|
|
1279
|
-
"src/
|
|
1324
|
+
"src/validation/dtcg-schemas/2025.10/format/values/cubicBezier.json"() {
|
|
1280
1325
|
cubicBezier_default = {
|
|
1281
1326
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
1282
1327
|
$id: "https://www.designtokens.org/schemas/2025.10/format/values/cubicBezier.json",
|
|
@@ -1336,10 +1381,10 @@ var init_cubicBezier = __esm({
|
|
|
1336
1381
|
}
|
|
1337
1382
|
});
|
|
1338
1383
|
|
|
1339
|
-
// src/
|
|
1384
|
+
// src/validation/dtcg-schemas/2025.10/format/values/dimension.json
|
|
1340
1385
|
var dimension_default;
|
|
1341
1386
|
var init_dimension = __esm({
|
|
1342
|
-
"src/
|
|
1387
|
+
"src/validation/dtcg-schemas/2025.10/format/values/dimension.json"() {
|
|
1343
1388
|
dimension_default = {
|
|
1344
1389
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
1345
1390
|
$id: "https://www.designtokens.org/schemas/2025.10/format/values/dimension.json",
|
|
@@ -1377,10 +1422,10 @@ var init_dimension = __esm({
|
|
|
1377
1422
|
}
|
|
1378
1423
|
});
|
|
1379
1424
|
|
|
1380
|
-
// src/
|
|
1425
|
+
// src/validation/dtcg-schemas/2025.10/format/values/duration.json
|
|
1381
1426
|
var duration_default;
|
|
1382
1427
|
var init_duration = __esm({
|
|
1383
|
-
"src/
|
|
1428
|
+
"src/validation/dtcg-schemas/2025.10/format/values/duration.json"() {
|
|
1384
1429
|
duration_default = {
|
|
1385
1430
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
1386
1431
|
$id: "https://www.designtokens.org/schemas/2025.10/format/values/duration.json",
|
|
@@ -1418,10 +1463,10 @@ var init_duration = __esm({
|
|
|
1418
1463
|
}
|
|
1419
1464
|
});
|
|
1420
1465
|
|
|
1421
|
-
// src/
|
|
1466
|
+
// src/validation/dtcg-schemas/2025.10/format/values/fontFamily.json
|
|
1422
1467
|
var fontFamily_default;
|
|
1423
1468
|
var init_fontFamily = __esm({
|
|
1424
|
-
"src/
|
|
1469
|
+
"src/validation/dtcg-schemas/2025.10/format/values/fontFamily.json"() {
|
|
1425
1470
|
fontFamily_default = {
|
|
1426
1471
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
1427
1472
|
$id: "https://www.designtokens.org/schemas/2025.10/format/values/fontFamily.json",
|
|
@@ -1458,10 +1503,10 @@ var init_fontFamily = __esm({
|
|
|
1458
1503
|
}
|
|
1459
1504
|
});
|
|
1460
1505
|
|
|
1461
|
-
// src/
|
|
1506
|
+
// src/validation/dtcg-schemas/2025.10/format/values/fontWeight.json
|
|
1462
1507
|
var fontWeight_default;
|
|
1463
1508
|
var init_fontWeight = __esm({
|
|
1464
|
-
"src/
|
|
1509
|
+
"src/validation/dtcg-schemas/2025.10/format/values/fontWeight.json"() {
|
|
1465
1510
|
fontWeight_default = {
|
|
1466
1511
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
1467
1512
|
$id: "https://www.designtokens.org/schemas/2025.10/format/values/fontWeight.json",
|
|
@@ -1503,10 +1548,10 @@ var init_fontWeight = __esm({
|
|
|
1503
1548
|
}
|
|
1504
1549
|
});
|
|
1505
1550
|
|
|
1506
|
-
// src/
|
|
1551
|
+
// src/validation/dtcg-schemas/2025.10/format/values/gradient.json
|
|
1507
1552
|
var gradient_default;
|
|
1508
1553
|
var init_gradient = __esm({
|
|
1509
|
-
"src/
|
|
1554
|
+
"src/validation/dtcg-schemas/2025.10/format/values/gradient.json"() {
|
|
1510
1555
|
gradient_default = {
|
|
1511
1556
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
1512
1557
|
$id: "https://www.designtokens.org/schemas/2025.10/format/values/gradient.json",
|
|
@@ -1562,10 +1607,10 @@ var init_gradient = __esm({
|
|
|
1562
1607
|
}
|
|
1563
1608
|
});
|
|
1564
1609
|
|
|
1565
|
-
// src/
|
|
1610
|
+
// src/validation/dtcg-schemas/2025.10/format/values/number.json
|
|
1566
1611
|
var number_default;
|
|
1567
1612
|
var init_number = __esm({
|
|
1568
|
-
"src/
|
|
1613
|
+
"src/validation/dtcg-schemas/2025.10/format/values/number.json"() {
|
|
1569
1614
|
number_default = {
|
|
1570
1615
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
1571
1616
|
$id: "https://www.designtokens.org/schemas/2025.10/format/values/number.json",
|
|
@@ -1576,10 +1621,10 @@ var init_number = __esm({
|
|
|
1576
1621
|
}
|
|
1577
1622
|
});
|
|
1578
1623
|
|
|
1579
|
-
// src/
|
|
1624
|
+
// src/validation/dtcg-schemas/2025.10/format/values/shadow.json
|
|
1580
1625
|
var shadow_default;
|
|
1581
1626
|
var init_shadow = __esm({
|
|
1582
|
-
"src/
|
|
1627
|
+
"src/validation/dtcg-schemas/2025.10/format/values/shadow.json"() {
|
|
1583
1628
|
shadow_default = {
|
|
1584
1629
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
1585
1630
|
$id: "https://www.designtokens.org/schemas/2025.10/format/values/shadow.json",
|
|
@@ -1685,10 +1730,10 @@ var init_shadow = __esm({
|
|
|
1685
1730
|
}
|
|
1686
1731
|
});
|
|
1687
1732
|
|
|
1688
|
-
// src/
|
|
1733
|
+
// src/validation/dtcg-schemas/2025.10/format/values/strokeStyle.json
|
|
1689
1734
|
var strokeStyle_default;
|
|
1690
1735
|
var init_strokeStyle = __esm({
|
|
1691
|
-
"src/
|
|
1736
|
+
"src/validation/dtcg-schemas/2025.10/format/values/strokeStyle.json"() {
|
|
1692
1737
|
strokeStyle_default = {
|
|
1693
1738
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
1694
1739
|
$id: "https://www.designtokens.org/schemas/2025.10/format/values/strokeStyle.json",
|
|
@@ -1746,10 +1791,10 @@ var init_strokeStyle = __esm({
|
|
|
1746
1791
|
}
|
|
1747
1792
|
});
|
|
1748
1793
|
|
|
1749
|
-
// src/
|
|
1794
|
+
// src/validation/dtcg-schemas/2025.10/format/values/transition.json
|
|
1750
1795
|
var transition_default;
|
|
1751
1796
|
var init_transition = __esm({
|
|
1752
|
-
"src/
|
|
1797
|
+
"src/validation/dtcg-schemas/2025.10/format/values/transition.json"() {
|
|
1753
1798
|
transition_default = {
|
|
1754
1799
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
1755
1800
|
$id: "https://www.designtokens.org/schemas/2025.10/format/values/transition.json",
|
|
@@ -1797,10 +1842,10 @@ var init_transition = __esm({
|
|
|
1797
1842
|
}
|
|
1798
1843
|
});
|
|
1799
1844
|
|
|
1800
|
-
// src/
|
|
1845
|
+
// src/validation/dtcg-schemas/2025.10/format/values/typography.json
|
|
1801
1846
|
var typography_default;
|
|
1802
1847
|
var init_typography = __esm({
|
|
1803
|
-
"src/
|
|
1848
|
+
"src/validation/dtcg-schemas/2025.10/format/values/typography.json"() {
|
|
1804
1849
|
typography_default = {
|
|
1805
1850
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
1806
1851
|
$id: "https://www.designtokens.org/schemas/2025.10/format/values/typography.json",
|
|
@@ -1870,10 +1915,10 @@ var init_typography = __esm({
|
|
|
1870
1915
|
}
|
|
1871
1916
|
});
|
|
1872
1917
|
|
|
1873
|
-
// src/
|
|
1918
|
+
// src/validation/dtcg-schemas/2025.10/format.json
|
|
1874
1919
|
var format_default;
|
|
1875
1920
|
var init_format = __esm({
|
|
1876
|
-
"src/
|
|
1921
|
+
"src/validation/dtcg-schemas/2025.10/format.json"() {
|
|
1877
1922
|
format_default = {
|
|
1878
1923
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
1879
1924
|
$id: "https://www.designtokens.org/schemas/2025.10/format.json",
|
|
@@ -1982,10 +2027,10 @@ var init_format = __esm({
|
|
|
1982
2027
|
}
|
|
1983
2028
|
});
|
|
1984
2029
|
|
|
1985
|
-
// src/
|
|
2030
|
+
// src/validation/dtcg-schemas/2025.10/resolver/modifier.json
|
|
1986
2031
|
var modifier_default;
|
|
1987
2032
|
var init_modifier = __esm({
|
|
1988
|
-
"src/
|
|
2033
|
+
"src/validation/dtcg-schemas/2025.10/resolver/modifier.json"() {
|
|
1989
2034
|
modifier_default = {
|
|
1990
2035
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
1991
2036
|
$id: "https://www.designtokens.org/schemas/2025.10/resolver/modifier.json",
|
|
@@ -2073,10 +2118,10 @@ var init_modifier = __esm({
|
|
|
2073
2118
|
}
|
|
2074
2119
|
});
|
|
2075
2120
|
|
|
2076
|
-
// src/
|
|
2121
|
+
// src/validation/dtcg-schemas/2025.10/resolver/resolutionOrder.json
|
|
2077
2122
|
var resolutionOrder_default;
|
|
2078
2123
|
var init_resolutionOrder = __esm({
|
|
2079
|
-
"src/
|
|
2124
|
+
"src/validation/dtcg-schemas/2025.10/resolver/resolutionOrder.json"() {
|
|
2080
2125
|
resolutionOrder_default = {
|
|
2081
2126
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
2082
2127
|
$id: "https://www.designtokens.org/schemas/2025.10/resolver/resolutionOrder.json",
|
|
@@ -2196,10 +2241,10 @@ var init_resolutionOrder = __esm({
|
|
|
2196
2241
|
}
|
|
2197
2242
|
});
|
|
2198
2243
|
|
|
2199
|
-
// src/
|
|
2244
|
+
// src/validation/dtcg-schemas/2025.10/resolver/set.json
|
|
2200
2245
|
var set_default;
|
|
2201
2246
|
var init_set = __esm({
|
|
2202
|
-
"src/
|
|
2247
|
+
"src/validation/dtcg-schemas/2025.10/resolver/set.json"() {
|
|
2203
2248
|
set_default = {
|
|
2204
2249
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
2205
2250
|
$id: "https://www.designtokens.org/schemas/2025.10/resolver/set.json",
|
|
@@ -2273,10 +2318,10 @@ var init_set = __esm({
|
|
|
2273
2318
|
}
|
|
2274
2319
|
});
|
|
2275
2320
|
|
|
2276
|
-
// src/
|
|
2321
|
+
// src/validation/dtcg-schemas/2025.10/resolver.json
|
|
2277
2322
|
var resolver_default;
|
|
2278
2323
|
var init_resolver = __esm({
|
|
2279
|
-
"src/
|
|
2324
|
+
"src/validation/dtcg-schemas/2025.10/resolver.json"() {
|
|
2280
2325
|
resolver_default = {
|
|
2281
2326
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
2282
2327
|
$id: "https://www.designtokens.org/schemas/2025.10/resolver.json",
|
|
@@ -2341,10 +2386,10 @@ var init_resolver = __esm({
|
|
|
2341
2386
|
}
|
|
2342
2387
|
});
|
|
2343
2388
|
|
|
2344
|
-
// src/
|
|
2389
|
+
// src/validation/schemas.ts
|
|
2345
2390
|
var formatSchema, tokenSchema, tokenTypeSchema, groupSchema, groupOrTokenSchema, colorValueSchema, dimensionValueSchema, fontFamilyValueSchema, fontWeightValueSchema, durationValueSchema, cubicBezierValueSchema, numberValueSchema, strokeStyleValueSchema, borderValueSchema, transitionValueSchema, shadowValueSchema, gradientValueSchema, typographyValueSchema, resolverSchema, resolverSetSchema, resolverModifierSchema, resolverResolutionOrderSchema, dtcgSchemaRegistry;
|
|
2346
2391
|
var init_schemas = __esm({
|
|
2347
|
-
"src/
|
|
2392
|
+
"src/validation/schemas.ts"() {
|
|
2348
2393
|
init_group();
|
|
2349
2394
|
init_groupOrToken();
|
|
2350
2395
|
init_token();
|
|
@@ -2416,10 +2461,10 @@ var init_schemas = __esm({
|
|
|
2416
2461
|
}
|
|
2417
2462
|
});
|
|
2418
2463
|
|
|
2419
|
-
// src/
|
|
2464
|
+
// src/validation/config-schemas.ts
|
|
2420
2465
|
var resolverSchemaRef, basePluginProperties, commonRendererOptionsProperties, transformPluginSchema, rendererPluginSchema, filterPluginSchema, preprocessorPluginSchema, outputConfigSchema, dispersaOptionsSchema, buildConfigSchema;
|
|
2421
2466
|
var init_config_schemas = __esm({
|
|
2422
|
-
"src/
|
|
2467
|
+
"src/validation/config-schemas.ts"() {
|
|
2423
2468
|
init_schemas();
|
|
2424
2469
|
resolverSchemaRef = resolverSchema;
|
|
2425
2470
|
basePluginProperties = {
|
|
@@ -2473,6 +2518,25 @@ var init_config_schemas = __esm({
|
|
|
2473
2518
|
additionalProperties: true
|
|
2474
2519
|
// Allow custom properties for extended renderers
|
|
2475
2520
|
});
|
|
2521
|
+
({
|
|
2522
|
+
$schema: "http://json-schema.org/draft-07/schema#",
|
|
2523
|
+
type: "object",
|
|
2524
|
+
properties: {
|
|
2525
|
+
preset: { type: "string", enum: ["bundle", "standalone"] },
|
|
2526
|
+
includeImport: {
|
|
2527
|
+
type: "boolean",
|
|
2528
|
+
description: 'Prepend @import "tailwindcss" to the output'
|
|
2529
|
+
},
|
|
2530
|
+
namespace: {
|
|
2531
|
+
type: "string",
|
|
2532
|
+
description: "Optional Tailwind namespace prefix for @theme"
|
|
2533
|
+
},
|
|
2534
|
+
selector: { type: "string" },
|
|
2535
|
+
mediaQuery: { type: "string" },
|
|
2536
|
+
...commonRendererOptionsProperties
|
|
2537
|
+
},
|
|
2538
|
+
additionalProperties: true
|
|
2539
|
+
});
|
|
2476
2540
|
transformPluginSchema = {
|
|
2477
2541
|
$schema: "http://json-schema.org/draft-07/schema#",
|
|
2478
2542
|
type: "object",
|
|
@@ -2678,7 +2742,7 @@ var init_config_schemas = __esm({
|
|
|
2678
2742
|
});
|
|
2679
2743
|
var SchemaValidator;
|
|
2680
2744
|
var init_validator = __esm({
|
|
2681
|
-
"src/
|
|
2745
|
+
"src/validation/validator.ts"() {
|
|
2682
2746
|
init_errors();
|
|
2683
2747
|
init_token_utils();
|
|
2684
2748
|
init_config_schemas();
|
|
@@ -2930,63 +2994,18 @@ var init_validator = __esm({
|
|
|
2930
2994
|
}
|
|
2931
2995
|
});
|
|
2932
2996
|
|
|
2933
|
-
// src/
|
|
2997
|
+
// src/validation/index.ts
|
|
2934
2998
|
var init_validation = __esm({
|
|
2935
|
-
"src/
|
|
2999
|
+
"src/validation/index.ts"() {
|
|
2936
3000
|
init_validator();
|
|
2937
3001
|
}
|
|
2938
3002
|
});
|
|
2939
|
-
|
|
2940
|
-
// src/shared/utils/validation-handler.ts
|
|
2941
|
-
var ValidationHandler;
|
|
2942
|
-
var init_validation_handler = __esm({
|
|
2943
|
-
"src/shared/utils/validation-handler.ts"() {
|
|
2944
|
-
ValidationHandler = class {
|
|
2945
|
-
mode;
|
|
2946
|
-
constructor(options) {
|
|
2947
|
-
this.mode = options?.mode ?? "error";
|
|
2948
|
-
}
|
|
2949
|
-
/**
|
|
2950
|
-
* Whether validation checks should run (mode is not 'off')
|
|
2951
|
-
*/
|
|
2952
|
-
shouldValidate() {
|
|
2953
|
-
return this.mode !== "off";
|
|
2954
|
-
}
|
|
2955
|
-
/**
|
|
2956
|
-
* Whether the current mode is 'error' (strictest)
|
|
2957
|
-
*/
|
|
2958
|
-
isStrict() {
|
|
2959
|
-
return this.mode === "error";
|
|
2960
|
-
}
|
|
2961
|
-
/**
|
|
2962
|
-
* Handle a validation issue: throw in 'error' mode, warn in 'warn' mode, ignore in 'off' mode
|
|
2963
|
-
*/
|
|
2964
|
-
handleIssue(error) {
|
|
2965
|
-
if (this.mode === "error") {
|
|
2966
|
-
throw error;
|
|
2967
|
-
}
|
|
2968
|
-
if (this.mode === "warn") {
|
|
2969
|
-
console.warn(error.message);
|
|
2970
|
-
}
|
|
2971
|
-
}
|
|
2972
|
-
/**
|
|
2973
|
-
* Emit a warning (in 'error' and 'warn' modes, skip in 'off')
|
|
2974
|
-
*/
|
|
2975
|
-
warn(message) {
|
|
2976
|
-
if (this.mode === "off") {
|
|
2977
|
-
return;
|
|
2978
|
-
}
|
|
2979
|
-
console.warn(message);
|
|
2980
|
-
}
|
|
2981
|
-
};
|
|
2982
|
-
}
|
|
2983
|
-
});
|
|
2984
3003
|
var ResolverParser;
|
|
2985
3004
|
var init_resolver_parser = __esm({
|
|
2986
3005
|
"src/adapters/filesystem/resolver-parser.ts"() {
|
|
2987
|
-
init_validation();
|
|
2988
3006
|
init_errors();
|
|
2989
3007
|
init_validation_handler();
|
|
3008
|
+
init_validation();
|
|
2990
3009
|
ResolverParser = class {
|
|
2991
3010
|
validator;
|
|
2992
3011
|
options;
|
|
@@ -3568,7 +3587,7 @@ var init_json = __esm({
|
|
|
3568
3587
|
}
|
|
3569
3588
|
});
|
|
3570
3589
|
|
|
3571
|
-
// src/
|
|
3590
|
+
// src/codegen/type-generator.ts
|
|
3572
3591
|
var TypeGenerator = class {
|
|
3573
3592
|
/**
|
|
3574
3593
|
* Generates complete TypeScript type definitions from resolved tokens
|
|
@@ -3700,8 +3719,8 @@ var TypeGenerator = class {
|
|
|
3700
3719
|
/**
|
|
3701
3720
|
* Add structure properties to lines
|
|
3702
3721
|
*/
|
|
3703
|
-
addStructureProperties(lines, structure,
|
|
3704
|
-
const indentStr = " ".repeat(
|
|
3722
|
+
addStructureProperties(lines, structure, indent2) {
|
|
3723
|
+
const indentStr = " ".repeat(indent2);
|
|
3705
3724
|
for (const [key, value] of Object.entries(structure)) {
|
|
3706
3725
|
if (this.isToken(value)) {
|
|
3707
3726
|
const token = value;
|
|
@@ -3712,7 +3731,7 @@ var TypeGenerator = class {
|
|
|
3712
3731
|
lines.push(`${indentStr}${this.quoteKey(key)}: ${valueType}`);
|
|
3713
3732
|
} else {
|
|
3714
3733
|
lines.push(`${indentStr}${this.quoteKey(key)}: {`);
|
|
3715
|
-
this.addStructureProperties(lines, value,
|
|
3734
|
+
this.addStructureProperties(lines, value, indent2 + 1);
|
|
3716
3735
|
lines.push(`${indentStr}}`);
|
|
3717
3736
|
}
|
|
3718
3737
|
}
|
|
@@ -4057,7 +4076,7 @@ async function writeOutputFile(fileName, content, encoding = "utf-8") {
|
|
|
4057
4076
|
}
|
|
4058
4077
|
}
|
|
4059
4078
|
|
|
4060
|
-
// src/
|
|
4079
|
+
// src/processing/token-modifier.ts
|
|
4061
4080
|
function applyTransforms(tokens, transformList) {
|
|
4062
4081
|
const result = {};
|
|
4063
4082
|
for (const [name, token] of Object.entries(tokens)) {
|
|
@@ -4189,7 +4208,7 @@ init_validation_handler();
|
|
|
4189
4208
|
// src/shared/constants.ts
|
|
4190
4209
|
var DEFAULT_MAX_ALIAS_DEPTH = 10;
|
|
4191
4210
|
|
|
4192
|
-
// src/
|
|
4211
|
+
// src/resolution/alias-resolver.ts
|
|
4193
4212
|
init_errors();
|
|
4194
4213
|
|
|
4195
4214
|
// src/shared/utils/string-similarity.ts
|
|
@@ -4240,7 +4259,7 @@ function findSimilar(target, candidates, maxDistance, maxResults = 3) {
|
|
|
4240
4259
|
return scored.slice(0, maxResults).map((entry) => entry.value);
|
|
4241
4260
|
}
|
|
4242
4261
|
|
|
4243
|
-
// src/
|
|
4262
|
+
// src/resolution/alias-resolver.ts
|
|
4244
4263
|
init_token_utils();
|
|
4245
4264
|
init_validation_handler();
|
|
4246
4265
|
var AliasResolver = class _AliasResolver {
|
|
@@ -4498,7 +4517,7 @@ var AliasResolver = class _AliasResolver {
|
|
|
4498
4517
|
}
|
|
4499
4518
|
};
|
|
4500
4519
|
|
|
4501
|
-
// src/
|
|
4520
|
+
// src/resolution/reference-resolver.ts
|
|
4502
4521
|
init_errors();
|
|
4503
4522
|
init_validation_handler();
|
|
4504
4523
|
var ReferenceResolver = class _ReferenceResolver {
|
|
@@ -4805,7 +4824,7 @@ var ReferenceResolver = class _ReferenceResolver {
|
|
|
4805
4824
|
}
|
|
4806
4825
|
};
|
|
4807
4826
|
|
|
4808
|
-
// src/
|
|
4827
|
+
// src/resolution/resolution-engine.ts
|
|
4809
4828
|
init_errors();
|
|
4810
4829
|
|
|
4811
4830
|
// src/shared/utils/case-insensitive-map.ts
|
|
@@ -4907,10 +4926,10 @@ var CaseInsensitiveMap = class {
|
|
|
4907
4926
|
}
|
|
4908
4927
|
};
|
|
4909
4928
|
|
|
4910
|
-
// src/
|
|
4929
|
+
// src/resolution/resolution-engine.ts
|
|
4911
4930
|
init_validation_handler();
|
|
4912
4931
|
|
|
4913
|
-
// src/
|
|
4932
|
+
// src/resolution/modifier-input-processor.ts
|
|
4914
4933
|
init_errors();
|
|
4915
4934
|
var ModifierInputProcessor = class {
|
|
4916
4935
|
modifiers;
|
|
@@ -5093,7 +5112,7 @@ var ModifierInputProcessor = class {
|
|
|
5093
5112
|
}
|
|
5094
5113
|
};
|
|
5095
5114
|
|
|
5096
|
-
// src/
|
|
5115
|
+
// src/resolution/resolution-engine.ts
|
|
5097
5116
|
var JSON_POINTER_SETS_PREFIX = "#/sets/";
|
|
5098
5117
|
var JSON_POINTER_MODIFIERS_PREFIX = "#/modifiers/";
|
|
5099
5118
|
var ResolutionEngine = class {
|
|
@@ -5378,7 +5397,6 @@ var ResolutionEngine = class {
|
|
|
5378
5397
|
return typeof obj === "object" && obj !== null && "contexts" in obj && typeof obj.contexts === "object";
|
|
5379
5398
|
}
|
|
5380
5399
|
};
|
|
5381
|
-
init_validator();
|
|
5382
5400
|
init_errors();
|
|
5383
5401
|
|
|
5384
5402
|
// src/shared/utils/path-utils.ts
|
|
@@ -5389,11 +5407,12 @@ function formatTokenPath(parentPath, name) {
|
|
|
5389
5407
|
return parentPath.length > 0 ? `${parentPath.join(".")}.${name}` : name;
|
|
5390
5408
|
}
|
|
5391
5409
|
|
|
5392
|
-
// src/
|
|
5410
|
+
// src/tokens/token-parser.ts
|
|
5393
5411
|
init_token_utils();
|
|
5394
5412
|
init_validation_handler();
|
|
5413
|
+
init_validator();
|
|
5395
5414
|
|
|
5396
|
-
// src/
|
|
5415
|
+
// src/tokens/group-extension-resolver.ts
|
|
5397
5416
|
init_errors();
|
|
5398
5417
|
init_token_utils();
|
|
5399
5418
|
var GroupExtensionResolver = class {
|
|
@@ -5555,7 +5574,7 @@ var GroupExtensionResolver = class {
|
|
|
5555
5574
|
}
|
|
5556
5575
|
};
|
|
5557
5576
|
|
|
5558
|
-
// src/
|
|
5577
|
+
// src/tokens/token-parser.ts
|
|
5559
5578
|
var INVALID_NAME_CHARS_REGEX = /[{}.]/;
|
|
5560
5579
|
var TokenParser = class {
|
|
5561
5580
|
validator;
|
|
@@ -6068,9 +6087,9 @@ var TokenPipeline = class {
|
|
|
6068
6087
|
};
|
|
6069
6088
|
|
|
6070
6089
|
// src/dispersa.ts
|
|
6071
|
-
init_validator();
|
|
6072
6090
|
init_errors();
|
|
6073
6091
|
init_token_utils();
|
|
6092
|
+
init_validator();
|
|
6074
6093
|
var Dispersa = class {
|
|
6075
6094
|
validator;
|
|
6076
6095
|
pipeline;
|
|
@@ -6352,7 +6371,7 @@ var Dispersa = class {
|
|
|
6352
6371
|
}
|
|
6353
6372
|
};
|
|
6354
6373
|
|
|
6355
|
-
// src/
|
|
6374
|
+
// src/tokens/types.ts
|
|
6356
6375
|
function isColorToken(token) {
|
|
6357
6376
|
return token.$type === "color";
|
|
6358
6377
|
}
|
|
@@ -6434,7 +6453,7 @@ function colorObjectToHex(color) {
|
|
|
6434
6453
|
return formatHex(culoriColor);
|
|
6435
6454
|
}
|
|
6436
6455
|
|
|
6437
|
-
// src/
|
|
6456
|
+
// src/processing/processors/transforms/built-in/dimension-converter.ts
|
|
6438
6457
|
function isDimensionObject(value) {
|
|
6439
6458
|
return typeof value === "object" && value !== null && "value" in value && "unit" in value;
|
|
6440
6459
|
}
|
|
@@ -6442,127 +6461,868 @@ function dimensionObjectToString(dimension) {
|
|
|
6442
6461
|
return `${dimension.value}${dimension.unit}`;
|
|
6443
6462
|
}
|
|
6444
6463
|
|
|
6445
|
-
// src/renderers/
|
|
6464
|
+
// src/renderers/android.ts
|
|
6446
6465
|
init_errors();
|
|
6447
6466
|
init_token_utils();
|
|
6448
|
-
|
|
6449
|
-
// src/renderers/bundlers/css.ts
|
|
6450
|
-
init_errors();
|
|
6451
6467
|
init_utils();
|
|
6452
|
-
var
|
|
6453
|
-
|
|
6454
|
-
|
|
6455
|
-
|
|
6456
|
-
|
|
6457
|
-
|
|
6468
|
+
var toSRGB = converter("rgb");
|
|
6469
|
+
var toP3 = converter("p3");
|
|
6470
|
+
var KOTLIN_KEYWORDS = /* @__PURE__ */ new Set([
|
|
6471
|
+
"val",
|
|
6472
|
+
"var",
|
|
6473
|
+
"fun",
|
|
6474
|
+
"class",
|
|
6475
|
+
"object",
|
|
6476
|
+
"when",
|
|
6477
|
+
"is",
|
|
6478
|
+
"in",
|
|
6479
|
+
"return",
|
|
6480
|
+
"break",
|
|
6481
|
+
"continue",
|
|
6482
|
+
"do",
|
|
6483
|
+
"while",
|
|
6484
|
+
"for",
|
|
6485
|
+
"if",
|
|
6486
|
+
"else",
|
|
6487
|
+
"try",
|
|
6488
|
+
"catch",
|
|
6489
|
+
"throw",
|
|
6490
|
+
"as",
|
|
6491
|
+
"this",
|
|
6492
|
+
"super",
|
|
6493
|
+
"null",
|
|
6494
|
+
"true",
|
|
6495
|
+
"false"
|
|
6496
|
+
]);
|
|
6497
|
+
var KOTLIN_TYPE_GROUP_MAP = {
|
|
6498
|
+
color: "Colors",
|
|
6499
|
+
dimension: "Spacing",
|
|
6500
|
+
fontFamily: "Fonts",
|
|
6501
|
+
fontWeight: "FontWeights",
|
|
6502
|
+
duration: "Durations",
|
|
6503
|
+
shadow: "Shadows",
|
|
6504
|
+
typography: "Typography",
|
|
6505
|
+
number: "Numbers",
|
|
6506
|
+
cubicBezier: "Animations",
|
|
6507
|
+
border: "Borders"
|
|
6458
6508
|
};
|
|
6459
|
-
|
|
6460
|
-
if (
|
|
6461
|
-
return
|
|
6509
|
+
function resolveColorFormat(format) {
|
|
6510
|
+
if (format === "argb_floats" || format === "argb_float") {
|
|
6511
|
+
return "argb_float";
|
|
6462
6512
|
}
|
|
6463
|
-
|
|
6464
|
-
|
|
6465
|
-
|
|
6466
|
-
|
|
6467
|
-
|
|
6468
|
-
|
|
6469
|
-
|
|
6513
|
+
return "argb_hex";
|
|
6514
|
+
}
|
|
6515
|
+
function indent(width, level) {
|
|
6516
|
+
return " ".repeat(width * level);
|
|
6517
|
+
}
|
|
6518
|
+
function escapeKotlinString(str) {
|
|
6519
|
+
return str.replace(/\\/g, "\\\\").replace(/"/g, '\\"').replace(/\n/g, "\\n").replace(/\$/g, "\\$");
|
|
6520
|
+
}
|
|
6521
|
+
function escapeKDoc(str) {
|
|
6522
|
+
return str.replace(/\*\//g, "* /").replace(/\r?\n/g, " ").trim();
|
|
6523
|
+
}
|
|
6524
|
+
function formatKotlinNumber(value) {
|
|
6525
|
+
return Number.isInteger(value) ? `${value}.0` : String(value);
|
|
6526
|
+
}
|
|
6527
|
+
function roundComponent(value) {
|
|
6528
|
+
return Math.round(value * 1e3) / 1e3;
|
|
6529
|
+
}
|
|
6530
|
+
function toResourceName(family) {
|
|
6531
|
+
return family.toLowerCase().replace(/[^a-z0-9]+/g, "_").replace(/^_|_$/g, "");
|
|
6532
|
+
}
|
|
6533
|
+
function toPascalCase(name) {
|
|
6534
|
+
const pascal = name.replace(/[-._]+(.)/g, (_, c) => c.toUpperCase()).replace(/[-._]+$/g, "").replace(/^[-._]+/g, "");
|
|
6535
|
+
const result = pascal.charAt(0).toUpperCase() + pascal.slice(1);
|
|
6536
|
+
if (/^\d/.test(result)) {
|
|
6537
|
+
return `_${result}`;
|
|
6470
6538
|
}
|
|
6471
|
-
|
|
6472
|
-
|
|
6539
|
+
return KOTLIN_KEYWORDS.has(result.charAt(0).toLowerCase() + result.slice(1)) ? `\`${result}\`` : result;
|
|
6540
|
+
}
|
|
6541
|
+
function toKotlinIdentifier(name) {
|
|
6542
|
+
const camel = name.replace(/[-._]+(.)/g, (_, c) => c.toUpperCase()).replace(/[-._]+$/g, "").replace(/^[-._]+/g, "");
|
|
6543
|
+
const identifier = camel.charAt(0).toLowerCase() + camel.slice(1);
|
|
6544
|
+
if (/^\d/.test(identifier)) {
|
|
6545
|
+
return `_${identifier}`;
|
|
6473
6546
|
}
|
|
6474
|
-
|
|
6475
|
-
|
|
6476
|
-
|
|
6477
|
-
|
|
6478
|
-
|
|
6479
|
-
|
|
6480
|
-
|
|
6547
|
+
return KOTLIN_KEYWORDS.has(identifier) ? `\`${identifier}\`` : identifier;
|
|
6548
|
+
}
|
|
6549
|
+
var AndroidRenderer = class {
|
|
6550
|
+
async format(context, options) {
|
|
6551
|
+
if (!options?.packageName) {
|
|
6552
|
+
throw new ConfigurationError(
|
|
6553
|
+
`Output "${context.output.name}": packageName is required for Android output`
|
|
6554
|
+
);
|
|
6481
6555
|
}
|
|
6482
|
-
const
|
|
6483
|
-
|
|
6484
|
-
|
|
6556
|
+
const opts = {
|
|
6557
|
+
preset: options?.preset ?? "standalone",
|
|
6558
|
+
packageName: options.packageName,
|
|
6559
|
+
objectName: options?.objectName ?? "DesignTokens",
|
|
6560
|
+
colorFormat: resolveColorFormat(options?.colorFormat),
|
|
6561
|
+
colorSpace: options?.colorSpace ?? "sRGB",
|
|
6562
|
+
structure: options?.structure ?? "nested",
|
|
6563
|
+
visibility: options?.visibility,
|
|
6564
|
+
indent: options?.indent ?? 4
|
|
6565
|
+
};
|
|
6566
|
+
if (opts.preset === "bundle") {
|
|
6567
|
+
return await this.formatBundle(context, opts);
|
|
6485
6568
|
}
|
|
6569
|
+
return await this.formatStandalone(context, opts);
|
|
6486
6570
|
}
|
|
6487
|
-
|
|
6488
|
-
|
|
6489
|
-
|
|
6490
|
-
|
|
6491
|
-
|
|
6492
|
-
|
|
6493
|
-
|
|
6494
|
-
|
|
6495
|
-
|
|
6496
|
-
|
|
6497
|
-
|
|
6498
|
-
|
|
6499
|
-
|
|
6500
|
-
|
|
6501
|
-
|
|
6502
|
-
|
|
6503
|
-
|
|
6504
|
-
|
|
6505
|
-
|
|
6506
|
-
|
|
6507
|
-
|
|
6508
|
-
cssBlocks.push(`${header}
|
|
6509
|
-
${css2}`);
|
|
6571
|
+
// -----------------------------------------------------------------------
|
|
6572
|
+
// Token tree (nested mode)
|
|
6573
|
+
// -----------------------------------------------------------------------
|
|
6574
|
+
buildTokenTree(tokens) {
|
|
6575
|
+
const root = { children: /* @__PURE__ */ new Map() };
|
|
6576
|
+
for (const [, token] of getSortedTokenEntries(tokens)) {
|
|
6577
|
+
let current = root;
|
|
6578
|
+
const segments = token.path;
|
|
6579
|
+
for (let i = 0; i < segments.length - 1; i++) {
|
|
6580
|
+
const seg = segments[i];
|
|
6581
|
+
if (!current.children.has(seg)) {
|
|
6582
|
+
current.children.set(seg, { children: /* @__PURE__ */ new Map() });
|
|
6583
|
+
}
|
|
6584
|
+
current = current.children.get(seg);
|
|
6585
|
+
}
|
|
6586
|
+
const leafName = segments[segments.length - 1] ?? token.name;
|
|
6587
|
+
const leaf = current.children.get(leafName) ?? { children: /* @__PURE__ */ new Map() };
|
|
6588
|
+
leaf.token = token;
|
|
6589
|
+
current.children.set(leafName, leaf);
|
|
6590
|
+
}
|
|
6591
|
+
return root;
|
|
6510
6592
|
}
|
|
6511
|
-
|
|
6512
|
-
|
|
6513
|
-
|
|
6514
|
-
|
|
6515
|
-
|
|
6516
|
-
|
|
6593
|
+
// -----------------------------------------------------------------------
|
|
6594
|
+
// Flat structure grouping
|
|
6595
|
+
// -----------------------------------------------------------------------
|
|
6596
|
+
groupTokensByType(tokens) {
|
|
6597
|
+
const groupMap = /* @__PURE__ */ new Map();
|
|
6598
|
+
for (const [, token] of getSortedTokenEntries(tokens)) {
|
|
6599
|
+
const groupName = KOTLIN_TYPE_GROUP_MAP[token.$type ?? ""] ?? "Other";
|
|
6600
|
+
const existing = groupMap.get(groupName) ?? [];
|
|
6601
|
+
existing.push(token);
|
|
6602
|
+
groupMap.set(groupName, existing);
|
|
6603
|
+
}
|
|
6604
|
+
return Array.from(groupMap.entries()).map(([name, groupTokens]) => ({
|
|
6605
|
+
name,
|
|
6606
|
+
tokens: groupTokens
|
|
6607
|
+
}));
|
|
6517
6608
|
}
|
|
6518
|
-
|
|
6519
|
-
|
|
6520
|
-
|
|
6521
|
-
|
|
6522
|
-
)
|
|
6523
|
-
|
|
6524
|
-
|
|
6609
|
+
/**
|
|
6610
|
+
* Builds a flattened camelCase name from a token's path, stripping the
|
|
6611
|
+
* type prefix segment (which is already represented by the group object).
|
|
6612
|
+
*/
|
|
6613
|
+
buildFlatKotlinName(token) {
|
|
6614
|
+
const path7 = token.path;
|
|
6615
|
+
const withoutTypePrefix = path7.length > 1 ? path7.slice(1) : path7;
|
|
6616
|
+
const joined = withoutTypePrefix.join("_");
|
|
6617
|
+
return toKotlinIdentifier(joined);
|
|
6618
|
+
}
|
|
6619
|
+
// -----------------------------------------------------------------------
|
|
6620
|
+
// Rendering
|
|
6621
|
+
// -----------------------------------------------------------------------
|
|
6622
|
+
formatTokens(tokens, options) {
|
|
6623
|
+
if (options.structure === "flat") {
|
|
6624
|
+
return this.formatAsFlat(tokens, options);
|
|
6625
|
+
}
|
|
6626
|
+
return this.formatAsNested(tokens, options);
|
|
6627
|
+
}
|
|
6628
|
+
formatAsNested(tokens, options) {
|
|
6629
|
+
const tree = this.buildTokenTree(tokens);
|
|
6630
|
+
const tokenTypes = /* @__PURE__ */ new Set();
|
|
6631
|
+
this.collectTokenTypes(tree, tokenTypes);
|
|
6632
|
+
return this.buildFile(tokenTypes, options, (lines, vis) => {
|
|
6633
|
+
lines.push(`@Suppress("unused")`);
|
|
6634
|
+
lines.push(`${vis}object ${options.objectName} {`);
|
|
6635
|
+
this.renderTreeChildren(lines, tree, 1, options);
|
|
6636
|
+
lines.push("}");
|
|
6637
|
+
});
|
|
6525
6638
|
}
|
|
6526
|
-
|
|
6527
|
-
|
|
6639
|
+
formatAsFlat(tokens, options) {
|
|
6640
|
+
const groups = this.groupTokensByType(tokens);
|
|
6641
|
+
const tokenTypes = this.collectTokenTypesFromEntries(tokens);
|
|
6642
|
+
return this.buildFile(tokenTypes, options, (lines, vis) => {
|
|
6643
|
+
lines.push(`@Suppress("unused")`);
|
|
6644
|
+
lines.push(`${vis}object ${options.objectName} {`);
|
|
6645
|
+
this.renderFlatGroups(lines, groups, 1, options);
|
|
6646
|
+
lines.push("}");
|
|
6647
|
+
});
|
|
6528
6648
|
}
|
|
6529
|
-
|
|
6530
|
-
|
|
6531
|
-
|
|
6532
|
-
|
|
6533
|
-
|
|
6534
|
-
options
|
|
6535
|
-
|
|
6536
|
-
|
|
6537
|
-
|
|
6538
|
-
|
|
6539
|
-
|
|
6540
|
-
|
|
6541
|
-
|
|
6542
|
-
|
|
6543
|
-
minify: options?.minify,
|
|
6544
|
-
referenceTokens
|
|
6545
|
-
});
|
|
6546
|
-
return `/* Modifier: ${modifier}=${context} */
|
|
6547
|
-
${css2}`;
|
|
6548
|
-
}
|
|
6549
|
-
function collectSetTokens(tokens, setName, included) {
|
|
6550
|
-
const result = {};
|
|
6551
|
-
for (const [name, token] of Object.entries(tokens)) {
|
|
6552
|
-
if (!included.has(name) && getSourceSet(token) === setName) {
|
|
6553
|
-
result[name] = token;
|
|
6649
|
+
/**
|
|
6650
|
+
* Shared file preamble: header, package, imports, optional ShadowToken class.
|
|
6651
|
+
* The `renderBody` callback appends the main object(s) to `lines`.
|
|
6652
|
+
*/
|
|
6653
|
+
buildFile(tokenTypes, options, renderBody) {
|
|
6654
|
+
const imports = this.collectImports(tokenTypes, options);
|
|
6655
|
+
const vis = options.visibility ? `${options.visibility} ` : "";
|
|
6656
|
+
const lines = [];
|
|
6657
|
+
lines.push(this.buildFileHeader());
|
|
6658
|
+
lines.push("");
|
|
6659
|
+
lines.push(`package ${options.packageName}`);
|
|
6660
|
+
lines.push("");
|
|
6661
|
+
for (const imp of imports) {
|
|
6662
|
+
lines.push(`import ${imp}`);
|
|
6554
6663
|
}
|
|
6555
|
-
|
|
6556
|
-
|
|
6557
|
-
}
|
|
6558
|
-
|
|
6559
|
-
|
|
6560
|
-
|
|
6561
|
-
if (!included.has(name) && (getSourceModifier(token) ?? "").toLowerCase() === expectedSource) {
|
|
6562
|
-
result[name] = token;
|
|
6664
|
+
if (imports.length > 0) {
|
|
6665
|
+
lines.push("");
|
|
6666
|
+
}
|
|
6667
|
+
if (tokenTypes.has("shadow")) {
|
|
6668
|
+
lines.push(...this.buildShadowTokenClass(vis, options));
|
|
6669
|
+
lines.push("");
|
|
6563
6670
|
}
|
|
6671
|
+
renderBody(lines, vis);
|
|
6672
|
+
lines.push("");
|
|
6673
|
+
return lines.join("\n");
|
|
6564
6674
|
}
|
|
6565
|
-
|
|
6675
|
+
renderFlatGroups(lines, groups, baseDepth, options) {
|
|
6676
|
+
const vis = options.visibility ? `${options.visibility} ` : "";
|
|
6677
|
+
const groupIndent = indent(options.indent, baseDepth);
|
|
6678
|
+
const valIndent = indent(options.indent, baseDepth + 1);
|
|
6679
|
+
for (const group of groups) {
|
|
6680
|
+
lines.push(`${groupIndent}${vis}object ${group.name} {`);
|
|
6681
|
+
for (const token of group.tokens) {
|
|
6682
|
+
const kotlinName = this.buildFlatKotlinName(token);
|
|
6683
|
+
const kotlinValue = this.formatKotlinValue(token, options, baseDepth + 1);
|
|
6684
|
+
const annotation = this.typeAnnotationSuffix(token);
|
|
6685
|
+
if (token.$description) {
|
|
6686
|
+
lines.push(`${valIndent}/** ${escapeKDoc(token.$description)} */`);
|
|
6687
|
+
}
|
|
6688
|
+
lines.push(`${valIndent}${vis}val ${kotlinName}${annotation} = ${kotlinValue}`);
|
|
6689
|
+
}
|
|
6690
|
+
lines.push(`${groupIndent}}`);
|
|
6691
|
+
lines.push("");
|
|
6692
|
+
}
|
|
6693
|
+
}
|
|
6694
|
+
renderTreeChildren(lines, node, depth, options) {
|
|
6695
|
+
const vis = options.visibility ? `${options.visibility} ` : "";
|
|
6696
|
+
const pad = indent(options.indent, depth);
|
|
6697
|
+
const entries = Array.from(node.children.entries());
|
|
6698
|
+
for (let idx = 0; idx < entries.length; idx++) {
|
|
6699
|
+
const [key, child] = entries[idx];
|
|
6700
|
+
if (child.token && child.children.size === 0) {
|
|
6701
|
+
this.renderLeaf(lines, key, child.token, depth, options);
|
|
6702
|
+
} else if (child.children.size > 0 && !child.token) {
|
|
6703
|
+
const objectName = toPascalCase(key);
|
|
6704
|
+
lines.push(`${pad}${vis}object ${objectName} {`);
|
|
6705
|
+
this.renderTreeChildren(lines, child, depth + 1, options);
|
|
6706
|
+
lines.push(`${pad}}`);
|
|
6707
|
+
if (idx < entries.length - 1) {
|
|
6708
|
+
lines.push("");
|
|
6709
|
+
}
|
|
6710
|
+
} else {
|
|
6711
|
+
this.renderLeaf(lines, key, child.token, depth, options);
|
|
6712
|
+
this.renderTreeChildren(lines, child, depth, options);
|
|
6713
|
+
}
|
|
6714
|
+
}
|
|
6715
|
+
}
|
|
6716
|
+
renderLeaf(lines, key, token, depth, options) {
|
|
6717
|
+
const vis = options.visibility ? `${options.visibility} ` : "";
|
|
6718
|
+
const pad = indent(options.indent, depth);
|
|
6719
|
+
const kotlinName = toKotlinIdentifier(key);
|
|
6720
|
+
const kotlinValue = this.formatKotlinValue(token, options, depth);
|
|
6721
|
+
const annotation = this.typeAnnotationSuffix(token);
|
|
6722
|
+
if (token.$description) {
|
|
6723
|
+
lines.push(`${pad}/** ${escapeKDoc(token.$description)} */`);
|
|
6724
|
+
}
|
|
6725
|
+
lines.push(`${pad}${vis}val ${kotlinName}${annotation} = ${kotlinValue}`);
|
|
6726
|
+
}
|
|
6727
|
+
buildFileHeader() {
|
|
6728
|
+
return [
|
|
6729
|
+
"// Generated by Dispersa - do not edit manually",
|
|
6730
|
+
"// https://github.com/timges/dispersa"
|
|
6731
|
+
].join("\n");
|
|
6732
|
+
}
|
|
6733
|
+
// -----------------------------------------------------------------------
|
|
6734
|
+
// Shadow data class
|
|
6735
|
+
// -----------------------------------------------------------------------
|
|
6736
|
+
buildShadowTokenClass(vis, options) {
|
|
6737
|
+
const i1 = indent(options.indent, 1);
|
|
6738
|
+
return [
|
|
6739
|
+
"@Immutable",
|
|
6740
|
+
`${vis}data class ShadowToken(`,
|
|
6741
|
+
`${i1}val color: Color,`,
|
|
6742
|
+
`${i1}val elevation: Dp,`,
|
|
6743
|
+
`${i1}val offsetX: Dp,`,
|
|
6744
|
+
`${i1}val offsetY: Dp,`,
|
|
6745
|
+
")"
|
|
6746
|
+
];
|
|
6747
|
+
}
|
|
6748
|
+
// -----------------------------------------------------------------------
|
|
6749
|
+
// Imports (tree-shaken)
|
|
6750
|
+
// -----------------------------------------------------------------------
|
|
6751
|
+
collectImports(tokenTypes, options) {
|
|
6752
|
+
const imports = /* @__PURE__ */ new Set();
|
|
6753
|
+
const ns = "androidx.compose";
|
|
6754
|
+
const hasColors = tokenTypes.has("color") || tokenTypes.has("shadow") || tokenTypes.has("border");
|
|
6755
|
+
if (hasColors) {
|
|
6756
|
+
imports.add(`${ns}.ui.graphics.Color`);
|
|
6757
|
+
}
|
|
6758
|
+
if (tokenTypes.has("dimension") || tokenTypes.has("shadow") || tokenTypes.has("border")) {
|
|
6759
|
+
imports.add(`${ns}.ui.unit.Dp`);
|
|
6760
|
+
imports.add(`${ns}.ui.unit.dp`);
|
|
6761
|
+
}
|
|
6762
|
+
if (tokenTypes.has("typography") || tokenTypes.has("fontFamily")) {
|
|
6763
|
+
imports.add(`${ns}.ui.text.TextStyle`);
|
|
6764
|
+
imports.add(`${ns}.ui.unit.sp`);
|
|
6765
|
+
}
|
|
6766
|
+
if (tokenTypes.has("typography") || tokenTypes.has("fontWeight")) {
|
|
6767
|
+
imports.add(`${ns}.ui.text.font.FontWeight`);
|
|
6768
|
+
}
|
|
6769
|
+
if (tokenTypes.has("fontFamily")) {
|
|
6770
|
+
imports.add(`${ns}.ui.text.font.FontFamily`);
|
|
6771
|
+
}
|
|
6772
|
+
if (tokenTypes.has("duration")) {
|
|
6773
|
+
imports.add("kotlin.time.Duration");
|
|
6774
|
+
imports.add("kotlin.time.Duration.Companion.milliseconds");
|
|
6775
|
+
imports.add("kotlin.time.Duration.Companion.seconds");
|
|
6776
|
+
}
|
|
6777
|
+
if (tokenTypes.has("cubicBezier")) {
|
|
6778
|
+
imports.add(`${ns}.animation.core.CubicBezierEasing`);
|
|
6779
|
+
}
|
|
6780
|
+
if (tokenTypes.has("shadow")) {
|
|
6781
|
+
imports.add(`${ns}.runtime.Immutable`);
|
|
6782
|
+
}
|
|
6783
|
+
if (tokenTypes.has("border")) {
|
|
6784
|
+
imports.add(`${ns}.foundation.BorderStroke`);
|
|
6785
|
+
}
|
|
6786
|
+
if (options.colorSpace === "displayP3" && hasColors) {
|
|
6787
|
+
imports.add(`${ns}.ui.graphics.colorspace.ColorSpaces`);
|
|
6788
|
+
}
|
|
6789
|
+
return Array.from(imports).sort();
|
|
6790
|
+
}
|
|
6791
|
+
collectTokenTypes(node, types) {
|
|
6792
|
+
if (node.token?.$type) {
|
|
6793
|
+
types.add(node.token.$type);
|
|
6794
|
+
}
|
|
6795
|
+
for (const child of node.children.values()) {
|
|
6796
|
+
this.collectTokenTypes(child, types);
|
|
6797
|
+
}
|
|
6798
|
+
}
|
|
6799
|
+
collectTokenTypesFromEntries(tokens) {
|
|
6800
|
+
const types = /* @__PURE__ */ new Set();
|
|
6801
|
+
for (const [, token] of Object.entries(tokens)) {
|
|
6802
|
+
if (token.$type) {
|
|
6803
|
+
types.add(token.$type);
|
|
6804
|
+
}
|
|
6805
|
+
}
|
|
6806
|
+
return types;
|
|
6807
|
+
}
|
|
6808
|
+
// -----------------------------------------------------------------------
|
|
6809
|
+
// Type annotations
|
|
6810
|
+
// -----------------------------------------------------------------------
|
|
6811
|
+
getTypeAnnotation(token) {
|
|
6812
|
+
switch (token.$type) {
|
|
6813
|
+
case "color":
|
|
6814
|
+
return "Color";
|
|
6815
|
+
case "dimension":
|
|
6816
|
+
return "Dp";
|
|
6817
|
+
case "fontFamily":
|
|
6818
|
+
return "FontFamily";
|
|
6819
|
+
case "fontWeight":
|
|
6820
|
+
return "FontWeight";
|
|
6821
|
+
case "duration":
|
|
6822
|
+
return "Duration";
|
|
6823
|
+
case "shadow":
|
|
6824
|
+
return "ShadowToken";
|
|
6825
|
+
case "cubicBezier":
|
|
6826
|
+
return "CubicBezierEasing";
|
|
6827
|
+
case "number":
|
|
6828
|
+
return "Double";
|
|
6829
|
+
case "typography":
|
|
6830
|
+
return "TextStyle";
|
|
6831
|
+
case "border":
|
|
6832
|
+
return "BorderStroke";
|
|
6833
|
+
default: {
|
|
6834
|
+
const value = token.$value;
|
|
6835
|
+
if (typeof value === "string") {
|
|
6836
|
+
return "String";
|
|
6837
|
+
}
|
|
6838
|
+
if (typeof value === "boolean") {
|
|
6839
|
+
return "Boolean";
|
|
6840
|
+
}
|
|
6841
|
+
if (typeof value === "number") {
|
|
6842
|
+
return "Double";
|
|
6843
|
+
}
|
|
6844
|
+
return void 0;
|
|
6845
|
+
}
|
|
6846
|
+
}
|
|
6847
|
+
}
|
|
6848
|
+
typeAnnotationSuffix(token) {
|
|
6849
|
+
const type = this.getTypeAnnotation(token);
|
|
6850
|
+
return type ? `: ${type}` : "";
|
|
6851
|
+
}
|
|
6852
|
+
// -----------------------------------------------------------------------
|
|
6853
|
+
// Value formatting
|
|
6854
|
+
// -----------------------------------------------------------------------
|
|
6855
|
+
formatKotlinValue(token, options, depth) {
|
|
6856
|
+
const value = token.$value;
|
|
6857
|
+
if (token.$type === "color") {
|
|
6858
|
+
return this.formatColorValue(value, options);
|
|
6859
|
+
}
|
|
6860
|
+
if (token.$type === "dimension") {
|
|
6861
|
+
return this.formatDimensionValue(value);
|
|
6862
|
+
}
|
|
6863
|
+
if (token.$type === "fontFamily") {
|
|
6864
|
+
return this.formatFontFamilyValue(value);
|
|
6865
|
+
}
|
|
6866
|
+
if (token.$type === "fontWeight") {
|
|
6867
|
+
return this.formatFontWeightValue(value);
|
|
6868
|
+
}
|
|
6869
|
+
if (token.$type === "duration") {
|
|
6870
|
+
return this.formatDurationValue(value);
|
|
6871
|
+
}
|
|
6872
|
+
if (token.$type === "shadow") {
|
|
6873
|
+
return this.formatShadowValue(value, options, depth);
|
|
6874
|
+
}
|
|
6875
|
+
if (token.$type === "typography") {
|
|
6876
|
+
return this.formatTypographyValue(value, options, depth);
|
|
6877
|
+
}
|
|
6878
|
+
if (token.$type === "border") {
|
|
6879
|
+
return this.formatBorderValue(value, options);
|
|
6880
|
+
}
|
|
6881
|
+
if (token.$type === "number") {
|
|
6882
|
+
return typeof value === "number" ? formatKotlinNumber(value) : String(value);
|
|
6883
|
+
}
|
|
6884
|
+
if (token.$type === "cubicBezier" && Array.isArray(value) && value.length === 4) {
|
|
6885
|
+
return `CubicBezierEasing(${value[0]}f, ${value[1]}f, ${value[2]}f, ${value[3]}f)`;
|
|
6886
|
+
}
|
|
6887
|
+
if (typeof value === "string") {
|
|
6888
|
+
return `"${escapeKotlinString(value)}"`;
|
|
6889
|
+
}
|
|
6890
|
+
if (typeof value === "number") {
|
|
6891
|
+
return formatKotlinNumber(value);
|
|
6892
|
+
}
|
|
6893
|
+
if (typeof value === "boolean") {
|
|
6894
|
+
return value ? "true" : "false";
|
|
6895
|
+
}
|
|
6896
|
+
return `"${escapeKotlinString(String(value))}"`;
|
|
6897
|
+
}
|
|
6898
|
+
formatColorValue(value, options) {
|
|
6899
|
+
if (!isColorObject(value)) {
|
|
6900
|
+
if (typeof value === "string") {
|
|
6901
|
+
const hex = value.replace("#", "");
|
|
6902
|
+
if (/^[0-9a-fA-F]{6,8}$/.test(hex)) {
|
|
6903
|
+
const argb = hex.length === 8 ? hex : `FF${hex}`;
|
|
6904
|
+
return `Color(0x${argb.toUpperCase()})`;
|
|
6905
|
+
}
|
|
6906
|
+
}
|
|
6907
|
+
return "Color.Unspecified";
|
|
6908
|
+
}
|
|
6909
|
+
const colorObj = value;
|
|
6910
|
+
const alpha = colorObj.alpha ?? 1;
|
|
6911
|
+
if (options.colorFormat === "argb_float" || options.colorSpace === "displayP3") {
|
|
6912
|
+
return this.formatFloatColor(colorObj, alpha, options);
|
|
6913
|
+
}
|
|
6914
|
+
return this.formatHexColor(colorObj, alpha);
|
|
6915
|
+
}
|
|
6916
|
+
formatFloatColor(colorObj, alpha, options) {
|
|
6917
|
+
if (options.colorSpace === "displayP3") {
|
|
6918
|
+
const p3 = toP3(dtcgObjectToCulori(colorObj));
|
|
6919
|
+
const r2 = roundComponent(p3?.r ?? 0);
|
|
6920
|
+
const g2 = roundComponent(p3?.g ?? 0);
|
|
6921
|
+
const b2 = roundComponent(p3?.b ?? 0);
|
|
6922
|
+
return `Color(${r2}f, ${g2}f, ${b2}f, ${roundComponent(alpha)}f, ColorSpaces.DisplayP3)`;
|
|
6923
|
+
}
|
|
6924
|
+
const rgb = toSRGB(dtcgObjectToCulori(colorObj));
|
|
6925
|
+
const r = roundComponent(rgb?.r ?? 0);
|
|
6926
|
+
const g = roundComponent(rgb?.g ?? 0);
|
|
6927
|
+
const b = roundComponent(rgb?.b ?? 0);
|
|
6928
|
+
return `Color(${r}f, ${g}f, ${b}f, ${roundComponent(alpha)}f)`;
|
|
6929
|
+
}
|
|
6930
|
+
formatHexColor(colorObj, alpha) {
|
|
6931
|
+
const hex = colorObjectToHex(colorObj);
|
|
6932
|
+
const hexClean = hex.replace("#", "");
|
|
6933
|
+
if (hexClean.length === 8) {
|
|
6934
|
+
const rrggbb = hexClean.slice(0, 6);
|
|
6935
|
+
const aa = hexClean.slice(6, 8);
|
|
6936
|
+
return `Color(0x${aa.toUpperCase()}${rrggbb.toUpperCase()})`;
|
|
6937
|
+
}
|
|
6938
|
+
const alphaHex = alpha < 1 ? Math.round(alpha * 255).toString(16).padStart(2, "0").toUpperCase() : "FF";
|
|
6939
|
+
return `Color(0x${alphaHex}${hexClean.toUpperCase()})`;
|
|
6940
|
+
}
|
|
6941
|
+
formatDimensionValue(value) {
|
|
6942
|
+
if (isDimensionObject(value)) {
|
|
6943
|
+
const dim = value;
|
|
6944
|
+
const dpValue = dim.unit === "rem" ? dim.value * 16 : dim.value;
|
|
6945
|
+
return `${dpValue}.dp`;
|
|
6946
|
+
}
|
|
6947
|
+
return typeof value === "number" ? `${value}.dp` : `0.dp`;
|
|
6948
|
+
}
|
|
6949
|
+
formatFontFamilyValue(value) {
|
|
6950
|
+
if (Array.isArray(value)) {
|
|
6951
|
+
const primary = value[0];
|
|
6952
|
+
if (typeof primary === "string") {
|
|
6953
|
+
return this.mapKotlinFontFamily(primary);
|
|
6954
|
+
}
|
|
6955
|
+
return "FontFamily.Default";
|
|
6956
|
+
}
|
|
6957
|
+
return typeof value === "string" ? this.mapKotlinFontFamily(value) : "FontFamily.Default";
|
|
6958
|
+
}
|
|
6959
|
+
mapKotlinFontFamily(family) {
|
|
6960
|
+
const normalized = family.toLowerCase().replace(/['"]/g, "").trim();
|
|
6961
|
+
const builtIn = {
|
|
6962
|
+
"sans-serif": "FontFamily.SansSerif",
|
|
6963
|
+
serif: "FontFamily.Serif",
|
|
6964
|
+
monospace: "FontFamily.Monospace",
|
|
6965
|
+
cursive: "FontFamily.Cursive"
|
|
6966
|
+
};
|
|
6967
|
+
return builtIn[normalized] ?? `FontFamily.Default // TODO: load "${family}" via Font(R.font.${toResourceName(family)})`;
|
|
6968
|
+
}
|
|
6969
|
+
formatFontWeightValue(value) {
|
|
6970
|
+
if (typeof value === "number") {
|
|
6971
|
+
return this.numericFontWeight(value);
|
|
6972
|
+
}
|
|
6973
|
+
if (typeof value === "string") {
|
|
6974
|
+
return this.namedFontWeight(value) ?? "FontWeight.Normal";
|
|
6975
|
+
}
|
|
6976
|
+
return "FontWeight.Normal";
|
|
6977
|
+
}
|
|
6978
|
+
numericFontWeight(weight) {
|
|
6979
|
+
if (weight <= 100) {
|
|
6980
|
+
return "FontWeight.Thin";
|
|
6981
|
+
}
|
|
6982
|
+
if (weight <= 200) {
|
|
6983
|
+
return "FontWeight.ExtraLight";
|
|
6984
|
+
}
|
|
6985
|
+
if (weight <= 300) {
|
|
6986
|
+
return "FontWeight.Light";
|
|
6987
|
+
}
|
|
6988
|
+
if (weight <= 400) {
|
|
6989
|
+
return "FontWeight.Normal";
|
|
6990
|
+
}
|
|
6991
|
+
if (weight <= 500) {
|
|
6992
|
+
return "FontWeight.Medium";
|
|
6993
|
+
}
|
|
6994
|
+
if (weight <= 600) {
|
|
6995
|
+
return "FontWeight.SemiBold";
|
|
6996
|
+
}
|
|
6997
|
+
if (weight <= 700) {
|
|
6998
|
+
return "FontWeight.Bold";
|
|
6999
|
+
}
|
|
7000
|
+
if (weight <= 800) {
|
|
7001
|
+
return "FontWeight.ExtraBold";
|
|
7002
|
+
}
|
|
7003
|
+
return "FontWeight.Black";
|
|
7004
|
+
}
|
|
7005
|
+
namedFontWeight(name) {
|
|
7006
|
+
const map = {
|
|
7007
|
+
thin: "FontWeight.Thin",
|
|
7008
|
+
extralight: "FontWeight.ExtraLight",
|
|
7009
|
+
ultralight: "FontWeight.ExtraLight",
|
|
7010
|
+
light: "FontWeight.Light",
|
|
7011
|
+
regular: "FontWeight.Normal",
|
|
7012
|
+
normal: "FontWeight.Normal",
|
|
7013
|
+
medium: "FontWeight.Medium",
|
|
7014
|
+
semibold: "FontWeight.SemiBold",
|
|
7015
|
+
demibold: "FontWeight.SemiBold",
|
|
7016
|
+
bold: "FontWeight.Bold",
|
|
7017
|
+
extrabold: "FontWeight.ExtraBold",
|
|
7018
|
+
heavy: "FontWeight.ExtraBold",
|
|
7019
|
+
black: "FontWeight.Black",
|
|
7020
|
+
ultrabold: "FontWeight.Black"
|
|
7021
|
+
};
|
|
7022
|
+
return map[name.toLowerCase()];
|
|
7023
|
+
}
|
|
7024
|
+
formatDurationValue(value) {
|
|
7025
|
+
if (typeof value === "object" && value !== null && "value" in value && "unit" in value) {
|
|
7026
|
+
const dur = value;
|
|
7027
|
+
return dur.unit === "ms" ? `${dur.value}.milliseconds` : `${dur.value}.seconds`;
|
|
7028
|
+
}
|
|
7029
|
+
return typeof value === "number" ? `${value}.milliseconds` : "0.milliseconds";
|
|
7030
|
+
}
|
|
7031
|
+
formatShadowValue(value, options, depth) {
|
|
7032
|
+
if (Array.isArray(value) && value.length > 0) {
|
|
7033
|
+
return this.formatSingleShadow(value[0], options, depth);
|
|
7034
|
+
}
|
|
7035
|
+
if (typeof value === "object" && value !== null) {
|
|
7036
|
+
return this.formatSingleShadow(value, options, depth);
|
|
7037
|
+
}
|
|
7038
|
+
return "ShadowToken(color = Color.Unspecified, elevation = 0.dp, offsetX = 0.dp, offsetY = 0.dp)";
|
|
7039
|
+
}
|
|
7040
|
+
formatSingleShadow(shadow, options, depth) {
|
|
7041
|
+
const color = isColorObject(shadow.color) ? this.formatColorValue(shadow.color, options) : "Color.Black";
|
|
7042
|
+
const elevation = isDimensionObject(shadow.blur) ? this.formatDimensionValue(shadow.blur) : "0.dp";
|
|
7043
|
+
const offsetX = isDimensionObject(shadow.offsetX) ? this.formatDimensionValue(shadow.offsetX) : "0.dp";
|
|
7044
|
+
const offsetY = isDimensionObject(shadow.offsetY) ? this.formatDimensionValue(shadow.offsetY) : "0.dp";
|
|
7045
|
+
const propIndent = indent(options.indent, depth + 1);
|
|
7046
|
+
const closeIndent = indent(options.indent, depth);
|
|
7047
|
+
return [
|
|
7048
|
+
"ShadowToken(",
|
|
7049
|
+
`${propIndent}color = ${color},`,
|
|
7050
|
+
`${propIndent}elevation = ${elevation},`,
|
|
7051
|
+
`${propIndent}offsetX = ${offsetX},`,
|
|
7052
|
+
`${propIndent}offsetY = ${offsetY},`,
|
|
7053
|
+
`${closeIndent})`
|
|
7054
|
+
].join("\n");
|
|
7055
|
+
}
|
|
7056
|
+
formatBorderValue(value, options) {
|
|
7057
|
+
if (typeof value !== "object" || value === null) {
|
|
7058
|
+
return "BorderStroke(0.dp, Color.Unspecified)";
|
|
7059
|
+
}
|
|
7060
|
+
const border = value;
|
|
7061
|
+
const width = isDimensionObject(border.width) ? this.formatDimensionValue(border.width) : "0.dp";
|
|
7062
|
+
const color = isColorObject(border.color) ? this.formatColorValue(border.color, options) : "Color.Unspecified";
|
|
7063
|
+
return `BorderStroke(${width}, ${color})`;
|
|
7064
|
+
}
|
|
7065
|
+
formatTypographyValue(value, options, depth) {
|
|
7066
|
+
if (typeof value !== "object" || value === null) {
|
|
7067
|
+
return "TextStyle()";
|
|
7068
|
+
}
|
|
7069
|
+
const typo = value;
|
|
7070
|
+
const parts = [];
|
|
7071
|
+
if (isDimensionObject(typo.fontSize)) {
|
|
7072
|
+
const dim = typo.fontSize;
|
|
7073
|
+
const spValue = dim.unit === "rem" ? dim.value * 16 : dim.value;
|
|
7074
|
+
parts.push(`fontSize = ${spValue}.sp`);
|
|
7075
|
+
}
|
|
7076
|
+
if (typo.fontWeight != null) {
|
|
7077
|
+
parts.push(`fontWeight = ${this.formatFontWeightValue(typo.fontWeight)}`);
|
|
7078
|
+
}
|
|
7079
|
+
if (typo.lineHeight != null && typeof typo.lineHeight === "number") {
|
|
7080
|
+
if (isDimensionObject(typo.fontSize)) {
|
|
7081
|
+
const dim = typo.fontSize;
|
|
7082
|
+
const spValue = dim.unit === "rem" ? dim.value * 16 : dim.value;
|
|
7083
|
+
const lineHeightSp = Math.round(spValue * typo.lineHeight * 100) / 100;
|
|
7084
|
+
parts.push(`lineHeight = ${lineHeightSp}.sp`);
|
|
7085
|
+
}
|
|
7086
|
+
}
|
|
7087
|
+
if (isDimensionObject(typo.letterSpacing)) {
|
|
7088
|
+
const dim = typo.letterSpacing;
|
|
7089
|
+
const spValue = dim.unit === "rem" ? dim.value * 16 : dim.value;
|
|
7090
|
+
parts.push(`letterSpacing = ${spValue}.sp`);
|
|
7091
|
+
}
|
|
7092
|
+
if (parts.length === 0) {
|
|
7093
|
+
return "TextStyle()";
|
|
7094
|
+
}
|
|
7095
|
+
const propIndent = indent(options.indent, depth + 1);
|
|
7096
|
+
const closeIndent = indent(options.indent, depth);
|
|
7097
|
+
return `TextStyle(
|
|
7098
|
+
${parts.map((p) => `${propIndent}${p}`).join(",\n")},
|
|
7099
|
+
${closeIndent})`;
|
|
7100
|
+
}
|
|
7101
|
+
// -----------------------------------------------------------------------
|
|
7102
|
+
// Output: standalone
|
|
7103
|
+
// -----------------------------------------------------------------------
|
|
7104
|
+
async formatStandalone(context, options) {
|
|
7105
|
+
const requiresFile = context.buildPath !== void 0 && context.buildPath !== "";
|
|
7106
|
+
if (!context.output.file && requiresFile) {
|
|
7107
|
+
throw new ConfigurationError(
|
|
7108
|
+
`Output "${context.output.name}": file is required for standalone Android output`
|
|
7109
|
+
);
|
|
7110
|
+
}
|
|
7111
|
+
const files = {};
|
|
7112
|
+
for (const { tokens, modifierInputs } of context.permutations) {
|
|
7113
|
+
const processedTokens = stripInternalMetadata(tokens);
|
|
7114
|
+
const content = this.formatTokens(processedTokens, options);
|
|
7115
|
+
const fileName = context.output.file ? resolveFileName(context.output.file, modifierInputs) : buildInMemoryOutputKey({
|
|
7116
|
+
outputName: context.output.name,
|
|
7117
|
+
extension: "kt",
|
|
7118
|
+
modifierInputs,
|
|
7119
|
+
resolver: context.resolver,
|
|
7120
|
+
defaults: context.meta.defaults
|
|
7121
|
+
});
|
|
7122
|
+
files[fileName] = content;
|
|
7123
|
+
}
|
|
7124
|
+
return outputTree(files);
|
|
7125
|
+
}
|
|
7126
|
+
// -----------------------------------------------------------------------
|
|
7127
|
+
// Output: bundle
|
|
7128
|
+
// -----------------------------------------------------------------------
|
|
7129
|
+
async formatBundle(context, options) {
|
|
7130
|
+
const requiresFile = context.buildPath !== void 0 && context.buildPath !== "";
|
|
7131
|
+
if (!context.output.file && requiresFile) {
|
|
7132
|
+
throw new ConfigurationError(
|
|
7133
|
+
`Output "${context.output.name}": file is required for bundle Android output`
|
|
7134
|
+
);
|
|
7135
|
+
}
|
|
7136
|
+
const content = this.formatBundleContent(context, options);
|
|
7137
|
+
const fileName = context.output.file ? resolveFileName(context.output.file, context.meta.basePermutation) : buildInMemoryOutputKey({
|
|
7138
|
+
outputName: context.output.name,
|
|
7139
|
+
extension: "kt",
|
|
7140
|
+
modifierInputs: context.meta.basePermutation,
|
|
7141
|
+
resolver: context.resolver,
|
|
7142
|
+
defaults: context.meta.defaults
|
|
7143
|
+
});
|
|
7144
|
+
return outputTree({ [fileName]: content });
|
|
7145
|
+
}
|
|
7146
|
+
formatBundleContent(context, options) {
|
|
7147
|
+
const allTokenTypes = this.collectAllPermutationTypes(context);
|
|
7148
|
+
return this.buildFile(allTokenTypes, options, (lines, vis) => {
|
|
7149
|
+
const i1 = indent(options.indent, 1);
|
|
7150
|
+
lines.push(`@Suppress("unused")`);
|
|
7151
|
+
lines.push(`${vis}object ${options.objectName} {`);
|
|
7152
|
+
for (let idx = 0; idx < context.permutations.length; idx++) {
|
|
7153
|
+
const { tokens, modifierInputs } = context.permutations[idx];
|
|
7154
|
+
const processedTokens = stripInternalMetadata(tokens);
|
|
7155
|
+
const permName = this.buildPermutationName(modifierInputs);
|
|
7156
|
+
lines.push(`${i1}${vis}object ${permName} {`);
|
|
7157
|
+
this.renderBundleTokens(lines, processedTokens, options, 2);
|
|
7158
|
+
lines.push(`${i1}}`);
|
|
7159
|
+
if (idx < context.permutations.length - 1) {
|
|
7160
|
+
lines.push("");
|
|
7161
|
+
}
|
|
7162
|
+
}
|
|
7163
|
+
lines.push("}");
|
|
7164
|
+
});
|
|
7165
|
+
}
|
|
7166
|
+
collectAllPermutationTypes(context) {
|
|
7167
|
+
const allTokenTypes = /* @__PURE__ */ new Set();
|
|
7168
|
+
for (const { tokens } of context.permutations) {
|
|
7169
|
+
const processed = stripInternalMetadata(tokens);
|
|
7170
|
+
for (const [, token] of Object.entries(processed)) {
|
|
7171
|
+
if (token.$type) {
|
|
7172
|
+
allTokenTypes.add(token.$type);
|
|
7173
|
+
}
|
|
7174
|
+
}
|
|
7175
|
+
}
|
|
7176
|
+
return allTokenTypes;
|
|
7177
|
+
}
|
|
7178
|
+
renderBundleTokens(lines, tokens, options, baseDepth) {
|
|
7179
|
+
if (options.structure === "flat") {
|
|
7180
|
+
const groups = this.groupTokensByType(tokens);
|
|
7181
|
+
this.renderFlatGroups(lines, groups, baseDepth, options);
|
|
7182
|
+
return;
|
|
7183
|
+
}
|
|
7184
|
+
const tree = this.buildTokenTree(tokens);
|
|
7185
|
+
this.renderTreeChildren(lines, tree, baseDepth, options);
|
|
7186
|
+
}
|
|
7187
|
+
buildPermutationName(modifierInputs) {
|
|
7188
|
+
const values = Object.values(modifierInputs);
|
|
7189
|
+
if (values.length === 0) {
|
|
7190
|
+
return "Default";
|
|
7191
|
+
}
|
|
7192
|
+
return values.map((v) => toPascalCase(v)).join("");
|
|
7193
|
+
}
|
|
7194
|
+
};
|
|
7195
|
+
function androidRenderer() {
|
|
7196
|
+
const rendererInstance = new AndroidRenderer();
|
|
7197
|
+
return {
|
|
7198
|
+
format: (context, options) => rendererInstance.format(
|
|
7199
|
+
context,
|
|
7200
|
+
options ?? context.output.options
|
|
7201
|
+
)
|
|
7202
|
+
};
|
|
7203
|
+
}
|
|
7204
|
+
|
|
7205
|
+
// src/renderers/css.ts
|
|
7206
|
+
init_errors();
|
|
7207
|
+
init_token_utils();
|
|
7208
|
+
|
|
7209
|
+
// src/renderers/bundlers/css.ts
|
|
7210
|
+
init_errors();
|
|
7211
|
+
init_utils();
|
|
7212
|
+
var getSourceSet = (token) => {
|
|
7213
|
+
if (typeof token !== "object" || token === null) {
|
|
7214
|
+
return void 0;
|
|
7215
|
+
}
|
|
7216
|
+
const maybe = token;
|
|
7217
|
+
return typeof maybe._sourceSet === "string" ? maybe._sourceSet : void 0;
|
|
7218
|
+
};
|
|
7219
|
+
var getSourceModifier = (token) => {
|
|
7220
|
+
if (typeof token !== "object" || token === null) {
|
|
7221
|
+
return void 0;
|
|
7222
|
+
}
|
|
7223
|
+
const maybe = token;
|
|
7224
|
+
return typeof maybe._sourceModifier === "string" ? maybe._sourceModifier : void 0;
|
|
7225
|
+
};
|
|
7226
|
+
async function bundleAsCss(bundleData, resolver, options, formatTokens) {
|
|
7227
|
+
const baseItem = bundleData.find((item) => item.isBase);
|
|
7228
|
+
if (!baseItem) {
|
|
7229
|
+
throw new BasePermutationError("Base permutation not found in bundle data");
|
|
7230
|
+
}
|
|
7231
|
+
if (!formatTokens) {
|
|
7232
|
+
throw new ConfigurationError("CSS formatter was not provided");
|
|
7233
|
+
}
|
|
7234
|
+
const orderedBundleData = orderBundleData(bundleData, resolver, baseItem);
|
|
7235
|
+
const cssBlocks = [];
|
|
7236
|
+
for (const item of orderedBundleData) {
|
|
7237
|
+
if (item.isBase) {
|
|
7238
|
+
const blocks = await formatBasePermutation(item, resolver, options, formatTokens);
|
|
7239
|
+
cssBlocks.push(...blocks);
|
|
7240
|
+
continue;
|
|
7241
|
+
}
|
|
7242
|
+
const block = await formatModifierPermutation(item, baseItem, options, formatTokens);
|
|
7243
|
+
if (block) {
|
|
7244
|
+
cssBlocks.push(block);
|
|
7245
|
+
}
|
|
7246
|
+
}
|
|
7247
|
+
return cssBlocks.join("\n\n");
|
|
7248
|
+
}
|
|
7249
|
+
async function formatBasePermutation({ tokens, modifierInputs }, resolver, options, formatTokens) {
|
|
7250
|
+
const firstModifierName = resolver.modifiers ? Object.keys(resolver.modifiers)[0] : "";
|
|
7251
|
+
const modifier = firstModifierName ?? "";
|
|
7252
|
+
const context = modifierInputs[modifier] ?? "";
|
|
7253
|
+
const selector = resolveSelector(options?.selector, modifier, context, true, modifierInputs);
|
|
7254
|
+
const mediaQuery = resolveMediaQuery(options?.mediaQuery, modifier, context, true, modifierInputs);
|
|
7255
|
+
const referenceTokens = stripInternalMetadata(tokens);
|
|
7256
|
+
const defaultBlocks = buildDefaultLayerBlocks(tokens, modifierInputs, resolver);
|
|
7257
|
+
const cssBlocks = [];
|
|
7258
|
+
for (const block of defaultBlocks) {
|
|
7259
|
+
const cleanTokens = stripInternalMetadata(block.tokens);
|
|
7260
|
+
const css2 = await formatTokens(cleanTokens, {
|
|
7261
|
+
selector,
|
|
7262
|
+
mediaQuery,
|
|
7263
|
+
minify: options?.minify,
|
|
7264
|
+
referenceTokens
|
|
7265
|
+
});
|
|
7266
|
+
const header = block.description ? `/* ${block.key} */
|
|
7267
|
+
/* ${block.description} */` : `/* ${block.key} */`;
|
|
7268
|
+
cssBlocks.push(`${header}
|
|
7269
|
+
${css2}`);
|
|
7270
|
+
}
|
|
7271
|
+
return cssBlocks;
|
|
7272
|
+
}
|
|
7273
|
+
async function formatModifierPermutation({ tokens, modifierInputs }, baseItem, options, formatTokens) {
|
|
7274
|
+
const differenceCount = countModifierDifferences(modifierInputs, baseItem.modifierInputs);
|
|
7275
|
+
if (differenceCount > 1) {
|
|
7276
|
+
return void 0;
|
|
7277
|
+
}
|
|
7278
|
+
const expectedSource = getExpectedSource(modifierInputs, baseItem.modifierInputs);
|
|
7279
|
+
let tokensToInclude = filterTokensBySource(tokens, expectedSource);
|
|
7280
|
+
const hasSourceMetadata = Object.values(tokens).some(
|
|
7281
|
+
(token) => token != null && getSourceModifier(token) !== void 0
|
|
7282
|
+
);
|
|
7283
|
+
if (Object.keys(tokensToInclude).length === 0 && !hasSourceMetadata) {
|
|
7284
|
+
tokensToInclude = tokens;
|
|
7285
|
+
}
|
|
7286
|
+
if (Object.keys(tokensToInclude).length === 0) {
|
|
7287
|
+
return void 0;
|
|
7288
|
+
}
|
|
7289
|
+
const [modifier, context] = parseModifierSource(expectedSource);
|
|
7290
|
+
const cleanTokens = stripInternalMetadata(tokensToInclude);
|
|
7291
|
+
const referenceTokens = stripInternalMetadata(tokens);
|
|
7292
|
+
const selector = resolveSelector(options?.selector, modifier, context, false, modifierInputs);
|
|
7293
|
+
const mediaQuery = resolveMediaQuery(
|
|
7294
|
+
options?.mediaQuery,
|
|
7295
|
+
modifier,
|
|
7296
|
+
context,
|
|
7297
|
+
false,
|
|
7298
|
+
modifierInputs
|
|
7299
|
+
);
|
|
7300
|
+
const css2 = await formatTokens(cleanTokens, {
|
|
7301
|
+
selector,
|
|
7302
|
+
mediaQuery,
|
|
7303
|
+
minify: options?.minify,
|
|
7304
|
+
referenceTokens
|
|
7305
|
+
});
|
|
7306
|
+
return `/* Modifier: ${modifier}=${context} */
|
|
7307
|
+
${css2}`;
|
|
7308
|
+
}
|
|
7309
|
+
function collectSetTokens(tokens, setName, included) {
|
|
7310
|
+
const result = {};
|
|
7311
|
+
for (const [name, token] of Object.entries(tokens)) {
|
|
7312
|
+
if (!included.has(name) && getSourceSet(token) === setName) {
|
|
7313
|
+
result[name] = token;
|
|
7314
|
+
}
|
|
7315
|
+
}
|
|
7316
|
+
return result;
|
|
7317
|
+
}
|
|
7318
|
+
function collectModifierTokens(tokens, expectedSource, included) {
|
|
7319
|
+
const result = {};
|
|
7320
|
+
for (const [name, token] of Object.entries(tokens)) {
|
|
7321
|
+
if (!included.has(name) && (getSourceModifier(token) ?? "").toLowerCase() === expectedSource) {
|
|
7322
|
+
result[name] = token;
|
|
7323
|
+
}
|
|
7324
|
+
}
|
|
7325
|
+
return result;
|
|
6566
7326
|
}
|
|
6567
7327
|
function collectRemainder(tokens, included) {
|
|
6568
7328
|
const result = {};
|
|
@@ -6768,14 +7528,14 @@ var CssRenderer = class _CssRenderer {
|
|
|
6768
7528
|
return opts.minify ? cssString : await this.formatWithPrettier(cssString);
|
|
6769
7529
|
}
|
|
6770
7530
|
buildCssBlock(lines, groupTokens, selector, tokens, referenceTokens, opts) {
|
|
6771
|
-
const
|
|
7531
|
+
const indent2 = opts.minify ? "" : " ";
|
|
6772
7532
|
const newline = opts.minify ? "" : "\n";
|
|
6773
7533
|
const space = opts.minify ? "" : " ";
|
|
6774
7534
|
const hasMediaQuery = opts.mediaQuery != null && opts.mediaQuery !== "";
|
|
6775
|
-
const tokenIndent = hasMediaQuery ?
|
|
7535
|
+
const tokenIndent = hasMediaQuery ? indent2 + indent2 : indent2;
|
|
6776
7536
|
if (hasMediaQuery) {
|
|
6777
7537
|
lines.push(`@media ${opts.mediaQuery}${space}{${newline}`);
|
|
6778
|
-
lines.push(`${
|
|
7538
|
+
lines.push(`${indent2}${selector}${space}{${newline}`);
|
|
6779
7539
|
} else {
|
|
6780
7540
|
lines.push(`${selector}${space}{${newline}`);
|
|
6781
7541
|
}
|
|
@@ -6792,21 +7552,21 @@ var CssRenderer = class _CssRenderer {
|
|
|
6792
7552
|
);
|
|
6793
7553
|
}
|
|
6794
7554
|
if (hasMediaQuery) {
|
|
6795
|
-
lines.push(`${
|
|
7555
|
+
lines.push(`${indent2}}${newline}`);
|
|
6796
7556
|
}
|
|
6797
7557
|
lines.push(`}${newline}${newline}`);
|
|
6798
7558
|
}
|
|
6799
|
-
pushTokenLines(lines, token, tokens, referenceTokens, preserveReferences,
|
|
7559
|
+
pushTokenLines(lines, token, tokens, referenceTokens, preserveReferences, indent2, newline, space) {
|
|
6800
7560
|
const entries = this.buildCssEntries(token, tokens, referenceTokens, preserveReferences);
|
|
6801
7561
|
if (token.$deprecated != null && token.$deprecated !== false) {
|
|
6802
7562
|
const deprecationMsg = formatDeprecationMessage(token, "", "comment");
|
|
6803
|
-
lines.push(`${
|
|
7563
|
+
lines.push(`${indent2}/* ${this.sanitizeCssCommentText(deprecationMsg)} */${newline}`);
|
|
6804
7564
|
}
|
|
6805
7565
|
if (token.$description && token.$description !== "") {
|
|
6806
|
-
lines.push(`${
|
|
7566
|
+
lines.push(`${indent2}/* ${this.sanitizeCssCommentText(token.$description)} */${newline}`);
|
|
6807
7567
|
}
|
|
6808
7568
|
for (const entry of entries) {
|
|
6809
|
-
lines.push(`${
|
|
7569
|
+
lines.push(`${indent2}--${entry.name}:${space}${entry.value};${newline}`);
|
|
6810
7570
|
}
|
|
6811
7571
|
}
|
|
6812
7572
|
async formatWithPrettier(css2) {
|
|
@@ -7381,18 +8141,641 @@ var CssRenderer = class _CssRenderer {
|
|
|
7381
8141
|
return { modifierName: name, modifierContext: value };
|
|
7382
8142
|
}
|
|
7383
8143
|
}
|
|
7384
|
-
return { modifierName: "", modifierContext: "" };
|
|
7385
|
-
}
|
|
7386
|
-
isBasePermutation(modifierInputs, defaults) {
|
|
7387
|
-
const normalizedInputs = normalizeModifierInputs(modifierInputs);
|
|
7388
|
-
const normalizedDefaults = normalizeModifierInputs(defaults);
|
|
7389
|
-
return Object.entries(normalizedDefaults).every(
|
|
7390
|
-
([key, value]) => normalizedInputs[key] === value
|
|
7391
|
-
);
|
|
8144
|
+
return { modifierName: "", modifierContext: "" };
|
|
8145
|
+
}
|
|
8146
|
+
isBasePermutation(modifierInputs, defaults) {
|
|
8147
|
+
const normalizedInputs = normalizeModifierInputs(modifierInputs);
|
|
8148
|
+
const normalizedDefaults = normalizeModifierInputs(defaults);
|
|
8149
|
+
return Object.entries(normalizedDefaults).every(
|
|
8150
|
+
([key, value]) => normalizedInputs[key] === value
|
|
8151
|
+
);
|
|
8152
|
+
}
|
|
8153
|
+
};
|
|
8154
|
+
function cssRenderer() {
|
|
8155
|
+
const rendererInstance = new CssRenderer();
|
|
8156
|
+
return {
|
|
8157
|
+
format: (context, options) => rendererInstance.format(
|
|
8158
|
+
context,
|
|
8159
|
+
options ?? context.output.options
|
|
8160
|
+
)
|
|
8161
|
+
};
|
|
8162
|
+
}
|
|
8163
|
+
|
|
8164
|
+
// src/renderers/ios.ts
|
|
8165
|
+
init_errors();
|
|
8166
|
+
init_token_utils();
|
|
8167
|
+
init_utils();
|
|
8168
|
+
var toSRGB2 = converter("rgb");
|
|
8169
|
+
var toP32 = converter("p3");
|
|
8170
|
+
var SWIFT_TYPE_GROUP_MAP = {
|
|
8171
|
+
color: "Colors",
|
|
8172
|
+
dimension: "Spacing",
|
|
8173
|
+
fontFamily: "Fonts",
|
|
8174
|
+
fontWeight: "FontWeights",
|
|
8175
|
+
duration: "Durations",
|
|
8176
|
+
shadow: "Shadows",
|
|
8177
|
+
typography: "Typography",
|
|
8178
|
+
number: "Numbers",
|
|
8179
|
+
cubicBezier: "Animations",
|
|
8180
|
+
border: "Borders",
|
|
8181
|
+
gradient: "Gradients"
|
|
8182
|
+
};
|
|
8183
|
+
var SWIFT_KEYWORDS = /* @__PURE__ */ new Set([
|
|
8184
|
+
"associatedtype",
|
|
8185
|
+
"class",
|
|
8186
|
+
"deinit",
|
|
8187
|
+
"enum",
|
|
8188
|
+
"extension",
|
|
8189
|
+
"fileprivate",
|
|
8190
|
+
"func",
|
|
8191
|
+
"import",
|
|
8192
|
+
"init",
|
|
8193
|
+
"inout",
|
|
8194
|
+
"internal",
|
|
8195
|
+
"let",
|
|
8196
|
+
"open",
|
|
8197
|
+
"operator",
|
|
8198
|
+
"private",
|
|
8199
|
+
"protocol",
|
|
8200
|
+
"public",
|
|
8201
|
+
"rethrows",
|
|
8202
|
+
"static",
|
|
8203
|
+
"struct",
|
|
8204
|
+
"subscript",
|
|
8205
|
+
"typealias",
|
|
8206
|
+
"var",
|
|
8207
|
+
"break",
|
|
8208
|
+
"case",
|
|
8209
|
+
"continue",
|
|
8210
|
+
"default",
|
|
8211
|
+
"defer",
|
|
8212
|
+
"do",
|
|
8213
|
+
"else",
|
|
8214
|
+
"fallthrough",
|
|
8215
|
+
"for",
|
|
8216
|
+
"guard",
|
|
8217
|
+
"if",
|
|
8218
|
+
"in",
|
|
8219
|
+
"repeat",
|
|
8220
|
+
"return",
|
|
8221
|
+
"switch",
|
|
8222
|
+
"where",
|
|
8223
|
+
"while",
|
|
8224
|
+
"as",
|
|
8225
|
+
"catch",
|
|
8226
|
+
"false",
|
|
8227
|
+
"is",
|
|
8228
|
+
"nil",
|
|
8229
|
+
"super",
|
|
8230
|
+
"self",
|
|
8231
|
+
"Self",
|
|
8232
|
+
"throw",
|
|
8233
|
+
"throws",
|
|
8234
|
+
"true",
|
|
8235
|
+
"try",
|
|
8236
|
+
"Type",
|
|
8237
|
+
"Protocol"
|
|
8238
|
+
]);
|
|
8239
|
+
var IosRenderer = class {
|
|
8240
|
+
async format(context, options) {
|
|
8241
|
+
const opts = {
|
|
8242
|
+
preset: options?.preset ?? "standalone",
|
|
8243
|
+
accessLevel: options?.accessLevel ?? "public",
|
|
8244
|
+
structure: options?.structure ?? "enum",
|
|
8245
|
+
enumName: options?.enumName ?? "DesignTokens",
|
|
8246
|
+
extensionNamespace: options?.extensionNamespace ?? "DesignTokens",
|
|
8247
|
+
colorSpace: options?.colorSpace ?? "sRGB",
|
|
8248
|
+
swiftVersion: options?.swiftVersion ?? "5.9",
|
|
8249
|
+
indent: options?.indent ?? 4,
|
|
8250
|
+
frozen: options?.frozen ?? false
|
|
8251
|
+
};
|
|
8252
|
+
return await this.formatStandalone(context, opts);
|
|
8253
|
+
}
|
|
8254
|
+
formatTokens(tokens, options) {
|
|
8255
|
+
if (options.structure === "grouped") {
|
|
8256
|
+
return this.formatAsGrouped(tokens, options);
|
|
8257
|
+
}
|
|
8258
|
+
return this.formatAsEnum(tokens, options);
|
|
8259
|
+
}
|
|
8260
|
+
formatAsEnum(tokens, options) {
|
|
8261
|
+
const access3 = options.accessLevel;
|
|
8262
|
+
const groups = this.groupTokensByType(tokens);
|
|
8263
|
+
const imports = this.collectImports(tokens);
|
|
8264
|
+
const i1 = this.indentStr(options.indent, 1);
|
|
8265
|
+
const i2 = this.indentStr(options.indent, 2);
|
|
8266
|
+
const staticPrefix = this.staticLetPrefix(options);
|
|
8267
|
+
const frozen = this.frozenPrefix(options);
|
|
8268
|
+
const lines = [];
|
|
8269
|
+
lines.push(this.buildFileHeader());
|
|
8270
|
+
lines.push("");
|
|
8271
|
+
for (const imp of imports) {
|
|
8272
|
+
lines.push(`import ${imp}`);
|
|
8273
|
+
}
|
|
8274
|
+
lines.push(...this.buildStructDefinitions(tokens, access3, options));
|
|
8275
|
+
lines.push("");
|
|
8276
|
+
lines.push(`${frozen}${access3} enum ${options.enumName} {`);
|
|
8277
|
+
for (const group of groups) {
|
|
8278
|
+
lines.push(`${i1}${frozen}${access3} enum ${group.name} {`);
|
|
8279
|
+
for (const token of group.tokens) {
|
|
8280
|
+
const swiftName = this.buildQualifiedSwiftName(token);
|
|
8281
|
+
const swiftValue = this.formatSwiftValue(token, options);
|
|
8282
|
+
const typeAnnotation = this.getTypeAnnotation(token);
|
|
8283
|
+
const annotation = typeAnnotation ? `: ${typeAnnotation}` : "";
|
|
8284
|
+
const docComment = this.buildDocComment(token, i2);
|
|
8285
|
+
if (docComment) {
|
|
8286
|
+
lines.push(docComment);
|
|
8287
|
+
}
|
|
8288
|
+
lines.push(`${i2}${access3} ${staticPrefix}${swiftName}${annotation} = ${swiftValue}`);
|
|
8289
|
+
}
|
|
8290
|
+
lines.push(`${i1}}`);
|
|
8291
|
+
lines.push("");
|
|
8292
|
+
}
|
|
8293
|
+
lines.push("}");
|
|
8294
|
+
lines.push(...this.buildViewExtensions(tokens, access3, options));
|
|
8295
|
+
lines.push("");
|
|
8296
|
+
return lines.join("\n");
|
|
8297
|
+
}
|
|
8298
|
+
formatAsGrouped(tokens, options) {
|
|
8299
|
+
const access3 = options.accessLevel;
|
|
8300
|
+
const namespace = options.extensionNamespace;
|
|
8301
|
+
const groups = this.groupTokensByType(tokens);
|
|
8302
|
+
const imports = this.collectImports(tokens);
|
|
8303
|
+
const i1 = this.indentStr(options.indent, 1);
|
|
8304
|
+
const i2 = this.indentStr(options.indent, 2);
|
|
8305
|
+
const staticPrefix = this.staticLetPrefix(options);
|
|
8306
|
+
const frozen = this.frozenPrefix(options);
|
|
8307
|
+
const lines = [];
|
|
8308
|
+
lines.push(this.buildFileHeader());
|
|
8309
|
+
lines.push("");
|
|
8310
|
+
for (const imp of imports) {
|
|
8311
|
+
lines.push(`import ${imp}`);
|
|
8312
|
+
}
|
|
8313
|
+
lines.push(...this.buildStructDefinitions(tokens, access3, options));
|
|
8314
|
+
lines.push("");
|
|
8315
|
+
lines.push(`${frozen}${access3} enum ${namespace} {}`);
|
|
8316
|
+
lines.push("");
|
|
8317
|
+
for (const group of groups) {
|
|
8318
|
+
lines.push(`${access3} extension ${namespace} {`);
|
|
8319
|
+
lines.push(`${i1}${frozen}enum ${group.name} {`);
|
|
8320
|
+
for (const token of group.tokens) {
|
|
8321
|
+
const swiftName = this.buildQualifiedSwiftName(token);
|
|
8322
|
+
const swiftValue = this.formatSwiftValue(token, options);
|
|
8323
|
+
const typeAnnotation = this.getTypeAnnotation(token);
|
|
8324
|
+
const annotation = typeAnnotation ? `: ${typeAnnotation}` : "";
|
|
8325
|
+
const docComment = this.buildDocComment(token, i2);
|
|
8326
|
+
if (docComment) {
|
|
8327
|
+
lines.push(docComment);
|
|
8328
|
+
}
|
|
8329
|
+
lines.push(`${i2}${access3} ${staticPrefix}${swiftName}${annotation} = ${swiftValue}`);
|
|
8330
|
+
}
|
|
8331
|
+
lines.push(`${i1}}`);
|
|
8332
|
+
lines.push("}");
|
|
8333
|
+
lines.push("");
|
|
8334
|
+
}
|
|
8335
|
+
lines.push(...this.buildViewExtensions(tokens, access3, options));
|
|
8336
|
+
return lines.join("\n");
|
|
8337
|
+
}
|
|
8338
|
+
buildFileHeader() {
|
|
8339
|
+
return [
|
|
8340
|
+
"// Generated by Dispersa - do not edit manually",
|
|
8341
|
+
"// https://github.com/timges/dispersa"
|
|
8342
|
+
].join("\n");
|
|
8343
|
+
}
|
|
8344
|
+
collectImports(tokens) {
|
|
8345
|
+
const imports = /* @__PURE__ */ new Set();
|
|
8346
|
+
imports.add("SwiftUI");
|
|
8347
|
+
for (const [, token] of Object.entries(tokens)) {
|
|
8348
|
+
if (token.$type === "duration") {
|
|
8349
|
+
imports.add("Foundation");
|
|
8350
|
+
}
|
|
8351
|
+
}
|
|
8352
|
+
return Array.from(imports).sort();
|
|
8353
|
+
}
|
|
8354
|
+
/**
|
|
8355
|
+
* Builds a `///` doc comment from a token's `$description`, if present.
|
|
8356
|
+
*/
|
|
8357
|
+
buildDocComment(token, indent2) {
|
|
8358
|
+
if (!token.$description) {
|
|
8359
|
+
return void 0;
|
|
8360
|
+
}
|
|
8361
|
+
return `${indent2}/// ${token.$description}`;
|
|
8362
|
+
}
|
|
8363
|
+
groupTokensByType(tokens) {
|
|
8364
|
+
const groupMap = /* @__PURE__ */ new Map();
|
|
8365
|
+
for (const [, token] of getSortedTokenEntries(tokens)) {
|
|
8366
|
+
const groupName = SWIFT_TYPE_GROUP_MAP[token.$type ?? ""] ?? "Other";
|
|
8367
|
+
const existing = groupMap.get(groupName) ?? [];
|
|
8368
|
+
existing.push(token);
|
|
8369
|
+
groupMap.set(groupName, existing);
|
|
8370
|
+
}
|
|
8371
|
+
return Array.from(groupMap.entries()).map(([name, groupTokens]) => ({
|
|
8372
|
+
name,
|
|
8373
|
+
tokens: groupTokens
|
|
8374
|
+
}));
|
|
8375
|
+
}
|
|
8376
|
+
/**
|
|
8377
|
+
* Builds a qualified Swift name from a token's path, preserving parent
|
|
8378
|
+
* hierarchy segments to avoid duplicate identifiers.
|
|
8379
|
+
*
|
|
8380
|
+
* For example, `color.blue.400` in the `Colors` group becomes `blue400`
|
|
8381
|
+
* instead of just `_400`.
|
|
8382
|
+
*/
|
|
8383
|
+
buildQualifiedSwiftName(token) {
|
|
8384
|
+
const path7 = token.path;
|
|
8385
|
+
const withoutTypePrefix = path7.length > 1 ? path7.slice(1) : path7;
|
|
8386
|
+
const joined = withoutTypePrefix.join("_");
|
|
8387
|
+
return this.toSwiftIdentifier(joined);
|
|
8388
|
+
}
|
|
8389
|
+
formatSwiftValue(token, options) {
|
|
8390
|
+
const value = token.$value;
|
|
8391
|
+
if (token.$type === "color") {
|
|
8392
|
+
return this.formatColorValue(value, options);
|
|
8393
|
+
}
|
|
8394
|
+
if (token.$type === "dimension") {
|
|
8395
|
+
return this.formatDimensionValue(value);
|
|
8396
|
+
}
|
|
8397
|
+
if (token.$type === "fontFamily") {
|
|
8398
|
+
return this.formatFontFamilyValue(value);
|
|
8399
|
+
}
|
|
8400
|
+
if (token.$type === "fontWeight") {
|
|
8401
|
+
return this.formatFontWeightValue(value);
|
|
8402
|
+
}
|
|
8403
|
+
if (token.$type === "duration") {
|
|
8404
|
+
return this.formatDurationValue(value);
|
|
8405
|
+
}
|
|
8406
|
+
if (token.$type === "shadow") {
|
|
8407
|
+
return this.formatShadowValue(value, options);
|
|
8408
|
+
}
|
|
8409
|
+
if (token.$type === "typography") {
|
|
8410
|
+
return this.formatTypographyValue(value);
|
|
8411
|
+
}
|
|
8412
|
+
if (token.$type === "border") {
|
|
8413
|
+
return this.formatBorderValue(value, options);
|
|
8414
|
+
}
|
|
8415
|
+
if (token.$type === "gradient") {
|
|
8416
|
+
return this.formatGradientValue(value, options);
|
|
8417
|
+
}
|
|
8418
|
+
if (token.$type === "number") {
|
|
8419
|
+
return String(value);
|
|
8420
|
+
}
|
|
8421
|
+
if (token.$type === "cubicBezier" && Array.isArray(value) && value.length === 4) {
|
|
8422
|
+
return `UnitCurve.bezier(startControlPoint: UnitPoint(x: ${value[0]}, y: ${value[1]}), endControlPoint: UnitPoint(x: ${value[2]}, y: ${value[3]}))`;
|
|
8423
|
+
}
|
|
8424
|
+
if (typeof value === "string") {
|
|
8425
|
+
return `"${this.escapeSwiftString(value)}"`;
|
|
8426
|
+
}
|
|
8427
|
+
if (typeof value === "number") {
|
|
8428
|
+
return String(value);
|
|
8429
|
+
}
|
|
8430
|
+
if (typeof value === "boolean") {
|
|
8431
|
+
return value ? "true" : "false";
|
|
8432
|
+
}
|
|
8433
|
+
return `"${this.escapeSwiftString(String(value))}"`;
|
|
8434
|
+
}
|
|
8435
|
+
formatColorValue(value, options) {
|
|
8436
|
+
if (!isColorObject(value)) {
|
|
8437
|
+
return typeof value === "string" ? `Color("${this.escapeSwiftString(value)}")` : "Color.clear";
|
|
8438
|
+
}
|
|
8439
|
+
const colorObj = value;
|
|
8440
|
+
const alpha = colorObj.alpha ?? 1;
|
|
8441
|
+
if (options.colorSpace === "displayP3") {
|
|
8442
|
+
const p3 = toP32(dtcgObjectToCulori(colorObj));
|
|
8443
|
+
const r2 = this.roundComponent(p3?.r ?? 0);
|
|
8444
|
+
const g2 = this.roundComponent(p3?.g ?? 0);
|
|
8445
|
+
const b2 = this.roundComponent(p3?.b ?? 0);
|
|
8446
|
+
return alpha < 1 ? `Color(.displayP3, red: ${r2}, green: ${g2}, blue: ${b2}, opacity: ${this.roundComponent(alpha)})` : `Color(.displayP3, red: ${r2}, green: ${g2}, blue: ${b2})`;
|
|
8447
|
+
}
|
|
8448
|
+
const rgb = toSRGB2(dtcgObjectToCulori(colorObj));
|
|
8449
|
+
const r = this.roundComponent(rgb?.r ?? 0);
|
|
8450
|
+
const g = this.roundComponent(rgb?.g ?? 0);
|
|
8451
|
+
const b = this.roundComponent(rgb?.b ?? 0);
|
|
8452
|
+
return alpha < 1 ? `Color(red: ${r}, green: ${g}, blue: ${b}, opacity: ${this.roundComponent(alpha)})` : `Color(red: ${r}, green: ${g}, blue: ${b})`;
|
|
8453
|
+
}
|
|
8454
|
+
formatDimensionValue(value) {
|
|
8455
|
+
if (isDimensionObject(value)) {
|
|
8456
|
+
const dim = value;
|
|
8457
|
+
const ptValue = dim.unit === "rem" ? dim.value * 16 : dim.value;
|
|
8458
|
+
return String(ptValue);
|
|
8459
|
+
}
|
|
8460
|
+
return String(value);
|
|
8461
|
+
}
|
|
8462
|
+
formatFontFamilyValue(value) {
|
|
8463
|
+
if (Array.isArray(value)) {
|
|
8464
|
+
const primary = value[0];
|
|
8465
|
+
return typeof primary === "string" ? `"${this.escapeSwiftString(primary)}"` : '"system"';
|
|
8466
|
+
}
|
|
8467
|
+
return typeof value === "string" ? `"${this.escapeSwiftString(value)}"` : '"system"';
|
|
8468
|
+
}
|
|
8469
|
+
formatFontWeightValue(value) {
|
|
8470
|
+
if (typeof value === "number") {
|
|
8471
|
+
return this.numericFontWeight(value);
|
|
8472
|
+
}
|
|
8473
|
+
if (typeof value === "string") {
|
|
8474
|
+
return this.namedFontWeight(value) ?? "Font.Weight.regular";
|
|
8475
|
+
}
|
|
8476
|
+
return "Font.Weight.regular";
|
|
8477
|
+
}
|
|
8478
|
+
numericFontWeight(weight) {
|
|
8479
|
+
if (weight <= 100) {
|
|
8480
|
+
return "Font.Weight.ultraLight";
|
|
8481
|
+
}
|
|
8482
|
+
if (weight <= 200) {
|
|
8483
|
+
return "Font.Weight.thin";
|
|
8484
|
+
}
|
|
8485
|
+
if (weight <= 300) {
|
|
8486
|
+
return "Font.Weight.light";
|
|
8487
|
+
}
|
|
8488
|
+
if (weight <= 400) {
|
|
8489
|
+
return "Font.Weight.regular";
|
|
8490
|
+
}
|
|
8491
|
+
if (weight <= 500) {
|
|
8492
|
+
return "Font.Weight.medium";
|
|
8493
|
+
}
|
|
8494
|
+
if (weight <= 600) {
|
|
8495
|
+
return "Font.Weight.semibold";
|
|
8496
|
+
}
|
|
8497
|
+
if (weight <= 700) {
|
|
8498
|
+
return "Font.Weight.bold";
|
|
8499
|
+
}
|
|
8500
|
+
if (weight <= 800) {
|
|
8501
|
+
return "Font.Weight.heavy";
|
|
8502
|
+
}
|
|
8503
|
+
return "Font.Weight.black";
|
|
8504
|
+
}
|
|
8505
|
+
namedFontWeight(name) {
|
|
8506
|
+
const map = {
|
|
8507
|
+
thin: "Font.Weight.thin",
|
|
8508
|
+
ultralight: "Font.Weight.ultraLight",
|
|
8509
|
+
extralight: "Font.Weight.ultraLight",
|
|
8510
|
+
light: "Font.Weight.light",
|
|
8511
|
+
regular: "Font.Weight.regular",
|
|
8512
|
+
normal: "Font.Weight.regular",
|
|
8513
|
+
medium: "Font.Weight.medium",
|
|
8514
|
+
semibold: "Font.Weight.semibold",
|
|
8515
|
+
demibold: "Font.Weight.semibold",
|
|
8516
|
+
bold: "Font.Weight.bold",
|
|
8517
|
+
heavy: "Font.Weight.heavy",
|
|
8518
|
+
extrabold: "Font.Weight.heavy",
|
|
8519
|
+
black: "Font.Weight.black",
|
|
8520
|
+
ultrabold: "Font.Weight.black"
|
|
8521
|
+
};
|
|
8522
|
+
return map[name.toLowerCase()];
|
|
8523
|
+
}
|
|
8524
|
+
formatDurationValue(value) {
|
|
8525
|
+
if (typeof value === "object" && value !== null && "value" in value && "unit" in value) {
|
|
8526
|
+
const dur = value;
|
|
8527
|
+
const seconds = dur.unit === "ms" ? dur.value / 1e3 : dur.value;
|
|
8528
|
+
return String(seconds);
|
|
8529
|
+
}
|
|
8530
|
+
return typeof value === "number" ? String(value) : "0";
|
|
8531
|
+
}
|
|
8532
|
+
formatShadowValue(value, options) {
|
|
8533
|
+
if (Array.isArray(value) && value.length > 0) {
|
|
8534
|
+
return this.formatSingleShadow(value[0], options);
|
|
8535
|
+
}
|
|
8536
|
+
if (typeof value === "object" && value !== null) {
|
|
8537
|
+
return this.formatSingleShadow(value, options);
|
|
8538
|
+
}
|
|
8539
|
+
return "ShadowStyle(color: .clear, radius: 0, x: 0, y: 0, spread: 0)";
|
|
8540
|
+
}
|
|
8541
|
+
formatSingleShadow(shadow, options) {
|
|
8542
|
+
const color = isColorObject(shadow.color) ? this.formatColorValue(shadow.color, options) : "Color.black.opacity(0.25)";
|
|
8543
|
+
const radius = isDimensionObject(shadow.blur) ? this.dimensionToCGFloat(shadow.blur) : "8";
|
|
8544
|
+
const x = isDimensionObject(shadow.offsetX) ? this.dimensionToCGFloat(shadow.offsetX) : "0";
|
|
8545
|
+
const y = isDimensionObject(shadow.offsetY) ? this.dimensionToCGFloat(shadow.offsetY) : "0";
|
|
8546
|
+
const spread = isDimensionObject(shadow.spread) ? this.dimensionToCGFloat(shadow.spread) : "0";
|
|
8547
|
+
return `ShadowStyle(color: ${color}, radius: ${radius}, x: ${x}, y: ${y}, spread: ${spread})`;
|
|
8548
|
+
}
|
|
8549
|
+
formatTypographyValue(value) {
|
|
8550
|
+
if (typeof value !== "object" || value === null) {
|
|
8551
|
+
return "TypographyStyle(font: Font.body, tracking: 0, lineSpacing: 0)";
|
|
8552
|
+
}
|
|
8553
|
+
const typo = value;
|
|
8554
|
+
const size = isDimensionObject(typo.fontSize) ? this.dimensionToPoints(typo.fontSize) : "16";
|
|
8555
|
+
const weight = typo.fontWeight != null ? this.formatFontWeightValue(typo.fontWeight) : "Font.Weight.regular";
|
|
8556
|
+
const fontExpr = this.buildFontExpression(typo, size, weight);
|
|
8557
|
+
const tracking = this.extractTracking(typo);
|
|
8558
|
+
const lineSpacing = this.extractLineSpacing(typo);
|
|
8559
|
+
return `TypographyStyle(font: ${fontExpr}, tracking: ${tracking}, lineSpacing: ${lineSpacing})`;
|
|
8560
|
+
}
|
|
8561
|
+
buildFontExpression(typo, size, weight) {
|
|
8562
|
+
if (typo.fontFamily != null) {
|
|
8563
|
+
const family = Array.isArray(typo.fontFamily) ? typo.fontFamily[0] : typo.fontFamily;
|
|
8564
|
+
if (typeof family === "string") {
|
|
8565
|
+
return `Font.custom("${this.escapeSwiftString(family)}", size: ${size}).weight(${weight})`;
|
|
8566
|
+
}
|
|
8567
|
+
}
|
|
8568
|
+
return `Font.system(size: ${size}, weight: ${weight})`;
|
|
8569
|
+
}
|
|
8570
|
+
extractTracking(typo) {
|
|
8571
|
+
if (!isDimensionObject(typo.letterSpacing)) {
|
|
8572
|
+
return "0";
|
|
8573
|
+
}
|
|
8574
|
+
const dim = typo.letterSpacing;
|
|
8575
|
+
const ptValue = dim.unit === "rem" ? dim.value * 16 : dim.value;
|
|
8576
|
+
return String(ptValue);
|
|
8577
|
+
}
|
|
8578
|
+
extractLineSpacing(typo) {
|
|
8579
|
+
if (typo.lineHeight == null || typeof typo.lineHeight !== "number") {
|
|
8580
|
+
return "0";
|
|
8581
|
+
}
|
|
8582
|
+
if (!isDimensionObject(typo.fontSize)) {
|
|
8583
|
+
return "0";
|
|
8584
|
+
}
|
|
8585
|
+
const dim = typo.fontSize;
|
|
8586
|
+
const basePt = dim.unit === "rem" ? dim.value * 16 : dim.value;
|
|
8587
|
+
const lineHeightPt = Math.round(basePt * typo.lineHeight * 100) / 100;
|
|
8588
|
+
return String(lineHeightPt - basePt);
|
|
8589
|
+
}
|
|
8590
|
+
dimensionToPoints(dim) {
|
|
8591
|
+
const ptValue = dim.unit === "rem" ? dim.value * 16 : dim.value;
|
|
8592
|
+
return String(ptValue);
|
|
8593
|
+
}
|
|
8594
|
+
/** Formats a dimension as a CGFloat literal (appends `.0` for integers). */
|
|
8595
|
+
dimensionToCGFloat(dim) {
|
|
8596
|
+
const ptValue = dim.unit === "rem" ? dim.value * 16 : dim.value;
|
|
8597
|
+
return Number.isInteger(ptValue) ? `${ptValue}.0` : String(ptValue);
|
|
8598
|
+
}
|
|
8599
|
+
getTypeAnnotation(token) {
|
|
8600
|
+
switch (token.$type) {
|
|
8601
|
+
case "dimension":
|
|
8602
|
+
return "CGFloat";
|
|
8603
|
+
case "duration":
|
|
8604
|
+
return "TimeInterval";
|
|
8605
|
+
case "number":
|
|
8606
|
+
return "Double";
|
|
8607
|
+
case "fontWeight":
|
|
8608
|
+
return "Font.Weight";
|
|
8609
|
+
case "fontFamily":
|
|
8610
|
+
return "String";
|
|
8611
|
+
default:
|
|
8612
|
+
return void 0;
|
|
8613
|
+
}
|
|
8614
|
+
}
|
|
8615
|
+
toSwiftIdentifier(name) {
|
|
8616
|
+
const camel = name.replace(/[-._]+(.)/g, (_, c) => c.toUpperCase()).replace(/[-._]+$/g, "").replace(/^[-._]+/g, "");
|
|
8617
|
+
const identifier = camel.charAt(0).toLowerCase() + camel.slice(1);
|
|
8618
|
+
const safe = /^\d/.test(identifier) ? `_${identifier}` : identifier;
|
|
8619
|
+
return SWIFT_KEYWORDS.has(safe) ? `\`${safe}\`` : safe;
|
|
8620
|
+
}
|
|
8621
|
+
escapeSwiftString(str) {
|
|
8622
|
+
return str.replace(/\\/g, "\\\\").replace(/"/g, '\\"').replace(/\n/g, "\\n");
|
|
8623
|
+
}
|
|
8624
|
+
roundComponent(value) {
|
|
8625
|
+
return Math.round(value * 1e4) / 1e4;
|
|
8626
|
+
}
|
|
8627
|
+
indentStr(width, level) {
|
|
8628
|
+
return " ".repeat(width * level);
|
|
8629
|
+
}
|
|
8630
|
+
/**
|
|
8631
|
+
* Returns the prefix for `static let` declarations.
|
|
8632
|
+
* Swift 6 requires `nonisolated(unsafe)` on global stored properties.
|
|
8633
|
+
*/
|
|
8634
|
+
staticLetPrefix(options) {
|
|
8635
|
+
return options.swiftVersion === "6.0" ? "nonisolated(unsafe) static let " : "static let ";
|
|
8636
|
+
}
|
|
8637
|
+
/** Returns `@frozen ` when the frozen option is enabled, empty string otherwise. */
|
|
8638
|
+
frozenPrefix(options) {
|
|
8639
|
+
return options.frozen ? "@frozen " : "";
|
|
8640
|
+
}
|
|
8641
|
+
/** Returns `: Sendable` when targeting Swift 6, empty string otherwise. */
|
|
8642
|
+
structConformances(options) {
|
|
8643
|
+
return options.swiftVersion === "6.0" ? ": Sendable" : "";
|
|
8644
|
+
}
|
|
8645
|
+
hasShadowTokens(tokens) {
|
|
8646
|
+
return Object.values(tokens).some((t) => t.$type === "shadow");
|
|
8647
|
+
}
|
|
8648
|
+
hasTypographyTokens(tokens) {
|
|
8649
|
+
return Object.values(tokens).some((t) => t.$type === "typography");
|
|
8650
|
+
}
|
|
8651
|
+
hasBorderTokens(tokens) {
|
|
8652
|
+
return Object.values(tokens).some((t) => t.$type === "border");
|
|
8653
|
+
}
|
|
8654
|
+
/** Emits all struct definitions needed by the token set. */
|
|
8655
|
+
buildStructDefinitions(tokens, access3, options) {
|
|
8656
|
+
const lines = [];
|
|
8657
|
+
if (this.hasShadowTokens(tokens)) {
|
|
8658
|
+
lines.push("");
|
|
8659
|
+
lines.push(...this.buildShadowStyleStruct(access3, options));
|
|
8660
|
+
}
|
|
8661
|
+
if (this.hasTypographyTokens(tokens)) {
|
|
8662
|
+
lines.push("");
|
|
8663
|
+
lines.push(...this.buildTypographyStyleStruct(access3, options));
|
|
8664
|
+
}
|
|
8665
|
+
if (this.hasBorderTokens(tokens)) {
|
|
8666
|
+
lines.push("");
|
|
8667
|
+
lines.push(...this.buildBorderStyleStruct(access3, options));
|
|
8668
|
+
}
|
|
8669
|
+
return lines;
|
|
8670
|
+
}
|
|
8671
|
+
buildShadowStyleStruct(access3, options) {
|
|
8672
|
+
const i1 = this.indentStr(options.indent, 1);
|
|
8673
|
+
const conformances = this.structConformances(options);
|
|
8674
|
+
const frozen = this.frozenPrefix(options);
|
|
8675
|
+
return [
|
|
8676
|
+
`${frozen}${access3} struct ShadowStyle${conformances} {`,
|
|
8677
|
+
`${i1}${access3} let color: Color`,
|
|
8678
|
+
`${i1}${access3} let radius: CGFloat`,
|
|
8679
|
+
`${i1}${access3} let x: CGFloat`,
|
|
8680
|
+
`${i1}${access3} let y: CGFloat`,
|
|
8681
|
+
`${i1}${access3} let spread: CGFloat`,
|
|
8682
|
+
"}"
|
|
8683
|
+
];
|
|
8684
|
+
}
|
|
8685
|
+
buildTypographyStyleStruct(access3, options) {
|
|
8686
|
+
const i1 = this.indentStr(options.indent, 1);
|
|
8687
|
+
const conformances = this.structConformances(options);
|
|
8688
|
+
const frozen = this.frozenPrefix(options);
|
|
8689
|
+
return [
|
|
8690
|
+
`${frozen}${access3} struct TypographyStyle${conformances} {`,
|
|
8691
|
+
`${i1}${access3} let font: Font`,
|
|
8692
|
+
`${i1}${access3} let tracking: CGFloat`,
|
|
8693
|
+
`${i1}${access3} let lineSpacing: CGFloat`,
|
|
8694
|
+
"}"
|
|
8695
|
+
];
|
|
8696
|
+
}
|
|
8697
|
+
buildBorderStyleStruct(access3, options) {
|
|
8698
|
+
const i1 = this.indentStr(options.indent, 1);
|
|
8699
|
+
const conformances = this.structConformances(options);
|
|
8700
|
+
const frozen = this.frozenPrefix(options);
|
|
8701
|
+
return [
|
|
8702
|
+
`${frozen}${access3} struct BorderStyle${conformances} {`,
|
|
8703
|
+
`${i1}${access3} let color: Color`,
|
|
8704
|
+
`${i1}${access3} let width: CGFloat`,
|
|
8705
|
+
"}"
|
|
8706
|
+
];
|
|
8707
|
+
}
|
|
8708
|
+
/** Emits convenience View extensions for shadow and typography application. */
|
|
8709
|
+
buildViewExtensions(tokens, access3, options) {
|
|
8710
|
+
const lines = [];
|
|
8711
|
+
const i1 = this.indentStr(options.indent, 1);
|
|
8712
|
+
const i2 = this.indentStr(options.indent, 2);
|
|
8713
|
+
if (this.hasShadowTokens(tokens)) {
|
|
8714
|
+
lines.push("");
|
|
8715
|
+
lines.push(`${access3} extension View {`);
|
|
8716
|
+
lines.push(`${i1}func shadowStyle(_ style: ShadowStyle) -> some View {`);
|
|
8717
|
+
lines.push(
|
|
8718
|
+
`${i2}self.shadow(color: style.color, radius: style.radius, x: style.x, y: style.y)`
|
|
8719
|
+
);
|
|
8720
|
+
lines.push(`${i1}}`);
|
|
8721
|
+
lines.push("}");
|
|
8722
|
+
}
|
|
8723
|
+
if (this.hasTypographyTokens(tokens)) {
|
|
8724
|
+
lines.push("");
|
|
8725
|
+
lines.push(`${access3} extension View {`);
|
|
8726
|
+
lines.push(`${i1}func typographyStyle(_ style: TypographyStyle) -> some View {`);
|
|
8727
|
+
lines.push(
|
|
8728
|
+
`${i2}self.font(style.font).tracking(style.tracking).lineSpacing(style.lineSpacing)`
|
|
8729
|
+
);
|
|
8730
|
+
lines.push(`${i1}}`);
|
|
8731
|
+
lines.push("}");
|
|
8732
|
+
}
|
|
8733
|
+
return lines;
|
|
8734
|
+
}
|
|
8735
|
+
formatBorderValue(value, options) {
|
|
8736
|
+
if (typeof value !== "object" || value === null) {
|
|
8737
|
+
return "BorderStyle(color: .clear, width: 0)";
|
|
8738
|
+
}
|
|
8739
|
+
const border = value;
|
|
8740
|
+
const color = isColorObject(border.color) ? this.formatColorValue(border.color, options) : "Color.clear";
|
|
8741
|
+
const width = isDimensionObject(border.width) ? this.dimensionToCGFloat(border.width) : "1.0";
|
|
8742
|
+
return `BorderStyle(color: ${color}, width: ${width})`;
|
|
8743
|
+
}
|
|
8744
|
+
formatGradientValue(value, options) {
|
|
8745
|
+
if (!Array.isArray(value) || value.length === 0) {
|
|
8746
|
+
return "Gradient(stops: [])";
|
|
8747
|
+
}
|
|
8748
|
+
const stops = value.map((stop) => {
|
|
8749
|
+
const color = isColorObject(stop.color) ? this.formatColorValue(stop.color, options) : "Color.clear";
|
|
8750
|
+
return `.init(color: ${color}, location: ${stop.position})`;
|
|
8751
|
+
});
|
|
8752
|
+
return `Gradient(stops: [${stops.join(", ")}])`;
|
|
8753
|
+
}
|
|
8754
|
+
async formatStandalone(context, options) {
|
|
8755
|
+
const requiresFile = context.buildPath !== void 0 && context.buildPath !== "";
|
|
8756
|
+
if (!context.output.file && requiresFile) {
|
|
8757
|
+
throw new ConfigurationError(
|
|
8758
|
+
`Output "${context.output.name}": file is required for standalone iOS output`
|
|
8759
|
+
);
|
|
8760
|
+
}
|
|
8761
|
+
const files = {};
|
|
8762
|
+
for (const { tokens, modifierInputs } of context.permutations) {
|
|
8763
|
+
const processedTokens = stripInternalMetadata(tokens);
|
|
8764
|
+
const content = this.formatTokens(processedTokens, options);
|
|
8765
|
+
const fileName = context.output.file ? resolveFileName(context.output.file, modifierInputs) : buildInMemoryOutputKey({
|
|
8766
|
+
outputName: context.output.name,
|
|
8767
|
+
extension: "swift",
|
|
8768
|
+
modifierInputs,
|
|
8769
|
+
resolver: context.resolver,
|
|
8770
|
+
defaults: context.meta.defaults
|
|
8771
|
+
});
|
|
8772
|
+
files[fileName] = content;
|
|
8773
|
+
}
|
|
8774
|
+
return outputTree(files);
|
|
7392
8775
|
}
|
|
7393
8776
|
};
|
|
7394
|
-
function
|
|
7395
|
-
const rendererInstance = new
|
|
8777
|
+
function iosRenderer() {
|
|
8778
|
+
const rendererInstance = new IosRenderer();
|
|
7396
8779
|
return {
|
|
7397
8780
|
format: (context, options) => rendererInstance.format(
|
|
7398
8781
|
context,
|
|
@@ -7518,8 +8901,8 @@ var JsModuleRenderer = class {
|
|
|
7518
8901
|
/**
|
|
7519
8902
|
* Add object properties to lines
|
|
7520
8903
|
*/
|
|
7521
|
-
addObjectProperties(lines, obj,
|
|
7522
|
-
const indentStr = " ".repeat(
|
|
8904
|
+
addObjectProperties(lines, obj, indent2) {
|
|
8905
|
+
const indentStr = " ".repeat(indent2);
|
|
7523
8906
|
const entries = Object.entries(obj).sort(([keyA], [keyB]) => keyA.localeCompare(keyB));
|
|
7524
8907
|
for (let i = 0; i < entries.length; i++) {
|
|
7525
8908
|
const entry = entries[i];
|
|
@@ -7530,7 +8913,7 @@ var JsModuleRenderer = class {
|
|
|
7530
8913
|
const isLast = i === entries.length - 1;
|
|
7531
8914
|
if (typeof value === "object" && value !== null && !Array.isArray(value)) {
|
|
7532
8915
|
lines.push(`${indentStr}${this.quoteKey(key)}: {`);
|
|
7533
|
-
this.addObjectProperties(lines, value,
|
|
8916
|
+
this.addObjectProperties(lines, value, indent2 + 1);
|
|
7534
8917
|
lines.push(`${indentStr}}${isLast ? "" : ","}`);
|
|
7535
8918
|
} else {
|
|
7536
8919
|
const valueStr = JSON.stringify(value);
|
|
@@ -7722,6 +9105,349 @@ function jsonRenderer() {
|
|
|
7722
9105
|
};
|
|
7723
9106
|
}
|
|
7724
9107
|
|
|
9108
|
+
// src/renderers/tailwind.ts
|
|
9109
|
+
init_errors();
|
|
9110
|
+
init_token_utils();
|
|
9111
|
+
|
|
9112
|
+
// src/renderers/bundlers/tailwind.ts
|
|
9113
|
+
init_errors();
|
|
9114
|
+
init_utils();
|
|
9115
|
+
async function bundleAsTailwind(bundleData, options, formatThemeTokens, formatOverrideBlock) {
|
|
9116
|
+
const baseItem = bundleData.find((item) => item.isBase);
|
|
9117
|
+
if (!baseItem) {
|
|
9118
|
+
throw new BasePermutationError("Base permutation not found in bundle data");
|
|
9119
|
+
}
|
|
9120
|
+
const resolvedOpts = resolveOptions(options);
|
|
9121
|
+
const cssBlocks = [];
|
|
9122
|
+
const variantDeclarations = collectVariantDeclarations(bundleData, baseItem, resolvedOpts);
|
|
9123
|
+
const themeOpts = { ...resolvedOpts, variantDeclarations };
|
|
9124
|
+
const baseTokens = stripInternalMetadata(baseItem.tokens);
|
|
9125
|
+
const themeBlock = await formatThemeTokens(baseTokens, themeOpts);
|
|
9126
|
+
cssBlocks.push(themeBlock);
|
|
9127
|
+
for (const item of bundleData) {
|
|
9128
|
+
if (item.isBase) {
|
|
9129
|
+
continue;
|
|
9130
|
+
}
|
|
9131
|
+
const block = await formatModifierOverride(item, baseItem, resolvedOpts, formatOverrideBlock);
|
|
9132
|
+
if (block) {
|
|
9133
|
+
cssBlocks.push(block);
|
|
9134
|
+
}
|
|
9135
|
+
}
|
|
9136
|
+
return cssBlocks.join("\n");
|
|
9137
|
+
}
|
|
9138
|
+
async function formatModifierOverride({ tokens, modifierInputs }, baseItem, options, formatOverrideBlock) {
|
|
9139
|
+
const differenceCount = countModifierDifferences(modifierInputs, baseItem.modifierInputs);
|
|
9140
|
+
if (differenceCount > 1) {
|
|
9141
|
+
return void 0;
|
|
9142
|
+
}
|
|
9143
|
+
const tokensToInclude = filterTokensByValueChange(tokens, baseItem.tokens);
|
|
9144
|
+
if (Object.keys(tokensToInclude).length === 0) {
|
|
9145
|
+
return void 0;
|
|
9146
|
+
}
|
|
9147
|
+
const expectedSource = getExpectedSource(modifierInputs, baseItem.modifierInputs);
|
|
9148
|
+
const [modifier, context] = parseModifierSource(expectedSource);
|
|
9149
|
+
const cleanTokens = stripInternalMetadata(tokensToInclude);
|
|
9150
|
+
const selector = resolveSelector(
|
|
9151
|
+
options.selector,
|
|
9152
|
+
modifier,
|
|
9153
|
+
context,
|
|
9154
|
+
false,
|
|
9155
|
+
normalizeModifierInputs(modifierInputs)
|
|
9156
|
+
);
|
|
9157
|
+
const mediaQuery = resolveMediaQuery(
|
|
9158
|
+
options.mediaQuery,
|
|
9159
|
+
modifier,
|
|
9160
|
+
context,
|
|
9161
|
+
false,
|
|
9162
|
+
normalizeModifierInputs(modifierInputs)
|
|
9163
|
+
);
|
|
9164
|
+
const css2 = await formatOverrideBlock(cleanTokens, selector, mediaQuery, options.minify);
|
|
9165
|
+
return `/* Modifier: ${modifier}=${context} */
|
|
9166
|
+
${css2}`;
|
|
9167
|
+
}
|
|
9168
|
+
function filterTokensByValueChange(currentTokens, baseTokens) {
|
|
9169
|
+
const changed = {};
|
|
9170
|
+
for (const [name, token] of Object.entries(currentTokens)) {
|
|
9171
|
+
const baseToken = baseTokens[name];
|
|
9172
|
+
if (!baseToken) {
|
|
9173
|
+
changed[name] = token;
|
|
9174
|
+
continue;
|
|
9175
|
+
}
|
|
9176
|
+
if (JSON.stringify(token.$value) !== JSON.stringify(baseToken.$value)) {
|
|
9177
|
+
changed[name] = token;
|
|
9178
|
+
}
|
|
9179
|
+
}
|
|
9180
|
+
return changed;
|
|
9181
|
+
}
|
|
9182
|
+
function collectVariantDeclarations(bundleData, baseItem, options) {
|
|
9183
|
+
const declarations = [];
|
|
9184
|
+
for (const item of bundleData) {
|
|
9185
|
+
if (item.isBase) {
|
|
9186
|
+
continue;
|
|
9187
|
+
}
|
|
9188
|
+
const differenceCount = countModifierDifferences(item.modifierInputs, baseItem.modifierInputs);
|
|
9189
|
+
if (differenceCount > 1) {
|
|
9190
|
+
continue;
|
|
9191
|
+
}
|
|
9192
|
+
const expectedSource = getExpectedSource(item.modifierInputs, baseItem.modifierInputs);
|
|
9193
|
+
const [modifier, context] = parseModifierSource(expectedSource);
|
|
9194
|
+
const variantName = `${modifier}-${context}`;
|
|
9195
|
+
const normalized = normalizeModifierInputs(item.modifierInputs);
|
|
9196
|
+
const mediaQuery = resolveMediaQuery(options.mediaQuery, modifier, context, false, normalized);
|
|
9197
|
+
if (mediaQuery !== "") {
|
|
9198
|
+
declarations.push(`@custom-variant ${variantName} (@media ${mediaQuery});`);
|
|
9199
|
+
continue;
|
|
9200
|
+
}
|
|
9201
|
+
const selector = resolveSelector(options.selector, modifier, context, false, normalized);
|
|
9202
|
+
declarations.push(`@custom-variant ${variantName} (&:where(${selector}, ${selector} *));`);
|
|
9203
|
+
}
|
|
9204
|
+
return declarations;
|
|
9205
|
+
}
|
|
9206
|
+
function resolveOptions(options) {
|
|
9207
|
+
return {
|
|
9208
|
+
preset: options.preset ?? "bundle",
|
|
9209
|
+
includeImport: options.includeImport ?? true,
|
|
9210
|
+
namespace: options.namespace ?? "",
|
|
9211
|
+
minify: options.minify ?? false,
|
|
9212
|
+
selector: options.selector,
|
|
9213
|
+
mediaQuery: options.mediaQuery,
|
|
9214
|
+
variantDeclarations: []
|
|
9215
|
+
};
|
|
9216
|
+
}
|
|
9217
|
+
|
|
9218
|
+
// src/renderers/tailwind.ts
|
|
9219
|
+
init_utils();
|
|
9220
|
+
var TAILWIND_NAMESPACE_MAP = {
|
|
9221
|
+
color: "color",
|
|
9222
|
+
dimension: "spacing",
|
|
9223
|
+
fontFamily: "font",
|
|
9224
|
+
fontWeight: "font-weight",
|
|
9225
|
+
duration: "duration",
|
|
9226
|
+
shadow: "shadow",
|
|
9227
|
+
number: "number",
|
|
9228
|
+
cubicBezier: "ease"
|
|
9229
|
+
};
|
|
9230
|
+
var TailwindRenderer = class {
|
|
9231
|
+
async format(context, options) {
|
|
9232
|
+
const opts = {
|
|
9233
|
+
preset: options?.preset ?? "bundle",
|
|
9234
|
+
includeImport: options?.includeImport ?? true,
|
|
9235
|
+
namespace: options?.namespace ?? "",
|
|
9236
|
+
minify: options?.minify ?? false,
|
|
9237
|
+
selector: options?.selector,
|
|
9238
|
+
mediaQuery: options?.mediaQuery,
|
|
9239
|
+
variantDeclarations: []
|
|
9240
|
+
};
|
|
9241
|
+
if (opts.preset === "bundle") {
|
|
9242
|
+
return await this.formatBundle(context, opts);
|
|
9243
|
+
}
|
|
9244
|
+
return await this.formatStandalone(context, opts);
|
|
9245
|
+
}
|
|
9246
|
+
/**
|
|
9247
|
+
* Format tokens as Tailwind v4 @theme CSS variables
|
|
9248
|
+
*/
|
|
9249
|
+
async formatTokens(tokens, options) {
|
|
9250
|
+
const lines = [];
|
|
9251
|
+
const indent2 = options.minify ? "" : " ";
|
|
9252
|
+
const newline = options.minify ? "" : "\n";
|
|
9253
|
+
const space = options.minify ? "" : " ";
|
|
9254
|
+
if (options.includeImport) {
|
|
9255
|
+
lines.push(`@import "tailwindcss";${newline}`);
|
|
9256
|
+
}
|
|
9257
|
+
if (options.variantDeclarations.length > 0) {
|
|
9258
|
+
if (options.includeImport) {
|
|
9259
|
+
lines.push(newline);
|
|
9260
|
+
}
|
|
9261
|
+
for (const declaration of options.variantDeclarations) {
|
|
9262
|
+
lines.push(`${declaration}${newline}`);
|
|
9263
|
+
}
|
|
9264
|
+
}
|
|
9265
|
+
if (options.includeImport || options.variantDeclarations.length > 0) {
|
|
9266
|
+
lines.push(newline);
|
|
9267
|
+
}
|
|
9268
|
+
const themeDirective = options.namespace ? `@theme namespace(${options.namespace})` : "@theme";
|
|
9269
|
+
lines.push(`${themeDirective}${space}{${newline}`);
|
|
9270
|
+
for (const [, token] of getSortedTokenEntries(tokens)) {
|
|
9271
|
+
const varName = this.buildVariableName(token);
|
|
9272
|
+
const varValue = this.formatValue(token);
|
|
9273
|
+
lines.push(`${indent2}--${varName}:${space}${varValue};${newline}`);
|
|
9274
|
+
}
|
|
9275
|
+
lines.push(`}${newline}`);
|
|
9276
|
+
const cssString = lines.join("");
|
|
9277
|
+
return options.minify ? cssString : await this.formatWithPrettier(cssString);
|
|
9278
|
+
}
|
|
9279
|
+
/**
|
|
9280
|
+
* Format tokens as plain CSS custom property overrides inside a selector block.
|
|
9281
|
+
* Used for modifier overrides (e.g., dark mode) appended after the @theme block.
|
|
9282
|
+
*/
|
|
9283
|
+
async formatOverrideBlock(tokens, selector, mediaQuery, minify) {
|
|
9284
|
+
const indent2 = minify ? "" : " ";
|
|
9285
|
+
const newline = minify ? "" : "\n";
|
|
9286
|
+
const space = minify ? "" : " ";
|
|
9287
|
+
const hasMediaQuery = mediaQuery !== "";
|
|
9288
|
+
const tokenIndent = hasMediaQuery ? indent2 + indent2 : indent2;
|
|
9289
|
+
const lines = [];
|
|
9290
|
+
if (hasMediaQuery) {
|
|
9291
|
+
lines.push(`@media ${mediaQuery}${space}{${newline}`);
|
|
9292
|
+
lines.push(`${indent2}${selector}${space}{${newline}`);
|
|
9293
|
+
} else {
|
|
9294
|
+
lines.push(`${selector}${space}{${newline}`);
|
|
9295
|
+
}
|
|
9296
|
+
for (const [, token] of getSortedTokenEntries(tokens)) {
|
|
9297
|
+
const varName = this.buildVariableName(token);
|
|
9298
|
+
const varValue = this.formatValue(token);
|
|
9299
|
+
lines.push(`${tokenIndent}--${varName}:${space}${varValue};${newline}`);
|
|
9300
|
+
}
|
|
9301
|
+
if (hasMediaQuery) {
|
|
9302
|
+
lines.push(`${indent2}}${newline}`);
|
|
9303
|
+
lines.push(`}${newline}`);
|
|
9304
|
+
} else {
|
|
9305
|
+
lines.push(`}${newline}`);
|
|
9306
|
+
}
|
|
9307
|
+
return lines.join("");
|
|
9308
|
+
}
|
|
9309
|
+
buildVariableName(token) {
|
|
9310
|
+
const prefix = TAILWIND_NAMESPACE_MAP[token.$type ?? ""];
|
|
9311
|
+
if (!prefix) {
|
|
9312
|
+
return token.name;
|
|
9313
|
+
}
|
|
9314
|
+
const nameLower = token.name.toLowerCase();
|
|
9315
|
+
const prefixLower = prefix.toLowerCase();
|
|
9316
|
+
if (nameLower.startsWith(`${prefixLower}-`) || nameLower.startsWith(`${prefixLower}.`)) {
|
|
9317
|
+
return token.name;
|
|
9318
|
+
}
|
|
9319
|
+
return `${prefix}-${token.name}`;
|
|
9320
|
+
}
|
|
9321
|
+
formatValue(token) {
|
|
9322
|
+
const value = token.$value;
|
|
9323
|
+
if (token.$type === "color" && isColorObject(value)) {
|
|
9324
|
+
return colorObjectToHex(value);
|
|
9325
|
+
}
|
|
9326
|
+
if (token.$type === "dimension" && isDimensionObject(value)) {
|
|
9327
|
+
return dimensionObjectToString(value);
|
|
9328
|
+
}
|
|
9329
|
+
if (token.$type === "duration" && this.isDurationObject(value)) {
|
|
9330
|
+
return `${value.value}${value.unit}`;
|
|
9331
|
+
}
|
|
9332
|
+
if (token.$type === "fontFamily") {
|
|
9333
|
+
if (Array.isArray(value)) {
|
|
9334
|
+
return value.map((v) => typeof v === "string" && v.includes(" ") ? `"${v}"` : v).join(", ");
|
|
9335
|
+
}
|
|
9336
|
+
return typeof value === "string" ? value : String(value);
|
|
9337
|
+
}
|
|
9338
|
+
if (token.$type === "shadow") {
|
|
9339
|
+
return this.formatShadowValue(value);
|
|
9340
|
+
}
|
|
9341
|
+
if (token.$type === "cubicBezier" && Array.isArray(value) && value.length === 4) {
|
|
9342
|
+
return `cubic-bezier(${value.join(", ")})`;
|
|
9343
|
+
}
|
|
9344
|
+
if (typeof value === "string") {
|
|
9345
|
+
return value;
|
|
9346
|
+
}
|
|
9347
|
+
if (typeof value === "number") {
|
|
9348
|
+
return String(value);
|
|
9349
|
+
}
|
|
9350
|
+
return String(value);
|
|
9351
|
+
}
|
|
9352
|
+
formatShadowValue(value) {
|
|
9353
|
+
if (Array.isArray(value) && value.length > 0 && typeof value[0] === "object") {
|
|
9354
|
+
return value.map((s) => this.formatSingleShadow(s)).join(", ");
|
|
9355
|
+
}
|
|
9356
|
+
if (typeof value === "object" && value !== null) {
|
|
9357
|
+
return this.formatSingleShadow(value);
|
|
9358
|
+
}
|
|
9359
|
+
return String(value);
|
|
9360
|
+
}
|
|
9361
|
+
formatSingleShadow(shadow) {
|
|
9362
|
+
const parts = [];
|
|
9363
|
+
if (shadow.inset === true) {
|
|
9364
|
+
parts.push("inset");
|
|
9365
|
+
}
|
|
9366
|
+
if (isDimensionObject(shadow.offsetX)) {
|
|
9367
|
+
parts.push(dimensionObjectToString(shadow.offsetX));
|
|
9368
|
+
}
|
|
9369
|
+
if (isDimensionObject(shadow.offsetY)) {
|
|
9370
|
+
parts.push(dimensionObjectToString(shadow.offsetY));
|
|
9371
|
+
}
|
|
9372
|
+
if (isDimensionObject(shadow.blur)) {
|
|
9373
|
+
parts.push(dimensionObjectToString(shadow.blur));
|
|
9374
|
+
}
|
|
9375
|
+
if (shadow.spread != null && isDimensionObject(shadow.spread)) {
|
|
9376
|
+
parts.push(dimensionObjectToString(shadow.spread));
|
|
9377
|
+
}
|
|
9378
|
+
if (isColorObject(shadow.color)) {
|
|
9379
|
+
parts.push(colorObjectToHex(shadow.color));
|
|
9380
|
+
} else if (shadow.color != null) {
|
|
9381
|
+
parts.push(String(shadow.color));
|
|
9382
|
+
}
|
|
9383
|
+
return parts.join(" ");
|
|
9384
|
+
}
|
|
9385
|
+
isDurationObject(value) {
|
|
9386
|
+
return typeof value === "object" && value !== null && "value" in value && "unit" in value && value.unit !== void 0;
|
|
9387
|
+
}
|
|
9388
|
+
async formatWithPrettier(css2) {
|
|
9389
|
+
try {
|
|
9390
|
+
return await prettier.format(css2, {
|
|
9391
|
+
parser: "css",
|
|
9392
|
+
printWidth: 80,
|
|
9393
|
+
tabWidth: 2,
|
|
9394
|
+
useTabs: false
|
|
9395
|
+
});
|
|
9396
|
+
} catch {
|
|
9397
|
+
return css2;
|
|
9398
|
+
}
|
|
9399
|
+
}
|
|
9400
|
+
async formatBundle(context, options) {
|
|
9401
|
+
const bundleData = context.permutations.map(({ tokens, modifierInputs }) => ({
|
|
9402
|
+
tokens,
|
|
9403
|
+
modifierInputs,
|
|
9404
|
+
isBase: this.isBasePermutation(modifierInputs, context.meta.defaults)
|
|
9405
|
+
}));
|
|
9406
|
+
return await bundleAsTailwind(
|
|
9407
|
+
bundleData,
|
|
9408
|
+
options,
|
|
9409
|
+
async (tokens, opts) => await this.formatTokens(tokens, opts),
|
|
9410
|
+
async (tokens, selector, mediaQuery, minify) => await this.formatOverrideBlock(tokens, selector, mediaQuery, minify)
|
|
9411
|
+
);
|
|
9412
|
+
}
|
|
9413
|
+
async formatStandalone(context, options) {
|
|
9414
|
+
const requiresFile = context.buildPath !== void 0 && context.buildPath !== "";
|
|
9415
|
+
if (!context.output.file && requiresFile) {
|
|
9416
|
+
throw new ConfigurationError(
|
|
9417
|
+
`Output "${context.output.name}": file is required for standalone Tailwind output`
|
|
9418
|
+
);
|
|
9419
|
+
}
|
|
9420
|
+
const files = {};
|
|
9421
|
+
for (const { tokens, modifierInputs } of context.permutations) {
|
|
9422
|
+
const processedTokens = stripInternalMetadata(tokens);
|
|
9423
|
+
const content = await this.formatTokens(processedTokens, options);
|
|
9424
|
+
const fileName = context.output.file ? resolveFileName(context.output.file, modifierInputs) : buildInMemoryOutputKey({
|
|
9425
|
+
outputName: context.output.name,
|
|
9426
|
+
extension: "css",
|
|
9427
|
+
modifierInputs,
|
|
9428
|
+
resolver: context.resolver,
|
|
9429
|
+
defaults: context.meta.defaults
|
|
9430
|
+
});
|
|
9431
|
+
files[fileName] = content;
|
|
9432
|
+
}
|
|
9433
|
+
return outputTree(files);
|
|
9434
|
+
}
|
|
9435
|
+
isBasePermutation(modifierInputs, defaults) {
|
|
9436
|
+
return Object.entries(defaults).every(
|
|
9437
|
+
([key, value]) => modifierInputs[key]?.toLowerCase() === value.toLowerCase()
|
|
9438
|
+
);
|
|
9439
|
+
}
|
|
9440
|
+
};
|
|
9441
|
+
function tailwindRenderer() {
|
|
9442
|
+
const rendererInstance = new TailwindRenderer();
|
|
9443
|
+
return {
|
|
9444
|
+
format: (context, options) => rendererInstance.format(
|
|
9445
|
+
context,
|
|
9446
|
+
options ?? context.output.options
|
|
9447
|
+
)
|
|
9448
|
+
};
|
|
9449
|
+
}
|
|
9450
|
+
|
|
7725
9451
|
// src/builders.ts
|
|
7726
9452
|
function css(config) {
|
|
7727
9453
|
const {
|
|
@@ -7783,6 +9509,58 @@ function js(config) {
|
|
|
7783
9509
|
hooks
|
|
7784
9510
|
};
|
|
7785
9511
|
}
|
|
9512
|
+
function tailwind(config) {
|
|
9513
|
+
const { name, file, transforms, filters, hooks, preset = "bundle", ...rendererOptions } = config;
|
|
9514
|
+
return {
|
|
9515
|
+
name,
|
|
9516
|
+
file,
|
|
9517
|
+
renderer: tailwindRenderer(),
|
|
9518
|
+
options: { preset, ...rendererOptions },
|
|
9519
|
+
transforms,
|
|
9520
|
+
filters,
|
|
9521
|
+
hooks
|
|
9522
|
+
};
|
|
9523
|
+
}
|
|
9524
|
+
function ios(config) {
|
|
9525
|
+
const {
|
|
9526
|
+
name,
|
|
9527
|
+
file,
|
|
9528
|
+
transforms,
|
|
9529
|
+
filters,
|
|
9530
|
+
hooks,
|
|
9531
|
+
preset = "standalone",
|
|
9532
|
+
...rendererOptions
|
|
9533
|
+
} = config;
|
|
9534
|
+
return {
|
|
9535
|
+
name,
|
|
9536
|
+
file,
|
|
9537
|
+
renderer: iosRenderer(),
|
|
9538
|
+
options: { preset, ...rendererOptions },
|
|
9539
|
+
transforms,
|
|
9540
|
+
filters,
|
|
9541
|
+
hooks
|
|
9542
|
+
};
|
|
9543
|
+
}
|
|
9544
|
+
function android(config) {
|
|
9545
|
+
const {
|
|
9546
|
+
name,
|
|
9547
|
+
file,
|
|
9548
|
+
transforms,
|
|
9549
|
+
filters,
|
|
9550
|
+
hooks,
|
|
9551
|
+
preset = "standalone",
|
|
9552
|
+
...rendererOptions
|
|
9553
|
+
} = config;
|
|
9554
|
+
return {
|
|
9555
|
+
name,
|
|
9556
|
+
file,
|
|
9557
|
+
renderer: androidRenderer(),
|
|
9558
|
+
options: { preset, ...rendererOptions },
|
|
9559
|
+
transforms,
|
|
9560
|
+
filters,
|
|
9561
|
+
hooks
|
|
9562
|
+
};
|
|
9563
|
+
}
|
|
7786
9564
|
|
|
7787
9565
|
// src/renderers/types.ts
|
|
7788
9566
|
function defineRenderer(renderer) {
|
|
@@ -7796,7 +9574,14 @@ init_errors();
|
|
|
7796
9574
|
* Copyright (c) 2025 Dispersa Contributors
|
|
7797
9575
|
* SPDX-License-Identifier: MIT
|
|
7798
9576
|
*/
|
|
9577
|
+
/**
|
|
9578
|
+
* @license MIT
|
|
9579
|
+
* Copyright (c) 2025-present Dispersa Contributors
|
|
9580
|
+
*
|
|
9581
|
+
* This source code is licensed under the MIT license found in the
|
|
9582
|
+
* LICENSE file in the root directory of this source tree.
|
|
9583
|
+
*/
|
|
7799
9584
|
|
|
7800
|
-
export { BasePermutationError, CircularReferenceError, ColorParseError, ConfigurationError, DimensionFormatError, Dispersa, DispersaError, FileOperationError, ModifierError, TokenReferenceError, ValidationError, css, defineRenderer, isBorderToken, isColorToken, isDimensionToken, isDurationToken, isGradientToken, isOutputTree, isShadowToken, isTransitionToken, isTypographyToken, js, json, outputTree };
|
|
9585
|
+
export { BasePermutationError, CircularReferenceError, ColorParseError, ConfigurationError, DimensionFormatError, Dispersa, DispersaError, FileOperationError, ModifierError, TokenReferenceError, ValidationError, android, css, defineRenderer, ios, isBorderToken, isColorToken, isDimensionToken, isDurationToken, isGradientToken, isOutputTree, isShadowToken, isTransitionToken, isTypographyToken, js, json, outputTree, tailwind };
|
|
7801
9586
|
//# sourceMappingURL=index.js.map
|
|
7802
9587
|
//# sourceMappingURL=index.js.map
|