Co robi calc()
calc() wykonuje działania wewnątrz wartości CSS i może łączyć jednostki, które dostają rozmiar dopiero w czasie układania strony. Klasyczny przypadek to "pełna szerokość minus stały panel boczny":
100% jest znane dopiero po ułożeniu strony, a 180px jest stałe, więc żadna pojedyncza jednostka nie wyrazi tego wyniku. calc() go oblicza: w podglądzie o szerokości 800px wiersz ma 784px, a główna kolumna dostaje 604px, a linia pod układem pokazuje prawdziwe liczby. Dziś flexbox albo grid zrobiłyby ten układ bez obliczeń, ale to samo odejmowanie wciąż pojawia się wszędzie: wysokość minus nagłówek, szerokość minus odstęp.
Zasady składni
width: calc(100% - 2rem); /* + and - need spaces on both sides */
width: calc(100% / 3); /* divide by a plain number */
margin: calc(var(--space) * 2); /* multiply by a plain number */
height: calc(100vh - (64px + 1rem)); /* parentheses group */
| Zasada | Poprawnie | Niepoprawnie |
|---|---|---|
Spacje wokół + i - | calc(100% - 20px) | calc(100%-20px) |
*: co najmniej jedna strona to zwykła liczba | calc(2 * 1rem) | calc(2px * 3px) |
/: dziel długość przez zwykłą liczbę | calc(100% / 3) | width: calc(300px / 3px) (to nie długość) |
| Jednostki muszą być zgodne | calc(1rem + 10px) | calc(1rem + 2s) |
Zasada spacji istnieje, bo 100% -20px zostałoby odczytane jako dwie osobne wartości, z czego druga to liczba ujemna. Gdy calc() jest niepoprawne, cała deklaracja zostaje odrzucona, a element zachowuje wartość z wcześniejszych reguł.
Wypróbuj wyrażenie
Wpisz dowolne wyrażenie dla szerokości pudełka. Przeglądarka pokaże, czy jest poprawne, i jaką szerokość z niego obliczyła:
Wypróbuj 100%-200px (niepoprawne, bez spacji), 100% / 3, 50% + 4rem, 2 * 120px, 200px * 2px (niepoprawne) i (100% - 40px) / 2.
calc() ze zmiennymi CSS
Zmienne i calc() świetnie ze sobą współpracują: zapisz wartość bazową raz i wyprowadź z niej resztę. Zmienna bez jednostki staje się długością, gdy pomnożysz ją przez jedną jednostkę:
Zmień --space na 12px albo --cols na 4, a wszystkie wyprowadzone wartości się dostosują. Deklarowanie zmiennych i ich zasięg omawia strona o zmiennych CSS.
Typowe zastosowania
| Potrzeba | calc() |
|---|---|
| Wypełnienie miejsca obok elementu o stałej szerokości | width: calc(100% - 240px) |
| Sekcja pod stałym nagłówkiem | min-height: calc(100vh - 64px) |
| Połowa szerokości minus połowa odstępu | width: calc(50% - 8px) |
| Wyśrodkowanie pozycjonowanego absolutnie pudełka 100px | left: calc(50% - 50px) |
| Rozmiar czcionki, który trochę rośnie z ekranem | font-size: calc(1rem + 0.5vw) |
| Zamiana zmiennej liczbowej na długość | calc(var(--n) * 1px) |
| Wartość przeciwna zmiennej | calc(var(--space) * -1) |
Dla wartości, która musi zostać między granicami, użyj clamp(), które przyjmuje te same obliczenia w argumentach bez pisania calc().
Gdzie działa calc()
Wszędzie tam, gdzie dozwolona jest długość, procent, liczba, kąt albo czas: width, margin, padding, top, font-size, line-height, rozmiary ścieżek siatki, transition-delay oraz kąty w transform. Można je zagnieżdżać, a zagnieżdżone calc() działa tak samo jak zwykłe nawiasy.
Kąty to dobry przykład. Każda kreska poniżej ma własne --i (od 0 do 11), a jedna reguła zamienia je na kąt przez calc(var(--i) * 30deg):
Kreska 3 dostaje rotate(90deg), co Chrome pokazuje jako macierz matrix(0, 1, -1, 0, 0, 0): ćwierć obrotu. left: calc(50% - 2px) wyśrodkowuje każdą kreskę, odejmując połowę jej własnej szerokości 4px.
Częste błędy
- Brak spacji wokół
-albo+.calc(100%-20px)jest niepoprawne i ignorowane. - Mnożenie dwóch długości.
calc(10px * 2px)nie ma w CSS sensu. Jedna strona*musi być zwykłą liczbą. - calc() dla wysokości w procentach bez wysokości rodzica.
calc(100% - 20px)dlaheightwymaga rodzica z ustawioną wysokością, tak samo jakheight: 100%. - calc() tam, gdzie wystarczy flexbox albo grid.
width: calc(33.333% - 10px)dla kolumn jest kruche;display: grid; grid-template-columns: repeat(3, 1fr); gap: 15pxnie wymaga żadnych obliczeń. - Oczekiwanie komunikatu o błędzie. Przeglądarka nie ostrzega o niepoprawnym calc(). Sprawdź element w narzędziach deweloperskich: niepoprawna deklaracja jest tam przekreślona.
Najczęściej zadawane pytania
Co robi calc() w CSS?
Oblicza wartość z wyrażenia z +, -, * i / i może łączyć jednostki, które przeglądarka zna dopiero w czasie układania strony. width: calc(100% - 200px) to pełna szerokość rodzica minus 200px, bez względu na to, jaka jest szerokość rodzica.
Dlaczego moje calc() nie działa?
Najczęstsza przyczyna to brak spacji: + i - muszą mieć odstęp z obu stron, więc calc(100%-20px) jest niepoprawne. Inne przyczyny to mnożenie dwóch długości (10px * 2px) albo dzielenie przez długość, które nie daje długości. Niepoprawne calc() unieważnia całą deklarację, więc przeglądarka ją ignoruje.
Czy mogę używać zmiennych CSS w calc()?
Tak. calc(var(--gap) * 2) podwaja zmienną, a calc(var(--columns) * 1px) zamienia liczbę bez jednostki na piksele. Najpierw podstawiana jest wartość zmiennej, a potem wykonywane są obliczenia.
Czy wokół * i / w calc() potrzebne są spacje?
Nie. Spacji wymagają tylko + i -, bo bez nich -20px zostałoby odczytane jako liczba ujemna. Spacje wokół * i / są opcjonalne, ale pisanie ich wszędzie to najłatwiejsza zasada do zapamiętania.
Czym różni się calc() od clamp()?
calc() oblicza jedną wartość z wyrażenia. clamp(MIN, VAL, MAX) utrzymuje wartość między dwiema granicami. Można je łączyć: każdy argument clamp() może już zawierać obliczenia w stylu calc, na przykład clamp(1rem, 1rem + 2vw, 3rem).