Animación CSS3: pantalla + opacidad

101

Tengo un problema con una animación CSS3.

.child {
    opacity: 0;
    display: none;

    -webkit-transition: opacity 0.5s ease-in-out;
    -moz-transition: opacity 0.5s ease-in-out;
    transition: opacity 0.5s ease-in-out;
}

.parent:hover .child {
    opacity: 0.9;
    display: block;
}

Este código solo funciona si elimino el cambio de display.

Quiero cambiar la pantalla justo después del desplazamiento, pero la opacidad debe cambiarse usando la transición.

Alexis Delrieu
fuente
2
Si CSS no funciona como sugirieron los demás, aquí hay un código Javascript muy simple para desvanecer.
Abhranil Das

Respuestas:

118

Según la respuesta de Michaels, este es el código CSS real que se debe usar

.parent:hover .child
{
    display: block;

    -webkit-animation: fadeInFromNone 0.5s ease-out;
    -moz-animation: fadeInFromNone 0.5s ease-out;
    -o-animation: fadeInFromNone 0.5s ease-out;
    animation: fadeInFromNone 0.5s ease-out;
}

@-webkit-keyframes fadeInFromNone {
    0% {
        display: none;
        opacity: 0;
    }

    1% {
        display: block;
        opacity: 0;
    }

    100% {
        display: block;
        opacity: 1;
    }
}

@-moz-keyframes fadeInFromNone {
    0% {
        display: none;
        opacity: 0;
    }

    1% {
        display: block;
        opacity: 0;
    }

    100% {
        display: block;
        opacity: 1;
    }
}

@-o-keyframes fadeInFromNone {
    0% {
        display: none;
        opacity: 0;
    }

    1% {
        display: block;
        opacity: 0;
    }

    100% {
        display: block;
        opacity: 1;
    }
}

@keyframes fadeInFromNone {
    0% {
        display: none;
        opacity: 0;
    }

    1% {
        display: block;
        opacity: 0;
    }

    100% {
        display: block;
        opacity: 1;
    }
}
Chris
fuente
1
para admitir todos los navegadores ..?
david_adler
CSS3 no es compatible con todos los navegadores. Si desea extender, simplemente agregue los prefijos correctos
Chris
17
¿Qué pasa cuando se desplaza hacia afuera, cómo implementar fadeOutToNone?
Verde
4
Como puede usar fracciones de un porcentaje, es una mejor práctica usar algo como 0.001% en lugar de 1% porque minimiza el retraso para "comenzar", lo que puede hacerse evidente con duraciones de animación más largas
Zach Saucier
1
La directiva -o-keyframes es realmente inútil porque la primera versión de Opera que soporta animaciones ya estaba basada en webkit.
Rico Ocepek
43

Puedes hacerlo con animaciones CSS:

0% display:none ; opacity: 0;
1% display: block ; opacity: 0;
100% display: block ; opacity: 1;
Michael Mullany
fuente
Buena idea, logré seguir mostrando mi elemento durante el desplazamiento con el modo animation-fill-mode, pero luego el mouseout, el elemento desaparece.
Alexis Delrieu
2
puede usar el modo de relleno: adelante para persistir los cambios después de que finalice la animación.
Michael Mullany
42

Si es posible, utilice visibility lugar dedisplay

Por ejemplo:

.child {
    visibility: hidden;
    opacity: 0;
    transition: opacity 0.3s, visibility 0.3s;
}

.parent:hover .child {
    visibility: visible;
    opacity: 1;
    transition: opacity 0.3s, visibility 0.3s;
}
tomas.satinsky
fuente
24
El problema con la propiedad de visibilidad es que esto no oculta el elemento, solo lo hace invisible. Por lo que todavía ocupará espacio.
Samuel
6
No solo invisible, sino también transparente a los eventos (clics, etc.). No cambiar la visualización significa no volver a procesar el documento, lo cual es bueno. La mayoría de los elementos que deberían aparecer / desaparecer gradualmente a través de la opacidad probablemente deberían tener una posición fija o absoluta de todos modos.
Rasmus Kaj
13

