Co sprawia, że ​​BEM jest lepszy niż używanie zagnieżdżonego języka arkuszy stylów, takiego jak LESS?

27

Mój kolega mocno naciska na metodę BEM ( Block Element Modifier ) dla CSS w projekcie, którym kieruje, i po prostu nie potrafię zrozumieć, co czyni go lepszym niż LESS CSS, który piszemy od lat.

Twierdzi, że „wyższa wydajność”, ale nie wyobrażam sobie, jak wydajność może mieć znaczenie dla rodzajów aplikacji internetowych, które piszemy w tym sklepie z kodami. Nie tworzymy tutaj Twittera ani Facebooka. Byłbym bardzo zaskoczony, gdyby nasze aplikacje najczęściej używane miały ponad 10000 odsłon miesięcznie , a większość z nich ma znacznie poniżej 1000.

Twierdzi, że „czytelność” i „ponowne użycie”, ale według mnie LESS już robi to znacznie lepiej . I uważam, że BEM tak źle modyfikuje znaczniki dziesiątkami dodatkowych znaków poświęconych tym bardzo długim nazwom klas, że radykalnie zmniejsza czytelność.

Twierdzi, że „zagnieżdżony CSS jest anty-wzorcem”. Co robi „anti-pattern”, nawet średniej i dlaczego jest zagnieżdżona CSS źle?

Twierdzi, że „wszyscy zmierzają w kierunku korzystania z BEM, więc my też powinniśmy”. Mój licznik brzmi: „Gdyby wszyscy skakali z mostu, poszedłbyś za nim?” Ale nadal jest całkowicie nieugięty w tej sprawie.

Czy ktoś mógłby szczegółowo wyjaśnić, co czyni BEM lepszym niż LESS? Mój kolega kompletnie mnie nie przekonuje, ale nie wiem, czy mam wybór, ale podążać. Naprawdę wolałbym docenić BEM, niż niechętnie to zaakceptować.

Coredumperror
źródło
1
BEM i LESS służą różnym celom. Używam zarówno BEM, jak i MNIEJ.
zzzzBov
4
Zauważ, że BEM nie polega przede wszystkim na CSS - chodzi o identyfikację powtarzających się enkapsulowanych wzorców w twoim projekcie i zebranie wszystkiego, co potrzebne dla tego bloku (zachowanie, szablon, style) w jednym centralnym miejscu. Nawet jeśli ogranicza się tylko do CSS, BEM jest nadal doskonałym sposobem na uporządkowanie stylów i niezawodne zapobieganie konfliktom nazw. To wszystko jest całkowicie niezależne od preprocesorów, takich jak LESS lub SASS, które są po prostu bardziej produktywnymi językami stylizacyjnymi niż zwykły CSS, ponieważ oferują makra i zmienne oraz notację stenograficzną i wszelkiego rodzaju fajne funkcje. MNIEJ = wygrana, BEM = wygrana, ale MNIEJ × BEM = wygrana²!
amon

Odpowiedzi:

29

Mój kolega mocno naciska na metodę BEM (Block Element Modifier) ​​dla CSS w projekcie, którym kieruje, i po prostu nie potrafię zrozumieć, co czyni go lepszym niż LESS CSS, który piszemy od lat.

BEM to metodologia CSS. Inne obejmują OOCSS i SMACSS. Metodologie te są używane do pisania modułowego, rozszerzalnego kodu wielokrotnego użytku, który działa dobrze na dużą skalę.

MNIEJ jest preprocesorem CSS. Inne obejmują Sass i Stylus. Te preprocesory są używane do konwersji odpowiednich źródeł na rozszerzony CSS.

BEM i LESS nie są porównywalne jako „lepsze” od siebie, są to narzędzia, które służą różnym celom. Nie powiedziałbyś, że śrubokręt jest lepszy niż młotek, chyba że rozważasz użyteczność rozwiązania konkretnego problemu.

Twierdzi, że „wyższa wydajność” ...

