zyzz 0.0.0 → 0.0.2
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/LICENSE +21 -0
- package/README.md +380 -0
- package/dist/Config.d.ts +170 -0
- package/dist/Config.d.ts.map +1 -0
- package/dist/Config.js +249 -0
- package/dist/Config.js.map +1 -0
- package/dist/Props.d.ts +7 -0
- package/dist/Props.d.ts.map +1 -0
- package/dist/Props.js +3 -0
- package/dist/Props.js.map +1 -0
- package/dist/Style.d.ts +167 -0
- package/dist/Style.d.ts.map +1 -0
- package/dist/Style.js +284 -0
- package/dist/Style.js.map +1 -0
- package/dist/Theme.d.ts +154 -0
- package/dist/Theme.d.ts.map +1 -0
- package/dist/Theme.js +257 -0
- package/dist/Theme.js.map +1 -0
- package/dist/babel/NativeEdits.d.ts +8 -0
- package/dist/babel/NativeEdits.d.ts.map +1 -0
- package/dist/babel/NativeEdits.js +233 -0
- package/dist/babel/NativeEdits.js.map +1 -0
- package/dist/babel/NativeJsx.d.ts +10 -0
- package/dist/babel/NativeJsx.d.ts.map +1 -0
- package/dist/babel/NativeJsx.js +204 -0
- package/dist/babel/NativeJsx.js.map +1 -0
- package/dist/babel/index.d.ts +51 -0
- package/dist/babel/index.d.ts.map +1 -0
- package/dist/babel/index.js +220 -0
- package/dist/babel/index.js.map +1 -0
- package/dist/cli/index.d.ts +3 -0
- package/dist/cli/index.d.ts.map +1 -0
- package/dist/cli/index.js +178 -0
- package/dist/cli/index.js.map +1 -0
- package/dist/compiler/Graph.d.ts +64 -0
- package/dist/compiler/Graph.d.ts.map +1 -0
- package/dist/compiler/Graph.js +1111 -0
- package/dist/compiler/Graph.js.map +1 -0
- package/dist/compiler/Native.d.ts +53 -0
- package/dist/compiler/Native.d.ts.map +1 -0
- package/dist/compiler/Native.js +617 -0
- package/dist/compiler/Native.js.map +1 -0
- package/dist/compiler/Source.d.ts +165 -0
- package/dist/compiler/Source.d.ts.map +1 -0
- package/dist/compiler/Source.js +990 -0
- package/dist/compiler/Source.js.map +1 -0
- package/dist/compiler/Transform.d.ts +57 -0
- package/dist/compiler/Transform.d.ts.map +1 -0
- package/dist/compiler/Transform.js +884 -0
- package/dist/compiler/Transform.js.map +1 -0
- package/dist/compiler/index.d.ts +13 -0
- package/dist/compiler/index.d.ts.map +1 -0
- package/dist/compiler/index.js +13 -0
- package/dist/compiler/index.js.map +1 -0
- package/dist/compiler/internal/Applications.d.ts +35 -0
- package/dist/compiler/internal/Applications.d.ts.map +1 -0
- package/dist/compiler/internal/Applications.js +248 -0
- package/dist/compiler/internal/Applications.js.map +1 -0
- package/dist/compiler/internal/AtRules.d.ts +8 -0
- package/dist/compiler/internal/AtRules.d.ts.map +1 -0
- package/dist/compiler/internal/AtRules.js +180 -0
- package/dist/compiler/internal/AtRules.js.map +1 -0
- package/dist/compiler/internal/Catalogs.d.ts +19 -0
- package/dist/compiler/internal/Catalogs.d.ts.map +1 -0
- package/dist/compiler/internal/Catalogs.js +68 -0
- package/dist/compiler/internal/Catalogs.js.map +1 -0
- package/dist/compiler/internal/ColorProfiles.d.ts +3 -0
- package/dist/compiler/internal/ColorProfiles.d.ts.map +1 -0
- package/dist/compiler/internal/ColorProfiles.js +84 -0
- package/dist/compiler/internal/ColorProfiles.js.map +1 -0
- package/dist/compiler/internal/CompositionBindings.d.ts +16 -0
- package/dist/compiler/internal/CompositionBindings.d.ts.map +1 -0
- package/dist/compiler/internal/CompositionBindings.js +89 -0
- package/dist/compiler/internal/CompositionBindings.js.map +1 -0
- package/dist/compiler/internal/Compositions.d.ts +32 -0
- package/dist/compiler/internal/Compositions.d.ts.map +1 -0
- package/dist/compiler/internal/Compositions.js +464 -0
- package/dist/compiler/internal/Compositions.js.map +1 -0
- package/dist/compiler/internal/Configurations.d.ts +21 -0
- package/dist/compiler/internal/Configurations.d.ts.map +1 -0
- package/dist/compiler/internal/Configurations.js +171 -0
- package/dist/compiler/internal/Configurations.js.map +1 -0
- package/dist/compiler/internal/Contract.d.ts +27 -0
- package/dist/compiler/internal/Contract.d.ts.map +1 -0
- package/dist/compiler/internal/Contract.js +600 -0
- package/dist/compiler/internal/Contract.js.map +1 -0
- package/dist/compiler/internal/Contributions.d.ts +54 -0
- package/dist/compiler/internal/Contributions.d.ts.map +1 -0
- package/dist/compiler/internal/Contributions.js +1109 -0
- package/dist/compiler/internal/Contributions.js.map +1 -0
- package/dist/compiler/internal/Descriptors.d.ts +15 -0
- package/dist/compiler/internal/Descriptors.d.ts.map +1 -0
- package/dist/compiler/internal/Descriptors.js +183 -0
- package/dist/compiler/internal/Descriptors.js.map +1 -0
- package/dist/compiler/internal/Dynamic.d.ts +14 -0
- package/dist/compiler/internal/Dynamic.d.ts.map +1 -0
- package/dist/compiler/internal/Dynamic.js +172 -0
- package/dist/compiler/internal/Dynamic.js.map +1 -0
- package/dist/compiler/internal/Edits.d.ts +12 -0
- package/dist/compiler/internal/Edits.d.ts.map +1 -0
- package/dist/compiler/internal/Edits.js +5 -0
- package/dist/compiler/internal/Edits.js.map +1 -0
- package/dist/compiler/internal/Expression.d.ts +12 -0
- package/dist/compiler/internal/Expression.d.ts.map +1 -0
- package/dist/compiler/internal/Expression.js +98 -0
- package/dist/compiler/internal/Expression.js.map +1 -0
- package/dist/compiler/internal/Functions.d.ts +5 -0
- package/dist/compiler/internal/Functions.d.ts.map +1 -0
- package/dist/compiler/internal/Functions.js +191 -0
- package/dist/compiler/internal/Functions.js.map +1 -0
- package/dist/compiler/internal/Identifiers.d.ts +9 -0
- package/dist/compiler/internal/Identifiers.d.ts.map +1 -0
- package/dist/compiler/internal/Identifiers.js +106 -0
- package/dist/compiler/internal/Identifiers.js.map +1 -0
- package/dist/compiler/internal/Keyframes.d.ts +5 -0
- package/dist/compiler/internal/Keyframes.d.ts.map +1 -0
- package/dist/compiler/internal/Keyframes.js +51 -0
- package/dist/compiler/internal/Keyframes.js.map +1 -0
- package/dist/compiler/internal/Namespaces.d.ts +17 -0
- package/dist/compiler/internal/Namespaces.d.ts.map +1 -0
- package/dist/compiler/internal/Namespaces.js +265 -0
- package/dist/compiler/internal/Namespaces.js.map +1 -0
- package/dist/compiler/internal/NativeBindings.d.ts +74 -0
- package/dist/compiler/internal/NativeBindings.d.ts.map +1 -0
- package/dist/compiler/internal/NativeBindings.js +117 -0
- package/dist/compiler/internal/NativeBindings.js.map +1 -0
- package/dist/compiler/internal/PackedStyles.d.ts +35 -0
- package/dist/compiler/internal/PackedStyles.d.ts.map +1 -0
- package/dist/compiler/internal/PackedStyles.js +345 -0
- package/dist/compiler/internal/PackedStyles.js.map +1 -0
- package/dist/compiler/internal/Properties.d.ts +5 -0
- package/dist/compiler/internal/Properties.d.ts.map +1 -0
- package/dist/compiler/internal/Properties.js +82 -0
- package/dist/compiler/internal/Properties.js.map +1 -0
- package/dist/compiler/internal/RecipeConditions.d.ts +41 -0
- package/dist/compiler/internal/RecipeConditions.d.ts.map +1 -0
- package/dist/compiler/internal/RecipeConditions.js +82 -0
- package/dist/compiler/internal/RecipeConditions.js.map +1 -0
- package/dist/compiler/internal/RecipePayloads.d.ts +31 -0
- package/dist/compiler/internal/RecipePayloads.d.ts.map +1 -0
- package/dist/compiler/internal/RecipePayloads.js +99 -0
- package/dist/compiler/internal/RecipePayloads.js.map +1 -0
- package/dist/compiler/internal/Recipes.d.ts +32 -0
- package/dist/compiler/internal/Recipes.d.ts.map +1 -0
- package/dist/compiler/internal/Recipes.js +339 -0
- package/dist/compiler/internal/Recipes.js.map +1 -0
- package/dist/compiler/internal/Relative.d.ts +19 -0
- package/dist/compiler/internal/Relative.d.ts.map +1 -0
- package/dist/compiler/internal/Relative.js +62 -0
- package/dist/compiler/internal/Relative.js.map +1 -0
- package/dist/compiler/internal/Scope.d.ts +10 -0
- package/dist/compiler/internal/Scope.d.ts.map +1 -0
- package/dist/compiler/internal/Scope.js +28 -0
- package/dist/compiler/internal/Scope.js.map +1 -0
- package/dist/compiler/internal/Selectors.d.ts +12 -0
- package/dist/compiler/internal/Selectors.d.ts.map +1 -0
- package/dist/compiler/internal/Selectors.js +265 -0
- package/dist/compiler/internal/Selectors.js.map +1 -0
- package/dist/compiler/internal/Static.d.ts +39 -0
- package/dist/compiler/internal/Static.d.ts.map +1 -0
- package/dist/compiler/internal/Static.js +532 -0
- package/dist/compiler/internal/Static.js.map +1 -0
- package/dist/compiler/internal/Stylesheets.d.ts +47 -0
- package/dist/compiler/internal/Stylesheets.d.ts.map +1 -0
- package/dist/compiler/internal/Stylesheets.js +272 -0
- package/dist/compiler/internal/Stylesheets.js.map +1 -0
- package/dist/compiler/internal/Syntax.d.ts +17 -0
- package/dist/compiler/internal/Syntax.d.ts.map +1 -0
- package/dist/compiler/internal/Syntax.js +19 -0
- package/dist/compiler/internal/Syntax.js.map +1 -0
- package/dist/compiler/internal/Themes.d.ts +158 -0
- package/dist/compiler/internal/Themes.d.ts.map +1 -0
- package/dist/compiler/internal/Themes.js +1169 -0
- package/dist/compiler/internal/Themes.js.map +1 -0
- package/dist/compiler/internal/Variables.d.ts +31 -0
- package/dist/compiler/internal/Variables.d.ts.map +1 -0
- package/dist/compiler/internal/Variables.js +376 -0
- package/dist/compiler/internal/Variables.js.map +1 -0
- package/dist/compiler/internal/ViewTransitions.d.ts +3 -0
- package/dist/compiler/internal/ViewTransitions.d.ts.map +1 -0
- package/dist/compiler/internal/ViewTransitions.js +68 -0
- package/dist/compiler/internal/ViewTransitions.js.map +1 -0
- package/dist/cx.d.ts +18 -0
- package/dist/cx.d.ts.map +1 -0
- package/dist/cx.js +60 -0
- package/dist/cx.js.map +1 -0
- package/dist/default.d.ts +2008 -0
- package/dist/default.d.ts.map +1 -0
- package/dist/default.js +243 -0
- package/dist/default.js.map +7 -0
- package/dist/default.js.zyzz.json +1 -0
- package/dist/index.d.ts +21 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +19 -0
- package/dist/index.js.map +1 -0
- package/dist/internal/Authoring.d.ts +26 -0
- package/dist/internal/Authoring.d.ts.map +1 -0
- package/dist/internal/Authoring.js +134 -0
- package/dist/internal/Authoring.js.map +1 -0
- package/dist/internal/Binding.d.ts +64 -0
- package/dist/internal/Binding.d.ts.map +1 -0
- package/dist/internal/Binding.js +27 -0
- package/dist/internal/Binding.js.map +1 -0
- package/dist/internal/BindingDomains.d.ts +11 -0
- package/dist/internal/BindingDomains.d.ts.map +1 -0
- package/dist/internal/BindingDomains.js +459 -0
- package/dist/internal/BindingDomains.js.map +1 -0
- package/dist/internal/Cascade.d.ts +45 -0
- package/dist/internal/Cascade.d.ts.map +1 -0
- package/dist/internal/Cascade.js +165 -0
- package/dist/internal/Cascade.js.map +1 -0
- package/dist/internal/Compound.d.ts +132 -0
- package/dist/internal/Compound.d.ts.map +1 -0
- package/dist/internal/Compound.js +2 -0
- package/dist/internal/Compound.js.map +1 -0
- package/dist/internal/Condition.d.ts +33 -0
- package/dist/internal/Condition.d.ts.map +1 -0
- package/dist/internal/Condition.js +180 -0
- package/dist/internal/Condition.js.map +1 -0
- package/dist/internal/Corner.d.ts +9 -0
- package/dist/internal/Corner.d.ts.map +1 -0
- package/dist/internal/Corner.js +14 -0
- package/dist/internal/Corner.js.map +1 -0
- package/dist/internal/FunctionSyntax.d.ts +27 -0
- package/dist/internal/FunctionSyntax.d.ts.map +1 -0
- package/dist/internal/FunctionSyntax.js +91 -0
- package/dist/internal/FunctionSyntax.js.map +1 -0
- package/dist/internal/FunctionValue.d.ts +19 -0
- package/dist/internal/FunctionValue.d.ts.map +1 -0
- package/dist/internal/FunctionValue.js +2 -0
- package/dist/internal/FunctionValue.js.map +1 -0
- package/dist/internal/Geometry.d.ts +8 -0
- package/dist/internal/Geometry.d.ts.map +1 -0
- package/dist/internal/Geometry.js +2 -0
- package/dist/internal/Geometry.js.map +1 -0
- package/dist/internal/Grid.d.ts +15 -0
- package/dist/internal/Grid.d.ts.map +1 -0
- package/dist/internal/Grid.js +2 -0
- package/dist/internal/Grid.js.map +1 -0
- package/dist/internal/Identifier.d.ts +15 -0
- package/dist/internal/Identifier.d.ts.map +1 -0
- package/dist/internal/Identifier.js +2 -0
- package/dist/internal/Identifier.js.map +1 -0
- package/dist/internal/Identity.d.ts +16 -0
- package/dist/internal/Identity.d.ts.map +1 -0
- package/dist/internal/Identity.js +78 -0
- package/dist/internal/Identity.js.map +1 -0
- package/dist/internal/Lexical.d.ts +89 -0
- package/dist/internal/Lexical.d.ts.map +1 -0
- package/dist/internal/Lexical.js +15 -0
- package/dist/internal/Lexical.js.map +1 -0
- package/dist/internal/Literal.d.ts +3459 -0
- package/dist/internal/Literal.d.ts.map +1 -0
- package/dist/internal/Literal.js +3371 -0
- package/dist/internal/Literal.js.map +1 -0
- package/dist/internal/NativeProperties.d.ts +596 -0
- package/dist/internal/NativeProperties.d.ts.map +1 -0
- package/dist/internal/NativeProperties.js +2 -0
- package/dist/internal/NativeProperties.js.map +1 -0
- package/dist/internal/Numeric.d.ts +23 -0
- package/dist/internal/Numeric.d.ts.map +1 -0
- package/dist/internal/Numeric.js +2 -0
- package/dist/internal/Numeric.js.map +1 -0
- package/dist/internal/Query.d.ts +15 -0
- package/dist/internal/Query.d.ts.map +1 -0
- package/dist/internal/Query.js +58 -0
- package/dist/internal/Query.js.map +1 -0
- package/dist/internal/Recipe.d.ts +17 -0
- package/dist/internal/Recipe.d.ts.map +1 -0
- package/dist/internal/Recipe.js +2 -0
- package/dist/internal/Recipe.js.map +1 -0
- package/dist/internal/RuleReference.d.ts +23 -0
- package/dist/internal/RuleReference.d.ts.map +1 -0
- package/dist/internal/RuleReference.js +65 -0
- package/dist/internal/RuleReference.js.map +1 -0
- package/dist/internal/Scheme.d.ts +12 -0
- package/dist/internal/Scheme.d.ts.map +1 -0
- package/dist/internal/Scheme.js +16 -0
- package/dist/internal/Scheme.js.map +1 -0
- package/dist/internal/Shorthands.d.ts +20 -0
- package/dist/internal/Shorthands.d.ts.map +1 -0
- package/dist/internal/Shorthands.js +49 -0
- package/dist/internal/Shorthands.js.map +1 -0
- package/dist/internal/Targets.d.ts +43 -0
- package/dist/internal/Targets.d.ts.map +1 -0
- package/dist/internal/Targets.js +60 -0
- package/dist/internal/Targets.js.map +1 -0
- package/dist/internal/Token.d.ts +104 -0
- package/dist/internal/Token.d.ts.map +1 -0
- package/dist/internal/Token.js +162 -0
- package/dist/internal/Token.js.map +1 -0
- package/dist/internal/Tuple.d.ts +23 -0
- package/dist/internal/Tuple.d.ts.map +1 -0
- package/dist/internal/Tuple.js +2 -0
- package/dist/internal/Tuple.js.map +1 -0
- package/dist/internal/Value.d.ts +74 -0
- package/dist/internal/Value.d.ts.map +1 -0
- package/dist/internal/Value.js +60 -0
- package/dist/internal/Value.js.map +1 -0
- package/dist/metro/Graph.d.ts +8 -0
- package/dist/metro/Graph.d.ts.map +1 -0
- package/dist/metro/Graph.js +63 -0
- package/dist/metro/Graph.js.map +1 -0
- package/dist/metro/Watch.d.ts +21 -0
- package/dist/metro/Watch.d.ts.map +1 -0
- package/dist/metro/Watch.js +51 -0
- package/dist/metro/Watch.js.map +1 -0
- package/dist/metro/index.d.ts +30 -0
- package/dist/metro/index.d.ts.map +1 -0
- package/dist/metro/index.js +52 -0
- package/dist/metro/index.js.map +1 -0
- package/dist/metro/transformer.d.ts +21 -0
- package/dist/metro/transformer.d.ts.map +1 -0
- package/dist/metro/transformer.js +71 -0
- package/dist/metro/transformer.js.map +1 -0
- package/dist/next/index.d.ts +18 -0
- package/dist/next/index.d.ts.map +1 -0
- package/dist/next/index.js +92 -0
- package/dist/next/index.js.map +1 -0
- package/dist/next/loader.d.ts +16 -0
- package/dist/next/loader.d.ts.map +1 -0
- package/dist/next/loader.js +282 -0
- package/dist/next/loader.js.map +1 -0
- package/dist/node/Host.d.ts +80 -0
- package/dist/node/Host.d.ts.map +1 -0
- package/dist/node/Host.js +882 -0
- package/dist/node/Host.js.map +1 -0
- package/dist/node/index.d.ts +7 -0
- package/dist/node/index.d.ts.map +1 -0
- package/dist/node/index.js +7 -0
- package/dist/node/index.js.map +1 -0
- package/dist/react-native/Host.d.ts +76 -0
- package/dist/react-native/Host.d.ts.map +1 -0
- package/dist/react-native/Host.js +209 -0
- package/dist/react-native/Host.js.map +1 -0
- package/dist/react-native/StyleSheet.d.ts +226 -0
- package/dist/react-native/StyleSheet.d.ts.map +1 -0
- package/dist/react-native/StyleSheet.js +606 -0
- package/dist/react-native/StyleSheet.js.map +1 -0
- package/dist/react-native/Variants.d.ts +38 -0
- package/dist/react-native/Variants.d.ts.map +1 -0
- package/dist/react-native/Variants.js +66 -0
- package/dist/react-native/Variants.js.map +1 -0
- package/dist/react-native/index.d.ts +8 -0
- package/dist/react-native/index.d.ts.map +1 -0
- package/dist/react-native/index.js +8 -0
- package/dist/react-native/index.js.map +1 -0
- package/dist/react-native/internal/Color.d.ts +7 -0
- package/dist/react-native/internal/Color.d.ts.map +1 -0
- package/dist/react-native/internal/Color.js +93 -0
- package/dist/react-native/internal/Color.js.map +1 -0
- package/dist/react-native/internal/NativeSchema.d.ts +5138 -0
- package/dist/react-native/internal/NativeSchema.d.ts.map +1 -0
- package/dist/react-native/internal/NativeSchema.js +3097 -0
- package/dist/react-native/internal/NativeSchema.js.map +1 -0
- package/dist/react-native/internal/Scalar.d.ts +95 -0
- package/dist/react-native/internal/Scalar.d.ts.map +1 -0
- package/dist/react-native/internal/Scalar.js +199 -0
- package/dist/react-native/internal/Scalar.js.map +1 -0
- package/dist/react-native/internal/Values.d.ts +5 -0
- package/dist/react-native/internal/Values.d.ts.map +1 -0
- package/dist/react-native/internal/Values.js +65 -0
- package/dist/react-native/internal/Values.js.map +1 -0
- package/dist/react-native/react.d.ts +22 -0
- package/dist/react-native/react.d.ts.map +1 -0
- package/dist/react-native/react.js +26 -0
- package/dist/react-native/react.js.map +1 -0
- package/dist/reset.css +244 -0
- package/dist/runtime/Appearance.d.ts +55 -0
- package/dist/runtime/Appearance.d.ts.map +1 -0
- package/dist/runtime/Appearance.js +84 -0
- package/dist/runtime/Appearance.js.map +1 -0
- package/dist/runtime/Composition.d.ts +46 -0
- package/dist/runtime/Composition.d.ts.map +1 -0
- package/dist/runtime/Composition.js +52 -0
- package/dist/runtime/Composition.js.map +1 -0
- package/dist/runtime/CompositionHtml.d.ts +15 -0
- package/dist/runtime/CompositionHtml.d.ts.map +1 -0
- package/dist/runtime/CompositionHtml.js +20 -0
- package/dist/runtime/CompositionHtml.js.map +1 -0
- package/dist/runtime/ConditionalRecipe.d.ts +30 -0
- package/dist/runtime/ConditionalRecipe.d.ts.map +1 -0
- package/dist/runtime/ConditionalRecipe.js +39 -0
- package/dist/runtime/ConditionalRecipe.js.map +1 -0
- package/dist/runtime/Dynamic.d.ts +19 -0
- package/dist/runtime/Dynamic.d.ts.map +1 -0
- package/dist/runtime/Dynamic.js +22 -0
- package/dist/runtime/Dynamic.js.map +1 -0
- package/dist/runtime/Html.d.ts +32 -0
- package/dist/runtime/Html.d.ts.map +1 -0
- package/dist/runtime/Html.js +63 -0
- package/dist/runtime/Html.js.map +1 -0
- package/dist/runtime/Native.d.ts +48 -0
- package/dist/runtime/Native.d.ts.map +1 -0
- package/dist/runtime/Native.js +78 -0
- package/dist/runtime/Native.js.map +1 -0
- package/dist/runtime/NativeContext.d.ts +17 -0
- package/dist/runtime/NativeContext.d.ts.map +1 -0
- package/dist/runtime/NativeContext.js +47 -0
- package/dist/runtime/NativeContext.js.map +1 -0
- package/dist/runtime/NativeDynamic.d.ts +47 -0
- package/dist/runtime/NativeDynamic.d.ts.map +1 -0
- package/dist/runtime/NativeDynamic.js +141 -0
- package/dist/runtime/NativeDynamic.js.map +1 -0
- package/dist/runtime/PayloadRecipe.d.ts +22 -0
- package/dist/runtime/PayloadRecipe.d.ts.map +1 -0
- package/dist/runtime/PayloadRecipe.js +59 -0
- package/dist/runtime/PayloadRecipe.js.map +1 -0
- package/dist/runtime/Props.d.ts +21 -0
- package/dist/runtime/Props.d.ts.map +1 -0
- package/dist/runtime/Props.js +17 -0
- package/dist/runtime/Props.js.map +1 -0
- package/dist/runtime/Recipe.d.ts +52 -0
- package/dist/runtime/Recipe.d.ts.map +1 -0
- package/dist/runtime/Recipe.js +30 -0
- package/dist/runtime/Recipe.js.map +1 -0
- package/dist/runtime/Selection.d.ts +31 -0
- package/dist/runtime/Selection.d.ts.map +1 -0
- package/dist/runtime/Selection.js +30 -0
- package/dist/runtime/Selection.js.map +1 -0
- package/dist/runtime/Variable.d.ts +6 -0
- package/dist/runtime/Variable.d.ts.map +1 -0
- package/dist/runtime/Variable.js +10 -0
- package/dist/runtime/Variable.js.map +1 -0
- package/dist/runtime/index.d.ts +33 -0
- package/dist/runtime/index.d.ts.map +1 -0
- package/dist/runtime/index.js +33 -0
- package/dist/runtime/index.js.map +1 -0
- package/dist/styleFunction.d.ts +72 -0
- package/dist/styleFunction.d.ts.map +1 -0
- package/dist/styleFunction.js +18 -0
- package/dist/styleFunction.js.map +1 -0
- package/dist/themes/LICENSE.tailwind +21 -0
- package/dist/variable.d.ts +50 -0
- package/dist/variable.d.ts.map +1 -0
- package/dist/variable.js +20 -0
- package/dist/variable.js.map +1 -0
- package/dist/variants.d.ts +84 -0
- package/dist/variants.d.ts.map +1 -0
- package/dist/variants.js +21 -0
- package/dist/variants.js.map +1 -0
- package/dist/vite/index.d.ts +24 -0
- package/dist/vite/index.d.ts.map +1 -0
- package/dist/vite/index.js +1089 -0
- package/dist/vite/index.js.map +1 -0
- package/dist/web/Css.d.ts +81 -0
- package/dist/web/Css.d.ts.map +1 -0
- package/dist/web/Css.js +593 -0
- package/dist/web/Css.js.map +1 -0
- package/dist/web/colorProfile.d.ts +28 -0
- package/dist/web/colorProfile.d.ts.map +1 -0
- package/dist/web/colorProfile.js +8 -0
- package/dist/web/colorProfile.js.map +1 -0
- package/dist/web/counterStyle.d.ts +48 -0
- package/dist/web/counterStyle.d.ts.map +1 -0
- package/dist/web/counterStyle.js +8 -0
- package/dist/web/counterStyle.js.map +1 -0
- package/dist/web/cssFunction.d.ts +80 -0
- package/dist/web/cssFunction.d.ts.map +1 -0
- package/dist/web/cssFunction.js +18 -0
- package/dist/web/cssFunction.js.map +1 -0
- package/dist/web/customMedia.d.ts +12 -0
- package/dist/web/customMedia.d.ts.map +1 -0
- package/dist/web/customMedia.js +7 -0
- package/dist/web/customMedia.js.map +1 -0
- package/dist/web/fontFace.d.ts +26 -0
- package/dist/web/fontFace.d.ts.map +1 -0
- package/dist/web/fontFace.js +7 -0
- package/dist/web/fontFace.js.map +1 -0
- package/dist/web/fontFeatureValues.d.ts +40 -0
- package/dist/web/fontFeatureValues.d.ts.map +1 -0
- package/dist/web/fontFeatureValues.js +7 -0
- package/dist/web/fontFeatureValues.js.map +1 -0
- package/dist/web/fontPaletteValues.d.ts +21 -0
- package/dist/web/fontPaletteValues.d.ts.map +1 -0
- package/dist/web/fontPaletteValues.js +9 -0
- package/dist/web/fontPaletteValues.js.map +1 -0
- package/dist/web/global.d.ts +19 -0
- package/dist/web/global.d.ts.map +1 -0
- package/dist/web/global.js +6 -0
- package/dist/web/global.js.map +1 -0
- package/dist/web/importCss.d.ts +18 -0
- package/dist/web/importCss.d.ts.map +1 -0
- package/dist/web/importCss.js +7 -0
- package/dist/web/importCss.js.map +1 -0
- package/dist/web/index.d.ts +22 -0
- package/dist/web/index.d.ts.map +1 -0
- package/dist/web/index.js +22 -0
- package/dist/web/index.js.map +1 -0
- package/dist/web/internal/Block.d.ts +18 -0
- package/dist/web/internal/Block.d.ts.map +1 -0
- package/dist/web/internal/Block.js +13 -0
- package/dist/web/internal/Block.js.map +1 -0
- package/dist/web/internal/ClassName.d.ts +19 -0
- package/dist/web/internal/ClassName.d.ts.map +1 -0
- package/dist/web/internal/ClassName.js +77 -0
- package/dist/web/internal/ClassName.js.map +1 -0
- package/dist/web/internal/Context.d.ts +11 -0
- package/dist/web/internal/Context.d.ts.map +1 -0
- package/dist/web/internal/Context.js +2 -0
- package/dist/web/internal/Context.js.map +1 -0
- package/dist/web/internal/Contributions.d.ts +70 -0
- package/dist/web/internal/Contributions.d.ts.map +1 -0
- package/dist/web/internal/Contributions.js +109 -0
- package/dist/web/internal/Contributions.js.map +1 -0
- package/dist/web/internal/Namespace.d.ts +13 -0
- package/dist/web/internal/Namespace.d.ts.map +1 -0
- package/dist/web/internal/Namespace.js +13 -0
- package/dist/web/internal/Namespace.js.map +1 -0
- package/dist/web/internal/Themes.d.ts +13 -0
- package/dist/web/internal/Themes.d.ts.map +1 -0
- package/dist/web/internal/Themes.js +96 -0
- package/dist/web/internal/Themes.js.map +1 -0
- package/dist/web/keyframes.d.ts +14 -0
- package/dist/web/keyframes.d.ts.map +1 -0
- package/dist/web/keyframes.js +8 -0
- package/dist/web/keyframes.js.map +1 -0
- package/dist/web/layers.d.ts +4 -0
- package/dist/web/layers.d.ts.map +1 -0
- package/dist/web/layers.js +7 -0
- package/dist/web/layers.js.map +1 -0
- package/dist/web/namespace.d.ts +14 -0
- package/dist/web/namespace.d.ts.map +1 -0
- package/dist/web/namespace.js +7 -0
- package/dist/web/namespace.js.map +1 -0
- package/dist/web/page.d.ts +38 -0
- package/dist/web/page.d.ts.map +1 -0
- package/dist/web/page.js +7 -0
- package/dist/web/page.js.map +1 -0
- package/dist/web/positionTry.d.ts +14 -0
- package/dist/web/positionTry.d.ts.map +1 -0
- package/dist/web/positionTry.js +9 -0
- package/dist/web/positionTry.js.map +1 -0
- package/dist/web/property.d.ts +24 -0
- package/dist/web/property.d.ts.map +1 -0
- package/dist/web/property.js +7 -0
- package/dist/web/property.js.map +1 -0
- package/dist/web/viewTransition.d.ts +29 -0
- package/dist/web/viewTransition.d.ts.map +1 -0
- package/dist/web/viewTransition.js +7 -0
- package/dist/web/viewTransition.js.map +1 -0
- package/package.json +136 -10
- package/src/Config.ts +690 -0
- package/src/Props.ts +8 -0
- package/src/Style.ts +748 -0
- package/src/Theme.ts +713 -0
- package/src/babel/NativeEdits.ts +273 -0
- package/src/babel/NativeJsx.ts +260 -0
- package/src/babel/index.ts +332 -0
- package/src/cli/index.ts +196 -0
- package/src/compiler/Graph.ts +1586 -0
- package/src/compiler/Native.ts +801 -0
- package/src/compiler/Source.ts +1550 -0
- package/src/compiler/Transform.ts +1235 -0
- package/src/compiler/index.ts +12 -0
- package/src/compiler/internal/Applications.ts +378 -0
- package/src/compiler/internal/AtRules.ts +202 -0
- package/src/compiler/internal/Catalogs.ts +114 -0
- package/src/compiler/internal/ColorProfiles.ts +93 -0
- package/src/compiler/internal/CompositionBindings.ts +120 -0
- package/src/compiler/internal/Compositions.ts +629 -0
- package/src/compiler/internal/Configurations.ts +244 -0
- package/src/compiler/internal/Contract.ts +846 -0
- package/src/compiler/internal/Contributions.ts +1507 -0
- package/src/compiler/internal/Descriptors.ts +238 -0
- package/src/compiler/internal/Dynamic.ts +266 -0
- package/src/compiler/internal/Edits.ts +13 -0
- package/src/compiler/internal/Expression.ts +135 -0
- package/src/compiler/internal/Functions.ts +206 -0
- package/src/compiler/internal/Identifiers.ts +124 -0
- package/src/compiler/internal/Keyframes.ts +62 -0
- package/src/compiler/internal/Namespaces.ts +296 -0
- package/src/compiler/internal/NativeBindings.ts +151 -0
- package/src/compiler/internal/PackedStyles.ts +464 -0
- package/src/compiler/internal/Properties.ts +121 -0
- package/src/compiler/internal/RecipeConditions.ts +139 -0
- package/src/compiler/internal/RecipePayloads.ts +132 -0
- package/src/compiler/internal/Recipes.ts +531 -0
- package/src/compiler/internal/Relative.ts +87 -0
- package/src/compiler/internal/Scope.ts +36 -0
- package/src/compiler/internal/Selectors.ts +334 -0
- package/src/compiler/internal/Static.ts +783 -0
- package/src/compiler/internal/Stylesheets.ts +361 -0
- package/src/compiler/internal/Syntax.ts +31 -0
- package/src/compiler/internal/Themes.ts +1794 -0
- package/src/compiler/internal/Variables.ts +497 -0
- package/src/compiler/internal/ViewTransitions.ts +82 -0
- package/src/cx.ts +98 -0
- package/src/default.ts +484 -0
- package/src/index.ts +20 -0
- package/src/internal/Authoring.ts +199 -0
- package/src/internal/Binding.ts +187 -0
- package/src/internal/BindingDomains.ts +458 -0
- package/src/internal/Cascade.ts +165 -0
- package/src/internal/Compound.ts +522 -0
- package/src/internal/Condition.ts +283 -0
- package/src/internal/Corner.ts +17 -0
- package/src/internal/FunctionSyntax.ts +271 -0
- package/src/internal/FunctionValue.ts +96 -0
- package/src/internal/Geometry.ts +30 -0
- package/src/internal/Grid.ts +67 -0
- package/src/internal/Identifier.ts +14 -0
- package/src/internal/Identity.ts +89 -0
- package/src/internal/Lexical.ts +202 -0
- package/src/internal/Literal.ts +3820 -0
- package/src/internal/NativeProperties.ts +936 -0
- package/src/internal/Numeric.ts +77 -0
- package/src/internal/Query.ts +87 -0
- package/src/internal/Recipe.ts +17 -0
- package/src/internal/RuleReference.ts +102 -0
- package/src/internal/Scheme.ts +20 -0
- package/src/internal/Shorthands.ts +120 -0
- package/src/internal/Targets.ts +162 -0
- package/src/internal/Token.ts +380 -0
- package/src/internal/Tuple.ts +29 -0
- package/src/internal/Value.ts +320 -0
- package/src/metro/Graph.ts +78 -0
- package/src/metro/Watch.ts +88 -0
- package/src/metro/index.ts +99 -0
- package/src/metro/transformer.ts +97 -0
- package/src/next/index.ts +114 -0
- package/src/next/loader.ts +369 -0
- package/src/node/Host.ts +1204 -0
- package/src/node/index.ts +6 -0
- package/src/react-native/Host.ts +289 -0
- package/src/react-native/StyleSheet.ts +1084 -0
- package/src/react-native/Variants.ts +122 -0
- package/src/react-native/index.ts +7 -0
- package/src/react-native/internal/Color.ts +110 -0
- package/src/react-native/internal/NativeSchema.ts +3096 -0
- package/src/react-native/internal/Scalar.ts +253 -0
- package/src/react-native/internal/Values.ts +87 -0
- package/src/react-native/react.ts +47 -0
- package/src/reset.css +244 -0
- package/src/runtime/Appearance.ts +155 -0
- package/src/runtime/Composition.ts +87 -0
- package/src/runtime/CompositionHtml.ts +38 -0
- package/src/runtime/ConditionalRecipe.ts +70 -0
- package/src/runtime/Dynamic.ts +51 -0
- package/src/runtime/Html.ts +91 -0
- package/src/runtime/Native.ts +144 -0
- package/src/runtime/NativeContext.ts +74 -0
- package/src/runtime/NativeDynamic.ts +246 -0
- package/src/runtime/PayloadRecipe.ts +96 -0
- package/src/runtime/Props.ts +33 -0
- package/src/runtime/Recipe.ts +74 -0
- package/src/runtime/Selection.ts +82 -0
- package/src/runtime/Variable.ts +15 -0
- package/src/runtime/index.ts +45 -0
- package/src/styleFunction.ts +138 -0
- package/src/themes/LICENSE.tailwind +21 -0
- package/src/variable.ts +105 -0
- package/src/variants.ts +218 -0
- package/src/vite/index.ts +1473 -0
- package/src/web/Css.ts +801 -0
- package/src/web/colorProfile.ts +60 -0
- package/src/web/counterStyle.ts +82 -0
- package/src/web/cssFunction.ts +181 -0
- package/src/web/customMedia.ts +16 -0
- package/src/web/fontFace.ts +41 -0
- package/src/web/fontFeatureValues.ts +79 -0
- package/src/web/fontPaletteValues.ts +42 -0
- package/src/web/global.ts +39 -0
- package/src/web/importCss.ts +23 -0
- package/src/web/index.ts +22 -0
- package/src/web/internal/Block.ts +29 -0
- package/src/web/internal/ClassName.ts +112 -0
- package/src/web/internal/Context.ts +16 -0
- package/src/web/internal/Contributions.ts +219 -0
- package/src/web/internal/Namespace.ts +21 -0
- package/src/web/internal/Themes.ts +133 -0
- package/src/web/keyframes.ts +43 -0
- package/src/web/layers.ts +6 -0
- package/src/web/namespace.ts +19 -0
- package/src/web/page.ts +140 -0
- package/src/web/positionTry.ts +71 -0
- package/src/web/property.ts +35 -0
- package/src/web/viewTransition.ts +89 -0
|
@@ -0,0 +1,1507 @@
|
|
|
1
|
+
/** Extracts module-level stylesheet effects without evaluating application code. @module */
|
|
2
|
+
import * as Identity from '../../internal/Identity.js'
|
|
3
|
+
import type * as Ast from '@oxc-project/types'
|
|
4
|
+
import type * as Block from '../../web/internal/Block.js'
|
|
5
|
+
import * as Condition from '../../internal/Condition.js'
|
|
6
|
+
import type * as Css from '../../web/Css.js'
|
|
7
|
+
import type { cssFunction } from '../../web/cssFunction.js'
|
|
8
|
+
import * as Descriptors from './Descriptors.js'
|
|
9
|
+
import * as Expression from './Expression.js'
|
|
10
|
+
import * as Functions from './Functions.js'
|
|
11
|
+
import * as FunctionSyntax from '../../internal/FunctionSyntax.js'
|
|
12
|
+
import * as Identifiers from './Identifiers.js'
|
|
13
|
+
import * as Keyframes from './Keyframes.js'
|
|
14
|
+
import * as Lexical from '../../internal/Lexical.js'
|
|
15
|
+
import * as Lightning from 'lightningcss'
|
|
16
|
+
import * as Literal from '../../internal/Literal.js'
|
|
17
|
+
import * as Properties from './Properties.js'
|
|
18
|
+
import * as RuleReference from '../../internal/RuleReference.js'
|
|
19
|
+
import type * as Scope from './Scope.js'
|
|
20
|
+
import * as Style from '../../Style.js'
|
|
21
|
+
import * as Theme from '../../Theme.js'
|
|
22
|
+
import * as Themes from './Themes.js'
|
|
23
|
+
import type * as Token from '../../internal/Token.js'
|
|
24
|
+
import * as Walker from 'oxc-walker'
|
|
25
|
+
|
|
26
|
+
type Kind =
|
|
27
|
+
| 'importCss'
|
|
28
|
+
| 'namespace'
|
|
29
|
+
| 'fontFeatureValues'
|
|
30
|
+
| 'page'
|
|
31
|
+
| 'property'
|
|
32
|
+
| 'viewTransition'
|
|
33
|
+
| 'fontFace'
|
|
34
|
+
| 'global'
|
|
35
|
+
| 'keyframes'
|
|
36
|
+
| 'layers'
|
|
37
|
+
| RuleReference.Kind
|
|
38
|
+
const named = [
|
|
39
|
+
'cssFunction',
|
|
40
|
+
'customMedia',
|
|
41
|
+
'colorProfile',
|
|
42
|
+
'counterStyle',
|
|
43
|
+
'fontPaletteValues',
|
|
44
|
+
'keyframes',
|
|
45
|
+
'positionTry',
|
|
46
|
+
]
|
|
47
|
+
/** Stylesheet factory exports recognized by source and graph linking. */
|
|
48
|
+
export const factories: readonly string[] = [
|
|
49
|
+
'importCss',
|
|
50
|
+
'namespace',
|
|
51
|
+
'fontFace',
|
|
52
|
+
'fontFeatureValues',
|
|
53
|
+
'global',
|
|
54
|
+
'layers',
|
|
55
|
+
'page',
|
|
56
|
+
'property',
|
|
57
|
+
'viewTransition',
|
|
58
|
+
...named,
|
|
59
|
+
]
|
|
60
|
+
|
|
61
|
+
/** Source-owned factory replacement and optional animation identity. */
|
|
62
|
+
export type Call = {
|
|
63
|
+
/** CSS function signature populated by literal extraction. */
|
|
64
|
+
readonly function?: NonNullable<Themes.Call['function']> | undefined
|
|
65
|
+
readonly start: number
|
|
66
|
+
readonly end: number
|
|
67
|
+
readonly kind: Kind
|
|
68
|
+
readonly context?: Ast.Node | undefined
|
|
69
|
+
readonly argument: Ast.Node
|
|
70
|
+
readonly name?: string | undefined
|
|
71
|
+
readonly binding?: number | undefined
|
|
72
|
+
readonly exported?: boolean | undefined
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
/** Collects lexical macro calls and animation references. */
|
|
76
|
+
export function scan(
|
|
77
|
+
program: Ast.Program,
|
|
78
|
+
scope: Scope.Tracker,
|
|
79
|
+
namespace: string,
|
|
80
|
+
links: Readonly<Record<string, Themes.Link>> = {},
|
|
81
|
+
factoryImports: Readonly<Record<string, string>> = {},
|
|
82
|
+
) {
|
|
83
|
+
const imports = new Map<number, Kind>()
|
|
84
|
+
|
|
85
|
+
for (const node of program.body)
|
|
86
|
+
if (node.type === 'ImportDeclaration' && node.importKind !== 'type')
|
|
87
|
+
for (const specifier of node.specifiers)
|
|
88
|
+
if (
|
|
89
|
+
specifier.type === 'ImportSpecifier' &&
|
|
90
|
+
specifier.importKind !== 'type'
|
|
91
|
+
) {
|
|
92
|
+
const imported =
|
|
93
|
+
specifier.imported.type === 'Identifier'
|
|
94
|
+
? specifier.imported.name
|
|
95
|
+
: specifier.imported.value
|
|
96
|
+
const name =
|
|
97
|
+
node.source.value === 'zyzz/web'
|
|
98
|
+
? imported
|
|
99
|
+
: factoryImports[specifier.local.name]
|
|
100
|
+
if (name && factories.includes(name))
|
|
101
|
+
imports.set(specifier.start, name as Kind)
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
const exported: Record<string, Themes.Link> = Object.create(null)
|
|
105
|
+
const linkedNames = new Map<string, Themes.Link>()
|
|
106
|
+
const imported = new Map<number, string>()
|
|
107
|
+
|
|
108
|
+
for (const node of program.body)
|
|
109
|
+
if (node.type === 'ImportDeclaration')
|
|
110
|
+
for (const specifier of node.specifiers) {
|
|
111
|
+
const link = links[specifier.local.name]
|
|
112
|
+
if (link?.kind === 'animation' || link?.kind === 'rule-reference') {
|
|
113
|
+
imported.set(specifier.start, link.call.name)
|
|
114
|
+
linkedNames.set(specifier.local.name, link)
|
|
115
|
+
}
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
const calls: Call[] = []
|
|
119
|
+
const functionInputs: {
|
|
120
|
+
name: string
|
|
121
|
+
signature: NonNullable<Themes.Call['function']>
|
|
122
|
+
values: readonly (string | undefined)[]
|
|
123
|
+
node: Extract<Ast.Node, { type: 'CallExpression' }>
|
|
124
|
+
}[] = []
|
|
125
|
+
const bindings = new Map<number, Call>()
|
|
126
|
+
const references = new Map<number, string>()
|
|
127
|
+
const queryKeys = new Map<number, string>()
|
|
128
|
+
const used = new Set<string>()
|
|
129
|
+
const undefinedValues = new Set<number>()
|
|
130
|
+
const ancestors: Ast.Node[] = []
|
|
131
|
+
|
|
132
|
+
function kind(node: Ast.Node): Kind | undefined {
|
|
133
|
+
if (node.type === 'Identifier') {
|
|
134
|
+
const binding = scope.getDeclaration(node.name)
|
|
135
|
+
const name =
|
|
136
|
+
binding?.type === 'Import' ? imports.get(binding.node.start) : undefined
|
|
137
|
+
|
|
138
|
+
return name
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
return undefined
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
if (imports.size || imported.size)
|
|
145
|
+
Walker.walk(program, {
|
|
146
|
+
scopeTracker: scope,
|
|
147
|
+
enter(node, parent) {
|
|
148
|
+
ancestors.push(node)
|
|
149
|
+
|
|
150
|
+
if (
|
|
151
|
+
node.type === 'Identifier' &&
|
|
152
|
+
node.name === 'undefined' &&
|
|
153
|
+
!scope.getDeclaration(node.name)
|
|
154
|
+
)
|
|
155
|
+
undefinedValues.add(node.start)
|
|
156
|
+
|
|
157
|
+
if (
|
|
158
|
+
node.type === 'VariableDeclarator' &&
|
|
159
|
+
node.id.type === 'Identifier' &&
|
|
160
|
+
node.init &&
|
|
161
|
+
Expression.unwrap(node.init).type === 'Identifier'
|
|
162
|
+
) {
|
|
163
|
+
const init = Expression.unwrap(node.init) as Extract<
|
|
164
|
+
Ast.Node,
|
|
165
|
+
{ type: 'Identifier' }
|
|
166
|
+
>
|
|
167
|
+
const declaration = scope.getDeclaration(init.name)
|
|
168
|
+
const identity = declaration
|
|
169
|
+
? imported.get(declaration.node.start)
|
|
170
|
+
: undefined
|
|
171
|
+
|
|
172
|
+
const link = identity
|
|
173
|
+
? [...linkedNames.values()].find(
|
|
174
|
+
(link) => link.call.name === identity,
|
|
175
|
+
)
|
|
176
|
+
: undefined
|
|
177
|
+
|
|
178
|
+
if (link) {
|
|
179
|
+
if (
|
|
180
|
+
parent?.type !== 'VariableDeclaration' ||
|
|
181
|
+
parent.kind !== 'const'
|
|
182
|
+
)
|
|
183
|
+
throw new Themes.InvalidError(
|
|
184
|
+
'Animation aliases require const bindings.',
|
|
185
|
+
node,
|
|
186
|
+
)
|
|
187
|
+
|
|
188
|
+
imported.set(node.start, link.call.name)
|
|
189
|
+
|
|
190
|
+
if (
|
|
191
|
+
ancestors.at(-3)?.type === 'Program' ||
|
|
192
|
+
ancestors.at(-3)?.type === 'ExportNamedDeclaration'
|
|
193
|
+
)
|
|
194
|
+
linkedNames.set(node.id.name, link)
|
|
195
|
+
|
|
196
|
+
if (
|
|
197
|
+
ancestors.some((node) => node.type === 'ExportNamedDeclaration')
|
|
198
|
+
)
|
|
199
|
+
exported[node.id.name] = link
|
|
200
|
+
}
|
|
201
|
+
}
|
|
202
|
+
|
|
203
|
+
if (node.type !== 'CallExpression') return
|
|
204
|
+
|
|
205
|
+
const type = kind(node.callee)
|
|
206
|
+
if (!type) return
|
|
207
|
+
|
|
208
|
+
const variable =
|
|
209
|
+
parent?.type === 'VariableDeclarator' && parent.init === node
|
|
210
|
+
? parent
|
|
211
|
+
: undefined
|
|
212
|
+
const statement = variable ? ancestors.at(-3) : parent
|
|
213
|
+
if (
|
|
214
|
+
node.optional ||
|
|
215
|
+
(node.arguments.length !== 1 &&
|
|
216
|
+
(![
|
|
217
|
+
'fontFace',
|
|
218
|
+
'fontFeatureValues',
|
|
219
|
+
'page',
|
|
220
|
+
'property',
|
|
221
|
+
'viewTransition',
|
|
222
|
+
...named,
|
|
223
|
+
].includes(type) ||
|
|
224
|
+
node.arguments.length !== 2)) ||
|
|
225
|
+
(!variable && parent?.type !== 'ExpressionStatement') ||
|
|
226
|
+
ancestors
|
|
227
|
+
.slice(0, -1)
|
|
228
|
+
.some(
|
|
229
|
+
(ancestor) =>
|
|
230
|
+
![
|
|
231
|
+
'Program',
|
|
232
|
+
'ExportNamedDeclaration',
|
|
233
|
+
'VariableDeclaration',
|
|
234
|
+
'VariableDeclarator',
|
|
235
|
+
'ExpressionStatement',
|
|
236
|
+
].includes(ancestor.type),
|
|
237
|
+
) ||
|
|
238
|
+
(variable &&
|
|
239
|
+
(statement?.type !== 'VariableDeclaration' ||
|
|
240
|
+
statement.kind !== 'const' ||
|
|
241
|
+
variable.id.type !== 'Identifier'))
|
|
242
|
+
)
|
|
243
|
+
throw new Themes.InvalidError(
|
|
244
|
+
'Stylesheet contributions require direct module-level calls and constant named stylesheet bindings.',
|
|
245
|
+
node,
|
|
246
|
+
)
|
|
247
|
+
if (named.includes(type) && !variable)
|
|
248
|
+
throw new Themes.InvalidError(
|
|
249
|
+
'Named stylesheet definitions require a module-level named constant.',
|
|
250
|
+
node,
|
|
251
|
+
)
|
|
252
|
+
|
|
253
|
+
const context = node.arguments[1]
|
|
254
|
+
const idProperty =
|
|
255
|
+
context?.type === 'ObjectExpression'
|
|
256
|
+
? context.properties.find(
|
|
257
|
+
(property) =>
|
|
258
|
+
property.type === 'Property' &&
|
|
259
|
+
!property.computed &&
|
|
260
|
+
(property.key.type === 'Identifier'
|
|
261
|
+
? property.key.name
|
|
262
|
+
: property.key.type === 'Literal'
|
|
263
|
+
? property.key.value
|
|
264
|
+
: undefined) === 'id',
|
|
265
|
+
)
|
|
266
|
+
: undefined
|
|
267
|
+
if (
|
|
268
|
+
idProperty &&
|
|
269
|
+
(idProperty.type !== 'Property' ||
|
|
270
|
+
idProperty.value.type !== 'Literal' ||
|
|
271
|
+
typeof idProperty.value.value !== 'string' ||
|
|
272
|
+
!idProperty.value.value)
|
|
273
|
+
)
|
|
274
|
+
throw new Themes.InvalidError(
|
|
275
|
+
'Stylesheet ids must be nonempty string literals.',
|
|
276
|
+
node,
|
|
277
|
+
)
|
|
278
|
+
|
|
279
|
+
const explicit =
|
|
280
|
+
idProperty?.type === 'Property' &&
|
|
281
|
+
idProperty.value.type === 'Literal' &&
|
|
282
|
+
typeof idProperty.value.value === 'string'
|
|
283
|
+
? idProperty.value.value
|
|
284
|
+
: undefined
|
|
285
|
+
const name =
|
|
286
|
+
explicit !== undefined
|
|
287
|
+
? Identity.contribution(type, explicit)
|
|
288
|
+
: variable?.id.type === 'Identifier'
|
|
289
|
+
? `${type === 'keyframes' ? 'z-k' : `${type === 'counterStyle' ? '' : '--'}z-${type.toLowerCase()}`}${namespace}-${Array.from(
|
|
290
|
+
variable.id.name,
|
|
291
|
+
)
|
|
292
|
+
.map((value) => value.codePointAt(0)!.toString(16))
|
|
293
|
+
.join('-')}`
|
|
294
|
+
: undefined
|
|
295
|
+
|
|
296
|
+
const call: Call = {
|
|
297
|
+
kind: type,
|
|
298
|
+
start: node.start,
|
|
299
|
+
end: node.end,
|
|
300
|
+
argument: node.arguments[0]!,
|
|
301
|
+
context: node.arguments[1],
|
|
302
|
+
...(type === 'cssFunction'
|
|
303
|
+
? { function: { parameters: [], returns: '*' as const } }
|
|
304
|
+
: {}),
|
|
305
|
+
...(named.includes(type)
|
|
306
|
+
? {
|
|
307
|
+
name,
|
|
308
|
+
binding: variable!.start,
|
|
309
|
+
exported: ancestors.some(
|
|
310
|
+
(node) => node.type === 'ExportNamedDeclaration',
|
|
311
|
+
),
|
|
312
|
+
}
|
|
313
|
+
: {}),
|
|
314
|
+
}
|
|
315
|
+
|
|
316
|
+
calls.push(call)
|
|
317
|
+
if (named.includes(call.kind) && variable?.id.type === 'Identifier') {
|
|
318
|
+
const link: Themes.Link = {
|
|
319
|
+
binding: call.name!,
|
|
320
|
+
kind: call.kind === 'keyframes' ? 'animation' : 'rule-reference',
|
|
321
|
+
definition: Theme.define({}),
|
|
322
|
+
call: {
|
|
323
|
+
start: call.start,
|
|
324
|
+
end: call.end,
|
|
325
|
+
name: call.name!,
|
|
326
|
+
tokenType: '{}',
|
|
327
|
+
...(call.function ? { function: call.function } : {}),
|
|
328
|
+
...(call.kind !== 'keyframes'
|
|
329
|
+
? { reference: call.kind as RuleReference.Kind }
|
|
330
|
+
: {}),
|
|
331
|
+
},
|
|
332
|
+
}
|
|
333
|
+
|
|
334
|
+
imported.set(variable.start, call.name!)
|
|
335
|
+
linkedNames.set(variable.id.name, link)
|
|
336
|
+
|
|
337
|
+
if (call.exported) exported[variable.id.name] = link
|
|
338
|
+
}
|
|
339
|
+
|
|
340
|
+
if (call.binding !== undefined) bindings.set(call.binding, call)
|
|
341
|
+
},
|
|
342
|
+
leave() {
|
|
343
|
+
ancestors.pop()
|
|
344
|
+
},
|
|
345
|
+
})
|
|
346
|
+
|
|
347
|
+
function read(
|
|
348
|
+
node: Extract<Ast.Node, { type: 'Identifier' | 'JSXIdentifier' }>,
|
|
349
|
+
parent: Ast.Node,
|
|
350
|
+
binding: Walker.ScopeTrackerNode | null,
|
|
351
|
+
) {
|
|
352
|
+
if (
|
|
353
|
+
(binding?.type === 'Import' || binding?.type === 'Variable') &&
|
|
354
|
+
imported.has(binding.node.start)
|
|
355
|
+
) {
|
|
356
|
+
const name = imported.get(binding.node.start)!
|
|
357
|
+
const link = [...linkedNames.values()].find(
|
|
358
|
+
(link) => link.call.name === name,
|
|
359
|
+
)
|
|
360
|
+
const text =
|
|
361
|
+
link?.call.reference === 'customMedia' ? `@media (${name})` : name
|
|
362
|
+
references.set(node.start, name)
|
|
363
|
+
if (link?.call.reference === 'customMedia')
|
|
364
|
+
queryKeys.set(node.start, text)
|
|
365
|
+
if (
|
|
366
|
+
link?.call.reference === 'cssFunction' &&
|
|
367
|
+
parent.type === 'CallExpression' &&
|
|
368
|
+
parent.callee === node
|
|
369
|
+
) {
|
|
370
|
+
// A call and its callee share their start offset. Never keep the bare name
|
|
371
|
+
// when an argument cannot be serialized as a static CSS expression.
|
|
372
|
+
references.delete(node.start)
|
|
373
|
+
const args = parent.arguments.map((argument) => {
|
|
374
|
+
const input = Expression.unwrap(argument)
|
|
375
|
+
if (
|
|
376
|
+
input.type === 'Literal' &&
|
|
377
|
+
(typeof input.value === 'string' || typeof input.value === 'number')
|
|
378
|
+
)
|
|
379
|
+
return String(input.value)
|
|
380
|
+
if (
|
|
381
|
+
input.type === 'UnaryExpression' &&
|
|
382
|
+
(input.operator === '-' || input.operator === '+') &&
|
|
383
|
+
input.argument.type === 'Literal' &&
|
|
384
|
+
typeof input.argument.value === 'number'
|
|
385
|
+
)
|
|
386
|
+
return String(
|
|
387
|
+
input.operator === '-'
|
|
388
|
+
? -input.argument.value
|
|
389
|
+
: input.argument.value,
|
|
390
|
+
)
|
|
391
|
+
return undefined
|
|
392
|
+
})
|
|
393
|
+
if (link.call.function)
|
|
394
|
+
functionInputs.push({
|
|
395
|
+
name,
|
|
396
|
+
signature: link.call.function,
|
|
397
|
+
values: args,
|
|
398
|
+
node: parent,
|
|
399
|
+
})
|
|
400
|
+
if (args.every((value) => value !== undefined))
|
|
401
|
+
references.set(
|
|
402
|
+
parent.start,
|
|
403
|
+
`${name}(${args.map((value) => (typeof value === 'string' && value.includes(',') && !value.trimStart().startsWith('{') ? `{${value}}` : value)).join(',')})`,
|
|
404
|
+
)
|
|
405
|
+
}
|
|
406
|
+
used.add(imported.get(binding.node.start)!)
|
|
407
|
+
|
|
408
|
+
return
|
|
409
|
+
}
|
|
410
|
+
|
|
411
|
+
if (binding?.type !== 'Variable') return
|
|
412
|
+
|
|
413
|
+
const call = bindings.get(binding.node.start)
|
|
414
|
+
if (
|
|
415
|
+
!call?.name ||
|
|
416
|
+
(parent.type === 'VariableDeclarator' && parent.id === node)
|
|
417
|
+
)
|
|
418
|
+
return
|
|
419
|
+
|
|
420
|
+
references.set(node.start, call.name)
|
|
421
|
+
used.add(call.name)
|
|
422
|
+
}
|
|
423
|
+
|
|
424
|
+
for (const statement of program.body) {
|
|
425
|
+
if (statement.type === 'ExportDefaultDeclaration') {
|
|
426
|
+
const declaration = Expression.unwrap(statement.declaration)
|
|
427
|
+
const link =
|
|
428
|
+
declaration.type === 'Identifier'
|
|
429
|
+
? linkedNames.get(declaration.name)
|
|
430
|
+
: undefined
|
|
431
|
+
|
|
432
|
+
if (link) {
|
|
433
|
+
used.add(link.call.name)
|
|
434
|
+
exported.default = link
|
|
435
|
+
}
|
|
436
|
+
}
|
|
437
|
+
|
|
438
|
+
if (
|
|
439
|
+
statement.type === 'ExportNamedDeclaration' &&
|
|
440
|
+
statement.exportKind !== 'type' &&
|
|
441
|
+
!statement.source
|
|
442
|
+
)
|
|
443
|
+
for (const specifier of statement.specifiers) {
|
|
444
|
+
if ('exportKind' in specifier && specifier.exportKind === 'type')
|
|
445
|
+
continue
|
|
446
|
+
|
|
447
|
+
const name =
|
|
448
|
+
specifier.local.type === 'Identifier'
|
|
449
|
+
? specifier.local.name
|
|
450
|
+
: specifier.local.value
|
|
451
|
+
const link = linkedNames.get(name)
|
|
452
|
+
|
|
453
|
+
if (link) {
|
|
454
|
+
used.add(link.call.name)
|
|
455
|
+
exported[
|
|
456
|
+
specifier.exported.type === 'Identifier'
|
|
457
|
+
? specifier.exported.name
|
|
458
|
+
: specifier.exported.value
|
|
459
|
+
] = link
|
|
460
|
+
}
|
|
461
|
+
}
|
|
462
|
+
}
|
|
463
|
+
const kinds = new Map(
|
|
464
|
+
[...linkedNames.values()].flatMap((link) =>
|
|
465
|
+
link.call.reference
|
|
466
|
+
? [[link.call.name, link.call.reference] as const]
|
|
467
|
+
: [],
|
|
468
|
+
),
|
|
469
|
+
)
|
|
470
|
+
return {
|
|
471
|
+
functionInputs,
|
|
472
|
+
namespace,
|
|
473
|
+
queryKeys,
|
|
474
|
+
calls,
|
|
475
|
+
kinds,
|
|
476
|
+
references,
|
|
477
|
+
read,
|
|
478
|
+
used,
|
|
479
|
+
undefinedValues,
|
|
480
|
+
exports: exported,
|
|
481
|
+
}
|
|
482
|
+
}
|
|
483
|
+
|
|
484
|
+
/** Resolves nested static invocations after lexical reference discovery. */
|
|
485
|
+
export function resolve(scanned: ReturnType<typeof scan>): void {
|
|
486
|
+
for (const input of [...scanned.functionInputs].reverse()) {
|
|
487
|
+
input.values = input.values.map((value, index) => {
|
|
488
|
+
const node = Expression.unwrap(input.node.arguments[index]!)
|
|
489
|
+
return (
|
|
490
|
+
value ??
|
|
491
|
+
(node.type === 'CallExpression'
|
|
492
|
+
? scanned.references.get(node.start)
|
|
493
|
+
: undefined)
|
|
494
|
+
)
|
|
495
|
+
})
|
|
496
|
+
if (input.values.every((value) => value !== undefined))
|
|
497
|
+
scanned.references.set(
|
|
498
|
+
input.node.start,
|
|
499
|
+
`${input.name}(${input.values.map((value) => (value!.includes(',') && !value!.trimStart().startsWith('{') ? `{${value}}` : value)).join(',')})`,
|
|
500
|
+
)
|
|
501
|
+
}
|
|
502
|
+
}
|
|
503
|
+
|
|
504
|
+
/** Builds ordered pure web data after lexical theme references are resolved. */
|
|
505
|
+
export function extract(
|
|
506
|
+
scanned: ReturnType<typeof scan>,
|
|
507
|
+
tokens: ReadonlyMap<number, { end: number; reference: Token.Reference }>,
|
|
508
|
+
starts?: number[],
|
|
509
|
+
): readonly Css.Contribution[] {
|
|
510
|
+
const result: Css.Contribution[] = []
|
|
511
|
+
function value(node: Ast.Node, property?: string): unknown {
|
|
512
|
+
const reference = tokens.get(node.start)
|
|
513
|
+
if (reference?.end === node.end) return reference.reference
|
|
514
|
+
node = Expression.unwrap(node)
|
|
515
|
+
|
|
516
|
+
const animation = scanned.references.get(node.start)
|
|
517
|
+
if (animation) return animation
|
|
518
|
+
|
|
519
|
+
node = Expression.unwrap(node)
|
|
520
|
+
|
|
521
|
+
if (scanned.undefinedValues.has(node.start)) return undefined
|
|
522
|
+
|
|
523
|
+
if (
|
|
524
|
+
node.type === 'UnaryExpression' &&
|
|
525
|
+
node.operator === 'void' &&
|
|
526
|
+
Expression.unwrap(node.argument).type === 'Literal'
|
|
527
|
+
)
|
|
528
|
+
return undefined
|
|
529
|
+
if (
|
|
530
|
+
node.type === 'Literal' &&
|
|
531
|
+
(typeof node.value === 'string' ||
|
|
532
|
+
typeof node.value === 'number' ||
|
|
533
|
+
typeof node.value === 'boolean')
|
|
534
|
+
) {
|
|
535
|
+
return node.value
|
|
536
|
+
}
|
|
537
|
+
|
|
538
|
+
if (
|
|
539
|
+
node.type === 'UnaryExpression' &&
|
|
540
|
+
(node.operator === '-' || node.operator === '+') &&
|
|
541
|
+
node.argument.type === 'Literal' &&
|
|
542
|
+
typeof node.argument.value === 'number'
|
|
543
|
+
)
|
|
544
|
+
return node.operator === '-' ? -node.argument.value : node.argument.value
|
|
545
|
+
|
|
546
|
+
if (node.type === 'TemplateLiteral') {
|
|
547
|
+
const template = Expression.template(node, 0, (expression, prefix) => {
|
|
548
|
+
const node = Expression.unwrap(expression)
|
|
549
|
+
const name = scanned.references.get(node.start)
|
|
550
|
+
const kind = name ? scanned.kinds.get(name) : undefined
|
|
551
|
+
if (
|
|
552
|
+
kind &&
|
|
553
|
+
property &&
|
|
554
|
+
!RuleReference.acceptsExpression(kind, property, prefix)
|
|
555
|
+
)
|
|
556
|
+
throw new Themes.InvalidError(
|
|
557
|
+
'Named stylesheet reference is incompatible with this descriptor.',
|
|
558
|
+
node,
|
|
559
|
+
)
|
|
560
|
+
return name ?? tokens.get(node.start)?.reference
|
|
561
|
+
})
|
|
562
|
+
if (template !== undefined) return template
|
|
563
|
+
}
|
|
564
|
+
|
|
565
|
+
if (node.type === 'ArrayExpression')
|
|
566
|
+
return node.elements.map((element) => {
|
|
567
|
+
if (!element || element.type === 'SpreadElement')
|
|
568
|
+
throw new Themes.InvalidError(
|
|
569
|
+
'Contribution arrays require dense literal entries.',
|
|
570
|
+
node,
|
|
571
|
+
)
|
|
572
|
+
return value(element, property)
|
|
573
|
+
})
|
|
574
|
+
|
|
575
|
+
if (node.type !== 'ObjectExpression')
|
|
576
|
+
throw new Themes.InvalidError(
|
|
577
|
+
'Stylesheet contributions require literal data.',
|
|
578
|
+
node,
|
|
579
|
+
)
|
|
580
|
+
|
|
581
|
+
const output: Record<string, unknown> = Object.create(null)
|
|
582
|
+
|
|
583
|
+
for (const property of node.properties) {
|
|
584
|
+
if (
|
|
585
|
+
property.type !== 'Property' ||
|
|
586
|
+
(property.computed && !scanned.queryKeys.has(property.key.start)) ||
|
|
587
|
+
property.shorthand ||
|
|
588
|
+
property.method ||
|
|
589
|
+
property.kind !== 'init'
|
|
590
|
+
)
|
|
591
|
+
throw new Themes.InvalidError(
|
|
592
|
+
'Contribution objects require explicit literal properties.',
|
|
593
|
+
property,
|
|
594
|
+
)
|
|
595
|
+
|
|
596
|
+
const key =
|
|
597
|
+
scanned.queryKeys.get(property.key.start) ??
|
|
598
|
+
(property.key.type === 'Identifier'
|
|
599
|
+
? property.key.name
|
|
600
|
+
: property.key.type === 'Literal' &&
|
|
601
|
+
typeof property.key.value === 'string'
|
|
602
|
+
? property.key.value
|
|
603
|
+
: undefined)
|
|
604
|
+
if (key === undefined || Object.hasOwn(output, key))
|
|
605
|
+
throw new Themes.InvalidError(
|
|
606
|
+
'Contribution keys must be unique literal strings.',
|
|
607
|
+
property,
|
|
608
|
+
)
|
|
609
|
+
const item = Expression.unwrap(property.value)
|
|
610
|
+
const name = scanned.references.get(item.start)
|
|
611
|
+
const kind = name ? scanned.kinds.get(name) : undefined
|
|
612
|
+
if (kind && !RuleReference.accepts(kind, key))
|
|
613
|
+
throw new Themes.InvalidError(
|
|
614
|
+
'Named stylesheet reference is incompatible with this descriptor.',
|
|
615
|
+
item,
|
|
616
|
+
)
|
|
617
|
+
output[key] = value(property.value, key)
|
|
618
|
+
}
|
|
619
|
+
|
|
620
|
+
return output
|
|
621
|
+
}
|
|
622
|
+
|
|
623
|
+
function record(value: unknown): Record<string, unknown> {
|
|
624
|
+
if (!value || typeof value !== 'object' || Array.isArray(value))
|
|
625
|
+
throw new Error('Expected a contribution object.')
|
|
626
|
+
|
|
627
|
+
return value as Record<string, unknown>
|
|
628
|
+
}
|
|
629
|
+
|
|
630
|
+
function style(value: unknown): Style.NamedStyle {
|
|
631
|
+
return (
|
|
632
|
+
Style.define as unknown as (
|
|
633
|
+
styles: Record<string, unknown>,
|
|
634
|
+
) => Style.Definition
|
|
635
|
+
)({ contribution: record(value) }).styles[0]!
|
|
636
|
+
}
|
|
637
|
+
function grouping(selector: string): boolean {
|
|
638
|
+
if (!selector.startsWith('@')) return false
|
|
639
|
+
if (!Condition.is(selector))
|
|
640
|
+
throw new Error('Expected a selector or supported grouping rule.')
|
|
641
|
+
if (
|
|
642
|
+
/^@container(?=[\t\n\r\f (/])/.test(selector) &&
|
|
643
|
+
!selector.includes('(')
|
|
644
|
+
)
|
|
645
|
+
throw new Error(
|
|
646
|
+
'Container rules require a query after the optional name.',
|
|
647
|
+
)
|
|
648
|
+
Condition.normalize(selector)
|
|
649
|
+
return true
|
|
650
|
+
}
|
|
651
|
+
|
|
652
|
+
function global(input: unknown): Style.NamedStyle {
|
|
653
|
+
return {
|
|
654
|
+
name: 'global',
|
|
655
|
+
declarations: [],
|
|
656
|
+
rules: Object.entries(record(input)).map(([selector, input]) => ({
|
|
657
|
+
condition: selector,
|
|
658
|
+
style: grouping(selector) ? global(input) : style(input),
|
|
659
|
+
})),
|
|
660
|
+
}
|
|
661
|
+
}
|
|
662
|
+
|
|
663
|
+
for (const call of scanned.calls) {
|
|
664
|
+
const before = result.length
|
|
665
|
+
|
|
666
|
+
try {
|
|
667
|
+
const input = value(call.argument)
|
|
668
|
+
if (call.name && !call.exported && !scanned.used.has(call.name)) continue
|
|
669
|
+
if (call.kind === 'importCss') {
|
|
670
|
+
const options = record(input)
|
|
671
|
+
if (
|
|
672
|
+
Object.keys(options).some(
|
|
673
|
+
(key) => !['layer', 'media', 'supports', 'url'].includes(key),
|
|
674
|
+
) ||
|
|
675
|
+
typeof options.url !== 'string' ||
|
|
676
|
+
Object.entries(options).some(
|
|
677
|
+
([key, value]) =>
|
|
678
|
+
key !== 'url' &&
|
|
679
|
+
value !== undefined &&
|
|
680
|
+
typeof value !== 'string' &&
|
|
681
|
+
!(key === 'layer' && value === true),
|
|
682
|
+
)
|
|
683
|
+
)
|
|
684
|
+
throw new Error(
|
|
685
|
+
'Expected a stylesheet URL and static import conditions.',
|
|
686
|
+
)
|
|
687
|
+
result.push({
|
|
688
|
+
kind: 'import',
|
|
689
|
+
url: options.url,
|
|
690
|
+
...(options.layer !== undefined
|
|
691
|
+
? { layer: options.layer as string | true }
|
|
692
|
+
: {}),
|
|
693
|
+
...(options.supports !== undefined
|
|
694
|
+
? { supports: options.supports as string }
|
|
695
|
+
: {}),
|
|
696
|
+
...(options.media !== undefined
|
|
697
|
+
? { media: options.media as string }
|
|
698
|
+
: {}),
|
|
699
|
+
})
|
|
700
|
+
} else if (call.kind === 'namespace') {
|
|
701
|
+
const options = record(input)
|
|
702
|
+
if (
|
|
703
|
+
Object.keys(options).some(
|
|
704
|
+
(key) => !['prefix', 'uri'].includes(key),
|
|
705
|
+
) ||
|
|
706
|
+
typeof options.uri !== 'string' ||
|
|
707
|
+
(options.prefix !== undefined &&
|
|
708
|
+
(typeof options.prefix !== 'string' ||
|
|
709
|
+
Identifiers.read(options.prefix) === undefined))
|
|
710
|
+
)
|
|
711
|
+
throw new Error(
|
|
712
|
+
'Expected a namespace URI and optional identifier prefix.',
|
|
713
|
+
)
|
|
714
|
+
result.push({
|
|
715
|
+
kind: 'namespace',
|
|
716
|
+
uri: options.uri,
|
|
717
|
+
...(options.prefix !== undefined
|
|
718
|
+
? { prefix: options.prefix as string }
|
|
719
|
+
: {}),
|
|
720
|
+
name: `z-n${scanned.namespace}-${call.start.toString(36)}`,
|
|
721
|
+
})
|
|
722
|
+
} else if (call.kind === 'customMedia') {
|
|
723
|
+
if (typeof input !== 'string' && typeof input !== 'boolean')
|
|
724
|
+
throw new Error('Expected a media query or boolean.')
|
|
725
|
+
if (typeof input === 'string') Descriptors.media(input)
|
|
726
|
+
result.push({ kind: 'custom-media', name: call.name!, query: input })
|
|
727
|
+
} else if (call.kind === 'cssFunction') {
|
|
728
|
+
const options = record(input)
|
|
729
|
+
if (
|
|
730
|
+
Object.keys(options).some(
|
|
731
|
+
(key) => !['body', 'parameters', 'returns'].includes(key),
|
|
732
|
+
) ||
|
|
733
|
+
!Array.isArray(options.parameters) ||
|
|
734
|
+
(options.returns !== undefined &&
|
|
735
|
+
(typeof options.returns !== 'string' ||
|
|
736
|
+
!FunctionSyntax.accepts(options.returns)))
|
|
737
|
+
)
|
|
738
|
+
throw new Error(
|
|
739
|
+
'Expected CSS function parameters, body, and optional return syntax.',
|
|
740
|
+
)
|
|
741
|
+
const names = new Set<string>()
|
|
742
|
+
const parameters = options.parameters.map((input) => {
|
|
743
|
+
const parameter = record(input)
|
|
744
|
+
if (
|
|
745
|
+
Object.keys(parameter).some(
|
|
746
|
+
(key) => !['default', 'name', 'syntax'].includes(key),
|
|
747
|
+
) ||
|
|
748
|
+
typeof parameter.name !== 'string' ||
|
|
749
|
+
!dashed(parameter.name) ||
|
|
750
|
+
names.has(Identifiers.read(parameter.name)!) ||
|
|
751
|
+
(parameter.syntax !== undefined &&
|
|
752
|
+
(typeof parameter.syntax !== 'string' ||
|
|
753
|
+
!FunctionSyntax.accepts(parameter.syntax))) ||
|
|
754
|
+
(parameter.default !== undefined &&
|
|
755
|
+
typeof parameter.default !== 'string' &&
|
|
756
|
+
typeof parameter.default !== 'number')
|
|
757
|
+
)
|
|
758
|
+
throw new Error(
|
|
759
|
+
'Expected unique CSS parameters with supported syntaxes and scalar defaults.',
|
|
760
|
+
)
|
|
761
|
+
names.add(Identifiers.read(parameter.name)!)
|
|
762
|
+
if (parameter.default !== undefined)
|
|
763
|
+
Functions.value(
|
|
764
|
+
String(parameter.syntax ?? '*'),
|
|
765
|
+
String(parameter.default),
|
|
766
|
+
)
|
|
767
|
+
return `${parameter.name}${parameter.syntax ? ` ${parameter.syntax === '*' ? 'type(*)' : parameter.syntax}` : ''}${parameter.default !== undefined ? `: ${parameter.default}` : ''}`
|
|
768
|
+
})
|
|
769
|
+
function body(input: unknown): readonly Block.Entry[] {
|
|
770
|
+
return Object.entries(record(input)).flatMap(
|
|
771
|
+
([key, value]): Block.Entry[] => {
|
|
772
|
+
if (value === undefined) return []
|
|
773
|
+
if (/^@(media|supports|container) /.test(key))
|
|
774
|
+
return [
|
|
775
|
+
{
|
|
776
|
+
kind: 'block',
|
|
777
|
+
header: Condition.normalize(key),
|
|
778
|
+
entries: body(value),
|
|
779
|
+
},
|
|
780
|
+
]
|
|
781
|
+
if (
|
|
782
|
+
(key !== 'result' && !dashed(key)) ||
|
|
783
|
+
(typeof value !== 'string' && typeof value !== 'number')
|
|
784
|
+
)
|
|
785
|
+
throw new Error(
|
|
786
|
+
'CSS function bodies accept result, local variables, and conditional groups.',
|
|
787
|
+
)
|
|
788
|
+
Functions.value('*', String(value))
|
|
789
|
+
return [{ kind: 'descriptor', name: key, value }]
|
|
790
|
+
},
|
|
791
|
+
)
|
|
792
|
+
}
|
|
793
|
+
call.function!.parameters =
|
|
794
|
+
options.parameters as readonly cssFunction.Parameter[]
|
|
795
|
+
call.function!.returns = (options.returns ?? '*') as cssFunction.Syntax
|
|
796
|
+
result.push({
|
|
797
|
+
kind: 'block',
|
|
798
|
+
header: `@function ${call.name}(${parameters.join(',')})${options.returns ? ` returns ${options.returns === '*' ? 'type(*)' : options.returns}` : ''}`,
|
|
799
|
+
entries: body(options.body),
|
|
800
|
+
})
|
|
801
|
+
} else if (call.kind === 'layers') {
|
|
802
|
+
if (
|
|
803
|
+
!Array.isArray(input) ||
|
|
804
|
+
input.some((value) => typeof value !== 'string')
|
|
805
|
+
)
|
|
806
|
+
throw new Error('Layers require a literal string list.')
|
|
807
|
+
|
|
808
|
+
result.push({ kind: 'layers', names: input })
|
|
809
|
+
} else if (call.kind === 'global') {
|
|
810
|
+
for (const [selector, child] of Object.entries(record(input)))
|
|
811
|
+
result.push({
|
|
812
|
+
kind: 'rule',
|
|
813
|
+
selector,
|
|
814
|
+
style: grouping(selector) ? global(child) : style(child),
|
|
815
|
+
})
|
|
816
|
+
} else if (call.kind === 'fontFace') {
|
|
817
|
+
const declarations = record(input)
|
|
818
|
+
|
|
819
|
+
for (const key of Object.keys(declarations))
|
|
820
|
+
if (
|
|
821
|
+
declarations[key] === undefined &&
|
|
822
|
+
key !== 'fontFamily' &&
|
|
823
|
+
key !== 'src'
|
|
824
|
+
)
|
|
825
|
+
delete declarations[key]
|
|
826
|
+
|
|
827
|
+
const keys = [
|
|
828
|
+
'fontFeatureSettings',
|
|
829
|
+
'fontVariationSettings',
|
|
830
|
+
'fontFamily',
|
|
831
|
+
'src',
|
|
832
|
+
'fontDisplay',
|
|
833
|
+
'fontStyle',
|
|
834
|
+
'fontWeight',
|
|
835
|
+
'fontStretch',
|
|
836
|
+
'unicodeRange',
|
|
837
|
+
'sizeAdjust',
|
|
838
|
+
'ascentOverride',
|
|
839
|
+
'descentOverride',
|
|
840
|
+
'lineGapOverride',
|
|
841
|
+
]
|
|
842
|
+
if (
|
|
843
|
+
typeof declarations.fontFamily !== 'string' ||
|
|
844
|
+
typeof declarations.src !== 'string' ||
|
|
845
|
+
Object.entries(declarations).some(
|
|
846
|
+
([key, value]) =>
|
|
847
|
+
!keys.includes(key) ||
|
|
848
|
+
(typeof value !== 'string' && typeof value !== 'number'),
|
|
849
|
+
)
|
|
850
|
+
)
|
|
851
|
+
throw new Error(
|
|
852
|
+
'Font faces require family/source and scalar supported descriptors.',
|
|
853
|
+
)
|
|
854
|
+
|
|
855
|
+
for (const [name, value] of Object.entries(declarations))
|
|
856
|
+
Descriptors.check({ rule: 'font-face', name, value: String(value) })
|
|
857
|
+
result.push({
|
|
858
|
+
kind: 'font-face',
|
|
859
|
+
declarations: declarations as Record<string, string | number>,
|
|
860
|
+
})
|
|
861
|
+
} else if (call.kind === 'property') {
|
|
862
|
+
const options = record(input)
|
|
863
|
+
const names =
|
|
864
|
+
typeof options.name === 'string'
|
|
865
|
+
? Identifiers.list(options.name, 'space')
|
|
866
|
+
: undefined
|
|
867
|
+
if (
|
|
868
|
+
Object.keys(options).some(
|
|
869
|
+
(key) =>
|
|
870
|
+
!['name', 'syntax', 'inherits', 'initialValue'].includes(key),
|
|
871
|
+
) ||
|
|
872
|
+
names?.length !== 1 ||
|
|
873
|
+
!names[0]!.startsWith('--') ||
|
|
874
|
+
names[0]!.length <= 2 ||
|
|
875
|
+
typeof options.syntax !== 'string' ||
|
|
876
|
+
typeof options.inherits !== 'boolean' ||
|
|
877
|
+
(options.initialValue !== undefined &&
|
|
878
|
+
typeof options.initialValue !== 'string' &&
|
|
879
|
+
typeof options.initialValue !== 'number')
|
|
880
|
+
)
|
|
881
|
+
throw new Error(
|
|
882
|
+
'Expected a native property registration with scalar descriptors.',
|
|
883
|
+
)
|
|
884
|
+
if (options.initialValue !== undefined)
|
|
885
|
+
Properties.initial(String(options.initialValue))
|
|
886
|
+
result.push({
|
|
887
|
+
kind: 'property',
|
|
888
|
+
name: options.name as `--${string}`,
|
|
889
|
+
syntax: options.syntax,
|
|
890
|
+
inherits: options.inherits,
|
|
891
|
+
...(options.initialValue !== undefined
|
|
892
|
+
? { initialValue: options.initialValue as string | number }
|
|
893
|
+
: {}),
|
|
894
|
+
})
|
|
895
|
+
} else if (call.kind === 'page') {
|
|
896
|
+
const options = record(input)
|
|
897
|
+
if (
|
|
898
|
+
Object.keys(options).some(
|
|
899
|
+
(key) => !['descriptors', 'selector'].includes(key),
|
|
900
|
+
) ||
|
|
901
|
+
(options.selector !== undefined &&
|
|
902
|
+
typeof options.selector !== 'string')
|
|
903
|
+
)
|
|
904
|
+
throw new Error('Expected page descriptors and an optional selector.')
|
|
905
|
+
const margins = [
|
|
906
|
+
'top-left-corner',
|
|
907
|
+
'top-left',
|
|
908
|
+
'top-center',
|
|
909
|
+
'top-right',
|
|
910
|
+
'top-right-corner',
|
|
911
|
+
'bottom-left-corner',
|
|
912
|
+
'bottom-left',
|
|
913
|
+
'bottom-center',
|
|
914
|
+
'bottom-right',
|
|
915
|
+
'bottom-right-corner',
|
|
916
|
+
'left-top',
|
|
917
|
+
'left-middle',
|
|
918
|
+
'left-bottom',
|
|
919
|
+
'right-top',
|
|
920
|
+
'right-middle',
|
|
921
|
+
'right-bottom',
|
|
922
|
+
].map((name) => `@${name}`)
|
|
923
|
+
const properties =
|
|
924
|
+
/^(?!border(?:Collapse|Spacing)$)(?:background|border|font|margin|padding|outline)/
|
|
925
|
+
const names = [
|
|
926
|
+
'color',
|
|
927
|
+
'counterIncrement',
|
|
928
|
+
'counterReset',
|
|
929
|
+
'direction',
|
|
930
|
+
'height',
|
|
931
|
+
'letterSpacing',
|
|
932
|
+
'lineHeight',
|
|
933
|
+
'maxHeight',
|
|
934
|
+
'maxWidth',
|
|
935
|
+
'minHeight',
|
|
936
|
+
'minWidth',
|
|
937
|
+
'quotes',
|
|
938
|
+
'textAlign',
|
|
939
|
+
'textDecoration',
|
|
940
|
+
'textIndent',
|
|
941
|
+
'textTransform',
|
|
942
|
+
'visibility',
|
|
943
|
+
'whiteSpace',
|
|
944
|
+
'width',
|
|
945
|
+
'wordSpacing',
|
|
946
|
+
]
|
|
947
|
+
function body(input: unknown, margin = false): readonly Block.Entry[] {
|
|
948
|
+
return Object.entries(record(input)).flatMap(
|
|
949
|
+
([key, value]): Block.Entry[] => {
|
|
950
|
+
if (value === undefined) return []
|
|
951
|
+
if (!margin && margins.includes(key))
|
|
952
|
+
return [
|
|
953
|
+
{ kind: 'block', header: key, entries: body(value, true) },
|
|
954
|
+
]
|
|
955
|
+
if (
|
|
956
|
+
!margin &&
|
|
957
|
+
['bleed', 'marks', 'pageOrientation', 'size'].includes(key)
|
|
958
|
+
) {
|
|
959
|
+
if (typeof value !== 'string' && typeof value !== 'number')
|
|
960
|
+
throw new Error('Expected a scalar page descriptor.')
|
|
961
|
+
Descriptors.check({
|
|
962
|
+
rule: 'page',
|
|
963
|
+
name: key,
|
|
964
|
+
value: String(value),
|
|
965
|
+
})
|
|
966
|
+
return [
|
|
967
|
+
{
|
|
968
|
+
kind: 'descriptor',
|
|
969
|
+
name: key.replace(
|
|
970
|
+
/[A-Z]/g,
|
|
971
|
+
(letter) => `-${letter.toLowerCase()}`,
|
|
972
|
+
),
|
|
973
|
+
value,
|
|
974
|
+
},
|
|
975
|
+
]
|
|
976
|
+
}
|
|
977
|
+
if (
|
|
978
|
+
!properties.test(key) &&
|
|
979
|
+
!names.includes(key) &&
|
|
980
|
+
!(
|
|
981
|
+
margin &&
|
|
982
|
+
[
|
|
983
|
+
'content',
|
|
984
|
+
'overflow',
|
|
985
|
+
'unicodeBidi',
|
|
986
|
+
'verticalAlign',
|
|
987
|
+
'zIndex',
|
|
988
|
+
].includes(key)
|
|
989
|
+
)
|
|
990
|
+
)
|
|
991
|
+
throw new Error('Unsupported page or page-margin declaration.')
|
|
992
|
+
return [{ kind: 'style', style: style({ [key]: value }) }]
|
|
993
|
+
},
|
|
994
|
+
)
|
|
995
|
+
}
|
|
996
|
+
result.push({
|
|
997
|
+
kind: 'block',
|
|
998
|
+
header: Condition.normalize(
|
|
999
|
+
`@page${options.selector ? ` ${options.selector}` : ''}`,
|
|
1000
|
+
),
|
|
1001
|
+
entries: body(options.descriptors),
|
|
1002
|
+
})
|
|
1003
|
+
} else if (call.kind === 'fontFeatureValues') {
|
|
1004
|
+
const options = record(input)
|
|
1005
|
+
if (
|
|
1006
|
+
Object.keys(options).some(
|
|
1007
|
+
(key) => !['families', 'features', 'fontDisplay'].includes(key),
|
|
1008
|
+
)
|
|
1009
|
+
)
|
|
1010
|
+
throw new Error('Unknown font-feature-values option.')
|
|
1011
|
+
const families = options.families
|
|
1012
|
+
if (
|
|
1013
|
+
typeof families !== 'string' &&
|
|
1014
|
+
(!Array.isArray(families) ||
|
|
1015
|
+
!families.length ||
|
|
1016
|
+
families.some((value) => typeof value !== 'string'))
|
|
1017
|
+
)
|
|
1018
|
+
throw new Error('Expected a font family list.')
|
|
1019
|
+
const familyList = Array.isArray(families)
|
|
1020
|
+
? families
|
|
1021
|
+
.map(
|
|
1022
|
+
(value) =>
|
|
1023
|
+
'"' +
|
|
1024
|
+
Array.from(value as string, (char) => {
|
|
1025
|
+
const code = char.codePointAt(0)!
|
|
1026
|
+
return code < 32 ||
|
|
1027
|
+
code === 127 ||
|
|
1028
|
+
char === '"' ||
|
|
1029
|
+
char === '\\'
|
|
1030
|
+
? `\\${code.toString(16)} `
|
|
1031
|
+
: char
|
|
1032
|
+
}).join('') +
|
|
1033
|
+
'"',
|
|
1034
|
+
)
|
|
1035
|
+
.join(',')
|
|
1036
|
+
: families
|
|
1037
|
+
// Validate the native prelude before shielding newer body descriptors.
|
|
1038
|
+
Lightning.transform({
|
|
1039
|
+
filename: 'font-feature-values.css',
|
|
1040
|
+
code: new TextEncoder().encode(
|
|
1041
|
+
`@font-feature-values ${familyList} {}`,
|
|
1042
|
+
),
|
|
1043
|
+
})
|
|
1044
|
+
const entries: Block.Entry[] = []
|
|
1045
|
+
for (const key of Object.keys(options)) {
|
|
1046
|
+
if (key === 'fontDisplay' && options.fontDisplay !== undefined) {
|
|
1047
|
+
if (
|
|
1048
|
+
typeof options.fontDisplay !== 'string' ||
|
|
1049
|
+
!['auto', 'block', 'fallback', 'optional', 'swap'].includes(
|
|
1050
|
+
Identifiers.list(options.fontDisplay, 'space')
|
|
1051
|
+
?.join(' ')
|
|
1052
|
+
.replace(/[A-Z]/g, (letter) => letter.toLowerCase()) ?? '',
|
|
1053
|
+
)
|
|
1054
|
+
)
|
|
1055
|
+
throw new Error('Invalid font display descriptor.')
|
|
1056
|
+
entries.push({
|
|
1057
|
+
kind: 'descriptor',
|
|
1058
|
+
name: 'font-display',
|
|
1059
|
+
value: options.fontDisplay,
|
|
1060
|
+
})
|
|
1061
|
+
}
|
|
1062
|
+
if (key !== 'features') continue
|
|
1063
|
+
for (const [header, input] of Object.entries(
|
|
1064
|
+
record(options.features),
|
|
1065
|
+
)) {
|
|
1066
|
+
if (input === undefined) continue
|
|
1067
|
+
if (
|
|
1068
|
+
![
|
|
1069
|
+
'@annotation',
|
|
1070
|
+
'@character-variant',
|
|
1071
|
+
'@ornaments',
|
|
1072
|
+
'@styleset',
|
|
1073
|
+
'@stylistic',
|
|
1074
|
+
'@swash',
|
|
1075
|
+
].includes(header)
|
|
1076
|
+
)
|
|
1077
|
+
throw new Error('Unknown font feature block.')
|
|
1078
|
+
const declarations: Block.Entry[] = Object.entries(
|
|
1079
|
+
record(input),
|
|
1080
|
+
).map(([name, value]) => {
|
|
1081
|
+
const values = Array.isArray(value) ? value : [value]
|
|
1082
|
+
const maximum =
|
|
1083
|
+
header === '@styleset'
|
|
1084
|
+
? Infinity
|
|
1085
|
+
: header === '@character-variant'
|
|
1086
|
+
? 2
|
|
1087
|
+
: 1
|
|
1088
|
+
if (
|
|
1089
|
+
!identifier(name) ||
|
|
1090
|
+
!values.length ||
|
|
1091
|
+
values.length > maximum ||
|
|
1092
|
+
values.some(
|
|
1093
|
+
(value) =>
|
|
1094
|
+
typeof value !== 'number' ||
|
|
1095
|
+
!Number.isSafeInteger(value) ||
|
|
1096
|
+
value < 0,
|
|
1097
|
+
)
|
|
1098
|
+
)
|
|
1099
|
+
throw new Error(
|
|
1100
|
+
'Expected feature aliases with nonnegative integer indices.',
|
|
1101
|
+
)
|
|
1102
|
+
return { kind: 'descriptor', name, value: values.join(' ') }
|
|
1103
|
+
})
|
|
1104
|
+
entries.push({ kind: 'block', header, entries: declarations })
|
|
1105
|
+
}
|
|
1106
|
+
}
|
|
1107
|
+
result.push({
|
|
1108
|
+
kind: 'block',
|
|
1109
|
+
header: `@font-feature-values ${familyList}`,
|
|
1110
|
+
entries,
|
|
1111
|
+
})
|
|
1112
|
+
} else if (call.kind === 'viewTransition') {
|
|
1113
|
+
const entries = Object.entries(record(input)).flatMap(
|
|
1114
|
+
([key, value]): Block.Entry[] => {
|
|
1115
|
+
if (value === undefined) return []
|
|
1116
|
+
if (
|
|
1117
|
+
(key !== 'navigation' && key !== 'types') ||
|
|
1118
|
+
typeof value !== 'string' ||
|
|
1119
|
+
(key === 'navigation' &&
|
|
1120
|
+
!['auto', 'none'].includes(
|
|
1121
|
+
Identifiers.list(value, 'space')?.join(' ').toLowerCase() ??
|
|
1122
|
+
'',
|
|
1123
|
+
))
|
|
1124
|
+
)
|
|
1125
|
+
throw new Error(
|
|
1126
|
+
'Expected navigation or types view-transition descriptors.',
|
|
1127
|
+
)
|
|
1128
|
+
if (key === 'types') {
|
|
1129
|
+
const names = Identifiers.list(value, 'space')
|
|
1130
|
+
if (
|
|
1131
|
+
!names ||
|
|
1132
|
+
names.some(
|
|
1133
|
+
(name) =>
|
|
1134
|
+
[
|
|
1135
|
+
'default',
|
|
1136
|
+
'inherit',
|
|
1137
|
+
'initial',
|
|
1138
|
+
'revert',
|
|
1139
|
+
'revert-layer',
|
|
1140
|
+
'unset',
|
|
1141
|
+
].includes(name.toLowerCase()) ||
|
|
1142
|
+
(name.toLowerCase() === 'none' && names.length !== 1),
|
|
1143
|
+
)
|
|
1144
|
+
)
|
|
1145
|
+
throw new Error(
|
|
1146
|
+
'Expected none or a list of view-transition custom identifiers.',
|
|
1147
|
+
)
|
|
1148
|
+
}
|
|
1149
|
+
Functions.value('*', String(value))
|
|
1150
|
+
return [{ kind: 'descriptor', name: key, value }]
|
|
1151
|
+
},
|
|
1152
|
+
)
|
|
1153
|
+
result.push({ kind: 'block', header: '@view-transition', entries })
|
|
1154
|
+
} else if (call.kind === 'positionTry') {
|
|
1155
|
+
const declarations = record(input)
|
|
1156
|
+
const keys = [
|
|
1157
|
+
'alignSelf',
|
|
1158
|
+
'blockSize',
|
|
1159
|
+
'bottom',
|
|
1160
|
+
'height',
|
|
1161
|
+
'inlineSize',
|
|
1162
|
+
'inset',
|
|
1163
|
+
'insetBlock',
|
|
1164
|
+
'insetBlockEnd',
|
|
1165
|
+
'insetBlockStart',
|
|
1166
|
+
'insetInline',
|
|
1167
|
+
'insetInlineEnd',
|
|
1168
|
+
'insetInlineStart',
|
|
1169
|
+
'justifySelf',
|
|
1170
|
+
'left',
|
|
1171
|
+
'margin',
|
|
1172
|
+
'marginBlock',
|
|
1173
|
+
'marginBlockEnd',
|
|
1174
|
+
'marginBlockStart',
|
|
1175
|
+
'marginBottom',
|
|
1176
|
+
'marginInline',
|
|
1177
|
+
'marginInlineEnd',
|
|
1178
|
+
'marginInlineStart',
|
|
1179
|
+
'marginLeft',
|
|
1180
|
+
'marginRight',
|
|
1181
|
+
'marginTop',
|
|
1182
|
+
'maxBlockSize',
|
|
1183
|
+
'maxHeight',
|
|
1184
|
+
'maxInlineSize',
|
|
1185
|
+
'maxWidth',
|
|
1186
|
+
'minBlockSize',
|
|
1187
|
+
'minHeight',
|
|
1188
|
+
'minInlineSize',
|
|
1189
|
+
'minWidth',
|
|
1190
|
+
'placeSelf',
|
|
1191
|
+
'positionAnchor',
|
|
1192
|
+
'positionArea',
|
|
1193
|
+
'right',
|
|
1194
|
+
'top',
|
|
1195
|
+
'width',
|
|
1196
|
+
]
|
|
1197
|
+
if (Object.keys(declarations).some((key) => !keys.includes(key)))
|
|
1198
|
+
throw new Error('Unsupported position-try declaration.')
|
|
1199
|
+
const block = style(declarations)
|
|
1200
|
+
if (block.rules || block.declarations.some((value) => value.important))
|
|
1201
|
+
throw new Error(
|
|
1202
|
+
'Position-try forbids nested rules and important declarations.',
|
|
1203
|
+
)
|
|
1204
|
+
result.push({
|
|
1205
|
+
kind: 'rule',
|
|
1206
|
+
selector: `@position-try ${call.name}`,
|
|
1207
|
+
style: block,
|
|
1208
|
+
})
|
|
1209
|
+
} else if (
|
|
1210
|
+
call.kind === 'colorProfile' ||
|
|
1211
|
+
call.kind === 'counterStyle' ||
|
|
1212
|
+
call.kind === 'fontPaletteValues'
|
|
1213
|
+
) {
|
|
1214
|
+
const descriptors = {
|
|
1215
|
+
colorProfile: {
|
|
1216
|
+
rule: 'color-profile',
|
|
1217
|
+
keys: ['components', 'renderingIntent', 'src'],
|
|
1218
|
+
required: ['src'],
|
|
1219
|
+
},
|
|
1220
|
+
counterStyle: {
|
|
1221
|
+
rule: 'counter-style',
|
|
1222
|
+
keys: [
|
|
1223
|
+
'additiveSymbols',
|
|
1224
|
+
'fallback',
|
|
1225
|
+
'negative',
|
|
1226
|
+
'pad',
|
|
1227
|
+
'prefix',
|
|
1228
|
+
'range',
|
|
1229
|
+
'speakAs',
|
|
1230
|
+
'suffix',
|
|
1231
|
+
'symbols',
|
|
1232
|
+
'system',
|
|
1233
|
+
],
|
|
1234
|
+
required: [],
|
|
1235
|
+
},
|
|
1236
|
+
fontPaletteValues: {
|
|
1237
|
+
rule: 'font-palette-values',
|
|
1238
|
+
keys: ['basePalette', 'fontFamily', 'overrideColors'],
|
|
1239
|
+
required: ['fontFamily'],
|
|
1240
|
+
},
|
|
1241
|
+
} as const
|
|
1242
|
+
const definition = descriptors[call.kind]
|
|
1243
|
+
const declarations = record(input)
|
|
1244
|
+
for (const key of Object.keys(declarations))
|
|
1245
|
+
if (declarations[key] === undefined) delete declarations[key]
|
|
1246
|
+
if (
|
|
1247
|
+
definition.required.some(
|
|
1248
|
+
(key) => typeof declarations[key] !== 'string',
|
|
1249
|
+
) ||
|
|
1250
|
+
Object.entries(declarations).some(
|
|
1251
|
+
([key, value]) =>
|
|
1252
|
+
!(definition.keys as readonly string[]).includes(key) ||
|
|
1253
|
+
(typeof value !== 'string' &&
|
|
1254
|
+
!(
|
|
1255
|
+
key === 'basePalette' &&
|
|
1256
|
+
typeof value === 'number' &&
|
|
1257
|
+
Number.isSafeInteger(value) &&
|
|
1258
|
+
value >= 0
|
|
1259
|
+
)),
|
|
1260
|
+
)
|
|
1261
|
+
)
|
|
1262
|
+
throw new Error(
|
|
1263
|
+
'Expected supported scalar descriptors and required fields.',
|
|
1264
|
+
)
|
|
1265
|
+
if (call.kind === 'colorProfile') {
|
|
1266
|
+
if (!Identifiers.url(declarations.src as string))
|
|
1267
|
+
throw new Error('Color-profile src requires one URL.')
|
|
1268
|
+
if (typeof declarations.components === 'string') {
|
|
1269
|
+
const names = Identifiers.list(declarations.components, 'comma')
|
|
1270
|
+
if (!names || names.some((name) => name.toLowerCase() === 'none'))
|
|
1271
|
+
throw new Error(
|
|
1272
|
+
'Color-profile components require comma-separated identifiers other than none.',
|
|
1273
|
+
)
|
|
1274
|
+
}
|
|
1275
|
+
if (typeof declarations.renderingIntent === 'string') {
|
|
1276
|
+
const names = Identifiers.list(
|
|
1277
|
+
declarations.renderingIntent,
|
|
1278
|
+
'space',
|
|
1279
|
+
)
|
|
1280
|
+
if (
|
|
1281
|
+
names?.length !== 1 ||
|
|
1282
|
+
![
|
|
1283
|
+
'absolute-colorimetric',
|
|
1284
|
+
'relative-colorimetric',
|
|
1285
|
+
'perceptual',
|
|
1286
|
+
'saturation',
|
|
1287
|
+
].includes(names[0]!.toLowerCase())
|
|
1288
|
+
)
|
|
1289
|
+
throw new Error('Invalid color-profile rendering intent.')
|
|
1290
|
+
}
|
|
1291
|
+
}
|
|
1292
|
+
if (call.kind === 'counterStyle') {
|
|
1293
|
+
const system =
|
|
1294
|
+
typeof declarations.system === 'string'
|
|
1295
|
+
? Lexical.normalize(declarations.system)
|
|
1296
|
+
.trim()
|
|
1297
|
+
.replace(/[A-Z]/g, (letter) => letter.toLowerCase())
|
|
1298
|
+
: 'symbolic'
|
|
1299
|
+
try {
|
|
1300
|
+
Descriptors.check({
|
|
1301
|
+
rule: 'counter-style',
|
|
1302
|
+
name: 'system',
|
|
1303
|
+
value:
|
|
1304
|
+
typeof declarations.system === 'string'
|
|
1305
|
+
? declarations.system
|
|
1306
|
+
: 'symbolic',
|
|
1307
|
+
})
|
|
1308
|
+
} catch {
|
|
1309
|
+
throw new Error(
|
|
1310
|
+
'Expected a supported counter system, with an integer after fixed.',
|
|
1311
|
+
)
|
|
1312
|
+
}
|
|
1313
|
+
const required =
|
|
1314
|
+
system === 'additive'
|
|
1315
|
+
? 'additiveSymbols'
|
|
1316
|
+
: system.startsWith('extends ')
|
|
1317
|
+
? undefined
|
|
1318
|
+
: 'symbols'
|
|
1319
|
+
if (
|
|
1320
|
+
required &&
|
|
1321
|
+
(typeof declarations[required] !== 'string' ||
|
|
1322
|
+
!(declarations[required] as string).trim())
|
|
1323
|
+
)
|
|
1324
|
+
throw new Error(
|
|
1325
|
+
'The counter system requires symbols or additiveSymbols.',
|
|
1326
|
+
)
|
|
1327
|
+
}
|
|
1328
|
+
if (call.kind !== 'colorProfile')
|
|
1329
|
+
for (const [name, value] of Object.entries(declarations))
|
|
1330
|
+
Descriptors.check({
|
|
1331
|
+
rule: definition.rule,
|
|
1332
|
+
name,
|
|
1333
|
+
value: String(value),
|
|
1334
|
+
})
|
|
1335
|
+
result.push({
|
|
1336
|
+
kind: 'descriptor',
|
|
1337
|
+
rule: definition.rule,
|
|
1338
|
+
name: call.name!,
|
|
1339
|
+
declarations: declarations as Record<string, string | number>,
|
|
1340
|
+
})
|
|
1341
|
+
} else {
|
|
1342
|
+
const frames = Object.entries(record(input)).map(([stop, input]) => {
|
|
1343
|
+
if (!Keyframes.accepts(stop))
|
|
1344
|
+
throw new Error(
|
|
1345
|
+
'Keyframe stops require from, to, 0–100% offsets, or named timeline percentages.',
|
|
1346
|
+
)
|
|
1347
|
+
|
|
1348
|
+
const frame = style(input)
|
|
1349
|
+
if (
|
|
1350
|
+
frame.rules ||
|
|
1351
|
+
frame.declarations.some((value) => value.important)
|
|
1352
|
+
)
|
|
1353
|
+
throw new Error(
|
|
1354
|
+
'Keyframes forbid nested rules and important declarations.',
|
|
1355
|
+
)
|
|
1356
|
+
|
|
1357
|
+
return { stop, style: frame }
|
|
1358
|
+
})
|
|
1359
|
+
|
|
1360
|
+
if (call.exported || scanned.used.has(call.name!))
|
|
1361
|
+
result.push({ kind: 'keyframes', name: call.name!, frames })
|
|
1362
|
+
}
|
|
1363
|
+
const contextValue = call.context ? value(call.context) : undefined
|
|
1364
|
+
if (contextValue !== undefined) {
|
|
1365
|
+
const context = record(contextValue)
|
|
1366
|
+
if (Object.keys(context).some((key) => !['id', 'within'].includes(key)))
|
|
1367
|
+
throw new Error('Unknown contribution context option.')
|
|
1368
|
+
if (call.kind === 'customMedia' && 'within' in context)
|
|
1369
|
+
throw new Error(
|
|
1370
|
+
'Custom media definitions do not accept a within context.',
|
|
1371
|
+
)
|
|
1372
|
+
|
|
1373
|
+
const within = context.within ?? []
|
|
1374
|
+
if (
|
|
1375
|
+
!Array.isArray(within) ||
|
|
1376
|
+
within.some(
|
|
1377
|
+
(header) =>
|
|
1378
|
+
typeof header !== 'string' ||
|
|
1379
|
+
!(
|
|
1380
|
+
header === '@layer' ||
|
|
1381
|
+
/^@(media|supports|container|layer)(?=[\t\n\r\f (/])/.test(
|
|
1382
|
+
header,
|
|
1383
|
+
)
|
|
1384
|
+
),
|
|
1385
|
+
)
|
|
1386
|
+
)
|
|
1387
|
+
throw new Error('Expected enclosing conditional or layer headers.')
|
|
1388
|
+
const headers = within.map((header: string) =>
|
|
1389
|
+
Condition.normalize(header),
|
|
1390
|
+
)
|
|
1391
|
+
for (let index = before; index < result.length; index++)
|
|
1392
|
+
result[index] = { ...result[index]!, within: headers }
|
|
1393
|
+
}
|
|
1394
|
+
|
|
1395
|
+
for (let index = before; index < result.length; index++)
|
|
1396
|
+
starts?.push(call.start)
|
|
1397
|
+
} catch (error) {
|
|
1398
|
+
throw new Themes.InvalidError((error as Error).message, call)
|
|
1399
|
+
}
|
|
1400
|
+
}
|
|
1401
|
+
for (const input of scanned.functionInputs)
|
|
1402
|
+
if (
|
|
1403
|
+
input.values.some((value, index) => {
|
|
1404
|
+
const syntax = input.signature.parameters[index]?.syntax ?? '*'
|
|
1405
|
+
if (value === undefined || !FunctionSyntax.integerOnly(syntax))
|
|
1406
|
+
return false
|
|
1407
|
+
|
|
1408
|
+
const text = value.trim()
|
|
1409
|
+
// List contents retain their existing CSS-text contract; this diagnostic checks scalar tokens.
|
|
1410
|
+
if (
|
|
1411
|
+
(syntax.includes('+') && /\s/.test(text)) ||
|
|
1412
|
+
(syntax.includes('#') && text.includes(','))
|
|
1413
|
+
)
|
|
1414
|
+
return false
|
|
1415
|
+
|
|
1416
|
+
if (!/^[+-]?(?:\d|\.\d)/.test(text) || /^[+-]?\d+$/.test(text))
|
|
1417
|
+
return false
|
|
1418
|
+
|
|
1419
|
+
const suffix = /^[+-]?(?:\d*\.\d+|\d+)(?:[eE][+-]?\d+)?(.+)$/.exec(
|
|
1420
|
+
text,
|
|
1421
|
+
)?.[1]
|
|
1422
|
+
const unit =
|
|
1423
|
+
suffix === '%'
|
|
1424
|
+
? suffix
|
|
1425
|
+
: suffix && Identifiers.read(suffix)?.toLowerCase()
|
|
1426
|
+
const normalized = syntax.trim()
|
|
1427
|
+
const body = normalized.startsWith('type(')
|
|
1428
|
+
? normalized.slice(5, -1)
|
|
1429
|
+
: normalized
|
|
1430
|
+
const alternatives = body.split('|').map((part) => part.trim())
|
|
1431
|
+
|
|
1432
|
+
return (
|
|
1433
|
+
!unit ||
|
|
1434
|
+
!alternatives.some((alternative) => {
|
|
1435
|
+
if (alternative === '<percentage>') return unit === '%'
|
|
1436
|
+
if (alternative === '<length-percentage>' && unit === '%')
|
|
1437
|
+
return true
|
|
1438
|
+
if (
|
|
1439
|
+
alternative === '<length>' ||
|
|
1440
|
+
alternative === '<length-percentage>'
|
|
1441
|
+
)
|
|
1442
|
+
return (Literal.lengthUnits as readonly string[]).includes(unit)
|
|
1443
|
+
if (alternative === '<angle>')
|
|
1444
|
+
return ['deg', 'grad', 'rad', 'turn'].includes(unit)
|
|
1445
|
+
if (alternative === '<time>') return ['s', 'ms'].includes(unit)
|
|
1446
|
+
if (alternative === '<resolution>')
|
|
1447
|
+
return ['dpi', 'dpcm', 'dppx', 'x'].includes(unit)
|
|
1448
|
+
return false
|
|
1449
|
+
})
|
|
1450
|
+
)
|
|
1451
|
+
})
|
|
1452
|
+
)
|
|
1453
|
+
throw new Themes.InvalidError(
|
|
1454
|
+
'CSS integer parameters require integer tokens.',
|
|
1455
|
+
input.node,
|
|
1456
|
+
)
|
|
1457
|
+
|
|
1458
|
+
for (const input of scanned.functionInputs) {
|
|
1459
|
+
const required =
|
|
1460
|
+
input.signature.parameters.findLastIndex(
|
|
1461
|
+
(parameter) => parameter.default === undefined,
|
|
1462
|
+
) + 1
|
|
1463
|
+
if (
|
|
1464
|
+
input.values.length < required ||
|
|
1465
|
+
input.values.length > input.signature.parameters.length
|
|
1466
|
+
)
|
|
1467
|
+
throw new Themes.InvalidError(
|
|
1468
|
+
'CSS function arguments must match the declared parameter count.',
|
|
1469
|
+
input.node,
|
|
1470
|
+
)
|
|
1471
|
+
for (const [index, value] of input.values.entries()) {
|
|
1472
|
+
if (value === undefined) continue
|
|
1473
|
+
try {
|
|
1474
|
+
Functions.value(input.signature.parameters[index]?.syntax ?? '*', value)
|
|
1475
|
+
} catch (error) {
|
|
1476
|
+
throw new Themes.InvalidError((error as Error).message, input.node)
|
|
1477
|
+
}
|
|
1478
|
+
}
|
|
1479
|
+
}
|
|
1480
|
+
return result
|
|
1481
|
+
}
|
|
1482
|
+
|
|
1483
|
+
function dashed(value: string): boolean {
|
|
1484
|
+
const name = Identifiers.read(value)
|
|
1485
|
+
return name !== undefined && name.startsWith('--') && name.length > 2
|
|
1486
|
+
}
|
|
1487
|
+
|
|
1488
|
+
// CSS identifiers allow non-ASCII code points and escaped identifier characters.
|
|
1489
|
+
function identifier(value: string): boolean {
|
|
1490
|
+
const escape = String.raw`\\(?:[\da-fA-F]{1,6}(?:\r\n|[ \t\n\r\f])?|[^\n\r\f\da-fA-F])`
|
|
1491
|
+
const start = `(?:[_a-zA-Z\\u0080-\\u{10FFFF}]|${escape})`
|
|
1492
|
+
const rest = `(?:[_a-zA-Z0-9-\\u0080-\\u{10FFFF}]|${escape})`
|
|
1493
|
+
if (!new RegExp(`^(?:--|-?${start})${rest}*$`, 'u').test(value)) return false
|
|
1494
|
+
const decoded = value.replace(
|
|
1495
|
+
/\\([\da-fA-F]{1,6})(?:\r\n|[ \t\n\r\f])?|\\([^\n\r\f])/g,
|
|
1496
|
+
(_, hex: string | undefined, char: string) =>
|
|
1497
|
+
hex ? String.fromCodePoint(Math.min(parseInt(hex, 16), 0x10ffff)) : char,
|
|
1498
|
+
)
|
|
1499
|
+
return ![
|
|
1500
|
+
'default',
|
|
1501
|
+
'inherit',
|
|
1502
|
+
'initial',
|
|
1503
|
+
'revert',
|
|
1504
|
+
'revert-layer',
|
|
1505
|
+
'unset',
|
|
1506
|
+
].includes(decoded.toLowerCase())
|
|
1507
|
+
}
|