Esta solución funciona:

  1. definir un "fotograma clave":

    @-webkit-keyframes fadeIn { 
      0% { opacity: 0; }
      20% { opacity: 0; }
      40% { opacity: 0.3; }
      60% { opacity: 0.5; }
      80% { opacity: 0.9; }
      100% { opacity: 1; }
    }
    
    @keyframes fadeIn {
      0% { opacity: 0; }
      20% { opacity: 0; }
      40% { opacity: 0.3; }
      60% { opacity: 0.5; }
      80% { opacity: 0.9; }
      100% { opacity: 1; }
    }
  2. Utilice este "fotograma clave" en "hover":

    div a span { 
      display: none;
    }
    
    div a:hover span {
      display: block;
    
      -webkit-animation-name: fadeIn;
      -webkit-animation-duration: 1s;
      animation-name: fadeIn;
      animation-duration: 1s;
    }
Hermann Schwarz
fuente
9

Usé esto para lograrlo. Se desvanecen al pasar el mouse, pero no ocupan espacio cuando se ocultan, ¡perfecto!

.child {
    height: 0px;
    opacity: 0;
    visibility: hidden;
    transition: all .5s ease-in-out;
}

.parent:hover .child {
    height: auto;
    opacity: 1;
    visibility: visible;
}
Felixhirschfeld
fuente
6

Cambié un poco pero el resultado es hermoso.

.child {
    width: 0px;
    height: 0px;
    opacity: 0;
}

.parent:hover child {
    width: 150px;
    height: 300px;
    opacity: .9;
}

Gracias a todos.

Alexis Delrieu
fuente
4
Esto no funciona bien con los lectores de pantalla: seguirán leyendo el contenido.
ehdv
1
Puede agregar visibility: hidden;a .child / visibility:visible;al hover y esto debería solucionar el problema del lector de pantalla
csilk
6

Hay otro buen método para hacer esto usando eventos de puntero:

.child {
    opacity: 0;
    pointer-events: none;

    -webkit-transition: opacity 0.5s ease-in-out;
    -moz-transition: opacity 0.5s ease-in-out;
    transition: opacity 0.5s ease-in-out;
}

.parent:hover .child {
    opacity: 0.9;
    pointer-events: all;
}

Desafortunadamente, esto no es compatible con IE10 y versiones anteriores.

RafaelKr
fuente
4

Yo tuve el mismo problema. Intenté usar animaciones en lugar de transiciones, como sugirieron @MichaelMullany y @Chris, pero solo funcionó para navegadores webkit incluso si copiaba y pegaba con los prefijos "-moz" y "-o".

Pude solucionar el problema usando en visibilitylugar de display. Esto funciona para mí porque mi elemento hijo esposition: absolute , por lo que el flujo de documentos no se ve afectado. También podría funcionar para otros.

Así es como se vería el código original usando mi solución:

.child {
    position: absolute;
    opacity: 0;
    visibility: hidden;

    -webkit-transition: opacity 0.5s ease-in-out;
    -moz-transition: opacity 0.5s ease-in-out;
    transition: opacity 0.5s ease-in-out;
}

.parent:hover .child {
    position: relative;
    opacity: 0.9;
    visibility: visible;
}
Dave
fuente
Si volviera a colocar el cursor sobre el niño mientras se está animando fuera de la vista, volvería a aparecer ya que el elemento simplemente está oculto. Es bastante molesto si mueves el mouse por el lugar.
Adamj
4

Si está activando el cambio con JS, digamos al hacer clic, hay una buena solución.

Verá que el problema ocurre porque la animación se ignora en la pantalla: ningún elemento, pero el navegador aplica todos los cambios a la vez y el elemento nunca se muestra: bloque mientras no está animado al mismo tiempo.

El truco consiste en pedirle al navegador que renderice el fotograma después de cambiar la visibilidad, pero antes de activar la animación.

Aquí hay un ejemplo de JQuery:

    $('.child').css({"display":"block"});
    //now ask the browser what is the value of the display property
    $('.child').css("display"); //this will trigger the browser to apply the change. this costs one frame render
    //now a change to opacity will trigger the animation
    $('.child').css("opacity":100);
daniel.sedlacek
fuente
2
Esta pregunta no está etiquetada con JavaScript ni jQuery
j08691
Lo sé, lo escribí para explicar la razón por la que esto está sucediendo. Fue muy útil para mí cuando me enteré de esto y espero que también ayude a otros.
daniel.sedlacek
1
Por cierto, los valores de opacidad están entre 0 y 1
Amr
2

En elementos absolutos o fijos, también puede usar z-index:

.item {
    position: absolute;
    z-index: -100;
}

.item:hover {
    z-index: 100;
}

Otros elementos deberían tener un índice z entre -100 y 100 ahora.

Luca Steeb
fuente
Desafortunadamente, eso arruina el símbolo indicador de contraseña de KeePass en los type=passwordcampos. No es visible.
philk
1
¿Podemos dejar de usar números de índice z arbitrarios? Aquí: índice z: 1; vs z-index: -1 funcionará bien. Elegir números de índice Z enormes hace que las cosas sean inmanejables.
dudewad
2

Lo sé, esto no es realmente una solución para tu pregunta, porque pides

pantalla + opacidad

Mi enfoque resuelve una pregunta más general, pero tal vez este fue el problema de fondo que debería resolverse usando displayen combinación conopacity .

Mi deseo era sacar el Elemento del camino cuando no es visible. Esta solución hace exactamente eso: mueve el elemento fuera de la distancia, y esto se puede usar para la transición:

.child {
  left: -2000px;
  opacity: 0;
  visibility: hidden;
  transition: left 0s 0.8s, visibility 0s 0.8s, opacity 0.8s;
}

.parent:hover .child {
  left: 0;
  opacity: 1;
  visibility: visible;
  transition: left 0s, visibility 0s, opacity 0.8s;
}

Este código no contiene prefijos de navegador ni trucos de compatibilidad con versiones anteriores. Simplemente ilustra el concepto de cómo se aleja el elemento ya que ya no se necesita.

La parte interesante son las dos definiciones de transición diferentes. Cuando el puntero del mouse se desplaza sobre el .parentelemento, el .childelemento debe colocarse en su lugar inmediatamente y luego se cambiará la opacidad:

transition: left 0s, visibility 0s, opacity 0.8s;

Cuando no hay desplazamiento, o el puntero del mouse se movió fuera del elemento, uno tiene que esperar hasta que el cambio de opacidad haya terminado antes de que el elemento pueda moverse fuera de la pantalla:

transition: left 0s 0.8s, visibility 0s 0.8s, opacity 0.8s;

Alejar el objeto será una alternativa viable en el caso de que la configuración display:none no rompa el diseño.

Espero haber dado en el clavo con esta pregunta, aunque no la he respondido.

Hannes Morgenstern
fuente
Ese filtro de Microsoft ha quedado obsoleto desde IE9. ¿Alguna razón en particular por la que desea agregarlo a las respuestas en 2016?
TylerH
@TylerH A cuántos usuarios uno está dispuesto a llegar es una cuestión de gustos.
Hannes Morgenstern
Teniendo en cuenta que está obsoleto y que Microsoft ya no admite IE <11, el uso de esa propiedad es, en el mejor de los casos, de dudoso gusto.
TylerH
@TylerH Es común tener que adaptarse a los clientes que no pueden o no pueden actualizar a un navegador más nuevo. Tengo un banco muy conocido como cliente que todavía usa IE6 y se niega a actualizar por "razones".
Marcus Cunningham
@MarcusCunningham La pregunta está etiquetada con css3, lo que excluye el uso de IE6 (e IE7 e IE8) por completo. En el navegador más antiguo posible para el que OP podría haber estado escribiendo código, el filtro MS en esta respuesta estaba en desuso. Y para los futuros lectores, es aún más inútil ya que ni siquiera es compatible. No hay ningún argumento para incluirlo en una respuesta a esta pregunta. Sin embargo, es un punto discutible, ya que Hannes ya lo ha eliminado de su respuesta.
TylerH
1

