Read This
There are several "correct" answers. Since this question gets a lot of traffic, I figured I should keep up with what (I think) the best answer is (based on the LESS documentation) as the LESS project matures, and change my accepted answer accordingly.
I'm using LESS and I haven't been able to find a fix for allowing multiple CSS3 box-shadows. I have the following mixin:
.box-shadow(@arguments) {
-webkit-box-shadow: @arguments;
-moz-box-shadow: @arguments;
box-shadow: @arguments;
}
and I'm attempting this:
.box-shadow(
inset 0 0 50px rgba(0,0,0,0.3),
0 0 10px rgba(0,0,0,0.5);
);
This works in normal CSS3, but fails when running from a LESS file. I've read somewhere that the comma separating the 2 shadows is what causes the issue in the LESS parser.
Does anyone know how to make this work? The only workaround I can think of is creating an additional CSS file that contains my multiple box-shadow properties.
The best solution is to make separate overloads for each number of shadows. Less handles the proper overload resolution:
.box-shadow(@shadow1) {
-webkit-box-shadow: @shadow1;
-moz-box-shadow: @shadow1;
box-shadow: @shadow1;
}
.box-shadow(@shadow1, @shadow2) {
-webkit-box-shadow: @shadow1, @shadow2;
-moz-box-shadow: @shadow1, @shadow2;
box-shadow: @shadow1, @shadow2;
}
.box-shadow(@shadow1, @shadow2, @shadow3) {
-webkit-box-shadow: @shadow1, @shadow2, @shadow3;
-moz-box-shadow: @shadow1, @shadow2, @shadow3;
box-shadow: @shadow1, @shadow2, @shadow3;
}
.box-shadow(@shadow1, @shadow2, @shadow3, @shadow4) {
-webkit-box-shadow: @shadow1, @shadow2, @shadow3, @shadow4;
-moz-box-shadow: @shadow1, @shadow2, @shadow3, @shadow4;
box-shadow: @shadow1, @shadow2, @shadow3, @shadow4;
}
.box-shadow(@shadow1, @shadow2, @shadow3, @shadow4, @shadow5) {
-webkit-box-shadow: @shadow1, @shadow2, @shadow3, @shadow4, @shadow5;
-moz-box-shadow: @shadow1, @shadow2, @shadow3, @shadow4, @shadow5;
box-shadow: @shadow1, @shadow2, @shadow3, @shadow4, @shadow5;
}
EDIT:
Ok, I'm still learning about LESS, but it appears that will actually mixin ALL of the overloads in certain situations, instead of the one with the most applicable parameter list, so you may get varying results. I've since revised my mixins so that they're named box-shadow-2 or box-shadow-3, to match the expected number of parameters. I'll revise my answer once I figure out what's going on / have a better solution.
This works with newer LESS versions:
.box-shadow(2px 2px 3px rgba(0,0,0,.4), 0px 0px 5px rgba(0,0,0,.8););
// this semicolon is important! ^
And this uglier version works even with older LESS versions:
.box-shadow(~"2px 2px 3px rgba(0,0,0,.4), 0px 0px 5px rgba(0,0,0,.8)");
Update: LESS evolved, so this answer was updated and is now correct again. Thanks Michał Rybak
It should work just fine. I've used it before. Try with this mixin:
.box-shadow (@shadow1, @shadow2: transparent 0 0 0 ) {
-moz-box-shadow: @shadow1, @shadow2;
-webkit-box-shadow: @shadow1, @shadow2;
box-shadow: @shadow1, @shadow2;
}
And then:
.box-shadow(inset 0 0 50px rgba(0,0,0,0.3), 0 0 10px rgba(0,0,0,0.5));
LESS strips the comma. So the @arguments
value becomes:
inset 0 0 50px rgba(0,0,0,0.3) 0 0 10px rgba(0,0,0,0.5);
Which is invalid as a box-shadow.
Instead, do this when you want a comma:
@temp: inset 0 0 50px rgba(0,0,0,0.3), 0 0 10px rgba(0,0,0,0.5);
.box-shadow(@temp);
.box-shadow (@shadow1) {
-webkit-box-shadow: @shadow1;
-moz-box-shadow: @shadow1;
-ms-box-shadow: @shadow1;
-o-box-shadow: @shadow1;
box-shadow: @shadow1;
}
.box-shadow (@shadow1, @shadow2) {
@temp: @shadow1, @shadow2;
.box-shadow(@temp);
}
.box-shadow (@shadow1, @shadow2, @shadow3) {
@temp: @shadow1, @shadow2, @shadow3;
.box-shadow(@temp);
}
This question is kind of out-of-date, as for now your solution actually works.
However, I'll try to explain why, because many people seem to be unaware of that:
Actually passing a list of comma-separated arguments to a mixin is pretty simple: just use semicolon (;
) instead of comma in mixin call.
From LESS documentation:
Parameters are either semicolon or comma separated. It is recommended to use semicolon. The symbol comma has double meaning: it can be interpreted either as a mixin parameters separator or as css list separator. Using comma as mixin separator makes it impossible to use comma separated list as an argument.
Semicolon does not have such limitation. If the compiler sees at least one semicolon inside mixin call or declaration, it assumes that arguments are separated by semicolons. All commas then belong to css lists.
Mixin definition uses well-known, regular syntax:
.box-shadow(@params) {
-webkit-box-shadow: @params;
-moz-box-shadow: @params;
box-shadow: @params;
}
But mixin call should use semicolons to separate arguments. If semicolons are used, commas are no longer treated as separators and are passed to mixin without problems:
.box-shadow(
inset 0 0 50px rgba(0,0,0,0.3), 0 0 10px rgba(0,0,0,0.5);
);
Note that if (as in the case above) only one list is passed, you have to use semicolon at the end, too.
Check out my answer regarding multiple backgrounds to see how mixin call should look with multiple parameters, some of which are comma-separated lists.
Here is another solution(which I prefer more):
Use e()
string function. Ex: e("S1, S2")
will return S1, S2
without quotes.
Long example:
Definition:
.c3_box-shadow(@val){
-webkit-box-shadow: @val;
-moz-box-shadow: @val;
box-shadow: @val;
}
Usage:
.box-shadow( e("inset 0 1px 0 rgba(255,255,255,.4), inset 0 -1px 0 rgba(255,255,255,.2)") );
Output:
-webkit-box-shadow: inset 0 1px 0 rgba(255,255,255,.4), inset 0 -1px 0 rgba(255,255,255,.2);
-moz-box-shadow: inset 0 1px 0 rgba(255,255,255,.4), inset 0 -1px 0 rgba(255,255,255,.2);
box-shadow: inset 0 1px 0 rgba(255,255,255,.4), inset 0 -1px 0 rgba(255,255,255,.2);
来源:https://stackoverflow.com/questions/9231369/how-do-you-create-multiple-box-shadow-values-in-less-css