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 :

Traduire code jQuery en JS pur (pour navbar multi-level - Bootstrap 5)


Sujet :

JavaScript

  1. #1
    Inactif  
    Homme Profil pro
    Webmaster
    Inscrit en
    Juin 2021
    Messages
    645
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 57
    Localisation : France, Pas de Calais (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Webmaster
    Secteur : Arts - Culture

    Informations forums :
    Inscription : Juin 2021
    Messages : 645
    Points : 1 280
    Points
    1 280
    Par défaut Traduire code jQuery en JS pur (pour navbar multi-level - Bootstrap 5)
    Bonjour,

    j'essaie - vainement - de traduire un script jQuery en JS pur, pour un menu Bootstrap 5 multi-level.

    voir :

    Le script jQuery semble bien fonctionner
    Le script JS... non :
    Je n'arrive pas à refermer l'autre sous-menu (ils se superposent)
    Nom : bs5-nav-multi-level.jpg
Affichages : 177
Taille : 17,7 Ko

    jQuery :
    Code js : 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
    // ---------------------------------------------------------
    // Bootstrap 5 : Responsive Dropdown Multi Submenu
    // (nécessite jQuery, EN ATTENTE de conversion en JS vanilla)
    // ---------------------------------------------------------
    $(function(){
     
      $('.dropdown-menu a.dropdown-toggle').on('click', function(e) {
        e.stopPropagation();
        e.preventDefault();
        if (!$(this).next().hasClass('show')) {
          $(this).parents('.dropdown-menu').first().find('.show').removeClass("show");
        }
        var subMenu = $(this).next(".dropdown-menu");
        subMenu.toggleClass('show'); 			// appliqué au ul
        $(this).parent().toggleClass('show'); 	// appliqué au li parent
     
        $(this).parents('li.nav-item.dropdown.show').on('hidden.bs.dropdown', function(e) {
          $('.dropdown-submenu .show').removeClass('show'); 	// appliqué au ul
          $('.dropdown-submenu.show').removeClass('show'); 		// appliqué au li parent
        });
      });
     
    });
    Tentative en JS pur :
    Code js : 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
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    // ---------------------------------------------------------
    // Bootstrap 5 : Responsive Dropdown Multi Submenu
    // ---------------------------------------------------------
    window.addEventListener("DOMContentLoaded", (event) => {
      "use strict";
      document.querySelectorAll('.dropdown-menu a.dropdown-toggle').forEach( (elt) => {
        elt.addEventListener('click', (e) => {
          e.stopPropagation();
          e.preventDefault();
          /*
          if( elt.nextElementSibling && !elt.nextElementSibling.classList.contains('show') ){
            var parents = getParents(elt,'dropdown-menu'); // nodes
            for (const parent of parents) {
              if( parent.classList && parent.classList.contains('show') )
              {
                parent.classList.remove('show');
              }
            }
          }
          */
          if( elt.nextElementSibling )
          {
            var subMenu = elt.nextElementSibling;
            subMenu.classList.toggle('show'); 			// appliqué au ul
            elt.parentNode.classList.toggle('show'); 	// appliqué au li parent
          }
        });
      });
    });
    // ------------------------------
    // get parents of element with specific className
    /*
    function getParents(el, parentClass) {
      var parentSelector = document;
      var parents = [];
      var p = el.parentNode;
      while (p !== parentSelector)
      {
        var o = p;
        if( o.classList && o.classList.contains(parentClass) )
        {
          parents.push(o);
        }
        p = o.parentNode;
      }
      parents.push(parentSelector);
      return parents;
    }
    */


    Si une âme charitable passe par là...
    Merci.

  2. #2
    Expert confirmé Avatar de Toufik83
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Janvier 2012
    Messages
    2 436
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : Suisse

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Janvier 2012
    Messages : 2 436
    Points : 4 930
    Points
    4 930
    Par défaut
    Bonjour,

    Il faut cacher tous les .dropdown-submenu .dropdown-menu à chaque clic :
    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
     
     
    window.addEventListener("DOMContentLoaded", (event) => {
      "use strict";
      document.querySelectorAll('.dropdown-menu a.dropdown-toggle')
        .forEach( (elt) => {
        elt.addEventListener('click', (e) => {
          e.stopPropagation();
          e.preventDefault();
          document.querySelectorAll('.dropdown-submenu .dropdown-menu')//ici
            .forEach(elem=>{
            elem.classList.remove('show');
            elem.classList.add('hide');
          });
         if( elt.nextElementSibling )
          {
            var subMenu = elt.nextElementSibling;
            subMenu.classList.toggle('show'); 			// appliqué au ul
            elt.parentNode.classList.toggle('show'); 	// appliqué au li parent
          }
        });
      });
    });

  3. #3
    Inactif  
    Homme Profil pro
    Webmaster
    Inscrit en
    Juin 2021
    Messages
    645
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 57
    Localisation : France, Pas de Calais (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Webmaster
    Secteur : Arts - Culture

    Informations forums :
    Inscription : Juin 2021
    Messages : 645
    Points : 1 280
    Points
    1 280
    Par défaut
    @Toufik83
    MERCI, ça marche *



    * PAR CONTRE, le "toggle", non :
    • quand on clic sur le sous-menu en cours, il ne se referme pas


    N.B.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    elem.classList.add('hide');
    ??
    .remove('show') est censé suffire, non ?

  4. #4
    Inactif  
    Homme Profil pro
    Webmaster
    Inscrit en
    Juin 2021
    Messages
    645
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 57
    Localisation : France, Pas de Calais (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Webmaster
    Secteur : Arts - Culture

    Informations forums :
    Inscription : Juin 2021
    Messages : 645
    Points : 1 280
    Points
    1 280
    Par défaut
    C'est bon, je crois qu'on y est :




    Code js : 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
    // ---------------------------------------------------------
    // Bootstrap 5 : Responsive Dropdown Multi Submenu
    // ---------------------------------------------------------
    window.addEventListener("DOMContentLoaded", (event) => {
      "use strict";
      // Traitement des sous-sous-menus
      document.querySelectorAll('.dropdown-submenu a.dropdown-toggle').forEach( (elt) => {
        elt.addEventListener('click', (e) => {
          e.stopPropagation();
          e.preventDefault();
          if( elt.nextElementSibling )
          {
            var subMenu = elt.nextElementSibling;
            document.querySelectorAll('.dropdown-submenu .dropdown-menu').forEach( (elem) => {
              if( elem != subMenu )
              {
                elem.classList.remove('show');
              }
            });
            subMenu.classList.toggle('show'); 			// appliqué au ul
            elt.parentNode.classList.toggle('show'); 	// appliqué au li parent
          }
        });
      });
    });

  5. #5
    Expert confirmé Avatar de Toufik83
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Janvier 2012
    Messages
    2 436
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : Suisse

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Janvier 2012
    Messages : 2 436
    Points : 4 930
    Points
    4 930
    Par défaut
    oui jreaux62, je ne l'avais pas vu, mais apparemment tu as trouvé la solution.

  6. #6
    Inactif  
    Homme Profil pro
    Webmaster
    Inscrit en
    Juin 2021
    Messages
    645
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 57
    Localisation : France, Pas de Calais (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Webmaster
    Secteur : Arts - Culture

    Informations forums :
    Inscription : Juin 2021
    Messages : 645
    Points : 1 280
    Points
    1 280
    Par défaut
    Ci fait
    Merci à toi, Toufik83
    (j'avais testé tant du trucs que je n'y voyais plus rien...)

    Par contre.... "j'ai cru voir un Gros-Minet..."
    Je voulais dire : un message de Beginner.
    (effacé ?)

  7. #7
    Expert confirmé Avatar de Toufik83
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Janvier 2012
    Messages
    2 436
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : Suisse

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Janvier 2012
    Messages : 2 436
    Points : 4 930
    Points
    4 930
    Par défaut
    De rien, au plaisir jreaux62, eh oui Beginner n'a pas aimé son message .

  8. #8
    Membre expert
    Homme Profil pro
    Inscrit en
    Octobre 2011
    Messages
    2 886
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Octobre 2011
    Messages : 2 886
    Points : 3 725
    Points
    3 725
    Par défaut
    Citation Envoyé par jreaux62 Voir le message
    Par contre.... "j'ai cru voir un Gros-Minet..."
    Je voulais dire : un message de Beginner.
    (effacé ?)
    Oui j'avais posté un code qui ne fonctionnait pas toujours car j'avais mal traduit un passage.

    En fait dans ton code JS il me semble qu'il manquait juste cette partie :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    if (!$(this).next().hasClass('show')) {
                $(this).parents('.dropdown-menu').first().find('.show').removeClass("show");
            }
    Que j'ai traduit finalement (après correction) comme cela :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    if (!elt.nextElementSibling.classList.contains("show")) {
                    let show_elem = elt.parentElement.parentElement.querySelectorAll(".show")
                    for (let elem of show_elem) {
                        elem.classList.remove("show")
                    }
                }
    Ce qui donne :

    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
    window.addEventListener("DOMContentLoaded", (event) => {
        "use strict";
        document.querySelectorAll('.dropdown-menu a.dropdown-toggle').forEach((elt) => {
            elt.addEventListener('click', (e) => {
                e.stopPropagation();
                e.preventDefault();
     
                if (!elt.nextElementSibling.classList.contains("show")) {
                    let show_elem = elt.parentElement.parentElement.querySelectorAll(".show")
                    for (let elem of show_elem) {
                        elem.classList.remove("show")
                    }
                }
                if (elt.nextElementSibling) {
                    var subMenu = elt.nextElementSibling;
                    subMenu.classList.toggle('show'); 			// appliqué au ul
                    elt.parentNode.classList.toggle('show'); 	// appliqué au li parent
                }
            });
        });
    });
    Cela fonctionne bien chez moi...

  9. #9
    Membre expert
    Homme Profil pro
    Inscrit en
    Octobre 2011
    Messages
    2 886
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Octobre 2011
    Messages : 2 886
    Points : 3 725
    Points
    3 725
    Par défaut
    Citation Envoyé par Beginner. Voir le message

    Ce qui donne :
    J'ai laissé la suite de ton code tel quel mais il semble que le if (elt.nextElementSibling ne soit pas nécessaire, ce qui permet de simplifier un peu le code :


    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
    window.addEventListener("DOMContentLoaded", (event) => {
        "use strict";
        document.querySelectorAll('.dropdown-menu a.dropdown-toggle').forEach((elt) => {
            elt.addEventListener('click', (e) => {
                e.stopPropagation();
                e.preventDefault();
                let subMenu = elt.nextElementSibling;
                if (!subMenu.classList.contains("show")) {
                    let show_elem = elt.parentElement.parentElement.querySelectorAll(".show")
                    for (let elem of show_elem) {
                        elem.classList.remove("show")
                    }
                }            
                subMenu.classList.toggle('show');             // appliqué au ul
                elt.parentNode.classList.toggle('show');     // appliqué au li parent
     
            });
        });
    });

  10. #10
    Inactif  
    Homme Profil pro
    Webmaster
    Inscrit en
    Juin 2021
    Messages
    645
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 57
    Localisation : France, Pas de Calais (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Webmaster
    Secteur : Arts - Culture

    Informations forums :
    Inscription : Juin 2021
    Messages : 645
    Points : 1 280
    Points
    1 280
    Par défaut
    @Beginner.

    Cela me semble bel et bon, Monseigneur...

    N.B. Cependant...
    Pas testé sur des sub-sub-submenus

    A tout dire : c'était AUSSI et SURTOUT pour répondre (et en finir ) avec le menu de SosChiensDordogne...

  11. #11
    Membre expert
    Homme Profil pro
    Inscrit en
    Octobre 2011
    Messages
    2 886
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Octobre 2011
    Messages : 2 886
    Points : 3 725
    Points
    3 725
    Par défaut
    Citation Envoyé par jreaux62 Voir le message
    C'est bon, je crois qu'on y est :

    J'ai testé et ça marche bien.

    Par contre il y a une condition dans ton code JQuery if (!$(this).next().hasClass('show')) qui était utile je trouve car cela permettait de faire ce qui suit seulement si nécessaire...

    Et aussi peut-être que tu devrais cibler un peu plus cette recherche : document.querySelectorAll('.dropdown-submenu .dropdown-menu').forEach(...) car là tu recherches dans tout le document. On pourrait par exemple limiter la recherche au menu, ce serait déjà ça et si on veut faire plus précis on peut s'inspirer de ton code JQuery : $(this).parents('.dropdown-menu').first().find('.show').removeClass("show");.

    J'ai remarqué que $(this).parents('.dropdown-menu').first() correspondait au grand-père lol de l’élément cliqué c'est pourquoi j'ai fait ça : let show_elem = elt.parentElement.parentElement.querySelectorAll(".show").

    En tous cas là tu n'as plus besoin de JQuery et je voulais aussi te demander : penses-tu qu'on peut aussi se passer de bootstrap pour faire ce menu ?

    PS : Je serais tenter aussi d'utiliser la délégation : un seul listener pour le menu...

  12. #12
    Membre expert
    Homme Profil pro
    Inscrit en
    Octobre 2011
    Messages
    2 886
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Octobre 2011
    Messages : 2 886
    Points : 3 725
    Points
    3 725
    Par défaut
    Citation Envoyé par jreaux62 Voir le message
    N.B. Cependant...
    Pas testé sur des sub-sub-submenus
    A tester, as-tu un exemple ?

    Citation Envoyé par jreaux62 Voir le message

    A tout dire : c'était AUSSI et SURTOUT pour répondre (et en finir ) avec le menu de SosChiensDordogne...
    Ah ok je vais regarder...

  13. #13
    Inactif  
    Homme Profil pro
    Webmaster
    Inscrit en
    Juin 2021
    Messages
    645
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 57
    Localisation : France, Pas de Calais (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Webmaster
    Secteur : Arts - Culture

    Informations forums :
    Inscription : Juin 2021
    Messages : 645
    Points : 1 280
    Points
    1 280
    Par défaut
    Bon,
    je suis allé plus loin dans le code :


    A priori, tout à l'air OK.

    Code js : 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
    // -------------------------------------------------
    // Bootstrap 5 : Responsive Dropdown Multi Submenu
    // -------------------------------------------------
    window.addEventListener("DOMContentLoaded", (event) => {
      "use strict";
      // management of Submenus
      // clic on Submenu link : open Submenu
      document.querySelectorAll('.navbar .dropdown-menu .dropdown-submenu > a.dropdown-toggle').forEach( (elt) => {
        elt.addEventListener('click', (e) => {
          e.stopPropagation();
          e.preventDefault();
          let eltParent = elt.parentNode; // li parent
          let subMenu = elt.nextElementSibling; // ul (dropdown)
          document.querySelectorAll('.navbar .dropdown-submenu.show, .navbar .dropdown-submenu .show').forEach( (elem) => {
            if(elem!=eltParent && elem!=subMenu){
              elem.classList.remove('show');
            }
          });
          subMenu.classList.toggle('show'); // appliqué au ul
          eltParent.classList.toggle('show'); // appliqué au li parent
        });
      });
      // clic on other link : close Submenus
      document.querySelectorAll('.navbar .dropdown > a.dropdown-toggle').forEach( (elt) => {
        elt.addEventListener('click', (e) => {
          document.querySelectorAll('.dropdown-submenu.show, .dropdown-submenu .show').forEach( (elem) => {
              elem.classList.remove('show');
          });
        });
      });
    });
    // -------------------------------------------------

    N.B. Toujours pas testé sur des sub-sub-...-submenus, car d'un point de vue "ergonomie", ça ne tient pas la route...
    [EDIT] Je viens de tester avec sub-submenus : ça ne fonctionne pas... Peu importe (cf remarque ci-dessus )

  14. #14
    Modérateur

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

    Informations forums :
    Inscription : Janvier 2011
    Messages : 17 075
    Points : 44 657
    Points
    44 657
    Par défaut
    Bonjour,
    let show_elem = elt.parentElement.parentElement.querySelectorAll(".show").
    il existe une méthode méconnue qui fait le job, pour peu que le sélecteur soit le bon :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    const dropMenu = elt.closest(".dropdown-menu");

    • avec fermeture des sous-menus au clic sur un autre lien
    c'est effectivement nécessaire pour ne pas revenir avec des sous-menus déjà ouvert.

    Le plus gros du travail ayant été fait, et sur base de celui-ci, je vous propose :
    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
    window.addEventListener("DOMContentLoaded", (event) => {
      "use strict";
      // récup. des acteurs
      const elemNav = document.querySelectorAll(".nav-item");
      const elemToggle = document.querySelectorAll(".dropdown-menu a.dropdown-toggle");
     
      // affectation des clics
      elemNav.forEach((nav) => {
        nav.addEventListener('click', (e) => {
          elemToggle.forEach((elem) => {
            elem.parentElement.classList.remove('show');
            elem.nextElementSibling.classList.remove('show');
          });
        })
      });
     
      elemToggle.forEach((elt) => {
        elt.addEventListener('click', (e) => {
          e.stopPropagation();
          e.preventDefault();
          let subMenu = elt.nextElementSibling;
     
          if (!subMenu.classList.contains('show')) {
            const dropMenu = elt.closest(".dropdown-menu");
            dropMenu.querySelectorAll('.show').forEach((elem) => {
              elem.classList.remove('show');
            });
          }
          subMenu.classList.toggle('show'); // appliqué au ul
          elt.parentNode.classList.toggle('show'); // appliqué au li parent
        });
      });
    });
    ... sachant qu'une partie des actions est directement prise en charge par BootStrap.



    N.B. Toujours pas testé sur des sub-sub-...-submenus, car d'un point de vue "ergonomie", ça ne tient pas la route...
    [EDIT] Je viens de tester avec sub-submenus : ça ne fonctionne pas... Peu importe (cf remarque ci-dessus )
    Cela devrait fonctionner mais effectivement cela reste une mauvaise pratique surtout pour le site en question.

  15. #15
    Inactif  
    Homme Profil pro
    Webmaster
    Inscrit en
    Juin 2021
    Messages
    645
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 57
    Localisation : France, Pas de Calais (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Webmaster
    Secteur : Arts - Culture

    Informations forums :
    Inscription : Juin 2021
    Messages : 645
    Points : 1 280
    Points
    1 280
    Par défaut
    @NoSmoking

    Code adopté !
    Fonctionne aussi avec sous-sous-menus.



    Code js : 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
    36
    // -------------------------------------------------
    // Bootstrap 5 : Responsive Dropdown Multi Submenu
    // -------------------------------------------------
    window.addEventListener("DOMContentLoaded", (event) => {
      "use strict";
      // navbar : management of Submenus
      // récup. des acteurs
      const elemNav = document.querySelectorAll(".navbar .nav-item");
      const elemToggle = document.querySelectorAll(".navbar .dropdown-menu a.dropdown-toggle");
      // affectation des clics
      elemNav.forEach((nav) => {
        nav.addEventListener('click', (e) => {
          elemToggle.forEach((elem) => {
            elem.parentElement.classList.remove('show');
            elem.nextElementSibling.classList.remove('show');
          });
        })
      });
     // au clic
      elemToggle.forEach((elt) => {
        elt.addEventListener('click', (e) => {
          e.stopPropagation();
          e.preventDefault();
          let subMenu = elt.nextElementSibling;
          if (!subMenu.classList.contains('show')) {
            const dropMenu = elt.closest(".dropdown-menu");
            dropMenu.querySelectorAll('.show').forEach((elem) => {
              elem.classList.remove('show');
            });
          }
          subMenu.classList.toggle('show'); // appliqué au ul
          elt.parentNode.classList.toggle('show'); // appliqué au li parent
        });
      });
    });
    // -------------------------------------------------

  16. #16
    Modérateur

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

    Informations forums :
    Inscription : Janvier 2011
    Messages : 17 075
    Points : 44 657
    Points
    44 657
    Par défaut
    Citation Envoyé par Beginner.
    En tous cas là tu n'as plus besoin de JQuery et je voulais aussi te demander : penses-tu qu'on peut aussi se passer de bootstrap pour faire ce menu ?
    Les menus de ce type existaient bien avant que BootStrap ne voit le jour


    Citation Envoyé par Beginner.
    PS : Je serais tenter aussi d'utiliser la délégation : un seul listener pour le menu...
    L'utilisation de la délégation est surtout intéressante lorsqu'il y a création dynamique d'éléments, dans le cas présent cela ne représente pas un véritable intérêt même si c'est effectivement faisable.



    Citation Envoyé par jreaux62
    Code adopté !
    alors prend en bien soin !

  17. #17
    Inactif  
    Homme Profil pro
    Webmaster
    Inscrit en
    Juin 2021
    Messages
    645
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 57
    Localisation : France, Pas de Calais (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Webmaster
    Secteur : Arts - Culture

    Informations forums :
    Inscription : Juin 2021
    Messages : 645
    Points : 1 280
    Points
    1 280
    Par défaut
    Bonjour,

    Citation Envoyé par NoSmoking Voir le message
    Les menus de ce type existaient bien avant que BootStrap ne voit le jour
    @Beginner.

    Oui, j'avais déjà ça aussi, sans Bootstrap (mais avec jQuery) :


    On remarquera le HTML hyper simple (les classes "hasSub" étant ajoutées dynamiquement en JS)

  18. #18
    Membre expert
    Homme Profil pro
    Inscrit en
    Octobre 2011
    Messages
    2 886
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Octobre 2011
    Messages : 2 886
    Points : 3 725
    Points
    3 725
    Par défaut
    Salut,
    Citation Envoyé par NoSmoking Voir le message
    il existe une méthode méconnue qui fait le job, pour peu que le sélecteur soit le bon :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    const dropMenu = elt.closest(".dropdown-menu");
    Bien vu.

    Citation Envoyé par NoSmoking Voir le message
    Les menus de ce type existaient bien avant que BootStrap ne voit le jour



    L'utilisation de la délégation est surtout intéressante lorsqu'il y a création dynamique d'éléments, dans le cas présent cela ne représente pas un véritable intérêt même si c'est effectivement faisable.
    Oui je m'en doute, BootStrap n'invente rien mais j'ai l'impression que c'est à la mode, ça a l'air très répandu...

    Perso je n'aime pas trop les boites noires,j'aime bien savoir comment les choses sont faites, c'est plus instructif... C'est entre autres pour cela que je préfère éviter JQuery, BootStrap... du moins au début mais c'est vrai que pour être productif on doit parfois utiliser ce qui existe déjà...

    Citation Envoyé par NoSmoking Voir le message
    L'utilisation de la délégation est surtout intéressante lorsqu'il y a création dynamique d'éléments, dans le cas présent cela ne représente pas un véritable intérêt même si c'est effectivement faisable.
    Je pense qu'il y a d'autres cas où son usage peut être intéressants... On peut vouloir limiter le nombre d'écouteurs et de gestionnaire d’événement, je suppose que c'est plus performant et moins gourmand en ressources mais je trouve aussi que c'est plus lisible, que c'est plus simple de voir qui fait quoi...

    Citation Envoyé par jreaux62 Voir le message
    Oui, j'avais déjà ça aussi, sans Bootstrap (mais avec jQuery) :

    Ah cela m'a l'air bien. Je regarderai plus en détail le code quand j'aurai besoin d'un menu...


    Citation Envoyé par jreaux62 Voir le message
    On remarquera le HTML hyper simple (les classes "hasSub" étant ajoutées dynamiquement en JS)
    Oui justement je me disais que certains menus étaient assez pénible à lire et du coup ils ne sont pas toujours facile à modifier, il faut trouver le bon endroit où insérer le code html, choisir les bonnes class selon qu'on ajoute un item ou un sous-menu...

    Bref je me dis maintenant que le mieux c'est de tout faire automatiquement en JS : l'utilisateur n'a plus qu'à fournir une liste ul/li qu'il peut faire avec un traitement de texte...

  19. #19
    Inactif  
    Homme Profil pro
    Webmaster
    Inscrit en
    Juin 2021
    Messages
    645
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 57
    Localisation : France, Pas de Calais (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Webmaster
    Secteur : Arts - Culture

    Informations forums :
    Inscription : Juin 2021
    Messages : 645
    Points : 1 280
    Points
    1 280
    Par défaut
    Citation Envoyé par Beginner. Voir le message
    Bref je me dis maintenant que le mieux c'est de tout faire automatiquement en JS...
    A la rigueur, la seule "difficulté" est de définir QUEL MENU est "actif" (= sur quelle page on est -> <li class="active ...">).

    Jusqu'ici, je construis mes menus avec PHP (+SQL) : une fonction PHP (récursive) affiche le chemin "actif".
    (code juste pour exemple)
    Code php : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    	foreach( $rubriqueIdsAll[0] as $rubriqueId )
    	{
    ...
    		// Menu "active" ?
    		$parentIdsAll = mnm_menus_get_parentIdsAll_array_byRubId_recursive( $rubriqueId, $arr=[] ); // Parents
    		$nav_class .= ( !empty($activePage['rubriqueId']) && in_array( $activePage['rubriqueId'] ,$parentIdsAll ) )? ' active' : ''; 
    ...

    Mais ça peut certainement se faire aussi en JS, au chargement de la page.

  20. #20
    Expert confirmé
    Avatar de Doksuri
    Profil pro
    Développeur Web
    Inscrit en
    Juin 2006
    Messages
    2 467
    Détails du profil
    Informations personnelles :
    Âge : 54
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Web

    Informations forums :
    Inscription : Juin 2006
    Messages : 2 467
    Points : 4 658
    Points
    4 658
    Par défaut
    j'arrive apres la bataille, mais pour la suite, tu peux mettre ce lien de cote, c'est ce qui m'a aide a l'epoque a abandonner jQuery

    github.com/nefe/You-Dont-Need-jQuery/blob/master/README-fr.md

    ce que je faisais, c'est qu'apres avoir trouve l'equivalent en JS, j'allais voir la doc sur MDN

+ Répondre à la discussion
Cette discussion est résolue.
Page 1 sur 2 12 DernièreDernière

Discussions similaires

  1. traduire code fortran en c++
    Par frereamir dans le forum C++
    Réponses: 1
    Dernier message: 15/07/2009, 13h59
  2. Traduire code Perl en C++
    Par dng05 dans le forum Langage
    Réponses: 11
    Dernier message: 24/06/2009, 14h32
  3. traduire code C en VBA
    Par Emcy dans le forum Général VBA
    Réponses: 11
    Dernier message: 06/01/2009, 10h15
  4. Traduire Code C# --> Delphi
    Par mmsalem dans le forum API, COM et SDKs
    Réponses: 7
    Dernier message: 09/06/2008, 01h22
  5. traduire code uml en code source
    Par open_source dans le forum EDI/Outils
    Réponses: 2
    Dernier message: 16/11/2007, 10h00

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