SASS Mixins, Functions, Loops (@each, @for), and Inheritance (@extend)0%
Compiling and Organizing Enterprise SCSS: The 7-1 Architecture Pattern

SASS Mixins, Functions, Loops (@each, @for), and Inheritance (@extend)

Advanced15 min readUpdated: 2026-09-10
Study Materials

SASS Mixins, Functions, Loops (@each, @for), and Inheritance (@extend)

Think of a commercial Indian bakery preparing 500 batches of festive Diwali sweets. When making laddus, the chef does not reinvent the recipe from scratch each morning. They have standard stainless steel molds (mixins) that produce identically sized round sweets every single time. For syrup concentration, they have a precise mathematical hydrometer formula (functions) that calculates water-to-sugar ratios. And for packaging gift boxes in 6 different color tins, an automated conveyor belt loops through each batch sequentially.

In SCSS, Mixins, Functions, Inheritance, and Control Loops turn your stylesheet from a passive collection of static rules into a high-powered, automated CSS production engine!


1. @mixin vs. @function: What is the Difference?

The fundamental distinction is simple:

Visual Architecture Blueprint
+-------------------------------------------------------------------------+
|                        MIXIN VS FUNCTION IN SCSS                        |
+-------------------------------------------------------------------------+

  1. @mixin name($arg)                 2. @function name($arg)
     OUTPUTS CSS DECLARATIONS             OUTPUTS A SINGLE COMPUTED VALUE
     (Properties, rules, vendors)         (Pixels, rems, colors, ratios)

     @mixin center-flex {                 @function rem($pixels) {
       display: flex;                       @return ($pixels / 16) * 1rem;
       align-items: center;               }
       justify-content: center;
     }                                    .title {
                                            font-size: rem(32); // 2rem
     .hero {                              }
       @include center-flex;
     }

2. Advanced Parameterized Mixins with Defaults

Mixins can accept arguments, default fallback values, and even variable content blocks via @content:

SCSS
// Breakpoint Mixin with @content
$breakpoints: (
"sm": 576px,
"md": 768px,
"lg": 1024px,
"xl": 1280px
);
 
@mixin respond-to($breakpoint) {
@if map-has-key($breakpoints, $breakpoint) {
@media (min-width: map-get($breakpoints, $breakpoint)) {
@content;
}
} @else {
@warn "Unknown breakpoint: `#{$breakpoint}`.";
}
}
 
// Usage in Components:
.gallery-grid {
display: grid;
grid-template-columns: 1fr;
 
@include respond-to("md") {
grid-template-columns: repeat(2, 1fr);
}
 
@include respond-to("lg") {
grid-template-columns: repeat(4, 1fr);
}
}

3. Mixin (@include) vs. Inheritance (@extend)

A major senior architectural decision in SCSS is choosing between @include and @extend:

SCSS
// Approach A: Mixin
@mixin alert-base {
padding: 1rem;
border-radius: 0.5rem;
}
.alert-warning { @include alert-base; }
.alert-error { @include alert-base; }
 
// Compiles to duplicate CSS rules:
// .alert-warning { padding: 1rem; border-radius: 0.5rem; }
// .alert-error { padding: 1rem; border-radius: 0.5rem; }
 
 
// Approach B: Extend (%placeholder selector)
%alert-base {
padding: 1rem;
border-radius: 0.5rem;
}
.alert-warning { @extend %alert-base; }
.alert-error { @extend %alert-base; }
 
// Compiles to a single comma-separated selector group:
// .alert-warning, .alert-error { padding: 1rem; border-radius: 0.5rem; }

The Caution with @extend:

While @extend produces fewer repeated CSS declarations, it cannot extend across different @media queries and can cause unintended runaway selector explosion if overused on deeply nested classes. Modern industry standards heavily favor parameterized @mixin over @extend!


4. Automation Loops: @for and @each

Why handcraft 12 separate grid column classes or 6 alert banner colors when SASS can loop through them in milliseconds?

The @for Loop (Numerical Increments):

SCSS
// Generate a 12-column grid system
@for $i from 1 through 12 {
.col-#{$i} {
width: percentage($i / 12);
}
}
 
// Compiles into:
// .col-1 { width: 8.33333%; }
// .col-2 { width: 16.66667%; }
// ...
// .col-12 { width: 100%; }

The @each Loop (Iterating Over Maps):

