Задание 1: дёшево вместо дорогого
Заменяем top (reflow) на transform (composite). Эффект для глаза тот же — карточка приподнимается, но без пересчёта раскладки.
Наведи — приподнимается без reflow
.card { transition: transform 200ms ease; }
.card:hover { transform: translateY(-10px); } /* было: top: -10px */
Задание 2: стабильная картинка (нет CLS)
Добавляем размеры (браузер резервирует место) и loading="lazy" для картинок ниже первого экрана. Заодно — современный формат через <picture>.
📄 lesson-49/solution.html
<picture>
<source srcset="banner.avif" type="image/avif">
<source srcset="banner.webp" type="image/webp">
<img src="banner.jpg" width="1200" height="400"
loading="lazy" alt="Баннер">
</picture>
Задание 3: Critical CSS первого экрана
Минимум стилей первого экрана встраиваем инлайн, остальное грузим отдельным минифицированным файлом, не блокируя рендер.
📄 lesson-49/solution.html
<head>
<style>.hero{min-height:70svh;padding:2rem}</style>
<link rel="stylesheet" href="styles.min.css">
</head>
📄 lesson-49/styles.css (минифицируется в styles.min.css)
.hero {
width: min(100% - 2rem, 72rem);
min-height: 70svh;
margin-inline: auto;
padding-block: clamp(3rem, 8vw, 7rem);
}
.hero img { display: block; width: 100%; height: auto; }
.card { transition: transform 180ms ease, opacity 180ms ease; }
.card:hover { transform: translateY(-0.25rem); }
Задание 5: чеклист оптимизации
- Картинки: WebP/AVIF, явные
width/height,loading="lazy"ниже сгиба. - CSS: минифицирован, неиспользуемое вырезано PurgeCSS, Critical CSS инлайн.
- Шрифты:
font-display: swap. - Анимации: только
transform/opacity, никакихwidth/top. - Метрики: Lighthouse зелёный, LCP < 2.5 с, CLS < 0.1, INP < 200 мс.