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 :

Passer un bloc en display none au clic en dehors du bloc


Sujet :

JavaScript

  1. #1
    Membre habitué
    Profil pro
    Inscrit en
    Mai 2004
    Messages
    685
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2004
    Messages : 685
    Points : 132
    Points
    132
    Par défaut Passer un bloc en display none au clic en dehors du bloc
    Bonjour,

    J'ai un menu déroulant qui apparaît au survol de son titre, cela en css, un classique.

    Voir le codepen.

    Sur iPhone il est impossible de refermer le menu, la seule solution est de recharger la page.

    Sur Androïd, il suffit de retoucher "table d'orientation" ou de toucher n'importe quelle partie de la page en dehors du menu pour faire disparaître le menu.

    Sur grand écran il suffit bien sûr de déplacer le pointeur en dehors du menu pour qu'il disparaisse.

    Voyez-vous un moyen d'aider un peu les iPhone ?

    En css cela me semble impossible.

    On peut penser à un petit javascript qui demanderait de fermer table.ore pour tout contact en dehors du block.

    Si vous pouvez me donner les bases du code...

    Merci d'avance.

  2. #2
    Membre habitué
    Profil pro
    Inscrit en
    Mai 2004
    Messages
    685
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2004
    Messages : 685
    Points : 132
    Points
    132
    Par défaut
    Bonjour,

    Mon codepen a évolué, je gère désormais l'afficher-masquer du menu par clic sur le bouton.

    Par contre j'ai un problème pour retrouver ensuite le fonctionnement en css par hover.

    J'ai essayé :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    tableau.addEventListener ('MouseOut', function ()
    {
    tableau.style.display = 'none';
    }
    );
    Mais cela ne donne aucun résultat.

    Voyez-vous où est l'erreur ?

    Mon idée :

    On ouvre le menu par hover (css) ou click (javascript).

    On ferme le menu par click (javascript) ou sortie de pointeur du tableau (d'où le code ci-dessus mais qui ne marche pas).

    Une fois le menu fermé par javascript il doit pouvoir être réouvert par hover (css) comme au chargement de la page. Actuellement si j'ai ouvert par click je dois fermer par click et ensuite le css hover ne fonctionne plus.

    J'espère que c'est clair.

  3. #3
    Modérateur

    Avatar de NoSmoking
    Homme Profil pro
    Inscrit en
    Janvier 2011
    Messages
    17 056
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Isère (Rhône Alpes)

    Informations forums :
    Inscription : Janvier 2011
    Messages : 17 056
    Points : 44 575
    Points
    44 575
    Par défaut
    Bonjour,
    je n'adopterais pas cette stratégie et je passerais par l'« add/remove » d'une classe.

    Par exemple :
    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
    const bouton = document.querySelector("div.tab > button");
    const tableau = document.querySelector("table.ore");
    /*
    bouton.addEventListener("click", function () {
      if (tableau.style.display == "none") tableau.style.display = "block";
      else tableau.style.display = "none";
    });
    tableau.addEventListener("MouseOut", function () {
      tableau.style.display = "none";
    });
    /*--*/
    bouton.addEventListener("mouseover", function() {
      tableau.classList.add("open");
    });
    bouton.addEventListener("click", function(e) {
      e.stopPropagation();   // il ne faut pas que cela arrive au document, voir plus loin
      if (tableau.classList.contains("open")) {
        tableau.classList.remove("open");
      }
      else {
        tableau.classList.add("open");
      }
    });
    // Attention mouseleave et pas mouseout
    tableau.addEventListener("mouseleave", function() {
      tableau.classList.remove("open");
    });
    document.body.addEventListener("click", function() {
      tableau.classList.remove("open");
    });

  4. #4
    Membre habitué
    Profil pro
    Inscrit en
    Mai 2004
    Messages
    685
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2004
    Messages : 685
    Points : 132
    Points
    132
    Par défaut
    Bonjour NoSmoking,

    Merci pour ce code, je le teste pendant le week-end au plus tard mais je suis déjà sûr que c'est la bonne approche.

    Je vous tiens informés.

  5. #5
    Membre habitué
    Profil pro
    Inscrit en
    Mai 2004
    Messages
    685
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2004
    Messages : 685
    Points : 132
    Points
    132
    Par défaut
    Bonjour NoSmoking,

    Sur le codepen il me semble que ton code fait exactement ce qui est demandé.

    Sauf la dernière instruction, le clic dans body ne masque pas le menu.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    document.body.addEventListener("click", function() {
      tableau.classList.remove("open");
    });
    Tu survoles ou cliques sur le bouton, tu sors par la droite de façon à ne pas provoquer mouseleave sur le tableau, tu cliques dans le body et il ne se passe rien.
    Bug du codepen ou défaut du code ?

  6. #6
    Modérateur

    Avatar de NoSmoking
    Homme Profil pro
    Inscrit en
    Janvier 2011
    Messages
    17 056
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Isère (Rhône Alpes)

    Informations forums :
    Inscription : Janvier 2011
    Messages : 17 056
    Points : 44 575
    Points
    44 575
    Par défaut
    Bug du codepen ou défaut du code ?
    il suffit de mettre un
    Code css : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    body {
      height: 100vh;
    }
    par exemple pour que le <body> recouvre la totalité la fenêtre et soit donc cliquable.

  7. #7
    Membre habitué
    Profil pro
    Inscrit en
    Mai 2004
    Messages
    685
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2004
    Messages : 685
    Points : 132
    Points
    132
    Par défaut
    Bonjour NoSmoking,

    Cela parait probable, je teste ce soir.

    Je te tiens informé.

  8. #8
    Modérateur

    Avatar de NoSmoking
    Homme Profil pro
    Inscrit en
    Janvier 2011
    Messages
    17 056
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Isère (Rhône Alpes)

    Informations forums :
    Inscription : Janvier 2011
    Messages : 17 056
    Points : 44 575
    Points
    44 575
    Par défaut
    Pour visualiser les zones, ajoute ces lignes dans le CSS
    Code css : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    html {
      background-color: #DEF;
    }
    body {
      background-color: #FDE;
    }

  9. #9
    Membre habitué
    Profil pro
    Inscrit en
    Mai 2004
    Messages
    685
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2004
    Messages : 685
    Points : 132
    Points
    132
    Par défaut
    Oui, ou une bordure sur body.

    Encore merci.

  10. #10
    Membre habitué
    Profil pro
    Inscrit en
    Mai 2004
    Messages
    685
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2004
    Messages : 685
    Points : 132
    Points
    132
    Par défaut
    Bonjour,

    Le nouveau codepen fonctionne très bien.

    Juste 2 questions :

    1)

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    bouton.addEventListener("click", function(e) {
      e.stopPropagation();   // il ne faut pas que cela arrive au document, voir plus loin
      if (tableau.classList.contains("open")) {
        tableau.classList.remove("open");
      }
      else {
        tableau.classList.add("open");
      }
    });
    e.stopPropagation(); // il ne faut pas que cela arrive au document, voir plus loin

    Je ne comprends pas du tout à quoi e.stopPropagation(); sert...
    Je vois que c'est indispensable mais je ne comprends pas pourquoi.

    2) Dans le code css :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    /*
    div.tab button:hover+table {display: block}
    */
    Si j'active cette déclaration elle plante le javascript.

    Pas moyen de gérer l'effet de survol par le css et l'effet de click par le javascript ?
    Si sur un poste javascript est désactivé le css est un secours pour voir le menu.

  11. #11
    Modérateur

    Avatar de NoSmoking
    Homme Profil pro
    Inscrit en
    Janvier 2011
    Messages
    17 056
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Isère (Rhône Alpes)

    Informations forums :
    Inscription : Janvier 2011
    Messages : 17 056
    Points : 44 575
    Points
    44 575
    Par défaut
    Je ne comprends pas du tout à quoi e.stopPropagation(); sert...
    lorsque tu vas cliquer sur le bouton le document recevra également le clic, c'est la propagation, donc il faut l'éviter sinon tu annulera systématiquement ce clic sur le bouton et inversement.

    Ressources :



    Pas moyen de gérer l'effet de survol par le css et l'effet de click par le javascript ?
    Si sur un poste JavaScript est désactivé le css est un secours pour voir le menu.
    c'est l'un ou l'autre, les eux en même temps faisant souvent mauvais ménage.

    Dans le cas où le JavaScript est désactivé il te faut activer le CSS de « secours » en vérifiant par exemple une classe mise sur le body par le JavaScript.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    /* ajout class "js" via JavaScript */
    document.body.classList.add("js");
    Si le JavaScript est désactivé le <body> n'aura pas la classe "js". , dans ce cas le code suivant sera pris en compte :
    Code css : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    body:not(.js) div.tab button:hover + table {
      display: block;
    }
    body:not(.js) table.ore:hover {
      display: block;
    }

  12. #12
    Membre habitué
    Profil pro
    Inscrit en
    Mai 2004
    Messages
    685
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2004
    Messages : 685
    Points : 132
    Points
    132
    Par défaut
    Bonjour NoSmoking,

    Merci de ton suivi.

    Pour e.stopPropagation(); j'ai compris.

    Pour le reste je fais les tests dès que je peux, ce week-end au plus tard.

    J'ai découvert un problème avec les téléphones sous certaines versions d'Android.
    Il faut sur le bouton un clic long ou un double clic pour que cela fonctionne, ennuyeux...

    Je continue les tests avec de petites variantes.

    Je te tiens informé.

  13. #13
    Membre habitué
    Profil pro
    Inscrit en
    Mai 2004
    Messages
    685
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2004
    Messages : 685
    Points : 132
    Points
    132
    Par défaut
    Bonjour NoSmoking,

    j'ai bien intégré tous les éléments de ta dernière réponse, pas de souci.

    Je bute toujours sur cette histoire de clic long avec Android, je pense que c'est complétement indépendant du script.

    Je te tiens informé.

  14. #14
    Membre habitué
    Profil pro
    Inscrit en
    Mai 2004
    Messages
    685
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2004
    Messages : 685
    Points : 132
    Points
    132
    Par défaut
    Bonjour,

    Je ne comprends pas ce problème de clic long avec Android.

    Je récapitule :

    Déclenchement par le css :hover
    Android ouvre le menu, il suffit de cliquer n'importe-où ailleurs que sur le menu pour le fermer. A noter que rien ne demande à Android de fermer de cette manière mais c'est parfait.
    Iphone ouvre mais ne ferme pas.

    Déclenchement par le javascript du codepen.
    Double clic ou clic long avec Android.
    Fonctionnement conforme au script avec iPhone.

    Avez-vous connaissance de ce type de problème avec Android ?

  15. #15
    Modérateur

    Avatar de NoSmoking
    Homme Profil pro
    Inscrit en
    Janvier 2011
    Messages
    17 056
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Isère (Rhône Alpes)

    Informations forums :
    Inscription : Janvier 2011
    Messages : 17 056
    Points : 44 575
    Points
    44 575
    Par défaut
    Je ne comprends pas ce problème de clic long avec Android.
    A voir peut-être le paramétrage pour prise en compte afin de différencier les différentes actions.

    Avez-vous connaissance de ce type de problème avec Android ?
    ton fichier présente-t-il les données minimum comme un <!DOCTYPE html> ?

  16. #16
    Membre habitué
    Profil pro
    Inscrit en
    Mai 2004
    Messages
    685
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2004
    Messages : 685
    Points : 132
    Points
    132
    Par défaut
    Bonjour NoSmoking,

    Merci de ton suivi.

    Citation Envoyé par NoSmoking
    A voir peut-être le paramétrage pour prise en compte afin de différencier les différentes actions.
    Je ne comprends pas de quel paramétrage tu parles, celui d'Android ?

    Pour ta deuxième question le fichier est parfait, 0 erreur ou warning avec le validateur W3C.

  17. #17
    Modérateur

    Avatar de NoSmoking
    Homme Profil pro
    Inscrit en
    Janvier 2011
    Messages
    17 056
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Isère (Rhône Alpes)

    Informations forums :
    Inscription : Janvier 2011
    Messages : 17 056
    Points : 44 575
    Points
    44 575
    Par défaut
    je te l'accorde la phase n'est pas franchement clair, je parlais du réglage du délai de pression, court, moyen ou long.

    L'autre approche, que tu pourrais avoir, est d'utiliser également les événements liés aux tactiles, les « touch events » et notamment l'événement touchstart.

  18. #18
    Membre habitué
    Profil pro
    Inscrit en
    Mai 2004
    Messages
    685
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2004
    Messages : 685
    Points : 132
    Points
    132
    Par défaut
    Bonjour NoSmoking,

    Je n'imagine pas une personne changer les réglages de son portable pour s'adapter à mon site...

    L'idée de l'approche avec avec touch events semble intéressante, j'avoue que ne connaissais pas, je vais y réfléchir, sans doute pendant le week-end.

    Est-ce que cela se marie avec un code css responsive avec structure html unique et media-queries ?
    Je veux dire qu'il n'y a pas de site dédié aux petits écrans.

  19. #19
    Membre habitué
    Profil pro
    Inscrit en
    Mai 2004
    Messages
    685
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2004
    Messages : 685
    Points : 132
    Points
    132
    Par défaut
    Bonjour,

    J'ai fait un essai du code sur un autre téléphone Android et cette fois cela fonctionne correctement, je veux lire avec clic court.
    Peut-être l'Android qui nécessite le double-clic est un peu bogué.
    Je n'ai pas 50 téléphones sous la main, connaissez-vous pour Android un outil de test ?

    Autrement, pour revenir au codepen, question à NoSmoking : en quoi ta stratégie d'ajout de classe est-elle supérieure à celle de changement du display dans la première version ?
    Avec le changement de display je n'ai rien à changer dans le css d'origine.
    Ce n'est pas que ce soit compliqué de changer le css mais pourquoi passer par une classe alors que le but est de changer le display ?

  20. #20
    Modérateur

    Avatar de NoSmoking
    Homme Profil pro
    Inscrit en
    Janvier 2011
    Messages
    17 056
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Isère (Rhône Alpes)

    Informations forums :
    Inscription : Janvier 2011
    Messages : 17 056
    Points : 44 575
    Points
    44 575
    Par défaut
    question à NoSmoking : en quoi ta stratégie d'ajout de classe est-elle supérieure à celle de changement du display dans la première version ?
    je n'ai pas dit qu'elle était supérieur, je pense simplement qu'elle est plus souple dans le sens où on ne mélange pas le CSS et le JavaScript.

    Si demain tu souhaites ajouter un effet d'ouverture à ton élément tu fais comment ?

    D'autre par le swap display:none/display:block peut poser soucis si il est appliqué à des éléments qui ne sont pas de type bloc.

Discussions similaires

  1. Réponses: 2
    Dernier message: 30/03/2021, 22h02
  2. Problème de decalage à l'apparition d'un bloc display:none
    Par programmeur400 dans le forum Mise en page CSS
    Réponses: 4
    Dernier message: 17/11/2011, 15h37
  3. display:none vers display:bloc
    Par afif_2010 dans le forum Mise en page CSS
    Réponses: 2
    Dernier message: 16/04/2010, 15h19
  4. Faire fonctionner le onfocus sur un élément en display:none
    Par eXiaNazaire dans le forum Général JavaScript
    Réponses: 5
    Dernier message: 27/04/2006, 11h10
  5. [W3C] Problème avec la balise div et le style "display:none&a
    Par Golork dans le forum Balisage (X)HTML et validation W3C
    Réponses: 8
    Dernier message: 14/11/2005, 20h30

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