SCSS
$status-colors: (
"info": #3b82f6,
"success": #10b981,
"warning": #f59e0b,
"danger": #ef4444
);
 
@each $state, $color in $status-colors {
.badge--#{$state} {
background-color: rgba($color, 0.15);
color: $color;
border: 1px solid rgba($color, 0.3);
}
}

One 5-line @each loop outputs crisp, semantic badge styles for every state in your design system!


5. Do's and Don'ts of SCSS Logic

CategoryDoDon't
FunctionsUse @function strictly to return calculated values (e.g. rem(24)).Use @function to output CSS declaration blocks (use @mixin instead).
MixinsSupply sensible default parameter values (e.g. @mixin shadow($blur: 10px)).Create bloated mixins with 10 required arguments that nobody can remember.
ExtendUse %placeholder selectors when extending simple component bases.Use @extend across different @media queries, which throws compile errors.
LoopsUse @each and @for to generate repetitive utility classes.Write hundred-line stylesheets containing identical manually typed classes.

6. Quick Revision Summary

Visual Architecture Blueprint
+-------------------------------------------------------------------------+
|                  SCSS LOGIC & DIRECTIVES CHEAT SHEET                    |
+-------------------------------------------------------------------------+

  1. Mixin (Declarations):
     @mixin flex-center { display: flex; align-items: center; justify-content: center; }
     .box { @include flex-center; }

  2. Function (Computed Value):
     @function rem($px) { @return ($px / 16) * 1rem; }
     .text { font-size: rem(20); }

  3. Loops (@for & @each):
     @for $i from 1 through 6 { .stagger-#{$i} { animation-delay: #{$i * 100}ms; } }
     @each $name, $val in $map { .btn-#{$name} { background: $val; } }

Multiple Choice Questions

1. What is the fundamental difference between a SASS @mixin and a SASS @function?

A. A mixin returns a single calculated value, whereas a function outputs CSS declarations B. A mixin outputs CSS declarations, whereas a function returns a single computed value via @return C. Mixins only work in .sass files, while functions only work in .scss files D. Functions execute on the client browser GPU, while mixins run in Node.js

Answer: B Explanation: Mixins are designed to output CSS declarations and selector rules via @include. Functions take inputs, perform computations, and return a single CSS value via @return.

2. What happens in compiled CSS when you use @extend %placeholder on three different classes?

A. The CSS declarations are duplicated three times inside each individual class B. The compiler groups all three classes into a single comma-separated selector sharing the rules C. The classes are converted into HTML data attributes D. The compiler ignores the placeholder

Answer: B Explanation: SASS @extend joins the extending selectors into a single grouped selector list (e.g. .class-a, .class-b, .class-c { ... }), avoiding declaration repetition in the output CSS.

3. What does the @content directive allow inside a SASS @mixin?

A. It fetches remote content via an HTTP GET request B. It acts as a placeholder where nested CSS rule blocks passed to @include will be injected C. It inserts automatic copyright comments at the top of the file D. It validates HTML markup against W3C standards

Answer: B Explanation: @content acts as an injection slot inside a mixin, allowing consumers to pass custom declaration blocks—frequently used for media query wrappers.

4. Which loop directive would you use to iterate over a key-value map of theme colors in SASS?

A. @while B. @for C. @each D. @switch

Answer: C Explanation: The @each $key, $value in $map directive is specifically designed to iterate through lists and key-value maps in SASS.

5. Why will the SASS compiler produce an error if you attempt to @extend an outer selector from inside a @media query?

A. CSS does not allow media queries to contain classes B. SASS cannot guarantee that selector grouping will obey media query boundaries without duplicating rules C. Media queries only accept vanilla CSS without preprocessor directives D. Browsers require all @media blocks to be written at the bottom of the file

Answer: B Explanation: SASS forbids @extend across media query boundaries because grouping an outer selector with an inner media-query selector would alter the cascading rules of elements outside that media query.

Hands-On Practice Challenge: Compiled SCSS Utility Generator

Experience how an enterprise SCSS codebase generates automated grid columns, staggered delay utilities, and semantic badges from loops and mixins.

Next Lesson

Compiling and Organizing Enterprise SCSS: The 7-1 Architecture Pattern

Continue learning with hands-on practice, examples, and exercises in the upcoming topic.

Practice Quiz

Test your understanding of this lesson with 5 questions. Each question has one correct answer.

PrevNext