CSS Animations Goodie (#3424)

* Base created

* YML File Updated

* Codepen logo added

* Logo renamed | urls added

* Initial version added

* Removes unwanted CSS

* Remove codepen logo

* Removes cssanimations.js

* Restructuring things

* Fixes bareword test file issue

* Test File fixed

* CSS Tricks Demos added

* Changes to tile and data

* Title added and styled

* Adds 2 demos to Goodie

* Fixes margin between title and demo

* Modularizing demos

* CSS Animations: Makes code more modular

* Data YML updated

* Fixes no file exist issue

* Minor changes in test file

* Fix: Reduces width of tile, fixes animation overflows

* Feature: CodePen AutoPen Generation added

* Fix: Test File fixed

* Add: Proportional Animations

* Add: Changing transform-origin mid-animation

* Add: Negative transform-origins

* Add: Box shadow magic

* Fix: Fix conflict in CSS

* Update: Removes unnecessary keys

* Fix: Warnings and errors for https

* Fix: Fixes text in demo 1

* Formats: Formats all CSS Stylesheets

* Fix: Handles unnecessary triggering

* Fix: Handles if variables are undefined

* Adds: Adds more test cases

* Fix: Moves logic to a separate sub routine

* Fix: Removes external resource usage
master
Manraj Singh 2016-12-16 01:39:55 +05:30 committed by Zaahir Moolla
parent cceafc1fde
commit 190fd4444c
17 changed files with 705 additions and 0 deletions

View File

@ -0,0 +1,65 @@
package DDG::Goodie::CssAnimations;
# ABSTRACT: Shows examples of CSS Animations from various references
use DDG::Goodie;
use YAML::XS 'LoadFile';
use strict;
use warnings;
use JSON;
zci answer_type => 'css_animations';
zci is_cached => 1;
triggers start => 'css animations', 'css animations example', 'css animation', 'css animation examples',
'css animation demo', 'css animations demos', 'css animations demo', 'css animation demos';
my $animations = LoadFile(share('data.yml'));
sub build_response() {
my $demo_count = keys $animations;
my @result = ();
for (my $i=0; $i < $demo_count; $i++) {
my $demo = "demo_$i";
my $title = $animations->{$demo}->{'title'};
my $html = share("$demo/demo.html")->slurp if -e share("$demo/demo.html");
my $css = share("$demo/style.css")->slurp if -e share("$demo/style.css");
my %value = ('title' => $title, 'html' => $html, 'css' => $css);
$animations->{$demo}->{'html'} = $html || '';
$animations->{$demo}->{'css'} = $css || '';
$animations->{$demo}->{'value'} = encode_json \%value || '';
push(@result, $animations->{$demo});
}
return @result;
}
my @result = build_response();
handle remainder => sub {
return unless $_ eq '';
return 'CSS Animations',
structured_answer => {
id => 'css_animations',
name => 'CSS Animations',
data => \@result,
templates => {
group => 'base',
detail => 0,
item_detail => 0,
options => {
content => 'DDH.css_animations.content'
},
variants => {
tile => 'xwide'
}
}
};
};
1;

View File

@ -0,0 +1,14 @@
<form action="https://codepen.io/pen/define" method="POST" target="_blank">
<input type="hidden" name="data" value="{{ value }}" />
<div onclick="javascript:this.parentNode.submit();">
<div class="tile--css_animations__title">
{{ title }}
</div>
<div class="tile--css_animations__demo">
<style type="text/css">
{{{ css }}}
</style>
{{{ html }}}
</div>
</div>
</form>

View File

@ -0,0 +1,14 @@
.tile--css_animations {
cursor: pointer !important;
}
.tile--css_animations__title {
font-size: 110%;
font-weight: 900;
margin-bottom: 6px;
}
.tile--css_animations__demo {
width: 230px;
height: 230px;
}

View File

@ -0,0 +1,13 @@
---
"demo_0":
title: "Jump to another state mid-animation"
"demo_1":
title: "Negative animation delays"
"demo_2":
title: "Proportional animations"
"demo_3":
title: "Changing transform-origin mid-animation"
"demo_4":
title: "Negative transform-origins"
"demo_5":
title: "Box shadow magic"

View File

@ -0,0 +1,6 @@
<div class="tile--css_animations__demo1">
<div>
<p id="status">O<span>P</span>EN</p>
<p id="message">CO<span>M</span><span>E</span> IN!</p>
</div>
</div>

View File

@ -0,0 +1,77 @@
.tile--css_animations__demo1 {
background-color: #111111;
height: 100%;
}
.tile--css_animations__demo1 div {
padding: 40px;
font-size: 36px;
font-family: monospace;
text-align: center;
text-transform: uppercase;
text-shadow: 0 0 80px red, 0 0 30px FireBrick, 0 0 6px DarkRed;
color: red;
}
.tile--css_animations__demo1 div p {
margin: 0;
}
.tile--css_animations__demo1 #status:hover {
text-shadow: 0 0 200px #ffffff, 0 0 80px #008000, 0 0 6px #0000ff;
}
.tile--css_animations__demo1 #message {
font-size: 20px;
}
.tile--css_animations__demo1 #message:hover {
text-shadow: 0 0 100px red, 0 0 40px FireBrick, 0 0 8px DarkRed;
}
.tile--css_animations__demo1 #status {
color: #fff;
text-shadow: 0 0 80px #ffffff, 0 0 30px #008000, 0 0 6px #0000ff;
}
.tile--css_animations__demo1 #status span {
animation: upper 11s linear infinite;
}
.tile--css_animations__demo1 #message span:nth-of-type(2) {
animation: lower 10s linear infinite;
}
.tile--css_animations__demo1 #message span:nth-of-type(1) {
text-shadow: none;
opacity: .4;
}
@keyframes upper {
0%, 19.999%, 22%, 62.999%, 64%, 64.999%, 70%, 100% {
opacity: .99;
text-shadow: 0 0 80px #ffffff, 0 0 30px #008000, 0 0 6px #0000ff;
}
20%,
21.999%,
63%,
63.999%,
65%,
69.999% {
opacity: 0.4;
text-shadow: none;
}
}
@keyframes lower {
0%, 12%, 18.999%, 23%, 31.999%, 37%, 44.999%, 46%, 49.999%, 51%, 58.999%, 61%, 68.999%, 71%, 85.999%, 96%, 100% {
opacity: 0.99;
text-shadow: 0 0 80px red, 0 0 30px FireBrick, 0 0 6px DarkRed;
}
19%,
22.99%,
32%,
36.999%,
45%,
45.999%,
50%,
50.99%,
59%,
60.999%,
69%,
70.999%,
86%,
95.999% {
opacity: 0.4;
text-shadow: none;
}
}

View File

@ -0,0 +1,5 @@
<div class="tile--css_animations__demo2">
<div></div>
<div></div>
<div></div>
</div>

View File

@ -0,0 +1,60 @@
.tile--css_animations__demo2 div {
border-radius: 50%;
position: absolute;
top: 50%;
left: 75%;
width: 100%;
}
.tile--css_animations__demo2 div:nth-of-type(odd) {
background: black;
}
.tile--css_animations__demo2 div:nth-of-type(even) {
background: white;
border: 2px solid black;
}
.tile--css_animations__demo2 div:nth-of-type(3) {
height: 10px;
width: 10px;
margin-top: -5px;
margin-left: -5px;
-webkit-animation: slide 3s ease-in-out infinite;
animation: slide 3s ease-in-out infinite;
}
.tile--css_animations__demo2 div:nth-of-type(2) {
height: 20px;
width: 20px;
margin-top: -12px;
margin-left: -12px;
-webkit-animation: slide 3s -2.7s ease-in-out infinite;
animation: slide 3s -2.7s ease-in-out infinite;
}
.tile--css_animations__demo2 div:nth-of-type(1) {
height: 40px;
width: 40px;
margin-top: -20px;
margin-left: -20px;
-webkit-animation: slide 3s -2.4s ease-in-out infinite;
animation: slide 3s -2.4s ease-in-out infinite;
}
@keyframes slide {
0% {
left: 75%
}
50% {
left: 25%;
}
100% {
left: 75%;
}
}
@-webkit-keyframes slide {
0% {
left: 75%
}
50% {
left: 25%;
}
100% {
left: 75%;
}
}

View File

@ -0,0 +1,26 @@
<div class="tile--css_animations__demo3">
<span>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
</span>
</div>

View File

