Mixins in SASS

Dit artikel legt mixins in SASS uit.

We leggen mixins in SASS uit met praktische voorbeelden.

YouTube Video

Mixins in SASS

Overzicht – Wat is een Mixin?

Mixins zijn een mechanisme waarmee je veelgebruikte sets van stijleigenschappen kunt definiëren als herbruikbare functies, die je overal waar nodig kunt aanroepen. Ze zijn erg handig om je CSS-klassen en meerdere eigenschappen DRY (Don't Repeat Yourself) te houden.

Voorbeeld: De eenvoudigste mixin

Hieronder staat een eenvoudig voorbeeld van een mixin die border-radius en box-shadow samen hergebruikt. Door deze mixin aan te roepen, kun je dezelfde uitstraling op meerdere elementen toepassen.

 1// Simple mixin that applies border-radius and box-shadow
 2@mixin card-style {
 3  border-radius: 8px;
 4  box-shadow: 0 4px 10px rgba(0, 0, 0, 0.12);
 5  background: #fff;
 6}
 7
 8.card {
 9  @include card-style;
10  padding: 1rem;
11}
  • Met deze mixin hoef je stijlen niet meer direct te herhalen.
  • Het aanroepen vereist slechts één regel: @include card-style;.

Mixins met argumenten (parameters)

Mixins kunnen argumenten accepteren, net als functies. Hierdoor kun je het uiterlijk wijzigen met dezelfde logica. Hierna volgt een voorbeeld waarbij kleur als argument wordt gebruikt.

 1// Mixin with parameters: accepts a color and optional radius
 2@mixin colored-box($bg-color, $radius: 4px) {
 3  background-color: $bg-color;
 4  border-radius: $radius;
 5  padding: 0.75rem;
 6}
 7
 8.box-primary {
 9  @include colored-box(#007acc);
10}
11
12.box-custom {
13  @include colored-box(#ffcc00, 12px);
14}
  • Door een standaardwaarde op te geven, kun je het gedrag bepalen als een argument wordt weggelaten.
  • In dit voorbeeld wordt de standaardradius gebruikt en wordt alleen de achtergrondkleur overschreven.

Situaties waarin variadische argumenten (...) worden gebruikt

Als je meerdere waarden wilt accepteren, kun je variadische argumenten ($args...) gebruiken. Dit is handig voor het genereren van utility classes of het doorgeven van fallback-lijsten.

Het is handig als je meerdere lettertypefamilies of schaduwwaarden wilt doorgeven.

1// Mixin that accepts variable arguments and forwards them to box-shadow
2@mixin multi-shadow($shadows...) {
3  box-shadow: $shadows;
4}
5
6.panel {
7  @include multi-shadow(0 2px 4px rgba(0,0,0,0.08), 0 8px 16px rgba(0,0,0,0.06));
8}
  • Aan de aanroepzijde kun je meerdere schaduwen doorgeven, gescheiden door komma's.
  • Op deze manier kun je dezelfde mixin gebruiken voor zowel eenvoudige als complexe schaduwen.

Mixins met @content — Een blok ontvangen

Met @content kan een mixin een stijlblok van de aanroeper ontvangen. Hierdoor kan de mixin een algemene wrapper aanbieden, terwijl de aanroeper de inhoudelijke details opgeeft.

 1// Mixin that sets up a responsive container and yields to caller via @content
 2@mixin responsive-container($max-width: 1200px) {
 3  margin-left: auto;
 4  margin-right: auto;
 5  padding-left: 1rem;
 6  padding-right: 1rem;
 7  max-width: $max-width;
 8
 9  @content; // place where caller's styles are inserted
10}
11
12.header {
13  @include responsive-container(1000px) {
14    display: flex;
15    align-items: center;
16    justify-content: space-between;
17  }
18}
  • Aan de aanroepzijde kun je een blok toevoegen aan @include om stijlen in te voegen.
  • Dit patroon is handig voor layout-wrappers zoals grids, kaarten en formulieren.

Geavanceerde mixins met conditionals en loops

Controle-structuren zoals @if en @for kunnen binnen mixins worden gebruikt. Je kunt deze gebruiken om utility-generatie te automatiseren en responsieve instellingen te groeperen.

Hieronder vind je een voorbeeld van het automatisch genereren van utility class-widths.

 1@use 'sass:math';
 2
 3// Mixin that generates width utility classes from a list of fractions
 4@mixin generate-widths($fractions) {
 5  @each $name, $fraction in $fractions {
 6    .w-#{$name} {
 7      width: math.percentage($fraction);
 8    }
 9  }
10}
11
12$widths: (
13  '1-4': 0.25,
14  '1-3': 0.3333,
15  '1-2': 0.5,
16  '3-4': 0.75
17);
18
19@include generate-widths($widths);
  • Door eenvoudigweg een map met de gewenste breuken aan de aanroepende zijde door te geven, kun je automatisch de bijbehorende utility-klassen in één keer genereren.
  • Het gebruik van deze aanpak heeft als voordeel dat handmatige stijldefinities worden verminderd, terwijl de consistentie in je ontwerp behouden blijft.

Mixins versus placeholders (%placeholder)

Terwijl mixins direct een set eigenschappen invoegen, worden placeholders gebruikt met @extend bij het overerven van stijlen. Mixins kunnen in sommige gevallen dubbele CSS genereren, maar met @extend kan de CSS in bepaalde situaties compacter worden.

Door de doelen en verschillen te begrijpen van de CSS die met elke methode wordt gegenereerd, kun je de meest optimale aanpak kiezen.

 1// Placeholder example (for comparison)
 2%btn-base {
 3  display: inline-block;
 4  padding: 0.5rem 1rem;
 5  border-radius: 4px;
 6}
 7
 8.btn-primary {
 9  @extend %btn-base;
10  background: #007acc;
11  color: #fff;
12}
13
14.btn-secondary {
15  @extend %btn-base;
16  background: #e0e0e0;
17}
  • Wanneer je een placeholder @extend, kunnen meerdere selectoren worden samengevoegd in één regel, wat resulteert in compactere CSS.
  • Aan de andere kant bieden mixins flexibiliteit doordat ze eigenschappen direct invoegen waar nodig en helpen ze onbedoelde samenvoeging van selectoren te voorkomen.

Algemene praktische patronen (responsive, vendor prefixes, enz.)

In de praktijk is het handig om algemene bewerkingen zoals vendor prefixes en responsive eigenschappen in mixins te plaatsen. Hieronder staat een voorbeeld waarin transform en prefix-eigenschappen worden gecombineerd. Je kunt code centraliseren voor browsercompatibiliteit, waardoor onderhoud eenvoudiger wordt.

 1// Mixin for transform with vendor prefixes
 2@mixin transform($value) {
 3  -webkit-transform: $value;
 4  -ms-transform: $value;
 5  transform: $value;
 6}
 7
 8.icon-rotate {
 9  @include transform(rotate(45deg));
10}
  • Het gebruik is eenvoudig en je kunt het overal toepassen, bijvoorbeeld @include transform(rotate(10deg));.
  • Zelfs als voorvoegsels in de toekomst overbodig worden, wordt het onderhoud eenvoudiger omdat een aanpassing aan de mixin overal in je codebase wordt doorgevoerd.

Praktisch voorbeeld: kaarten en knoppen gecombineerd

Hieronder staat een voorbeeld waarbij de knopstijlen die binnen de kaart worden gebruikt, zijn verenigd met een mixin, waardoor ze kunnen worden aangepast aan de themakleur.

Dit organiseert het vaak gebruikte 'kaart + knop'-patroon met mixins.

 1// Simple mixin that applies border-radius and box-shadow
 2@mixin card-style {
 3  border-radius: 8px;
 4  box-shadow: 0 4px 10px rgba(0, 0, 0, 0.12);
 5  background: #fff;
 6}
 7
 8// Mixin for transform with vendor prefixes
 9@mixin transform($value) {
10  -webkit-transform: $value;
11  -ms-transform: $value;
12  transform: $value;
13}
14
15// Button mixin with theme and size parameters
16@mixin btn($bg, $color: #fff, $padding: 0.5rem 1rem) {
17  display: inline-block;
18  padding: $padding;
19  background: $bg;
20  color: $color;
21  border-radius: 6px;
22  text-decoration: none;
23  cursor: pointer;
24  @include transform(translateY(0)); // reuse earlier transform mixin
25}
26
27// Card mixin that accepts inner button styling via @content
28@mixin card($gap: 1rem) {
29  @include card-style; // reuse earlier card-style mixin
30  padding: $gap;
31  @content;
32}
33
34.card-feature {
35  @include card {
36    .title { font-size: 1.125rem; margin-bottom: 0.5rem; }
37    .cta {
38      @include btn(#007acc);
39    }
40  }
41}
42
43.card-warning {
44  @include card {
45    .title { font-weight: bold; }
46    .cta {
47      @include btn(#ff6600);
48    }
49  }
50}
  • Door deze mixins te gebruiken, kun je componenten beknopt schrijven.

Let op de prestaties en de gegenereerde CSS

Omdat mixins bij elke aanroep eigenschappen invoegen, kan uitgebreid gebruik van @include voor dezelfde regel je uiteindelijke CSS vergroten. Je kunt optimaliseren door ze te combineren met placeholders en componentontwerp waar nodig.

Bovendien zijn de volgende maatregelen ook effectief.

  • Stijlen die vaak worden gebruikt, moeten als klassen worden gemaakt voor hergebruik.
  • Veelvoorkomende patronen moeten worden gegroepeerd met behulp van @content.
  • Het genereren van complexe utilities moet alleen tijdens de build-fase gebeuren.

Tips voor eenvoudiger debuggen

Bij het gebruik van mixins is het ook belangrijk om methoden te bedenken die het debuggen en onderhoud verbeteren. Door duidelijke variabelenamen te gebruiken en opmerkingen toe te voegen binnen mixins, wordt het later bij code-review eenvoudiger te begrijpen. Ook, als de functionaliteit complex wordt, maakt het verdelen van de mixin in kleinere onderdelen het testen eenvoudiger en verbetert het de onderhoudbaarheid.

Daarnaast maakt het inschakelen van source maps het eenvoudig om te achterhalen welke mixin welke CSS heeft gegenereerd, waardoor problemen makkelijker zijn te isoleren.

Hieronder vind je een voorbeeld van een goed te begrijpen mixin met documentatie-opmerkingen.

1// Example: readable mixin with clear param names and comments
2/// Adds a subtle focus ring for accessibility
3/// $color - ring color
4/// $size - thickness of the ring
5@mixin focus-ring($color: #007acc, $size: 2px) {
6  outline: none;
7  box-shadow: 0 0 0 $size rgba(blue($color), 0.15);
8}
  • Georganiseerde documentatie-opmerkingen zoals deze maken het eenvoudiger om kennis te delen en te begrijpen binnen het team.
  • Omdat SASS documentatie-opmerkingen automatisch kunnen worden geëxtraheerd met compatibele tools, zijn ze ook nuttig voor het genereren van documenten zoals stijlgidsen.

Samenvatting

Omdat mixins je in staat stellen vaak gebruikte stijlen te bundelen voor hergebruik, helpen ze codeverdubbeling te verminderen en de onderhoudbaarheid te verbeteren. Als meerdere selectoren dezelfde regels delen, overweeg dan niet alleen mixins te gebruiken maar ook @extend (placeholders). Verder maakt @content een flexibele scheiding tussen layout-wrappers en inhoud mogelijk, maar overmatig gebruik van @include kan leiden tot opgeblazen gegenereerde CSS, dus wees voorzichtig. Het is belangrijk om optimaal gebruik te maken van argumenten, standaardwaarden en variadische argumenten om mixins te ontwerpen die generiek en eenvoudig uit te breiden zijn.

Je kunt het bovenstaande artikel volgen met Visual Studio Code op ons YouTube-kanaal. Bekijk ook het YouTube-kanaal.

YouTube Video