SCSS - Conditional include not working and all the blocks gets executed

Viewed 92

I am trying to do conditional include in scss. Here is the code:

HTML

<div class="test" data-active data-label data-comment >1</div>
<div class="test" data-active data-label>2</div>
<div class="test" data-active data-comment >3</div>
<div class="test" data-active data-comment data-label>4</div>
<div class="test" data-active>5</div>

SCSS

.test[data-active]{

  background : red;
  width: 50px;
  height: 50px;
  display: inline-block;
  
  $margin: 0px;
  &[data-label]{
    background : blue;
    $margin: $margin + 10px;
  }
  &[data-comment]{
    background: yellow;
    $margin: $margin + 10px;
  }
  &[something]{
    $margin: $margin + 100px;
  }
  margin-right : $margin;
}

Here is the codepen link: https://codepen.io/gaurav-neema/pen/VwpPBxY

In the code, you can see that even if the element does not contain the attribute, all the blocks get executed and the margin is included.

Can anyone help in indentifying what's wrong with the code?

2 Answers

You are redefining $margin every time, you cannot use selectors like if statements.

Redefining with:

  • $margin: $margin + 10px;
  • $margin: $margin + 100px;

You are setting all margin-right: 100px;

I think you might want:

SCSS

$margin: 0px;

.test[data-active] {
  background: red;
  width: 50px;
  height: 50px;
  display: inline-block;
  
  &[data-label] {
    background : blue;
    margin: $margin + 10px;
  }

  &[data-comment] {
    background: yellow;
    margin: $margin + 10px;
  }

  &[something] {
    margin: $margin + 100px;
  }

  margin-right: $margin;
}

What you are looking for is CSS custom properties. SCSS is not dynamic and there for renders at compile. CSS custom properties are dynamic so they get applied once the condition is for filled, meaning when your class is applied it will change the value then.

Read about the difference at:

Read about CSS custom properties at:

This is just 3 of so many articles about the subject.

Now demo time, I changed the property to be background-color to make it more clear for the demo.

.test[data-active] {
  --background-color: aqua;

  background: var(--background-color);
  width: 50px;
  height: 50px;
  display: inline-block;
}

.test[data-label] {
  --background-color: deeppink;
}

.test[data-something] {
  --background-color: deepskyblue;
}
<div class="test" data-active data-label data-comment>1</div>
<div class="test" data-active data-label>2</div>
<div class="test" data-active data-comment>3</div>
<div class="test" data-active data-comment data-label>4</div>
<div class="test" data-active data-something>5</div>

Related