IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

JavaScript Discussion :

Manipulation des animations CSS


Sujet :

JavaScript

  1. #1
    Membre éclairé Avatar de tribaleur
    Profil pro
    Développeur informatique
    Inscrit en
    Mai 2006
    Messages
    401
    Détails du profil
    Informations personnelles :
    Âge : 39
    Localisation : France, Haute Savoie (Rhône Alpes)

    Informations professionnelles :
    Activité : Développeur informatique

    Informations forums :
    Inscription : Mai 2006
    Messages : 401
    Par défaut Manipulation des animations CSS
    Bonjour.

    Je débute en Javascript/CSS/PHP et je rencontre des soucis aux niveaux des animations CSS3.
    J'ai créé une fonction qui permet d'affiché un élément en modifiant son display. Mais avant d'afficher l'élément je joue une petite animation de FadeIn pour que l'élément s'affiche progressivement. L'animation est susceptible d'être joué plusieurs fois (sur le même élément) en alternance avec une fonction de FadeOut => display="none".
    Ma fonction fonctionne (sauf sur IE) ... MAIS soulève des interrogations (voir à la fin du message) concernant la gestion des animations.
    Voici ma fonction Javascript:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    // Affiche l'élément passé en paramètre avec par défaut le display à "block"
    function show(ElementID){
    	var element = document.getElementById(ElementID); // récupère l'élément avec son ID
     
    	element.classList.remove("CFadeIn"); //Enlève la classe de FadeIn si l'élément l'avait déjà
    	element.classList.remove("CFadeOut"); //Enlève la classe de FadeOut si l'élément l'avait déjà
    	element.classList.add("CFadeIn"); //Ajoute la classe  FadeIn à l'élément
     
    	element.style.display=DefaultElementDisplay;// On affiche l'élément avant l'animation sinon l'élément est caché durant l'animation et n'apparait qu'à la fin.
     
    	//On affiche l'élément A LA FIN de l'animation de FadeIn
    	element.addEventListener('webkitAnimationEnd', function(EventShowSafariEtChrome) {element.style.display="block";}, false);//"webkitAnimationEnd" => majuscule très importantes
    	element.addEventListener('animationend', function(EventShowIEetFirefox) {element.style.display="block";}, false);
     
    /* --------- Ceci est le code de ma fonction de FadeOut qui sera joué en alternance avec la fonction ci-dessus ----- 
    // masque l'élément passé en paramètre
    function hide(ElementID){
    	var element = document.getElementById(ElementID);
    	element.classList.remove("CFadeIn");
    	element.classList.remove("CFadeOut");	
    	element.classList.add("CFadeOut");
    	//Quand l'animation de fading est fini on cache l'élément
    	element.addEventListener('webkitAnimationEnd', function(EventHideSafariEtChrome) {element.style.display ="none";}, false);//"webkitAnimationEnd" => majuscules très importantes
    	element.addEventListener('animationend', function(EventHideIEetFirefox) {element.style.display="none";}, false);
    } */
     
    }
    Voici l'animation en CSS :
    Code css : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    .CFadeIn {
    	-webkit-animation : FadeIn 0.2s  ;
    	animation : FadeIn 0.2s  ;
     
    }
    .CFadeOut {
    	-webkit-animation : FadeOut 0.2s ;
    	animation : FadeOut 0.2s  ;
    }
     
    /* ------------------ ANIMATION CSS3 -------------------- */
    @-webkit-keyframes FadeIn {
      0%   { opacity: 0.0; }
      50%  { opacity: 0.5; }
      100% { opacity: 1.0; }
    }
    @keyframes FadeIn {
      0%   { opacity: 0.0; }
      50%  { opacity: 0.5; }
      100% { opacity: 1.0; }
    }
     
    @-webkit-keyframes FadeOut {
      0%   { opacity: 1.0; }
      50%  { opacity: 0.5; }
      100% { opacity: 0.0; }
    }
    @keyframes FadeOut {
      0%   { opacity: 1.0; }
      50%  { opacity: 0.5; }
      100% { opacity: 0.0; }
    }

    Mes interrogations :
    -Dans ma fonction il me semblait plus logique de ne pas afficher l'élément avant l'animation et de modifier l'affichage au début de l'animation :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    //element.style.display=DefaultElementDisplay; => On supprime cette ligne
     
    	//On affiche l'élément AU DEBUT de l'animation de FadeIn
    	element.addEventListener('webkitAnimationStart', function(EventShowSafariEtChrome) {element.style.display="block";}, false);
    	element.addEventListener('animationstart', function(EventShowIEetFirefox) {element.style.display="block";}, false);
    Mais ce code ne fonctionne que la première fois que l'animation est joué. Si je re-cache l'élément avec la fonction de FadeOut ... puis le ré-affiche de nouveau avec la FadeIn ... l'animation FadeIn est rejoué à moitié (le display deviens "block" un cours instant), puis l'animation FadeOut est rejoué ( ... je l'appel nul part!! vérifié et revérifié!! sure à 100%) et pour finir l'élément redeviens display="none". Après plus rien ne ce passe sur cet élément. Ça fait exactement la même chose pour les autres éléments.

    Pour information j'ai un bouton "afficher" qui appel la fonction "show" sur un <div>. J'ai un autre bouton "cacher" qui appel la fonction "hide" sur le même div.

    Est-ce que quelqu'un peut expliquer ce comportement qui me parait bizarre sur le "animationstart".

    -Après plusieurs essais sur IE11 avec la première fonction que je vous ai donné ... il ce trouve que la div animé par le FadeIn clignote au deuxième lancement (FadeIn => FadeOut => FadeIn => clignote) ... je n'ai pas encore trouvé de solutions. Des idées?


    Merci d'avance.

    Si vous avez des questions je suis ouvert.
    Et désolé pour les fautes d’orthographes/conjugaison ... je sais que j'en fait énormément malgré mes relectures.

    *** EDIT *** : ajout du résultat des tests sur IE avec la première fonction que j'ai déclaré.

  2. #2
    Rédacteur/Modérateur

    Avatar de SylvainPV
    Profil pro
    Inscrit en
    Novembre 2012
    Messages
    3 375
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2012
    Messages : 3 375
    Par défaut
    Le display doit être changé juste avant le début de l'animation, et non juste après comme tu voudrais le faire avec un callback sur animationstart.

    Et je ne comprends pas cette partie :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    //On affiche l'élément A LA FIN de l'animation de FadeIn
    element.addEventListener('webkitAnimationEnd', function(EventShowSafariEtChrome) {element.style.display="block";}, false);//"webkitAnimationEnd" => majuscule très importantes
    element.addEventListener('animationend', function(EventShowIEetFirefox) {element.style.display="block";}, false);
    Si c'est un fadeIn, il faut afficher l'élément dès le début de l'animation. C'est justement ce que tu dis avec le commentaire au-dessus :
    // On affiche l'élément avant l'animation sinon l'élément est caché durant l'animation et n'apparait qu'à la fin.

  3. #3
    Membre éclairé Avatar de tribaleur
    Profil pro
    Développeur informatique
    Inscrit en
    Mai 2006
    Messages
    401
    Détails du profil
    Informations personnelles :
    Âge : 39
    Localisation : France, Haute Savoie (Rhône Alpes)

    Informations professionnelles :
    Activité : Développeur informatique

    Informations forums :
    Inscription : Mai 2006
    Messages : 401
    Par défaut
    Et je ne comprends pas cette partie :
    En fait si je n'ai pas ces deux lignes, l'animation ne ce lance correctement qu'au premier appel. Après elle se lance mais ne garde pas le display à "block" à la fin. Du coup le div re-disparait tout seul. Je me demande si ces lignes ne serai pas facultatives et si je n'ai pas un soucis dans mon animation en CSS.

    Le display doit être changé juste avant le début de l'animation, et non juste après comme tu voudrais le faire avec un callback sur animationstart.
    En fait je pensais que "animationstart" permettait de dire : "l'animation va commencer donc je fait '...' et je lance l'animation." Mais si je comprend bien c'est plutot "Pendant que l'animation commence ... ". Du coup je ne l'utilise pas.

    Si c'est un fadeIn, il faut afficher l'élément dès le début de l'animation. C'est justement ce que tu dis avec le commentaire au-dessus :
    Oui du coup c'est ce que je fait vus que l'utilisation de "animationstart" n'est pas bonne ici.

    En tous cas merci d'avoir répondus. As tu des idées concernant mon animation en CSS. Est-elle mal écrite? Ou sinon aurais tu un avis pour expliquer pourquoi ma fonction "Show" (comme elle est écrite actuellement) fait clignoter mon div à partir de la deuxième utilisation sur IE?

    Merci d'avance.

  4. #4
    Rédacteur/Modérateur

    Avatar de SylvainPV
    Profil pro
    Inscrit en
    Novembre 2012
    Messages
    3 375
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2012
    Messages : 3 375
    Par défaut
    Je ne sais pas, c'est très variable selon l’implémentation navigateur. Là, le fait de retirer et d'ajouter des classes consécutivement est sans doute mal géré par IE. Essaie de simplifier le changement comme ça :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    // Affiche l'élément passé en paramètre avec par défaut le display à "block"
    function show(ElementID){
        var element = document.getElementById(ElementID); // récupère l'élément avec son ID
        element.style.display="block";// On affiche l'élément avant l'animation sinon l'élément est caché durant l'animation et n'apparait qu'à la fin.
        element.className = "CFadeIn"; //Ajoute la classe  FadeIn à l'élément
    }
     
    // masque l'élément passé en paramètre
    function hide(ElementID){
        var element = document.getElementById(ElementID);
        element.className = "CFadeOut";
     
        //Quand l'animation de fading est fini on cache l'élément
        var onEnd = function(){ element.style.display="none"; }
        element.addEventListener('webkitAnimationEnd', onEnd, false);
        element.addEventListener('animationend', onEnd, false);
    }

  5. #5
    Membre éclairé Avatar de tribaleur
    Profil pro
    Développeur informatique
    Inscrit en
    Mai 2006
    Messages
    401
    Détails du profil
    Informations personnelles :
    Âge : 39
    Localisation : France, Haute Savoie (Rhône Alpes)

    Informations professionnelles :
    Activité : Développeur informatique

    Informations forums :
    Inscription : Mai 2006
    Messages : 401
    Par défaut
    Alors je te remercie car tu m'a mis sur la voix qui m'a permis de trouver une solution

    Je pense effectivement que le problème viens de la gestion des ajouts et suppression de classes. IE 11 doit mal les gérer.

    J'ai donc simplifié cet ajout/suppression de classe (ce qui en plus est plus propre ):
    -en ajoutant uniquement la nouvelle classe en début de fonction.
    -Puis en supprimant la classe à la fin de l'animation.

    De cette manière je suis sûr de ne pas avoir l'animation en boucle. Et je n'ai pas à supprimer les classes FadeIn et FadeOut quand il n'y a pas lieu de le faire.
    C'est donc plus propre et surtout ça FONCTIONNE!!! (testé sous Opéra/IE11/Firefox/Chrome ... tous mis à jour)

    Je met le code pour ceux que ça intéresse :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    // Affiche l'élément passé en paramètre avec par défaut le display à "block"
    function show(ElementID){
    	var element = document.getElementById(ElementID); // récupère l'élément avec son ID
     
            // On affiche l'élément avant l'animation sinon l'élément est caché durant l'animation.
    	element.style.display="block";
     
            //Ajoute la classe  FadeIn à l'élément => ça lance l'animation!!
    	element.classList.add("CFadeIn"); 
     
     
    	//Quand l'animation est FINIE, on re-confirme le display (pour que l'élément ne disparaisse pas à la fin de l'animation). 
            //On supprime la classe de l'animation pour être sure qu'elle ne boucle pas.
    	element.addEventListener('webkitAnimationEnd', function(EventShowSafariEtChrome) {element.style.display="block";
                                                                                              element.classList.remove("CFadeIn");}, false);//"webkitAnimationEnd" => majuscule très importantes
    	element.addEventListener('animationend', function(EventShowIEetFirefox) {element.style.display="block";
                                                                                     element.classList.remove("CFadeIn");}, false);
     
    /* --------- Ceci est le code de ma fonction de FadeOut qui sera joué en alternance avec la fonction ci-dessus ----- 
    // masque l'élément passé en paramètre
    function hide(ElementID){
    	var element = document.getElementById(ElementID);
     
            //Ajout de la classe FadeOut à l'élément => ça lance l'animation!!!
    	element.classList.add("CFadeOut");
     
    	//Quand l'animation est FINIE, on re-confirme le display (pour que l'élément ne ré-apparaisse pas à la fin de l'animation).
            //On supprime la classe de l'animation pour être sure qu'elle ne boucle pas.
    	element.addEventListener('webkitAnimationEnd', function(EventHideSafariEtChrome) {element.style.display ="none";
                                                                                              element.classList.remove("CFadeOut");}, false);//"webkitAnimationEnd" => majuscules très importantes
    	element.addEventListener('animationend', function(EventHideIEetFirefox) {element.style.display="none";
                                                                                     element.classList.remove("CFadeOut");}, false);
    } */
     
    }
    Une solution alternative aux animation est d'utiliser des "transitions" (sur l'opacity) à la place des "animations", en modifiant le display et l'opacity dans le Javascript.
    => Ça fonctionne sur la FadeOut car on modifie le display à la fin de la transition (transitionend/webkitTransitionEnd).
    => Ça ne fonctionne PAS sur le FadeIn car apparemment la modification du display désactive les transitions sur ce même élément.

    Il faut donc utiliser les propriété visibility:"hidden/visible" à la place du display. Mais du coup il faut faire attention à la place que prend l'objet une fois masqué. (La propriété visibility ne fait que cacher l'élément ... mais ce dernier prend toujours la même place dans la page ... je vous laisse voir la différence entre Display et Visibility )


    Dans tous les cas merci à toi pour m'avoir mis sur la bonne piste et pour avoir essayé de m'aider!!
    Avec de la chance ça aidera d'autres personnes ... car j'ai l'impression qu'apparemment l'utilisation des animation en CSS3 est un sujet plutôt flou pour beaucoup de gens


+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. [Autre] CSS Shaders : le futur standard qui repousse les limites des animations CSS3
    Par Idelways dans le forum Publications (X)HTML et CSS
    Réponses: 8
    Dernier message: 14/10/2011, 17h18
  2. Réponses: 8
    Dernier message: 14/10/2011, 17h18
  3. Réponses: 0
    Dernier message: 05/10/2011, 18h53
  4. Manipulation des handle contexte
    Par rockbiker dans le forum DirectX
    Réponses: 1
    Dernier message: 09/05/2003, 18h51
  5. Fonctions de manipulation des chaines et des dates
    Par Fares BELHAOUAS dans le forum Débuter
    Réponses: 3
    Dernier message: 09/11/2002, 22h43

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo