/* Carga de imágenes: del icono a la nítida, carga «Suave» (v4.1 de Puck, docs/web/komba-paginas, [SITIO] 6, punto 1b de
   implementacion.md; elegida por Antony en lugar de la «Borrosa» v4).
   - <img>: dentro de <span class="k-pic" style="aspect-ratio:W/H; --pic-i:url(icono); --pic-c:#rrggbb">. El icono borroso
     es una CAPA aparte (::before) encima de la foto, que se desvanece en 0,5 s cuando llega la nítida (js/responsive-images.js
     pone pic-ready). La foto nítida no cambia de tamaño ni de color: está quieta debajo.
   - Fondo con texto encima: capa <span class="k-bglayer pic-loading" style="background-image:...; --pic-i:..."> como primera
     hija del bloque (el texto no se desenfoca); la capa borrosa es su ::before.
   - <image> de SVG (tarjetas, despiece): no admite capa; el icono se desenfoca sin cambiar de color y se aclara en 0,5 s.
     Solo filter, nunca transform (perdería el suyo).
   - Lo que ya está en caché llega sin animación (pic-instant).
   - --pic-c es el color dominante de la foto (DominantColor, opcional); sin él, #0d0d0d. */

/* Contenedor: reserva el alto (aspect-ratio) para que nada salte y recorta la capa borrosa. */
.k-pic { position: relative; display: block; width: 100%; height: 100%; overflow: hidden; isolation: isolate; background: var(--pic-c, #0d0d0d); }
.k-pic > img { display: block; width: 100%; height: 100%; object-fit: cover; }
/* Fondo con texto encima: la foto en una capa propia; se sale 24 px por lado. */
.k-bglayer { position: absolute; inset: -24px; z-index: -2; background: var(--pic-c, #0d0d0d) center / cover no-repeat; }
.k-bglayer--fixed { background-attachment: fixed; }
@media (hover: none) { .k-bglayer--fixed { background-attachment: scroll; } }
.e5cards-panel { isolation: isolate; }
.e5cards-panel::before { z-index: -1; }

/* La capa borrosa. Sobresale 40 px por lado y el contenedor la recorta: el borde del desenfoque no se ve. El icono ocupa
   exactamente la caja de la foto (content-box, cover como la foto); debajo, el mismo icono estirado llena el borde de 40 px,
   así el desenfoque no mezcla negro y la nítida llega en el mismo lugar. 16 px de desenfoque: no se ven los cuadros del
   icono de 128 px en una foto ancha; algo de saturación contra el color lavado. */
.k-pic::before, .k-bglayer::before {
  content: ""; position: absolute; inset: -40px; padding: 40px; z-index: 1; pointer-events: none;
  background: var(--pic-i, none) center / cover no-repeat content-box, var(--pic-i, none) center / 100% 100% no-repeat border-box, var(--pic-c, #0d0d0d);
  filter: blur(16px) saturate(1.2) contrast(1.04); }
.k-bglayer::before { inset: 0; padding: 0; }
.k-pic:has(> .pic-ready)::before, .k-bglayer.pic-ready::before { opacity: 0; transition: opacity .5s var(--k-ease, ease); }
/* Si la imagen no llega: se queda el icono, quieto y apenas desenfocado, sin barrido. */
.k-pic:has(> .pic-error)::before, .k-bglayer.pic-error::before { filter: blur(8px) saturate(1.1); }

/* El barrido de luz cálida, como el haz de una lámpara que recorre la foto, dice "está cargando". */
.k-pic::after, .k-bglayer::after { content: ""; position: absolute; inset: 0; z-index: 2; pointer-events: none; opacity: 0; mix-blend-mode: screen;
  background: linear-gradient(105deg, transparent 38%, rgba(var(--k-light, 255, 214, 150), .18) 50%, transparent 62%) 0 0 / 260% 100% no-repeat; transition: opacity .4s; }
.k-pic:has(> .pic-loading)::after, .k-bglayer.pic-loading::after { opacity: 1; animation: k-sweep 1.8s linear infinite; }
@keyframes k-sweep { from { background-position: 130% 0; } to { background-position: -30% 0; } }

/* Sin contenedor (<image> de SVG, el visor de la lupa): el propio elemento se desenfoca mientras llega. */
.pic-loading { filter: blur(var(--pic-blur, 14px)); }
.pic-ready { filter: none; transition: filter .5s var(--k-ease, ease), transform .7s var(--k-ease, ease); }
.pic-error { filter: blur(4px); }
/* Con contenedor el desenfoque es de la capa: la foto no se toca. */
.k-pic > img.pic-loading, .k-pic > img.pic-error, .k-bglayer.pic-loading, .k-bglayer.pic-error { filter: none; transform: none; }

/* Ya en caché: sin fundido ni desenfoque (se conserva la transición del zoom al pasar). */
.pic-instant { transition-property: transform; animation: none; }
.k-pic:has(> .pic-instant)::before, .k-bglayer.pic-instant::before { transition: none; }
.k-cardsvg .photo-frame image.photo-frame-src.pic-instant { transition: transform .4s ease; }

@media (prefers-reduced-motion: reduce) {
  .k-pic:has(> .pic-loading)::after, .k-bglayer.pic-loading::after { animation: none; opacity: .5; background-position: 50% 0; }
  .k-pic:has(> .pic-ready)::before, .k-bglayer.pic-ready::before { transition-duration: .2s; }
  .pic-ready { transition: none; }
}
/* Sin JavaScript no hay cambio de imagen: al menos no se deja el icono desenfocado encima. */
html:not(.js) .pic-loading { filter: none; }
html:not(.js) .k-pic::before, html:not(.js) .k-bglayer::before, html:not(.js) .k-pic::after, html:not(.js) .k-bglayer::after { display: none; }

/* Ajustes de los contenedores que ya existían */
.k-media > .k-pic, .k-card__media > .k-pic, .k-uses li > .k-pic, .k-mosaic figure > .k-pic { height: 100%; }
.k-media > .k-pic > img { filter: saturate(.92) contrast(1.05); }
.k-mosaic figure:hover .k-pic > img.pic-ready, .k-card:hover .k-card__media .k-pic > img.pic-ready { transform: scale(1.04); }
.k-stage > .k-pic { position: absolute; inset: 0; }

/* Ver de cerca (lupa): siempre la variante L. */
.pic-zoomable { cursor: zoom-in; }
.pic-lightbox { position: fixed; inset: 0; z-index: 2000; display: flex; align-items: center; justify-content: center; padding: 1rem; background: rgba(0, 0, 0, .9); cursor: zoom-out; }
.pic-lightbox img { max-width: 100%; max-height: 100%; object-fit: contain; }
