html, body {
    width: 100%;
    height: 100%;
    margin: 0;
    padding: 0;
    overflow: hidden;
    /* ⚡ Evita scroll bouncing en iOS Safari */
    overscroll-behavior: none;
    /* ⚡ Previene text selection accidental durante resize */
    -webkit-user-select: none;
    user-select: none;
    /*
     * 🔤 Suavizado tipográfico para HTML/SVG fuera del canvas (loaders,
     * tooltips nativos…). El texto del propio Compose se rasteriza en el
     * canvas y depende de Skia, pero estos hints no estorban.
     */
    -webkit-font-smoothing: antialiased;
    -moz-osx-font-smoothing: grayscale;
    text-rendering: optimizeLegibility;
}

/*
 * ⚡ Canvas de Compose Multiplatform.
 *
 * IMPORTANTE: NO forzar `width: 100% !important; height: 100% !important;`.
 * Skiko ajusta el backing-store del canvas en píxeles físicos
 * (multiplicado por `devicePixelRatio`) y fija los atributos
 * `width`/`height` HTML para que el ratio CSS-px ↔ device-px sea 1:1.
 * Si forzamos un tamaño CSS distinto, el navegador escala los píxeles
 * del canvas → todo el texto rasterizado por Skia se ve borroso
 * (especialmente en pantallas HiDPI o con zoom del navegador).
 *
 * Para que el canvas ocupe toda la ventana usamos la regla de
 * `position: absolute; top/left/right/bottom: 0;` de más abajo, que
 * delega el sizing al ComposeViewport sin estirar bitmap.
 */
canvas {
    display: block;
    /*
     * will-change: transform promueve a capa GPU propia (compositing layer)
     * SIN invalidar cache de contenido (contents lo invalidaba → lento en Safari).
     */
    will-change: transform;
    /*
     * contain: layout paint → el browser sabe que nada fuera del canvas cambia
     * cuando el canvas se repinta. NO usamos "strict" porque incluye "size"
     * que interfiere con el resize dinámico del canvas.
     */
    contain: layout paint;
    /* Fuerza compositing en Safari/WebKit (translateZ hack) */
    -webkit-transform: translateZ(0);
    transform: translateZ(0);
    /* Hint para que Safari use GPU rasterization */
    -webkit-backface-visibility: hidden;
    backface-visibility: hidden;
    /*
     * 🔤 Pedimos al navegador la mejor calidad posible al componer el
     * canvas (importante en navegadores que sí escalan el canvas, p. ej.
     * con zoom de página). Reemplaza el antiguo `pixelated` durante
     * resize, que dejaba el texto serrado.
     */
    image-rendering: auto;
    image-rendering: -webkit-optimize-contrast;
}

/*
 * ⚡ Durante resize activo NO degradamos la calidad del canvas: con
 * `pixelated` el texto del Compose quedaba aliado y "pixelado" mientras
 * el usuario arrastraba el borde de la ventana. El throttling de
 * ResizeObserver de index.html ya es suficiente para mantener fluidez.
 */
canvas.resizing {
    /* sin overrides: mantenemos la nitidez */
}

/* ⚡ Reduce layout thrashing durante resize del navegador */
body > canvas,
body > div {
    position: absolute;
    top: 0;
    left: 0;
    right: 0;
    bottom: 0;
}