Wydajność musiałaby być mierzona pomiędzy klasycznym stylem CSS:

.widget .header

i styl BEM:

.widget__header

ale ogólnie rzecz biorąc, wydajność selektora CSS nie stanowi wąskiego gardła i nie trzeba go optymalizować.

„Wydajność” BEM dotyczy zazwyczaj kodu pisania wydajności programisty. Jeśli metodologia BEM jest stosowana konsekwentnie i poprawnie, grupom programistów łatwo jest jednocześnie tworzyć odrębne moduły bez kolizji stylów.

Twierdzi, że „czytelność” i „ponowne użycie” ...

Nie wiem, czy powiedziałbym nowemu deweloperowi, że BEM jest bardziej czytelny. Mogę powiedzieć, że zapewnia pewne dobrze zdefiniowane wytyczne dotyczące znaczenia i struktury klas.

Widzę klasę jak

.foo--bar__baz

Mówi mi, że istnieje fooblok, który jest w barstanie i zawiera bazelement.

Absolutnie powiedziałbym, że BEM jest bardziej wielokrotnego użytku niż klasyczny model.

Jeśli dwóch programistów utworzy bloki ( fooi bar), a oba bloki mają nagłówki, mogą bezpiecznie ponownie użyć swoich bloków w różnych kontekstach bez obawy o kolizję nazewnictwa.

To dlatego, że w klasycznym kontekście .foo .headingi .bar .headingbyłoby sprzeczne i wprowadzają konflikt specyficzności, które muszą zostać rozwiązane, ewentualnie na podstawie indywidualnego przypadku.

W witrynie BEM klasy byłyby .foo__headingi .bar__heading, co nigdy nie byłoby sprzeczne.

Twierdzi, że „zagnieżdżony CSS jest anty-wzorcem”. Co to znaczy „anty-wzór” i dlaczego zagnieżdżony CSS jest zły?

„Anty-wzorzec” to wzorzec kodowania, który dla niedoświadczonych programistów jest łatwiejszy do nauczenia się i używania niż bardziej odpowiednia alternatywa.

O ile zagnieżdżony CSS jest zły: zagnieżdżanie zwiększa specyficzność selektora. Im wyższa specyficzność, tym więcej wysiłku potrzeba, aby ją zastąpić. Niedoświadczeni programiści często martwią się, że ich CSS może wpływać na wiele stron, dlatego używają selektorów takich jak:

#something .lorem .ipsum .dolor ul.sit li.amet a.more

Gdy doświadczony programista martwi się, że jego CSS może nie wpływać na wiele stron, używają selektorów takich jak:

.more

Twierdzi, że „wszyscy zmierzają w kierunku korzystania z BEM, więc my też powinniśmy”.

To błędne podejście , więc zignoruj ​​to jako zły argument. Nie wpadnij w pułapkę błędnego błędu , ponieważ zły argument na poparcie BEM nie jest powodem, by sądzić, że BEM nie może być dobry.

Czy ktoś mógłby szczegółowo wyjaśnić, co czyni BEM lepszym niż LESS?

Omówiłem to wcześniej, BEM i MNIEJ nie są porównywalne. Jabłka i Pomarańcze itp.

Mój kolega kompletnie mnie nie przekonuje, ale nie wiem, czy mam wybór, ale podążać.

Polecam przyjrzeć się OOCSS, SMACSS i BEM i rozważyć zalety i wady każdej metodologii ... jako zespół . Używam BEM, ponieważ podoba mi się jego ścisłość formatu i nie mam nic przeciwko brzydkim selektorom, ale nie mogę powiedzieć, co jest odpowiednie dla ciebie lub twojego zespołu. Nie pozwól jednemu otwartemu osobiście uruchomić program. Jeśli nie czujesz się dobrze z BEM, pamiętaj, że istnieją inne alternatywy, które mogą być łatwiejsze do wsparcia dla twojego zespołu. Być może będziesz musiał bronić swojej pozycji ze współpracownikiem, ale w perspektywie długoterminowej prawdopodobnie będzie to miało pozytywny wpływ na wynik twoich projektów.

