color.complement() belongs to the built-in sass:color module. It builds a complementary color by rotating hue 180deg in a polar color space—at compile time. This page covers the default HSL behavior for hex/RGB, optional $space (Dart Sass 1.79+), how it differs from adjust / change, and five compiled examples.
01
Concept
Opposite hue (+180deg)
02
Module
@use "sass:color"
03
Space
hsl · hwb · lch · oklch
04
Default
Legacy → hsl
05
Alias
complement()
06
Practice
5 examples
Concept
What Is color.complement()?
Complement means “spin this color halfway around the hue wheel.” Official docs describe it as rotating $color’s hue by 180deg in a polar space. Saturation and lightness stay related to the original—you get a strong opposite accent, not a random new palette color.
Picture a color wheel. If your brand sits at one point, the complement sits directly across from it. Call color.complement() twice and you land back near the start—handy for checking round-trips in examples.
Foundation
📝 Syntax
Load the color module, then pass a color and an optional polar space:
Polar space used for the 180deg rotation: hsl, hwb, lch, or oklch. Dart Sass 1.79+. For legacy colors without $space, Sass defaults to hsl.
Return value
Type
Meaning
Color
A complementary color in the same space as $color (after the hue rotation in $space).
Modules
📦 Loading sass:color
Prefer the module API. Official docs also document the global name complement() for older stylesheets.
styles.scss
// Recommended — namespaced
@use "sass:color";
$accent: color.complement(#6b717f);
// Optional — bring members into the current namespace
@use "sass:color" as *;
$accent: complement(#6b717f);
// Optional — custom namespace
@use "sass:color" as c;
$accent: c.complement(#6b717f);
// Legacy global name
$accent: complement(#6b717f);
⚠️
Put @use first
Keep @use "sass:color"; near the top of the file. Built-in modules need Dart Sass (about 1.23+). Passing $space / oklch needs 1.79+.
Rules
🎨 Polar Spaces Only
Official docs require a polar color space for the rotation. RGB is not a valid $space here—you need a space that has a hue angle.
Allowed $space
Notes
hsl
Default for legacy hex/RGB colors when $space is omitted
hwb
Hue + whiteness/blackness model
lch / oklch
Modern perceptual spaces (Dart Sass 1.79+)
💡
Heads up from the docs
For historical reasons, $space is optional when $color is already in a legacy space—then it defaults to hsl. Official guidance: pass $space explicitly once you are on Dart Sass 1.79+.
Support
🛠 Compatibility
This is about Sass compilers, not browsers. Compiled CSS receives a finished color—no color.complement() call remains.
Feature
Dart Sass
Notes
@use "sass:color" / color.complement
1.23+
Preferred module API; legacy colors use HSL by default
$space (hsl / hwb / lch / oklch)
1.79+
Explicit polar-space rotation
Global complement()
Long-standing
Prefer module form in new SCSS
LibSass / Ruby Sass
No modern module API
May expose global complement(); prefer Dart Sass
Cheat Sheet
⚡ Quick Reference
Goal
Code
Import color
@use "sass:color";
Complement a hex (HSL default)
color.complement(#6b717f)
Brand accent pair
color.complement($brand)
Explicit HSL (1.79+)
color.complement($c, $space: hsl)
Oklch complement (1.79+)
color.complement($c, $space: oklch)
Legacy global
complement(#6b717f)
Compare
📋 complement vs adjust vs change
All three can touch hue, but they answer different questions.
Helper
What it does
Mental model
color.complement()
Rotate hue by 180deg
“Opposite on the wheel”
color.adjust()
Add/subtract a hue amount
“Plus 30deg”
color.change()
Set hue to an exact angle
“Make hue 200deg”
styles.scss
@use "sass:color";
$brand: #336699;
// Clearest intent for “opposite hue”
$opposite: color.complement($brand);
// Similar idea with an explicit HSL hue nudge
$also: color.adjust($brand, $hue: 180deg);
Hands-On
Examples Gallery
Each example uses @use "sass:color". Open View Compiled CSS to see what Dart Sass emits.
📚 Getting Started
Official-style complement and everyday brand accents.
Example 1 — Official Hex Complement
Rotate a muted blue-gray halfway around the HSL wheel.
Each call keeps the color’s general intensity while flipping hue. Blue becomes a warm brown-orange, green becomes magenta, and red becomes cyan—classic complements.
📈 Practical Patterns
Brand pairs, modern spaces, and the global alias.
Example 3 — Brand + Complement Pair
Use one token for fill and its complement for contrast text; double-check the round-trip.
styles.scss
@use "sass:color";
$brand: #336699;
.card {
background: $brand;
color: color.complement($brand);
// 180deg twice → back to the brand hue
border-color: color.complement(color.complement($brand));
}
The complement provides a related opposite accent. Complementing twice restores the original brand hex for this opaque color—useful when teaching hue rotation.
Example 4 — Complement in oklch (Dart Sass 1.79+)
Official docs show a different result when you rotate in oklch instead of HSL.
Same starting hex, different polar ruler. HSL and oklch complements are both “opposite,” but they do not always land on the same RGB result—so pick the space your design system prefers.
Example 5 — Module vs Global complement()
Both names perform the same HSL default complement on legacy colors.
Module and global calls match. Prefer color.complement() so readers see the helper comes from sass:color.
Applications
🚀 Real-World Use Cases
Accent pairs — derive a secondary brand color from one hex token.
Charts & tags — give series or badges opposite hues that still feel related.
Alert styling — invent a contrasting outline or icon color quickly.
Design exploration — preview complements before locking a palette.
Theme kits — store $brand and $brand-complement together.
Space experiments — compare HSL vs oklch complements on Dart Sass 1.79+.
🧠 How Compilation Works
1
Write SCSS
Call color.complement($color) after @use.
Source
2
Pick a polar space
Use $space, or default legacy colors to hsl.
Space
3
Rotate hue +180deg
Spin halfway around the wheel in that space.
Complement
4
✓
Plain CSS color ships
Browsers receive hex/rgb—not a Sass call.
Watch Out
⚠️ Common Pitfalls
Expecting RGB $space — only polar spaces (hsl, hwb, lch, oklch) are valid.
Using $space on older Dart Sass — needs 1.79+; bare color.complement($hex) still works earlier.
Assuming HSL and oklch match — same hex can yield different complements per space.
Low-saturation colors — complements stay muted when the original is nearly gray.
Confusing with invert — complement flips hue; it is not the same as photographic invert.
Pro Tips
💡 Best Practices
✅ Do
Use @use "sass:color" and color.complement() in new SCSS
Store one brand token and derive the opposite accent
Pass $space explicitly on Dart Sass 1.79+
Compare HSL vs oklch when building modern palettes
Check contrast after complementing—opposite hue ≠ readable contrast
❌ Don’t
Pass a non-polar space such as rgb to $space
Expect the browser to run color.complement
Rely on LibSass for the modern module API
Assume every complement pair passes accessibility contrast checks
Hand-pick dozens of opposite hexes you can derive
Summary
Key Takeaways
Knowledge Unlocked
Five things to remember about color.complement()
Opposite hue in a polar space—fast accents from one brand color.
5
Core concepts
📝01
Call
complement($color)
API
📦02
Module
sass:color
@use
🎨03
Does
hue +180deg
Rotate
⚡04
Space
hsl / oklch
Polar
✓05
Global
complement()
Alias
❓ Frequently Asked Questions
color.complement($color, $space: null) rotates the color’s hue by 180deg in a polar color space and returns the complementary color. Example: color.complement(#6b717f) is #7f796b.
Add @use "sass:color"; then call color.complement($brand). Prefer the module form in new SCSS. The global alias is complement().
Official docs require a polar space: hsl, hwb, lch, or oklch. The $space argument needs Dart Sass 1.79+. For legacy hex/RGB colors without $space, Sass defaults to hsl.
Yes for the same space. Rotating hue by 180deg twice returns you to the starting hue, so color.complement(color.complement($c)) matches $c for typical opaque colors.
complement is a convenience for a full opposite hue. You can also write color.adjust($c, $hue: 180deg) in HSL for a similar idea, but complement is clearer when you want the opposite color.
The module form needs Dart Sass with @use (about 1.23+). The $space parameter needs Dart Sass 1.79+. LibSass/Ruby Sass may expose a global complement() but lack the modern module API.
Did you know?
Official Sass docs stress that $space must be polar, and that for legacy colors it historically defaults to hsl. Once you are on Dart Sass 1.79+, passing $space: oklch (or another polar space) can produce a different complementary RGB than the classic HSL path—even from the same hex.
color.complement() is the clearest way to ask Sass for the opposite hue. Use it for accent pairs from one brand token, remember polar spaces only, pass $space explicitly on Dart Sass 1.79+, and prefer @use "sass:color".