@ -0,0 +1,174 @@
.tile--css_animations__demo3 {
background: rgb(20, 20, 20);
overflow: hidden;
padding-top: 50px;
}
.tile--css_animations__demo3 span {
position: relative;
display: block;
width: 100%;
height: 0;
padding-top: 78%;
overflow: hidden;
}
.tile--css_animations__demo3 div {
margin-top: -17%;
height: 34%;
width: 2%;
top: 30%;
border-radius: 20px;
position: absolute;
}
.tile--css_animations__demo3 div:nth-of-type(1) {
animation: wave 17s 0.000s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(2) {
animation: wave 17s -16.227s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(3) {
animation: wave 17s -15.455s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(4) {
animation: wave 17s -14.682s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(5) {
animation: wave 17s -13.909s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(6) {
animation: wave 17s -13.136s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(7) {
animation: wave 17s -12.364s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(8) {
animation: wave 17s -11.591s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(9) {
animation: wave 17s -10.818s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(10) {
animation: wave 17s -10.045s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(11) {
animation: wave 17s -9.273s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(12) {
animation: wave 17s -8.500s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(13) {
animation: wave 17s -7.727s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(14) {
animation: wave 17s -6.955s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(15) {
animation: wave 17s -6.182s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(16) {
animation: wave 17s -5.409s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(17) {
animation: wave 17s -4.636s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(18) {
animation: wave 17s -3.864s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(19) {
animation: wave 17s -3.091s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(20) {
animation: wave 17s -2.318s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(21) {
animation: wave 17s -1.545s linear infinite;
}
.tile--css_animations__demo3 div:nth-of-type(22) {
animation: wave 17s -0.773s linear infinite;
}
@keyframes wave {
0% {
left: -2%;
background: #3B44D1;
}
5% {
background: #9337FE;
}
10% {
height: 10%;
margin-top: -5%;
background: #C532FC;
}
15% {
background: #F639F8;
}
20% {
height: 34%;
margin-top: -17%;
background: #F236C8;
}
25% {
background: #FF2F8D;
}
30% {
height: 10%;
margin-top: -5%;
background: #EE3860;
}
35% {
background: #DC5245;
}
40% {
height: 34%;
margin-top: -17%;
background: #F38643;
}
45% {
background: #F8B435;
}
50% {
height: 10%;
margin-top: -5%;
background: #FAF444;
}
55% {
background: #E0FF3B;
}
60% {
height: 34%;
margin-top: -17%;
background: #E1FF3C;
}
65% {
background: #46F443;
}
70% {
height: 10%;
margin-top: -5%;
background: #54E67B;
}
75% {
background: #4DF3A9;
}
80% {
height: 34%;
margin-top: -17%;
background: #3AF9DA;
}
85% {
background: #36EBF4;
}
90% {
height: 10%;
margin-top: -5%;
background: #3DB3F3;
}
95% {
background: #3C82F1;
}
100% {
height: 34%;
margin-top: -17%;
left: 100%;
background: #5B38EE;
}
}

View File

@ -0,0 +1,3 @@
<div class="tile--css_animations__demo4">
<div></div>
</div>

View File

@ -0,0 +1,43 @@
.tile--css_animations__demo4 div {
width: 115px;
height: 115px;
background: rgb(0, 0, 255);
animation: flipAround 8s infinite;
transform-origin: right;
}
@keyframes flipAround {
25% {
transform-origin: right;
animation-mode: forwards;
transform: rotateY(-180deg);
}
25.001% {
transform-origin: bottom;
transform: translateX(115px);
}
50% {
transform-origin: bottom;
transform: translateX(115px) rotateX(-180deg);
}
50.001% {
transform-origin: left;
transform: translateX(115px) translateY(115px);
}
75% {
transform-origin: left;
transform-origin: left;
transform: translateX(115px) translateY(115px) rotateY(180deg);
}
75.001% {
transform-origin: top;
transform: translateY(115px);
}
100% {
transform-origin: top;
transform-origin: top;
transform: translateY(115px) rotateX(180deg);
}
}
.tile--css_animations__demo4 {
height: 230px;
}

View File

@ -0,0 +1,3 @@
<div class="tile--css_animations__demo5">
<div></div>
</div>

View File

@ -0,0 +1,26 @@
.tile--css_animations__demo5 div {
width: 50px;
height: 50px;
transform-origin: 100px 70px;
position: relative;
animation: single_rotate 3s linear infinite;
}
.tile--css_animations__demo5 div:before {
content: '';
position: absolute;
height: 100%;
width: 100%;
background: blue;
animation: single_rotate 3s linear reverse infinite;
border-radius: 50px;
}
@keyframes single_rotate {
100% {
transform: rotate(-360deg);
}
}
.tile--css_animations__demo5 {
width: 230px;
height: 230px;
padding: 50px 10px;
}

View File

@ -0,0 +1,3 @@
<div class="tile--css_animations__demo6">
<div></div>
</div>

View File

@ -0,0 +1,131 @@
.tile--css_animations__demo6 div {
border-radius:50%;
height:2px; width:2px; /* To allow border-radius to work */
position:absolute;
top:50%; left:50%;
margin-top:-1px; margin-left:-1px;
box-shadow:
-30px -50px 0 15px #6cce74,
30px -50px 0 15px #c18d46,
60px 0px 0 15px #c14745,
30px 50px 0 15px #2e1e5b,
-30px 50px 0 15px #9c37a6,
-60px 0px 0 15px #76bdd1;
-webkit-animation:rotate 12s infinite linear;
animation:rotate 12s infinite linear;
}
@keyframes rotate {
16.67% {
box-shadow:
-30px -50px 0 15px #76bdd1,
30px -50px 0 15px #6cce74,
60px 0px 0 15px #c18d46,
30px 50px 0 15px #c14745,
-30px 50px 0 15px #2e1e5b,
-60px 0px 0 15px #9c37a6;
}
33.33% {
box-shadow:
-30px -50px 0 15px #9c37a6,
30px -50px 0 15px #76bdd1,
60px 0px 0 15px #6cce74,
30px 50px 0 15px #c18d46,
-30px 50px 0 15px #c14745,
-60px 0px 0 15px #2e1e5b;
}
50% {
box-shadow:
-30px -50px 0 15px #2e1e5b,
30px -50px 0 15px #9c37a6,
60px 0px 0 15px #76bdd1,
30px 50px 0 15px #6cce74,
-30px 50px 0 15px #c18d46,
-60px 0px 0 15px #c14745;
}
66.67% {
box-shadow:
-30px -50px 0 15px #c14745,
30px -50px 0 15px #2e1e5b,
60px 0px 0 15px #9c37a6,
30px 50px 0 15px #76bdd1,
-30px 50px 0 15px #6cce74,
-60px 0px 0 15px #c18d46;
}
88.88% {
box-shadow:
-30px -50px 0 15px #c18d46,
30px -50px 0 15px #c14745,
60px 0px 0 15px #2e1e5b,
30px 50px 0 15px #9c37a6,
-30px 50px 0 15px #76bdd1,
-60px 0px 0 15px #6cce74;
}
100% {
transform:rotate(-360deg);
box-shadow:
-30px -50px 0 15px #6cce74,
30px -50px 0 15px #c18d46,
60px 0px 0 15px #c14745,
30px 50px 0 15px #2e1e5b,
-30px 50px 0 15px #9c37a6,
-60px 0px 0 15px #76bdd1;
}
}
@-webkit-keyframes rotate {
16.67% {
box-shadow:
-30px -50px 0 15px #76bdd1,
30px -50px 0 15px #6cce74,
60px 0px 0 15px #c18d46,
30px 50px 0 15px #c14745,
-30px 50px 0 15px #2e1e5b,
-60px 0px 0 15px #9c37a6;
}
33.33% {
box-shadow:
-30px -50px 0 15px #9c37a6,
30px -50px 0 15px #76bdd1,
60px 0px 0 15px #6cce74,
30px 50px 0 15px #c18d46,
-30px 50px 0 15px #c14745,
-60px 0px 0 15px #2e1e5b;
}
50% {
box-shadow:
-30px -50px 0 15px #2e1e5b,
30px -50px 0 15px #9c37a6,
60px 0px 0 15px #76bdd1,
30px 50px 0 15px #6cce74,
-30px 50px 0 15px #c18d46,
-60px 0px 0 15px #c14745;
}
66.67% {
box-shadow:
-30px -50px 0 15px #c14745,
30px -50px 0 15px #2e1e5b,
60px 0px 0 15px #9c37a6,
30px 50px 0 15px #76bdd1,
-30px 50px 0 15px #6cce74,
-60px 0px 0 15px #c18d46;
}
88.88% {
box-shadow:
-30px -50px 0 15px #c18d46,
30px -50px 0 15px #c14745,
60px 0px 0 15px #2e1e5b,
30px 50px 0 15px #9c37a6,
-30px 50px 0 15px #76bdd1,
-60px 0px 0 15px #6cce74;
}
100% {
-webkit-transform:rotate(-360deg);
box-shadow:
-30px -50px 0 15px #6cce74,
30px -50px 0 15px #c18d46,
60px 0px 0 15px #c14745,
30px 50px 0 15px #2e1e5b,
-30px 50px 0 15px #9c37a6,
-60px 0px 0 15px #76bdd1;
}
}

42
t/CssAnimations.t Normal file
View File

@ -0,0 +1,42 @@
#!/usr/bin/env perl
use strict;
use warnings;
use Test::More;
use Test::Deep;
use DDG::Test::Goodie;
zci answer_type => 'css_animations';
zci is_cached => 1;
sub build_structured_answer {
return 'CSS Animations',
structured_answer => {
id => 'css_animations',
name => 'CSS Animations',
data => ignore(),
templates => {
group => 'base',
detail => 0,
item_detail => 0,
options => {
content => 'DDH.css_animations.content'
},
variants => {
tile => 'xwide'
}
}
};
}
sub build_test { test_zci(build_structured_answer()) }
ddg_goodie_test(
[qw( DDG::Goodie::CssAnimations )],
'css animations' => build_test(),
'css animations demo' => build_test(),
'help css animations' => undef,
'css animations generator' => undef
);
done_testing;