Mobile-first approach
Mobile-first vuol dire progettare prima per lo schermo piccolo e poi aggiungere man mano che c'è spazio. Il vantaggio vero è che ti costringe a decidere cosa conta: su 360 pixel di larghezza non ci sta il superfluo, e quello che sopravvive è quello che serviva.
Punti chiave
- Il responsive moderno parte dal mobile e arricchisce verso il desktop con media query
min-width. - Le container queries adattano i componenti al loro contenitore, non al viewport.
clamp()easpect-ratiocreano tipografia e proporzioni fluide senza moltiplicare i breakpoint.- CSS Grid
auto-fite i pattern Flexbox costruiscono layout adattivi quasi senza media query. - I breakpoint vanno scelti in base al contenuto e validati con testing su dispositivi reali.
In pratica, il CSS base definisce gli stili per schermi piccoli. Le media query con min-width aggiungono complessità man mano che lo schermo si allarga:
/* Stili base: mobile */
.card { padding: 1rem; }
/* Tablet in su */
@media (min-width: 768px) {
.card { padding: 2rem; display: flex; gap: 2rem; }
}
/* Desktop */
@media (min-width: 1200px) {
.card { max-width: 1140px; margin: 0 auto; }
}
Questo approccio garantisce che il sito funzioni perfettamente su mobile anche se il CSS delle media query non viene caricato. Google utilizza il mobile-first indexing: la versione mobile del sito è quella che viene indicizzata e valutata per il ranking nella SEO.
"Progettare mobile-first non significa togliere funzionalità al desktop. Significa costruire le fondamenta giuste e aggiungere piani solo dove servono."
Container queries CSS
Le container queries sono la rivoluzione più significativa nel responsive design dopo le media query. Mentre le media query rispondono alle dimensioni del viewport, le container queries rispondono alle dimensioni del contenitore padre.
/* Dichiara il contenitore */
.card-wrapper {
container-type: inline-size;
container-name: card;
}
/* Stili in base alla larghezza del contenitore */
@container card (min-width: 400px) {
.card { display: flex; flex-direction: row; }
.card-image { width: 40%; }
}
@container card (min-width: 700px) {
.card { gap: 2rem; }
.card-title { font-size: 1.5rem; }
}
Qui sta il salto per i componenti riusabili: la stessa card si adatta da sola dentro una colonna stretta o dentro un'area larga, senza sapere niente della finestra del browser. Le container query sono supportate da tutti i browser moderni dal 2023, quindi si possono usare senza scuse.
Fluid typography con clamp()
Con clamp() il testo cresce insieme allo schermo, senza dover scrivere una media query per ogni soglia. Prima servivano cinque o sei salti di dimensione fissa, con i titoli che scattavano passando da un formato all'altro; adesso una riga sola fa una scala continua. Sui titoli e sui pulsanti si vede subito: restano leggibili dal telefono al monitor grande, e non li tocchi più.
/* clamp(minimo, preferito, massimo) */
h1 { font-size: clamp(1.75rem, 4vw + 0.5rem, 3.5rem); }
h2 { font-size: clamp(1.25rem, 3vw + 0.25rem, 2.25rem); }
p { font-size: clamp(1rem, 1.5vw + 0.5rem, 1.25rem); }
Il valore minimo garantisce la leggibilità su mobile, il valore preferito (che usa unità viewport come vw) crea la fluidità, e il valore massimo impedisce che il testo diventi troppo grande su schermi ultrawide. La combinazione di vw con rem nel valore preferito crea una transizione più morbida.
La proprietà aspect-ratio ti fa dichiarare il rapporto fra base e altezza in una riga, e manda in pensione il vecchio trucco del padding percentuale, che funzionava e che nessuno riusciva a leggere:
.video-wrapper { aspect-ratio: 16 / 9; width: 100%; }
.avatar { aspect-ratio: 1; border-radius: 50%; }
.card-image { aspect-ratio: 4 / 3; object-fit: cover; }
CSS Grid: auto-fit e auto-fill
CSS Grid con auto-fit e auto-fill crea layout responsive senza media query. Le colonne si adattano automaticamente allo spazio disponibile.
/* Griglia automatica con colonne minimo 280px */
.grid {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(280px, 1fr));
gap: 1.5rem;
}
La differenza fra i due è piccola e conta:
- auto-fill: crea il maggior numero possibile di colonne, anche se vuote. Le colonne vuote occupano spazio.
- auto-fit: come auto-fill, ma le colonne vuote collassano a 0, permettendo agli elementi esistenti di espandersi per riempire lo spazio.
Nella maggior parte dei casi, auto-fit è la scelta giusta: gli elementi si distribuiscono uniformemente e la griglia si adatta fluidamente da 1 colonna su mobile a 3-4 colonne su desktop, il tutto senza una sola media query.
Per i layout complicati le griglie con le aree nominate sono il modo più leggibile: il CSS diventa un disegno della pagina che si capisce a occhio.
.page {
display: grid;
grid-template-areas:
"header header"
"sidebar main"
"footer footer";
grid-template-columns: 250px 1fr;
}
@media (max-width: 768px) {
.page {
grid-template-areas: "header" "main" "sidebar" "footer";
grid-template-columns: 1fr;
}
}
Flexbox advanced patterns
Flexbox eccelle nella distribuzione di elementi lungo un singolo asse. Combinato con flex-wrap e dimensioni minime, crea pattern responsive potenti.
/* Holy Albatross: switch automatico da riga a colonna */
.container {
display: flex;
flex-wrap: wrap;
gap: 1rem;
}
.container > * {
flex: 1 1 300px; /* cresci, riduciti, base 300px */
}
Questo pattern, noto come "Holy Albatross", fa sì che gli elementi si dispongano in riga quando c'è spazio sufficiente e si impilino automaticamente in colonna quando lo spazio si riduce, il tutto senza media query.
Altri schemi Flexbox che uso spesso:
- Sticky footer:
body { display: flex; flex-direction: column; min-height: 100vh; }conmain { flex: 1; }per un footer sempre in fondo alla pagina. - Centering perfetto:
display: flex; align-items: center; justify-content: center;rimane il modo più affidabile per centrare qualsiasi elemento. - Spacing automatico:
margin-left: auto;su un elemento flex per spingerlo a destra (utile nelle navbar).
Breakpoint strategy moderna
La strategia dei breakpoint è evoluta significativamente. L'approccio moderno si basa sul contenuto, non sui dispositivi.
| Approccio | Strategia | Quando usarlo |
|---|---|---|
| Device-based (vecchio) | 320px, 768px, 1024px, 1440px | Mai: i dispositivi cambiano troppo rapidamente |
| Content-based (moderno) | Breakpoint dove il layout si rompe | Sempre: adatta il design al contenuto reale |
| Fluid + breakpoint | clamp() + pochi breakpoint strutturali | Da preferire: riduce le media query al minimo |
Un approccio pratico consiste nell'usare 3 breakpoint strutturali per il layout generale (colonne della pagina, visibilità della sidebar) e affidarsi a container queries, clamp() e auto-fit per tutto il resto. La maggior parte dei siti moderni necessita al massimo di 3-4 media query globali.
Immagini responsive
Le immagini sono quasi sempre la cosa più pesante di una pagina, e servirne una da 2000 pixel a un telefono è il modo più rapido di rovinare le performance.
L'attributo srcset permette al browser di scegliere l'immagine più appropriata:
<img
src="hero-800.webp"
srcset="hero-400.webp 400w,
hero-800.webp 800w,
hero-1200.webp 1200w,
hero-1600.webp 1600w"
sizes="(max-width: 768px) 100vw,
(max-width: 1200px) 75vw,
60vw"
alt="Descrizione immagine"
loading="lazy"
>
L'elemento <picture> offre un controllo ancora maggiore: puoi servire formati diversi e immagini diverse per contesti differenti:
<picture>
<source media="(max-width: 768px)" srcset="hero-mobile.avif" type="image/avif">
<source media="(max-width: 768px)" srcset="hero-mobile.webp" type="image/webp">
<source srcset="hero-desktop.avif" type="image/avif">
<source srcset="hero-desktop.webp" type="image/webp">
<img src="hero-desktop.jpg" alt="Descrizione" loading="lazy">
</picture>
loading="lazy" per le immagini below the fold e fetchpriority="high" per l'immagine hero (LCP).
Testing cross-device
Provare su dispositivi veri resta l'unica cosa che dice la verità, e nel frattempo si combina qualche strumento:
- Chrome DevTools (Device Mode): simulazione rapida di diverse risoluzioni e condizioni di rete. Utile per lo sviluppo quotidiano, ma non sostituisce i test reali.
- BrowserStack / Sauce Labs: piattaforme cloud che offrono accesso a dispositivi e browser reali. Servono a testare Safari su iOS, Samsung Internet e browser meno comuni.
- Lighthouse: audit automatico di performance, accessibilità, SEO e best practice. Eseguilo sia in modalità mobile che desktop.
- Dispositivi fisici: testa almeno su un iPhone recente, un Android di fascia media e un tablet. Le differenze di rendering tra browser reali e simulatori possono essere significative.
- Resize manuale del browser: ridimensiona la finestra gradualmente per individuare i punti in cui il layout si rompe, quelli sono i breakpoint naturali del contenuto.
L'errore che vedo più spesso è provare il sito solo sul proprio telefono, che di solito è un telefono buono su una connessione buona. Una fetta importante delle persone naviga con Android economici, schermi a bassa risoluzione e linee lente, e lì il sito che «funziona» diventa un altro sito. Vale la pena leggere anche gli errori comuni nel web design, perché quasi tutti si vedono solo in queste condizioni.
Vuoi imparare ad applicarlo davvero?
Scopri i corsi e la formazione di Federico Boggia su AI, dati e digitale.