Icons Pack

Material Symbols Outlined variable icon font. Context-aware weight and optical size. Attractor animations via data-vb-attract.

TypeFull (theme + effects + JS)
Theme CSSpacks/icons.theme.css
Effects CSSpacks/icons.effects.css
Effects JSpacks/icons.effects.js
Full bundlepacks/icons.full.css + packs/icons.full.js
Font weight~3.8MB (full set) — subset for production

Coexistence with icon-wc

This pack coexists with the existing <icon-wc> SVG icon system. Use whichever fits your needs:

Loading

<link rel="stylesheet" href="/cdn/packs/icons.full.css"> <script type="module" src="/cdn/packs/icons.full.js"></script> <!-- Icons without attractor animations --> <link rel="stylesheet" href="/cdn/packs/icons.theme.css">

Basic Usage

<!-- Inline with text --> <p>Upload your files <span class="vb-icon">upload</span> to get started.</p> <!-- Button with fill-on-hover --> <button data-vb-icon-fill="hover"> <span class="vb-icon">favorite</span> Save </button> <!-- Standalone large icon --> <span class="vb-icon" data-size="xl">notifications</span> <!-- Always filled --> <span class="vb-icon filled">star</span>

Context-Aware Sizing

Icons automatically adjust weight and optical size based on their context:

ContextWeightOptical Size
h1, h260048
h3, h450040
buttonInherits text weight24
small, caption40020

Icon Axes (Custom Properties)

PropertyRangeDefaultEffect
--vb-icon-fill0–10Outline to filled
--vb-icon-weight100–700400Stroke weight
--vb-icon-grad−50–2000Grade (weight without spacing shift)
--vb-icon-opsz20–4824Optical size

Attractor Animations

Add data-vb-attract to animate an icon. Animations respect prefers-reduced-motion.

<!-- Pulse: fill breathes 0 → 1 → 0 --> <span class="vb-icon" data-vb-attract="pulse">notifications</span> <!-- Beat: weight surges like a heartbeat --> <span class="vb-icon" data-vb-attract="beat">favorite</span> <!-- Bounce: vertical nudge, 3 times --> <span class="vb-icon" data-vb-attract="bounce">arrow_downward</span> <!-- Wiggle: rotation shake, suggests error --> <span class="vb-icon" data-vb-attract="wiggle">warning</span> <!-- Breathe: slow continuous fill oscillation --> <span class="vb-icon" data-vb-attract="breathe">mic</span>
TypeMeaningIterations
pulseSomething happened here3
beatNew/unread content3
bounceCall to action3
wiggleError/warning3
breatheActive/live signalInfinite

Declarative Triggers

Use data-vb-attract-on for event-driven attractors without JS:

<!-- Animate when scrolled into view --> <span class="vb-icon" data-vb-attract="pulse" data-vb-attract-on="visible">star</span> <!-- Animate on hover --> <span class="vb-icon" data-vb-attract="beat" data-vb-attract-on="hover">favorite</span>

JS API

import { attract, attractRandom, enableWhimsy } from 'vanilla-breeze/icons-js'; // Trigger a specific attractor attract(document.querySelector('.vb-icon'), 'pulse'); // Random weighted attractor attractRandom(iconElement); // Idle whimsy mode (opt-in) const { stop } = enableWhimsy(45000);

Whimsy can also be enabled declaratively: <body data-vb-whimsy>

Demo