Jamdesk Documentation logo

Custom CSS

Add custom CSS to override theme styles, tweak typography, or add brand-specific styling. Jamdesk exposes CSS variables for common customizations.

Jamdesk themes provide sensible defaults, but you can add custom CSS to match your brand or adjust specific styles.

Adding Custom CSS

Create a style.css file in your project root (the same folder as your docs.json). Jamdesk applies it to every page automatically; no docs.json entry is needed.

Any .css file in the project root works, not just style.css, which is handy when migrating from another tool. When there are several, Jamdesk combines them in alphabetical filename order.

Run jamdesk dev to preview the result locally. It renders your custom CSS the same way the published site does.

style.css
/* Your custom styles */
article h1 {
  font-size: 2.5rem;
}

For a longer walkthrough that recolors the header and adds a floating button, see CSS & JS Examples.

CSS Variables

Colors and corner radii come from CSS variables. Override them on :root and every component that uses them follows:

style.css
:root {
  /* Page and text colors */
  --color-bg-primary: #ffffff;      /* page background */
  --color-bg-secondary: #f8fafc;    /* inputs, subtle panels */
  --color-text-primary: #0a0a0a;    /* headings */
  --color-text-secondary: #404144;  /* body text */
  --color-text-muted: #737373;      /* captions and hints */
  --color-border: #e2e8f0;

  /* Corner radius for cards, buttons and panels */
  --radius-sm: 6px;
  --radius-md: 8px;
  --radius-lg: 12px;
}

The values above are the Jam theme's defaults. Other themes start from their own values, and you can read any of them in your browser's dev tools on the <html> element.

Your brand colors belong in docs.json, not here. Jamdesk turns colors.primary into the accent used for links, buttons and the active sidebar item. See Custom Colors.

Fonts belong in docs.json too. The fonts field loads a Google Font or your own font file and applies it everywhere. Setting font-family in CSS only works with !important, because themes set fonts with more specific selectors. See Typography.

Common Customizations

Change the Code Font

Code blocks keep the theme's monospace font unless you override it with !important:

@import url('https://fonts.googleapis.com/css2?family=Fira+Code&display=swap');

article pre,
article pre code,
article code {
  font-family: 'Fira Code', monospace !important;
  font-variant-ligatures: common-ligatures;
}

Links inside the page body always have classes, so select them by where they sit, not with a:not([class]):

article .prose a {
  text-decoration: underline;
  text-underline-offset: 3px;
}

article .prose a:hover {
  text-decoration-thickness: 2px;
}

Adjust Heading Spacing

article .prose h2 {
  margin-top: 3rem;
  margin-bottom: 1rem;
}

article .prose h3 {
  margin-top: 2rem;
  margin-bottom: 0.75rem;
}

Style Callouts

Callouts take their colors from variables ending in -bg, -border and -text:

CalloutVariable prefix
<Note>--color-note-
<Info>--color-info-
<Warning>--color-warning-
<Tip>, <Check>--color-success-
<Danger>--color-error-
/* Warmer Note callouts */
:root {
  --color-note-bg: #fef3c7;
  --color-note-border: #f59e0b;
}

Style the Active Tab

article [role="tab"][aria-selected="true"] {
  border-bottom-width: 3px;
}

Dark Mode

Jamdesk adds the dark class to <html> in dark mode. Put dark-mode overrides under html.dark:

/* Light mode */
:root {
  --color-bg-primary: #fffdf7;
}

.custom-banner {
  background: #f0f4ff;
  color: #1e3a5f;
}

/* Dark mode */
html.dark {
  --color-bg-primary: #14110f;
}

html.dark .custom-banner {
  background: #1e293b;
  color: #e2e8f0;
}

[data-theme="dark"] never matches. data-theme on <body> holds your theme's name (jam, nebula and so on), not light or dark.

Selectors to Use

Jamdesk's class names come from Tailwind and can change in any release. These hooks are stable:

SelectorMatches
html.darkThe page while dark mode is on
body[data-theme="jam"]The active theme, by name
header[data-has-tabs]The site header
articleThe current page, including its title
article .proseThe page's body content
#content-scroll-containerThe page content column
[role="tab"][aria-selected="true"]The selected tab in a <Tabs> group

External Fonts

Load fonts through docs.json whenever you can. The fonts field handles Google Fonts and self-hosted files, including .woff2 files in your repo, and applies them to headings and body text.

CSS is the fallback for anything fonts doesn't cover, such as the code font above or a different font on one element. Load the font with @import or @font-face, then set it with !important:

@font-face {
  font-family: 'CustomFont';
  src: url('/fonts/custom-font.woff2') format('woff2');
  font-weight: 400;
  font-display: swap;
}

article .prose blockquote {
  font-family: 'CustomFont', serif !important;
}

Responsive Styles

Use media queries for screen-size adjustments:

/* Phones */
@media (max-width: 768px) {
  article h1 {
    font-size: 1.75rem;
  }
}

Debugging

Right-click an element and choose Inspect to find what to target. Prefer the hooks in Selectors to Use, roles such as role="tab", and CSS variables over long Tailwind class names. If a rule doesn't apply, check the Styles panel for a theme rule that wins on specificity or uses !important.

Limitations

  • CSS is applied globally; use specific selectors to avoid conflicts
  • Some theme styles, including fonts and the Jam header background, use !important or very specific selectors, so you may need !important to override them
  • In local preview (jamdesk dev), edits to your CSS file(s) apply on browser refresh; on your published site, changes take effect on the next build

What's Next?

Theming

Choose and configure themes

CSS & JS Examples

A branded header and a floating Ask AI button