简体   繁体   中英

Adding class via js won't trigger css animation

I have a modified version of animate.css (added some delay, new timings and new positions), and it works really great when the classes are set by default (html document). But when I am adding the animate class dynamically via js, the animation is not executed!

Even more annoying, I did have it working at some point, but I can't get it to work again (using gumby framework and inview js to add a class when the element is on screen (adding .animated)) . The left box had the classes already in the html, and the right box have the .animate class added by js.

Example:
http://onepageframework.com/28_2_14/strange_anim.html

Any ideas why the right box is not animating?

Using the Gumby inview extension: http://gumbyframework.com/docs/extensions/#!/inview

Edit: added html:

<div class="six columns text-center fadeInLeftMedium delay_2 animated">
    <!-- left box content here -->
</div>
<div class="six columns text-center fadeInLeftMedium delay_2 inview" data-classname="animated">
    <!-- right box content here -->
</div>

css:

.animated {
    -webkit-animation-duration: 1s;
       -moz-animation-duration: 1s;
         -o-animation-duration: 1s;
            animation-duration: 1s;
    -webkit-animation-fill-mode: both;
       -moz-animation-fill-mode: both;
         -o-animation-fill-mode: both;
            animation-fill-mode: both;
}

.delay_2 {
    -webkit-animation-delay: 2s;
       -moz-animation-delay: 2s;
         -o-animation-delay: 2s;
            animation-delay: 2s;    
}

@-webkit-keyframes fadeInLeftMedium {
    0% {
        opacity: 0;
        -webkit-transform: translateX(-400px);
    }

    100% {
        opacity: 1;
        -webkit-transform: translateX(0);
    }
}
@-moz-keyframes fadeInLeftMedium {
    0% {
        opacity: 0;
        -moz-transform: translateX(-400px);
    }

    100% {
        opacity: 1;
        -moz-transform: translateX(0);
    }
}
@-o-keyframes fadeInLeftMedium {
    0% {
        opacity: 0;
        -o-transform: translateX(-400px);
    }

    100% {
        opacity: 1;
        -o-transform: translateX(0);
    }
}
@keyframes fadeInLeftMedium {
    0% {
        opacity: 0;
        transform: translateX(-400px);
    }

    100% {
        opacity: 1;
        transform: translateX(0);
    }
}

.fadeInLeftMedium {
    -webkit-animation-name: fadeInLeftMedium;
    -moz-animation-name: fadeInLeftMedium;
    -o-animation-name: fadeInLeftMedium;
    animation-name: fadeInLeftMedium;
}

The reason is the same why you can't re-trigger CSS based animations by just subsequently removing and adding a class. The reason is that browsers batch-up these modifications and optimize away the animation. Reason and solutions are discussed here .

From the article, your options are (paraphrased):

  1. Add a small delay before re-adding the class (not recommended)
  2. Clone the element, remove it, and insert the clone
  3. Have 2 identical animations (attached to different css rules) and switch between them
  4. Trigger a reflow between removing and adding the class name:
        element.classList.remove("run-animation");
     // element.offsetWidth = element.offsetWidth; //doesn't work in strict mode
        void element.offsetWidth; // reading the property requires a recalc
        element.classList.add("run-animation");
  1. Change (cycle) the element's CSS animation-play-state attribute to paused or running (does not restart animation)

I think you just need to add animated as a class rather than as data-classname="animated" ...

So basically:

<div class="six columns text-center fadeInLeftMedium delay_2 inview" data-classname="animated">
    <!-- right box content here -->
</div>

Should be:

<div class="six columns text-center fadeInLeftMedium delay_2 inview animated">
    <!-- right box content here -->
</div>

Otherwise the animation lacks a specified animation duration and without the animation-duration property specified the animation won't work.

By swaping the classes, it looks like it got it to work (aminated in the class, and fadeInLeftMedium as the data-classname):

<div class="six columns text-center fadeInLeftMedium delay_2 animated">
    <!-- left box content here -->
</div>
<div class="six columns text-center animated delay_2 inview" data-classname="fadeInLeftMedium">
    <!-- right box content here -->
</div>

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM