Skip to content

Bookmark Toggle

A copy-paste micro-interactions component in pure HTML, CSS & vanilla JS. Zero dependencies, framework-agnostic, MIT-licensed.

Micro-interactionsHTMLCSSJavaScriptany framework

Copy into your project

HTML
<button class="nuda-bookmark" aria-label="Bookmark" aria-pressed="false">
  <svg viewBox="0 0 24 24" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
    <path d="M19 21l-7-5-7 5V5a2 2 0 0 1 2-2h10a2 2 0 0 1 2 2z"/>
  </svg>
</button>
CSS
/* Bookmark Toggle
   Bookmark icon with fill animation.
   Customize: --bookmark-color */

.nuda-bookmark {
  --bookmark-color: #f59e0b;
  background: none;
  border: none;
  cursor: pointer;
  padding: 8px;
  outline: none;
}

.nuda-bookmark svg {
  width: 24px;
  height: 24px;
  fill: none;
  stroke: #888;
  transition: all 0.3s cubic-bezier(0.4, 0.2, 0.2, 1.3);
  will-change: transform;
}

.nuda-bookmark[aria-pressed="true"] svg {
  fill: var(--bookmark-color);
  stroke: var(--bookmark-color);
  transform: scale(1.15);
}

.nuda-bookmark:active svg {
  transform: scale(0.85);
}

@media (prefers-reduced-motion: reduce) {
  .nuda-bookmark svg { transition: none; }
}
JavaScript
/* Bookmark Toggle — vanilla JS
   Toggles aria-pressed state. */

(function () {
  document.querySelectorAll(".nuda-bookmark").forEach(function (btn) {
    btn.addEventListener("click", function () {
      var pressed = btn.getAttribute("aria-pressed") === "true";
      btn.setAttribute("aria-pressed", String(!pressed));
    });
  });
})();

How to use Bookmark Toggle

Paste the HTML where you need it and the CSS into a global stylesheet (or a <style> tag). Every class is prefixed nuda- so it never collides with Tailwind or your own styles. Tweak the CSS custom properties to match your design system.

Works in React, Vue, Svelte, Astro, Next.js, Nuxt, Laravel Blade, Django, Rails — or a single .html file. No npm install, no build step.

More micro-interactions components

← Browse all NudaUI components