Search code examples
cssvariableslessmixins

LESS - how to parse/escape parametric variables (ie. variable variables) in a mixin/loop


I'm attempting to loop through a number of indexed variables, in this case colours, to create a class for each. Something along the lines of this:

@colour-1: #FF0000;
@colour-name-1: "red";

.loop (@index) when (@index > 0) {
  @colour: ~"@{colour-@{index}}";
  @name: "@{colour-name-@{index}}";

  (~'*[data-colour="@{name}"]') {
    background-color: @colour;
    background-color: hsla(hue(@colour), saturation(@colour), lightness(@colour), 0.5);
  }

  .loop(@index - 1);
}
.loop (0) {}
.loop (1);

Rather than providing a fallback variable for IE<9, I'd like to update each colour/value programatically within the mixin to provide both an RGBA & Hex version. Problem is the @{@var} doesn't evaluate until after the fact and so won't parse as a colour.

Is there a way to escape the variables so they don't pass by reference? JSFiddle here showing the output: http://jsfiddle.net/Qj2cZ/


Solution

  • On further examination (and following a bit of a breather) I found a working solution for less v1.3.3. If you are using v1.4 I would still recommend ScottS's answer, as this hacks around a bug.

    As mentioned, the issue is with the variable not being parsed in time for the color() function. However if the variable is evaluated in one function and passed to another for conversion to a colour everything works fine. So the following outputs the required styles:

    @colour-1: #FF0000;
    @colour-name-1: "red";
    
    .loop (@index) when (@index > 0) {
      @colour: ~"@{colour-@{index}}";
      @name: "@{colour-name-@{index}}";
      .setColour(@colour, @name);
      .loop(@index - 1);
    }
    
    .setColour (@colour-string, @name) {
      @colour: color(@colour-string);
      (~'*[data-colour="@{name}"]') {
        background-color: @colour;
        background-color: hsla(hue(@colour), saturation(@colour), lightness(@colour), 0.5);
      }
    }
    
    .loop (0) {}
    .loop (1);
    

    JSFiddle here: http://jsfiddle.net/LJ3zX/