Global font-family with next/font
?
#1019
Replies: 3 comments 1 reply
-
Here's how I did my setup: import React from 'react';
import { Inter } from 'next/font/google';
const inter = Inter({ subsets: ['latin'] });
export const Fonts: React.FC = () => {
return (
<style jsx global>{`
:root {
--font-family: ${inter.style.fontFamily};
}
`}</style>
);
}; Import the export const fontFamilies = {
'sans-serif': `var(--font-family), Arial, sans-serif`,
};
globalStyle('body', {
fontFamily: fontFamilies['sans-serif'],
});
// for sprinkles
const fontProperties = defineProperties({
properties: {
fontFamily: fontFamilies,
},
}); |
Beta Was this translation helpful? Give feedback.
-
@Msordet's approach works perfectly, until you try to get server components involved. I'm using Next 13's new app directory, which is using React server/client component dichotomy under the hood. For me, the workaround was to use Wherever you're setting up your theme, leave a space for your font variables: /** #/themes/_contract.css.ts */
import { createThemeContract } from "@vanilla-extract/css";
export const theme = createThemeContract({
font: {
display: null,
body: null,
},
}); In your server components, import your font(s) with next: /** app/layout.tsx */
import { Inter } from "next/font/google";
import { assignInlineVars } from "@vanilla-extract/dynamic";
import localFont from "next/font/local";
import { theme } from "#/themes/_contract.css";
// Set up your fonts
const borel = localFont({ src: "./Borel-Regular.ttf" });
const inter = Inter({ subsets: ["latin"] });
export default function RootLayout({ children }: { children: React.ReactNode }) {
return (
<html lang="en">
<body
className={nightTheme}
style={assignInlineVars({
[theme.font.display]: borel.style.fontFamily, // <--- This is the good stuff!
[theme.font.body]: inter.style.fontFamily,
})}
>
{children}
</body>
</html>
);
} Now, you can invoke your theme properties in your css.ts files: /** component.css.ts */
import { theme } from "#/themes/_contract.css";
import { style } from "@vanilla-extract/css";
export const displayHeader = style({
fontFamily: theme.font.display,
}); The end result loads without a FOUC/layout shift! Screen.Recording.2023-07-28.at.11.10.17.PM.mov |
Beta Was this translation helpful? Give feedback.
-
I'm not sure if this is the best solution, but it seems to work well in my environment. /** styles/theme.css.ts */
import { createGlobalTheme } from "@vanilla-extract/css";
/**
* ```
* Font loader values must be explicitly written literals.
* ```
* @see app/layout.tsx
*/
export const vars = createGlobalTheme(":root", {
font: {
jp: `var(--font-noto-sans-jp)`,
en: `var(--font-inter)`,
},
}); /** app/layout.tsx */
import { Noto_Sans_JP, Inter } from "next/font/google";
import "~/styles/theme.css";
export const noto = Noto_Sans_JP({
display: "swap",
subsets: ["latin"],
variable: "--font-noto-sans-jp",
});
export const inter = Inter({
display: "swap",
variable: "--font-inter",
subsets: ["latin"],
});
export default function RootLayout({
children,
}: {
children: React.ReactNode;
}) {
return (
<html lang="ja" className={`${noto.variable} ${inter.variable}`}>
<body>
<RootHeader />
<main>{children}</main>
<RootFooter />
</body>
</html>
);
} /** component.css.ts */
import { style } from "@vanilla-extract/css";
import { vars } from "~/styles/theme.css";
export const displayHeader = style({
fontFamily: vars.font.en,
}); |
Beta Was this translation helpful? Give feedback.
-
Hi, I'm trying to use the custom font in my Next app using
next/font
method.Here's my file having global styles:
& I'm applying it this way:
I just do this and can see an error in the terminal:
How should I do it the ideal way?
I just want to add that
themeClass
to mybody
element.Beta Was this translation helpful? Give feedback.
All reactions