Transformaciones Disponibles

Redimensionar: w=800&h=600
Calidad: q=85
Formato: f=webp
Recorte: c=fill
DPR: dpr=2
Filtros: blur=10

🌐 URLs de Variantes

Las variantes se generan dinámicamente usando parámetros URL:

URL Pattern
https://limbo.lefebvre.es/assets/{assetId}/transform?w=800&h=600&f=webp&q=85

Ejemplos de Transformaciones

Original
1920×1080
Original

Sin transformaciones

800×600
?w=800&h=600

Redimensionado a 800×600

400×400
?w=400&h=400&c=fill

Cuadrado con recorte

Blur
?blur=10&w=400

Con efecto blur

⚙️ Parámetros de Transformación

Lista completa de parámetros disponibles para personalizar tus imágenes:

📏 Parámetros de Tamaño

w
integer
Ancho en píxeles (1-4000)
w=800
h
integer
Alto en píxeles (1-4000)
h=600
dpr
float
Device Pixel Ratio (1.0-3.0)
dpr=2
ar
string
Aspect ratio (16:9, 4:3, 1:1)
ar=16:9
Ejemplos de Redimensionado
# Ancho fijo, alto proporcional
?w=800

# Dimensiones específicas
?w=800&h=600

# Para pantallas Retina
?w=400&h=300&dpr=2

# Aspect ratio específico
?w=800&ar=16:9

✂️ Parámetros de Recorte

c
string
Modo de recorte
c=fill
g
string
Gravedad del recorte
g=center
x
integer
Offset X para recorte manual
x=100
y
integer
Offset Y para recorte manual
y=50
Modos de Recorte
scale

Escala sin recortar, puede distorsionar

fit

Encaja completo, puede haber barras

fill

Llena completamente, recorta si es necesario

crop

Recorte manual con coordenadas

Opciones de Gravedad
center
north
south
east
west
northeast
northwest
southeast
southwest
face

🖼️ Parámetros de Formato

f
string
Formato de salida
f=webp
q
integer
Calidad (1-100)
q=85
auto
string
Optimización automática
auto=format
Formatos Soportados
webp Moderno

Excelente compresión, soporte amplio

avif Avanzado

Mejor compresión, soporte limitado

jpeg Universal

Compatibilidad total

png Universal

Soporte para transparencia

Optimización Automática
# Formato automático basado en soporte del navegador
?auto=format&w=800

# Calidad automática basada en contenido
?auto=quality&w=800

# Ambos: formato y calidad automáticos
?auto=format,quality&w=800

✨ Parámetros de Efectos

blur
integer
Desenfoque (1-100)
blur=10
sharpen
integer
Enfoque (1-100)
sharpen=50
brightness
integer
Brillo (-100 a 100)
brightness=20
contrast
integer
Contraste (-100 a 100)
contrast=15
saturation
integer
Saturación (-100 a 100)
saturation=-30
grayscale
boolean
Convertir a escala de grises
grayscale=true
Ejemplos de Efectos
# Imagen en blanco y negro
?w=800&grayscale=true

# Efecto vintage
?w=800&brightness=-10&contrast=20&saturation=-40

# Imagen para placeholder
?w=400&h=300&blur=50&brightness=-50

# Thumbnail con enfoque
?w=200&h=200&c=fill&sharpen=30

📱 Implementación Responsiva

Ejemplos prácticos para implementar imágenes responsivas y optimizadas:

HTML

<!-- Picture element con formato automático -->
<picture>
  <source 
    media="(min-width: 1200px)" 
    srcset="https://limbo.lefebvre.es/assets/{id}/transform?w=1200&auto=format&dpr=1 1x,
            https://limbo.lefebvre.es/assets/{id}/transform?w=1200&auto=format&dpr=2 2x"
  >
  <source 
    media="(min-width: 768px)" 
    srcset="https://limbo.lefebvre.es/assets/{id}/transform?w=800&auto=format&dpr=1 1x,
            https://limbo.lefebvre.es/assets/{id}/transform?w=800&auto=format&dpr=2 2x"
  >
  <img 
    src="https://limbo.lefebvre.es/assets/{id}/transform?w=400&auto=format" 
    srcset="https://limbo.lefebvre.es/assets/{id}/transform?w=400&auto=format&dpr=1 1x,
            https://limbo.lefebvre.es/assets/{id}/transform?w=400&auto=format&dpr=2 2x"
    alt="Descripción de la imagen"
    loading="lazy"
  >
</picture>

