Animation return to initial state after animationend - javascript

I encountered a problem when animating slide-in and slide-out.
The number "0" has to move and fade to left and the number "7" has to arrive from right when clicking on "Click" and the inverse when clicking back, indefinitely.
I have used 4 classes : "move-in", "move-out", "move-in-rev" and "move-in-rev" containing the animation with "animationend" that removes it to repeat the animation over and over.
Unfortunally, my skills stop here because the removing of the class removes also the property "animation-fill-mode : towards" which leads to the initial state (opacity = 1 on "0" and not on the "7") and I don't see how to handle it.
Could someone help me please ?
page = 0;
num1 = document.getElementById("num2-1");
num2 = document.getElementById("num2-2");
document
.querySelector("a")
.addEventListener("click", function(event) {
//Go from 0 to 7
if (page == 0) {
//0 go to left and fade
num1.classList.add("move-out");
num1.addEventListener('animationend', function() {
num1.classList.remove("move-out");
});
//7 arrives from right
num2.classList.add("move-in");
num2.addEventListener('animationend', function() {
num2.classList.remove("move-in");
});
page = (++page);
}
//Go from 7 to 0
else {
//0 arrives from left
num1.classList.add("move-out-rev");
num1.addEventListener('animationend', function() {
num1.classList.remove("move-out-rev");
});
//0 go to right and fade
num2.classList.add("move-in-rev");
num2.addEventListener('animationend', function() {
num2.classList.remove("move-in-rev");
});
page = (--page);
};
});
#keyframes slide-in {
from {
transform: translateX(0%);
opacity: 0;
}
to {
transform: translateX(-100%);
opacity: 1;
}
}
#keyframes slide-out {
from {
transform: translateX(0%);
opacity: 1;
}
to {
transform: translateX(-100%);
opacity: 0;
}
}
body,html {
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
width: 100%;
height: 100%;
}
#nums {
display: flex;
flex-direction: row;
}
#num2-1 {
opacity: 1;
}
#num2-2 {
opacity: 0;
}
a {
text-decoration: none;
cursor: pointer;
user-select: none;
}
a:hover {
color: red;
}
.move-in {
animation : slide-in 0.5s;
animation-fill-mode: forwards;
}
.move-in-rev {
animation : slide-in 0.5s reverse;
animation-fill-mode: forwards;
}
.move-out {
animation : slide-out 0.5s;
animation-fill-mode: forwards;
}
.move-out-rev {
animation : slide-out 0.5s reverse;
animation-fill-mode: forwards;
}
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<link rel="stylesheet" href="style.css" />
<title>transition</title>
</head>
<body>
<div id="nums">
<div id="num1">8</div>
<div id="num2-1">0</div>
<div id="num2-2">7</div>
</div>
<div id="button">
<a id="test">
Click
</a>
</div>
<script src="index.js"></script>
</body>
</html>

Related

How can I make successive movements with the same div?

hello I have the following problem, I want to make a series of random movements with the divs and using translate I managed to do only one because when I want to move that element again it returns to its initial position, my question is how can I maintain the position to be able to continue moving it and exchanging positions with other divs?
CSS:
body{
padding: 5rem ;
}
.elem{
width: 100px;
height: 100px;
}
#elem-1{
background-color: aqua;
}
#elem-2{
background-color: red;
}
#elem-3{
background-color: green;
}
#elem-4{
background-color: blue;
}
#elem-5{
background-color: violet;
}
#elem-6{
background-color: yellowgreen;
}
#elem-7{
background-color: gray;
}
#elem-0{
background-color: fuchsia;
}
.contenedor{
width: 400px;
height: 200px;
/* display: grid;
grid-template-columns: repeat(4,1fr); */
display: flex;
align-items: center;
justify-content: center;
flex-direction: row;
flex-wrap: wrap;
}
.move-right{
animation-duration: 4s;
animation-name: moving-x-right;
animation-fill-mode: forwards;
}
.move-left{
animation-duration: 4s;
animation-name: moving-x-left;
animation-fill-mode: forwards;
}
.move-down{
animation-duration: 2s;
animation-name: moving-y-down;
animation-fill-mode: forwards;
}
.move-up{
animation-duration: 2s;
animation-name: moving-y-up;
animation-fill-mode: forwards;
}
#keyframes moving-x-right {
from {
}
to {
transform: translateX(100px);
}
}
#keyframes moving-x-left {
from {
}
to {
transform: translateX(-100px);
}
}
#keyframes moving-y-up {
from {
}
to {
transform: translateY(-100px);
}
}
#keyframes moving-y-down {
from {
}
to {
transform: translateY(100px);
}
}
HTML:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
<link rel="stylesheet" href="styles.css">
</head>
<body>
<div class="contenedor">
<div class="elem" id="elem-0">1</div>
<div class="elem" id="elem-1">2</div>
<div class="elem" id="elem-2">3</div>
<div class="elem" id="elem-3">4</div>
<div class="elem" id="elem-4">5</div>
<div class="elem" id="elem-5">6</div>
<div class="elem" id="elem-6">7</div>
<div class="elem" id="elem-7">8</div>
</div>
<script src="/scripts.js"></script>
</body>
</html>
and JS:
window.onload = moveGridElement
function moveGridElement() {
const elem1 = document.querySelector("#elem-0")
const elem2 = document.querySelector("#elem-1")
const elem3 = document.querySelector("#elem-2")
const elem4 = document.querySelector("#elem-3")
const elem5 = document.querySelector("#elem-4")
const elem6 = document.querySelector("#elem-5")
const elem7 = document.querySelector("#elem-6")
const elem8 = document.querySelector("#elem-7")
elem1.classList.add("move-right")
elem2.classList.add("move-left")
setTimeout(() => {
elem4.classList.add("move-down")
elem8.classList.add("move-up")
}, 1000);
setTimeout(() => {
elem1.classList.add("move-down")
elem6.classList.add("move-up")
}, 3000);
I need that when a div changes places it maintains that position to continue making movements and changing positions with other divs with HTML, CSS and JS only

slowly scrolling bug, div stay on page but shouldn't

I have three div boxes in a row, and on scroll, they should show slowly from the side, but when I scroll up slowly and a little after they show up, the left and right boxes for some reason stay on the page.
My function showBox3 writes in console "false" and classList where is "show" class, but this class shouldn't be there.
Actually, my code works when I scroll normally but when I stop scrolling slightly above the limit, the left and right boxes stay on page.
And one more problem is when "topBox" is a little below the limit, and I scroll up just a little more, but still below the limit, boxes quickly remove from the page and show up again.
const box21 = document.querySelector(".box21");
const box22 = document.querySelector(".box22");
const box23 = document.querySelector(".box23");
var trigger = window.innerHeight * 0.8;
window.addEventListener("scroll", showBox2);
function showBox2() {
var check;
const topBox = box22.getBoundingClientRect().top;
if (trigger > topBox) {
box22.classList.add("show");
check = true;
} else {
box22.classList.remove("show");
check = false;
}
showBox1(check);
showBox3(check);
}
function showBox1(ch) {
if (ch == true) {
setTimeout(() => {
box21.classList.add("show");
}, 400);
} else {
box21.classList.remove("show");
}
}
function showBox3(ch) {
if (ch == true) {
setTimeout(function () {
box23.classList.add("show");
}, 700);
} else {
box23.classList.remove("show");
console.log(box23.classList);
console.log(ch);
}
}
* {
box-sizing: border-box;
margin: 0;
padding: 0;
}
.box1 {
height: 110vh;
background-color: aqua;
display: flex;
align-items: center;
justify-content: center;
}
/* I have a bug in box 2 */
.box2 {
height: 60vh;
width: 100%;
background-color: #ddd;
display: flex;
align-items: center;
justify-content: space-around;
}
.box2>div {
height: 70%;
width: 27%;
background-color: black;
}
.box21 {
transform: translateX(-140%) rotate(-45deg);
transition: transform 1.4s ease;
}
.box21.show {
transform: translateX(0%) rotate(0deg);
}
.box22 {
transform: translateX(340%) rotate(+45deg);
transition: transform 0.8s ease;
}
.box22.show {
transform: translateX(0%) rotate(0deg);
}
.box23 {
transform: translateX(340%) rotate(-45deg);
transition: transform 1.8s ease;
}
.box23.show {
transform: translateX(0%) rotate(0deg);
}
/* this part below is not important */
.box3 {
height: 60vh;
width: 100%;
background-color: cornflowerblue;
}
<!DOCTYPE html>
<html>
<head>
<link rel="stylesheet" href="css.css" />
</head>
<body>
<div class="box1">
<h1>Scroll down</h1>
</div>
<div class="box2">
<div class="box21"></div>
<div class="box22"></div>
<div class="box23"></div>
</div>
<div class="box3"></div>
</body>
<script src="js.js"></script>
</html>

I want to pause/play CSS animation using one button with Javascript. The sun and sky colors should be controlled with the button

HTML CODE:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset = "utf-8">
<title>Keyframe Animations</title>
<link rel="stylesheet" href="SunLabcss.css" type="text/css"/>
<script src="scriptSun.js"></script>
</head>
<body>
<button id = "sunButton" onclick="sunPausePlayToggle()">PLAY/PAUSE</button
sunPausePlayToggle() is a function in JS which will control the animation .
<div id = "sunSky"
this is a div which i am using as a background sky
<div id = "sun"></div
the upper div is a sun which rise from right and dawn in the left
</div>
</body>
</html>
CSS code:
I am using keyframe animations to animate the sun and sky.
#keyframes risesky {
0% {
top: 100%;
left : 100%;
background-color: red;
}
50% {
left:50%;
top: 10%;
background-color: yellow;
}
100% {
background-color: orangered;
top: 100%;
left: 0%;
}
}
#keyframes sky {
0% , 100% {
background-color: #1c1341;
}
10% {
background-color: darkorange;
}
50% {
background-color: skyblue;
}
80% {
background-color: crimson;
}
}
#sunButton{
animation-play-state: running;
}
#sun {
position: relative;
border-radius: 50%;
width: 80px;
height: 80px;
animation: risesky 11s infinite;
}
#sunSky {
height: 500px;
overflow: hidden;
animation: sky 11s infinite both;
}
Javascript code:
here is the problem I am getting, I can only pause the animation in JS ,but can't play.
function sunPausePlayToggle(){
document.getElementById("sunSky").style.animationPlayState = "paused";
document.getElementById("sun").style.animationPlayState = "running";
}
Turn #sunButton = animation-play-state: "paused"; in css
And this is the js
function sunPausePlayToggle(){
let sunsky = document.getElementById("sunSky")
let sun = document.getElementById("sun")
const sky_sty = sunsky.style.animationPlayState === 'running';
const sun_sty = sun.style.animationPlayState === 'running';
sunsky.style.animationPlayState = sky_sty ? 'paused' : 'running';
sun.style.animationPlayState = sun_sty ? 'paused' : 'running';
}

