Material ripple style background animation - css

I have found this fiddle, but the animation works only if I click and hold.
#parent {
height: 200px;
width: 400px;
background-color: lightgray;
}
#circle {
background-image: url("http://upload.wikimedia.org/wikipedia/commons/0/0e/Ski_trail_rating_symbol-green_circle.svg");
background-position: center center;
background-repeat: no-repeat;
background-size: 0 0;
height: 200px;
width: 400px;
transition: .3s ease-in;
}
#parent:active #circle {
background-size: 600px 600px;
}
<div id="parent">
<div id="circle"></div>
</div>
Would it be possible to make the animation to load when the page loads?
Just want some background load in animation similarly to Android Lollipop ripple / Firefox OS for TV.

You can use CSS3 animation for the transition to start automatically.
Learn more about animation here:
https://css-tricks.com/almanac/properties/a/animation/
https://developer.mozilla.org/en-US/docs/Web/CSS/CSS_Animations/Using_CSS_animations
http://www.w3schools.com/css/css3_animations.asp
Updated fiddle: Fiddle
Snippet:
#parent {
height: 200px;
width: 400px;
background-color: lightgray;
}
#circle {
background-image: url("http://upload.wikimedia.org/wikipedia/commons/0/0e/Ski_trail_rating_symbol-green_circle.svg");
background-position: center center;
background-repeat: no-repeat;
background-size: 0 0;
height: 200px;
width: 400px;
/*transition: .3s ease-in;*/
animation: example 1s ease-in infinite;
}
#keyframes example {
0% {
background-size: 0px 0px;
}
50% {
background-size: 600px 600px;
}
100% {
background-size: 0px 0px;
}
}
<div id="parent">
<div id="circle"></div>
</div>

Related

How can I make a page hero image move on page load?

