Porządkowanie kodu CSS - okładka

Porządkowanie kodu CSS

Na samym początku swojej przygody z tworzeniem stron WWW zupełnie nie zwracałem uwagi na porządkowanie kodu CSS. Tworzony przeze mnie kod zwykle zawierał się w jednym, spuchniętym pliku CSS. Nazwy klas co prawda
( zwykle ) opisywały czym dany element jest jednak brakowało im systematyczności. Po powrocie do takiego kodu miałem bardzo dużo momentów, gdy nie wiedziałem, czy np. klasa page-header odpowiada za nagłówek całej strony, czy też za np. nagłówek artykułu.

Przykład złego kodu

Zobaczmy następujący fragment kodu SCSS ( wykorzystałem tu jedynie zagnieżdżenia ) :


.name-item
{
    height: 100%;
}
.name-item > h1 > small
{
    display: block;
    text-align: center;
    padding-bottom: 9vmin;
    padding-top: 1vmin;
    color: rgba(0,0,0,0.4);
    font-size: 3vmin;
}
.projects-container
{
    img
    {
        padding:3vmin;
        transition:0.4s all;
    }
    img:hover {
        transform: scale( 0.9 );
    }
}
.text-justify
{
    box-sizing:border-box;
    font-size: 1.6vmax;
}
.blog
{
    font-size:2rem;
    color:#4d4646;
}

Zobaczmy teraz co z tym kodem jest nie tak:

  • Przede wszystkim złe i mylące są nazwy klas. Nazwy takie jak name-item, czy blog  nie mówią nam absolutnie NIC o stylowanym elemencie. Czy te elementy to są kontenery, nagłówki czy może bloki tekstu? Nie wiadomo.
  • Nazwa jest jeszcze bardziej myląca w przypadku klasy text-justify – sugeruje wyjustowanie tekstu. Problem leży w tym, że klasa nie justuje tekstu. Co gorsza, owa klasa nakłada inne style!
  • Moją uwagę zwróciła też klasa projects-container. Nie chodzi tu o samą nazwę lecz o zagnieżdżony w niej element. Wnioskując po nazwie jest to jakiś kontener zawierający projekty. Zapewne jest to lista projektów, którym towarzyszy jakieś zdjęcie. Zakładając, że w owym kontenerze są tylko miniaturki projektów to fragment kodu jeszcze jest akceptowalny.
    Wyobraźmy sobie jednak sytuację, gdy zechcemy umieścić pomiędzy naszymi projektami banery reklamowe będące zdjęciami. W tym momencie dodane banery przyjmą style miniaturek. Czy chcemy, aby baner reklamowy zachowywał się podczas najechania kursorem tak jak miniaturka? Ja bym nie chciał. Problem w tym miejscu można rozwiązać poprzez dodanie klasy np. project-thumbnail na miniaturę projektu.
  • Staram się również unikać stylowania po idelementach, a przy stylowaniu korzystać głównie z klas. Aczkolwiek wydaje mi się, że jest to głównie moje widzimisię. Główny powód mojej decyzji opisałem w kolejnym akapicie.
  • Kolejnym punktem, gdzie brakuje spójności jest kolorystyka. Nie chodzi tu jednak o zły dobór kolorów, a o ich zapis. Wykorzystano tu dwa różne sposoby na zapis koloru: #4d4646 oraz rgba(0,0,0,0.4). Starajmy się trzymać jednego formatu. Dodatkowo owe wartości można wyciągnąć i przypisać do zmiennych, które oczywiście również powinny mieć spójne i deskryptywne nazwy. Zmienne są już wspierane nie tylko przez preprocesory, ale i przez natywny CSS, więc nie widzę żadnych przeciwwskazań do ich używania.
  • Ostatnim punktem, który zwrócił moją uwagę jest po raz kolejny klasa text-justify. Osobiście nie jestem zwolennikiem klas, których jedynym zadaniem jest nałożenie stylu. Mam tu na myśli klasy pokroju: font-bold czy align-center. Jednak możemy spotkać się z tego typu klasami chociażby w bibliotekach np. Bootstrap, a samo podejście do tego typu klas jest moją subiektywną opinią i jak widać nie każdy się z nią zgadza. Decyzję pozostawiam Tobie 🙂

Porządkowanie kodu CSS - specificity

Specificity

Mając już przykład złego kodu zastanówmy się, co możemy zrobić, aby nasz kod wyglądał i działał lepiej. Pierwszym terminem, jaki warto jest poznać, aby tworzyć lepszy i bardziej czytelny kod CSS jest specificity. Intuicyjnie tłumaczę sobie termin ten w ten sposób, że określamy specyficzność danego elementu. Oczywiście najbardziej specyficzne elementy możemy wskazać za pomocą id. Element z danym id na danej stronie powinien znajdować się dokładnie JEDEN, także z chirurgiczną precyzją jesteśmy w stanie go ostylować. Następnie w hierarchii mamy klasy, a na końcu elementy.

Specificity jesteśmy w stanie dokładnie obliczyć za pomocą licznych kalkulatorów online. Przykładowy z nich znajdziesz TUTAJ.

Przeanalizujmy poniższy fragment kodu:


<style>
  #square {
    background-color: black;
  }
  
  .square {
    background-color: pink;
  }
  
  div {
    width: 100px;
    height: 100px;
    background-color: orange;
  }
  
</style>

<div class="square" id="square" style="background-color: purple;"> </div>

