With code below, when tapping the sample element, the sample will go big and then go small, it's nice.
But the question is, when I tap the sample element twice, the effect will only show once.
I know that's because the sample element is still focused, so the animation is not triggered.
I want to solve this with just css, what should I do?
.sample:hover, .sample:focus {
animation: phoneButtonEffect 0.2s linear;
}
#keyframes phoneButtonEffect {
50% {
transform: scale(1.1)
}
100% {
transform: scale(1)
}
}
That can be achieved with the :active pseudo class.
Take a look at this:
.sample{
height: 10em;
width: 10em;
background-color: red;
transition: all .2s ease-in-out;
}
.sample:active {
transform: scale(1.1);
transition: .1s;
}
<div class="sample">
</div>
The first .2s value is the that the transition will take to be back to normal and the second value .1s in the :active selector, is the time that the .sample element will take the reach the desired state, in this case, scale(1.1).
Related
I am trying to make a loading animation. I am using css transition to transition into the loading by scaling and then using animation to scale out the x axis. But when I try to transition back to the original state it doesn't use the transition anymore it just snaps back. I could use animation for the whole thing but I want to account for the page continuing to load so I don't want to have to write extra javascript logic to handle it. It would be nice if It would just transition on its own.
When you click the following snippet the first time it works fine. But when you click it again it just snaps back to its original state and doesn't use the transition. If you use a different property like opacity in the animation part then it works fine so I'm assuming there is something with the browser not recognizing the current scaled value. Is this a bug or am I doing something wrong?
document.querySelector('.wrapper').addEventListener('click', () => {
document.querySelector('.wrapper').classList.toggle('loading')
})
.wrapper{
position:fixed;
top: 0;
left: 0;
width: 100%;
height: 100%;
}
.wrapper > div{
color: white;
display:flex;
align-items: center;
justify-content: center;
width: 100%;
height: 100%;
background: blue;
transition: transform 500ms ease-out;
transform: scale(1);
}
.wrapper.loading > div{
transform: scale(0.2, 0.002);
animation: loading 1000ms ease-out infinite;
animation-delay: 500ms;
}
#keyframes loading {
0%{
transform: scale(0.2, 0.002)
}
50%{
transform: scale(0.5, 0.002)
}
100%{
transform: scale(0.2, 0.002)
}
}
<div class="wrapper">
<div>click me</div>
</div>
TL;DR
I believe that this happens because CSS transition eventually gives a class two states and transitions between them, when you remove your class you don't change its state, you remove it. my solution would be to add another class to set it back.
CSS transitions work by defining two states for the object using CSS. In your case, you define how the object looks when it has the class "loading" and you define how it looks when it doesn't have the class "saved" (it's normal look). When you remove the class "loading", it will transition to the other state according to the transition settings in place for the object without the "loading" class.
If the CSS transition settings apply to the object (without the "loading" class), then they will apply to both transitions.
your transition CSS settings only apply to .saved and thus when you remove it, there are no controls to specify a CSS setting. You may want to add another class ".fade" that you leave on the object all the time and you can specify your CSS transition settings on that class so they are always in effect.
I don't know a pure css fix for this.
But you can add a different class with a animation that restores to what it was before with JS
const wrapper = document.querySelector(".wrapper");
wrapper.onclick = () => {
if ([...wrapper.classList].includes("loading")) {
wrapper.classList.add("restore");
} else {
wrapper.classList.remove("restore");
}
wrapper.classList.toggle("loading");
};
.wrapper {
position: fixed;
top: 0;
left: 0;
width: 100%;
height: 100%;
}
.wrapper>div {
color: white;
display: flex;
align-items: center;
justify-content: center;
width: 100%;
height: 100%;
background: blue;
animation: none;
transform: scale(1);
transition: transform 500ms ease-out;
}
.wrapper.restore>div {
animation: restore 500ms ease-out;
}
.wrapper.loading>div {
transform: scale(0.2, 0.002);
animation: loading 1000ms 500ms ease-out infinite;
}
#keyframes restore {
0% {
transform: scale(0.2, 0.002);
}
100% {
transform: scale(1);
}
}
#keyframes loading {
0% {
transform: scale(0.2, 0.002)
}
50% {
transform: scale(0.5, 0.002)
}
100% {
transform: scale(0.2, 0.002)
}
}
<div class="wrapper">
<div>click me</div>
</div>
You can use animation iteration count property:
div {
animation-iteration-count: 2;
}
or use fill mode to freeze the animation at the end:
-webkit-animation-fill-mode: forwards;
I have html like this:
<div class="projectThumb">
<div class="textContainer">
<h1>Header1</h1>
<h2>▪ Header2a ▪ Header2b ▪</h2>
</div>
<a class="project1 video" href="https://player.vimeo.com/video/xxxxxx?transparent=0"><img src="Thumbnails/project1.png"></a>
</div>
Clicking the <a> tags with class="video" trigger a JS plugin that opens a video player within the page.
My CSS looks like this:
.projectThumb img {
width: 100%;
height: 100%;
object-fit: cover;
-webkit-transform: scaleY(1);
-moz-transform: scaleY(1);
-o-transform: scaleY(1);
-ms-transform: scaleY(1);
transform: scaleY(1);
-webkit-transition: all 0.3s ease-in-out;
-moz-transition: all 0.3s ease-in-out;
-o-transition: all 0.3s ease-in-out;
-ms-transition: all 0.3s ease-in-out;
transition: all 0.3s ease-in-out;
}
.projectThumb img:hover {
-ms-filter: "progid: DXImageTransform.Microsoft.Alpha(Opacity=0.2)";
filter: alpha(opacity=0.2);
opacity: 0.2;
}
When you hover over the <img> within the <a> (which takes up the whole projectThumb), the <img> opacity decreases revealing the text, but the image still bleeds through the text because the image is still on top of it. Is there a way to change the z-index of one of the elements to avoid having it bleed through? I've tried adding the following to CSS:
.projectThumb a:hover {
z-index: -999;
}
I've also tried adding z-index to .projectThumb img:hover like this:
.projectThumb img:hover {
-ms-filter: "progid: DXImageTransform.Microsoft.Alpha(Opacity=0.2)";
filter: alpha(opacity=0.2);
opacity: 0.2;
z-index: -999;
}
Neither work. I can bring the text to the front by setting the z-index of .textContainer h1, .textContainer h2, .textContainer h3, which does bring the text to the front, but I don't know how to trigger that on projectThumb img:hover so that it's only on top of the image on hover. I'd also like the entire <div> to remain clickable, even the text portion. When I bring the text to the front using z-index, the text area isn't clickable because it's on top of the <a>.
Not sure if its anywhere else in the CSS but I don't see any positioning.
In order for z-indexing to work you need to have some sort of position set.
Add position: relative to any of the classes you want to apply z-indexing to.
.projectThumb a, .projectThumb img {
position: relative;
}
If you really want to use z-index for that, you may use variables:
:root {
--thumbIndex: 0;
}
.projectThumb {
z-index: var(--thumbIndex);
}
a:hover {
--thumbIndex: -999;
}
I think thou, better idea will be to use the display property instead.
The problem I have is that when I set a:
.banner-division2 h2:hover {
-webkit-transition: 0.6 ease;
transition: 1s ease;
-webkit-transform: scale(1.2);
transform: scale(1.2);
color: #00C8BD;
}
It will only transition for the first part of the hover. In other words, once the mouse has exited the "hover" area, it will automatically go back to it's original form - however, I want it to transition ease back into it's original form (it isn't doing this).
Many thanks.
You need to put the transition property on the element you want the effect, not on the :hover.
Like this
h2 {
color: blue;
transition: 1s ease;
}
h2:hover {
color: red;
}
If this not work , try to add the value all on the transition property
You have defined the transition for the :hover state only. When not in :hover, no transition is defined - and ofc, none does happen. So split your rule:
.banner-division2 h2 {
-webkit-transition: all 1s ease;
transition: all 1s ease;
}
.banner-division2 h2:hover {
-webkit-transform: scale(1.2);
transform: scale(1.2);
color: #00C8BD;
}
This way, the transition targets your h2, not only your h2:hover.
I have an over hover animation glitch. When you're near the bottom of the item, it jumps, uncontrollably, is there any fix?
Sample image :
.btn:hover{
background-color: #2795de;
-moz-transform: translate(0, -1.3em);
-o-transform: translate(0, -1.3em);
-webkit-transform: translate(0, -1.3em);
}
Just set transition on .btn
.btn{
-moz-transition: all 2s ease;
-o-transition: all 2s ease;
-webkit-transition: all 2s ease;
}
.btn:hover{
background-color:#2795de;
-moz-transform:translate(0,-1.3em);
-o-transform:translate(0,-1.3em);
-webkit-transform:translate(0,-1.3em);
}
DEMO
.btn{
width:200px;
height:200px;
border-radius:4px;
background: red;
-moz-transition: all 2s ease;
-o-transition: all 2s ease;
-webkit-transition: all 2s ease;
}
.btn:hover{
background-color:#2795de;
-moz-transform:translate(0,-1.3em);
-o-transform:translate(0,-1.3em);
-webkit-transform:translate(0,-1.3em);
}
<div class=btn > HOVER ME </div>
The jump is being caused by the translate property in your CSS definitions.
If the jump is unintended, you can simply remove it from your CSS definition :
.btn:hover{
background-color:#2795de;
/* -moz-transform:translate(0,-1.3em);
-o-transform:translate(0,-1.3em);
-webkit-transform:translate(0,-1.3em); */
}
Or you can split the css into two parts :
.btn{
-moz-transform:translate(0,-1.3em);
-o-transform:translate(0,-1.3em);
-webkit-transform:translate(0,-1.3em);
}
.btn:hover {
background-color:#2795de;
}
remove your btn.hover and write only btn because hover is take event when your mouse cuser comes up on your button(.btn). so remove it.
and write
`.btn{
background-color:#2795de;
-moz-transform:translate(0,-1.3em);
-o-transform:translate(0,-1.3em);
-webkit-transform:translate(0,-1.3em);
}`
Basically your button is only going up on :hover but the distance that it goes up puts your button out of :hover state and it goes down. When it goes down it goes under the cursor again and goes into :hover state.
depending on what you want to achieve but instead of actually moving your button up on hover just change the background-color of it. You'll find people will be unable to actually click on it. Or just add a large padding-bottom so when button goes up the cursor still stays in :hover state.
There is example of animation:
.b-ball_bounce {transform-origin: top;}
#-webkit-keyframes ball_animation {
20% {transform: rotate(-9deg);}
40% {transform: rotate(6deg);}
60% {transform: rotate(-3deg);}
80% {transform: rotate(1.5deg);}
100% {transform: rotate(0deg);}
}
.b-ball_bounce:hover {
-webkit-animation: ball_animation 1.5s;
animation-iteration-count: 1;
}
When mouse hover an element animation start. But when mouse leave, animation stops immediately. But I want to finish animation after mouse leave.
This is example with help of JavaScript: http://codepen.io/Profesor08/pen/pvbzjX
And I want to do the same with pure CSS3, there is how it looks now: http://codepen.io/Profesor08/pen/WbxeoW
You can do a lot of stuff with transition:
#some-div {
background-color: rgba(100,100,0,0.2);
transition: background-color 0.5s ease;
}
#some-div:hover { background-color: rgba(100,0,0,0.7); }
Look at the JSfiddle or look here for more
CSS might help in some cases but not all, below is the code that will animate letter spacing on both hover and after hover.
h1
{
-webkit-transition:all 0.3s ease;
}
h1:hover
{
-webkit-transition:all 0.3s ease;
letter-spacing:3px;
}
<body>
<h1>Hello</h1>
</body>
To achieve this we can use javascript to append the CSS class "onMouseEnter" and remove the class "onAnimationEnd" and completly remove the :hover tag from our css.
React example:
onMouseEnter={(e) => e.currentTarget.classList.add('bounce') }
onAnimationEnd={(e) => e.currentTarget.classList.remove('bounce')}
Working Example: https://codepen.io/jamesprenticez/pen/jOpQvPP