Tailwind CSS Academy · Lektion

CSS Modules og Tailwind

Brug Tailwind-utilities i CSS Modules for at kombinere scoped komponentstyles med utility-first-tilgangen i React- og Next.js-apps.

Lektion 3 af 413 trin

CSS Modules og Tailwind er en gratis Tailwind CSS Academy-lektion på CoddyKit. Dette er lektion 3 af 4. Du kan læse hele lektionen gratis nedenfor — og derefter øve dig praktisk i browseren med en indbygget kodeeditor og en AI-vejleder, der er tilgængelig døgnet rundt. Den er en del af læringsforløbet i Tailwind CSS Academy, og dine fremskridt synkroniseres på tværs af nettet og CoddyKit-appen. Tailwind CSS Academy-kurset indeholder 4 lektioner i alt.

Hvad er CSS Modules

CSS Modules er CSS-filer, hvor klassenavne som standard er lokalt afgrænsede. Når du importerer et CSS Module i en JavaScript-komponent, bliver klassenavnene omdannet til entydige identifikatorer som Button_root__Xk2p1, så styling ikke lækker mellem komponenter. CSS Modules er indbygget i Next.js og findes i de fleste React-opsætninger via webpack eller Vite.

/* Button.module.css */
.root {
  display: flex;
  align-items: center;
}

// Button.tsx
import styles from './Button.module.css';

const Button = () => (
  // styles.root resolves to 'Button_root__Xk2p1' at runtime
  <button className={styles.root}>Click me</button>
);

Hvorfor kombinere CSS Modules med Tailwind

Tailwind og CSS Modules virker filosofisk modsatrettede — Tailwind undgår at navngive ting, mens CSS Modules netop handler om at navngive ting lokalt. I praksis supplerer de dog hinanden. CSS Modules håndterer komplekse selektorer, :focus-within-kæder og styling af pseudo-elementer, som Tailwind ikke nemt kan udtrykke. Tailwind håndterer størstedelen af den visuelle styling. Tilsammen dækker de alle stylingbehov.

Brug af @apply i CSS Modules

Det mest almindelige mønster til at kombinere de to er at bruge @apply i en CSS Module-fil. Du definerer en lokalt afgrænset klasse i filen .module.css og sammensætter den af Tailwinds hjælpeklasser ved hjælp af @apply. På den måde får du CSS Modules' fordele ved afgrænsning, samtidig med at stylingen udtrykkes med Tailwinds ordforråd.

/* Card.module.css */
.card {
  @apply rounded-xl bg-white p-6 shadow-sm;
}

.cardHeader {
  @apply border-b border-gray-100 pb-4 text-lg font-semibold text-gray-900;
}

.cardBody {
  @apply pt-4 text-sm text-gray-600 leading-relaxed;
}

Import og brug af modulklasser

Importér CSS Module i React-komponenten, og referér til de lokale klassenavne via det importerede objekt. Kombinér modulklassenavne med globale Tailwind-hjælpeklasser i className-egenskaben ved hjælp af strenginterpolation eller clsx. Modulklasser håndterer strukturen, mens Tailwind-hjælpeklasser håndterer responsive ændringer eller tilstandsbestemte tilsidesættelser direkte i JSX.

import styles from './Card.module.css';
import { clsx } from 'clsx';

interface CardProps {
  highlighted?: boolean;
  children: React.ReactNode;
}

export function Card({ highlighted, children }: CardProps) {
  return (
    <div
      className={clsx(
        styles.card,
        // Tailwind utilities alongside module classes
        highlighted && 'ring-2 ring-blue-500',
        'transition hover:shadow-md'
      )}
    >
      {children}
    </div>
  );
}

CSS Modules til komplekse selektorer

Brug CSS Modules specifikt, når Tailwind ikke kan udtrykke en selektor. Det kan for eksempel være styling af et underordnet element baseret på forælderens tilstand med en kompleks selektor eller brug af pseudo-elementerne ::before og ::after til dekorativt indhold, som ikke kan opnås med hjælpeklasser til ring eller skygge. Filen .module.css er det rette sted til disse undtagelser.

/* Dropdown.module.css */
/* Tailwind cannot easily target this nested state */
.trigger:focus-within .menu {
  opacity: 1;
  pointer-events: auto;
  transform: translateY(0);
}

