CSS

REM Sass Mixin With Pixel Fallback

The REM CSS unit is similar to the EM CSS unit except it allows you to size elements relative to the root of the HTML tag, as it stands for Root EM. The EM unit is relative to the font-size of the parent, which can cause problems in working out the correct size to use in descendent elements.

Because the REM is relative to the root we can set the default font-size in the HTML tag which allows us to easily define the size of the other elements.

Defining the html font-size as 62.5% allows us to defines REMs similar to pixels.

html { font-size: 62.5%; } 
body { font-size: 1.4rem; } /* =14px */
h1   { font-size: 2.4rem; } /* =24px */

The REM CSS unit is widely supported on most modern browsers but it's not supported in IE8 and lower browsers, for unit values to work in both modern browsers and IE8 we will need to duplicate the property in the CSS.

html 
{ 
    font-size: 62.5%; 
} 

body 
{ 
    font-size: 14px;
    font-size: 1.4rem;
}

h1   
{ 
    font-size: 24px;
    font-size: 2.4rem;
}

Instead of repeating ourself everywhere in the CSS we can use a Sass Mixin for our REM property and pixel fallback.

@mixin rem2px($property, $sizeValue: 1.6) {
  #{$property}: ($sizeValue * 10) + px;
  #{$property}: $sizeValue + rem;
}

Now we can use this in our Sass to output the same as above with the following code.

body 
{ 
    @include rem2px(font-size, 1.4);
}

h1   
{ 
    @include rem2px(font-size, 2.4);
}

This @mixin can work well for single value elements like font-size but it's not going to help when you need to have multiple values in properties like margins or padding.

The following @mixin was found on Hugo Giraudel post which allows you to handle properties with multiple values.

html {
  font-size: 62.5%; /* 1 */
}

@function parseInt($n) { /* 2 */
  @return $n / ($n * 0 + 1);
}

@mixin rem($property, $values) {
  $px : (); /* 3 */
  $rem: (); /* 3 */
  
  @each $value in $values { /* 4 */
   
    @if $value == 0 or $value == auto { /* 5 */
      $px : append($px , $value);
      $rem: append($rem, $value);
    }
    
    @else { 
      $unit: unit($value);    /* 6 */
      $val: parseInt($value); /* 6 */
      
      @if $unit == "px" {  /* 7 */
        $px : append($px,  $value);
        $rem: append($rem, ($val / 10 + rem));
      }
      
      @if $unit == "rem" { /* 7 */
        $px : append($px,  ($val * 10 + px));
        $rem: append($rem, $value);
      }
    }
  }
  
  @if $px == $rem {     /* 8 */
    #{$property}: $px;  /* 9 */
  } @else {
    #{$property}: $px;  /* 9 */
    #{$property}: $rem; /* 9 */
  }
}
Back to top ^

Join Paulund

  • Get access to 100s of premium tutorials and downloadable content
  • Members content consists of Premium WordPress plugins, CSS packages, jQuery packages, tutorial demo files and templates for 100s of web development tutorials
  • In-depth development tutorials
  • Priority tutorial requests
  • Priority email development support
  • No ads

Here at Paulund you'll find Web Development tutorials and snippets focusing mainly on PHP, WordPress and CSS. Members will get access to premium tutorials that go into more detail about development with these languages. You will also get access to downloadable premium content based on the tutorial.

Join Paulund

Leave a Reply

Your email address will not be published. Required fields are marked *