Wklejając ten kod do pliku HTML i uruchamiając plik w przeglądarce otrzymamy kwadrat w kolorze… fioletowym. Jest to oczywiście spowodowane stylem inline na elemencie. Starajmy się unikać takich zabiegów. Sam stosuję style inline w bardzo rzadkich i wyjątkowych sytuacjach. Natomiast skupmy się teraz na kodzie w znaczniku <style>. Gdy usuniemy style inline to nasz kwadrat otrzyma kolor czarny. Ktoś mógłby zapytać – dlaczego? Odpowiedzią jest właśnie specificity. Stylowanie po id ma wyższy priorytet niż stylowanie po klasach czy elementach przez co mimo, tego że późniejszy kod CSS definiuje inny kolor kwadratu to kolor się nie zmienia. Gdybyśmy z przykładu usunęli style dla #square to otrzymamy kwadrat w kolorze różowym, ponieważ style klasy są wyżej w hierarchii niż style elementu. Natomiast należy pamiętać, że dla takich samych specificity zaaplikowany będzie ostatni styl:


 #square {
    background-color: black;
  }

 #square {
    background-color: red;
  }

W tym momencie kolor zostanie już zmieniony na czerwony.

Jeśli w dalszym ciągu nie rozumiesz jak działa specificity to skopiuj kod z poprzedniego przykładu i pobaw się nim. Najpierw usuń style inline, a następnie style #square. Zachęcam też do wypróbowania kalkulatora specificity.

Podział na pliki

Na samym początku wspomniałem, że swoje pierwsze CSS’y trzymałem w dużym napuchniętym pliku CSS. Oczywiście jest to błąd. Style należy odpowiednio wydzielić do poszczególnych plików. Sposób podziału i granulacja jest na tyle specyficzna względem konkretnego projektu, że stworzenie uniwersalnej recepty podziału mogłoby być karkołomne, a wręcz awykonalne.
Nie powinniśmy się natomiast zbytnio martwić ilością plików, ponieważ żyjemy w dobie powszechności narzędzi tj. Webpack ( jeśli nie znasz Webpacka to zachęcam do zapoznania się z artykułem – Webpack – szybki start i pierwsza konfiguracja ), które powinny za nas, podczas budowania projektu połączyć te pliki w jeden oraz zminifikować powstały kod.

Metodyki CSS

Mechanizmem, który BARDZO pomaga uporządkować selektory są metodyki. Definiują one pewne schematy i wytyczne stylowania czy nazewnictwa klas. Samych metodyk jest całkiem sporo, a przykładowe z nich to:

  • Object Oriented CSS (OOCSS)
  • Atomic CSS (ACSS)
  • Atomic Design
  • SUIT CSS
  • Scalable and Modular Architecture for CSS (SMACSS)
  • Block Element Modifier (BEM)

Oczywiście metodyk w sieci można znaleźć sporo więcej, ale z tymi raczej spotkasz się najczęściej. Sam używam metodyki BEM. Jest ona dla mnie najwygodniejsza i w zupełności spełnia moje oczekiwania.

Nie jest to wpis będący poradnikiem BEM’a, dlatego też nie wyczerpię tematu w całości. Pokażę natomiast przykład jego zastosowania, aby zobrazować jakie problemy rozwiązuje zastosowanie metodyk.

Przykład zastosowania metodyki BEM

Załóżmy, że mamy do ostylowania formularz logowania. Formularz musi mieć pole na email oraz na hasło. Całość formularza musimy zawrzeć w jakimś kontenerze – nazwijmy go login-form. Będzie to nasz blok (B). Następnie nałóżmy klasę na pola do wpisywania danych. Stwórzmy klasę login-form__field i nałóżmy ją na każdy element <input> w formularzu. Szczególną uwagę należy zwrócić na podwójne podkreślenie, które służy do oznaczania elementu (E) w BEM. Oczywiście taki formularz musi mieć również walidację. W przypadku błędnego adresu email czy hasła pole powinno otrzymać np. czerwoną ramkę. Odpowiedzialną za to klasę nazwijmy login-form__field--invalid. Oddzielone podwójnym myślnikiem słowo invalid to modyfikator (M).

Jak widać BEM wymusza na nas pewne wzorce nazewnictwa. Owe wzorce nie tylko pomagają nam w utrzymaniu, modyfikacji i łatwej rozbudowie kodu CSS, ale też nakładają pewną abstrakcję na DOM, dzięki której nasza strona nie jest zlepkiem “div’ów” i “span’ów”, ale staje się logiczną strukturą z podziałem na bloki takie jak np. menu, toolbary, slidery itd.

Jeśli jesteś zainteresowany metodologią BEM, to w źródłach znajdziesz naprawdę sporo materiałów dotyczących BEM’a.

Podsumowanie

Uważam, że utrzymanie dobrego, łatwego w rozbudowie i utrzymaniu i czytelnego kodu CSS jest sztuką a zarazem wyzwaniem. Mam nadzieję, że ten artykuł pomoże Ci w pisaniu lepszego kodu CSS, a porządkowanie kodu CSS nie będzie już dla Ciebie wyzwaniem. Oczywiście nie wyczerpałem tematu “polerowania” CSS w 100% ( nie poruszyłem chociażby tematu preprocesorów i ich możliwości tj. zagnieżdżenia, funkcje czy mixiny ), dlatego też zachęcam do pozostawienia komentarza jakie jeszcze sposoby na polepszenie kodu CSS znasz. Zajrzyj również do źródeł, gdzie dowiesz się więcej o omawianych zagadnieniach.

Źródła i materiał dodatkowe