zyzz 0.0.21 → 0.0.23
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/Zyzz.podspec +16 -0
- package/dist/Style.d.ts +3 -1
- package/dist/Style.d.ts.map +1 -1
- package/dist/Style.js.map +1 -1
- package/dist/babel/NativeJsx.d.ts.map +1 -1
- package/dist/babel/NativeJsx.js +217 -15
- package/dist/babel/NativeJsx.js.map +1 -1
- package/dist/babel/index.d.ts +6 -2
- package/dist/babel/index.d.ts.map +1 -1
- package/dist/babel/index.js +10 -1
- package/dist/babel/index.js.map +1 -1
- package/dist/compiler/Graph.d.ts.map +1 -1
- package/dist/compiler/Graph.js +107 -0
- package/dist/compiler/Graph.js.map +1 -1
- package/dist/compiler/Native.d.ts +6 -3
- package/dist/compiler/Native.d.ts.map +1 -1
- package/dist/compiler/Native.js +142 -24
- package/dist/compiler/Native.js.map +1 -1
- package/dist/compiler/Source.d.ts +2 -0
- package/dist/compiler/Source.d.ts.map +1 -1
- package/dist/compiler/Source.js +17 -5
- package/dist/compiler/Source.js.map +1 -1
- package/dist/compiler/internal/Configurations.d.ts +2 -0
- package/dist/compiler/internal/Configurations.d.ts.map +1 -1
- package/dist/compiler/internal/Configurations.js +21 -3
- package/dist/compiler/internal/Configurations.js.map +1 -1
- package/dist/compiler/internal/Contract.d.ts.map +1 -1
- package/dist/compiler/internal/Contract.js +75 -38
- package/dist/compiler/internal/Contract.js.map +1 -1
- package/dist/compiler/internal/Contributions.d.ts.map +1 -1
- package/dist/compiler/internal/Contributions.js +7 -1
- package/dist/compiler/internal/Contributions.js.map +1 -1
- package/dist/compiler/internal/Descriptors.d.ts.map +1 -1
- package/dist/compiler/internal/Descriptors.js +11 -2
- package/dist/compiler/internal/Descriptors.js.map +1 -1
- package/dist/compiler/internal/Dynamic.d.ts.map +1 -1
- package/dist/compiler/internal/Dynamic.js +3 -0
- package/dist/compiler/internal/Dynamic.js.map +1 -1
- package/dist/compiler/internal/Expression.js +2 -2
- package/dist/compiler/internal/Expression.js.map +1 -1
- package/dist/compiler/internal/NativeBindings.d.ts +24 -26
- package/dist/compiler/internal/NativeBindings.d.ts.map +1 -1
- package/dist/compiler/internal/NativeBindings.js +62 -8
- package/dist/compiler/internal/NativeBindings.js.map +1 -1
- package/dist/compiler/internal/NativeMedia.d.ts +14 -0
- package/dist/compiler/internal/NativeMedia.d.ts.map +1 -0
- package/dist/compiler/internal/NativeMedia.js +287 -0
- package/dist/compiler/internal/NativeMedia.js.map +1 -0
- package/dist/compiler/internal/NativeVars.d.ts +28 -0
- package/dist/compiler/internal/NativeVars.d.ts.map +1 -0
- package/dist/compiler/internal/NativeVars.js +160 -0
- package/dist/compiler/internal/NativeVars.js.map +1 -0
- package/dist/compiler/internal/PackedStyles.d.ts +2 -0
- package/dist/compiler/internal/PackedStyles.d.ts.map +1 -1
- package/dist/compiler/internal/PackedStyles.js +2 -0
- package/dist/compiler/internal/PackedStyles.js.map +1 -1
- package/dist/compiler/internal/Themes.d.ts +24 -1
- package/dist/compiler/internal/Themes.d.ts.map +1 -1
- package/dist/compiler/internal/Themes.js +120 -3
- package/dist/compiler/internal/Themes.js.map +1 -1
- package/dist/compiler/internal/Vars.d.ts +1 -1
- package/dist/compiler/internal/Vars.d.ts.map +1 -1
- package/dist/compiler/internal/Vars.js +7 -2
- package/dist/compiler/internal/Vars.js.map +1 -1
- package/dist/default.js.zyzz.json +1 -1
- package/dist/internal/Completion.d.ts +1 -1
- package/dist/internal/Completion.d.ts.map +1 -1
- package/dist/internal/Targets.d.ts.map +1 -1
- package/dist/internal/Targets.js +2 -0
- package/dist/internal/Targets.js.map +1 -1
- package/dist/internal/Token.d.ts +0 -2
- package/dist/internal/Token.d.ts.map +1 -1
- package/dist/internal/Token.js.map +1 -1
- package/dist/internal/Value.d.ts +7 -0
- package/dist/internal/Value.d.ts.map +1 -1
- package/dist/internal/Value.js.map +1 -1
- package/dist/metro/Graph.d.ts +22 -7
- package/dist/metro/Graph.d.ts.map +1 -1
- package/dist/metro/Graph.js +188 -42
- package/dist/metro/Graph.js.map +1 -1
- package/dist/metro/Watch.d.ts +28 -4
- package/dist/metro/Watch.d.ts.map +1 -1
- package/dist/metro/Watch.js +39 -7
- package/dist/metro/Watch.js.map +1 -1
- package/dist/metro/index.d.ts +15 -4
- package/dist/metro/index.d.ts.map +1 -1
- package/dist/metro/index.js +27 -0
- package/dist/metro/index.js.map +1 -1
- package/dist/metro/transformer.d.ts +5 -1
- package/dist/metro/transformer.d.ts.map +1 -1
- package/dist/metro/transformer.js +5 -3
- package/dist/metro/transformer.js.map +1 -1
- package/dist/react-native/StyleSheet.d.ts +8 -3
- package/dist/react-native/StyleSheet.d.ts.map +1 -1
- package/dist/react-native/StyleSheet.js +25 -34
- package/dist/react-native/StyleSheet.js.map +1 -1
- package/dist/react-native/index.d.ts +1 -1
- package/dist/react-native/index.d.ts.map +1 -1
- package/dist/react-native/index.js +1 -1
- package/dist/react-native/index.js.map +1 -1
- package/dist/react-native/index.native.d.ts +5 -0
- package/dist/react-native/index.native.js +20 -0
- package/dist/react-native/index.native.js.map +7 -0
- package/dist/react-native/internal/Calculation.d.ts +7 -0
- package/dist/react-native/internal/Calculation.d.ts.map +1 -0
- package/dist/react-native/internal/Calculation.js +134 -0
- package/dist/react-native/internal/Calculation.js.map +1 -0
- package/dist/react-native/internal/Device.js +218 -0
- package/dist/react-native/internal/Device.js.map +7 -0
- package/dist/react-native/internal/NativeZyzz.js +7 -0
- package/dist/react-native/internal/NativeZyzz.js.map +7 -0
- package/dist/react-native/internal/Scalar.d.ts +16 -0
- package/dist/react-native/internal/Scalar.d.ts.map +1 -1
- package/dist/react-native/internal/Scalar.js +62 -4
- package/dist/react-native/internal/Scalar.js.map +1 -1
- package/dist/react-native/internal/Store.d.ts +32 -0
- package/dist/react-native/internal/Store.d.ts.map +1 -0
- package/dist/react-native/internal/Store.js +57 -0
- package/dist/react-native/internal/Store.js.map +1 -0
- package/dist/react-native/internal/Styles.d.ts +19 -0
- package/dist/react-native/internal/Styles.d.ts.map +1 -0
- package/dist/react-native/internal/Styles.js +35 -0
- package/dist/react-native/internal/Styles.js.map +1 -0
- package/dist/react-native/internal/Tokens.d.ts +21 -0
- package/dist/react-native/internal/Tokens.d.ts.map +1 -0
- package/dist/react-native/internal/Tokens.js +58 -0
- package/dist/react-native/internal/Tokens.js.map +1 -0
- package/dist/react-native/internal/Viewport.d.ts +6 -0
- package/dist/react-native/internal/Viewport.d.ts.map +1 -0
- package/dist/react-native/internal/Viewport.js +4 -0
- package/dist/react-native/internal/Viewport.js.map +1 -0
- package/dist/react-native/react.d.ts +102 -14
- package/dist/react-native/react.d.ts.map +1 -1
- package/dist/react-native/react.js +86 -18
- package/dist/react-native/react.js.map +1 -1
- package/dist/react-native/reanimated.d.ts +39 -0
- package/dist/react-native/reanimated.d.ts.map +1 -0
- package/dist/react-native/reanimated.js +76 -0
- package/dist/react-native/reanimated.js.map +1 -0
- package/dist/runtime/NativeContext.d.ts +10 -1
- package/dist/runtime/NativeContext.d.ts.map +1 -1
- package/dist/runtime/NativeContext.js +67 -14
- package/dist/runtime/NativeContext.js.map +1 -1
- package/dist/runtime/NativeDynamic.d.ts +3 -2
- package/dist/runtime/NativeDynamic.d.ts.map +1 -1
- package/dist/runtime/NativeDynamic.js +37 -7
- package/dist/runtime/NativeDynamic.js.map +1 -1
- package/dist/runtime/NativeStatic.d.ts +23 -0
- package/dist/runtime/NativeStatic.d.ts.map +1 -0
- package/dist/runtime/NativeStatic.js +106 -0
- package/dist/runtime/NativeStatic.js.map +1 -0
- package/dist/runtime/NativeVars.d.ts +53 -0
- package/dist/runtime/NativeVars.d.ts.map +1 -0
- package/dist/runtime/NativeVars.js +77 -0
- package/dist/runtime/NativeVars.js.map +1 -0
- package/dist/runtime/index.d.ts +4 -0
- package/dist/runtime/index.d.ts.map +1 -1
- package/dist/runtime/index.js +4 -0
- package/dist/runtime/index.js.map +1 -1
- package/dist/runtime/internal/NativeMedia.d.ts +25 -0
- package/dist/runtime/internal/NativeMedia.d.ts.map +1 -0
- package/dist/runtime/internal/NativeMedia.js +36 -0
- package/dist/runtime/internal/NativeMedia.js.map +1 -0
- package/dist/vite/index.d.ts.map +1 -1
- package/dist/vite/index.js +7 -35
- package/dist/vite/index.js.map +1 -1
- package/dist/web/Css.d.ts.map +1 -1
- package/dist/web/Css.js +31 -19
- package/dist/web/Css.js.map +1 -1
- package/dist/web/internal/Themes.d.ts +0 -2
- package/dist/web/internal/Themes.d.ts.map +1 -1
- package/dist/web/internal/Themes.js +30 -28
- package/dist/web/internal/Themes.js.map +1 -1
- package/dist/web/page.d.ts +2 -0
- package/dist/web/page.d.ts.map +1 -1
- package/native/NativeZyzz.cpp +215 -0
- package/native/NativeZyzz.h +52 -0
- package/native/ZyzzSpecJSI.h +65 -0
- package/native/android/CMakeLists.txt +8 -0
- package/native/android/ZyzzSpec-generated.cpp +50 -0
- package/native/android/ZyzzSpec.h +31 -0
- package/native/ios/ZyzzModuleProvider.mm +13 -0
- package/package.json +39 -1
- package/react-native.config.ts +14 -0
- package/src/Style.ts +11 -8
- package/src/babel/NativeJsx.ts +319 -33
- package/src/babel/index.ts +21 -3
- package/src/compiler/Graph.ts +126 -0
- package/src/compiler/Native.ts +158 -26
- package/src/compiler/Source.ts +32 -5
- package/src/compiler/internal/Configurations.ts +25 -3
- package/src/compiler/internal/Contract.ts +98 -50
- package/src/compiler/internal/Contributions.ts +7 -1
- package/src/compiler/internal/Descriptors.ts +12 -8
- package/src/compiler/internal/Dynamic.ts +4 -0
- package/src/compiler/internal/Expression.ts +2 -2
- package/src/compiler/internal/NativeBindings.ts +99 -15
- package/src/compiler/internal/NativeMedia.ts +342 -0
- package/src/compiler/internal/NativeVars.ts +231 -0
- package/src/compiler/internal/PackedStyles.ts +4 -0
- package/src/compiler/internal/Themes.ts +193 -2
- package/src/compiler/internal/Vars.ts +12 -1
- package/src/internal/Completion.ts +6 -3
- package/src/internal/Targets.ts +2 -0
- package/src/internal/Token.ts +0 -2
- package/src/internal/Value.ts +20 -0
- package/src/metro/Graph.ts +250 -50
- package/src/metro/Watch.ts +95 -10
- package/src/metro/index.ts +62 -4
- package/src/metro/transformer.ts +21 -11
- package/src/react-native/StyleSheet.ts +56 -49
- package/src/react-native/index.native.ts +10 -0
- package/src/react-native/index.ts +1 -1
- package/src/react-native/internal/Calculation.ts +159 -0
- package/src/react-native/internal/Device.ts +297 -0
- package/src/react-native/internal/NativeZyzz.ts +20 -0
- package/src/react-native/internal/Scalar.ts +86 -4
- package/src/react-native/internal/Store.ts +78 -0
- package/src/react-native/internal/Styles.ts +77 -0
- package/src/react-native/internal/Tokens.ts +85 -0
- package/src/react-native/internal/Viewport.ts +8 -0
- package/src/react-native/react.ts +218 -26
- package/src/react-native/reanimated.ts +162 -0
- package/src/runtime/NativeContext.ts +88 -17
- package/src/runtime/NativeDynamic.ts +42 -10
- package/src/runtime/NativeStatic.ts +145 -0
- package/src/runtime/NativeVars.ts +189 -0
- package/src/runtime/index.ts +6 -0
- package/src/runtime/internal/NativeMedia.ts +63 -0
- package/src/vite/index.ts +9 -42
- package/src/web/Css.ts +42 -27
- package/src/web/internal/Themes.ts +34 -57
- package/src/web/page.ts +2 -0
|
@@ -32,6 +32,8 @@ export type Alias = Call & {
|
|
|
32
32
|
|
|
33
33
|
/** Theme factory span and generated scope key. */
|
|
34
34
|
export type Call = {
|
|
35
|
+
/** Whether native defineConfig retains a typed React Provider. */
|
|
36
|
+
readonly nativeProvider?: boolean | undefined
|
|
35
37
|
readonly variableSet?: boolean | undefined
|
|
36
38
|
readonly directVariables?: boolean | undefined
|
|
37
39
|
readonly variableConfig?: boolean | undefined
|
|
@@ -102,6 +104,50 @@ export type Link = {
|
|
|
102
104
|
readonly members?: Readonly<Record<string, Link>> | undefined
|
|
103
105
|
}
|
|
104
106
|
|
|
107
|
+
/** A readonly variable argument consumed by a native React hook. */
|
|
108
|
+
export type VarsRead = {
|
|
109
|
+
/** Owning configuration fallback. */
|
|
110
|
+
readonly defaultVars: string
|
|
111
|
+
/** Exclusive source offset. */
|
|
112
|
+
readonly end: number
|
|
113
|
+
/** Stable configuration identity for graph-owned native profiles. */
|
|
114
|
+
readonly owner: string
|
|
115
|
+
/** Inclusive source offset. */
|
|
116
|
+
readonly start: number
|
|
117
|
+
/** A standalone definition that does not select a named catalog entry. */
|
|
118
|
+
readonly unnamed: boolean
|
|
119
|
+
/** Complete compatible variable alternatives. */
|
|
120
|
+
readonly vars: Readonly<Record<string, Theme.Definition>>
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
/** Resolves the variable alternatives a linked configuration or variable set exposes to native hooks. */
|
|
124
|
+
export function varsRead(
|
|
125
|
+
link: Pick<Link, 'call' | 'definition' | 'members'>,
|
|
126
|
+
): Omit<VarsRead, 'end' | 'start'> {
|
|
127
|
+
const named = link.call.options?.themes !== undefined
|
|
128
|
+
const vars = (() => {
|
|
129
|
+
if (!named) return { default: link.definition }
|
|
130
|
+
return Object.fromEntries(
|
|
131
|
+
Object.entries(link.members ?? {}).flatMap((entry) => {
|
|
132
|
+
const [key, member] = entry
|
|
133
|
+
const path = JSON.parse(key) as string[]
|
|
134
|
+
if (path.length === 1 && link.call.selection)
|
|
135
|
+
return [[path[0]!, member.definition]]
|
|
136
|
+
if (path.length === 2 && path[0] === 'themes')
|
|
137
|
+
return [[path[1]!, member.definition]]
|
|
138
|
+
return []
|
|
139
|
+
}),
|
|
140
|
+
)
|
|
141
|
+
})()
|
|
142
|
+
|
|
143
|
+
return {
|
|
144
|
+
defaultVars: named ? String(link.call.options!.defaultTheme) : 'default',
|
|
145
|
+
owner: link.call.name,
|
|
146
|
+
unnamed: !named,
|
|
147
|
+
vars,
|
|
148
|
+
}
|
|
149
|
+
}
|
|
150
|
+
|
|
105
151
|
/** Shared graph data; no filesystem or runtime evaluation is involved. */
|
|
106
152
|
export type Context = {
|
|
107
153
|
/** Canonical identifier names collected during graph validation. */
|
|
@@ -137,6 +183,7 @@ export function collect(program: Ast.Program, options: collect.Options) {
|
|
|
137
183
|
{ end: number; output: 'html' | undefined }
|
|
138
184
|
>()
|
|
139
185
|
const selections = new Set<string>()
|
|
186
|
+
const selectionUses = new Set<string>()
|
|
140
187
|
const calls: Call[] = []
|
|
141
188
|
const scripts = new Set<string>()
|
|
142
189
|
const definitions = new Map<number, Call>()
|
|
@@ -145,10 +192,12 @@ export function collect(program: Ast.Program, options: collect.Options) {
|
|
|
145
192
|
const variableImports = new Set<number>()
|
|
146
193
|
const configImports = new Set<number>()
|
|
147
194
|
const factoryImports = new Map<number, 'create' | 'define' | 'extend'>()
|
|
195
|
+
const nativeFactories = new Set<string>()
|
|
148
196
|
const configs = new Map<string, Link>()
|
|
149
197
|
const configBindings = new Map<number, Link>()
|
|
150
198
|
const factoryReferences = new Set<number>()
|
|
151
199
|
const references: Reference[] = []
|
|
200
|
+
const varsReads: VarsRead[] = []
|
|
152
201
|
|
|
153
202
|
const styles = new Map<
|
|
154
203
|
number,
|
|
@@ -166,12 +215,28 @@ export function collect(program: Ast.Program, options: collect.Options) {
|
|
|
166
215
|
for (const node of program.body) {
|
|
167
216
|
if (
|
|
168
217
|
node.type !== 'ImportDeclaration' ||
|
|
169
|
-
|
|
218
|
+
!['zyzz', 'zyzz/react-native', 'zyzz/react-native/react'].includes(
|
|
219
|
+
node.source.value,
|
|
220
|
+
) ||
|
|
170
221
|
node.importKind === 'type'
|
|
171
222
|
)
|
|
172
223
|
continue
|
|
173
224
|
|
|
174
|
-
for (const specifier of node.specifiers)
|
|
225
|
+
for (const specifier of node.specifiers) {
|
|
226
|
+
if (node.source.value !== 'zyzz') {
|
|
227
|
+
if (
|
|
228
|
+
specifier.type === 'ImportSpecifier' &&
|
|
229
|
+
specifier.importKind !== 'type' &&
|
|
230
|
+
(specifier.imported.type === 'Identifier'
|
|
231
|
+
? specifier.imported.name
|
|
232
|
+
: specifier.imported.value) === 'defineConfig'
|
|
233
|
+
) {
|
|
234
|
+
factoryImports.set(specifier.start, 'create')
|
|
235
|
+
nativeFactories.add(specifier.local.name)
|
|
236
|
+
}
|
|
237
|
+
continue
|
|
238
|
+
}
|
|
239
|
+
|
|
175
240
|
if (
|
|
176
241
|
specifier.type === 'ImportSpecifier' &&
|
|
177
242
|
specifier.importKind !== 'type' &&
|
|
@@ -208,6 +273,7 @@ export function collect(program: Ast.Program, options: collect.Options) {
|
|
|
208
273
|
factoryImports.set(specifier.start, 'define')
|
|
209
274
|
else factoryImports.set(specifier.start, 'extend')
|
|
210
275
|
}
|
|
276
|
+
}
|
|
211
277
|
}
|
|
212
278
|
|
|
213
279
|
if (
|
|
@@ -686,11 +752,20 @@ export function collect(program: Ast.Program, options: collect.Options) {
|
|
|
686
752
|
}
|
|
687
753
|
|
|
688
754
|
if (config) {
|
|
755
|
+
const nativeProvider =
|
|
756
|
+
member.type === 'Identifier' && nativeFactories.has(member.name)
|
|
757
|
+
if (nativeProvider && !options.native)
|
|
758
|
+
fail(
|
|
759
|
+
'Native defineConfig requires a native compilation target.',
|
|
760
|
+
expression,
|
|
761
|
+
)
|
|
762
|
+
|
|
689
763
|
try {
|
|
690
764
|
const link = Configurations.collect({
|
|
691
765
|
data,
|
|
692
766
|
expression,
|
|
693
767
|
name,
|
|
768
|
+
nativeProvider,
|
|
694
769
|
resolve: (node) => {
|
|
695
770
|
const link = resolve(node)
|
|
696
771
|
|
|
@@ -717,6 +792,8 @@ export function collect(program: Ast.Program, options: collect.Options) {
|
|
|
717
792
|
themes[link.call.name] = link.definition
|
|
718
793
|
|
|
719
794
|
for (const { key, id } of bindings) {
|
|
795
|
+
if (key === 'Provider' && link.call.nativeProvider) continue
|
|
796
|
+
|
|
720
797
|
if (
|
|
721
798
|
(key === 'style' || key === 'variants') &&
|
|
722
799
|
!link.call.selection &&
|
|
@@ -1046,6 +1123,15 @@ export function collect(program: Ast.Program, options: collect.Options) {
|
|
|
1046
1123
|
})
|
|
1047
1124
|
|
|
1048
1125
|
for (const { key, id } of bindings) {
|
|
1126
|
+
if (
|
|
1127
|
+
key === 'Provider' &&
|
|
1128
|
+
link.call.nativeProvider &&
|
|
1129
|
+
!link.call.initialization &&
|
|
1130
|
+
!link.call.root &&
|
|
1131
|
+
!link.call.selection
|
|
1132
|
+
)
|
|
1133
|
+
continue
|
|
1134
|
+
|
|
1049
1135
|
if (
|
|
1050
1136
|
(key === 'style' || key === 'variants') &&
|
|
1051
1137
|
!link.call.selection &&
|
|
@@ -1351,6 +1437,7 @@ export function collect(program: Ast.Program, options: collect.Options) {
|
|
|
1351
1437
|
parent: Ast.Node,
|
|
1352
1438
|
ancestors: readonly Ast.Node[],
|
|
1353
1439
|
binding: Walker.ScopeTrackerNode | null,
|
|
1440
|
+
lookup: (name: string) => Walker.ScopeTrackerNode | null,
|
|
1354
1441
|
): boolean {
|
|
1355
1442
|
const grandparent = ancestors.at(-3)
|
|
1356
1443
|
|
|
@@ -1438,6 +1525,13 @@ export function collect(program: Ast.Program, options: collect.Options) {
|
|
|
1438
1525
|
)
|
|
1439
1526
|
fail('Configuration references must follow their definition.', node)
|
|
1440
1527
|
|
|
1528
|
+
if (
|
|
1529
|
+
config.call.variableConfig &&
|
|
1530
|
+
config.call.selection &&
|
|
1531
|
+
readVars(node, parent, config, lookup)
|
|
1532
|
+
)
|
|
1533
|
+
return true
|
|
1534
|
+
|
|
1441
1535
|
// Root controls are an ordinary runtime object; any read or call is valid.
|
|
1442
1536
|
if (config.call.root) {
|
|
1443
1537
|
appearances.add(config.call.name)
|
|
@@ -1459,6 +1553,7 @@ export function collect(program: Ast.Program, options: collect.Options) {
|
|
|
1459
1553
|
|
|
1460
1554
|
if (config.call.selection) {
|
|
1461
1555
|
selections.add(config.call.name)
|
|
1556
|
+
selectionUses.add(config.call.name)
|
|
1462
1557
|
scopeApplications.set(parent.start, {
|
|
1463
1558
|
end: parent.end,
|
|
1464
1559
|
output: config.call.options?.output === 'html' ? 'html' : undefined,
|
|
@@ -1504,6 +1599,24 @@ export function collect(program: Ast.Program, options: collect.Options) {
|
|
|
1504
1599
|
path.push(key)
|
|
1505
1600
|
target = member
|
|
1506
1601
|
|
|
1602
|
+
if (
|
|
1603
|
+
path.length === 1 &&
|
|
1604
|
+
path[0] === 'Provider' &&
|
|
1605
|
+
config.call.nativeProvider &&
|
|
1606
|
+
!config.call.initialization &&
|
|
1607
|
+
!config.call.root &&
|
|
1608
|
+
!config.call.selection
|
|
1609
|
+
)
|
|
1610
|
+
return true
|
|
1611
|
+
|
|
1612
|
+
if (
|
|
1613
|
+
config.call.variableConfig &&
|
|
1614
|
+
path.length === 1 &&
|
|
1615
|
+
path[0] === 'vars' &&
|
|
1616
|
+
readVars(target, ancestors[index - 1]!, config, lookup)
|
|
1617
|
+
)
|
|
1618
|
+
return true
|
|
1619
|
+
|
|
1507
1620
|
if (
|
|
1508
1621
|
aliasReferences.has(target.start) ||
|
|
1509
1622
|
factoryReferences.has(target.start)
|
|
@@ -1562,6 +1675,7 @@ export function collect(program: Ast.Program, options: collect.Options) {
|
|
|
1562
1675
|
|
|
1563
1676
|
if (path[0] === 'themes' || path[0] === 'vars') {
|
|
1564
1677
|
selections.add(config.call.name)
|
|
1678
|
+
selectionUses.add(config.call.name)
|
|
1565
1679
|
const application = ancestors[index - 1]!
|
|
1566
1680
|
scopeApplications.set(application.start, {
|
|
1567
1681
|
end: application.end,
|
|
@@ -1623,6 +1737,7 @@ export function collect(program: Ast.Program, options: collect.Options) {
|
|
|
1623
1737
|
// A compiled selector is an ordinary runtime function, so passing or storing it is safe.
|
|
1624
1738
|
if (config.call.selection && !config.call.catalogOnly && !path.length) {
|
|
1625
1739
|
selections.add(config.call.name)
|
|
1740
|
+
selectionUses.add(config.call.name)
|
|
1626
1741
|
|
|
1627
1742
|
return true
|
|
1628
1743
|
}
|
|
@@ -1640,9 +1755,79 @@ export function collect(program: Ast.Program, options: collect.Options) {
|
|
|
1640
1755
|
if (!theme) return false
|
|
1641
1756
|
if (node.start === binding!.node.start) return true
|
|
1642
1757
|
|
|
1758
|
+
if (
|
|
1759
|
+
theme.variableSet &&
|
|
1760
|
+
readVars(
|
|
1761
|
+
node,
|
|
1762
|
+
parent,
|
|
1763
|
+
{
|
|
1764
|
+
call: theme,
|
|
1765
|
+
definition: themes[theme.name]!,
|
|
1766
|
+
},
|
|
1767
|
+
lookup,
|
|
1768
|
+
)
|
|
1769
|
+
)
|
|
1770
|
+
return true
|
|
1771
|
+
|
|
1643
1772
|
return themeReference(node, parent, ancestors, theme)
|
|
1644
1773
|
}
|
|
1645
1774
|
|
|
1775
|
+
function readVars(
|
|
1776
|
+
node: Ast.Node,
|
|
1777
|
+
parent: Ast.Node,
|
|
1778
|
+
link: Pick<Link, 'call' | 'definition' | 'members'>,
|
|
1779
|
+
lookup: (name: string) => Walker.ScopeTrackerNode | null,
|
|
1780
|
+
): boolean {
|
|
1781
|
+
if (
|
|
1782
|
+
!options.native ||
|
|
1783
|
+
parent.type !== 'CallExpression' ||
|
|
1784
|
+
parent.optional ||
|
|
1785
|
+
parent.arguments[0] !== node
|
|
1786
|
+
)
|
|
1787
|
+
return false
|
|
1788
|
+
|
|
1789
|
+
const callee = parent.callee
|
|
1790
|
+
const name =
|
|
1791
|
+
callee.type === 'Identifier'
|
|
1792
|
+
? callee.name
|
|
1793
|
+
: callee.type === 'MemberExpression' &&
|
|
1794
|
+
!callee.computed &&
|
|
1795
|
+
!callee.optional &&
|
|
1796
|
+
callee.object.type === 'Identifier' &&
|
|
1797
|
+
callee.property.type === 'Identifier' &&
|
|
1798
|
+
['useAnimatedVars', 'useVars'].includes(callee.property.name)
|
|
1799
|
+
? callee.object.name
|
|
1800
|
+
: undefined
|
|
1801
|
+
const binding = name === undefined ? undefined : lookup(name)
|
|
1802
|
+
if (
|
|
1803
|
+
binding?.type !== 'Import' ||
|
|
1804
|
+
![
|
|
1805
|
+
'zyzz/react-native',
|
|
1806
|
+
'zyzz/react-native/reanimated',
|
|
1807
|
+
'zyzz/react-native/react',
|
|
1808
|
+
].includes(binding.importNode.source.value) ||
|
|
1809
|
+
binding.importNode.importKind === 'type'
|
|
1810
|
+
)
|
|
1811
|
+
return false
|
|
1812
|
+
|
|
1813
|
+
const specifier = binding.node
|
|
1814
|
+
if (
|
|
1815
|
+
callee.type === 'Identifier'
|
|
1816
|
+
? specifier.type !== 'ImportSpecifier' ||
|
|
1817
|
+
specifier.importKind === 'type' ||
|
|
1818
|
+
!['useAnimatedVars', 'useVars'].includes(
|
|
1819
|
+
specifier.imported.type === 'Identifier'
|
|
1820
|
+
? specifier.imported.name
|
|
1821
|
+
: specifier.imported.value,
|
|
1822
|
+
)
|
|
1823
|
+
: specifier.type !== 'ImportNamespaceSpecifier'
|
|
1824
|
+
)
|
|
1825
|
+
return false
|
|
1826
|
+
|
|
1827
|
+
varsReads.push({ ...varsRead(link), end: node.end, start: node.start })
|
|
1828
|
+
return true
|
|
1829
|
+
}
|
|
1830
|
+
|
|
1646
1831
|
function themeReference(
|
|
1647
1832
|
node: Ast.Node,
|
|
1648
1833
|
parent: Ast.Node,
|
|
@@ -2023,6 +2208,8 @@ export function collect(program: Ast.Program, options: collect.Options) {
|
|
|
2023
2208
|
const entries = Object.entries(config.members ?? {}).flatMap(
|
|
2024
2209
|
([key, value]) => {
|
|
2025
2210
|
const path = JSON.parse(key) as string[]
|
|
2211
|
+
if (config.call.selection && path.length === 1)
|
|
2212
|
+
return [[path[0]!, value.definition] as const]
|
|
2026
2213
|
return (path[0] === 'themes' || path[0] === 'vars') &&
|
|
2027
2214
|
path.length === 2
|
|
2028
2215
|
? [[path[1]!, value.definition] as const]
|
|
@@ -2045,10 +2232,12 @@ export function collect(program: Ast.Program, options: collect.Options) {
|
|
|
2045
2232
|
scopeApplications,
|
|
2046
2233
|
scripts,
|
|
2047
2234
|
selections,
|
|
2235
|
+
selectionUses,
|
|
2048
2236
|
staticTokens,
|
|
2049
2237
|
styles,
|
|
2050
2238
|
themes: Object.freeze(themes),
|
|
2051
2239
|
tokens,
|
|
2240
|
+
varsReads,
|
|
2052
2241
|
}
|
|
2053
2242
|
}
|
|
2054
2243
|
|
|
@@ -2056,6 +2245,8 @@ export function collect(program: Ast.Program, options: collect.Options) {
|
|
|
2056
2245
|
export declare namespace collect {
|
|
2057
2246
|
/** Stable module namespace, independent of token values and call offsets. */
|
|
2058
2247
|
type Options = {
|
|
2248
|
+
/** Captures readonly variable arguments for native React hooks. */
|
|
2249
|
+
readonly native?: boolean | undefined
|
|
2059
2250
|
/** Encoded package/module identity from the source adapter. */
|
|
2060
2251
|
readonly staticBindings?: ReadonlySet<number> | undefined
|
|
2061
2252
|
readonly contributionCalls?: ReadonlySet<number> | undefined
|
|
@@ -477,6 +477,7 @@ export function collect(
|
|
|
477
477
|
function reference(
|
|
478
478
|
node: Extract<Ast.Node, { type: 'Identifier' | 'JSXIdentifier' }>,
|
|
479
479
|
parent: Ast.Node,
|
|
480
|
+
ancestors: readonly Ast.Node[],
|
|
480
481
|
binding: Walker.ScopeTrackerNode | null,
|
|
481
482
|
) {
|
|
482
483
|
if (binding?.type === 'Import' && imports.has(binding.node.start))
|
|
@@ -488,7 +489,17 @@ export function collect(
|
|
|
488
489
|
: node,
|
|
489
490
|
) ?? resolve(node)
|
|
490
491
|
if (!link) return false
|
|
491
|
-
|
|
492
|
+
// Reads inside functions wait for a call, so only module-scope reads must follow the declaration.
|
|
493
|
+
if (
|
|
494
|
+
link.call.start >= 0 &&
|
|
495
|
+
node.start < link.call.end &&
|
|
496
|
+
!ancestors.some(
|
|
497
|
+
(ancestor) =>
|
|
498
|
+
ancestor.type === 'ArrowFunctionExpression' ||
|
|
499
|
+
ancestor.type === 'FunctionDeclaration' ||
|
|
500
|
+
ancestor.type === 'FunctionExpression',
|
|
501
|
+
)
|
|
502
|
+
)
|
|
492
503
|
throw new InvalidError('Vars must be declared before use.', node)
|
|
493
504
|
return true
|
|
494
505
|
}
|
|
@@ -11,9 +11,12 @@ export type Properties<
|
|
|
11
11
|
styles = Record<string, unknown>,
|
|
12
12
|
> = {
|
|
13
13
|
readonly [property in keyof Literal.Properties & keyof styles]?:
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
14
|
+
// Configured tokens replace literal CSS values, so only token names are suggested.
|
|
15
|
+
| ([Token.Names<tokens, property>] extends [never]
|
|
16
|
+
? string extends Literal.Properties[property]
|
|
17
|
+
? never
|
|
18
|
+
: Literal.Properties[property]
|
|
19
|
+
: never)
|
|
17
20
|
| Token.Names<tokens, property>
|
|
18
21
|
| (string & {})
|
|
19
22
|
| number
|
package/src/internal/Targets.ts
CHANGED
|
@@ -147,6 +147,8 @@ export function copy(
|
|
|
147
147
|
export function web<name extends string>(
|
|
148
148
|
style: Style.NamedStyle<name>,
|
|
149
149
|
): Style.NamedStyle<name> {
|
|
150
|
+
if (!style.rules && !style.targets) return style
|
|
151
|
+
|
|
150
152
|
const rules = style.rules?.map((rule) => ({
|
|
151
153
|
...rule,
|
|
152
154
|
style: web(rule.style),
|
package/src/internal/Token.ts
CHANGED
|
@@ -391,8 +391,6 @@ export const complete = Symbol('zyzz.contract.complete')
|
|
|
391
391
|
export type Contract = {
|
|
392
392
|
/** Whether values belong to independent variables rather than fixed theme categories. */
|
|
393
393
|
readonly variableSet?: boolean | undefined
|
|
394
|
-
/** Custom-property spelling retained by older packed producers. */
|
|
395
|
-
readonly variableNaming?: 'legacy' | 'hashed' | undefined
|
|
396
394
|
/** Configuration-local category-to-property mappings. */
|
|
397
395
|
readonly mappings?: VariableSets.Mappings | false | undefined
|
|
398
396
|
/** Web emission mode retained by configuration-bound theme handles. */
|
package/src/internal/Value.ts
CHANGED
|
@@ -190,6 +190,26 @@ type CheckedArray<values, property extends PropertyKey, tokens> = {
|
|
|
190
190
|
>[property]
|
|
191
191
|
}
|
|
192
192
|
|
|
193
|
+
/** Lists the values a token-constrained property accepts, so mismatch diagnostics name them. */
|
|
194
|
+
export type Mismatch<tokens, property extends keyof Literal.Properties> =
|
|
195
|
+
// Resolving through a conditional prints the expected values instead of this alias's arguments.
|
|
196
|
+
tokens extends unknown
|
|
197
|
+
? Expected<
|
|
198
|
+
| Extract<Token.Names<tokens, property>, string>
|
|
199
|
+
| NumericNames<Token.Names<tokens, property>>
|
|
200
|
+
| `${string} !custom`
|
|
201
|
+
>
|
|
202
|
+
: never
|
|
203
|
+
|
|
204
|
+
// An object brand never reduces with a string literal, so the diagnostic keeps the expected values.
|
|
205
|
+
type Expected<values> = { readonly [expected]: values }
|
|
206
|
+
|
|
207
|
+
declare const expected: unique symbol
|
|
208
|
+
|
|
209
|
+
type NumericNames<names> = names extends `${infer value extends number}`
|
|
210
|
+
? value
|
|
211
|
+
: never
|
|
212
|
+
|
|
193
213
|
/** Requires tokens for properties with configured values. */
|
|
194
214
|
export type Tokens<
|
|
195
215
|
value,
|