@stolbov.r/nuxt-font-loader
Version:
Fork of nuxt-font-loader with Nuxt 4 compatibility
158 lines (152 loc) • 4.12 kB
JavaScript
import { defineNuxtModule, createResolver, addImports } from '@nuxt/kit';
const parseFormat = (src, strict = false) => {
let [, format] = src.split(/\.(?=[^.]+$)/);
if (strict) {
if (format === "ttf")
format = "truetype";
else if (format === "otf")
format = "opentype";
}
return format;
};
const generateStyles = (fonts) => {
let fontFace = "";
let classes = "";
let root = "";
let variables = "";
for (const font of fonts) {
const options = {
weight: "400",
display: "optional",
style: "normal",
...font
};
const { src, family, fallback, weight, style, display } = options;
const { class: _class, variable } = options;
const { unicode } = options;
let unicodes = "";
const format = parseFormat(src, true);
const fb = fallback ? `,${fallback}` : "";
const faceRules = [
`font-family:"${family}";`,
`font-weight:${weight};`,
`font-style:${style};`,
`font-display:${display};`,
`src:url('${src}') format('${format}');`
].join("");
if (unicode)
unicodes = `unicode-range:${unicode};`;
if (_class)
classes += `.${_class}{font-family:"${family}"${fb};}`;
if (variable)
variables += `--${variable}:"${family}"${fb};`;
fontFace += `@font-face{${faceRules}${unicodes}}`;
}
if (variables)
root += `:root{${variables}}`;
return {
fontFace,
classes,
root
};
};
const name = "@stolbov.r/nuxt-font-loader";
const version = "1.1.0";
const configKey = "fontLoader";
const compatibility = {
nuxt: ">=3.0.0"
};
var module = defineNuxtModule({
meta: {
name,
version,
configKey,
compatibility
},
defaults: {
autoImport: false
},
setup(options, nuxt) {
const { local, external, autoImport } = options;
const head = nuxt.options.app.head;
const { resolve } = createResolver(import.meta.url);
nuxt.options.build.transpile.push(resolve("./runtime"));
const composables = resolve("./runtime/composables");
nuxt.options.alias["#font-loader"] = composables;
if (autoImport) {
addImports([
{ name: "useLocalFont", from: composables },
{ name: "useExternalFont", from: composables }
]);
}
if (local) {
const { fontFace, classes, root } = generateStyles(local);
const styles = `${fontFace}${classes}${root}`;
for (const font of local) {
const options2 = {
preload: true,
...font
};
if (options2.preload) {
const { src } = options2;
const format = parseFormat(src);
if (!head.link?.some((v) => v.href === src)) {
head.link?.push({
rel: "preload",
as: "font",
type: `font/${format}`,
crossorigin: "anonymous",
href: src
});
}
}
}
head.style?.push(styles);
}
if (external) {
const { classes, root } = generateStyles(external);
const styles = `${classes}${root}`;
let google = false;
let typekit = false;
for (const font of external) {
const { src } = font;
if (src.includes("google") && !google) {
google = true;
head.link?.push(
{
rel: "preconnect",
href: "https://fonts.googleapis.com"
},
{
rel: "preconnect",
crossorigin: "anonymous",
href: "https://fonts.gstatic.com"
}
);
}
if (src.includes("typekit") && !typekit) {
typekit = true;
head.link?.push({
rel: "preconnect",
crossorigin: "anonymous",
href: "https://use.typekit.net"
});
}
head.link?.push(
{
rel: "preload",
as: "style",
href: src
},
{
rel: "stylesheet",
href: src
}
);
}
if (styles)
head.style?.push(styles);
}
}
});
export { module as default };