Search code examples
javascriptphphtmlwordpress

Open/Close submenu when clicking the item name


I am having problems with the menu part of a wordpress site (salient theme), when i am on mobile, i open the menu with the hamburger button and have several options, some with sub menus, so the items with sub menus only open when clicking the little arrow icon to the right of the item, i am trying to get it to open also when you click on the item itself by making it so when you click the item it triggers a click on the arrow

enter image description here

here is the html of the menu

enter image description here

and here is the javascript i am doing to get it to work(only doing it for the first item with submenu here), i am new to javascript but for what i've seen i think this should work (i am using the Code Snippets plugin for wordpress)

<?php
add_action( 'wp_footer', function () { ?>
<script>    


var el = (document.querySelector('.menu-item.menu-item-type-custom.menu- 
item-object-custom.menu-item-has-children.menu-item-5812 a'));
console.log(el);    

var el2 =(document.querySelector('.menu-item.menu-item-type-custom.menu- 
item-object-custom.menu-item-has-children.menu-item-5812 span'));
console.log(el2);

el.onclick = function() 
{
    $el2.click();
};

</script>

<?php } );
?>

SOLUTION:

aside from the answear by Alvaro Montoro i needed to encapsulate everything inside an eventListener with DomLoaded, here is the final code

add_action( 'wp_footer', function () { ?>
<script>

document.addEventListener('DOMContentLoaded', function() {

var elSupervivencia = document.querySelector('#slide-out-widget-area > div > 
div.inner > div > ul:nth-child(1) > li.menu-item.menu-item-type-custom.menu- 
item-object-custom.menu-item-has-children.menu-item-5812 > a');
console.log(elSupervivencia);    

var elSupervivenciaFlecha = document.querySelector('#slide-out-widget-area > 
div > div.inner > div > ul:nth-child(1) > li.menu-item.menu-item-type- 
custom.menu-item-object-custom.menu-item-has-children.menu-item-5812 .ocm- 
dropdown-arrow i');
console.log(elSupervivenciaFlecha);

elSupervivenciaFlecha.onclick = function() {
console.log("Clicked on the span");
}

elSupervivencia.onclick = function(e) 
{
e.preventDefault();
elSupervivenciaFlecha.click(); 
};
    });
</script>

<?php } );

Solution

  • For what you seem to want, you almost have it. The only thing that seems to be missing is to prevent the default behavior when you click on the link (which could be a potential problem as pointed on the comments above, because the linked page may be innaccessible through the menu now).

    With .preventDefault() you will prevent the default action for that element for that event, so you would just need to add that:

    var el = (document.querySelector('.menu-item.menu-item-type-custom.menu-item-object-custom.menu-item-has-children.menu-item-5812 a'));
    console.log(el);
    
    var el2 = (document.querySelector('.menu-item.menu-item-type-custom.menu-item-object-custom.menu-item-has-children.menu-item-5812 span'));
    console.log(el2);
    
    el2.onclick = function() {
      console.log("Clicked on the span");
    }
    
    el.onclick = function(e) {
      e.preventDefault();
      el2.click(); // removed the $
    };
    <ul class="menu">
      <li class="menu-item menu-item-type-custom menu-item-object-custom menu-item-has-children menu-item-5812">
        <a href="#">Supervivencia</a>
        <ul class="sub-menu">
          <li><a href="super1.html">Supervivencia 1</a></li>
          <li><a href="super2.html">Supervivencia 2</a></li>
          <li><a href="super3.html">Supervivencia 3</a></li>
        </ul>
        <span class="ocm-drowndown-arrow" style="top: 17.5px">
          <i class="fa-angle-down"></i>
        </span>
      </li>
    </ul>

    As they pointed in the comments, that may not be too usable, as the linked page is no longer accessible on the menu, you may want to add some conditions (checking for window size or a variable/class that indicates that the mobile menu is active) to perform that preventDefault().

    Apart from that, you may want to consider changing the selector for el and el2, as they are not specific and could match more than one element. I know you are using querySelector so only the first element that matches the selector will be returned, which should not be a problem for el but could be problematic with el2 (because the a could be a child span that would be selected over the sibling one that is the one you want.)