So the element That I am manipulating has an id of spinning and a class of rotors
I can get my element to spin. I did this by using the css code here:
.rotors {
position: relative;
top: 90px;
left: 30px;
-webkit-animation:spin .5s linear infinite;
-moz-animation:spin .5s linear infinite;
animation:spin .5s linear infinite;
} #-moz-keyframes spin { 100% { -moz-transform:rotate(360deg);}}
#-webkit-keyframes spin { 100% { -webkit-transform:rotate(360deg);}}`
#keyframes spin { 100% { -webkit-transform:rotate(360deg);}}
But Say instead of it spinning automatically on the page load that I could press a button with an id of one and it would start to spin, and if I press a second button with an id of two, it would spin even faster then the first.
I am not sure how to achieve this. I did see where some people pointed out that you can change the css of an element using javascript but am unsure on how to achieve this especially on a button click. I want it to be something like getElementById(spinning).style.property = but on button click and just changing the speed of the rotation of my element.
One option would be to change the animation-duration CSS property dynamically with JavaScript.
var rotors = document.querySelector(".rotors");
function fast() {
rotors.style.animationDuration = ".2s";
}
function slow() {
rotors.style.animationDuration = ".5s";
}
.rotors {
height: 50px; /* for demo purpose */
width: 50px; /* for demo purpose */
animation: spin .5s linear infinite;
}
#keyframes spin {
100% { transform: rotate(360deg); }
}
<p>
<button onclick="fast()">Fast</button>
<button onclick="slow()">Slow</button>
</p>
<img class="rotors" src="https://cdn.onlinewebfonts.com/svg/img_489361.png" />
Add 2 buttons and use it to change the classes like below:
function startSpinning(){
var spDiv = document.getElementById('test');
if(spDiv.classList.contains('rotorsFast')){
spDiv.classList.remove('rotorsFast');
spDiv.classList.add('rotors');
}else{
spDiv.classList.add('rotors');
}
}
function startSpinningFast(){
var spDiv = document.getElementById('test');
if(spDiv.classList.contains('rotors')){
spDiv.classList.remove('rotors');
spDiv.classList.add('rotorsFast');
}else{
spDiv.classList.add('rotorsFast');
}
}
.rotors {
position: relative;
top: 90px;
left: 30px;
-webkit-animation: spin .5s linear infinite;
-moz-animation: spin .5s linear infinite;
animation: spin .5s linear infinite;
}
.rotorsFast {
position: relative;
top: 90px;
left: 30px;
-webkit-animation: spin .2s linear infinite;
-moz-animation: spin .2s linear infinite;
animation: spin .2s linear infinite;
}
#-moz-keyframes spin {
100% {
-moz-transform: rotate(360deg);
}
}
#-webkit-keyframes spin {
100% {
-webkit-transform: rotate(360deg);
}
}
` #keyframes spin {
100% {
-webkit-transform: rotate(360deg);
}
}
<div id="test" style="width:20px">apple</div>
<button onclick="startSpinning()">spin</button>
<button onclick="startSpinningFast()">spin Fast</button>
This is a nice spot to use a CSS custom variable. When the button is clicked, we toggle a secondary class on the .rotors div. When the faster class is present, the custom variable resets the animation speed to the faster speed, which is automatically applied to the animation.
const rotors = document.querySelector('.rotors');
const btn = document.querySelector('.rotorButton');
btn.addEventListener('click', () => {
rotors.classList.toggle('faster')
});
.rotors {
--spin-speed: 2s; /* Initial speed */
position: relative;
top: 40px;
left: 30px;
background-color: yellow;
color: black;
display: inline-block;
animation: spin var(--spin-speed) linear infinite;
}
.rotors.faster {
--spin-speed: .5s; /* Faster speed 🔥 */
}
#keyframes spin {
100% {
transform: rotate(360deg);
}
}
<div class="rotors">text</div>
<button class="rotorButton" type="button">Toggle Rotor Speed</button>
jsFiddle
Related
I am having a little trouble in using javascript to access a css animation. My goal in this code is if you click the next button or previous button the border should spin but I am having trouble to trigger the css animation.
This is my html
<template>
<div v-on:click="prev" class="prevButton"><p><</p></div>
<div class="borderTop"></div>
<div v-on:click="next" class="nextButton"><p>></p></div>
</template>
This is the css
.border{
position: fixed;
height: 500px;
width: 500px;
top: 0;
left: 0;
right: 0;
bottom: 0;
margin: auto;
border-radius: 50%;
border: 120px solid rgba(0, 0, 0, 0.555);
transform: rotate(45deg);
-webkit-animation: spin 2s linear; /* Safari */
animation: spin 2s linear;
}
#keyframes spin {
0% { transform: rotate(0deg);
border-right: 120px solid rgba(255, 255, 255, 0.226);}
100% { transform: rotate(360deg); }
}
this is the javascript
prev(){
document.querySelector(".borderTop").animate;
}
next(){
document.querySelector(".borderTop").animate;
}
You can't trigger the animation from Javascript. Instead you should add your animation style to an additional class which you can add to the div for the duration of the animation.
.animate {
animation: spin 2s linear;
}
Add anther class with animation-direction: reverse; if you would like to reverse the animation for the prev button.
prev() {
document.querySelector('.borderTop').classList.add('animate');
// Remove the animate class after the spin was performed so it works again when the button is clicked.
setTimeout(function() {
document.querySelector('.borderTop').classList.remove('animate');
}, 2000)
});
}
next() {
document.querySelector('.borderTop').classList.add('animate');
setTimeout(function() {
document.querySelector('.borderTop').classList.remove('animate');
}, 2000)
});
}
let borderAnimatable = document.querySelector(".borderTop")
prev(){
borderAnimatable.style.animation = "spin 2s linear";
borderAnimatable.style.WebkitAnimation = "spin 2s linear";
}
next(){
borderAnimatable.style.animation = "spin 2s linear";
borderAnimatable.style.WebkitAnimation = "spin 2s linear";
}
According to the Mozilla Web Animations API docs, "The getAnimations() method of the Document interface returns an array of all Animation objects currently in effect whose target elements are descendants of the document. This array includes CSS Animations, CSS Transitions, and Web Animations."
Is there any way to use this to only add the Web animation objects to the array, excluding the CSS Animations and CSS transitions?
The following code returns all the animations on the document:
var allAnimations;
if (typeof document.getAnimations === 'function') {
allAnimations = document.getAnimations();
} else {
allAnimations = document.timeline.getAnimations();
}
allAnimations array result is this:
Array(72) [ CSSTransition, CSSTransition, CSSTransition, CSSTransition, CSSTransition, CSSTransition, Animation, Animation, Animation, Animation, … ]
I would like it to only consist of the web animations, so like this:
Array(66) [ Animation, Animation, Animation, Animation, Animation, Animation, Animation, Animation, Animation, Animation, … ]
You can check the type of animation you're looking at using instanceof, and use that to filter the list:
const animations = [
...document.getAnimations(),
new Animation(),
];
const isCSSAnimation = x => x instanceof CSSAnimation;
const onlyAnimations = animations.filter(x => x.constructor.name === 'Animation');
console.dir(animations);
console.dir(onlyAnimations);
.animated {
-webkit-animation-duration: .5s;
animation-duration: .5s;
-webkit-animation-fill-mode: both;
animation-fill-mode: both;
-webkit-animation-timing-function: linear;
animation-timing-function: linear;
animation-iteration-count: infinite;
-webkit-animation-iteration-count: infinite;
}
#-webkit-keyframes bounce {
0%, 100% {
-webkit-transform: translateY(0);
}
50% {
-webkit-transform: translateY(-5px);
}
}
#keyframes bounce {
0%, 100% {
transform: translateY(0);
}
50% {
transform: translateY(-5px);
}
}
.bounce {
-webkit-animation-name: bounce;
animation-name: bounce;
}
#animated-example {
width: 20px;
height: 20px;
background-color: red;
position: relative;
top: 100px;
left: 100px;
border-radius: 50%;
}
hr {
position: relative;
top: 92px;
left: -300px;
width: 200px;
}
<div id="animated-example" class="animated bounce"></div>
I need to chain two animations in my interface HTML/CSS on user event (here just a click on the document). The first animation start correctly, but when I want to restart the second animation nothing move ?
I know if i remove the .rotaiotn class and with a timeout put other animation class for the element, the second animation start from the first position of the element.
I want to know if exist a solution to start the second animation from the position of the blue ball after the first animation ?
document.addEventListener('click', startAnimation, false);
var isFisrtAnim = false;
function startAnimation(evt) {
var elt = document.querySelector('#blue_ball');
if (!isFisrtAnim) {
elt.setAttribute('class', 'rotation');
} else {
elt.setAttribute('class', 'rotation2');
}
elt.addEventListener("animationend", animationAtEnd, false);
}
function animationAtEnd(evt) {
evt.preventDefault();
isFisrtAnim = !isFisrtAnim;
var elt = evt.target;
// todo here get new position of elt to start another animation
// from the new position after first animation
var new_margin_top = window.getComputedStyle(elt).getPropertyValue('margin-top');
var new_margin_left = window.getComputedStyle(elt).getPropertyValue('margin-left');
console.log('At end new margin-top : ' + new_margin_top + ' - new margin-left : ' + new_margin_left);
// positions are the same of start element ? they are not modify ?
}
#circleNav {
background: rgba(215, 229, 231, 0.4) !important;
margin-top: 100px;
margin-left: 120px;
border-radius: 50%;
width: 335px;
height: 335px;
border: 2px solid #0e6694;
}
img {
max-width: 100%;
}
#blue_ball {
position: absolute;
margin-top: -350px;
margin-left: 165px;
width: 70px;
height: 70px;
border: none;
z-index: 5;
transform-origin: 120px 180px;
}
.rotation {
-webkit-animation: rotation 3s linear;
animation-fill-mode: forwards;
-webkit-animation-fill-mode: forwards !important;
}
#-webkit-keyframes rotation {
from {
-webkit-transform: rotate(0deg);
}
to {
-webkit-transform: rotate(240deg);
}
}
.rotation2 {
-webkit-animation: rotation 3s linear;
animation-fill-mode: forwards;
-webkit-animation-fill-mode: forwards !important;
}
#-webkit-keyframes rotation2 {
from {
-webkit-transform: rotate(240deg);
}
to {
-webkit-transform: rotate(360deg);
}
}
<h2>
CLICK ON THE BODY TO START ANIMATION
</h2>
<h4>
When the Blue ball stop click an other time to start second animation, but don't work ?
</h4>
<div id="circleNav"></div>
<div id="blue_ball">
<a href="#">
<img id="btn_menu" src="http://mascaron.net/img/mini_rond_logo.png">
</a>
</div>
smaple code on jsfiddle
thanks in advance.
Just one question, in css:
.rotation2 {
-webkit-animation: rotation 3s linear;
animation-fill-mode: forwards;
-webkit-animation-fill-mode: forwards !important;
}
should not be:
.rotation2 {
-webkit-animation: rotation2 3s linear; /* <----- here, rotation2
animation-fill-mode: forwards;
-webkit-animation-fill-mode: forwards !important;
}
In js part, why not use elem.classList https://developer.mozilla.org/fr/docs/Web/API/Element/classList to manipulate css class property.
I am trying to make the color of a button pulse from its current color, say, #ed8c55, to pure white and back to the original color with the entire cycle taking about 2-3 seconds. How could I do that?
In particular, I see that there are a couple of problems here. One is to make the timer and attach some variable's increment to the value of the color. The second problem is the actual color itself. How would one go about continuously changing a hex color towards white and back using a loop of some sort?
I have the following timer implemented that counts seconds. I could easily modify it to count milliseconds or something like that.
var mytimeout = null; // the current timeoutID
$scope.counter = 0;
// actual timer method, counts up every second
$scope.onTimeout = function() {
$scope.counter++;
mytimeout = $timeout($scope.onTimeout, 1000);
};
Any help is appreciated.
I know you want an animation via AngularJS but I dont think thats the right tool for the job as its easily achieved via CSS alone. I'd really advise you to do it like so;
EDIT ------------------
After your comments of dynamically adding a background colour that will then pulse the best way is to inline style the colour via angular and css keyframe the animation.
CSS --
#-webkit-keyframes pulse {
25% { background-color: #FFF; }
}
#-moz-keyframes pulse {
25% { background-color: #FFF; }
}
#-o-keyframes pulse {
25% { background-color: #FFF; }
}
#keyframes pulse {
25% { background-color: #FFF; } // changed to 25% to stop the sudden change to white
}
.element {
transition: background-color 3s;
width: 50px;
height: 50px;
-webkit-animation: pulse 3s infinite; /* Safari 4+ */
-moz-animation: pulse 3s infinite; /* Fx 5+ */
-o-animation: pulse 3s infinite; /* Opera 12+ */
animation: pulse 3s infinite; /* IE 10+, Fx 29+ */
}
HTML -
<div style="background-color: #ed8c55;" class="element"></div>
View my codepen here
/ EDIT ------------------
OG Answer ---
#-webkit-keyframes pulse {
0% { background-color: #ed8c55; }
50% { background-color: #FFF; }
100% { background-color: #ed8c55; }
}
#-moz-keyframes pulse {
0% { background-color: #ed8c55; }
50% { background-color: #FFF; }
100% { background-color: #ed8c55; }
}
#-o-keyframes pulse {
0% { background-color: #ed8c55; }
50% { background-color: #FFF; }
100% { background-color: #ed8c55; }
}
#keyframes pulse {
0% { background-color: #ed8c55; }
50% { background-color: #FFF; }
100% { background-color: #ed8c55; }
}
.element {
width: 50px;
height: 50px;
background: #ed8c55;
-webkit-animation: pulse 3s infinite; /* Safari 4+ */
-moz-animation: pulse 3s infinite; /* Fx 5+ */
-o-animation: pulse 3s infinite; /* Opera 12+ */
animation: pulse 3s infinite; /* IE 10+, Fx 29+ */
}
And that will continuously loop between the two colours.
You can view my code pen on it here.
I am using WOW.js and animate.css, right now I am running my CSS to Infinite. I would like know how can I make my class run for 3 seconds stop and start again to infinite?
My html:
<img src="images/fork.png" class="fork wow rubberBand" >
My CSS class:
.fork {
position: absolute;
top: 38%;
left: 81%;
max-width: 110px;
-webkit-animation-iteration-count: infinite ;
-webkit-animation-delay: 5s;
}
The solution can be in JS or CSS3.
With pure CSS3 animations, one way to add a delay between every single iteration of the animation would be to modify the keyframes setting such that they produce the required delay.
In the below snippet, the following is what is being done:
The whole duration of the animation is 6 seconds. In order to have the delay, the whole duration should be the duration for which your animation actually runs + time delay. Here, the animation actually runs for 3s, we need a 3s delay and so the duration is set as 6 seconds.
For the first 50% of the animation (that is, 3 seconds), nothing happens and the element basically holds its position. This gives the appearance of the 3 second delay being applied
For the next 25% of the animation (that is, 1.5 seconds) the element moves down by 50px using transform: translateY(50px).
For the final 25% of the animation (that is, last 1.5 seconds) the element moves up by 50px using transform: translate(0px) (back to its original position).
The whole animation is repeated infinite number of times and each iteration will end up having a 3 second delay.
div{
height: 100px;
width: 100px;
border: 1px solid;
animation: move 6s infinite forwards;
}
#keyframes move{
0% { transform: translateY(0px);}
50% { transform: translateY(0px);}
75% { transform: translateY(50px);}
100% { transform: translateY(0px);}
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/prefixfree/1.0.7/prefixfree.min.js"></script>
<div>Some content</div>
The animation-delay property introduces a delay only for the first iteration and hence it cannot be used to add delays between every iteration. Below is a sample snippet illustrating this.
div{
height: 100px;
width: 100px;
border: 1px solid;
animation: move 6s infinite forwards;
animation-delay: 3s;
}
#keyframes move{
0% { transform: translateY(0px);}
50% { transform: translateY(50px);}
100% { transform: translateY(0px);}
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/prefixfree/1.0.7/prefixfree.min.js"></script>
<div>Some content</div>
LIke this
html
<div class="halo halo-robford-animate"></div>
css
body{
background: black;
}
.halo{
width: 263px;
height: 77px;
background: url('http://i.imgur.com/3M05lmj.png');
}
.halo-robford-animate{
animation: leaves 0.3s ease-in-out 3s infinite alternate;
-webkit-animation: leaves 0.3s ease-in-out 3s infinite alternate;
-moz-animation: leaves 0.3s ease-in-out 3s infinite alternate;
-o-animation: leaves 0.3s ease-in-out 3s infinite alternate;
}
#-webkit-keyframes leaves {
0% {
opacity: 1;
}
50% {
opacity: 0.5;
}
100% {
opacity: 1;
}
}
#-moz-keyframes leaves {
0% {
opacity: 1;
}
50% {
opacity: 0.5;
}
100% {
opacity: 1;
}
}
#-o-keyframes leaves {
0% {
opacity: 1;
}
50% {
opacity: 0.5;
}
100% {
opacity: 1;
}
}
#keyframes leaves {
0% {
opacity: 1;
}
50% {
opacity: 0.5
}
100% {
opacity: 1;
}
}
jsfiddle