.menu {
  opacity: 0;
  pointer-events: none;
  transform: translateY(-8px);
  transition: opacity 150ms ease, transform 150ms ease;
}

/* Decorative pseudo-element */
.triangle::after {
  content: '';
  position: absolute;
  border: 6px solid transparent;
  border-bottom-color: white;
  top: -12px;
  left: 50%;
  transform: translateX(-50%);
}

Sammensætning af modulklasser

CSS Modules understøtter nøgleordet composes, som kan arve styling fra en anden klasse i den samme fil eller i en anden modulfil. Dette er CSS Modules' indbyggede tilgang til genbrug. Hvor @apply tilføjer Tailwind-hjælpeklasser, tilføjer composes andre modulklasser — du kan kombinere begge dele i den samme fil for maksimal fleksibilitet.

/* base.module.css */
.baseButton {
  @apply inline-flex items-center rounded-lg px-4 py-2 font-semibold
         transition focus:outline-none focus:ring-2 focus:ring-offset-2;
}

/* Button.module.css */
.primary {
  composes: baseButton from './base.module.css';
  @apply bg-blue-600 text-white focus:ring-blue-500 hover:bg-blue-700;
}

.secondary {
  composes: baseButton from './base.module.css';
  @apply border border-gray-300 text-gray-700 hover:bg-gray-50 focus:ring-gray-400;
}

CSS Modules i Next.js

Next.js understøtter CSS Modules direkte uden konfiguration — enhver fil, der slutter på .module.css, bliver automatisk afgrænset. Den PostCSS-pipeline, der behandler Tailwind, behandler også CSS Modules, så @apply fungerer i modul-filer uden yderligere opsætning. Det gør Next.js til det ideelle miljø for kombinationen af Tailwind og CSS Modules.

// next.config.js — no extra config needed
// CSS Modules and Tailwind work automatically

// Any .module.css file is locally scoped:
// components/Hero/Hero.module.css  ← scoped
// styles/globals.css               ← global (Tailwind entry)

// Verify your postcss.config.js has tailwindcss:
module.exports = {
  plugins: {
    tailwindcss: {},
    autoprefixer: {},
  },
};

Hvornår skal du IKKE bruge CSS Modules

CSS Modules tilføjer en fil pr. komponent og et ekstra indirektionslag, som er unødvendigt omfattende for de fleste Tailwind-komponenter. Undgå dem til simple komponenter, hvor al styling uden problemer kan være i className med hjælpeklasser. Gem CSS Modules til komponenter med oprigtigt kompleks CSS, der overstiger det, hjælpeklasser kan udtrykke — det er normalt mindre end 10 % af komponenterne i et typisk Tailwind-projekt.

// DON'T: CSS Module for a simple button — overkill
/* Button.module.css */
/* .btn { @apply px-4 py-2 rounded bg-blue-600 text-white; } */

// DO: Just use classes directly — much simpler
const Button = ({ children }) => (
  <button className="rounded bg-blue-600 px-4 py-2 font-semibold text-white
                     transition hover:bg-blue-700">
    {children}
  </button>
);

Global og lokal CSS i Next.js

I Next.js kan kun globale stylesheets (globals.css) importeres i _app.js eller layout.tsx. CSS Modules importeres kun i den komponent, der bruger dem. Denne begrænsning er tilsigtet — den forhindrer utilsigtet lækage af global styling. Tailwinds globale direktiver findes altid i globals.css; modulfiler indeholder kun komponentafgrænsede regler.

// app/layout.tsx — import globals (Tailwind entry) here
import '../styles/globals.css';     // ✅ global CSS
// import './Card.module.css';      // ❌ Error: CSS Modules not allowed here

// components/Card.tsx — import module CSS here
import styles from './Card.module.css'; // ✅ scoped to this file

export function Card() {
  return <div className={styles.card}>...</div>;
}

Fejlfinding af CSS Module-klassenavne

I udviklingstilstand indeholder CSS Module-klassenavne filnavnet og det oprindelige klassenavn, så de er nemme at læse: Card_root__Xk2p1. I produktion forkortes de til uigennemsigtige hashværdier for at spare plads. Hvis en modulklasse ikke anvendes, skal du inspicere elementet i browserens DevTools for at se det genererede klassenavn og bekræfte, at det findes på elementets klasseliste. Kontrollér, om egenskabsadgangen indeholder en stavefejl: styles.cardHeader, ikke styles.card-header (camelCase er påkrævet).