<!-- Hero image con múltiples breakpoints -->
<div class="hero">
  <picture>
    <source 
      media="(min-width: 1400px)" 
      srcset="https://limbo.lefebvre.es/assets/{id}/transform?w=1400&h=600&c=fill&g=center&f=webp"
    >
    <source 
      media="(min-width: 1024px)" 
      srcset="https://limbo.lefebvre.es/assets/{id}/transform?w=1200&h=500&c=fill&g=center&f=webp"
    >
    <source 
      media="(min-width: 768px)" 
      srcset="https://limbo.lefebvre.es/assets/{id}/transform?w=800&h=400&c=fill&g=center&f=webp"
    >
    <img 
      src="https://limbo.lefebvre.es/assets/{id}/transform?w=600&h=300&c=fill&g=center&f=jpeg" 
      alt="Hero image"
      class="hero-image">
  </picture>
</div>

<!-- Grid de productos -->
<div class="product-grid">
  <article class="product-card">
    <img 
      src="https://limbo.lefebvre.es/assets/{id}/transform?w=300&h=300&c=fill&auto=format&q=85"
      srcset="https://limbo.lefebvre.es/assets/{id}/transform?w=300&h=300&c=fill&auto=format&q=85&dpr=1 1x,
              https://limbo.lefebvre.es/assets/{id}/transform?w=300&h=300&c=fill&auto=format&q=85&dpr=2 2x"
      alt="Producto"
      loading="lazy"
      class="product-image">
  </article>
</div>
CSS
/* Background images responsivos */
.hero {
  min-height: 60vh;
  background-image: url('https://limbo.lefebvre.es/assets/{id}/transform?w=600&h=300&c=fill&f=webp');
  background-size: cover;
  background-position: center;
}

@media (min-width: 768px) {
  .hero {
    background-image: url('https://limbo.lefebvre.es/assets/{id}/transform?w=1200&h=500&c=fill&f=webp');
  }
}

@media (min-width: 1200px) {
  .hero {
    background-image: url('https://limbo.lefebvre.es/assets/{id}/transform?w=1600&h=600&c=fill&f=webp');
  }
}

/* Grid de imágenes adaptativo */
.image-grid {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(250px, 1fr));
  gap: 1rem;
}

.image-grid img {
  width: 100%;
  height: 200px;
  object-fit: cover;
  border-radius: 8px;
}

/* Placeholder con blur */
.image-placeholder {
  background-image: url('https://limbo.lefebvre.es/assets/{id}/transform?w=50&h=50&blur=20&q=20');
  background-size: cover;
  filter: blur(5px);
  transition: filter 0.3s ease;
}

.image-placeholder.loaded {
  filter: none;
}

/* Aspectos ratio fijos */
.aspect-16-9 {
  aspect-ratio: 16 / 9;
}

.aspect-4-3 {
  aspect-ratio: 4 / 3;
}

.aspect-1-1 {
  aspect-ratio: 1 / 1;
}
JavaScript
class ResponsiveImageManager {
    constructor(baseUrl = 'https://limbo.lefebvre.es') {
        this.baseUrl = baseUrl;
        this.breakpoints = {
            mobile: 480,
            tablet: 768,
            desktop: 1024,
            wide: 1400
        };
    }

    generateVariantUrl(assetId, options = {}) {
        const params = new URLSearchParams();
        
        Object.entries(options).forEach(([key, value]) => {
            if (value !== undefined && value !== null) {
                params.append(key, value);
            }
        });

        return `${this.baseUrl}/assets/${assetId}/transform?${params.toString()}`;
    }

    createResponsiveSrcSet(assetId, widths, options = {}) {
        return widths.map(width => {
            const variantOptions = { ...options, w: width };
            const url = this.generateVariantUrl(assetId, variantOptions);
            return `${url} ${width}w`;
        }).join(', ');
    }

    createRetinaSrcSet(assetId, width, options = {}) {
        const normalUrl = this.generateVariantUrl(assetId, { ...options, w: width });
        const retinaUrl = this.generateVariantUrl(assetId, { ...options, w: width, dpr: 2 });
        return `${normalUrl} 1x, ${retinaUrl} 2x`;
    }

    optimizeImagesOnLoad() {
        // Detectar soporte de formatos modernos
        const supportsWebP = this.checkWebPSupport();
        const supportsAVIF = this.checkAVIFSupport();

        document.querySelectorAll('[data-limbo-asset]').forEach(img => {
            const assetId = img.dataset.limboAsset;
            const width = img.dataset.width || 800;
            const height = img.dataset.height;
            const crop = img.dataset.crop || 'fit';

            const options = {
                w: width,
                auto: 'format,quality',
                c: crop
            };

            if (height) options.h = height;

            // Aplicar formato óptimo
            if (supportsAVIF) {
                options.f = 'avif';
            } else if (supportsWebP) {
                options.f = 'webp';
            }

            img.src = this.generateVariantUrl(assetId, options);
            
            // Configurar srcset para diferentes densidades
            img.srcset = this.createRetinaSrcSet(assetId, width, options);
        });
    }

