Lekcja 25

Przejścia CSS: transition

transition pozwala płynnie zmieniać wartości CSS między stanami elementu. Dzięki temu hover, focus, active i otwieranie prostych komponentów mogą być czytelniejsze, spokojniejsze i bardziej profesjonalne.

Cele lekcji

Po ukończeniu tej lekcji będziesz umieć:

  • wyjaśnić, kiedy użyć transition, a kiedy nie jest potrzebny,
  • kontrolować transition-property, transition-duration, transition-timing-function i transition-delay,
  • zapisywać przejścia skrótem transition,
  • dobierać właściwości bezpieczne dla wydajności,
  • budować płynne stany :hover, :focus-visible i :active,
  • uwzględniać prefers-reduced-motion w projektach UI.

Kontekst praktyczny

Przejścia są używane w przyciskach, linkach, kartach, formularzach, dropdownach, menu, tooltipach i stanach walidacji. Dobra animacja stanu nie ma odciągać uwagi. Ma pomóc użytkownikowi zauważyć zmianę i zrozumieć reakcję interfejsu.

W praktyce: transition działa tylko wtedy, gdy przeglądarka ma stan początkowy i końcowy tej samej właściwości. Nie animuje magicznie wszystkiego i nie zastępuje dobrze zaprojektowanych stanów UI.

Czym jest transition

transition mówi przeglądarce, że zmiana wartości CSS ma nastąpić płynnie w czasie. Najczęściej deklarujesz przejście na stanie bazowym elementu, a właściwość zmieniasz dopiero w stanie interakcji.

.button {
  background: #3b82f6;
  transition: background-color .18s ease;
}

.button:hover {
  background: #1d4ed8;
}

Jeżeli dodasz transition tylko w :hover, wejście w hover może być płynne, ale wyjście często będzie nagłe. Dlatego bazowy selektor jest najbezpieczniejszym miejscem dla deklaracji przejścia.

Transition property

transition-property określa, które właściwości mają się zmieniać płynnie. W profesjonalnym kodzie zwykle lepiej wskazać konkretne właściwości niż używać all.

.card {
  transition-property: transform, box-shadow, border-color;
  transition-duration: .2s;
  transition-timing-function: ease;
}

all bywa wygodne, ale może animować przypadkowe właściwości dodane później. To utrudnia debugowanie i może pogorszyć wydajność.

Duration, delay i timing

transition-duration określa czas trwania, transition-delay opóźnienie startu, a transition-timing-function charakter zmiany. Dla interfejsów najczęściej sprawdzają się krótkie czasy: od 120ms do 250ms.

.menu-item {
  transition-property: color, background-color;
  transition-duration: 180ms;
  transition-timing-function: ease-out;
  transition-delay: 0ms;
}

Opóźnienie jest przydatne rzadziej niż duration i timing. W nawigacji albo formularzu zbyt duży delay zwykle sprawia wrażenie ospałego interfejsu.

Skrót transition

Skrót transition pozwala zapisać property, duration, timing i delay w jednej linii. Możesz też podać kilka przejść rozdzielonych przecinkami, gdy różne właściwości potrzebują innego czasu.

.card {
  transition:
    transform .18s ease,
    box-shadow .18s ease,
    border-color .18s ease;
}

Najpierw pisz przejście jawnie, gdy uczysz się mechanizmu. Skrót jest wygodny, ale łatwo zgubić, co dokładnie animujesz.

Stany interakcji

Przejścia najlepiej wspierają istniejące stany. Najpierw zaprojektuj czytelny :hover, :focus-visible i :active, a dopiero potem dodaj płynność. Animacja nie może być jedynym sygnałem zmiany.

.link-card {
  transition: transform .18s ease, border-color .18s ease;
}

.link-card:hover,
.link-card:focus-visible {
  border-color: #3b82f6;
  transform: translateY(-.2rem);
}

Stan fokusu powinien pozostać wyraźny także bez ruchu. Użytkownik klawiatury musi natychmiast widzieć, gdzie aktualnie jest.

Wydajność i dostępność

Najbezpieczniejsze do animowania są zwykle transform i opacity. Ostrożnie podchodź do właściwości wpływających na layout, takich jak width, height, top czy left. Pamiętaj też o użytkownikach, którzy wolą ograniczony ruch.

@media (prefers-reduced-motion: reduce) {
  *,
  *::before,
  *::after {
    transition: none !important;
  }
}

Ograniczenie ruchu nie oznacza usunięcia stanów. Kolor, obramowanie, tło i outline nadal powinny jasno informować o interakcji.

Demo transition

Poniższe demo pokazuje trzy typowe przejścia: przycisk, kartę oraz wskaźnik statusu. Najedź kursorem albo przejdź klawiaturą do elementów interaktywnych, aby zobaczyć zmianę stanu.

Transition

Płynne stany komponentów

120ms 180ms 260ms
Timing

Krzywe i czas

easeUniwersalne, spokojne przejście

ease-outSzybki start, łagodny koniec

linearStałe tempo, dobre do wskaźników

Dobór timing function wpływa na odczucie interfejsu tak samo jak sam czas trwania.

Najczęstsze błędy początkujących

  • Dodawanie transition: all do każdego komponentu bez kontroli właściwości.
  • Umieszczanie deklaracji transition tylko w stanie :hover.
  • Animowanie właściwości layoutowych, które powodują kosztowne przeliczenia układu.
  • Zbyt długie czasy przejść w podstawowych akcjach UI.
  • Brak wyraźnego stanu fokusu, gdy ruch jest wyłączony.
  • Ignorowanie prefers-reduced-motion.

Mini zadanie

Zbuduj kartę linku z płynnymi stanami interakcji.

  • Dodaj bazowy styl karty z ramką i cieniem.
  • Dodaj transition dla transform, box-shadow i border-color.
  • W stanie :hover przesuń kartę przez translateY(-.25rem).
  • W stanie :focus-visible dodaj wyraźny outline niezależny od ruchu.
  • Dodaj regułę prefers-reduced-motion, która wyłącza przejścia, ale zostawia stany wizualne.

Checklista

  • Rozumiem, że transition wymaga stanu początkowego i końcowego.
  • Potrafię wskazać konkretne właściwości przez transition-property.
  • Dobieram rozsądny czas trwania i timing function.
  • Unikam transition: all w komponentach produkcyjnych.
  • Projektuję hover, focus i active przed dodaniem płynności.
  • Uwzględniam prefers-reduced-motion.

Podsumowanie lekcji

transition zamienia nagłą zmianę stanu w płynne przejście. Profesjonalne użycie polega na animowaniu konkretnych właściwości, krótkim czasie trwania, czytelnych stanach fokusu i respektowaniu preferencji ograniczonego ruchu.

Kolejny krok roadmapy to animacje CSS przez @keyframes.

Przejdź do Lekcji 26