@cobalt-ui/plugin-css
Advanced tools
Comparing version 1.5.1 to 1.6.0
# @cobalt-ui/plugin-css | ||
## 1.6.0 | ||
### Minor Changes | ||
- [#131](https://github.com/drwpow/cobalt-ui/pull/131) [`6628a8c`](https://github.com/drwpow/cobalt-ui/commit/6628a8cfe9adf20e9a6b437a82c7f6c1b28e1480) Thanks [@dev-nicolaos](https://github.com/dev-nicolaos)! - Handle whitespace in token ids when creating CSS variables | ||
## 1.5.1 | ||
@@ -4,0 +10,0 @@ |
import type { ParsedColorToken, ParsedCubicBezierToken, ParsedDimensionToken, ParsedDurationToken, ParsedFontFamilyToken, ParsedFontWeightToken, ParsedNumberToken, ParsedLinkToken, ParsedStrokeStyleToken, ParsedToken, Plugin } from '@cobalt-ui/core'; | ||
import { CustomNameGenerator, makeNameGenerator } from './utils/generate-token-name.js'; | ||
export { makeNameGenerator as _INTERNAL_makeNameGenerator, defaultNameGenerator } from './utils/generate-token-name.js'; | ||
/** @deprecated */ | ||
@@ -21,3 +23,3 @@ export type LegacyModeSelectors = Record<string, string | string[]>; | ||
transform?: <T extends ParsedToken>(token: T, mode?: string) => string; | ||
/** prefix variable names */ | ||
/** @deprecated prefix variable names */ | ||
prefix?: string; | ||
@@ -28,2 +30,4 @@ /** enable P3 color enhancement? (default: true) */ | ||
colorFormat?: 'none' | 'hex' | 'rgb' | 'hsl' | 'hwb' | 'srgb-linear' | 'p3' | 'lab' | 'lch' | 'oklab' | 'oklch' | 'xyz-d50' | 'xyz-d65'; | ||
/** generate variable name */ | ||
generateName?: CustomNameGenerator; | ||
} | ||
@@ -49,18 +53,8 @@ export default function pluginCSS(options?: Options): Plugin; | ||
export declare function transformStrokeStyle(value: ParsedStrokeStyleToken['$value']): string; | ||
export declare function defaultTransformer(token: ParsedToken, { colorFormat, mode, prefix }: { | ||
export declare function defaultTransformer(token: ParsedToken, tokens: ParsedToken[], { colorFormat, mode, generateName }: { | ||
colorFormat: Options['colorFormat']; | ||
mode?: string; | ||
prefix?: string; | ||
generateName: ReturnType<typeof makeNameGenerator>; | ||
}): string | number | Record<string, string>; | ||
/** convert token name to CSS variable */ | ||
export declare function varName(id: string, options?: { | ||
prefix?: string; | ||
suffix?: string; | ||
}): string; | ||
/** reference an existing CSS var */ | ||
export declare function varRef(id: string, options?: { | ||
prefix?: string; | ||
suffix?: string; | ||
fallbacks?: string[]; | ||
mode?: string; | ||
}): string; | ||
export declare function varRef(id: string, tokens: ParsedToken[], generateName: ReturnType<typeof makeNameGenerator>, suffix?: string): string; |
@@ -27,6 +27,7 @@ /** | ||
import { clampChroma, converter, formatCss, formatHex, formatHex8, formatHsl, formatRgb, parse as parseColor } from 'culori'; | ||
import { encode, formatFontNames, isTokenMatch } from './util.js'; | ||
const DASH_PREFIX_RE = /^-+/; | ||
const DASH_SUFFIX_RE = /-+$/; | ||
const DOT_UNDER_GLOB_RE = /[._]/g; | ||
import { DASH_PREFIX_RE, makeNameGenerator } from './utils/generate-token-name.js'; | ||
import { encode } from './utils/encode.js'; | ||
import { formatFontNames } from './utils/format-font-names.js'; | ||
import { isTokenMatch } from './utils/is-token-match.js'; | ||
export { makeNameGenerator as _INTERNAL_makeNameGenerator, defaultNameGenerator } from './utils/generate-token-name.js'; | ||
const SELECTOR_BRACKET_RE = /\s*{/; | ||
@@ -49,3 +50,4 @@ const HEX_RE = /#[0-9a-f]{3,8}/g; | ||
let filename = options?.filename || './tokens.css'; | ||
let prefix = options?.prefix || ''; | ||
const prefix = options?.prefix || ''; | ||
const generateName = makeNameGenerator(options?.generateName, prefix); | ||
function makeVars({ tokens, indentLv = 0, root = false }) { | ||
@@ -55,6 +57,5 @@ const output = []; | ||
output.push(indent(':root {', indentLv)); | ||
const sortedTokens = Object.entries(tokens); | ||
sortedTokens.sort((a, b) => a[0].localeCompare(b[0], 'en-us', { numeric: true })); | ||
for (const [id, value] of sortedTokens) { | ||
output.push(indent(`${varName(id, { prefix })}: ${value};`, indentLv + (root ? 1 : 0))); | ||
const sortedTokens = Object.entries(tokens).sort((a, b) => a[0].localeCompare(b[0], 'en-us', { numeric: true })); | ||
for (const [variableName, value] of sortedTokens) { | ||
output.push(indent(`${variableName}: ${value};`, indentLv + (root ? 1 : 0))); | ||
} | ||
@@ -105,3 +106,3 @@ if (root) | ||
if (value === undefined || value === null) { | ||
value = defaultTransformer(token, { colorFormat, prefix }); | ||
value = defaultTransformer(token, tokens, { colorFormat, generateName }); | ||
} | ||
@@ -112,3 +113,3 @@ switch (token.$type) { | ||
value = encode(value, config.outDir); | ||
tokenVals[token.id] = value; | ||
tokenVals[generateName(token.id, token)] = value; | ||
break; | ||
@@ -118,3 +119,3 @@ } | ||
for (const [k, v] of Object.entries(value)) { | ||
tokenVals[`${token.id}-${k}`] = v; | ||
tokenVals[generateName(`${token.id}-${k}`, token)] = v; | ||
} | ||
@@ -124,3 +125,3 @@ break; | ||
default: { | ||
tokenVals[token.id] = value; | ||
tokenVals[generateName(token.id, token)] = value; | ||
break; | ||
@@ -168,3 +169,3 @@ } | ||
if (modeVal === undefined || modeVal === null) { | ||
modeVal = defaultTransformer(token, { colorFormat, prefix, mode: modeSelector.mode }); | ||
modeVal = defaultTransformer(token, tokens, { colorFormat, mode: modeSelector.mode, generateName }); | ||
} | ||
@@ -175,3 +176,3 @@ switch (token.$type) { | ||
modeVal = encode(modeVal, config.outDir); | ||
modeVals[selector][token.id] = modeVal; | ||
modeVals[selector][generateName(token.id, token)] = modeVal; | ||
break; | ||
@@ -181,3 +182,3 @@ } | ||
for (const [k, v] of Object.entries(modeVal)) { | ||
modeVals[selector][`${token.id}-${k}`] = v; | ||
modeVals[selector][generateName(`${token.id}-${k}`, token)] = v; | ||
} | ||
@@ -187,3 +188,3 @@ break; | ||
default: { | ||
modeVals[selector][token.id] = modeVal; | ||
modeVals[selector][generateName(token.id, token)] = modeVal; | ||
break; | ||
@@ -330,3 +331,3 @@ } | ||
} | ||
export function defaultTransformer(token, { colorFormat = 'hex', mode, prefix }) { | ||
export function defaultTransformer(token, tokens, { colorFormat = 'hex', mode, generateName }) { | ||
switch (token.$type) { | ||
@@ -337,3 +338,3 @@ // base tokens | ||
if (isAlias(originalVal)) { | ||
return varRef(originalVal, { prefix }); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
@@ -345,3 +346,3 @@ return transformColor(originalVal, colorFormat); // note: use original value because it may have been normalized to hex (which matters if it wasn’t in sRGB gamut to begin with) | ||
if (isAlias(originalVal)) { | ||
return varRef(originalVal, { prefix }); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
@@ -353,3 +354,3 @@ return transformDimension(value); | ||
if (isAlias(originalVal)) { | ||
return varRef(originalVal, { prefix }); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
@@ -362,3 +363,3 @@ return transformDuration(value); | ||
if (isAlias(originalVal)) { | ||
return varRef(originalVal, { prefix }); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
@@ -370,3 +371,3 @@ return transformFontFamily(value); | ||
if (isAlias(originalVal)) { | ||
return varRef(originalVal, { prefix }); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
@@ -378,3 +379,3 @@ return transformFontWeight(value); | ||
if (isAlias(originalVal)) { | ||
return varRef(originalVal, { prefix }); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
@@ -386,3 +387,3 @@ return transformCubicBezier(value); | ||
if (isAlias(originalVal)) { | ||
return varRef(originalVal, { prefix }); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
@@ -394,3 +395,3 @@ return transformNumber(value); | ||
if (isAlias(originalVal)) { | ||
return varRef(originalVal, { prefix }); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
@@ -402,3 +403,3 @@ return transformLink(value); | ||
if (isAlias(originalVal)) { | ||
return varRef(originalVal, { prefix }); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
@@ -411,7 +412,7 @@ return transformStrokeStyle(value); | ||
if (typeof originalVal === 'string') { | ||
return varRef(originalVal, { prefix }); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
const width = isAlias(originalVal.width) ? varRef(originalVal.width, { prefix }) : transformDimension(value.width); | ||
const color = isAlias(originalVal.color) ? varRef(originalVal.color, { prefix }) : transformColor(originalVal.color, colorFormat); | ||
const style = isAlias(originalVal.style) ? varRef(originalVal.style, { prefix }) : transformStrokeStyle(value.style); | ||
const width = isAlias(originalVal.width) ? varRef(originalVal.width, tokens, generateName) : transformDimension(value.width); | ||
const color = isAlias(originalVal.color) ? varRef(originalVal.color, tokens, generateName) : transformColor(originalVal.color, colorFormat); | ||
const style = isAlias(originalVal.style) ? varRef(originalVal.style, tokens, generateName) : transformStrokeStyle(value.style); | ||
return `${width} ${style} ${color}`; | ||
@@ -422,3 +423,3 @@ } | ||
if (typeof originalVal === 'string') { | ||
return varRef(originalVal, { prefix }); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
@@ -434,9 +435,9 @@ // handle backwards compat for previous versions that didn’t always return array | ||
if (typeof origShadow === 'string') { | ||
return varRef(origShadow, { prefix }); | ||
return varRef(origShadow, tokens, generateName); | ||
} | ||
const offsetX = isAlias(origShadow.offsetX) ? varRef(origShadow.offsetX, { prefix }) : transformDimension(shadow.offsetX); | ||
const offsetY = isAlias(origShadow.offsetY) ? varRef(origShadow.offsetY, { prefix }) : transformDimension(shadow.offsetY); | ||
const blur = isAlias(origShadow.blur) ? varRef(origShadow.blur, { prefix }) : transformDimension(shadow.blur); | ||
const spread = isAlias(origShadow.spread) ? varRef(origShadow.spread, { prefix }) : transformDimension(shadow.spread); | ||
const color = isAlias(origShadow.color) ? varRef(origShadow.color, { prefix }) : transformColor(origShadow.color, colorFormat); | ||
const offsetX = isAlias(origShadow.offsetX) ? varRef(origShadow.offsetX, tokens, generateName) : transformDimension(shadow.offsetX); | ||
const offsetY = isAlias(origShadow.offsetY) ? varRef(origShadow.offsetY, tokens, generateName) : transformDimension(shadow.offsetY); | ||
const blur = isAlias(origShadow.blur) ? varRef(origShadow.blur, tokens, generateName) : transformDimension(shadow.blur); | ||
const spread = isAlias(origShadow.spread) ? varRef(origShadow.spread, tokens, generateName) : transformDimension(shadow.spread); | ||
const color = isAlias(origShadow.color) ? varRef(origShadow.color, tokens, generateName) : transformColor(origShadow.color, colorFormat); | ||
return `${shadow.inset ? 'inset ' : ''}${offsetX} ${offsetY} ${blur} ${spread} ${color}`; | ||
@@ -449,3 +450,3 @@ }) | ||
if (typeof originalVal === 'string') { | ||
return varRef(originalVal, { prefix }); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
@@ -456,6 +457,6 @@ return value | ||
if (typeof origGradient === 'string') { | ||
return varRef(origGradient, { prefix }); | ||
return varRef(origGradient, tokens, generateName); | ||
} | ||
const color = isAlias(origGradient.color) ? varRef(origGradient.color, { prefix }) : transformColor(origGradient.color, colorFormat); | ||
const stop = isAlias(origGradient.position) ? varRef(origGradient.position, { prefix }) : `${100 * gradient.position}%`; | ||
const color = isAlias(origGradient.color) ? varRef(origGradient.color, tokens, generateName) : transformColor(origGradient.color, colorFormat); | ||
const stop = isAlias(origGradient.position) ? varRef(origGradient.position, tokens, generateName) : `${100 * gradient.position}%`; | ||
return `${color} ${stop}`; | ||
@@ -468,10 +469,10 @@ }) | ||
if (typeof originalVal === 'string') { | ||
return varRef(originalVal, { prefix }); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
const duration = isAlias(originalVal.duration) ? varRef(originalVal.duration, { prefix }) : transformDuration(value.duration); | ||
const duration = isAlias(originalVal.duration) ? varRef(originalVal.duration, tokens, generateName) : transformDuration(value.duration); | ||
let delay = undefined; | ||
if (value.delay) { | ||
delay = isAlias(originalVal.delay) ? varRef(originalVal.delay, { prefix }) : transformDuration(value.delay); | ||
delay = isAlias(originalVal.delay) ? varRef(originalVal.delay, tokens, generateName) : transformDuration(value.delay); | ||
} | ||
const timingFunction = isAlias(originalVal.timingFunction) ? varRef(originalVal.timingFunction, { prefix }) : transformCubicBezier(value.timingFunction); | ||
const timingFunction = isAlias(originalVal.timingFunction) ? varRef(originalVal.timingFunction, tokens, generateName) : transformCubicBezier(value.timingFunction); | ||
return `${duration} ${delay ?? ''} ${timingFunction}`; | ||
@@ -482,3 +483,3 @@ } | ||
if (typeof originalVal === 'string') { | ||
return varRef(originalVal, { prefix }); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
@@ -488,3 +489,3 @@ const output = {}; | ||
const formatter = k === 'fontFamily' ? transformFontFamily : (val) => String(val); | ||
output[kebabinate(k)] = isAlias(originalVal[k]) ? varRef(originalVal[k], { prefix }) : formatter(v); | ||
output[kebabinate(k)] = isAlias(originalVal[k]) ? varRef(originalVal[k], tokens, generateName) : formatter(v); | ||
} | ||
@@ -509,16 +510,18 @@ return output; | ||
} | ||
/** convert token name to CSS variable */ | ||
export function varName(id, options) { | ||
return ['--', options?.prefix ? `${options.prefix.replace(DASH_PREFIX_RE, '').replace(DASH_SUFFIX_RE, '')}-` : '', id.replace(DOT_UNDER_GLOB_RE, '-'), options?.suffix ? `-${options.suffix.replace(DASH_PREFIX_RE, '')}` : ''].join(''); | ||
} | ||
/** reference an existing CSS var */ | ||
export function varRef(id, options) { | ||
export function varRef(id, tokens, generateName, suffix) { | ||
let refID = id; | ||
if (isAlias(id)) { | ||
const [rootID, mode] = id.substring(1, id.length - 1).split('#'); | ||
if (mode && options?.mode && mode !== options?.mode) | ||
console.warn(`⚠️ ${FG_YELLOW}"${id}" referenced from within mode "${options.mode}". This may produce unexpected values.${RESET}`); // eslint-disable-line no-console | ||
// unclear if mode is ever appended to id when passed here, but leaving for safety in case | ||
const [rootID, _mode] = id.substring(1, id.length - 1).split('#'); | ||
refID = rootID; | ||
} | ||
return ['var(', varName(refID, { prefix: options?.prefix, suffix: options?.suffix }), Array.isArray(options?.fallbacks) && options?.fallbacks.length ? `, ${options.fallbacks.join(', ')}` : '', ')'].join(''); | ||
const token = tokens.find((t) => t.id === refID); | ||
// eslint-disable-next-line no-console | ||
if (!token) | ||
console.warn(`Tried to reference variable with id: ${refID}, no token found`); | ||
// suffix is only used internally (one place in plugin-sass), so handle it here rather than clutter the public API in defaultNameGenerator | ||
const normalizedSuffix = suffix ? `-${suffix.replace(DASH_PREFIX_RE, '')}` : ''; | ||
const variableId = refID + normalizedSuffix; | ||
return `var(${generateName(variableId, token)})`; | ||
} | ||
@@ -525,0 +528,0 @@ /** @deprecated parse legacy modeSelector */ |
{ | ||
"name": "@cobalt-ui/plugin-css", | ||
"description": "Generate CSS from your design tokens schema (requires @cobalt-ui/cli)", | ||
"version": "1.5.1", | ||
"version": "1.6.0", | ||
"author": { | ||
@@ -12,5 +12,6 @@ "name": "Drew Powers", | ||
"design tokens", | ||
"design tokens format module", | ||
"design system", | ||
"dtfm", | ||
"w3c", | ||
"w3c design tokens", | ||
"css" | ||
@@ -32,4 +33,4 @@ ], | ||
"@cobalt-ui/utils": "^1.2.2", | ||
"@types/culori": "^2.0.0", | ||
"@types/mime": "^3.0.1", | ||
"@types/culori": "^2.0.3", | ||
"@types/mime": "^3.0.3", | ||
"culori": "^3.2.0", | ||
@@ -42,3 +43,3 @@ "mime": "^3.0.0", | ||
"@cobalt-ui/core": "^1.6.0", | ||
"@types/node": "^20.8.7", | ||
"@types/node": "^20.8.10", | ||
"npm-run-all": "^4.1.5", | ||
@@ -45,0 +46,0 @@ "vitest": "^0.34.6" |
@@ -78,3 +78,3 @@ # @cobalt-ui/plugin-css | ||
transform: () => null, | ||
/** (optional) add custom namespace to CSS vars */ | ||
/** (deprecated, use generateName instead) add custom namespace to CSS vars */ | ||
prefix: '', | ||
@@ -85,2 +85,4 @@ /** enable P3 support? */ | ||
colorFormat: 'hex', | ||
/** used to generate the name of each CSS variable */ | ||
generateName: defaultNameGenerator, | ||
}), | ||
@@ -323,2 +325,48 @@ ], | ||
### Generate Name | ||
Because token IDs are a dot-separated series of JSON keys, they cannot be trusted to be valid CSS variable names. By default, Cobalt generates CSS variable names using the `defaultNameGenerator` function which... | ||
- Removes leading and trailing whitespace from each group or token name in an ID | ||
- camelCases any group or token name that has a space in the middle of it | ||
- Joins the normalized segments together with a single dashes | ||
If you wish to customize this behavior, you can specify your own name generator with the plugin's `generateName` option. It accepts a function with the following signature. | ||
```ts | ||
type CustomNameGenerator = (variableId: string, token?: ParsedToken) => string; | ||
``` | ||
A couple things to be aware of: | ||
- `token` can be undefined in rare cases | ||
- This occurs when a token references another token that is not defined. Currently, this is not explicitly disallowed by the design tokens specification. | ||
- `variableId` may not be a 1:1 match with the `token.id` | ||
- For example, each property in a composite token will have its own variable generated, so those `variableId`s will include the property name. In most cases you should use `variableId` rather than `token.id`. | ||
- The string returned does not need to be prefixed with `--`, Cobalt will take care of that for you | ||
If you wish, you can use the `defaultNameGenerator` in your custom name generator. This is handy if you only want to modify the behavior of a special case. | ||
```js | ||
// tokens.config.mjs | ||
import pluginCSS, { defaultNameGenerator } from '@cobalt-ui/plugin-css'; | ||
/** @type import('@cobalt-ui/core').Config */ | ||
export default { | ||
tokens: './tokens.json', | ||
outDir: './tokens/', | ||
plugins: [ | ||
pluginCSS({ | ||
generateName: (variableId, token) { | ||
if (variableId === 'my.special.token') { | ||
return "SUPER_IMPORTANT_VARIABLE"; | ||
} | ||
return defaultNameGenerator(variableId); | ||
}, | ||
}), | ||
], | ||
}; | ||
``` | ||
### Usage with @cobalt-ui/plugin-sass | ||
@@ -325,0 +373,0 @@ |
133
src/index.ts
@@ -18,7 +18,9 @@ import type { | ||
import {clampChroma, converter, formatCss, formatHex, formatHex8, formatHsl, formatRgb, parse as parseColor} from 'culori'; | ||
import {encode, formatFontNames, isTokenMatch} from './util.js'; | ||
import {CustomNameGenerator, DASH_PREFIX_RE, makeNameGenerator} from './utils/generate-token-name.js'; | ||
import {encode} from './utils/encode.js'; | ||
import {formatFontNames} from './utils/format-font-names.js'; | ||
import {isTokenMatch} from './utils/is-token-match.js'; | ||
const DASH_PREFIX_RE = /^-+/; | ||
const DASH_SUFFIX_RE = /-+$/; | ||
const DOT_UNDER_GLOB_RE = /[._]/g; | ||
export {makeNameGenerator as _INTERNAL_makeNameGenerator, defaultNameGenerator} from './utils/generate-token-name.js'; | ||
const SELECTOR_BRACKET_RE = /\s*{/; | ||
@@ -48,3 +50,3 @@ const HEX_RE = /#[0-9a-f]{3,8}/g; | ||
transform?: <T extends ParsedToken>(token: T, mode?: string) => string; | ||
/** prefix variable names */ | ||
/** @deprecated prefix variable names */ | ||
prefix?: string; | ||
@@ -55,2 +57,4 @@ /** enable P3 color enhancement? (default: true) */ | ||
colorFormat?: 'none' | 'hex' | 'rgb' | 'hsl' | 'hwb' | 'srgb-linear' | 'p3' | 'lab' | 'lch' | 'oklab' | 'oklch' | 'xyz-d50' | 'xyz-d65'; | ||
/** generate variable name */ | ||
generateName?: CustomNameGenerator; | ||
} | ||
@@ -74,3 +78,4 @@ | ||
let filename = options?.filename || './tokens.css'; | ||
let prefix = options?.prefix || ''; | ||
const prefix = options?.prefix || ''; | ||
const generateName = makeNameGenerator(options?.generateName, prefix); | ||
@@ -80,6 +85,5 @@ function makeVars({tokens, indentLv = 0, root = false}: {tokens: Record<string, string>; indentLv: number; root: boolean}): string[] { | ||
if (root) output.push(indent(':root {', indentLv)); | ||
const sortedTokens = Object.entries(tokens); | ||
sortedTokens.sort((a, b) => a[0].localeCompare(b[0], 'en-us', {numeric: true})); | ||
for (const [id, value] of sortedTokens) { | ||
output.push(indent(`${varName(id, {prefix})}: ${value};`, indentLv + (root ? 1 : 0))); | ||
const sortedTokens = Object.entries(tokens).sort((a, b) => a[0].localeCompare(b[0], 'en-us', {numeric: true})); | ||
for (const [variableName, value] of sortedTokens) { | ||
output.push(indent(`${variableName}: ${value};`, indentLv + (root ? 1 : 0))); | ||
} | ||
@@ -122,4 +126,4 @@ if (root) output.push(indent('}', indentLv)); | ||
async build({tokens, metadata}): Promise<BuildResult[]> { | ||
const tokenVals: {[id: string]: any} = {}; | ||
const modeVals: {[selector: string]: {[id: string]: any}} = {}; | ||
const tokenVals: {[variableName: string]: any} = {}; | ||
const modeVals: {[selector: string]: {[variableName: string]: any}} = {}; | ||
const selectors: string[] = []; | ||
@@ -130,3 +134,3 @@ const colorFormat = options?.colorFormat ?? 'hex'; | ||
if (value === undefined || value === null) { | ||
value = defaultTransformer(token, {colorFormat, prefix}); | ||
value = defaultTransformer(token, tokens, {colorFormat, generateName}); | ||
} | ||
@@ -136,3 +140,3 @@ switch (token.$type) { | ||
if (options?.embedFiles) value = encode(value as string, config.outDir); | ||
tokenVals[token.id] = value; | ||
tokenVals[generateName(token.id, token)] = value; | ||
break; | ||
@@ -142,3 +146,3 @@ } | ||
for (const [k, v] of Object.entries(value)) { | ||
tokenVals[`${token.id}-${k}`] = v; | ||
tokenVals[generateName(`${token.id}-${k}`, token)] = v; | ||
} | ||
@@ -148,3 +152,3 @@ break; | ||
default: { | ||
tokenVals[token.id] = value; | ||
tokenVals[generateName(token.id, token)] = value; | ||
break; | ||
@@ -193,3 +197,3 @@ } | ||
if (modeVal === undefined || modeVal === null) { | ||
modeVal = defaultTransformer(token, {colorFormat, prefix, mode: modeSelector.mode}); | ||
modeVal = defaultTransformer(token, tokens, {colorFormat, mode: modeSelector.mode, generateName}); | ||
} | ||
@@ -199,3 +203,3 @@ switch (token.$type) { | ||
if (options?.embedFiles) modeVal = encode(modeVal as string, config.outDir); | ||
modeVals[selector]![token.id] = modeVal; | ||
modeVals[selector]![generateName(token.id, token)] = modeVal; | ||
break; | ||
@@ -205,3 +209,3 @@ } | ||
for (const [k, v] of Object.entries(modeVal)) { | ||
modeVals[selector]![`${token.id}-${k}`] = v; | ||
modeVals[selector]![generateName(`${token.id}-${k}`, token)] = v; | ||
} | ||
@@ -211,3 +215,3 @@ break; | ||
default: { | ||
modeVals[selector]![token.id] = modeVal; | ||
modeVals[selector]![generateName(token.id, token)] = modeVal; | ||
break; | ||
@@ -362,3 +366,7 @@ } | ||
export function defaultTransformer(token: ParsedToken, {colorFormat = 'hex', mode, prefix}: {colorFormat: Options['colorFormat']; mode?: string; prefix?: string}): string | number | Record<string, string> { | ||
export function defaultTransformer( | ||
token: ParsedToken, | ||
tokens: ParsedToken[], | ||
{colorFormat = 'hex', mode, generateName}: {colorFormat: Options['colorFormat']; mode?: string; generateName: ReturnType<typeof makeNameGenerator>}, | ||
): string | number | Record<string, string> { | ||
switch (token.$type) { | ||
@@ -369,3 +377,3 @@ // base tokens | ||
if (isAlias(originalVal)) { | ||
return varRef(originalVal, {prefix}); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
@@ -377,3 +385,3 @@ return transformColor(originalVal, colorFormat); // note: use original value because it may have been normalized to hex (which matters if it wasn’t in sRGB gamut to begin with) | ||
if (isAlias(originalVal)) { | ||
return varRef(originalVal as string, {prefix}); | ||
return varRef(originalVal as string, tokens, generateName); | ||
} | ||
@@ -385,3 +393,3 @@ return transformDimension(value); | ||
if (isAlias(originalVal)) { | ||
return varRef(originalVal as string, {prefix}); | ||
return varRef(originalVal as string, tokens, generateName); | ||
} | ||
@@ -394,3 +402,3 @@ return transformDuration(value); | ||
if (isAlias(originalVal)) { | ||
return varRef(originalVal as string, {prefix}); | ||
return varRef(originalVal as string, tokens, generateName); | ||
} | ||
@@ -402,3 +410,3 @@ return transformFontFamily(value); | ||
if (isAlias(originalVal)) { | ||
return varRef(originalVal as string, {prefix}); | ||
return varRef(originalVal as string, tokens, generateName); | ||
} | ||
@@ -410,3 +418,3 @@ return transformFontWeight(value); | ||
if (isAlias(originalVal)) { | ||
return varRef(originalVal as string, {prefix}); | ||
return varRef(originalVal as string, tokens, generateName); | ||
} | ||
@@ -418,3 +426,3 @@ return transformCubicBezier(value); | ||
if (isAlias(originalVal)) { | ||
return varRef(originalVal as string, {prefix}); | ||
return varRef(originalVal as string, tokens, generateName); | ||
} | ||
@@ -426,3 +434,3 @@ return transformNumber(value); | ||
if (isAlias(originalVal)) { | ||
return varRef(originalVal as string, {prefix}); | ||
return varRef(originalVal as string, tokens, generateName); | ||
} | ||
@@ -434,3 +442,3 @@ return transformLink(value); | ||
if (isAlias(originalVal)) { | ||
return varRef(originalVal as string, {prefix}); | ||
return varRef(originalVal as string, tokens, generateName); | ||
} | ||
@@ -443,7 +451,7 @@ return transformStrokeStyle(value); | ||
if (typeof originalVal === 'string') { | ||
return varRef(originalVal, {prefix}); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
const width = isAlias(originalVal.width) ? varRef(originalVal.width, {prefix}) : transformDimension(value.width); | ||
const color = isAlias(originalVal.color) ? varRef(originalVal.color, {prefix}) : transformColor(originalVal.color, colorFormat); | ||
const style = isAlias(originalVal.style) ? varRef(originalVal.style, {prefix}) : transformStrokeStyle(value.style); | ||
const width = isAlias(originalVal.width) ? varRef(originalVal.width, tokens, generateName) : transformDimension(value.width); | ||
const color = isAlias(originalVal.color) ? varRef(originalVal.color, tokens, generateName) : transformColor(originalVal.color, colorFormat); | ||
const style = isAlias(originalVal.style) ? varRef(originalVal.style, tokens, generateName) : transformStrokeStyle(value.style); | ||
return `${width} ${style} ${color}`; | ||
@@ -454,3 +462,3 @@ } | ||
if (typeof originalVal === 'string') { | ||
return varRef(originalVal, {prefix}); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
@@ -466,9 +474,9 @@ | ||
if (typeof origShadow === 'string') { | ||
return varRef(origShadow, {prefix}); | ||
return varRef(origShadow, tokens, generateName); | ||
} | ||
const offsetX = isAlias(origShadow.offsetX) ? varRef(origShadow.offsetX, {prefix}) : transformDimension(shadow.offsetX); | ||
const offsetY = isAlias(origShadow.offsetY) ? varRef(origShadow.offsetY, {prefix}) : transformDimension(shadow.offsetY); | ||
const blur = isAlias(origShadow.blur) ? varRef(origShadow.blur, {prefix}) : transformDimension(shadow.blur); | ||
const spread = isAlias(origShadow.spread) ? varRef(origShadow.spread, {prefix}) : transformDimension(shadow.spread); | ||
const color = isAlias(origShadow.color) ? varRef(origShadow.color, {prefix}) : transformColor(origShadow.color, colorFormat); | ||
const offsetX = isAlias(origShadow.offsetX) ? varRef(origShadow.offsetX, tokens, generateName) : transformDimension(shadow.offsetX); | ||
const offsetY = isAlias(origShadow.offsetY) ? varRef(origShadow.offsetY, tokens, generateName) : transformDimension(shadow.offsetY); | ||
const blur = isAlias(origShadow.blur) ? varRef(origShadow.blur, tokens, generateName) : transformDimension(shadow.blur); | ||
const spread = isAlias(origShadow.spread) ? varRef(origShadow.spread, tokens, generateName) : transformDimension(shadow.spread); | ||
const color = isAlias(origShadow.color) ? varRef(origShadow.color, tokens, generateName) : transformColor(origShadow.color, colorFormat); | ||
return `${shadow.inset ? 'inset ' : ''}${offsetX} ${offsetY} ${blur} ${spread} ${color}`; | ||
@@ -481,3 +489,3 @@ }) | ||
if (typeof originalVal === 'string') { | ||
return varRef(originalVal, {prefix}); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
@@ -488,6 +496,6 @@ return value | ||
if (typeof origGradient === 'string') { | ||
return varRef(origGradient, {prefix}); | ||
return varRef(origGradient, tokens, generateName); | ||
} | ||
const color = isAlias(origGradient.color) ? varRef(origGradient.color, {prefix}) : transformColor(origGradient.color, colorFormat); | ||
const stop = isAlias(origGradient.position) ? varRef(origGradient.position as any, {prefix}) : `${100 * gradient.position}%`; | ||
const color = isAlias(origGradient.color) ? varRef(origGradient.color, tokens, generateName) : transformColor(origGradient.color, colorFormat); | ||
const stop = isAlias(origGradient.position) ? varRef(origGradient.position as any, tokens, generateName) : `${100 * gradient.position}%`; | ||
return `${color} ${stop}`; | ||
@@ -500,10 +508,10 @@ }) | ||
if (typeof originalVal === 'string') { | ||
return varRef(originalVal, {prefix}); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
const duration = isAlias(originalVal.duration) ? varRef(originalVal.duration, {prefix}) : transformDuration(value.duration); | ||
const duration = isAlias(originalVal.duration) ? varRef(originalVal.duration, tokens, generateName) : transformDuration(value.duration); | ||
let delay: string | undefined = undefined; | ||
if (value.delay) { | ||
delay = isAlias(originalVal.delay) ? varRef(originalVal.delay, {prefix}) : transformDuration(value.delay); | ||
delay = isAlias(originalVal.delay) ? varRef(originalVal.delay, tokens, generateName) : transformDuration(value.delay); | ||
} | ||
const timingFunction = isAlias(originalVal.timingFunction) ? varRef(originalVal.timingFunction as any, {prefix}) : transformCubicBezier(value.timingFunction); | ||
const timingFunction = isAlias(originalVal.timingFunction) ? varRef(originalVal.timingFunction as any, tokens, generateName) : transformCubicBezier(value.timingFunction); | ||
return `${duration} ${delay ?? ''} ${timingFunction}`; | ||
@@ -514,3 +522,3 @@ } | ||
if (typeof originalVal === 'string') { | ||
return varRef(originalVal, {prefix}); | ||
return varRef(originalVal, tokens, generateName); | ||
} | ||
@@ -520,3 +528,3 @@ const output: Record<string, string> = {}; | ||
const formatter = k === 'fontFamily' ? transformFontFamily : (val: any): string => String(val); | ||
output[kebabinate(k)] = isAlias((originalVal as any)[k] as any) ? varRef((originalVal as any)[k], {prefix}) : formatter(v as any); | ||
output[kebabinate(k)] = isAlias((originalVal as any)[k] as any) ? varRef((originalVal as any)[k], tokens, generateName) : formatter(v as any); | ||
} | ||
@@ -542,16 +550,21 @@ return output; | ||
/** convert token name to CSS variable */ | ||
export function varName(id: string, options?: {prefix?: string; suffix?: string}): string { | ||
return ['--', options?.prefix ? `${options.prefix.replace(DASH_PREFIX_RE, '').replace(DASH_SUFFIX_RE, '')}-` : '', id.replace(DOT_UNDER_GLOB_RE, '-'), options?.suffix ? `-${options.suffix.replace(DASH_PREFIX_RE, '')}` : ''].join(''); | ||
} | ||
/** reference an existing CSS var */ | ||
export function varRef(id: string, options?: {prefix?: string; suffix?: string; fallbacks?: string[]; mode?: string}): string { | ||
export function varRef(id: string, tokens: ParsedToken[], generateName: ReturnType<typeof makeNameGenerator>, suffix?: string): string { | ||
let refID = id; | ||
if (isAlias(id)) { | ||
const [rootID, mode] = id.substring(1, id.length - 1).split('#'); | ||
if (mode && options?.mode && mode !== options?.mode) console.warn(`⚠️ ${FG_YELLOW}"${id}" referenced from within mode "${options.mode}". This may produce unexpected values.${RESET}`); // eslint-disable-line no-console | ||
// unclear if mode is ever appended to id when passed here, but leaving for safety in case | ||
const [rootID, _mode] = id.substring(1, id.length - 1).split('#'); | ||
refID = rootID!; | ||
} | ||
return ['var(', varName(refID, {prefix: options?.prefix, suffix: options?.suffix}), Array.isArray(options?.fallbacks) && options?.fallbacks.length ? `, ${options.fallbacks.join(', ')}` : '', ')'].join(''); | ||
const token = tokens.find((t) => t.id === refID); | ||
// eslint-disable-next-line no-console | ||
if (!token) console.warn(`Tried to reference variable with id: ${refID}, no token found`); | ||
// suffix is only used internally (one place in plugin-sass), so handle it here rather than clutter the public API in defaultNameGenerator | ||
const normalizedSuffix = suffix ? `-${suffix.replace(DASH_PREFIX_RE, '')}` : ''; | ||
const variableId = refID + normalizedSuffix; | ||
return `var(${generateName(variableId, token)})`; | ||
} | ||
@@ -558,0 +571,0 @@ |
Sorry, the diff of this file is not supported yet
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
126204
30
1747
393
Updated@types/culori@^2.0.3
Updated@types/mime@^3.0.3