SnippetUI

Tarjeta de Contador de Estadísticas

Este es un componente de tarjeta de estadísticas que es ideal para paneles y páginas de destino, ya que los números se animan y cuentan desde cero a medida que se desplaza la página.

HTMLCSSJavaScript

Vista previa

Cuatro tarjetas de estadísticas están dispuestas en una cuadrícula y, a medida que se desplaza, los números cuentan desde cero.

🚀
0
Active Users
0%
Satisfaction
🌍
0+
Countries
0%
Uptime

Casos de uso y características

  • Sección de rendimiento de la página de destino: comunique de manera impactante métricas como vistas, satisfacción del cliente, número de países, etc.
  • Usando Intersection Observer: la animación se activa cuando se desplaza y es visible por primera vez.
  • Soporte de punto decimal: admite contadores de números enteros y decimales con el atributo “datos-decimales”.
  • Gestión de color con variables CSS: Puede utilizar la variable --accent para separar los colores de acento para cada tarjeta.

Puntos de diseño y UX

  1. Animación de salida gradual: en lugar de cubic-bezier, una salida gradual única que utiliza una función cúbica oculta es un movimiento natural en el que el valor numérico deja de acelerar.
  2. Texto degradado: con -webkit-background-clip: text, el número en sí se convierte en una gradación, creando una sensación premium.
  3. Formatear números con toLocaleString(): muestra los números según la configuración regional, como 12847 → 12,847.

Cómo personalizar

Cambiar la velocidad de conteo (milisegundos):

// Acortar el tiempo de animación
// animateCounter(el, target, suffix, decimals, 1000);

// Alargar el tiempo de animación
// animateCounter(el, target, suffix, decimals, 3000);

Cambiar los decimales:

<!-- 3 decimales -->
<span class="stat-number" data-target="99.999" data-suffix="%" data-decimals="3">0%</span>

Código de implementación

<div class="stats-grid">
<div class="stat-card stat-card-1">
  <div class="stat-icon">🚀</div>
  <span class="stat-number" data-target="12847" data-suffix="" data-decimals="0">0</span>
  <div class="stat-label">Active Users</div>
</div>
<!-- Estructura similar para otras tarjetas. -->
</div>

<style>
`
.stat-number {
background: linear-gradient(135deg, var(--accent), var(--accent-light));
-webkit-background-clip: text;
-webkit-text-fill-color: transparent;
background-clip: text;
}
.stat-card-1 { --accent: #6366f1; --accent-light: #8b5cf6; }
`
</style>

<script>
(function() {
function animateCounter(el, target, suffix, decimals, duration) {
  var start = null;
  function step(ts) {
    if (!start) start = ts;
    var p = Math.min((ts-start)/duration,1);
    var v = (1-Math.pow(1-p,3))*target;
    el.textContent=(decimals>0?v.toFixed(decimals):Math.floor(v).toLocaleString())+suffix;
    if(p<1) requestAnimationFrame(step);
  }
  requestAnimationFrame(step);
}
var observer = new IntersectionObserver(function(entries) {
  entries.forEach(function(e) {
    if (e.isIntersecting) {
      var el = e.target;
      if (!el.classList.contains('animated')) {
        el.classList.add('animated');
        animateCounter(el, parseFloat(el.dataset.target), el.dataset.suffix || '', parseInt(el.dataset.decimals || '0'), 2000);
      }
    }
  });
}, { threshold: 0.5 });

document.querySelectorAll('.stat-number').forEach(function(el) {
  observer.observe(el);
});
})();
</script>

Estado de compatibilidad del navegador

NavegadorEstado de compatibilidad
Cromo 51+✅ Totalmente compatible
Firefox 55+✅ Totalmente compatible
Safari 12.1+✅Compatibles
Borde 79+✅ Totalmente compatible

La API de Intersection Observer admite Nenewa solo en navegadores modernos. Se requiere un polyfill si desea compatibilidad con IE11.����������������