Using Sass lists and each loops for super easy CSS branding

Lately, here at Mikamai we’ve been working on a large client project that substantially consists in building an API for injecting content in a page. The content is requested via a JS API that accepts some arguments, one of which being the brand the developer needs – based on this brand, the script injects different content that needs to be styled in different ways (one per brand). So, how to approach that last step?

The problem

The first solution that came to mind was to assign a different class to the body and, based on that, apply the according styles for each different brand. For example:

  body {
    /* Default style */
    background-color: #ffffff;

    &.brand-one {
      background-color: #c09853;

      .title {
        color: #fcf8e3;
      }
    }

    &.brand-two {
      background-color: #eaeaea;

      .title {
        color: #a200b8;
      }
    }

    /* And so on.. */
  }

This could work, but we’ll eventually have some problems. The first (and probably biggest) one is that we have a lot of duplicated code, that means an hard-to-mantain codebase and readability concerns.

Sass to the rescue

Among Sass’ awesome features, there are two in particular that could come handy in our case: Lists (arrays, basically) and each loops (I’ll let you guess that). With these tools in our hands, we could convert the above code snippet in something like this:

$brands:  (brand-one   #c09853 #fcf8e3), 
          (brand-two   #eaeaea #a200b8),
          (brand-three #000000 #222222);

body {
  @each $brand in $brands {
    $division: nth($brand, 1);
    $division-bg-color: nth($brand, 2);
    $division-title-color: nth($brand, 3);

    &.#{$division} {
      background-color: #{$division-bg-color};

      .title {
        color: #{$division-title-color};
      }
    }
  }
}

What we’re doing here is creating some nested Sass lists with 3 values: respectively the brand name, the brand background color and the brand title color. It could be expressed this way:

$list: (brand-name background-color title-color)

Then, in the body style declaration, we start a @each loop that iterates over each list value and – with the nth operation – assigns every nested value to a variable. We then interpolate our newly created variables in our style declaration, resulting in what we wanted at the beginning. Cool, right? But we could improve that solution to be more flexible and clean. How?

Mixins and variables

The power of Sass offers again great ways to write modular and easy to read and mantain code. Defining a mixin that includes our über-cool function is super easy:

$brands:  (brand-one $brandone-bgcolor $brandone-title-color), 
          (brand-two $brandtwo-bgcolor $brandtwo-title-color),
          (brand-three $brandthree-bgcolor $brandthree-title-color);

@mixin brand-colors {
  @each $brand in $brands {
    $division: nth($brand, 1);
    $division-color: nth($brand, 2);
    $division-title-color: nth($brand, 3);

    &.#{$division} {
      background-color: #{$division-color};

      .title {
        color: #{$division-title-color};
      }
    }
  }
}

As you can see we just defined a mixin (presumably in a separated helper.scss file) that we can trivially include in our main css. Plus, we don’t have any hardcoded color value in our mixin, since we replaced them with variables (that we could declare in a specific var.scss file – separation of concerns, right?). That means that in the end we’ll have 3 files:

  • vars.scss
  • helpers.scss
  • main.scss

In vars.scss we’ll have something like that:

  $brandone-bgcolor: #eaeaea;
  $brandone-title-color: #333333;

  // etc.

In helpers.scss our “brand-colors” mixin:

$brands:  (brand-one $brandone-bgcolor $brandone-title-color), 
          (brand-two $brandtwo-bgcolor $brandtwo-title-color),
          (brand-three $brandthree-bgcolor $brandthree-title-color);

@mixin brand-colors {
  @each $brand in $brands {
    $division: nth($brand, 1);
    $division-color: nth($brand, 2);
    $division-title-color: nth($brand, 3);

    &.#{$division} {
      background-color: #{$division-color};

      .title {
        color: #{$division-title-color};
      }
    }
  }
}

In main.scss we could do something like that:

  @import "vars";
  @import "helpers";

  body {
    @include brand-colors;
  }

Ta-dah! Modular, extensible code and easy to mantain styles for all the brand variations you wish.

Lists and mixins can do much more than this. Try them and you’ll never come back! 

Bonus codepen bonanza.

Align vertically any element in CSS using translateY

If you’re reading this, you probably had to face – at least once in your life – the challenge of the vertical align in CSS.

image

There are many, many solutions. One could argue about which one is cleaner, more elegant, more compatible, and so on. Today I’ll just give you another option – you decide which one you like the most!

Yet another way to do it