CSS Animation Won't Play Per Click

I built a carousel for some images. I need my 'next' and 'previous' buttons to use the CSS animation that I assigned them in my javascript function for their event listeners.The animation will only play for one click, and when the buttons are clicked again to navigate the carousel the animation doesn't play. I need the buttons to grow and shrink for every click.
Here's the CSS:
.carousel-actions {
position: absolute;
display: flex;
justify-content: space-between;
width: 105%;
top: 30%;
}
.carousel-actions button {
padding: 30px 50px;
background-color: rgba(255, 255, 255, 0.329);
font-weight: 900;
cursor: pointer;
border-radius: 100px;
border: 0;
font-size: 60px;
color: black;
outline: none;
}
#keyframes grow {
0% {
transform: scale(1);
}
50% {
transform: scale(1.3);
}
100% {
transform: scale(1);
}
}
Here's the HTML:
<div class="carousel-actions">
<button id="prev" aria-label="Previous Slide"><</button>
<button id="next" aria-label="Next Slide">></button>
</div>
Here's the JS:
const slides = document.querySelectorAll(".carousel-item");
const totalSlides = slides.length;
let slidePosition = 0;
console.log(totalSlides);
const next = document.getElementById("next");
const prev = document.getElementById("prev");
function hideAllSlides() {
for (const slide of slides) {
slide.classList.remove("carousel-item-visible") &&
slide.classList.add("carousel-item-hidden");
}
}
function nextSlide() {
hideAllSlides();
if (slidePosition === totalSlides - 1) {
slidePosition = 0;
} else {
slidePosition++;
}
slides[slidePosition].classList.add("carousel-item-visible");
next.style.animation = "grow 1s";
}
function prevSlide() {
hideAllSlides();
if (slidePosition === 0) {
slidePosition = totalSlides - 1;
} else {
slidePosition--;
}
slides[slidePosition].classList.add("carousel-item-visible");
prev.style.animation = "grow 1s";
}
next.addEventListener("click", nextSlide);
prev.addEventListener("click", prevSlide);
The problem is seen because once the system has played the animation it thinks 'well, I've played it'. Setting it to the same again does not make it play again.
To get round this you can unset the animation when it has finished.
In your code add an event listener for the animationend event.
Here's a simplified example:
const div = document.querySelector('div');
div.addEventListener('click', function() { div.style.animationName='grow';});
div.addEventListener('animationend', function() { div.style.animationName='';});
div {
width: 100px;
height: 100px;
background-color: blue;
animation-duration: 1s;
animation-iteration-count: 1;
}
#keyframes grow {
0% {
transform: scale(1);
}
50% {
transform: scale(1.3);
}
100% {
transform: scale(1);
}
<div></div>

