Calcola con dimensioni intrinseche

Funzionalità web: calc-size() interpolate-size

calc-size() è una funzione CSS per eseguire operazioni matematiche su parole chiave di dimensionamento intrinseco come auto, min-content e fit-content. OBBLIGATORIO: utilizza calc-size() solo quando devi modificare una dimensione intrinseca con un calcolo o un vincolo; per animazioni semplici basate su parole chiave (ad es. da 0 a auto), devi utilizzare interpolate-size: allow-keywords.

Procedura di implementazione

  1. Identifica la base intrinseca: determina quale parola chiave intrinseca (auto, min-content e così via) deve formare la base del calcolo.
  2. Definisci i vincoli: utilizza funzioni matematiche CSS come clamp(), min() o max() all'interno del secondo argomento per applicare vincoli di progettazione alle dimensioni intrinseche.
  3. OBBLIGATORIO: fornisci un'alternativa: dichiara sempre una parola chiave o una lunghezza di dimensionamento standard immediatamente prima della proprietà utilizzando calc-size() per assicurarti che il layout rimanga funzionale nei browser non supportati.
  4. Applica le proprietà logiche: utilizza per impostazione predefinita proprietà logiche come inline-size o block-size per assicurarti che i calcoli rispettino la modalità di scrittura del documento.
  5. (Facoltativo) Potenziamento progressivo: inserisci la logica di layout o le animazioni complesse in un blocco @supports (inline-size: calc-size(auto, size + 0px)) per offrire funzionalità avanzate solo ai browser compatibili.

Sintassi di base

/* calc-size(<calc-size-basis>, <calc-sum>) — mathematical operations on intrinsic sizing keywords */
.element {
  /* MANDATORY: Always provide a fallback for browsers that do not support calc-size() */
  inline-size: min-content;
  
  /* DO: Use calc-size to modify an intrinsic basis with a calculation or function */
  inline-size: calc-size(min-content, size + 2rem);
}

Argomenti di base validi (<calc-size-basis>)

Il primo argomento definisce la dimensione "di base" per il calcolo.

Parole chiave standard:

  • auto: le dimensioni predefinite dell'elemento.
  • min-content: la dimensione più piccola che l'elemento può assumere senza overflow.
  • max-content: le dimensioni necessarie all'elemento per adattare tutti i contenuti su una riga.
  • fit-content: equivalente a clamp(min-content, auto, max-content).
  • content: valido solo quando calc-size() viene utilizzato all'interno della proprietà flex-basis.

Argomenti speciali:

  • any: una base generica utilizzata quando il tipo intrinseco specifico è sconosciuto o quando si nidificano i calcoli.
  • calc-size() nidificata: consente calcoli in più passaggi o condizionali.
  • <calc-sum>: una lunghezza, una percentuale o un'espressione matematica specifica (ad es. 100px o 20%). Quando viene utilizzato un valore fisso come base, la parola chiave size è ancora disponibile (ma solo all'interno del secondo argomento) e rappresenta il valore risolto di quella base.

OBBLIGATORIO: la parola chiave size non è valida all'interno del primo argomento (<calc-size-basis>). Si tratta di una variabile locale che esiste solo per fare riferimento alla base dall'interno del secondo argomento (<calc-sum>).

Argomenti di calcolo validi (<calc-sum>)

Il secondo argomento è l'espressione matematica.

  • In genere utilizza la parola chiave size per fare riferimento al valore della base.
  • Sebbene la parola chiave size sia tecnicamente facoltativa, se la ometti il calcolo verrà risolto in un valore fisso, ignorando completamente la base.
  • Può includere operatori matematici standard (+, -, *, /).
  • Può includere funzioni matematiche CSS come clamp(), min(), max() e round().
  • OBBLIGATORIO: calc-size() consente un solo valore di dimensione intrinseca (la base) in ogni calcolo. Non puoi combinare parole chiave di dimensionamento intrinseco nella stessa chiamata calc-size().

Casi d'uso

Animazione da e verso le dimensioni intrinseche

Per impostazione predefinita, i browser non possono eseguire l'interpolazione tra una lunghezza (ad es. 0px) e una parola chiave intrinseca (ad es. auto). Se la parola chiave viene inserita in calc-size(), diventa un valore interpolabile.

Scegliere lo strumento giusto per le animazioni

  • OBBLIGATORIO: utilizza interpolate-size: allow-keywords: per animazioni semplici da o verso dimensioni intrinseche (ad es. height: 0 a height: auto) senza modifiche matematiche. Questo è l'approccio richiesto per l'interpolazione semplice delle parole chiave e idealmente dovrebbe essere applicato a livello globale tramite :root.

    :root {
      /* Best practice: Enable keyword interpolation globally */
      interpolate-size: allow-keywords;
    }
    
    .item {
      height: 0;
      transition: height 0.3s ease;
    }
    
    .item.open {
      /* Simple interpolation from 0 to auto now works without calc-size() */
      height: auto;
    }
    
  • Utilizza calc-size(): SOLO quando devi eseguire calcoli matematici su una dimensione intrinseca durante una transizione (ad es. aggiungendo spaziatura interna o limitando la dimensione).

.accordion-content {
  display: block;
  overflow: hidden;
  /* MANDATORY: Fallback value for closed state */
  block-size: 0;
  transition: block-size 0.3s ease-out;
}

.accordion-content.open {
  /* MANDATORY: Fallback value for open state */
  block-size: auto;

  /* 
    DO: Use calc-size(auto, ...) to enable animation from 0 to the element's 
    intrinsic size while doing a calculation (in this case, adding a space of 2rem).
  */
  block-size: calc-size(auto, size + 2rem);
}

OBBLIGATORIO: l'interpolazione tra due parole chiave di dimensionamento intrinseco non è possibile direttamente. Un'estremità della transizione deve essere una lunghezza o una percentuale.

Rispetto delle preferenze di movimento dell'utente

Le animazioni che modificano le dimensioni di grandi aree di layout possono essere particolarmente fastidiose per gli utenti con disturbi vestibolari. OBBLIGATORIO: rispetta sempre le preferenze di movimento dell'utente utilizzando la query supporti prefers-reduced-motion per semplificare o ridurre al minimo le animazioni non essenziali. Le strategie più comuni includono la disattivazione completa del movimento, la riduzione della durata o la sostituzione delle variazioni del layout con transizioni di opacità impercettibili.

.accordion-content {
  opacity: 0;
  transition: block-size 0.3s ease, opacity 0.3s ease;
}

.accordion-content.open {
  opacity: 1;
}

@media (prefers-reduced-motion: reduce) {
  .accordion-content {
    /* 
       EXAMPLE: Replacing disruptive layout animations with a subtle fade-in.
       Setting the block-size instantly and transitioning opacity 
       provides a clear state change without large-scale motion.
    */
    transition: opacity 1.5s ease;
  }

  .accordion-content.open {
    /* Jump the size instantly */
    block-size: auto;
  }
}

Applicazione di vincoli alle dimensioni intrinseche

Puoi utilizzare calc-size() con qualsiasi funzione matematica CSS, ad esempio min(), max(), clamp() o round(), per assicurarti che le dimensioni intrinseche di un elemento rimangano entro i limiti del design.

.dynamic-container {
  /* MANDATORY: Always provide a fallback for browsers that do not support calc-size() */
  inline-size: fit-content;

  /* 
    DO: Establish a dynamic size based on content, while:
    1. Enforcing boundaries using CSS math functions (min, clamp, etc.)
    2. Modifying the intrinsic size with fixed or relative offsets
  */
  inline-size: calc-size(fit-content, min(size + var(--extra-space), var(--max-allowed)));
}

Considerazioni critiche

  • Insidie delle percentuali: le percentuali all'interno di <calc-sum> vengono risolte in base alle dimensioni del container, non alla parola chiave size. Ad esempio, calc-size(auto, size + 10%) aggiunge il 10% della larghezza dell'elemento principale alla larghezza dell'elemento auto, il che potrebbe portare a risultati imprevisti o overflow.
  • Requisito per i calcoli: OBBLIGATORIO: utilizza interpolate-size: allow-keywords anziché calc-size() per le animazioni semplici (ad es. da 0 a auto). calc-size() deve essere utilizzato solo quando il layout richiede aggiustamenti matematici dinamici alla base intrinseca.
  • Nota sulle prestazioni: l'animazione delle proprietà del modello di box come inline-size o block-size attiva i ricalcoli del layout, che possono essere onerosi. Utilizza le animazioni calc-size() principalmente per gli elementi critici per il layout, quando le alternative non di layout non sono sufficienti.

Strategie di riserva

calc-size() e interpolate-size sono potenziamenti progressivi. Nei browser che non le supportano, le proprietà verranno ignorate e il layout continuerà a funzionare, anche se le animazioni alle parole chiave intrinseche verranno saltate anziché essere sottoposte a transizione. Fornisci sempre una parola chiave o una lunghezza standard come opzione di riserva.

.element {
  /* Fallback for browsers that don't support calc-size() */
  inline-size: fit-content; 
  /* Modern browsers will override the fallback */
  inline-size: calc-size(fit-content, size + 2rem);
}

Animazioni e transizioni di riserva

Nei browser che non supportano calc-size() o interpolate-size, le transizioni che coinvolgono parole chiave di dimensionamento intrinseco non verranno interpolate.

  • Riduzione controllata: il comportamento di riserva predefinito è un "salto istantaneo" tra gli stati (ad esempio, da 0 a auto). Spesso questo è accettabile, poiché il layout rimane funzionale.
  • Esperienza migliorata: utilizza @supports per applicare una logica di layout complessa o uno stile aggiuntivo che ha senso solo quando sono possibili animazioni intrinseche fluide.
  • Evita le misurazioni basate su JS: anche se potresti utilizzare JavaScript per misurare gli elementi e animare manualmente le loro dimensioni, spesso non è necessario e può causare un layout thrashing. L'utilizzo del "salto istantaneo" nativo è il comportamento di riserva consigliato per le applicazioni web moderne.

Per le animazioni, l'esperienza di riserva sarà un passaggio istantaneo alle dimensioni finali. Per rilevare il supporto in CSS o JavaScript:

/* CSS Feature Detection */
@supports (inline-size: calc-size(auto, size + 0px)) {
  .element {
    /* Apply advanced logic only when supported */
  }
}
/* JavaScript Feature Detection */
if (CSS.supports('inline-size', 'calc-size(auto, size + 0px)')) {
  // Apply advanced sizing or animations
}