Naprawdę wolałbym docenić BEM, niż niechętnie to zaakceptować.

Napisałem odpowiedź na StackOverflow, która opisuje, jak działa BEM . Ważną rzeczą do zrozumienia jest to, że twoje idealne selektory powinny mieć specyfikę 0-0-1-0, aby były łatwe do zastąpienia i rozszerzenia.

Wybór BEM nie oznacza, że ​​musisz się poddać MNIEJ! Nadal możesz używać zmiennych, nadal możesz używać @imports, a na pewno możesz nadal używać zagnieżdżania. Różnica polega na tym, że renderowany wynik ma być pojedynczą klasą, a nie łańcuchem potomnym.

Gdzie mogłeś

.widget {
    .heading {
        ...
    }
}

Z BEM możesz użyć:

.widget {
    &__heading {
        ...
    }
}

Dodatkowo, ponieważ BEM obraca się wokół pojedynczych bloków, możesz łatwo podzielić kod na osobne pliki. widget.lesszawiera style dla .widgetbloku, a component.lesszawiera style dla .componentbloku. To znacznie ułatwia znalezienie źródła dla dowolnej konkretnej klasy, chociaż nadal możesz chcieć korzystać z map źródłowych.

zzzzBov
źródło
4
@CoreDumpError, problem występuje, gdy zaczynasz zagnieżdżać moduły w modułach. „każdy programista może po prostu zagnieździć kod swojego widżetu o jeden poziom głębiej” nie jest do końca poprawny, każdy programista musi zagnieżdżać kod swojego widżetu głębiej i głębiej, w przeciwnym razie kaskadowe nazewnictwo kolizji odbywa się w sposób ogólnie niezamierzony. Jedynym sposobem na uniknięcie kolizji nazw jest zastosowanie pewnego rodzaju przestrzeni nazw, a BEM oferuje łatwy sposób na spójne klasy przestrzeni nazw.
zzzzBov
3
@CoreDumpError, Rozważ ten przykład . Autor piszący bez BEM musi poświęcić dodatkowy wysiłek, aby zweryfikować każdą kombinację każdego modułu, który może zostać dodany w jego module. Autor używający BEM nie.
zzzzBov 16.04.15
1
@CoreDumpError, na pewno może być. Uważam, że BEM łatwo szkolić nowych programistów i ułatwia przeglądanie kodu, ale SMACSS i OOCSS są dobrą alternatywą. Bardzo polecam przyjrzenie się tym opcjom jako alternatywy. Powiem, że używam BEM do własnego rozwoju, aby nie kolidować ze sobą, zwłaszcza z przyszłym mną, który jest głupi i zapomina o różnych sprawach.
zzzzBov 16.04.15
1
Uważam, że BEM jest doskonały w każdym projekcie, który wymaga jakiejkolwiek złożoności jest css. Możesz mieć witrynę, która znajduje się na WordPress i używa JavaScript do uruchamiania przewijania, ale nadal jest tak złożona jak aplikacja internetowa w css. Ważne jest, aby nie wpaść w pułapkę myślenia „moja strona nie jest złożona” tylko dlatego, że większość jej rzeczy wykonuje się wyłącznie w sferze wizualnej (jak wiele innych witryn marketingowych)
Toni Leigh,
1
@CoreDumpError większość moich wcześniejszych projektów była przedsięwzięciami solowymi i doszedłem do wielu BEM na własną rękę: specyfika i unikalne selektory. Utrzymanie bazy kodu jest ogromnym problemem, który staje się niezwykle jasny dzięki BEM. Kod to konserwacja. Budowanie rzeczy jest łatwe. Zachowanie idealnych wzorów jest trudne, szczególnie po kilku miesiącach od bazy kodu. Z biegiem czasu problemy ze specyficznością się pogłębiają. Korzyści dotyczą dowolnej wielkości zespołu IMO!
Yuji Tomita,
8