    checkWebPSupport() {
        return new Promise(resolve => {
            const webP = new Image();
            webP.onload = webP.onerror = () => resolve(webP.height === 2);
            webP.src = 'data:image/webp;base64,UklGRjoAAABXRUJQVlA4IC4AAACyAgCdASoCAAIALmk0mk0iIiIiIgBoSygABc6WWgAA/veff/0PP8bA//LwYAAA';
        });
    }

    checkAVIFSupport() {
        return new Promise(resolve => {
            const avif = new Image();
            avif.onload = avif.onerror = () => resolve(avif.height === 2);
            avif.src = 'data:image/avif;base64,AAAAIGZ0eXBhdmlmAAAAAGF2aWZtaWYxbWlhZk1BMUIAAADybWV0YQAAAAAAAAAoaGRscgAAAAAAAAAAcGljdAAAAAAAAAAAAAAAAGxpYmF2aWYAAAAADnBpdG0AAAAAAAEAAAAeaWxvYwAAAABEAAABAAEAAAABAAABGgAAAB0AAAAoaWluZgAAAAAAAQAAABppbmZlAgAAAAABAABhdjAxQ29sb3IAAAAAamlwcnAAAABLaXBjbwAAABRpc3BlAAAAAAAAAAIAAAACAAAAEHBpeGkAAAAAAwgICAAAAAxhdjFDgQ0MAAAAABNjb2xybmNseAACAAIAAYAAAAAXaXBtYQAAAAAAAAABAAEEAQKDBAAAACVtZGF0EgAKCBgABogQEAwgMg8f8D///8WfhwB8+ErK42A=';
        });
    }

    lazyLoadImages() {
        if ('IntersectionObserver' in window) {
            const imageObserver = new IntersectionObserver((entries, observer) => {
                entries.forEach(entry => {
                    if (entry.isIntersecting) {
                        const img = entry.target;
                        const assetId = img.dataset.limboAsset;
                        
                        if (assetId && !img.src) {
                            this.loadImage(img, assetId);
                        }
                        
                        observer.unobserve(img);
                    }
                });
            });

            document.querySelectorAll('[data-limbo-asset]:not([src])').forEach(img => {
                imageObserver.observe(img);
            });
        }
    }

    loadImage(img, assetId) {
        const width = img.dataset.width || img.offsetWidth || 400;
        const height = img.dataset.height;
        const crop = img.dataset.crop || 'fit';

        const options = {
            w: width,
            auto: 'format,quality',
            c: crop
        };

        if (height) options.h = height;

        // Mostrar placeholder blur mientras carga
        const placeholderUrl = this.generateVariantUrl(assetId, {
            w: 50,
            h: 50,
            blur: 20,
            q: 20
        });

        img.style.backgroundImage = `url(${placeholderUrl})`;
        img.style.backgroundSize = 'cover';

        // Cargar imagen principal
        const fullImg = new Image();
        fullImg.onload = () => {
            img.src = fullImg.src;
            img.srcset = this.createRetinaSrcSet(assetId, width, options);
            img.style.backgroundImage = '';
            img.classList.add('loaded');
        };

        fullImg.src = this.generateVariantUrl(assetId, options);
    }
}

// Inicializar
const imageManager = new ResponsiveImageManager();

document.addEventListener('DOMContentLoaded', () => {
    imageManager.optimizeImagesOnLoad();
    imageManager.lazyLoadImages();
});

⚡ Performance y Cache

Las variantes se optimizan automáticamente para máximo rendimiento:

🚀

Cache Inteligente

Las variantes se cachean automáticamente con TTL de 1 año. Cache invalidation automático al actualizar assets.

🌐

CDN Global

Distribución mundial con edge caching para latencia mínima. Optimización automática de rutas.

🎛️

Compresión Avanzada

Algoritmos de última generación para máxima compresión sin pérdida de calidad visual.

📊

Métricas en Tiempo Real

Monitoreo de performance, cache hit rate y optimización de bandwidth automática.

Headers de Cache

HTTP Headers
Cache-Control: public, max-age=31536000, immutable
ETag: "a1b2c3d4e5f6g7h8i9j0"
Last-Modified: Wed, 15 Jan 2024 14:35:18 GMT
Content-Type: image/webp
Vary: Accept, DPR, Width

🎯 Casos de Uso Avanzados

🛍️

E-commerce

Galerías de productos con zoom, múltiples vistas y optimización automática para conversión máxima.

?w=400&h=400&c=fill&q=90&sharpen=10
📰

Blog/Magazine

Imágenes editoriales adaptativas con múltiples breakpoints y formatos optimizados para lectura.

?w=800&ar=16:9&auto=format,quality
🎨

Portfolio

Presentación de trabajos artísticos con máxima calidad y efectos visuales personalizados.

?w=1200&f=jpeg&q=95&sharpen=5
📱

Móvil First

Optimización extrema para conexiones lentas con progressive loading y placeholders inteligentes.

?w=400&f=webp&q=75&auto=format

🚀 Próximos Pasos