Multiple properties are getting treated as separate arguments in mixins - less

I'm trying to write a mixin, but I can't seem to get the arguments working the way I want: multiple properties are getting treated each as a separate argument.
Current Code
.transition(#property: all, #time: 1s, #timing: ease-in-out) {
-moz-transition: #property #time #timing;
-webkit-transition: #property #time #timing;
-o-transition: #property #time #timing;
transition: #property #time #timing;
}
a {
.transition(color, opacity, .5s);
}
Desired Output
a {
-moz-transition: color, opacity .5s ease-in-out;
-webkit-transition: color, opacity .5s ease-in-out;
-o-transition: color, opacity .5s ease-in-out;
transition: color, opacity .5s ease-in-out;
}
Actual Output
a {
-moz-transition: color opacity .5s;
-webkit-transition: color opacity .5s;
-o-transition: color opacity .5s;
transition: color opacity .5s;
}
Any ideas?

I'd suggest using LESS's escape function, i.e.:
a:link, a:visited {
color: green;
opacity: .5;
font-size: 1em;
}
a:hover {
color: red;
opacity: 1;
font-size: 2em;
.transition(e("font-size, color"));
}
And though it seems that LESS accepts that, it will only animate the last property in the comma-separated string you send through. A pity.

Using the solution found here works with one AND multiple arguments:
.transition (#value1,#value2:X,...)
{
#value: ~`"#{arguments}".replace(/[\[\]]|\,\sX/g, '')`;
-webkit-transition: #value;
-moz-transition: #value;
-ms-transition: #value;
-o-transition: #value;
transition: #value;
}
Using it this way:
.transition(color, opacity .5s ease-in-out);
yields:
-webkit-transition: color, opacity .5s ease-in-out;
-moz-transition: color, opacity .5s ease-in-out;
-ms-transition: color, opacity .5s ease-in-out;
-o-transition: color, opacity .5s ease-in-outt;
transition: color, opacity .5s ease-in-out;

If you want to pass a comma-separated list as an argument to mixin, you can simply use a semicolon to separate arguments.
Code below works as desired with the mixin you defined:
a {
.transition(color, opacity; .5s);
}

Less mixins have the ability to use semicolon-separated arguments (as well as comma-separated). They recommend you always use semicolons.
If a semicolon is present in a list of arguments when the mixin is called, everything between semicolons will be considered as arguments, even if those things have commas in them. This allows you to pass a comma-separated list as ONE argument. If a semicolon is NOT present, it will treat commas as argument separators.
.transition(#property: all; #time: 1s; #timing: ease-in-out) { // NOTE THE SEMICOLONS
transition: #property #time #timing;
}
a {
.transition(color,opacity; .5s); // SEMICOLON AFTER 'opacity'
}
b {
.transition(color,opacity, .5s); // COMMA INSTEAD
}
output:
a {
transition: color,opacity .5s ease-in-out;
}
b {
transition: color opacity .5s; // invalid syntax
}
Note that the syntax of the shorthand transition property must be a comma-separated list of single transitions. So b has an invalid value, and a has two transitions, in which the unspecified values default to their initial value:
color 0s ease 0s
opacity .5s ease-in-out 0s
This is likely not what you intended. (It looks like you wanted color .5s ease-in-out 0s and opacity .5s ease-in-out 0s.)
Now you might be wondering, "how do I pass a comma-separated list as a single argument, when there are no other arguments?" Simply append a dummy semicolon at the end of the list.
.transition(#property: all; #time: 1s; #timing: ease-in-out) {
transition: #property #time #timing;
}
b {
.transition(color,opacity;); // DUMMY SEMICOLON AFTER ARGUMENT
}
i {
.transition(color,opacity); // MISSING SEMICOLON
}
output:
b {
transition: color,opacity 1s ease-in-out; // 'color,opacity' is the first argument
}
i {
transition: color opacity ease-in-out; // 'color' is 1st arg, 'opacity' is 2nd arg
}
Again, syntax for i is invalid, and b has two transitions:
color 0s ease 0s
opacity 1s ease-in-out 0s

Related

How to make owl-carousel with rotating cursor work in bootstrap?

I have been trying to make this owl-carousel by John Higgins (http://jonhiggins.co.uk/words/animated-rotating-cursor-over-carousel/) work with bootstrap.
This theme makes the cursor act like 'prev' and 'next' buttons when hovering the carousel image. But it seem that when I put html into a responsive container of bootstrap it somehow messes with the cursor.
When the browser width is expanded you will notice that the arrow doesn't switch from right to left. Please have a look at the fiddle.
https://jsfiddle.net/ftpptf/c6nw8yzt/
/* BEGIN Cursor*/
.cursor {
display: none;
top: 0;
left: 0;
position: fixed;
z-index: 1000;
width:33px;
height:54px;
margin-top: 60px;
margin-left: 33px;
pointer-events: none;
&.isVisible {
display: block;
}
}
.js--visible {
display: block;
}
.cursor__icon {
width:32px;
height:32px;
background-image: url('data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAw MC9zdmciIHdpZHRoPSIzMiIgaGVpZ2h0PSIzMiIgdmlld0JveD0iMCAwIDMyIDMyIiBpZD0ic3ZnIj48cGF0aCBmaWxsPSJub25lIiBzdHJva2U9IiNmZmYiIHN0cm9rZS13aWR0aD0iNCIgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIiBzdHJva2UtbGluZWpvaW49InJvdW5kIiBzdHJva2UtbWl0ZXJsa W1pdD0iMTAiIGQ9Ik0yNC4xIDMwTDcuOSAxNiAyNC4xIDIiPjwvcGF0aD48L3N2Zz4=');
background-repeat:no-repeat;
-webkit-transition: -webkit-transform 0.4s ease-out;
-moz-transition: -moz-transform 0.4s ease-out;
-o-transition: -o-transform 0.4s ease-out;
transition: transform 0.4s ease-out;
}
.carousel.offScreen .cursor {
display: none;
}
.carousel.right .cursor__icon {
-ms-transform: rotate(180deg);
-webkit-transform: rotate(180deg);
-moz-transform: rotate(180deg);
-o-transform: rotate(180deg);
transform: rotate(180deg);
}
/* END Cursor*/
I have set .cursor .cursor__icon position = absolute which seemed to help but it still acts weird.
I have tried loads of different settings but without any good results!
Any help will be highly appreciated - thanks in advance!
Glad the Codepen example is of use to you.
It looks like the issue is that your carousel's left edge isn't at 0px (far left of the window), it's halfway across the screen. My example didn't account for this scenario as the carousel filled the viewport horizontally.
Hopefully this fiddle resolves that: https://jsfiddle.net/jonjhiggins/z915kbe3/
Changes made were:
CSS: making the carousel and images 100% width instead of 800px (so that it will responsively fill the width of whatever you set it's parent to)
.carousel {
width: 100%;
cursor: none;
}
.carousel img {
width:100%;
}
JS: changing initLayout to account for when the carousel isn't on far left of screen
var _initLayout = function () {
left = $element.offset().left;
right = left + ($element.width() / 2);
};
JS: add resize event to re-calculate the left/right positions when the window is resized or device is rotated
var _initEvents = function () {
$element.on('mousemove', _mousemove)
.on('click', _click);
$(window).on('resize', _initLayout);
};

I want to fade the whole background on focus

I want to fade the whole background on focus the search field. I need only css, If there is a way please let me know I am stuck here for 2 days.
There are so many ways this can be done:
1) Use jQuery to add this class when the search field has focus:
.fader {
opacity: .5;
-webkit-transition: opacity .25s ease-in-out;
-moz-transition: opacity .25s ease-in-out;
transition: opacity .25s ease-in-out;
}
2) Use jQuery to apply this method when the search field has focus:
$("body").fadeOut(2500); // the higher the number the longer it takes to fade
Note for IE 8 compatibility: Use opacity: 0.5; filter: alpha(opacity=50);

LESS transition mixin with prefixes

I was wondering if it's possible to create a LESS mixin that I could use like this:
.transform(transition, .5s, ease-out);
and has this CSS as output:
-webkit-transition: -webkit-transform .5s ease-out;
-moz-transition: -moz-transform .5s ease-out;
transition: transform .5s ease-out;
but I would also be able to use the same mixin for other properties (i.e. .transition(opacity, .5s) should output to -webkit-transition:opacity .5s; -moz-transition:opacity .5s; transition:opacity .5s;
Thanks!
Leon
Since Less version 2 you can use the autoprefix postprocessor plugin and the consensus is that you should use it for best practice.
The Less autoprefix plugin can be found at: https://github.com/less/less-plugin-autoprefix.
After installing the you can run:
echo "selector {transition: transform .5s ease-out;}" | lessc - --autoprefix="last 20 versions"
The preceding command outputs:
selector {
-webkit-transition: -webkit-transform 0.5s ease-out;
-moz-transition: -moz-transform 0.5s ease-out;
-o-transition: -o-transform 0.5s ease-out;
transition: transform 0.5s ease-out;
}
You should consider Graceful degredation and run the autoprefix plugin without any browser argument. (lessc --autoprefix). Then your output will look like that shown below:
selector {
-webkit-transition: -webkit-transform 0.5s ease-out;
transition: transform 0.5s ease-out;
}
Notice that you can not use the auto prefix plugin when using less.js to compile your Less code in the browser. For client side compiling you can use the -prefix-free library.

How do I convert this nested selectors to LESS?

I am a novice in LESS CSS, but I have spent lot of time learning the CSS. Currently am migrating my CSS code to a LESS for learn and improve myself. I stumbled upon this when am doing the migration process,
Existing CSS Code
#sidebar {
-webkit-transition: background 1.2s ease, padding 1.8s linear;
background: #3c3c3c;
}
#sidebar .actionMenuList {
margin-bottom: 20%;
}
#sidebar .actionMenuList .topNavMenuList,
#sidebar .navigationMenuList .topNavMenuList {
-webkit-transition: background 0.3s ease-in-out;
border-bottom: .1em solid #FDF7F8;
}
Writing this LESS Code
#sidebar {
-webkit-transition: background 1.2s ease, padding 1.8s linear;
background: #3c3c3c;
.actionMenuList {
margin-bottom: 20%;
.topNavMenuList {
-webkit-transition: background .3s ease-in-out;
border-bottom: .1em solid #FDF7F8;
}
}
}
But am getting stuck in one place, how do I write the css prop for the navigationMenuList class selectors using the above hierarchy. Or do I need to fallback on the usual way of CSS for this
#sidebar .actionMenuList .topNavMenuList,
#sidebar .navigationMenuList .topNavMenuList {
You just do
#sidebar {
.navigationMenuList .topNavMenuList { }
}
all together
#sidebar {
.actionMenuList {
.topNavMenuList { ... }
}
.navigationMenuList {
.topNavMenuList { .... }
}
}
OR
assuming the rules are the same for both
#sidebar {
.actionMenuList,
.navigationMenuList {
.topNavMenuList {
-webkit-transition: background 0.3s ease-in-out;
border-bottom: .1em solid #FDF7F8;
}
}
}
you can even do
#sidebar {
.actionMenuList .topNavMenuList,
.navigationMenuList .topNavMenuList {
-webkit-transition: background 0.3s ease-in-out;
border-bottom: .1em solid #FDF7F8;
}
}
On a side note, if you ever get stuck at converting and need to make it work. Just leave the css in the less file and it will work like normal.
This works for me, and does what I expected.
#sidebar {
-webkit-transition: background 1.2s ease, padding 1.8s linear;
background: #3c3c3c;
.actionMenuList { margin-bottom: 20%; }
.actionMenuList .menuItem, .navigationMenuList .menuItem {
-webkit-transition: background .3s ease-in-out;
border-bottom: .1em solid #FDF7F8;
}
}

