@lovrozagar/flare 0.2.1 → 0.3.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 +2 -0
- package/package.json +1 -1
- package/src/plugins/sx-ast/rewrite.ts +109 -72
- package/src/styles/cn-vendor/NOTICE.md +18 -0
- package/src/styles/cn-vendor/engine.ts +1603 -0
- package/src/styles/cn-vendor/tables.generated.ts +123 -0
- package/src/styles/cn-vendor/types.ts +120 -0
- package/src/styles/cn.ts +15 -0
- package/src/styles/index.ts +1 -36
|
@@ -0,0 +1,123 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* MIT License
|
|
3
|
+
*
|
|
4
|
+
* Copyright (c) 2026 shadcn
|
|
5
|
+
*
|
|
6
|
+
* Vendored from https://github.com/shadcn-ui/cn
|
|
7
|
+
* tag cn@0.4.0
|
|
8
|
+
* commit 84db83298f69a229d6f1ffc5d8c8d99ef451fb49
|
|
9
|
+
* Source: packages/cn/src/tables.generated.ts
|
|
10
|
+
*/
|
|
11
|
+
|
|
12
|
+
// GENERATED by scripts/compile-tables.mjs from the vendored default config. Do not edit.
|
|
13
|
+
const P = 48
|
|
14
|
+
const U = (s: string, o = 0): Int32Array => {
|
|
15
|
+
const out = new Int32Array(s.length)
|
|
16
|
+
for (let i = 0; i < s.length; i++) out[i] = s.charCodeAt(i) - P - o
|
|
17
|
+
return out
|
|
18
|
+
}
|
|
19
|
+
const PS = (counts: Int32Array): Int32Array => {
|
|
20
|
+
const out = new Int32Array(counts.length + 1)
|
|
21
|
+
for (let i = 0; i < counts.length; i++) out[i + 1] = out[i]! + counts[i]!
|
|
22
|
+
return out
|
|
23
|
+
}
|
|
24
|
+
// zigzag-delta stream → running values
|
|
25
|
+
const DZ = (s: string): Int32Array => {
|
|
26
|
+
const out = new Int32Array(s.length)
|
|
27
|
+
let a = 0
|
|
28
|
+
for (let i = 0; i < s.length; i++) {
|
|
29
|
+
const z = s.charCodeAt(i) - P
|
|
30
|
+
a += (z >>> 1) ^ -(z & 1)
|
|
31
|
+
out[i] = a
|
|
32
|
+
}
|
|
33
|
+
return out
|
|
34
|
+
}
|
|
35
|
+
const GROUP_COUNT = 384
|
|
36
|
+
const customValidatorNames: string[] = []
|
|
37
|
+
const edgeStart = PS(U("E0500002005282000000002000150000020021820000011200000003022202000300004200120000200420001200021200301200010400162000010000220021010:2192001200220012000220012000200200200400010200040000000000400200108200110100000022010313000162002000020020012020080213000228200000000082000000000120002000120020020040101020300130001001010"))
|
|
38
|
+
const labelStart = PS(U(":11111111211111119311546544411119731869:671397415686432441111111111161114151214313433415:78311132233313187211117221449443411141111151152226611131111112212518142224214215421421542142424242516171151615616347111111111197911327451111111111111111111113134714133513411111311111111111111111111112444411111342312715245411117:3"))
|
|
39
|
+
const labelText = "@containerabcdefghinlmoprstunderlineviawzccentlignnimatespectuto-colsrowsaglorightnessckdrop-sisbcontrastfiltergrayscalehue-rotateinvertopacityslurrightnessaturateepia-coniclinearpositionradialsizeockurrderttom-belrstxyespacing-xyaretoursorlnt-umnsendspantartainentrasteividerop-shadowurationcorationlay-xyasendillexontromlter-featuresstretchapr-xyayscaleidow-colsrowsue-rotatedentlinesetvert-beringsxyeshadoweiadingftnest-clamp-imageabein-lrstxyskx--b-coniclpositionrsizet-x-y-fromto-fromto-inearfromto-fromto-adialfromto-fromtofromtofromtofromtoblockhinlinew-screenesblockhinlinewbjectpacityrutlinederigin-offsetbelrstxyesrspective-originaceholderioghtng-offsettateundedw-xyz-belrstlreseslr-endspantartaturatecepiahizekewpace-taleroll-xyz-barmpbelrstxyesbelrstxyes-thumbrackadowrink-xyxyartrokeabextora-shadowpckingnsformitionlate-xyz-offsetill-changeoom"
|
|
40
|
+
// pre-order tree: targets derived from edge counts via subtree sizes
|
|
41
|
+
const edgeTarget = (() => {
|
|
42
|
+
const N = edgeStart.length - 1
|
|
43
|
+
const sizes = new Int32Array(N)
|
|
44
|
+
for (let i = N - 1; i >= 0; i--) {
|
|
45
|
+
let s = 1
|
|
46
|
+
let c = i + 1
|
|
47
|
+
for (let k = edgeStart[i]!; k < edgeStart[i + 1]!; k++) { s += sizes[c]!; c += sizes[c]! }
|
|
48
|
+
sizes[i] = s
|
|
49
|
+
}
|
|
50
|
+
const out = new Int32Array(edgeStart[N]!)
|
|
51
|
+
let e = 0
|
|
52
|
+
for (let i = 0; i < N; i++) {
|
|
53
|
+
let c = i + 1
|
|
54
|
+
for (let k = edgeStart[i]!; k < edgeStart[i + 1]!; k++) { out[e++] = c; c += sizes[c]! }
|
|
55
|
+
}
|
|
56
|
+
return out
|
|
57
|
+
})()
|
|
58
|
+
const nodeGroup = U("02000000000000900<=0?000B000F00F00ŏI0J0LNPRTVX0000]_a00000000000000000000000rst0000000zŏ00000000000
ŏ0000000ŏ00000000000000000000000000000000000000000000000000000000000000Ë000000000000000000000Þ000000000000000000ð0000000ø0ùúûüýþÿĀāĂ㥹Ć000000000000000000000000000000000000000000ħ0ĨĪ00000000000000000000ļĽ00000Ŭ000000", 1)
|
|
59
|
+
// vlists = op-pattern pool + per-list refs; the engine indexes these directly
|
|
60
|
+
const vlistPat = PS(U("123333359346463635126536711576"))
|
|
61
|
+
const vlistOps = U("93203242332583253248325D>E?F@03263243255B:032523853:0325B:8GA032542H<C=12727B:0328432553;D>E?3257D>032585:0325B:;0328B:032")
|
|
62
|
+
const vlistRef = U("012113445661666666789111:5;;;;;;;;444;;;:62999<1161=62>>?61:21@ABCD4446996:64E:::;:?::64:F114GHHIHHHHIHH1HH1HH1HHHHHH::EEJ4444::EE4444441691;644444114244444:;K6666555555555555555999666664444444444444444444444226?6:66644L9M?D:111::::6DE199")
|
|
63
|
+
const vlistGroup = DZ("020200202020020020020020020020200200200200200200200002020202001003040106000200200200200200200200200200200200200200200200200200200200200200200200200200200200020020020020020020002020200202002002002002002002002002002020002002020020200220200200200200200200200200200200020020020000200020002000200200200020020020002000200200200020020202002020202000200200020022000200200020020002002000200220002002000200W0Z00020020002002020002002000200g0j0002002000200200020020002002000200200020020002000200002000002002002002002000200020000200002002002002002002002020020020200200200200200200200200202020020020020020020020020002002002020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020020002002002002002002000200200200200200200200200200020202020002000200020002002002002000020200200")
|
|
64
|
+
// nodeVlist rebuilt sparse: (anchor deltas, vlist ids)
|
|
65
|
+
const nodeVlist = (() => {
|
|
66
|
+
const out = new Int32Array(319).fill(-1)
|
|
67
|
+
const A = DZ("02422242:222222242224222242442222222422222244442242226224222426222422442462222422622222222626222462242622422622422424242422222222422222222242422222222222222222622442224222222222222224424442262222222222222222222226224222424242422224422422422222")
|
|
68
|
+
const V = DZ("02222222222222222222202222222222222222222222221422222222222222222222222222222222222Y\\222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222221422222222222222222222222222222222222222Ŀł222222222222222222")
|
|
69
|
+
for (let i = 0; i < A.length; i++) out[A[i]!] = V[i]!
|
|
70
|
+
return out
|
|
71
|
+
})()
|
|
72
|
+
const SETS = "container |break-after- all auto avoid avoid-page column left page right|break-before- all auto avoid avoid-page column left page right|break-inside-a uto void void-column void-page|box-decoration- clone slice|box- border content| contents flow-root hidden table table-caption table-cell table-column table-column-group table-footer-group table-header-group table-row table-row-group| not-sr-only sr-only|float- end left none right start|clear- both end left none right start|isolat e ion-auto|overflow- auto clip hidden scroll visible|overflow-x- auto clip hidden scroll visible|overflow-y- auto clip hidden scroll visible|overscroll- auto contain none|overscroll-x- auto contain none|overscroll-y- auto contain none| absolute fixed relative static sticky| collapse invisible visible|justify- around baseline between center center-safe end end-safe evenly normal start stretch|justify-items- center center-safe end end-safe normal start stretch|justify-self- auto center center-safe end end-safe start stretch|items- baseline baseline-last center center-safe end end-safe start stretch|self- auto baseline baseline-last center center-safe end end-safe start stretch|place-content- around baseline between center center-safe end end-safe evenly start stretch|place-items- baseline center center-safe end end-safe start stretch|place-self- auto center center-safe end end-safe start stretch| antialiased subpixel-antialiased| italic not-italic|normal-nums |ordinal |slashed-zero | lining-nums oldstyle-nums| proportional-nums tabular-nums| diagonal-fractions stacked-fractions| no-underline overline| capitalize lowercase normal-case uppercase|truncate |whitespace- break-spaces normal nowrap pre pre-line pre-wrap|break- all keep normal words|wrap- anywhere break-word normal|hyphens- auto manual none|mix-blend- color color-burn color-dodge darken difference exclusion hard-light hue lighten luminosity multiply normal overlay plus-darker plus-lighter saturation screen soft-light|table- auto fixed|caption- bottom top|backface- hidden visible|appearance- auto none|scheme- dark light light-dark normal only-dark only-light|field-sizing- content fixed|pointer-events- auto none|resize -none -x -y|snap- align-none center end start|snap- always normal|snap- both none x y|snap- mandatory proximity|touch- auto manipulation none|touch-pan- left right x|touch-pan- down up y|touch-pinch-zoom |select- all auto none text|forced-color-adjust- auto none| normal size| baseline bottom middle sub super text-bottom text-top top| bounce none ping pulse spin| auto square video| auto fr max min px|none | auto full px| fixed local scroll|clip- border content padding text|origin- border content padding| bottom bottom-left bottom-right center left left-bottom left-top right right-bottom right-top top top-left top-right| no-repeat repeat repeat-round repeat-space repeat-x repeat-y| auto contain cover| gradient-to-b gradient-to-bl gradient-to-br gradient-to-l gradient-to-r gradient-to-t gradient-to-tl gradient-to-tr none|blend- color color-burn color-dodge darken difference exclusion hard-light hue lighten luminosity multiply normal overlay saturation screen soft-light|to- b bl br l r t tl tr| auto dvh fit full lh lvh max min px screen svh| dashed dotted double hidden none solid| collapse separate|px |auto |full | content none strict| inline-size size|layout |paint |style | around baseline between center center-safe end end-safe evenly normal start stretch| alias all-scroll auto cell col-resize context-menu copy crosshair default e-resize ew-resize grab grabbing help move n-resize ne-resize nesw-resize no-drop none not-allowed ns-resize nw-resize nwse-resize pointer progress row-resize s-resize se-resize sw-resize text vertical-text w-resize wait zoom-in zoom-out| dashed dotted double solid wavy| auto from-font|reverse |initial | in in-out initial linear out| col col-reverse row row-reverse| nowrap wrap wrap-reverse| auto initial none| black bold extrabold extralight light medium normal semibold thin| condensed expanded extra-condensed extra-expanded normal semi-condensed semi-expanded ultra-condensed ultra-expanded|flow- col col-dense dense row row-dense| none subgrid| auto dvh dvw fit full lh lvh lvw max min px screen svh svw| block flex grid table| auto dvw fit full lvw max min px screen svw| loose none normal px relaxed snug tight|through |item | inside outside| decimal disc none| auto px| clip-border clip-content clip-fill clip-padding clip-stroke clip-view no-clip| add exclude intersect subtract| alpha luminance match|origin- border content fill padding stroke view|type- alpha luminance| circle ellipse| closest-corner closest-side farthest-corner farthest-side|at- bottom bottom-left bottom-right center left left-bottom left-top right right-bottom right-top top top-left top-right| dvh fit full lh lvh max min none px screen svh| auto dvh dvw fit full lh lvh lvw max min none px screen svh svw| dvw fit full lvw max min none px screen svw| auto dvh dvw fit full lvh lvw max min none prose px svh svw| auto dvh dvw fit full lvh lvw max min none px screen svh svw| contain cover fill none scale-down| first last none| distant dramatic midrange near none normal|inset | full none|3d | auto smooth|gutter- auto both stable| auto none thin| inner none| auto dvh dvw fit full lvh lvw max min px svh svw|base | center end justify left right start| clip ellipsis| balance nowrap pretty wrap| normal tight tighter wide wider widest| cpu gpu none| 3d flat| all colors none opacity shadow transform| discrete normal| full px| auto dvh dvw fit full lvh lvw max min px screen svh svw| auto contents scroll transform".split('|').map((s) => {
|
|
73
|
+
const tails = s.split(' ')
|
|
74
|
+
const prefix = tails.shift()!
|
|
75
|
+
for (let i = 0; i < tails.length; i++) {
|
|
76
|
+
tails[i] = prefix + tails[i]
|
|
77
|
+
}
|
|
78
|
+
return tails
|
|
79
|
+
})
|
|
80
|
+
const AA = DZ("0000000000000000000000000000000000000000000000000000000000000262242:6@200000006:240B428:4422400002046044222426220026642642462026224222824220022400000000\\00N222422242222222224062242222222422226264222422222222222222442804222422222222222222222222220<4<0204260002444020204224422")
|
|
81
|
+
const AG = DZ("ɠ222222222222222222222222222222222222222222222222222222222222˕4222226>ʶ22ʷʺʷ2ʸʷ42ʴ2ʓ22>621422ɶ222ɹɼɷɺɷɺ22ɱ42222ɨ2ɧ26622ɘɓ244ƸƵ222]d24242ǖǓƚÄȫ2263ȨȥȨ2222222ǣ222222222222222222ǂƽ2ƾƵ2222222422222ƜƑ22222222222222222222144Ŧţ22Ţş222222222222222222222ĸ2ı68ĦģĦɡŰ4Ġ«®ĝ822ĔđĔ2ē2222622")
|
|
82
|
+
const AS = DZ("02222222222222222222222222222222222222222222222222222222222222222202022222222222EH2200IL021042222Y\\222IL0cf2e10j2222U00X202[^2y0000120|{~22
:22|22222222222G000qOVI00000}2>40000B00000I¨©000¬00000000000000021M®00°000000000000000000000222HGHa1º222¿2À2222ÉÌ000°2±")
|
|
83
|
+
const litAnchor = new Int32Array(995)
|
|
84
|
+
const litGroup = new Int32Array(995)
|
|
85
|
+
const litPool = new Int32Array(995)
|
|
86
|
+
let poolText = ''
|
|
87
|
+
const poolOffsets = new Int32Array(1038)
|
|
88
|
+
{
|
|
89
|
+
const tailRef = new Map()
|
|
90
|
+
let nextRef = 0
|
|
91
|
+
let e = 0
|
|
92
|
+
for (let i = 0; i < AA.length; i++) {
|
|
93
|
+
for (const tail of SETS[AS[i]!]!) {
|
|
94
|
+
let r = tailRef.get(tail)
|
|
95
|
+
if (r === undefined) {
|
|
96
|
+
r = nextRef++
|
|
97
|
+
tailRef.set(tail, r)
|
|
98
|
+
poolOffsets[r * 2] = poolText.length
|
|
99
|
+
poolOffsets[r * 2 + 1] = tail.length
|
|
100
|
+
poolText += tail
|
|
101
|
+
}
|
|
102
|
+
litAnchor[e] = AA[i]!
|
|
103
|
+
litGroup[e] = AG[i]!
|
|
104
|
+
litPool[e] = r
|
|
105
|
+
e++
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
// conflict adjacency (engine builds claim bitmask CSR at init)
|
|
110
|
+
const adjGid = DZ("0b2N:222@R>F@286¦2@H2D266226FB22B2>BD\\6N22222Z222D222p")
|
|
111
|
+
const adjStart = PS(U("1::24444432:442:44:44>222222:44:4421322511111311111114"))
|
|
112
|
+
const adjTgt = DZ("24A;33N=C@H4A;33N=C@<27;83:;8393NQ:3NQʰ222ˉºŴŽ2R2=18cƴÅŇ=cĞÛC1ƈǝȈ:ħ25=11D3A@4=<1;1DEr25;11B3?<6;:371BCn9@7=<8192>2E121@9@EHE@9>2T25511<398454131<=V25511<398454131<=ƧNž2Đå242L222290000f22500ɛ000ǘ222")
|
|
113
|
+
const patGid = U("ij")
|
|
114
|
+
const patTgt = U("")
|
|
115
|
+
const postfixLookupGroups = U("1")
|
|
116
|
+
const orderSensitiveModifiers = "* ** after backdrop before details-content file first-letter first-line marker placeholder selection"
|
|
117
|
+
export default {
|
|
118
|
+
GROUP_COUNT, customValidatorNames, edgeStart, labelStart, labelText,
|
|
119
|
+
edgeTarget, nodeGroup, nodeVlist, vlistPat, vlistOps, vlistRef, vlistGroup,
|
|
120
|
+
litAnchor, litGroup, litPool, poolOffsets, poolText,
|
|
121
|
+
adjGid, adjStart, adjTgt, patGid, patTgt, postfixLookupGroups,
|
|
122
|
+
orderSensitiveModifiers,
|
|
123
|
+
}
|
|
@@ -0,0 +1,120 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* MIT License
|
|
3
|
+
*
|
|
4
|
+
* Copyright (c) 2026 shadcn
|
|
5
|
+
*
|
|
6
|
+
* Vendored from https://github.com/shadcn-ui/cn
|
|
7
|
+
* tag cn@0.4.0
|
|
8
|
+
* commit 84db83298f69a229d6f1ffc5d8c8d99ef451fb49
|
|
9
|
+
* Source: packages/cn/src/types.ts
|
|
10
|
+
*/
|
|
11
|
+
|
|
12
|
+
/**
|
|
13
|
+
* Compiled lookup tables consumed by the engine. Generated by the compiler
|
|
14
|
+
* (`scripts/compile-tables.mjs`) — flat typed arrays plus string pools; see
|
|
15
|
+
* the compiler for the encoding.
|
|
16
|
+
*/
|
|
17
|
+
export interface Tables {
|
|
18
|
+
/** number of static conflict groups */
|
|
19
|
+
GROUP_COUNT: number
|
|
20
|
+
/** CSR: node → [start,end) range into edge arrays */
|
|
21
|
+
edgeStart: Int32Array
|
|
22
|
+
/** CSR: edge → [start,end) range into labelText */
|
|
23
|
+
labelStart: Int32Array
|
|
24
|
+
/** radix-edge label characters, concatenated */
|
|
25
|
+
labelText: string
|
|
26
|
+
/** edge → target node */
|
|
27
|
+
edgeTarget: Int32Array
|
|
28
|
+
/** node → group id (0 = none) offset by 1 */
|
|
29
|
+
nodeGroup: Int32Array
|
|
30
|
+
/** node → validator-list id (-1 = none) */
|
|
31
|
+
nodeVlist: Int32Array
|
|
32
|
+
/** CSR: validator-list pattern → [start,end) into vlistOps */
|
|
33
|
+
vlistPat: Int32Array
|
|
34
|
+
/** validator opcodes */
|
|
35
|
+
vlistOps: Int32Array
|
|
36
|
+
/** validator-list → op pattern id */
|
|
37
|
+
vlistRef: Int32Array
|
|
38
|
+
/** flat per-list group ids (delta-coded at generation) */
|
|
39
|
+
vlistGroup: Int32Array
|
|
40
|
+
/** lifted-literal entry → anchor node */
|
|
41
|
+
litAnchor: Int32Array
|
|
42
|
+
/** lifted-literal entry → group id */
|
|
43
|
+
litGroup: Int32Array
|
|
44
|
+
/** lifted-literal entry → pool string id */
|
|
45
|
+
litPool: Int32Array
|
|
46
|
+
/** pool string id → (offset, length) pairs into poolText */
|
|
47
|
+
poolOffsets: Int32Array
|
|
48
|
+
/** deduplicated literal tail text */
|
|
49
|
+
poolText: string
|
|
50
|
+
/** conflict adjacency: row → source group id */
|
|
51
|
+
adjGid: Int32Array
|
|
52
|
+
/** CSR: row → [start,end) into adjTgt */
|
|
53
|
+
adjStart: Int32Array
|
|
54
|
+
/** overridden group ids */
|
|
55
|
+
adjTgt: Int32Array
|
|
56
|
+
/** postfix-extra conflict pairs (conflictingClassGroupModifiers) */
|
|
57
|
+
patGid: Int32Array
|
|
58
|
+
patTgt: Int32Array
|
|
59
|
+
/** groups participating in postfix re-lookup (postfixLookupClassGroups) */
|
|
60
|
+
postfixLookupGroups: Int32Array
|
|
61
|
+
/** names of validators not compiled to span opcodes (custom configs) */
|
|
62
|
+
customValidatorNames: string[]
|
|
63
|
+
/** space-separated order-sensitive variant names */
|
|
64
|
+
orderSensitiveModifiers: string
|
|
65
|
+
/** optional Tailwind v4 prefix baked into the tables */
|
|
66
|
+
prefix?: string
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
export interface EngineOptions {
|
|
70
|
+
/** whole-string result cache size; 0 disables (default 500) */
|
|
71
|
+
cacheSize?: number
|
|
72
|
+
/** Tailwind v4 prefix (`tw` matches `tw:hover:p-4`); overrides tables */
|
|
73
|
+
prefix?: string
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
/** implementations for validators named in `Tables.customValidatorNames` */
|
|
77
|
+
export type ValidatorImpls = Record<string, (value: string) => boolean>
|
|
78
|
+
|
|
79
|
+
/** tailwind-merge `twJoin`/`twMerge` argument shape (strings + nested arrays) */
|
|
80
|
+
export type ClassNameValue =
|
|
81
|
+
ClassNameArray | string | null | undefined | 0 | 0n | false
|
|
82
|
+
export type ClassNameArray = readonly ClassNameValue[]
|
|
83
|
+
|
|
84
|
+
/** clsx argument shape (adds numbers and object syntax) */
|
|
85
|
+
export type ClassValue =
|
|
86
|
+
| ClassArray
|
|
87
|
+
| ClassDictionary
|
|
88
|
+
| string
|
|
89
|
+
| number
|
|
90
|
+
| bigint
|
|
91
|
+
| null
|
|
92
|
+
| boolean
|
|
93
|
+
| undefined
|
|
94
|
+
export type ClassArray = ClassValue[]
|
|
95
|
+
export interface ClassDictionary {
|
|
96
|
+
// matches clsx's Record<string, any> for drop-in type parity
|
|
97
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
98
|
+
[id: string]: any
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
export interface Engine {
|
|
102
|
+
/** variadic merge, `twMerge`-compatible (strings + nested arrays) */
|
|
103
|
+
merge: (...inputs: ClassNameValue[]) => string
|
|
104
|
+
/** merge one already-joined class string */
|
|
105
|
+
mergeString: (input: string) => string
|
|
106
|
+
/**
|
|
107
|
+
* doorkeeper probe for a string that was just built: records this
|
|
108
|
+
* sighting and reports whether an earlier one exists. A first sighting
|
|
109
|
+
* is best merged with `mergeUncached` and not cached anywhere.
|
|
110
|
+
*/
|
|
111
|
+
seenBefore: (input: string) => boolean
|
|
112
|
+
/** merge one string, bypassing the whole-string cache */
|
|
113
|
+
mergeUncached: (input: string) => string
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
/** what `wrapClsx` needs from an engine to handle freshly joined strings */
|
|
117
|
+
export type FreshMerge = Pick<Engine, "seenBefore" | "mergeUncached">
|
|
118
|
+
|
|
119
|
+
/** the `cn` function shape: clsx arguments, merged output */
|
|
120
|
+
export type CnFunction = (...inputs: ClassValue[]) => string
|
package/src/styles/cn.ts
ADDED
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import tables from "./cn-vendor/tables.generated.ts";
|
|
2
|
+
import { createEngine, wrapClsx } from "./cn-vendor/engine.ts";
|
|
3
|
+
|
|
4
|
+
/** Accepted input shapes for `cn()`. Superset of the JSX `ClassValue` — adds object maps. */
|
|
5
|
+
export type CnValue = string | false | null | undefined | Record<string, boolean> | CnValue[];
|
|
6
|
+
|
|
7
|
+
const instance = /* @__PURE__ */ createEngine(tables);
|
|
8
|
+
|
|
9
|
+
/** Same merge the sx plugin runs on a fully static class string. */
|
|
10
|
+
export function mergeClassList(input: string): string {
|
|
11
|
+
return instance.mergeString(input);
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
/** Join class values and resolve Tailwind conflicts. Last conflicting utility wins. */
|
|
15
|
+
export const cn = /* @__PURE__ */ wrapClsx(instance.mergeString, instance) as (...inputs: CnValue[]) => string;
|
package/src/styles/index.ts
CHANGED
|
@@ -1173,42 +1173,7 @@ export function compileCss(text: string, layer: "user.lib" | "user.app" = "user.
|
|
|
1173
1173
|
return cls;
|
|
1174
1174
|
}
|
|
1175
1175
|
|
|
1176
|
-
|
|
1177
|
-
export type CnValue = string | false | null | undefined | Record<string, boolean> | CnValue[];
|
|
1178
|
-
|
|
1179
|
-
function collectClasses(input: CnValue, seen: Set<string>, out: string[]): void {
|
|
1180
|
-
if (!input) return;
|
|
1181
|
-
if (typeof input === "string") {
|
|
1182
|
-
/* Split on whitespace — each token deduped individually */
|
|
1183
|
-
for (const token of input.trim().split(/\s+/)) {
|
|
1184
|
-
if (token && !seen.has(token)) {
|
|
1185
|
-
seen.add(token);
|
|
1186
|
-
out.push(token);
|
|
1187
|
-
}
|
|
1188
|
-
}
|
|
1189
|
-
return;
|
|
1190
|
-
}
|
|
1191
|
-
if (Array.isArray(input)) {
|
|
1192
|
-
for (const item of input) collectClasses(item as CnValue, seen, out);
|
|
1193
|
-
return;
|
|
1194
|
-
}
|
|
1195
|
-
if (typeof input === "object") {
|
|
1196
|
-
for (const [key, active] of Object.entries(input)) {
|
|
1197
|
-
if (active && !seen.has(key)) {
|
|
1198
|
-
seen.add(key);
|
|
1199
|
-
out.push(key);
|
|
1200
|
-
}
|
|
1201
|
-
}
|
|
1202
|
-
}
|
|
1203
|
-
}
|
|
1204
|
-
|
|
1205
|
-
/** Merge class names, filter falsy, deduplicate. Matches clsx API. */
|
|
1206
|
-
export function cn(...inputs: CnValue[]): string {
|
|
1207
|
-
const seen = new Set<string>();
|
|
1208
|
-
const out: string[] = [];
|
|
1209
|
-
for (const input of inputs) collectClasses(input, seen, out);
|
|
1210
|
-
return out.join(" ");
|
|
1211
|
-
}
|
|
1176
|
+
export { cn, type CnValue } from "./cn.ts";
|
|
1212
1177
|
|
|
1213
1178
|
export function clearScopedStyles(): void {
|
|
1214
1179
|
registry.clear();
|