Mixins with LESS are really simple:
.some-rules() {
/* some rules */
}
.some-class {
.some-rules;
}
However, suppose I've got a ruleset within a media query, like:
#media (min-width: 800px) {
.my_ruleset {
/* more rules */
}
}
How can I include such a ruleset as a mixin?
My motivation here is that I am using Bootstrap. I am trying to avoid semantically polluting my markup with its selectors, and would rather incorporate its rulesets as mixins. That's simple enough given the first example above, but I'm not sure how to incorporate the #media selectors.
EDIT
Specifically, here is a summary of the code I am trying to use as a mixin:
.container {
.container-fixed();
}
// ...
#media (min-width: #screen-sm) {
.container {
max-width: #container-sm;
}
// ...
}
#media (min-width: #screen-md) {
.container {
max-width: #container-md;
}
// ...
}
#media (min-width: #screen-lg-min) {
.container {
max-width: #container-lg;
}
// ...
}
Just simply add:-
.my_ruleset {
/* more rules */
}
#media (min-width: 800px) {
.my_ruleset;
}
If you want to add parameters to this for instance then:-
.my_ruleset(#myMargin:5px;) {
margin:#myMargin;
}
#media (min-width: 800px) {
.my_ruleset(10px);
/* New Rules*/
}
.
.
/* And so On */
Update:-
if you want to adapt this in a dynamic form take whole media query into mixin and play with it...
.container(
#minSize:768px;
#maxSize:979px;
#myColor:green;
/* So on */
) {
#media (min-width: #minSize) and (max-width: #maxSize) {
.my_ruleset {
background-color:#myColor;
}
/* New Rules*/
}
}
.container(0px,480px,black);
.container(481px,767px,blue);
.container(768px,979px,pink);
.container(980px,1200px,white);
.container(1700px,2200px,red);
EDIT
Checkout these two answers (class set in media query, media query grouping), I feel like they are very closely related to your question. Looking at the second answer I tried to put something together. The snippet is below, but you can also see a demo.tar.gz I put together as well.
main.less
#import "less/bootstrap"; /*Obviously, make sure to have all the less src :)*/
/*source: http://tinyurl.com/less-query */
.make-container(#min-width) {
#media (min-width: #min-width) {
.page-maker(#max-width) {
.page {
max-width: #max-width;
.container-fixed();
}
}
.make-page-style() when (#min-width=#screen-lg-min) {
.page-maker(#container-lg);
}
.make-page-style() when (#min-width=#screen-md) {
.page-maker(#container-md);
}
.make-page-style() when (#min-width=#screen-sm) {
.page-maker(#container-sm);
}
.make-page-style();
}
}
.make-container(#screen-sm);
.make-container(#screen-md);
.make-container(#screen-lg-min);
HTML
...
<body>
<div class="page">
...
</div>
...
OLD
have you tried using the following mixins (n is the number of columns):
.make-row()
.make-lg-comun(n)
.make-md-column(n)
.make-xs-column(n)
These mixins are used to semantically structure the page. For example, if you have the following markup:
<div class="main">
<div class="left">
</div>
<div class="right">
</div>
</div>
then in your less you can do:
.main{
.make-row();
}
.left{
.make-lg-column(5); /* makes five large desktop column */
}
.right{
.make-lg-column(7);
}
if this is not what you are looking for, perhaps elaborate on your intent more, maybe you won't need to do a lot of media queries.
You can use parent selector:
#screen-sm: 400;
#screen-md: 800;
#screen-lg-min: 1000;
.responsive(#width-sm, #width-md, #width-lg) {
#media (min-width: #screen-sm) {
& {
max-width: #width-sm;
}
}
#media (min-width: #screen-md) {
& {
max-width: #width-md;
}
}
#media (min-width: #screen-lg-min) {
& {
max-width: #width-lg;
}
}
}
.container {
.responsive(100px, 200px, 300px);
}
Output:
#media (min-width: 400) {
.container {
max-width: 100px;
}
}
#media (min-width: 800) {
.container {
max-width: 200px;
}
}
#media (min-width: 1000) {
.container {
max-width: 300px;
}
}
Related
I'm using Bourbon Neat in my project and Neat has this neat (ha!) little mixin for media queries:
$xs-media: new-breakpoint(min-width 1px max-width 480px);
#include media($xs-media) {
// your styles
}
But #include media doesn't support multiple breakpoints. So I'm trying to do this:
#mixin multiple-media($breakpoints...) {
#each $breakpoint in $breakpoints {
#include media($breakpoint) {
#content
}
}
}
I can then use multiple breakpoints on it:
$xs-media: new-breakpoint(min-width 1px max-width 480px);
// $sm-media: ...
// $md-media: ...
#inlclude multiple-media($xs-media, $sm-media, $md-media) {
// my styles
}
But the compiled CSS doesn't quite work and look right. This is what gets generated (Just an example of what happens):
#media screen and (min-width: min-width) {
.instagram-widget .instagram-widget__images-container > a > img {
width: 25%; } }
#media screen and (min-width: min-width) {
.instagram-widget .instagram-widget__images-container > a > img {
width: 25%; } }
#media screen and (min-width: min-width) {
.instagram-widget .instagram-widget__images-container > a > img {
width: 25%; } }
#media screen and (min-width: min-width) { ??
I am trying to develop my own grid system. This is my first attempt so maybe I am missing something. Here is my CSS:
.column-1 {
width: 6.86666666667%;
}
.column-2 {
width: 15.3333333333%;
}
// More such columns
#media only screen and (max-width: 768px) {
.column-s-1 {
width: 6.86666666667%;
}
.column-s-2 {
width: 15.3333333333%;
}
}
As you can see the values are duplicated but class names are different. Is there any way I can avoid this duplication because it will become more and more complex with each additional class.
You can avoid some of duplication by grouping selectors:
.column-1,
.column-s-1 {
width: 6.86666666667%;
}
.column-2,
.column-s-2 {
width: 15.3333333333%;
}
// More such columns
#media only screen and (max-width: 768px) {
.column-s-1 {
/* only properties characteristic for this width*/
}
}
Another option is to use LESS or SASS
This question already has an answer here:
CSS property as SASS mixin value [duplicate]
(1 answer)
Closed 8 years ago.
I'm trying to create a mixin that will take a rule (e.g. margin) and return media queries. This is what I've tried so far:
$screen_smx: 767px;
$screen_sm: 768px;
$screen_md: 960px;
$screen_lg: 1200px;
$header_height_xs: 50px;
$header_height_sm: 80px;
$header_height_md: 60px;
$header_height_lg: 60px;
#mixin header_height($rule) {
#media (max-width: $screen_smx) {
$rule: $header_height_xs;
}
#media (min-width: $screen_sm) {
$rule: $header_height_sm;
}
#media (min-width: $screen_md) {
$rule: $header_height_md;
}
#media (min-width: $screen_lg) {
$rule: $header_height_lg;
}
}
So I can do something like the following:
#header {
position:fixed;
#include header_height(height);
}
body > .container {
#include header_height(padding-top);
}
The above code doesn't throw any errors it just doesn't create any code. Is there something I'm missing out or is what I'm trying to do just not achievable?
Thanks.
It turns out that to use a mixin param as a css rule the variable has to be wrapped in #{}
e.g.
#mixin header_height($rule) {
#media (max-width: $screen_smx) {
#{$rule}: $header_height_xs;
}
#media (min-width: $screen_sm) {
#{$rule}: $header_height_sm;
}
#media (min-width: $screen_md) {
#{$rule}: $header_height_md;
}
#media (min-width: $screen_lg) {
#{$rule}: $header_height_lg;
}
}
I'm trying to test the following code out in Chrome and Firefox and neither is picking it up. I have added it to the end of my stylesheet which works fine anyway.
#media all and (max-width : 850px) {
h1#site-name {
width: 100%;
a {
margin: auto;
}
}
nav#main-menu {
float: left;
}
}
I am re-sizing my browser window and the changes are obviously not taking effect at any width. The code is within a .scss file for reference.
Any ideas?
You can use mixins for media queries in scss too.
#mixin mq($mq) {
#if $mq == medium {
#media (max-width: 850px) { #content; }
}
}
#main-menu {
// default styles
// media query 850px max-width
#include mq(medium) {
float: left;
}
}
Check out this article for more info.. http://css-tricks.com/media-queries-sass-3-2-and-codekit/
I really enjoyed finding out you could create a media query variable that you can easily reuse and makes your code much more readable.
#tablet: ~"(min-width: 768px) and (max-width: 980px)";
#media #tablet { ... }
I want to know if it's possible to group a media query with a selector. It doesn't appear to work the way I've implemented it, but I thought I'd ask to see if it's even probable.
#tablet: ~"(min-width: 768px) and (max-width: 980px)";
body {
aside { ... }
&.homepage,
#media #tablet {
aside { ... }
}
}
I understand that media queries are different from run-of-the-mill selectors because you have to define your selectors inside of the media query, but is there some voodoo LESS way to accomplish grouping like this?
I'm not a 100% certain of the output you are going for, but this LESS only defines the color red once, and applies it to both:
#tablet: ~"(min-width: 768px) and (max-width: 980px)";
body {
aside { color: blue }
&.homepage {
aside { color: red }
}
#media #tablet {
.homepage;
}
}
Yields this CSS:
body aside {
color: #0000ff;
}
body.homepage aside {
color: #ff0000;
}
#media (min-width: 768px) and (max-width: 980px) {
body aside {
color: #ff0000;
}
}