Grouping CSS @Keyframes Rules

Grouping CSS @keyframes rules

Keep in mind that at-rules and selectors are completely different things.

At-rules are covered in this section of CSS2.1 spec, which says that an at-rule consists of exactly one at-keyword followed by some statement (be it a semicolon-terminated statement, or a block). As far as the CSS parser is concerned, what you have is a set of three separate at-rules, one prefix for each vendor and one unprefixed rule for the standard.

The more appropriate counterpart to at-rules would be rule sets, or style rules, described here. A rule set consists of a selector and a declaration block (containing style declarations). This is analogous to the contents of an at-rule as described above. It also means that the selector is just one part of a rule set.

Certain at-rules do allow comma-separated values in their preludes, such as @media:

@media screen, projection {
/* Styles for both screen and projection media */
}

But instead of grouping the at-rules in entirety, the grouping happens within the value that comes after the at-keyword in the beginning of the rule.

This @media rule can be expanded into two separate rules like so:

@media screen {
/* Styles for screen media */
}

@media projection {
/* Styles for projection media */
}

Notice that each rule has its own @media at-keyword.

Similarly, when you group multiple selectors into a single rule, what you have is one style rule. The part that is grouped is the selector; everything in the declaration block that follows applies to all the selectors that are listed in the group:

.foo, .bar {
/* Styles that apply to both .foo and .bar elements */
}

And when you expand it, it becomes two rule sets:

.foo {
/* Styles that apply to .foo elements */
}

.bar {
/* Styles that apply to .bar elements */
}

Grouping css at-rules

No, you cannot group at-rules.

That's the disadvantage of prefixed rules: you have to repeat values for every prefix as appropriate.

You could go with a preprocessor like Sass or LESS that offers mixin functionality, write a mixin that generates all the prefixed rules, and use that mixin throughout your stylesheet and it'll handle compiling the appropriate CSS at-rules for you. But you can't group prefixed at-rules using CSS without repeating the values.

!important with keyframe animations

There are really only two options:

  1. Rewrite the CSS code to avoid the use of !important
  2. Use JavaScript animations instead of CSS animations. A JavaScript solution would be able to alter any inline styles or even document-level stylesheets if necessary

Combining multiple CSS animations into one overall animation

One animation one element is how it works as the animations change the styles of a single element. You can however apply delays to the animations to achieve what you want, allowing you to move pretty much everything out of JS.

This example merges your .outside an .inside animations, by basically appending them with a comma to the rule and you JS now just adds the class like this -webkit-animation-name: button-bounce, rotate, skyblue;

jsFiddle

CSS

.outside.animate {
-webkit-animation-delay: 0s, .5s, .5s;
-webkit-animation-duration: 500ms, 1000ms, 1000ms;
-webkit-animation-name: button-bounce, rotate, skyblue;
}

.animate {
-webkit-animation-fill-mode: forwards;
-webkit-animation-timing-function: ease;
-webkit-transform: translateZ(0);
}

.outside.animate .inside {
-webkit-animation-delay: .5s, .5s, 1.5s;
-webkit-animation-duration: 1000ms, 1000ms, 750ms;
-webkit-animation-name: rotate, magenta, scale-in;
}

New animations

@-webkit-keyframes magenta {
0% { border: 1px solid magenta; }
99.99% { border: 1px solid magenta; }
100% { border: 1px solid skyblue; }
}
@-webkit-keyframes skyblue {
0% { border: 1px solid skyblue; }
99.99% { border: 1px solid skyblue; }
100% { border: 1px solid magenta; }
}

JavaScript

$(document).ready(function() {
$(document).click(function() {
var count = 0;
var jqElement = $('.outside');
if (!jqElement.hasClass('animate')) {
jqElement.addClass('animate');
jqElement.on('animationend webkitAnimationEnd oAnimationEnd MSAnimationEnd', function(event) {
count++;
if (count >= 6) {
jqElement.off('animationend webkitAnimationEnd oAnimationEnd MSAnimationEnd');
jqElement.removeClass('animate');
}
});
}
});
});

Is there a way to group browser-specific css3 animations?

No, it's not possible with CSS. You can't group different at-rules together, much like how you can't group vendor-prefixed selectors.

You could resort to using a Sass/LESS mixin, but that's assuming you're working with a preprocessor already, and that just outputs separate duplicate CSS rules anyway.

For what it's worth, there are several prefixes that can be removed to reduce some of the bloat in your CSS:

  • @-ms-keyframes and -ms-animation are not used by any stable version of IE; IE10 supports them unprefixed right out of the box

  • Firefox also supports unprefixed @keyframes/animation, starting from version 16

  • -ms-box-shadow and -o-box-shadow have never existed, so they should be removed/unprefixed

  • -moz-box-shadow is only required by Firefox 3.5 and 3.6, neither of which support CSS animations (not even via @-moz-keyframes — that was added in version 5), so it should be unprefixed

You should also place the prefixless item last instead of first, to ensure (by the cascade) that it takes precedence over the prefixed item in browsers that support it.

Activate CSS3 keyframe animation when the content scrolls into view

Change your checkAnimation() to

// Check if it's time to start the animation.
function checkAnimation() {
var $elem = $('.row .wpb_content_element');

$elem.each(function(){
var $singleElement = $(this);
// If the animation has already been started
if ($singleElement.hasClass('start')) return;

if (isElementInViewport($singleElement)) {
// Start the animation
$singleElement.addClass('start');
}
});
}


Related Topics



Leave a reply



Submit