I have a banner image loading on my site with this code:
#keyframes animatedBanner {
from {
background-position-y: bottom;
}
to {
background-position-y: top;
}
}
.page-hero {
background-image: url(https://via.placeholder.com/428x100);
background-repeat: no-repeat;
padding-top: 214px;
padding-bottom: 214px;
text-align: center;
animation: 2s ease-out 0s 1 animatedBanner;
background-size: auto;
}
<div class="page-hero">
<div class="inside-page-hero grid-container grid-parent">
<h2>this is an image</h2>
</div>
</div>
This does what I hoped it would (slide the image up when the page loads). But the problem is that I was hoping to have the image span the entire width of the screen regardless of width. I tried using cover, but then the image doesn't scroll at all.
Is there a way to make this design responsive on the image?
background are a bit tricky when it comes to animate the position. You need some specific sizes. I have a detailed answer (Using percentage values with background-position on a linear-gradient) explaining the logic behind the values I am using:
#keyframes animatedBanner {
from {
background-position: 50% 200%;
}
to {
background-position: 50% 50%;
}
}
.page-hero {
background-image: url(https://picsum.photos/id/1068/800/400);
background-repeat: no-repeat;
padding:100px 0;
text-align: center;
animation: 2s ease-out animatedBanner both .5s;
background-size: auto 200%;
}
<div class="page-hero">
<div class="inside-page-hero grid-container grid-parent">
<h2>this is an image</h2>
</div>
</div>
To get the opposite direction
#keyframes animatedBanner {
from {
background-position: 50% -100%;
}
to {
background-position: 50% 50%;
}
}
.page-hero {
background-image: url(https://picsum.photos/id/1068/800/400);
background-repeat: no-repeat;
padding:100px 0;
text-align: center;
animation: 2s ease-out animatedBanner both .5s;
background-size: auto 200%;
}
<div class="page-hero">
<div class="inside-page-hero grid-container grid-parent">
<h2>this is an image</h2>
</div>
</div>
And if you want to avoid the complexity of background-position and background-size, use pseudo-element
#keyframes animatedBanner {
from {
transform: translateY(100%); /* or -100% */
}
}
.page-hero {
padding: 100px 0;
text-align: center;
position: relative;
z-index: 0;
overflow: hidden;
}
.page-hero:before {
content: "";
position: absolute;
z-index: -1;
inset: 0;
background: url(https://picsum.photos/id/1068/800/400) center/cover;
animation: 2s ease-out animatedBanner both .5s;
}
<div class="page-hero">
<div class="inside-page-hero grid-container grid-parent">
<h2>this is an image</h2>
</div>
</div>

How to improve an animated tv static effect using a pure css gradient

How would I be able to improve this animated static noise effect using a css gradient?
CSS only, no javascript, no svg, no image, using only a gradient, and adjusting that.
A tv no signal noise effect is what I am looking for using a css gradient.
Does anyone know how this effect can be improved, made better?
Is there a better way it can be written?
I am looking for something that is more accurate to a tv noise effect.
I think the way this effect is written can be improved.
Are there any tweaks or adjustments that can be made to it to so that it better depicts a tv noise effect?
The gradient can be anything, as long as it is a gradient, it doesn't matter what kind.
This one uses radial gradient:
https://jsfiddle.net/xhdkza5w/
html,
body {
width: 100%;
height: 100%;
display: flex;
}
.tv-static {
width: 500px;
height: 300px;
margin: auto;
background-image: repeating-radial-gradient(circle at 17% 32%, white, black 0.00085px);
animation: back 5s linear infinite;
}
#keyframes back {
from {
background-size: 100% 100%;
}
to {
background-size: 200% 200%;
}
}
<div class="tv-static"></div>
This one uses a conic-gradient: https://jsfiddle.net/bkx50apm/
html,
body {
width: 100%;
height: 100%;
display: flex;
}
.tv-static {
width: 500px;
height: 300px;
margin: auto;
background-image: repeating-conic-gradient(white, black 0.00085%);
animation: back 25s linear infinite;
}
#keyframes back {
from {
background-size: 100% 100%;
}
to {
background-size: 200% 200%;
}
}
<div class="tv-static"></div>
Do you mean this effect?
html,
body {
width: 100%;
height: 100%;
display: flex;
}
.animation {
width: 240px;
height: 240px;
margin: auto;
background-image: repeating-radial-gradient(circle at 17% 32%, white, black 0.00085px);
animation: animation 5s linear infinite;
}
#keyframes animation {
from {
background-position: 0px 0px;
}
to {
background-position: 240px 240px;
}
}
<div class="animation"></div>
Or this effect?
html,
body {
width: 100%;
height: 100%;
display: flex;
}
.animation {
width: 240px;
height: 240px;
margin: auto;
background-image: repeating-radial-gradient(circle at 17% 32%, white, black 0.00085px);
background-position: center;
animation: back 5s linear infinite;
}
#keyframes back {
from {
background-size: 100% 100%;
}
to {
background-size: 200% 200%;
}
}
<div class="animation"></div>
Edit: Added background-position: center.
By overlaying 2 of those effect on top of each other and each div has a different animation, you can create interference between the two that removes the artifacts of only having 1 static noise made from a single div.
This might be improved as I'm not well versed in css but the proof of concept works
html,
body {
width: 100%;
height: 100%;
display: flex;
}
.container_row {
display: flex;
}
.layer1 {
width: 100%;
background-color: rgba(255, 255, 255, 0.5);
}
.layer2 {
width: 100%;
margin-left: -100%;
background-color: rgba(255, 255, 255, 0.5);
}
.tv-static {
width: 500px;
height: 300px;
margin: auto;
background-image: repeating-radial-gradient(circle at 17% 32%, white, black 0.00085px);
}
.animation1 {
animation: back1 1s linear infinite;
}
.animation2 {
animation: back2 0.1s linear infinite;
}
#keyframes back1 {
from {
background-size: 100% 100%;
}
to {
background-size: 99% 100%;
}
}
#keyframes back2 {
from {
background-size: 48.56% 50%;
}
to {
background-size: 43.9% 50.1%;
}
}
<div class="layer1">
<div class="tv-static animation1"></div>
</div>
<div class="layer2">
<div class="tv-static animation2"></div>
</div>
With smooth timing function, animations don't give that effect we need to use step timing function to give those sudden change effect.
Solution 1: I've changed animation. And tweaked your gradient a little bit. I think using gradient is not a reliable solution because browsers do calculations differently and fractions, rounding change output. You are using radial gradient it looks things are going outwards from center of the placement. You'll have to test his on every platform and browser to see if it looks same.
Solution 2: Used SVG instead of gradient. The feTurbulence filter gives the noise effect. You can use svg as background-image.
Solution 3: Used image instead of gradient with same animation. Advantage of using image is that it'll look same across all browsers and screens.
Solution 3: Simply used noise gif image. No animation is required. :)
View following in 'full page' mode:
body {
text-align: center;
}
.tv {
width: 400px;
height: 200px;
border: 6px solid black;
margin: 0 auto;
overflow: hidden;
position: relative;
border-radius: 50% / 10%;
}
.tv-static {
position: absolute;
top: -200px;
left: -200px;
margin: auto;
height: 800px;
width: 800px;
background-image: repeating-radial-gradient(circle at 17% 132%, white 0.0005px, black 0.00085px);
animation: anim 1s steps(2, jump-both) infinite both;
transform: translate3d(0, 0, 0);
}
/******************************/
.tv0 {
width: 400px;
height: 200px;
border: 6px solid black;
margin: 0 auto;
overflow: hidden;
position: relative;
border-radius: 50% / 10%;
isolation: isolate;
}
.tv-static0 {
position: absolute;
top: 0px;
left: 0px;
margin: auto;
height: 300%;
width: 300%;
animation: anim 1s steps(2, end) infinite both;
transform: translate3d(0, 0, 0);
filter: contrast(300%) brightness(50%);
}
.tv-static0 svg {
height: 200%;
width: 100%;
transform: scale(2.5);
}
/******************************/
.tv1 {
width: 400px;
height: 200px;
border: 6px solid black;
margin: 0 auto;
overflow: hidden;
position: relative;
border-radius: 50% / 10%;
}
.tv-static1 {
position: absolute;
top: -500px;
right: -500px;
bottom: -500px;
left: -500px;
margin: auto;
background-image: url(https://i.stack.imgur.com/uzEM4.png);
animation: anim 1s steps(2, end) infinite both;
transform: translate3d(0, 0, 0);
}
/******************************/
.tv2 {
width: 400px;
height: 200px;
border: 6px solid black;
margin: 0 auto;
overflow: hidden;
position: relative;
border-radius: 50% / 10%;
}
.tv-static2 {
position: absolute;
top: -500px;
right: -500px;
bottom: -500px;
left: -500px;
margin: auto;
background-image: url(https://i.stack.imgur.com/9Be02.gif);
transform: translate3d(0, 0, 0);
}
#keyframes anim {
0% {
transform: translateX(0px, 0px);
}
10% {
transform: translate(-100px, 100px);
}
20% {
transform: translate(150px, -100px);
}
30% {
transform: translate(-100px, 100px);
}
40% {
transform: translate(100px, -150px);
}
50% {
transform: translate(-100px, 200px);
}
60% {
transform: translate(-200px, -100px);
}
70% {
transform: translateY(50px, 100px);
}
80% {
transform: translate(100px, -150px);
}
90% {
transform: translate(0px, 200px);
}
100% {
transform: translate(-100px, 100px);
}
}
Your original code. modified. May not work on every browser.
<div class="tv">
<div class="tv-static"></div>
</div>
<br> Using SVG `feTurbulence` filter
<div class="tv0">
<div class="tv-static0">
<svg viewBox="0 0 200% 200%" xmlns='http://www.w3.org/2000/svg'>
<filter id='noiseFilter'>
<feTurbulence type='turbulence' result='noise' baseFrequency='0.7' numOctaves='6' seed='2'
stitchTiles='noStitch' />
</filter>
<rect width='100%' height='100%' filter='url(#noiseFilter)' />
</svg>
<div class="overlay"></div>
</div>
</div>
<br>
<br> Animating image. Color TV
<div class="tv1">
<div class="tv-static1"></div>
</div>
<br> Using gif. No animation.
<div class="tv2">
<div class="tv-static2"></div>
</div>

Adding image background size animation effect to element in pure CSS

Why I am not able to add animation of changing background image size of div on load? I know this is doable using JS by adding a class to the body or element but how we can achieve this in pure CSS?
html,body {
height: 100%;
width:100%;
}
div {
height: 100%;
width:100%;
background-image: url(https://upload.wikimedia.org/wikipedia/commons/d/da/Internet2.jpg);
background-size: 100%;
background-repeat: no-repeat;
background-position: 50% 50%;
animation-name: animate;
transition: all 3s;
}
.animate {
from {background-size: 100%}
to {background-size: 110%}
}
<div></div>
html, body { height: 100%; width: 100%; }
div {
height: 100%;
width: 100%;
background-image: url(https://upload.wikimedia.org/wikipedia/commons/d/da/Internet2.jpg);
background-size: 100%;
background-repeat: no-repeat;
background-position: 50% 50%;
animation: animate 3s ease forwards;
transition: all 3s;
}
#keyframes animate {
from { background-size: 100%; }
to { background-size: 150%; }
}
<div></div>

Simple loading bar

I'm trying to make a simple download bar, but it turns out only a solid color without transition animation.
In addition, the "repeating-linear-gradient" does not work and I cannot understand why.
I am hope for your help. Thank you!
.Download {
height: 80px;
width: 1000px;
border: 2px solid black;
border-radius: 100px;
/*background: repeating-linear-graient (90deg, blue, red, 100px);*/
background: linear-gradient(to left, blue, red);
animation-name: download;
animation-direction: 10s;
animation-timing-function: linear;
animation-direction: normal;
}
#keyframes download {
0% {
left: -100%;
}
100% {
left: 100%;
}
}
<div class="Download">
</div>
You can use pseudo code to achieve this.
.Download {
height: 80px;
width: 1000px;
border: 2px solid black;
border-radius: 100px;
position: relative;
overflow: hidden;
}
.Download:after {
content: "";
position: absolute;
background-image: linear-gradient(to left, blue, red);
width: 100%;
height: 100%;
top: 0;
left: -100%;
animation: download 5s;
}
#keyframes download {
0% {
left: -100%;
}
100% {
left: 0%;
}
}
<div class="Download">
</div>
You need to make half the linear gradient transparent (a bit list to prevent a hole in the end). Set the background position x to 100% to present only the transparent part. Then animation to 0:
.Download {
height: 80px;
width: 1000px;
border: 2px solid black;
border-radius: 100px;
background: linear-gradient(to right, red 0, blue 50.02%, transparent 50.02%) no-repeat;
animation: download 10s forwards;
background-position: 100% 0;
background-size: 200% 100%;
}
#keyframes download {
to {
background-position: 0 0;
}
}
<div class="Download">
</div>

