I'm trying to use LESS to dynamically generate a set of mixins that would help me write cleaner media query code. So far in my limited knowledge of the language I've put together code that looks like this:
@sizes: xxs, xs, sm, md, lg;
.mediaQueries(@iterator:1) when(@iterator <= length(@sizes)) {
//Extract name
@sizeName: extract(@sizes, @iterator);
//Attempt to build min-width query
.MQ-min-@{sizeName} (@content) {
@media (min-width: @screen-@{sizeName}) {
@content();
}
}
//Attempt to build max-width query
.MQ-max-@{sizeName} (@content) {
@media (max-width: @screen-@{sizeName}) {
@content();
}
}
.mediaQueries((@iterator + 1));
}
.mediaQueries();
The goal is to have a set of mixins that would allow me to easily and cleanly define some CSS properties for a specific breakpoint, like so:
.generic-class {
background: black;
//Sizes @screen-sm and up
.MQ-min-sm({
background: transparent;
})
}
It doesn't work. Something to note, I'm trying to interpolate the size name into a variable name that would then output me a the px
value of that variable into the @media
query. Is something like this even possible?
Otherwise my compiler currently breaks on the start of the nested mixin (.MQ-min-@{sizeName} (@content) {
) with the error:
Potentially unhandled rejection [2] Missing closing ')' in file ../mixins.less line no. 43
Is something like what I'm trying to achieve possible?
I think the simplest way for you to achieve this is by using a single parametric mixin like given below. This avoids the need for all those iterations, dynamic mixin creations etc.
@sizes: xxs, xs, sm, md, lg;
@screen-xxs: 100px;
@screen-sm: 200px;
.MQ(@content, @sizeName, @max-min) { /* get ruleset, size name and min/max as input */
@selector: ~"(@{max-min}-width: @{screen-@{sizeName}})"; /* form the media selector */
@media @selector { /* use it */
@content();
}
}
.generic-class {
background: black;
.MQ({
background: transparent;
}, /* ruleset */
sm, /* screen size */
max /* min/max */
);
}
If the mixins are for your own usage then this is all that you need. If it is for distribution as library then you may want to put some guards on @sizeName
and @max-min
variables to restrict invalid values.
Note: Less compiler always had a problem with the interpolation here - @media (min-width: @screen-@{sizeName})
also (I am not sure if it has been addressed) and that's why I created a temp variable.