/* Card.module.css */
.card-header { /* ← hyphenated CSS class */ }

// Card.tsx
import styles from './Card.module.css';

// Accessing hyphenated classes requires bracket notation:
const el = <div className={styles['card-header']}>...</div>;

// Better: use camelCase in the module file:
/* .cardHeader { } */
const el2 = <div className={styles.cardHeader}>...</div>;

TypeScript-understøttelse af CSS Modules

TypeScript kender som standard ikke formen på CSS Module-imports, hvilket får styles.anyClass til at blive typekontrolleret som any. Installér typescript-plugin-css-modules, eller brug typed-css-modules til at generere .d.ts-typedeklarationer for hver modulfil. Det giver autofuldførelse af klassenavne i din editor og opdager stavefejl på kompileringstidspunktet.

npm install -D typescript-plugin-css-modules

// tsconfig.json
{
  "compilerOptions": {
    "plugins": [
      { "name": "typescript-plugin-css-modules" }
    ]
  }
}

// Now styles.cardHeader shows autocomplete in VS Code
// and TypeScript warns if you access a class that does not exist

Hurtigt tjek

Test din forståelse af begreberne i Tailwind CSS Mastery fra denne lektion.

Opsummering af lektionen

I denne lektion har du lært at: bruge @apply i CSS Modules til at kombinere afgrænsede klassenavne med Tailwind-hjælpeklasser, vide hvornår du skal vælge CSS Modules frem for at blive i className (komplekse selektorer og pseudo-elementer), samt bruge TypeScript-understøttelse til typesikker adgang til CSS Module-klasser. Næste gang ser vi på, hvordan Tailwind skaleres på tværs af monorepoer.

Gratis at komme i gang

Lær HTML med en AI-underviser — gratis

Skriv og kør rigtig kode i din browser, få øjeblikkelig hjælp fra en AI-underviser døgnet rundt, og fortsæt, hvor du slap, på web eller i appen.

Kurser
30
Lektioner
120

Ofte stillede spørgsmål

Er lektionen “CSS Modules og Tailwind” gratis?

Ja — hele teksten til “CSS Modules og Tailwind” kan læses gratis her på nettet. Hvis du vil øve dig interaktivt med en indbygget kodeeditor og en AI-vejleder døgnet rundt og få adgang til resten af Tailwind CSS Academy-kurset, skal du opgradere til CoddyKit PRO. Tailwind CSS Academy-kurset indeholder 4 lektioner i alt.

Hvad lærer jeg i “CSS Modules og Tailwind”?

Brug Tailwind-utilities i CSS Modules for at kombinere scoped komponentstyles med utility-first-tilgangen i React- og Next.js-apps. Du øver dig i Tailwind CSS Academy med praktisk kode, som du kører direkte i browseren, og en AI-vejleder døgnet rundt besvarer dine spørgsmål, mens du arbejder dig gennem lektionen.

Skal jeg have erfaring for at begynde på Tailwind CSS Academy?

Der kræves ingen tidligere erfaring. Tailwind CSS Academy på CoddyKit er tilrettelagt for både begyndere og øvede, så du kan starte her eller fra begyndelsen og lære i dit eget tempo. Dette er lektion 3 af 4.

Hvor lang tid tager lektionen “CSS Modules og Tailwind”?

De fleste CoddyKit-lektioner tager cirka 5–10 minutter. Hver lektion er kort og interaktiv, så du gør løbende fremskridt og kan fortsætte, hvor du slap – på både web og app.

Kan jeg skrive og køre kode i denne Tailwind CSS Academy-lektion?

Ja. Alle Tailwind CSS Academy-lektioner har en indbygget kodeeditor, så du kan skrive og køre rigtig kode direkte i din browser og få øjeblikkelig feedback fra AI – uden lokal opsætning.

Alle lektioner i dette kursus

  1. Organisering af filer og mapper
  2. Sameksistens med ældre CSS
  3. CSS Modules og Tailwind
  4. Skalering af Tailwind på tværs af monorepos
← Tilbage til Tailwind CSS Academy