less Loops Writing a simple for loop


Usage of loops is an excellent way to keep the code DRY and avoid repetition. Unlike in Sass, there are no built-in @for or @each directive in Less for writing loops but it can still be written using recursive mixins. A recursive mixin is nothing but a mixin which keeps calling itself.

There are four key components to a loop written using Less and they are as follows:

  • A mixin with guard expressions. The guard is used to terminate the loop when the loop's exit criteria is met. In terms of a JavaScript for loop (for([initialization]; [condition]; [final-expression])), the guard is the [condition].
  • A primary call to the mixin to execute the first iteration. This primary call to the mixin can be made from within a selector block (if the mixin doesn't have a selector wrapping all its contents) or from outside a selector block (if the mixin has a selector wrapping its contents). In terms of a JavaScript for loop, this primary call serves as the [initialization] as it sets the base value for the counter-like variable.
  • A call to the mixin from within itself to make it recursive. This call typically passes an incremented or a decremented value of the counter variable as the argument. Thus it invokes the subsequent iterations. In terms of a JS for loop, this does the [final-expression] along with the next call.
  • Last but not the least, the other contents of the mixin which is equivalent to the statement in a typical for loop syntax.

Below is a simple for loop written in Less that creates multiple #img* selectors (where * is a number) and also sets the background-image property as image*.png.

.for-loop(@index) when (@index > 0) { /* recursive mixin with guard expression - condition */

  /* the statement */
  #img@{index} {
    background-image: url("http://mysite.com/image@{index}.png");
  /* end of the statement */

  .for-loop(@index - 1); /* the next iteration's call - final-expression*/
.for-loop(3); /* the primary call - initialization */

Compiled CSS:

#img3 {
  background-image: url("http://mysite.com/image3.png");
#img2 {
  background-image: url("http://mysite.com/image2.png");
#img1 {
  background-image: url("http://mysite.com/image1.png");