Lately I’m using the translateY method.


element {
  position: relative;
  top: 50%;
  transform: translateY(-50%);
}


The explanation is trivial: we position the element relatively and give it 50% top, pushing it down for the half of the container height. Then, we move it the half of its own height up. And.. That’s it!

image

You can find a live example here.

I like the simplicity and conciseness of this method, and I’m using it quite often. The only downside of this is that it only works on browsers that support CSS3 Transforms (basically > IE9).

If you don’t plan to support legacy browsers, give it a try!

Profiling web pages in Chrome DevTools for fun and profit

As a front-end developer, an important part of your work should be making your users comfortable interacting with your super-hot parallax website – that means, you should be careful avoiding framerate drops or laggy interactions.

I’ll quickly show you how to detect front-end bottlenecks in your web application using Chrome Developer Tools.

TL;DR

Chrome DevTools can inspect browser events and track your website framerate. Use it to debug your application and smoothen your site UX!


A little introduction

First, you’ll obviously need to open Chrome DevTools (on Macs you can press Alt + Cmd + I) and switch to the Timeline tab. You’ll see something like this:

image

Here you can take a peek at the 3 fundamental aspects for the (client side) performance of a web application:

  • Events. These are the events the page fires and that the browser executes (i.e. Build my layout! or Hide this div (and recalculate the width of the adjacent one)!)
  • Frames. You can guess that. The more the FPS, the smoother the website will be.
  • Memory. The amount of RAM memory your page takes to run. Useful for detecting JS memory leaks!

They’re obviously tied together very closely and you should keep an eye on each one.

Stop talkin’ now, let’s get our hands dirty!

To start profiling a page, you need to press the “Record” bullet icon in the bottom left menu:

image

When the icon switches red, reload the page, so that the DevTools can record and profile your website. Remember to turn it off! You’ll probably want to analyze a small bit of interaction at a time, otherwise you’ll be likely overwhelmed by a lot of data.

At this point, you’ll see something like this:

image

Each bar represents an event and its duration. As you can guess, every color refers to a different event: blue is for assets loading, yellow for scripting, violet for rendering and green for painting.

Just above that, you can see a timeline which represents the same events vertically – the higher the bar, the lesser the frames per second. This is very useful when you’re trying to detect lag spikes and you want to rapidly find the cause. Just look at the higher bar, pair it with its own event and.. debug! 🙂

You can select which time window you want to analyze moving the handles on the timeline highlighted section (or you can scroll with your mouse wheel on it to reduce or expand it).

Having a clear representation of every page event and its related consequences is cool, and can speed up a lot front-end debugging. But there’s more!

In this case we can see that a paint event is taking place and that it needs ~25ms to complete. Well, click on the arrow to the left of the event and you’ll see the best part!

image

Clicking on the arrow you can inspect the internal processes of the selected event, and see which are the required steps (and how much time they need) for the completion of it! Crazy, huh?

Plus, if you hover on an event, you’ll see a very useful resumé of its properties:

image


We just saw how the Frames section works, but the Events section is pretty much the same thing, so I’ll let you discover that by your own. The Memory tab, additionally, gives you a visual representation of the RAM memory usage, with other useful info (DOM Node count, Event Listener Count):

image

In conclusion

Chrome DevTools is a fantastic piece of software that can help you in many, many ways. We have just scratched the surface – if you want to dive in, you can read the official Google Developers documentation or read one of the many tutorials on HTML5 Rocks website.

 

Mantaining a fluid element aspect ratio with CSS pseudo-elements

Do you ever wondered how to scale a div within a fluid layout, keeping its aspect ratio?

The solution is pretty easy, and – amazingly – you don’t need Javascript

Just nest your element in a fluid container – this will be our ratio-killer – and give it these rules:

  
.container {
  position: relative;
  display: inline-block;
  width: 50%;
}

These properties will let our container div to scale accordingly to the parent element width. Then, we’ll use CSS3 pseudo elements on the container to do the magic:

&:before {
content: "";
display: block;
padding-top: 145%;
}

The padding-top will represent the height of our div. So tweak the percentage accordingly to the desired aspect ratio!

Finally, we’ll place the element for the contents and give it absolute positioning:

.inside-content {
position: absolute;
top: 0;
bottom: 0;
left: 0;
right: 0;
}

And voilà! The trick is done: we now have a fluid element that scales keeping its aspect ratio.

Want to give it a ride? Here’s an example: http://cdpn.io/GIJmz