Add inline style elements in Gatsby
I wanted to add inline style elements that are unique per page in this Gatsby blog. My use case was to create several posts where I would share my notes about some typefaces I like from Google Fonts. Inside those posts, I would download the font files, display an interactive component where the user can add text and change font-related CSS attributes, and, finally, show some interesting characters and OpenType features.
I didn’t want the font face rules to be present in all pages, something that would increase the HTML size. If you want that, you have a ton of options. Let’s name a few:
- You can import a CSS file inside your
gatsby-browser.js
file. - You can import a CSS file inside any React component.
- You can create a “global style” with a CSS-in-JS library like
styled-components
oremotion
. - You can use the Gatsby SSR APIs. More specifically, the
onRenderBody
and its parameterssetHeadComponents
andsetPostBodyComponents
.
Coming back to the initial requirement, if you want to add an inline style element that would apply only to a specific page in Gatsby, you can do the following:
const Page2 = () => (
<Layout>
<Helmet>
<style type="text/css">
{`
@font-face {
font-family: "Source Sans Variable";
font-display: swap;
font-weight: 200 900;
font-style: normal;
font-stretch: normal;
src: url("/fonts/SourceSansVariable-Roman-latin.woff2") format("woff2");
unicode-range: U+00-FF;
}
... skipping the rest
`}
</style>
</Helmet>
<h1>Page 1</h1>
{/* content */}
</Layout>
);
In my case, the pages were not JSX files but MDX, and the above snippet didn’t work inside an MDX page. The workaround was simple—and maybe preferred from a “clean code” perspective. I created a react-helmet
only component with the font faces, and then I imported that component inside the MDX. This the component I’m talking about:
import React from "react";
import { Helmet } from "react-helmet";
export default () => (
<Helmet>
<style type="text/css">
{`
@font-face {
... skipping
}
`}
</style>
</Helmet>
);
And this is the import/render inside the MDX page:
import FontFaces from "./font-faces";
<FontFaces />;
The GitHub page for the react-helmet
has a reference guide that shows how to add other types of elements in the head of the document.
react-helmet
properly in Gatsby, you need the gatsby-plugin-react-helmet plugin.Related links
- GitHub issue: Using different CSS file for different pages.
Other things to read
Popular
- Reveal animations on scroll with react-spring
- Gatsby background image example
- Extremely fast loading with Gatsby and self-hosted fonts