Edytuj 2017

Jeśli czytasz to w 2017 r., Wypełnienia DOM shadow i shadow DOM oraz komponenty rozwiązują wszystkie te problemy, jednocześnie utrzymując kod mały, zwarty i modułowy. Nie używaj BEM w projekcie IMO od podstaw.

Zamiast BEM mamy narzędzia takie jak ViewEncapsulation, Polymer, StyledJSX, SASS Modules, Styled Components itp.

Rozważ użycie BEM, jeśli nie masz architektury zorientowanej na komponenty; jeśli masz starszy kod do obsługi; lub jeśli jesteś po prostu martwy, robiąc wszystko ręcznie bez narzędzi.


BEM uniezależnia stylizację od zagnieżdżania DOM. Robi to, podając każdy element, który możesz chcieć nadać atrybutowi wielkiej klasy atrybut, który prawdopodobnie będzie unikalny na twojej stronie. Większość stylizacji jest następnie wykonywana na zajęciach.

To sprawia, że ​​Twój kod jest bardziej modułowy, ponieważ zagnieżdżanie nie jest już brane pod uwagę, kosztem dużej ilości gadatliwości.

Bez BEM

Bez BEM moglibyśmy napisać:

<div class="widget">
  <a>Hello!</a>
  <ul>...</ul>
</div>

Standardowy styl CSS może wyglądać następująco:

.widget {
  border: 1px solid red;
}

.widget a {
  color: green;
}

To samo z SASS wyglądałoby tak:

.widget {
  border: 1px solid red;
  a {
    color: green;
  }
}

Jeśli jesteś małym zespołem, w którym każdy może kodować CSS w wysokim standardzie, a projekt jest na tyle mały, że możesz zachować jego pełną znajomość, jest to dobre i rozsądne rozwiązanie.

Z BEM

Jeśli jednak Twój kod staje się większy i masz duży zespół o mieszanych umiejętnościach, może to nie być takie proste rozwiązanie. Co jeśli chcesz na przykład zielone kotwice w innym widżecie. Dlatego robimy kotwicę modułową i eliminujemy selektory potomne.

Teraz nasz HTML jest o wiele bardziej szczegółowy:

<div class="widget">
  <a class="widget__anchor">Hello!</a>
  <ul class="widget__ul">...</ul>
</div>

Nasz CSS nie ma selektorów potomków:

.widget {
  border: 1px solid red;
}

.widget__anchor {
  color: green;
}

Ale teraz możemy to zrobić:

<div class="widget__2">
  <a class="widget__anchor">Hello!</a>
</div>

Widget__anchor ma budowę modułową. Jest mało prawdopodobne, aby na stronie istniała inna definicja .widget__anchor.

kompromisy:

BEM:

  • Daje ci więcej kodu modułowego. Możesz wziąć dowolny kawałek w izolacji.
  • Pozwala każdemu pisać CSS. Nie musisz zdawać sobie sprawy z głównego stylu i niestandardowych przesłonięć. W dużym zespole jest to miłe.
  • Usuwa wszelkie problemy ze specyfiką.
  • Jest znacznie bardziej gadatliwy.

Standardowy CSS (który polega na użyciu selektorów potomków):

  • Oznacza, że ​​Twój styl zależy od kontekstu.
  • Wymaga świadomości kaskady. Kod w jednym miejscu może wpływać na kod w innym miejscu. W małym zespole jest to dobra rzecz.
  • Może cierpieć z powodu problemów ze specyfiką, które mogą być trudne do debugowania przez początkującego programistę.
  • Jest znacznie ciaśniejszy.

Trzeci sposób - prawdziwe komponenty.

Jeśli używasz czegoś takiego jak React, Angular 2 lub którekolwiek z innych współczesnych ramek front-end, masz inne rozwiązanie. Możesz użyć narzędzi do wymuszenia enkapsulacji.

