Search code examples
parametersargumentslessmixinsellipsis

Less: Is there a difference between @arguments and ellipsis (...)?


I was just wondering because it came up in our project today. There doesn't seem to be a difference when implementing a mixin and capturing the parameters with @arguments or ellipsis, couldn't find anything useful on google either so I'm asking here.

Example:

.transition(@arguments) {
    -webkit-transition: @arguments;
    -moz-transition: @arguments;
    transition: @arguments;
}

or

.transition(...) {
    -webkit-transition: @arguments;
    -moz-transition: @arguments;
    transition: @arguments;
}

Use:

.transition(left 0.3s ease, top 0.3s ease);

Is there any advantage to either of these implementations?


Solution

  • There doesn't seem to be a difference

    There's actually, did you try to compile your code? These are quite different mixins:

    // this is a mixin definition with a variable number of arguments
    .a(...) {
        // here you use built-in @arguments variable
        a-value: @arguments;
    }
    
    // this is a mixin definition with a single argument
    .b(@arguments) {
        // here you use a variable you've just declared in mixin's argument list
        // (and it's not the built-in @arguments!)
        b-value: @arguments;
    }
    
    test {
        .a(1, 2, 3); // OK
        .b(1, 2, 3); // Error
    }
    

    Or in other words:

    .a(@arguments) {
        a-value: @arguments;
    }
    

    is equal to:

    .a(@x) {
        @arguments: @x; // defines a new variable that overrides the built-in one
        a-value: @arguments;
    }
    

    There's also another way to declare a variable argument list: .mixin(@whatever...). Basically it is the same as (...) but it is useful when you need something like:

    .c(@head, @tail...) {
        head: @head;
        tail: @tail;
    }
    
    test {
        .c(1, 2, 3, 4, 5)
    }