Skip to content

Instantly share code, notes, and snippets.

@tnunamak
Last active November 17, 2015 21:08
Show Gist options
  • Save tnunamak/6b207bf25e2f7e0db324 to your computer and use it in GitHub Desktop.
Save tnunamak/6b207bf25e2f7e0db324 to your computer and use it in GitHub Desktop.
BEM

This document is a draft in progress Authors include @danheberden and @alitsa.

Goals

  • Our product should render well on most client sites by default.
  • Overrides should be straightforward and not require excessively specific selectors or work-arounds.
  • Style semantics should generally be portable to other BV products.

Proposal

Rule selectors should be formatted either as (with <token> indicating that token is optional):

.bv.product .block<__element><--modifier>

or

.bv.product .helper

While this enables the use of very specific rule selectors, in practice selectors should only be as long as they need to be.

/* Bazaarvoice stars */
.bv.bv_all .bv_stars {
  color: yellow;
}

/* Client customizations to Bazaarvoice stars  */
.bv_override.bv.bv_all .bv_stars {
  color: red;
}

/* All Bazaarvoice stars that are anchor tags */
.bv.bv_all a.bv_stars {
  text-decoration: none;
}

/* Seller Ratings stars only */
.bv.bv_seller-ratings-display .bv_stars {
  font-size: 1em;
}

/* Seller Ratings stars, but the ones up in the summary, specifically.
   Note that the block element .bv_summary__stars is the target, not all .bv_stars.*/
.bv.bv_seller-ratings-display .bv_summary__stars {
  font-size: 1.5em;
}

For overriding convenience, the container element should have the bv_override class.

<div class="bv bv_seller-ratings-display bv_override">
  <div class="bv_summary">
    <strong class="bv_rating bv_summary__rating">5 / 5</strong>
    <div class="bv_stars bv_summary__stars">★★★★★</div>
  </div>
</div>

This enables clients to override a rule by prepending the bv_override class to its selector.

.bv_override.bv.seller-ratings-display .bv_stars {
  color: red;
}

.bv_override.bv.seller-ratings-display .bv_summary__stars {
  font-size: 2em;
}

In addition to the seller-ratings-display class, the container should have the bv_all class. This class enables the use of rules that are global to BV products.

<div class="bv_seller-ratings-display bv_all bv_override">
  <!-- Product markup goes here. -->
</div>
.bv.bv_all .bv_stars {
  color: yellow;
}

We think the specificity of these selectors should override client styles most of the time without being excessively heavy. Read about how CSS specificity is computed for more context.

Resetting Global Styles

Some clients may have global style rules that cause Seller Ratings to render poorly. A small set of reset rules should be included by default. For example:

.bv.bv_all div { 
  display: block;
}

For clients who need a more aggressive reset, we will provide our support team with a style sheet that includes a broader set of reset rules on par with normalize.css.

Class Naming

Elements should be heavily annotated with classes that can be used for targeted overriding. Specifically, styles specific to blocks should follow BEM guidelines.

Conventions

Helper classes may be assigned to elements that make multiple appearances within one or more blocks.

<span class="bv_stars">★★★★★</span>

Elements may appear in logical groups and share a parent. The parent should also have a helper class of the helper name followed by the word "Group".

<span class="bv_starsGroup">
  <span class="bv_stars">★★★★★</span> 
  <span class="bv_stars">★★★★★</span>
</span>

It is possible for an element to simultaneously be the parent of like-siblings and a like-sibling itself. In this case, the element would simply contain all of the relevant classes.

Blocks are labeled with a class name.

<span class="bv_summary">
  <!-- Block markup goes here -->
</span>

Block elements are given a specific class name that allows them to be targeted individually. If an element has an associated helper class, it may be appropriate to include it in the element name. Just by looking at the CSS, BEM conventions convey the basic structure of the DOM.

<span class="bv_starsGroup bv_summary">
  <span class="bv_stars bv_summary__starsBottom">★★★★★</span> 
  <span class="bv_stars bv_summary__starsTop">★★★★★</span>
</span>

Blocks can contain other blocks.

<span class="bv_summary">
  <span class="bv_starsGroup">
    <span class="bv_stars bv_summary__starsBottom">★★★★★</span> 
    <span class="bv_stars bv_summary__starsTop">★★★★★</span>
  </span>
  <span class="bv_logo>
    <!-- Block markup goes here -->
  </span>
</span>

Some styles rules are defined globally.

/* Prevent grid columns from wrapping. */
.bv {
  box-sizing: border-box;
}

.bv *, .bv *:before, .bv *:after {
  box-sizing: inherit;
}

Helper Classes

Here are some classes expected to be recycled in future apps/modules:

  • bv_section – layout elements that are used in a way that is semantically similar to
  • bv_segment – layout elements that are will likely appear as a horizontal bar
  • bv_block – layout elements that are likely to be stacked
  • bv_stars – ratings
  • bv_num, bv_operator, bv_den – 4.3 , out of , 5
  • bv_prefix, bv_suffix – used to break up a sentence; <strong> is likely to be used for the main part
  • bv_grid – parent element which gives flex-box styles to its bv_cell children
  • bv_cell – layout elements used to organize content into rows, a grid, a table, or any other layout, dependent on the special class given to their parent element
  • bv_hidden – class name used to hide elements dynamically with Javascript
  • bv_clearfix – class name given to parent elements that will likely contain floating children
  • bv_offscreen – class name given to elements that wrap text intended for screen readers only
  • bv_nickname, bv_logo, bv_cgcLink, etc. – independent units (not part of a like-sibling group) have their own unique class names. Hopefully we will not collect too many of these given the link-sibling naming strategy.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment