Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to reverse a CSS animation on unchecked state?

My project will display a sunny field and a check box that says "make it rain". Upon clicking the button the sun sets, and clouds come in, and there will be animated CSS rain. I'm using a checked pseudo class to start the rain animation and the rotation of the sun.

How can I reverse the animation for the unchecked state?

The order the page should work in is as follows:

  1. Page loads, default unchecked state of button, sun should be up
  2. User clicks button, pseudo class:checked gets activated and the animation starts
  3. User clicks button again, thus unchecking the button and the animation should reverse to it's original state.

Right now, it just resets the whole page when the button gets unchecked. Is there a way to reverse the animation to it's original state without using any JavaScript? This project is CSS only.

.sky {
  height: 70%;
  width: 100%;
  position: absolute;
  z-index: 1;
  background: #e4f5fc;
  /* Old browsers */
  background: -moz-linear-gradient(top, #e4f5fc 0%, #bfe8f9 33%, #9fd8ef 86%);
  /* FF3.6+ */
  background: -webkit-gradient(linear, left top, left bottom, color-stop(0%, #e4f5fc), color-stop(33%, #bfe8f9), color-stop(86%, #9fd8ef));
  /* Chrome,Safari4+ */
  background: -webkit-linear-gradient(top, #e4f5fc 0%, #bfe8f9 33%, #9fd8ef 86%);
  /* Chrome10+,Safari5.1+ */
  background: -o-linear-gradient(top, #e4f5fc 0%, #bfe8f9 33%, #9fd8ef 86%);
  /* Opera 11.10+ */
  background: -ms-linear-gradient(top, #e4f5fc 0%, #bfe8f9 33%, #9fd8ef 86%);
  /* IE10+ */
  background: linear-gradient(to bottom, #e4f5fc 0%, #bfe8f9 33%, #9fd8ef 86%);
  /* W3C */
  filter: progid:DXImageTransform.Microsoft.gradient( startColorstr='#e4f5fc', endColorstr='#9fd8ef', GradientType=0);
  /* IE6-9 */
}

.rainsun {
  position: absolute;
  margin: 35px 45%;
  width: 15.74803%;
  /*--300px--*/
  color: white;
  text-align: center;
  text-shadow: 0 1px 0 rgba(0, 0, 0, .5);
  font-size: 2.5em;
  cursor: pointer;
  z-index: 5;
}

.rainsun:after {
  position: absolute;
  display: block;
  padding: 10px 0;
  width: 100%;
  /*--300px--*/
  border: 1px solid #76011b;
  border-radius: 8px;
  background: linear-gradient(to bottom, rgba(169, 3, 41, 1) 0%, rgba(143, 2, 34, 1) 44%, rgba(109, 0, 25, 1) 100%);
  box-shadow: 0px 0px 10px rgba(19, 93, 158, .6);
  content: "Make it Rain";
  z-index: 5;
}

.rainsun:checked:after {
  background: linear-gradient(to bottom, rgba(109, 0, 25, 1) 0%, rgba(143, 2, 34, 1) 61%, rgba(169, 3, 41, 1) 100%);
  content: "Make it Shine";
}

.sun_path {
  border: 1px dashed black;
  width: 44.094488%;
  height: 100%;
  position: absolute;
  z-index: 2;
  border-radius: 50%;
  margin-left: 10%;
  margin-top: 10%;
}

.sun {
  width: 30%;
  height: 30%;
  background-color: yellow;
  border: 8px solid orange;
  border-radius: 50%;
  box-shadow: 0 0 128px red;
  margin: auto;
  margin-top: -15%;
}

.grass {
  height: 30%;
  width: 100%;
  position: absolute;
  bottom: 0;
  z-index: 3;
  background: #9dd53a;
  /* Old browsers */
  background: -moz-linear-gradient(top, #9dd53a 0%, #a1d54f 23%, #80c217 70%, #7cbc0a 100%);
  /* FF3.6+ */
  background: -webkit-gradient(linear, left top, left bottom, color-stop(0%, #9dd53a), color-stop(23%, #a1d54f), color-stop(70%, #80c217), color-stop(100%, #7cbc0a));
  /* Chrome,Safari4+ */
  background: -webkit-linear-gradient(top, #9dd53a 0%, #a1d54f 23%, #80c217 70%, #7cbc0a 100%);
  /* Chrome10+,Safari5.1+ */
  background: -o-linear-gradient(top, #9dd53a 0%, #a1d54f 23%, #80c217 70%, #7cbc0a 100%);
  /* Opera 11.10+ */
  background: -ms-linear-gradient(top, #9dd53a 0%, #a1d54f 23%, #80c217 70%, #7cbc0a 100%);
  /* IE10+ */
  background: linear-gradient(to bottom, #9dd53a 0%, #a1d54f 23%, #80c217 70%, #7cbc0a 100%);
  /* W3C */
  filter: progid:DXImageTransform.Microsoft.gradient( startColorstr='#9dd53a', endColorstr='#7cbc0a', GradientType=0);
  /* IE6-9 */
}


/*animations*/

.rainsun:checked~.sun_path {
  -webkit-animation: spin-right 3s 1 forwards;
  -moz-animation: spin-right 3s 1 forwards;
  animation: spin-right 3s 1 forwards;
}


/* keyframes */

@-webkit-keyframes spin-right {
  100% {
    -webkit-transform: rotate(180deg);
  }
}

@-moz-keyframes spin-right {
  100% {
    -webkit-transform: rotate(180deg);
  }
}
<input class="rainsun" type="checkbox">
<div class="sky">
</div>
<!--end sky-->
<div class="sun_path">
  <div class="sun"></div>
</div>
<!--end sun_path-->
<div class="grass">
</div>
<!--end grass-->
like image 499
Longblog Avatar asked Feb 07 '14 02:02

Longblog


People also ask

How do you reset an animation in CSS?

To restart animation in CSS3 and JavaScript, we can get the offsetHeight property to trigger reflow. function resetAnimation() { const el = document. getElementById("animated"); el. style.

What is animation fill mode backwards?

backwards. When assigned animation-fill-mode: backwards, the target element will take the style values set by the first keyframe of the animation during the animation-delay period. animation-delay sets a time delay until an animation begins, and animation-fill-mode applies during this delay.


1 Answers

Instead of using keyframes, try a transform and set transition: transform. Here's an example of what I'm talking about:

.rainsun ~ .sun_path {
  -webkit-transition: -webkit-transform 3s;
  -moz-transition: -moz-transform 3s;
  transition: transform 3s;
}

.rainsun:checked ~ .sun_path {
  -webkit-transform: rotate(180deg);
  -moz-transform: rotate(180deg);
  transform: rotate(180deg);
}

Codepen Fork: Demo

like image 132
jonsuh Avatar answered Sep 29 '22 02:09

jonsuh