Верстка сайту на HTML5/CSS3
HTML5 та CSS3 — це не застарілий стек, а актуальний мінімум для будь-якого сайту. Семантична розмітка впливає на SEO та доступність. Сучасний CSS3 (Grid, Custom Properties, clamp(), container queries) вирішує задачі, для яких раніше потрібні були JavaScript та складні фреймворки.
Семантична структура документа
Браузери та пошукові машини будують дерево доступності з HTML. Правильна семантика — це не релігія, це конкретні бали в Lighthouse та коректна індексація:
<!DOCTYPE html>
<html lang="uk">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Назва сторінки — Назва сайту</title>
<meta name="description" content="Опис сторінки до 160 символів">
<link rel="canonical" href="https://example.com/page/">
<!-- Попередня завантаження критичних ресурсів -->
<link rel="preload" href="/fonts/inter.woff2" as="font" type="font/woff2" crossorigin>
</head>
<body>
<header role="banner">
<nav aria-label="Основна навігація">
<ul>
<li><a href="/">Головна</a></li>
<li><a href="/about/" aria-current="page">Про нас</a></li>
</ul>
</nav>
</header>
<main id="main-content">
<article>
<header>
<h1>Заголовок статті</h1>
<time datetime="2025-03-28">28 березня 2025</time>
</header>
<section aria-labelledby="section-intro">
<h2 id="section-intro">Вступ</h2>
<p>Текст...</p>
</section>
</article>
<aside aria-label="Схожі матеріали">
<!-- віджети -->
</aside>
</main>
<footer role="contentinfo">
<!-- ... -->
</footer>
</body>
</html>
<article> — самодостатній контент (стаття, карточка товару, коментар). <section> — тематичний блок всередині документа. <aside> — додатковий контент, який не впливає на розуміння основного. Не використовувати <div> там, де є відповідний семантичний тег.
Сучасний CSS: що використовувати у 2025
CSS Custom Properties як система дизайну:
:root {
--font-sans: 'Inter', system-ui, sans-serif;
--font-mono: 'JetBrains Mono', monospace;
--space-xs: 0.25rem;
--space-sm: 0.5rem;
--space-md: 1rem;
--space-lg: 2rem;
--space-xl: 4rem;
--color-text: hsl(220 13% 13%);
--color-muted: hsl(220 9% 46%);
--color-accent: hsl(221 83% 53%);
--color-surface: hsl(0 0% 98%);
}
clamp() для плинної типографіки — розмір шрифту масштабується зі шириною екрана без медіазапитів:
h1 { font-size: clamp(1.75rem, 4vw + 1rem, 3rem); }
h2 { font-size: clamp(1.375rem, 2.5vw + 0.75rem, 2.25rem); }
p { font-size: clamp(1rem, 1.5vw + 0.5rem, 1.125rem); }
Container Queries — компонент адаптується до розміру свого контейнера, а не екрана:
.card-wrapper {
container-type: inline-size;
container-name: card;
}
.card { display: block; }
@container card (min-width: 400px) {
.card {
display: grid;
grid-template-columns: 200px 1fr;
}
}
Продуктивність CSS
Критичний CSS — стилі вище згину вбудовані в <head>, решта завантажується асинхронно:
<style>
/* Вбудований критичний CSS — ~1-3kb */
body { margin: 0; font-family: var(--font-sans); }
header { ... }
.hero { ... }
</style>
<link rel="stylesheet" href="/css/main.css" media="print" onload="this.media='all'">
<noscript><link rel="stylesheet" href="/css/main.css"></noscript>
CSS Containment для ізоляції перерисування:
.card {
contain: layout paint; /* Браузер не буде перерисовувати поза карточкою */
}
will-change тільки де потрібно — не вішати глобально:
/* Тільки на елементи, які дійсно анімуються */
.modal { will-change: transform, opacity; }
Форми
<form novalidate>
<div class="field">
<label for="email">Email <span aria-hidden="true">*</span></label>
<input
type="email"
id="email"
name="email"
autocomplete="email"
aria-required="true"
aria-describedby="email-error"
>
<span id="email-error" role="alert" class="field__error" hidden>
Введіть коректний email
</span>
</div>
</form>
autocomplete — обов'язковий атрибут для форм авторизації та реєстрації. Браузери та менеджери паролів використовують його для автозаповнення.
Зображення
<!-- Адаптивні зображення з srcset -->
<img
src="image-800.webp"
srcset="image-400.webp 400w, image-800.webp 800w, image-1200.webp 1200w"
sizes="(max-width: 640px) 100vw, (max-width: 1024px) 50vw, 400px"
alt="Опис зображення"
width="800"
height="600"
loading="lazy"
decoding="async"
>
<!-- Для hero-зображення — loading="eager" + fetchpriority="high" -->
<img
src="hero.webp"
alt="..."
width="1440"
height="600"
loading="eager"
fetchpriority="high"
>
width та height обов'язкові — браузер резервує місце до завантаження та уникає CLS (Cumulative Layout Shift).
Доступність (a11y)
- Усі інтерактивні елементи досяжні з клавіатури (Tab, Enter, Space)
- Стиль фокуса видимий: не приховувати
outlineбез замінення - Контрастність кольорів ≥ 4.5:1 для тексту (WCAG 2.1 AA)
- Іконки без тексту —
aria-labelабо прихований<span>
/* Користувацький фокус замість типового outline */
:focus-visible {
outline: 2px solid var(--color-accent);
outline-offset: 3px;
border-radius: 3px;
}
/* Приховати для взаємодії з мишею */
:focus:not(:focus-visible) {
outline: none;
}
Терміни
Для верстки на HTML5/CSS3 терміни повністю залежать від обсягу:
| Обсяг | Час |
|---|---|
| Landing page (1 екран) | 0.5–1 день |
| Повноцінна landing page (6–8 секцій) | 1–2 дні |
| Корпоративний сайт (5–10 сторінок) | 3–5 днів |
| Інтернет-магазин (шаблони категорій, товару, кошика) | 5–8 днів |
Це верстка без логіки (без JavaScript фреймворків та backend).