Does webkit-scrollbar work with webkit-transition?

I want a custom webkit-scrollbar to animate a different background color for the hover state. The code below changes the color on hover but doesn't animate anything. It works on a div so I suspect webkit-scrollbar doesn't play nice with transitions.
::-webkit-scrollbar-thumb {
background-color: #a8a8a8;
-webkit-transition: background-color 1s linear;
}
::-webkit-scrollbar-thumb:hover {
background-color: #f6f6f6;
}
No, it is not implemented. We should file a bug on http://bugs.webkit.org/
You can still apply your transition by setting your -webkit-scrollbar-thumb background-color to inherit and apply transition to parent element - in this case the scrollbar container itself.
The only drawback is that, you have to create an inner container that would mask it's parent color and set scrollbar track background to the same masking color. Here it is an example:
Set container colors and transition
.container {
-webkit-transition: background-color 1s linear;
background-color: #fff;
}
.container:hover {
background-color: #cfcfcf;
}
.container .inner {
background-color: #FFFFFF;
}
Set scrolbar colors
::-webkit-scrollbar-thumb {
background-color: inherit;
}
::-webkit-scrollbar-track {
background: #fff;
}
It is fairly easy to achieve using xb1itz's background-color: inherit; technique in addition with -webkit-background-clip: text;.
Live demo; https://jsfiddle.net/s10f04du/
#media screen and (-webkit-min-device-pixel-ratio:0) {
.container {
overflow-y: scroll;
overflow-x: hidden;
background-color: rgba(0,0,0,0);
-webkit-background-clip: text;
transition: background-color .8s;
}
.container:hover {
background-color: rgba(0,0,0,0.18);
}
.container::-webkit-scrollbar-thumb {
background-color: inherit;
}
}