pull variable from css with js

I'm trying to get an action to occur when one clicks on an image, however only when the image is at full opacity
function func() {
if ($('.Absolute-Center').css('opacity') == 1) {
alert("it works");
}
}
.Absolute-Center {
margin: auto;
position: absolute;
top: 0;
left: 0;
bottom: 0;
right: 0;
}
img.Absolute-Center {
opacity: 0.05;
filter: alpha(opacity=5);
-webkit-transition: opacity 20s linear;
}
img.Absolute-Center:hover {
opacity: 1;
filter: alpha(opacity=100);
-webkit-transition: opacity 20s linear;
}
<img src="picture.png" class="Absolute-Center" onclick="func()" />
Try using transitionend event , .addClass() , .removeClass() ; removing :hover from css
function func(e) {
if ($(this).css("opacity") == 1) {
alert("it works");
$(this).removeClass("clicked")
}
};
$(".Absolute-Center").on({
"click": function() {
$(this).addClass("clicked")
},
"transitionend": func
})
.Absolute-Center {
margin: auto;
position: absolute;
top: 0;
left: 0;
bottom: 0;
right: 0;
}
img.Absolute-Center {
opacity: 0.05;
filter: alpha(opacity=5);
transition: opacity 20s linear;
}
img.Absolute-Center.clicked {
opacity: 1;
filter: alpha(opacity=100);
transition: opacity 20s linear;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js">
</script>
<img src="http://lorempixel.com/50/50" class="Absolute-Center" />
This should help improve understanding and should be easily adaptable to do exactly what you want.
$(function() {
$('img').on('click', function() {
var alpha = $(this).css('opacity');
$("#msg").text((alpha == 1) ? "full" : alpha);
}).on('transitionend', function() {
var alpha = $(this).css('opacity');
if (alpha == 1) {
$("#msg2").fadeIn().delay(700).fadeOut();
} else {
$("#msg3").fadeIn().delay(700).fadeOut();
}
});
});
img {
border: 1px solid #000;
}
img {
opacity: 0.05;
filter: alpha(opacity=5);
-webkit-transition: opacity 5s linear;
}
img:hover {
opacity: 1;
filter: alpha(opacity=100);
-webkit-transition: opacity 5s linear;
}
#msg2, #msg3 {
display: none;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<img src="picture.png" />
<div>Last clicked at opacity: <span id="msg"></span>
</div>
<div id="msg2">End of fade-IN transition</div>
<div id="msg3">End of fade-OUT transition</div>

Categories

Resources