unocss-transformer-alias
Version:
Transform alias for UnoCSS shortcuts
71 lines (68 loc) • 2.11 kB
JavaScript
import { isStaticShortcut, isString, expandVariantGroup } from '@unocss/core';
function transformerAlias(options) {
return {
name: "unocss-transformer-alias",
enforce: "pre",
async transform(code, _, { uno }) {
await transformAlias(code, uno, options);
}
};
}
async function transformAlias(code, uno, {
prefix = "*",
keep = "+"
} = {}) {
if (typeof keep === "string")
keep = { prefix: keep, block: true };
const extraRE = new RegExp(`(${escapeRegExp(prefix)}|${escapeRegExp(keep.prefix)})([\\w-:]+)`, "g");
const map = /* @__PURE__ */ new Map();
for (const item of Array.from(code.original.matchAll(extraRE))) {
let result = map.get(item[0]);
if (result === false) {
continue;
} else if (!result) {
const r = await expandShortcut(item[2], uno);
if (r) {
result = r[0].join(" ");
map.set(item[0], result);
} else {
map.set(item[0], false);
continue;
}
}
if (item[1] === keep.prefix) {
result = `${item[2]} ${result}`;
if (keep.block)
uno.config.blocklist = [.../* @__PURE__ */ new Set([...uno.config.blocklist, item[2]])];
}
code.overwrite(item.index, item.index + item[0].length, result);
}
}
async function expandShortcut(input, uno, depth = 5) {
if (depth <= 0)
return;
let result;
for (const shortcut of uno.config.shortcuts) {
if (isStaticShortcut(shortcut)) {
if (shortcut[0] === input)
result = shortcut[1];
} else {
const match = input.match(shortcut[0]);
if (match != null)
result = shortcut[1](match, {});
}
}
if (isString(result))
result = expandVariantGroup(result.trim()).split(/\s+/g);
if (!result)
return;
return [
(await Promise.all(
result.filter((s) => s !== input).map(async (r) => (isString(r) ? (await expandShortcut(r, uno, depth - 1))?.[0] : void 0) || [r])
)).flat(1).filter(Boolean)
];
}
function escapeRegExp(str) {
return str.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
}
export { transformerAlias as default, expandShortcut, transformAlias };