【问题标题】:Child input boxes close navigation dropdowns on click子输入框在点击时关闭导航下拉菜单
【发布时间】:2013-06-22 03:20:08
【问题描述】:

小提琴:http://jsfiddle.net/4PMwP/

我正在为我的导航栏使用以下脚本:

(function($){

  var timeout    = 500;
  var closetimer = 0;
  var ddmenuitem = null;

  // From https://github.com/Modernizr/Modernizr/blob/master/modernizr.js
  var isTouch = ('ontouchstart' in window) ||
                window.DocumentTouch && document instanceof DocumentTouch;

  // jsddm funcs from http://javascript-array.com/scripts/jquery_simple_drop_down_menu/
  function jsddm_open($this){
    jsddm_canceltimer();
    jsddm_close();
    ddmenuitem = $this.find('ul').css('visibility', 'visible');
  }

  function jsddm_close() {
    if(ddmenuitem){
      ddmenuitem.css('visibility', 'hidden');
      ddmenuitem = null;
    }
  }

  function jsddm_timer() { 
    closetimer = window.setTimeout(jsddm_close, timeout);
  }

  function jsddm_canceltimer() { 
    if(closetimer)
    {  window.clearTimeout(closetimer);
       closetimer = null;
    }
  }

  function jsddm_toggle($this) {
    if (ddmenuitem && $this.has(ddmenuitem[0]).length){
      jsddm_close();
    }
    else {
      jsddm_open($this);
    }
  }

  $.fn.make_dropdown = function(options){

    return this.each(function(){

      if (options && options['timeout']){
        timeout = options['timeout'];
      }

      $(this).click(function(event){
        jsddm_toggle($(this));
        event.stopPropagation();
      });
      if (!isTouch){
        $(this).mouseover(function(){ jsddm_open($(this)) }).mouseout(jsddm_timer);
      }

    });
  }

  $(document).click(jsddm_close);

})(jQuery);

悬停或单击时会显示下拉菜单,这对于桌面和移动浏览器非常有用。问题是我的下拉菜单将包括搜索、登录等输入框,单击这些不应关闭下拉菜单。由于下拉列表中的所有内容都是监听点击的 li 的子节点,因此无论如何都会关闭。

我需要在单击子元素时下拉菜单保持可见,但在单击主父 li 时仍会切换。

谢谢

【问题讨论】:

  • 这些答案对您有帮助吗?
  • 当然可以。在不问另一个问题的情况下,知道如何在输入框处于活动状态时启用它也不会关闭下拉菜单吗?所以它不会在用户打字时消失,等等
  • 给你小提琴jsfiddle.net/pF8Rp。我也会更新我的答案..

标签: jquery events drop-down-menu navigation


【解决方案1】:

试试这个:

$(document).ready(function () {
    $('#menubar > li').make_dropdown();
    $('li  input').click(function (e) {
        e.stopPropagation();
    })
});

Fiddle

您可以通过在输入级别使用event.stopPropagation 禁用它来阻止单击事件冒泡父树。这将阻止执行其他父单击处理程序。

另外我不确定这是否适合你的情况,但是:

使用mouseenter/mouseleave(hover) 事件而不是mouseover/mouseout 事件,因为即使您将鼠标悬停在绑定事件的父级内的子级上,后者也会被触发。

来自 docs

mouseenter 事件与 mouseover 处理事件冒泡的方式不同。如果在这个例子中使用了 mouseover,那么当鼠标指针移动到 Inner 元素上时,将触发处理程序。这通常是不受欢迎的行为。另一方面,mouseenter 事件仅在鼠标进入其绑定的元素而不是后代元素时触发其处理程序。所以在这个例子中,当鼠标进入 Outer 元素而不是 Inner 元素时,会触发处理程序。

更新

根据您在问题中的评论:当输入框处于活动状态时,不会出现菜单,这也会在鼠标移出时隐藏。只有在 int 框中按下 enter 键时,菜单才会被隐藏。只是基于我的假设

    // on Search Box click    
    $('li  .searchBox').click(function (e) {
        e.stopPropagation();
    }).keypress(function (e) {
        if (e.which == 13) // on enter key press close
        {
            $('.searchBox').closest('ul').css('visibility', 'hidden'); // SInce you are using visility for you menus. You can also try calling your method to hide, But this is a pointer
        }
    });

打开关闭

function jsddm_open($this) {
        if ($('.searchBox').css('visibility') == 'hidden') { // Dont show any other menu when searchbox is active
            jsddm_canceltimer();
            jsddm_close();
            ddmenuitem = $this.find('ul').css('visibility', 'visible');
        }
    }

    function jsddm_close() {
        if ($('.searchBox').css('visibility') == 'hidden') { // check if the input is visible if not then do this.

            if (ddmenuitem) {
                ddmenuitem.css('visibility', 'hidden');
                ddmenuitem = null;
            }
        }
    }

Fiddle

【讨论】:

    【解决方案2】:

    查看此演示,http://jsfiddle.net/4PMwP/12/

    为您的输入提供一个 ID,并在您的 $(document).click(jsddm_close); 脚本之后的一行中添加 $('#showInput').click(jsddm_open);。

    (function($){
    
      var timeout    = 500;
      var closetimer = 0;
      var ddmenuitem = null;
    
      // From https://github.com/Modernizr/Modernizr/blob/master/modernizr.js
      var isTouch = ('ontouchstart' in window) ||
                    window.DocumentTouch && document instanceof DocumentTouch;
    
      // jsddm funcs from http://javascript-array.com/scripts/jquery_simple_drop_down_menu/
      function jsddm_open($this){
        jsddm_canceltimer();
        jsddm_close();
        ddmenuitem = $this.find('ul').css('visibility', 'visible');
      }
    
      function jsddm_close() {
        if(ddmenuitem){
          ddmenuitem.css('visibility', 'hidden');
          ddmenuitem = null;
        }
      }
    
      function jsddm_timer() { 
        closetimer = window.setTimeout(jsddm_close, timeout);
      }
    
      function jsddm_canceltimer() { 
        if(closetimer)
        {  window.clearTimeout(closetimer);
           closetimer = null;
        }
      }
    
      function jsddm_toggle($this) {
        if (ddmenuitem && $this.has(ddmenuitem[0]).length){
          jsddm_close();
        }
        else {
          jsddm_open($this);
        }
      }
    
      $.fn.make_dropdown = function(options){
    
        return this.each(function(){
    
          if (options && options['timeout']){
            timeout = options['timeout'];
          }
    
          $(this).click(function(event){
            jsddm_toggle($(this));
            event.stopPropagation();
          });
          if (!isTouch){
            $(this).mouseover(function(){ jsddm_open($(this)) }).mouseout(jsddm_timer);
          }
    
        });
      }
    
      $(document).click(jsddm_close);
      $('#showInput').click(jsddm_open);
    
    })(jQuery);
    
    $(document).ready(function(){   $('#menubar > li').make_dropdown(); });
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-06-10
      • 1970-01-01
      • 2017-11-02
      • 2014-04-28
      • 1970-01-01
      相关资源
      最近更新 更多