Is it possible to do free transforms of an element using CSS - similar to a mesh transform?
The closest I can get to this is using something like transform: perspective(400px) rotateY(45deg); with three elements, but I would like it to be one continuous img element.
You can consider 3 elements and background-image. The trick is to adjust the background-size/background-position to create the illusion of one continuous image.
Hover to see the result:
.box {
margin: 50px auto;
width: 200px;
height: 200px;;
background-size: 300% auto;
background-position: center;
position: relative;
}
.box:before,
.box:after {
content: "";
position: absolute;
width: 100%;
top: 0;
bottom: 0;
background-image: inherit;
background-size: 300% auto;
transform: perspective(800px);
transition: 0.5s all;
}
.box:before {
right: 100%;
background-position: left;
transform-origin: right;
}
.box:after {
left: 100%;
background-position: right;
transform-origin: left;
}
.box:hover::before {
transform: perspective(800px) rotateY(50deg);
filter: brightness(0.8);
}
.box:hover::after {
transform: perspective(800px) rotateY(-50deg);
filter: brightness(0.8);
}
<div class="box" style="background-image: url(https://picsum.photos/id/1/1000/800)">
</div>
Related
here is the shape i want to do enter link description here
P.S.I am still learning the front-end stuff so could you pls help me with this assignment.
Here is the HTML code <div>Elzero</div>
here is the CSS code i tried to do with
* {
box-sizing: border-box;
}
div {
width: 200px;
height: 200px;
background-color: #eee;
margin: 80px auto;
color: black;
font-size: 50px;
font-weight: bold;
text-align: center;
line-height: 200px;
border-radius: 50%;
}
::after {
content: "";
width: 200px;
height: 200px;
background-color: #03a9f4;
margin: 80px auto;
border-radius: 50%;
position: absolute;
transform: translate(-190px, -80px);
z-index: -1;
}
::before {
content: "";
width: 200px;
height: 200px;
background-color: #e91e63;
margin: 80px auto;
border-radius: 50%;
position: absolute;
top: 0px;
z-index: -2;
}
div:hover {
transition: all 0.5s;
transform: rotate(180deg);
}
As you are constrained to use just one div, this snippet builds on your idea of having the pseudo elements but creating them with conic-gradient backgrounds and the 'main' div having the light gray circular background created using a radial gradient. That way it creates these 3 shapes.
and overlays them to give the impression of 3/4 circles. It then uses CSS animation to rotate them on hover.
Obviously you will want to play with the dimensions, the animations timings and directions to get exactly what you want but this should give a start.
* {
box-sizing: border-box;
}
div {
width: 200px;
height: 200px;
background-image: radial-gradient(#eee 0 55%, transparent 55% 100%);
margin: 80px auto;
color: black;
font-size: 50px;
font-weight: bold;
text-align: center;
line-height: 200px;
border-radius: 50%;
position: relative;
}
div::after {
content: "";
width: 200px;
height: 200px;
border-radius: 50%;
position: absolute;
top: 0;
left: 0;
z-index: -2;
background-image: conic-gradient(#03a9f4 0deg 45deg, white 45deg 135deg, #03a9f4 135deg 360deg);
}
div::before {
content: "";
width: calc(100% - 10%);
height: calc(100% - 10%);
position: absolute;
border-radius: 50%;
position: absolute;
top: 5%;
left: 5%;
z-index: -1;
background-image: conic-gradient(#e91e63 0, #e91e63 225deg, white 225deg, white 315deg, #e91e63 315deg, #e91e63 360deg);
}
div:hover::after {
animation: rot .4s linear;
}
div:hover::before {
animation: rot .4s linear;
animation-delay: .1s;
animation-direction: reverse;
}
#keyframes rot {
0% {
transform: rotate(0);
}
25% {
transform: rotate(180deg);
}
50% {
transform: rotate(180deg);
}
75% {
transform: rotate(0);
}
100% {}
}
<div>Elzero
</div>
also here is example in less:
https://codepen.io/nikitahl/pen/XooBXd
if you want to use css here is a converter:
https://jsonformatter.org/less-to-css
So I'm doing this for some lines on my webpage.
#keyframes dropHeader {
0% {
height: 0px;
}
100% {
height: 100%;
}
}
.slant-decor {
left: 50%;
height: 100%;
position: fixed;
display: inline-flex;
animation-name: dropHeader;
animation-iteration-count: 1;
animation-timing-function: ease-out;
animation-duration: 0.6s;
}
.slant-decor:after {
width: 5px;
height: 100%;
background-color: rgba(0, 0, 0, 0.55);
content: "";
position: relative;
margin-left: -5px;
transform: skewX(-30deg);
display: inline-block;
}
.slant-decor div {
width: 19px;
height: 100%;
display: inline-block;
margin-left: -4px;
-ms-transform: skewX(-30deg); /* IE 9 */
-webkit-transform: skewX(-30deg); /* Safari */
transform: skewX(-30deg); /* Standard syntax */
}
.decor-orange {
background-color: orange;
}
.decor-red {
background-color: red;
}
.decor-green {
background-color: green;
}
<div class="slant-decor">
<div class="decor-red"></div>
<div class="decor-orange"></div>
<div class="decor-green"></div>
</div>
As of right now, the animation on .slant-decor works fine, however - as you can see, it causes a kind of a weird effect on the lines. What I'd like to achieve is that the animation follow the skew angle aswell, creating an effect where the lines would slide in from the top of the page, at the right angle. How could I achieve this?
If my understanding is correct, setting a transform-origin: right top would produce the effect that you are looking for. The default value for transform-origin is 50% 50% (the center-mid point of the element). When you animate the height, this point is constantly changing and hence creates that weird effect. If the transform-origin is set to a point that is fixed then that problem would be avoided.
#keyframes dropHeader {
0% {
height: 0px;
}
100% {
height: 100%;
}
}
.slant-decor {
left: 50%;
height: 300px;
position: fixed;
display: inline-flex;
animation-name: dropHeader;
animation-iteration-count: 1;
animation-timing-function: ease-out;
animation-duration: 0.6s;
}
.slant-decor:after {
width: 5px;
height: 100%;
background-color: rgba(0, 0, 0, 0.55);
content: "";
position: relative;
margin-left: -5px;
transform-origin: right top;
transform: skewX(-30deg);
display: inline-block;
}
.slant-decor div {
width: 19px;
height: 100%;
display: inline-block;
margin-left: -4px;
transform-origin: right top;
transform: skewX(-30deg);
}
.decor-orange {
background-color: orange;
}
.decor-red {
background-color: red;
}
.decor-green {
background-color: green;
}
<div class="slant-decor">
<div class="decor-red"></div>
<div class="decor-orange"></div>
<div class="decor-green"></div>
</div>
Does anyone have any idea on how to implement an HTML+CSS button that once clicked has an animation like this one?
Source: http://www.materialup.com/posts/shinebutton
Thanks for the help!
with Twitter's "fave" animation
.heart {
width: 100px;
height: 100px;
position: absolute;
left: 50%;
top: 50%;
transform: translate(-50%, -50%);
background: url(https://cssanimation.rocks/images/posts/steps/heart.png) no-repeat;
background-position: 0 0;
cursor: pointer;
animation: fave-heart 1s steps(28);
}
.heart:hover {
background-position: -2800px 0;
transition: background 1s steps(28);
}
#keyframes fave-heart {
0% {
background-position: 0 0;
}
100% {
background-position: -2800px 0;
}
}
<div class="heart"></div>
More
The following HTML5 and CSS3 animation is giving me two different issues and I've not been able to find previous answers to the question that have worked on my code. I'm curious if I'm doing something completely wrong here.
I have tried the solutions in this question, and this one with no results.
The two issues:
1.) The moon orbit transforms fine; the moon, as a child element, transforms as well. I attempt to apply the opposite transform but it doesn't appear to have any effect.
2.) I'm trying to alter the z-index so the moon goes behind the planet. The orbit border is temporary so no worries there but no matter what I set the z-index to I can't get the effect.
body {
height: 100%;
top: 0px;
bottom: 0px;
margin-top: 300px;
background-color: #143856;
}
.moonorbit {
position: relative;
top: -249px;
left: 309px;
width: 500px;
height: 500px;
border: 2px solid white;
border-radius: 50%;
-moz-transform: rotateX(75deg);
-webkit-transform: rotateX(75deg);
-o-transform: rotateX(75deg);
-ms-transform: rotateX(75deg);
transform: rotateX(75deg);
}
.mooncontainer {
position: absolute;
top: 175px;
left: 175px;
width: 150px !important;
height: 150px;
-moz-transform: rotateX(-75deg);
-webkit-transform: rotateX(-75deg);
-o-transform: rotateX(-75deg);
-ms-transform: rotateX(-75deg);
transform: rotateX(-75deg);
animation: moon-orbit 10s linear infinite;
}
.moon {
width: 150px !important;
height: 150px;
border-radius: 50%;
background: red url(img/planets_MOON.png) no-repeat;
background-size: cover;
animation: rotate 10s linear infinite;
}
.earth {
position: absolute;
width: 417px;
top: 100px;
left: 350px;
z-index: 0;
height: 209px;
}
.earth .planet {
/*width: 417px !important;
height: 417px;*/
width: 300px !important;
height: 300px;
background: yellow url(img/planets_EARTH.png) no-repeat;
background-size: cover;
border-radius: 50%;
margin: 0 auto;
}
/*Moon Orbit*/
#keyframes moon-orbit {
0% {
transform: rotateZ(0deg) translateX(250px);
}
100% {
transform: rotateZ(360deg) translateX(250px);
}
}
#keyframes rotate {
0% {
z-index: 5;
transform: rotateZ(0deg);
}
25% {
z-index: -5;
}
50% {
z-index: -5;
}
75% {
z-index: 5;
}
100% {
z-index: 5;
transform: rotateZ(-360deg);
}
}
<body>
<div class="earth">
<div class="planet"></div>
</div>
<div class="moonorbit">
<div class="mooncontainer">
<div class="moon"></div>
</div>
</div>
</body>
About your first issue, you are applying the technique ok. But there are 2 transformations that you need to correct, the one from the animation of the circle, that you have done, and the one from the inclination of the orbit (the rotateX(75deg)
This would be your demo with the correction applied
body {
height: 60%;
top: 0px;
bottom: 0px;
margin-top: 300px;
background-color: #143856;
}
.moonorbit {
position: relative;
top: -300px;
left: 209px;
width: 500px;
height: 500px;
border: 2px solid white;
border-radius: 50%;
transform: rotateX(75deg);
transform-style: preserve-3d;
}
.mooncontainer {
position: absolute;
top: 175px;
left: 175px;
width: 150px !important;
height: 150px;
-webkit-transform: rotateX(-75deg);
transform: rotateX(-75deg);
animation: moon-orbit 10s linear infinite;
transform-style: preserve-3d;
}
.moon {
width: 150px !important;
height: 150px;
border-radius: 50%;
background-color: white;
background-size: cover;
animation: rotate 10s linear infinite;
transform-style: preserve-3d;
}
.earth {
position: absolute;
width: 417px;
top: 100px;
left: 250px;
z-index: 0;
height: 209px;
}
.earth .planet {
/*width: 417px !important;
height: 417px;*/
width: 300px !important;
height: 300px;
background-color: lightgreen;
background-size: cover;
border-radius: 50%;
margin: 0 auto;
}
/*Moon Orbit*/
#keyframes moon-orbit {
0% {
transform: rotateZ(0deg) translateX(250px);
}
100% {
transform: rotateZ(360deg) translateX(250px);
}
}
#keyframes rotate {
0% {
transform: rotateZ(0deg) rotateX(-75deg); /* added rotateX(-75deg) to compensate */
}
100% {
transform: rotateZ(-360deg) rotateX(-75deg);
}
}
<div class="earth">
<div class="planet"></div>
</div>
<div class="moonorbit">
<div class="mooncontainer">
<div class="moon"></div>
</div>
</div>
About the second issue, your best bet is to work all the time in 3d, so it will be automatically solved. Another technique that makes it simpler is to chain the transforms. In my demo I have chained everything, so it's easier to get the control (and you have a simpler HTML
body {
height: 60%;
top: 0px;
bottom: 0px;
background-color: #143856;
}
.moon {
width: 150px;
height: 150px;
border-radius: 50%;
background: url(http://i.stack.imgur.com/L3IE5.jpg);
background-size: 120%;
background-position: center center;
animation: rotate 10s linear infinite;
transform-style: preserve-3d;
margin: auto;
position: absolute;
left: 0px;
right: 0px;
top: 0px;
bottom: 0px;
}
.earth {
position: absolute;
width: 300px;
height: 300px;
background: url(http://i.stack.imgur.com/5sqwZ.jpg);
background-size: 140%;
background-position: center center;
border-radius: 50%;
margin: 100px 200px;
perspective: 1500px;
transform-style: preserve-3d;
}
#keyframes rotate {
0% {
transform: rotateX(-75deg) rotateZ(0deg) translateX(300px) rotateZ(0deg) rotateX(75deg);
}
100% {
transform: rotateX(-75deg) rotateZ(-360deg) translateX(300px) rotateZ(360deg) rotateX(75deg);
}
}
<div class="earth">
<div class="moon"></div>
</div>
Trying to fix this with z-index will end in failure 70% all the time. lol See what I did there? Anyways, your best bet is to do this with a keyframes. Create a keyframe to draw out your path and to be honest you will need other things that would take a while to explain but How about I'll post my code here and the DEMO and you will be able to see the difference?
HTML
<div id="universe" class="scale-stretched">
<div id="solar-system" class="earth">
<div id="earth" class="orbit">
<div class="pos">
<div class="planet"> </div>
</div>
</div>
<div id="sun"> </div>
</div>
</div>
CSS
#universe {
z-index: 1;
position: absolute;
overflow: hidden;
width: 100%;
height: 100%;
background-position: center 40%;
background-repeat: no-repeat;
background-size: cover; }
#solar-system {
position: absolute;
width: 100%;
height: 100%;
transform-style: preserve-3d; }
.orbit {
position: absolute;
top: 50%;
left: 50%;
border: 1px solid rgba(255, 255, 255, 0.2);
border-radius: 50%;
transform-style: preserve-3d;
animation-name: orbit;
animation-iteration-count: infinite;
animation-timing-function: linear; }
.orbit .orbit {
animation-name: suborbit; }
.pos {
position: absolute;
top: 50%;
width: 2em;
height: 2em;
margin-top: -1em;
margin-left: -1em;
transform-style: preserve-3d;
animation-name: invert;
animation-iteration-count: infinite;
animation-timing-function: linear; }
#sun, .planet, #earth{
position: absolute;
top: 50%;
left: 50%;
width: 1em;
height: 1em;
margin-top: -0.5em;
margin-left: -0.5em;
border-radius: 50%;
transform-style: preserve-3d; }
#sun {
background-color: #FB7209;
background-repeat: no-repeat;
background-size: cover;
box-shadow: 0 0 60px rgba(255, 160, 60, 0.4); }
.planet {
background-color: #202020;
background-repeat: no-repeat;
background-size: cover;
animation-iteration-count: infinite;
animation-timing-function: linear; }
.ring {
position: absolute;
top: 50%;
left: 50%;
border-radius: 50%; }
#earth {
z-index: 8; }
#sun {
z-index: 1; }
#keyframes orbit {
0% {
transform: rotateZ(0deg); }
100% {
transform: rotateZ(-360deg); } }
#keyframes invert {
0% {
transform: rotateX(-90deg) rotateY(360deg) rotateZ(0deg); }
100% {
transform: rotateX(-90deg) rotateY(0deg) rotateZ(0deg); } }
.view-3D #solar-system {
transform: rotateX(75deg); }
.view-3D #sun {
transform: rotateX(-90deg); }
#earth .pos,
#earth .planet,
#earth.orbit {
animation-duration: 12.00021s; }
#earth .orbit .pos,
#earth .orbit {
animation-duration: 0.89764s; }
.scale-stretched #sun {
font-size: 24em; }
.scale-stretched #earth .planet {
font-size: 3.92em; }
.scale-stretched #earth.orbit {
width: 56em;
height: 56em;
margin-top: -28em;
margin-left: -28em; }
body { background: #000; }
#sun { background: yellow; }
#earth .planet { background: blue; }
And some simple jQuery to get the 3D effect so it looks 2D but moves 3D
$(window).load(function(){
var body = $("body"),
universe = $("#universe"),
solarsys = $("#solar-system");
var init = function() {
body.removeClass('view-2D opening').addClass("view-3D").delay(2000).queue(function() {
$(this).removeClass('hide-UI').addClass("set-speed");
$(this).dequeue();
});
};
init();
});
Here is a DEMO
I think if you use my code you'll probably be better off than fixing yours. Just a suggestion ;)
Please see the code in the code pen in this link.
I wasted two or three hours on this and decided to not to waste anymore.
I already tried the code right here and it is not working.
.coin {
background-image: url("http://coins.thefuntimesguide.com/images/blogs/presidential-dollar-coin-reverse-statue-of-liberty-public-domain.png");
background-size: 100% 100%;
border-radius: 100%;
height: 100px;
margin: 50px auto;
position: relative;
width: 100px;
-webkit-transition: .5s linear;
-webkit-transform-style: preserve-3d;
}
.coin:after {
background-color: #a37131;
background-image: -webkit-linear-gradient(hsla(0,0%,100%,.25), hsla(0,0%,0%,.25));
bottom: 0;
content: '';
left: 45px;
position: absolute;
top: 0;
width: 5px;
z-index: -10;
-webkit-transform: rotateY(-90deg);
-webkit-transform-origin: 100% 50%;
}
.coin:before {
background-color: #a37131;
background-image: -webkit-linear-gradient(hsla(0,0%,100%,.25), hsla(0,0%,0%,.25));
border-radius: 100%;
content: '';
height: 100px;
left: 0;
position: absolute;
top: 0;
width: 100px;
-webkit-transform: translateZ(-5px);
}
.coin:hover {
-webkit-transform: rotateY(90deg);
}
All I want to know is how to apply thickness to the door visible to a user.
You need to add -webkit-transform-style: preserve-3d; to 'div.thumb' element.