W tym przykładzie użyto React i StyledJSX, ale istnieje wiele opcji. Oto widżet:

const Widget = () => 
  <div>
    <a>Hello</a>
  </div>
  <style jsx>
    div {border:red }
    a { background: pink }
  </style>

Następnie skorzystaj z nowego widżetu:

<Widget />

Wszystkie style zadeklarowane w widżecie zostaną obudowane i nie będą miały zastosowania do elementów poza komponentem. Możemy swobodnie stylizować divi abezpośrednio, nie martwiąc się o przypadkowe stylizowanie czegokolwiek na stronie.

superluminarny
źródło
1
Plusy i minusy bez faworyzowania żadnej strony, podoba mi się.
Adrian Moisa
Myślę, że jest coś naprawdę smutnego w powiedzeniu „napisz swój kod w ten sposób, aby ludzie, którzy nie rozumieją kaskadowania, mogli go zrozumieć”. To tak, jakby powiedzieć: „Piszę kod bez żadnych tablic, ponieważ jeden z młodszych członków zespołu nie rozumie, jak działają tablice”. Osobiście wolę bardziej zwięzłą metodę, która faworyzuje naturalną stronę kaskadową arkuszy stylów kaskadowych.
Matt Fletcher
@MattFletcher - Myślę, że to kwestia wielkości projektu. Kaskada jest z natury globalna. Ustawiasz wartości, a następnie zastępujesz i zastępujesz w dół drzewa. Jeśli masz mniejszy projekt z pełną widocznością, jest to w porządku, ale w większym projekcie staje się kruchy. Ludzie boją się zmieniać rzeczy, ponieważ zmiana wyżej w kaskadzie niszczy losowe rzeczy w innych miejscach. Hermetyzacja komponentów jest naprawdę bardzo ładna w przypadku większych projektów. Wszystko po prostu działa.
superluminarny
2

Żadne podejście nie jest idealne. IMHO, powinniśmy uzyskać najlepsze części każdej z metodologii (BEM, SMACSS, OOCSS, DRY). Użyj SMACSS do organizowania struktury folderów w swoim CSS - szczególnie do definiowania logicznego podziału poziomu całego CSS. DRY, aby utworzyć bibliotekę narzędzi lub może być wspólną biblioteką modyfikatorów, która może być czasem używana w połączeniu z klasami opartymi na BEM. OOCSS dla komponentów. I BEM dla małych komponentów lub podkomponentów. Tam możesz rozłożyć złożoność i uzyskać swobodę pracy w dużym zespole.

Wszystko, co zostanie użyte bez zrozumienia jego istoty, będzie złe.

Chociaż BEM jest dobrym podejściem dla większych zespołów, ma również pewne wady. 1. Czasami skutkuje to bardzo długimi nazwami w dużej strukturze HTML. Wynikowy duży rozmiar pliku CSS. 2. W przypadku zagnieżdżania html, które mają więcej niż 2-3 poziomy, definiowanie nazw staje się problemem.

Rozwiązaniem konfliktu można łatwo zarządzać, jeśli weźmiemy pod uwagę strukturę komponentu oraz bardzo podstawowy zestaw podstawowego stylu. To bardziej tylko dwupoziomowe dziedzictwo. Każdy element w komponencie miałby albo regułę stylu globalnego, albo specyficzny dla tego komponentu. To jedna z łatwiejszych opcji.

użytkownik224551
źródło
Niezwykle dobry argument. Deweloperzy powinni mieć możliwość samodzielnego myślenia i analizy zakresu problemu. Ślepe przestrzeganie metod nadal prowadzi do kłopotów. Mam kolegów, którzy w ogóle nie biorą pod uwagę skutków ich zmian na stronie i bez względu na to, jaką metodologię stosujemy, czas idzie na południe. Staram się podnieść poziom świadomości CSS w zespole. Zagnieżdżone SASS ze stylami lokalnymi i globalnymi wystarczy, aby projekt był czysty i łatwy do odczytania.
Adrian Moisa