Una cosa que hice fue establecer el margen del estado inicial en algo como "margin-left: -9999px" para que no aparezca en la pantalla, y luego restablecer "margin-left: 0" en el estado de desplazamiento. Manténgalo "display: block" en ese caso. Me hizo el truco :)

Editar: ¿Guardar el estado y no volver al estado de desplazamiento anterior? Ok, aquí necesitamos JS:

<style>
.hovered { 
    /* hover styles here */
}
</style>

<script type="text/javascript">
$('.link').hover(function() {
   var $link = $(this);
   if (!$link.hasclass('hovered')) { // check to see if the class was already given
        $(this).addClass('hovered');
   } 
});
</script>
Joshua
fuente
Buena idea, pero luego muevo el mouse, el elemento desaparece…
Alexis Delrieu
Alexis, ¿no es eso lo que quieres hacer? Hover significa SOLO cuando se desplaza con el mouse. Por favor aclare lo que está tratando de lograr.
Joshua
Si, lo siento. Quiero guardar el desvanecimiento en el mouseout.
Alexis Delrieu
Eso lo cambia todo. Casi. Básicamente, lo que desea es una función JS que detecte el estado de desplazamiento, como han indicado otros usuarios, y agregará ... bueno ... vea mi respuesta actualizada.
Joshua
1

Para tener animación en ambos sentidos onHoverIn / Out hice esta solución. Espero que ayude a alguien

@keyframes fadeOutFromBlock {
  0% {
    position: relative;
    opacity: 1;
    transform: translateX(0);
  }

  90% {
    position: relative;
    opacity: 0;
    transform: translateX(0);
  }

  100% {
    position: absolute;
    opacity: 0;
    transform: translateX(-999px);
  }
}

@keyframes fadeInFromNone {
  0% {
    position: absolute;
    opacity: 0;
    transform: translateX(-999px);
  }

  1% {
    position: relative;
    opacity: 0;
    transform: translateX(0);
  }

  100% {
    position: relative;
    opacity: 1;
    transform: translateX(0);
  }
}

.drafts-content {
  position: relative;
  opacity: 1;
  transform: translateX(0);
  animation: fadeInFromNone 1s ease-in;
  will-change: opacity, transform;

  &.hide-drafts {
    position: absolute;
    opacity: 0;
    transform: translateX(-999px);
    animation: fadeOutFromBlock 0.5s ease-out;
    will-change: opacity, transform;
  }
}
Nicolás
fuente
0

CÓMO ANIMAR LA OPACIDAD CON CSS:
este es mi código:
el código CSS

.item {   
    height:200px;
    width:200px;
    background:red;
    opacity:0;
    transition: opacity 1s ease-in-out;
}

.item:hover {
    opacity: 1;
}
code {
    background: linear-gradient(to right,#fce4ed,#ffe8cc);
}
<div class="item">

</div>
<p><code> move mouse over top of this text</code></p>

o consulte este archivo de demostración

function vote () {
var vote = getElementById ("yourOpinion")
if (this.workWithYou):
vote + = 1};
jajaja

zakizakibzr
fuente
1
No responde a la pregunta, ya que la displaypropiedad simplemente fue eliminada.
Brindis el
-4

display:no es transitable. Probablemente necesitará usar jQuery para hacer lo que quiera hacer.

Fantasma de Madara
fuente
3
Tienes que dejar de defender jQuery en todas partes, amigo.
Benjamin Gruenbaum
1
@BenjaminGruenbaum jQuery es un hombre increíble. Es genial y hace todas las cosas.
Madara's Ghost