CSS 70 views

Custom CSS Tooltip with Transition Effects

Create a reusable tooltip component using only HTML and CSS with smooth transitions for enhanced user experience.

By TWC Team • Jan 28, 2026

Code

/* Custom CSS Tooltip (HTML + CSS only)
   Reusable, themeable tooltip with smooth transitions; supports hover + keyboard focus. */

:root {
  --tt-bg: rgba(0, 0, 0, 0.78);
  --tt-fg: #fff;
  --tt-radius: 0.5rem;
  --tt-pad-y: 0.4rem;
  --tt-pad-x: 0.6rem;
  --tt-max-w: 18rem;
  --tt-offset: 0.6rem;
  --tt-arrow: 0.45rem;
  --tt-dur: 200ms;
  --tt-ease: cubic-bezier(.2, .8, .2, 1);
  --tt-z: 1000;
}

/* Tooltip container (BEM: tooltip + tooltip__content) */
.tooltip {
  position: relative;
  display: inline-flex; /* modern layout; keeps icon/text aligned */
  align-items: center;
  gap: 0.35rem;
  cursor: help;
  -webkit-tap-highlight-color: transparent; /* better mobile UX */
}

/* Tooltip bubble */
.tooltip__content {
  /* Hidden by default (visibility avoids accidental hover/focus capture) */
  visibility: hidden;
  opacity: 0;
  pointer-events: none;

  position: absolute;
  z-index: var(--tt-z);
  left: 50%;
  bottom: calc(100% + var(--tt-offset));
  transform: translateX(-50%) translateY(0.15rem);
  transform-origin: 50% 100%;

  max-width: min(var(--tt-max-w), 80vw); /* responsive */
  width: max-content;
  background: var(--tt-bg);
  color: var(--tt-fg);
  border-radius: var(--tt-radius);
  padding: var(--tt-pad-y) var(--tt-pad-x);
  font-size: 0.875rem;
  line-height: 1.25;
  text-align: center;
  white-space: normal;
  filter: drop-shadow(0 6px 18px rgba(0, 0, 0, 0.2));

  transition:
    opacity var(--tt-dur) var(--tt-ease),
    transform var(--tt-dur) var(--tt-ease),
    visibility 0s linear var(--tt-dur); /* prevents flicker on hide */
}

/* Arrow (pure CSS) */
.tooltip__content::after {
  content: "";
  position: absolute;
  left: 50%;
  top: 100%;
  transform: translateX(-50%);
  border: var(--tt-arrow) solid transparent;
  border-top-color: var(--tt-bg);
}

/* Show on hover + keyboard focus */
.tooltip:hover .tooltip__content,
.tooltip:focus-within .tooltip__content {
  visibility: visible;
  opacity: 1;
  transform: translateX(-50%) translateY(0);
  transition-delay: 0s;
}

/* Prefer reduced motion for accessibility */
@media (prefers-reduced-motion: reduce) {
  .tooltip__content { transition: none; transform: translateX(-50%); }
}

/* Fallback for older browsers without drop-shadow (keeps contrast) */
@supports not (filter: drop-shadow(0 0 0 rgba(0, 0, 0, 0.2))) {
  .tooltip__content { box-shadow: 0 10px 20px rgba(0, 0, 0, 0.25); }
}

/* Example usage (HTML):
   <span class="tooltip">
     <button type="button" aria-describedby="tt-1">Info</button>
     <span id="tt-1" class="tooltip__content" role="tooltip">Additional details shown on hover/focus.</span>
   </span>
*/
Back to Snippets