CSS way of looping a background image with cover or contain sizing

Say you are trying to animate a tilable background like this:
.container {
width: 160px;
height: 91px;
}
.bg {
width: 100%;
height: 100%;
background: url(http://i60.tinypic.com/2j2fhjm.jpg) repeat-x left center;
background-size: contain;
-webkit-animation: displace 2s linear infinite;
animation: displace 2s linear infinite;
}
#-webkit-keyframes displace {
from {
background-position: 0 center;
}
to {
background-position: 160px center;
}
}
#keyframes displace {
from {
background-position: 0 center;
}
to {
background-position: 160px center;
}
}
<div class="container">
<textarea class="bg"></textarea>
</div>
As soon as you change the dimensions of the container, the looping animation breaks!
Is there any way to make this responsive without JS?
The problem is that, to make it responsive, you need to set the animated background-position using percentages.
But, when you set background-size as cover or contain, in some cases the width is adjusted to 100%. In this case, background-position using percentages is useless (won't move it).
The only way that I have found to manage this is moving the image to a pseudo element, and moving it. To keep the continuity, though, we will need two pseudo elements.
But that won't work on a textarea.
You didn't said anything about textarea being a requirement, so I am posting this. To show that it works on resize, hover it.
.container {
width: 160px;
height: 100px;
position: relative;
border: solid 1px black;
display: inline-block;
}
.container:nth-child(2) {
width: 220px;
}
.bg {
position: absolute;
width: 100%;
height: 100%;
overflow: hidden;
}
.bg:before, .bg:after {
content: "";
position: absolute;
width: 100%;
height: 100%;
background-image: url(http://i.stack.imgur.com/wBHey.png);
background-size: 100%;
animation: move 2s infinite linear;
}
.bg:before {
right: 100%;
}
#keyframes move {
from {transform: translateX( 0%);}
to {transform: translateX(100%);}
}
<div class="container">
<div class="bg"></div>
</div>
<div class="container">
<div class="bg"></div>
</div>
I was able to make it work by making the background twice as big.
I know this isn't the perfect solution, but maybe you can do a trick with the image size or something to make it look the way you wanted it to.
.container {width: 160px;height: 91px;}
.bg {
width: 100%;
height: 100%;
background: url(http://i60.tinypic.com/2j2fhjm.jpg) repeat-x left center;
background-size: 200%;
-webkit-animation: displace 2s linear infinite;
animation: displace 2s linear infinite;
}
#-webkit-keyframes displace {
from { background-position: left center;
} to { background-position: 200% center; }
}
#keyframes displace {
from { background-position: left center;
} to { background-position: 200% center; }
}
<div class="container"><textarea class="bg"></textarea></div>
The problem you have is with the height resizing and your different settings. To get it to work with your actual settings, the displace would have to be 2x the height of the image (since the image has a ration of 2:1). I don't think you can do only by css.
But you have different options. I'm not sure exactly which part of you display you want to keep, so here are three ways to get your translation working on resize. None have exactly your settings, because the ones you have make it hard (impossible?) to set the proper displacement. Since you're stretching the width depending on the height, it's hard to follow. Via JS it would be easy, but css has limited access to these values.
The solutions proposed keep the height constant so you can keep your displace value constant.
First one, the background-size is the size of the container in px.
Second solution, you resize textarea only on x axis.
Third you repeat on y axis and keep height and width fixed.
There are probably other workarounds that are maybe more suited to your specific needs.
.container {
width: 160px;
height: 80px;
margin: 10px;
}
.bg {
width: 100%;
height: 100%;
background: url(http://i60.tinypic.com/2j2fhjm.jpg) repeat-x left center;
background-size: 160px 80px;
padding: 0px;
-webkit-animation: displace 2s linear infinite;
animation: displace 2s linear infinite;
}
.bg2 {
width: 100%;
height: 100%;
background: url(http://i60.tinypic.com/2j2fhjm.jpg) repeat-x left center;
background-size: contain;
padding: 0px;
resize: horizontal;
-webkit-animation: displace 2s linear infinite;
animation: displace 2s linear infinite;
}
.bg3 {
width: 100%;
height: 100%;
background: url(http://i60.tinypic.com/2j2fhjm.jpg) repeat left center;
background-size: 160px 80px;
padding: 0px;
-webkit-animation: displace 2s linear infinite;
animation: displace 2s linear infinite;
}
#-webkit-keyframes displace {
from {
background-position: 0 center;
}
to {
background-position: 160px center;
}
}
#-keyframes displace {
from {
background-position: 0 center;
}
to {
background-position: 160px center;
}
}
<div class="container">
<textarea class="bg"></textarea>
</div>
<div class="container">
<textarea class="bg2"></textarea>
</div>
<div class="container">
<textarea class="bg3"></textarea>
</div>
This is similar to Ilpo's answer, except it doesn't resize the image (background-size: auto;). The animation is smooth throughout, regardless of container size.
The downside is that the width (200px) of the image needs to be known beforehand.
Since you said tilable, and since this image looks to be tilable in both directions, I also made it repeat in both dimensions. As a result, your textarea is filled with the tiled background image, animated to scroll horizontally. If you only want to tile in 1 direction, you can change repeat back to repeat-x and change the vertical position from top to whatever you need.
.container {width: 160px;height: 91px;}
.bg {
width: 100%;
height: 100%;
background: url(http://i60.tinypic.com/2j2fhjm.jpg) repeat left top;
background-size: auto;
-webkit-animation: displace 2s linear infinite;
animation: displace 2s linear infinite;
}
#-webkit-keyframes displace {
from { background-position: 0px top; }
to { background-position: 200px top; }
}
#keyframes displace {
from { background-position: 0px top; }
to { background-position: 200px top; }
}
<div class="container"><textarea class="bg"></textarea></div>
For each background-position: 200px bottom; you need to add 1second for example if you want add 2S, you add another 200px so you
make it background-position: 400px bottom; I think.
Here is the code:
.container {
width: 160px;
height: 91px;
}
.bg {
width: 100%;
height: 100%;
background: url(http://i60.tinypic.com/2j2fhjm.jpg) fixed;
-webkit-animation: displace 1s linear infinite;
animation: displace 1s linear infinite;
}
#-webkit-keyframes displace {
from { background-position: 0 bottom; }
to { background-position: 200px bottom; }
}
#keyframes displace {
from { background-position: 0 bottom; }
to { background-position: 200px bottom;}
}
<div class="container">
<textarea class="bg"></textarea>
</div>
I hope it works for your case, Let me know if you have any question.
.container {
border: 1px solid black;
display: inline-block;
background: url(http://i60.tinypic.com/2j2fhjm.jpg) repeat-x left center;
-webkit-animation: displace 2s linear infinite;
animation: displace 2s linear infinite;
background-size: 160px 100%;
}
.bg {
float: left;
border: 0;
margin: 10px;
width: 160px;
height: 91px;
background-color: rgba(255, 255, 255, .5);
}
#-webkit-keyframes displace {
from {
background-position: 0 center;
}
to {
background-position: 160px center;
}
}
#keyframes displace {
from {
background-position: 0 center;
}
to {
background-position: 160px center;
}
}
<div class="container">
<textarea class="bg"></textarea>
</div>

Resources