【问题标题】:How can I keep Bootstrap popovers alive while being hovered?如何在悬停时保持 Bootstrap 弹出框活着?
【发布时间】:2013-04-06 01:22:02
【问题描述】:

我正在使用 Bootstrap 弹出框创建一个显示用户信息的悬停卡片,并且我在鼠标悬停按钮时触发它。我想在弹出框本身悬停时保持此弹出框处于活动状态,但是一旦用户停止将鼠标悬停在按钮上,它就会消失。我该怎么做?

$('#example').popover({
    html : true,
    trigger : 'manual',
    content : function() {
        return '<div class="box">Popover</div>';
    }
});

$(document).on('mouseover', '#example', function(){
    $('#example').popover('show');
});

$(document).on('mouseleave', '#example', function(){
    $('#example').popover('hide');
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/2.2.4/jquery.js"></script>
<script src="https://unpkg.com/@popperjs/core@2"></script>
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/js/bootstrap.min.js"></script>
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css"/>

<a href="#" id="example" class="btn btn-danger" rel="popover" >hover for popover</a>

【问题讨论】:

  • 你想让什么活着?我将鼠标悬停在按钮上并保持打开状态?
  • 阅读最后一行问题

标签: jquery twitter-bootstrap popper.js


【解决方案1】:

使用下面的代码 sn-p 进行测试:

小修改(来自 vikas 提供的解决方案)以适合我的用例。

  1. 在弹出按钮的悬停事件上打开弹出框
  2. 将鼠标悬停在弹出框上方时保持弹出框打开
  3. 鼠标离开时关闭弹出框按钮或弹出框的弹出框。

$(".pop").popover({
    trigger: "manual",
    html: true,
    animation: false
  })
  .on("mouseenter", function() {
    var _this = this;
    $(this).popover("show");
    $(".popover").on("mouseleave", function() {
      $(_this).popover('hide');
    });
  }).on("mouseleave", function() {
    var _this = this;
    setTimeout(function() {
      if (!$(".popover:hover").length) {
        $(_this).popover("hide");
      }
    }, 300);
  });
<!DOCTYPE html>
<html>

<head>
  <link data-require="bootstrap-css@*" data-semver="3.2.0" rel="stylesheet" href="//maxcdn.bootstrapcdn.com/bootstrap/3.2.0/css/bootstrap.min.css" />
  <script data-require="jquery@*" data-semver="2.1.1" src="//cdnjs.cloudflare.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
  <script data-require="bootstrap@*" data-semver="3.2.0" src="https://maxcdn.bootstrapcdn.com/bootstrap/3.2.0/js/bootstrap.js"></script>

  <link rel="stylesheet" href="style.css" />

</head>

<body>
  <h2 class='text-primary'>Another Great "KISS" Bootstrap Popover example!</h2>
  <p class='text-muted'>KISS = Keep It Simple S....</p>

  <p class='text-primary'>Goal:</p>
  <ul>
    <li>Open popover on hover event for the popover button</li>
    <li>Keep popover open when hovering over the popover box</li>
    <li>Close popover on mouseleave for either the popover button, or the popover box.</li>
  </ul>

  <button type="button" class="btn btn-danger pop" data-container="body" data-toggle="popover" data-placement="right" data-content="Optional parameter: Skip if this was not requested<br>                                    A placement group is a logical grouping of instances within a single Availability                                     Zone. Using placement groups enables applications to get the full-bisection bandwidth                                     and low-latency network performance required for tightly coupled, node-to-node                                     communication typical of HPC applications.<br>                                    This only applies to cluster compute instances: cc2.8xlarge, cg1.4xlarge, cr1.8xlarge, hi1.4xlarge and hs1.8xlarge.<br>                                    More info: <a href=&quot;http://docs.aws.amazon.com/AWSEC2/latest/UserGuide/placement-groups.html&quot; target=&quot;_blank&quot;>Click here...</a>"
    data-original-title="" title="">
    HOVER OVER ME
    </button>
  <br><br>
  <button type="button" class="btn btn-info pop" data-container="body" data-toggle="popover" data-placement="right" data-content="Optional parameter: Skip if this was not requested<br>                                    A placement group is a logical grouping of instances within a single Availability                                     Zone. Using placement groups enables applications to get the full-bisection bandwidth                                     and low-latency network performance required for tightly coupled, node-to-node                                     communication typical of HPC applications.<br>                                    This only applies to cluster compute instances: cc2.8xlarge, cg1.4xlarge, cr1.8xlarge, hi1.4xlarge and hs1.8xlarge.<br>                                    More info: <a href=&quot;http://docs.aws.amazon.com/AWSEC2/latest/UserGuide/placement-groups.html&quot; target=&quot;_blank&quot;>Click here...</a>"
    data-original-title="" title="">
    HOVER OVER ME... Again!
    </button><br><br>
  <button type="button" class="btn btn-success pop" data-container="body" data-toggle="popover" data-placement="right" data-content="Optional parameter: Skip if this was not requested<br>                                    A placement group is a logical grouping of instances within a single Availability                                     Zone. Using placement groups enables applications to get the full-bisection bandwidth                                     and low-latency network performance required for tightly coupled, node-to-node                                     communication typical of HPC applications.<br>                                    This only applies to cluster compute instances: cc2.8xlarge, cg1.4xlarge, cr1.8xlarge, hi1.4xlarge and hs1.8xlarge.<br>                                    More info: <a href=&quot;http://docs.aws.amazon.com/AWSEC2/latest/UserGuide/placement-groups.html&quot; target=&quot;_blank&quot;>Click here...</a>"
    data-original-title="" title="">
    Okay one more time... !
    </button>
  <br><br>
  <p class='text-info'>Hope that helps you... Drove me crazy for a while</p>
  <script src="script.js"></script>
</body>

</html>

【讨论】:

  • 这很好用,我确实注意到第二个$(_this).popover("hide") 中缺少;。但是谢谢你,它是如此简单和干净!
  • 这个答案太棒了。截至 2015 年 5 月,在 BS3 上运行良好^^
  • 我在表格中使用了它,并在选项中添加了container: 'body',因为它使单元格发生了变化。很好的答案!
  • 如果您输入弹出框,然后在 300 毫秒之前返回到触发元素,弹出框将被隐藏。要修复它,请检查弹出框及其触发器是否都是 :hover,然后再将其隐藏在 setTimeout 中。我还会使用 setTimeout 和 mouseleave 弹出框本身的相同方法来修复闪烁。
  • 一定要设置animation:false 来修复闪烁 - 检查我上面的 Plunker 链接。它非常适合我。
【解决方案2】:

我已经找到了另一个解决方案...这里是代码

    $('.selector').popover({
        html: true,
        trigger: 'manual',
        container: $(this).attr('id'),
        placement: 'top',
        content: function () {
            $return = '<div class="hover-hovercard"></div>';
        }
    }).on("mouseenter", function () {
        var _this = this;
        $(this).popover("show");
        $(this).siblings(".popover").on("mouseleave", function () {
            $(_this).popover('hide');
        });
    }).on("mouseleave", function () {
        var _this = this;
        setTimeout(function () {
            if (!$(".popover:hover").length) {
                $(_this).popover("hide")
            }
        }, 100);
    });

【讨论】:

  • 添加animation: false很重要,否则重复将鼠标移到链接上会导致链接无法正常工作
  • 我对你的代码@vikas (gist.github.com/Nitrodist/7913848) 做了一个小的修改。它会在 50 毫秒后重新检查状态,以免它保持打开状态。也就是说,它每 50 毫秒不断地重新检查一次。
  • 如何对其进行调整,使其适用于刚刚添加到文档中的实时元素?
  • 不幸的是,这些解决方案都不起作用。我感谢您的努力和所有贡献。所有的步骤都朝着正确的方向前进。但是,正确答案不应该被标记为正确答案,我知道如何改变它,特别是对于这样一个老话题。我写了一个看起来像一个强大的解决方案的解决方案。我仍在测试它以平滑一些边缘。一旦我对它有 100% 的信心,我会继续它。
【解决方案3】:

这是我的看法:http://jsfiddle.net/WojtekKruszewski/Zf3m7/22/

有时在将鼠标从弹出框触发器移动到实际弹出框内容时对角线,您将鼠标悬停在下面的元素上。我想处理这种情况——只要你在超时触发之前到达弹出框内容,你就是安全的(弹出框不会消失)。它需要delay 选项。

这个 hack 基本上覆盖了 Popover leave 函数,但调用了原始函数(它启动计时器以隐藏 popover)。然后它将一次性监听器附加到mouseenter popover 内容元素。

如果鼠标进入弹出框,计时器将被清除。然后它会在弹出框上监听mouseleave,如果它被触发,它会调用原始的离开函数,以便它可以开始隐藏计时器。

var originalLeave = $.fn.popover.Constructor.prototype.leave;
$.fn.popover.Constructor.prototype.leave = function(obj){
  var self = obj instanceof this.constructor ?
    obj : $(obj.currentTarget)[this.type](this.getDelegateOptions()).data('bs.' + this.type)
  var container, timeout;

  originalLeave.call(this, obj);

  if(obj.currentTarget) {
    container = $(obj.currentTarget).siblings('.popover')
    timeout = self.timeout;
    container.one('mouseenter', function(){
      //We entered the actual popover – call off the dogs
      clearTimeout(timeout);
      //Let's monitor popover content instead
      container.one('mouseleave', function(){
        $.fn.popover.Constructor.prototype.leave.call(self, self);
      });
    })
  }
};

【讨论】:

  • 使用container = self.$tip;可以改善容器的查找。这样,即使设置了container属性,也可以找到弹出框。这里有一个小提琴:jsfiddle.net/dennis_c/xJc65
  • @pferrel 我已经在我的@Wojtek_Kruszewski 的小提琴叉中解决了这个问题:jsfiddle.net/HugeHugh/pN26d 在调用originalShow() 之前查看检查if (!thisTip.is(':visible')) 的部分
  • 如果使用选项 container: 'body', 初始化弹出框,此解决方案将无法按预期工作。变量container 需要替换为self.$tip。查看我的答案以获取更多详细信息:stackoverflow.com/a/28731847/439427
  • 太棒了。与其他答案不同,这适用于使用“选择器”参数时。
  • 这里是一个改进版本,修复了离开和重新进入提示仍然隐藏的错误,还修复了提示附加到身体的场景jsfiddle.net/Zf3m7/1499
【解决方案4】:

我认为一个简单的方法是这样的:

$('.popover').each(function () {
                    var $this = $(this);
                    $this.popover({
                        trigger: 'hover',
                        content: 'Content Here',
                        container: $this
                    })
                });

这样,弹出框是在目标元素本身内部创建的。因此,当您将鼠标移到弹出框上方时,它仍然位于元素上方。 Bootstrap 3.3.2 可以很好地解决这个问题。旧版本的动画可能存在一些问题,因此您可能需要禁用“animation:false”

【讨论】:

  • 我知道这个帖子很旧,但在我看来这是最好、最干净的解决方案,应该排名更高。唯一需要注意的是,如果您将弹出框(以一种奇怪的方式)“远离”触发元素,这会中断。但是只要两者之间的距离为零(例如,它们重叠),它就可以很好地工作并且不需要任何自定义 JS。谢谢!
  • 这是迄今为止最好、干净、最简单的解决方案。应该排名更高!我添加了delay: { "hide": 400 } 以在隐藏之前添加一些延迟,效果很好! ?
【解决方案5】:

我将触发器设置为hover,并将容器设置为#element,最后将box的位置添加到right

这应该是你的设置:

$('#example').popover({
    html: true,
    trigger: 'hover',
    container: '#example',
    placement: 'right',
    content: function () {
        return '<div class="box"></div>';
    }
});

#example css 需要position:relative; 检查下面的jsfiddle:

https://jsfiddle.net/9qn6pw4p/1/

已编辑

这个小提琴的两个链接都可以正常工作 http://jsfiddle.net/davidchase03/FQE57/4/

【讨论】:

  • 嗯,可以,我可以在content 选项中使用jquery ajax 来从服务器端获取内容.. 是否可行,或者我需要为此做一些额外的工作
  • @vikasdevde 是的,您可以在内容中使用ajax,但您需要进行设置才能使其正常工作...如果它解决了您的OP,请标记答案。这样其他人可以受益
  • 但是如果我们将链接本身用作容器,那么整个弹出框就会变成一个链接....试试看
  • 如果你在盒子里放了一个链接,它仍然会链接出去..对吗?
  • jsfiddle 对我没有任何作用。铬 2014 年 3 月 20 日。
【解决方案6】:

这是我设计的一个解决方案,它似乎运行良好,同时还允许您使用正常的 Bootstrap 实现来打开所有弹出窗口。

原小提琴:https://jsfiddle.net/eXpressive/hfear592/

移植到这个问题:

<a href="#" id="example" class="btn btn-danger" rel="popover" >hover for popover</a>

$('#example').popover({
    html : true,
    trigger : 'hover',
    content : function() {
        return '<div class="box"></div>';
    }
}).on('hide.bs.popover', function () {
    if ($(".popover:hover").length) {
      return false;
    }                
}); 

$('body').on('mouseleave', '.popover', function(){
    $('.popover').popover('hide');
});

【讨论】:

  • 这是最好的答案!它避免了必须设置container,这在某些情况下可能是不可能的/不可取的(例如当弹出容器必须是不同的东西时,例如逃避父溢出:隐藏)。
【解决方案7】:

这就是我在网络上其他位的帮助下使用 bootstrap popover 所做的。从现场展示的各种产品中动态获取标题和内容。每个产品或弹出框都有唯一的 ID。退出产品($this .pop)或弹出框时弹出框将消失。超时用于显示弹出框,直到通过产品而不是弹出框退出。

$(".pop").each(function () {
        var $pElem = $(this);
        $pElem.popover(
            {
                html: true,
                trigger: "manual",
                title: getPopoverTitle($pElem.attr("id")),
                content: getPopoverContent($pElem.attr("id")),
                container: 'body',
                animation:false
            }
        );
    }).on("mouseenter", function () {
        var _this = this;
        $(this).popover("show");
        console.log("mouse entered");
        $(".popover").on("mouseleave", function () {
            $(_this).popover('hide');
        });
    }).on("mouseleave", function () {
        var _this = this;
        setTimeout(function () {
            if (!$(".popover:hover").length) {
                $(_this).popover("hide");
            }
        }, 100);
    });
    function getPopoverTitle(target) {
        return $("#" + target + "_content > h3.popover-title").html();
    };

    function getPopoverContent(target) {
        return $("#" + target + "_content > div.popover-content").html();
    };

【讨论】:

  • 如果弹出框不是目标元素的子元素,这也将起作用。 +1
【解决方案8】:

我同意最好的方法是使用David Chase、Cu Ly 和其他人给出的方法,最简单的方法是使用container: $(this) 属性,如下所示:

$(selectorString).each(function () {
  var $this = $(this);
  $this.popover({
    html: true,
    placement: "top",
    container: $this,
    trigger: "hover",
    title: "Popover",
    content: "Hey, you hovered on element"
  });
});

这里要指出的是,本例中的popover会继承当前元素的所有属性。因此,例如,如果您对 .btn 元素(引导程序)执行此操作,您将无法选择弹出框内的文本。只是想记录一下,因为我花了相当长的时间来敲打这个。

【讨论】:

  • 太糟糕了 Bootstrap 不允许 data-container="this" 所以这可以在没有额外的 each() 的情况下初始化...
【解决方案9】:

Vikas 回答对我来说非常有效,在这里我还添加了对延迟的支持(显示/隐藏)。

var popover = $('#example');
var options = {
    animation : true,
    html: true,
    trigger: 'manual',
    placement: 'right',
    delay: {show: 500, hide: 100}
};   
popover
    .popover(options)
    .on("mouseenter", function () {

        var t = this;
        var popover = $(this);    
        setTimeout(function () {

            if (popover.is(":hover")) {

                popover.popover("show");
                popover.siblings(".popover").on("mouseleave", function () {
                    $(t).popover('hide');
                });
            }
        }, options.delay.show);
    })
    .on("mouseleave", function () {
        var t = this;
        var popover = $(this);

        setTimeout(function () {
            if (popover.siblings(".popover").length && !popover.siblings(".popover").is(":hover")) {
                $(t).popover("hide")
            }
        }, options.delay.hide);
    });     

另外请注意我改了:

if (!$(".popover:hover").length) {

与:

if (popover.siblings(".popover").length && !popover.siblings(".popover").is(":hover")) {

以便它准确引用该打开的弹出窗口,而不是任何其他(因为现在,通过延迟,可以同时打开超过 1 个)

【讨论】:

  • 我最后的评论在使用container:body的时候其实是不对的,如果是这样的话,那一行还是要用Vikas的解决方案
【解决方案10】:

选择的答案有效,但如果使用 body 作为容器初始化弹出框,则会失败。

$('a').popover({ container: 'body' });

基于所选答案的解决方案是在使用弹出框之前需要放置以下代码。

var originalLeave = $.fn.popover.Constructor.prototype.leave;
$.fn.popover.Constructor.prototype.leave = function(obj) {
    var self = obj instanceof this.constructor ? obj : $(obj.currentTarget)[this.type](this.getDelegateOptions()).data('bs.' + this.type);
    originalLeave.call(this, obj);

    if (obj.currentTarget) {
        self.$tip.one('mouseenter', function() {
            clearTimeout(self.timeout);
            self.$tip.one('mouseleave', function() {
                $.fn.popover.Constructor.prototype.leave.call(self, self);
            });
        })
    }
};

使用self.$tip 而不是遍历 DOM 并期望弹出框始终是元素的兄弟姐妹,变化很小。

【讨论】:

    【解决方案11】:

    我最近需要让这个与 KO 一起工作,但上述解决方案在显示和隐藏延迟时效果不佳。下面应该解决这个问题。基于引导工具提示的工作方式。希望这对某人有所帮助。

    var options = {
                    delay: { show: 1000, hide: 50 },
                    trigger: 'manual',                      
                    html: true
                };
    var $popover = $(element).popover(options);
    
    $popover.on('mouseenter', function () { // This is entering the triggering element
        var self = this;
    
        clearTimeout(self.timeout);
        self.hoverState = 'in';
    
        self.timeout = setTimeout(function () {
            if (self.hoverState == 'in') {
                $(self).popover("show");
    
                $(".popover, .popover *").on('mouseover', function () { // This is moving over the popover
                    clearTimeout(self.timeout);
                });                                                                 
    
                $(".popover").on('mouseleave', function () { // This is leaving the popover
                    self.timeout = setTimeout(function () {
                        if (self.hoverState == 'out') {
                            $(self).popover('hide');
                        }
                    }, options.delay.hide);
                });
            }
        }, options.delay.show);
    }).on('mouseleave', function (event) { // This is leaving the triggering element
        var self = this;
    
        clearTimeout(self.timeout);
        self.hoverState = 'out';
    
        self.timeout = setTimeout(function () {                             
            if (self.hoverState == 'out') {
                $(self).popover('hide');
            }
    
        }, options.delay.hide);
    });
    

    【讨论】:

      【解决方案12】:

      工具提示也是如此:

      对我来说,以下解决方案有效,因为它不会在每个“mouseenter”上添加事件侦听器,并且可以将鼠标悬停在使工具提示保持活动状态的工具提示元素上。

      $ ->
      
        $('.element').tooltip({
          html: true,
          trigger: 'manual'
        }).
        on 'mouseenter', ->
          clearTimeout window.tooltipTimeout
          $(this).tooltip('show') unless $('.tooltip:visible').length > 0
        .
        on 'mouseleave', ->
          _this = this
          window.tooltipTimeout = setTimeout ->
            $(_this).tooltip('hide')
          , 100
      
      $(document).on 'mouseenter', '.tooltip', ->
        clearTimeout window.tooltipTimeout
      
      $(document).on 'mouseleave', '.tooltip', ->
        trigger = $($(this).siblings('.element')[0])
        window.tooltipTimeout = setTimeout ->
          trigger.tooltip('hide')
        , 100
      

      【讨论】:

        【解决方案13】:

        这个解决方案对我来说效果很好:(现在它是防弹的);-)

        function enableThumbPopover() {
            var counter;
        
            $('.thumbcontainer').popover({
                trigger: 'manual',
                animation: false,
                html: true,
                title: function () {
                    return $(this).parent().find('.thumbPopover > .title').html();
                },
                content: function () {
                    return $(this).parent().find('.thumbPopover > .body').html();
                },
                container: 'body',
                placement: 'auto'
            }).on("mouseenter",function () {
                var _this = this; // thumbcontainer
        
                console.log('thumbcontainer mouseenter')
                // clear the counter
                clearTimeout(counter);
                // Close all other Popovers
                $('.thumbcontainer').not(_this).popover('hide');
        
                // start new timeout to show popover
                counter = setTimeout(function(){
                    if($(_this).is(':hover'))
                    {
                        $(_this).popover("show");
                    }
                    $(".popover").on("mouseleave", function () {
                        $('.thumbcontainer').popover('hide');
                    });
                }, 400);
        
            }).on("mouseleave", function () {
                var _this = this;
        
                setTimeout(function () {
                    if (!$(".popover:hover").length) {
                        if(!$(this).is(':hover'))
                        {
                            $(_this).popover('hide');
                        }
                    }
                }, 200);
            });
        }
        

        【讨论】:

          【解决方案14】:
                  $(function() {
                      $("[data-toggle = 'popover']").popover({
                          placement: 'left',
                          html: true,
                          trigger: "  focus",
                      }).on("mouseenter", function() {
                          var _this = this;
                          $(this).popover("show");
                          $(this).siblings(".popover").on("mouseleave", function() {
                              $(_this).popover('hide');
                          });
                      }).on("mouseleave", function() {
                          var _this = this;
                          setTimeout(function() {
                              if (!$(".popover:hover").length) {
                                  $(_this).popover("hide")
                              }
                          }, 100);
                      });
                  }); 
          

          【讨论】:

            【解决方案15】:

            我发现mouseleave 不会在奇怪的事情发生时触发,比如窗口焦点突然改变,然后用户回到浏览器。在这种情况下,mouseleave 将永远不会触发,直到光标移过并再次离开元素。

            我想出的这个解决方案依赖于window 对象上的mouseenter,因此当鼠标移动到页面上的任何其他地方时它就会消失。

            这设计用于在页面上有多个触发它的元素(例如在表格中)。

            var allMenus = $(".menus");
            allMenus.popover({
                html: true,
                trigger: "manual",
                placement: "bottom",
                content: $("#menuContent")[0].outerHTML
            }).on("mouseenter", (e) => {
                allMenus.not(e.target).popover("hide");
                $(e.target).popover("show");
                e.stopPropagation();
            }).on("shown.bs.popover", () => {
                $(window).on("mouseenter.hidepopover", (e) => {
                    if ($(e.target).parents(".popover").length === 0) {
                        allMenus.popover("hide");
                        $(window).off("mouseenter.hidepopover");
                    }
                });
            });
            

            【讨论】:

              【解决方案16】:

              hover() 会更灵活

              $(".my-popover").hover(
                  function() {  // mouse in event
                      $this = $(this);
                      $this.popover({
                          html: true,
                          content: "Your content",
                          trigger: "manual",
                          animation: false
                          });
                      $this.popover("show");
                      $(".popover").on("mouseleave", function() {
                          $this.popover("hide");
                      });
                  },
                  function() {  // mouse out event
                      setTimeout(function() {
                          if (!$(".popover:hover").length) {
                              $this.popover("hide");
                          }
                      }, 100);
                  } 
              )
              

              【讨论】:

                【解决方案17】:

                简单:)

                $('[data-toggle="popover"]').popover( { "container":"body", "trigger":"focus", "html":true });
                $('[data-toggle="popover"]').mouseenter(function(){
                    $(this).trigger('focus');
                });
                

                【讨论】:

                  【解决方案18】:

                  我发现接受的答案和与之相似的答案存在一些缺陷。主要是它反复向元素添加 mouseleave 侦听器。

                  我已将他们的解决方案与一些自定义代码相结合,以实现有问题的功能,而不会出现内存泄漏或侦听器膨胀。

                      var getPopoverTimeout = function ($el) {
                          return $el.data('timeout');
                      }
                      $element.popover({
                          trigger: "manual",
                          html: true,
                          content: ...,
                          title: ...,
                          container: $element
                       }).on("mouseenter", function () {
                          var $this = $(this);
                          if (!$this.find('.popover').length) {
                              $this.popover("show");
                          } else if (getPopoverTimeout($element)) {
                              clearTimeout(getPopoverTimeout($element));
                          }
                      }).on("mouseleave", function () {
                          var $this = $(this);
                          $element.data('timeout', setTimeout(function () {
                              if (!$(".popover:hover").length) {
                                  $this.popover("hide")
                              }
                          }, 250));
                      });
                  

                  这提供了一个很好的类似“悬停意图”的解决方案,因此它不会闪入和闪出。

                  【讨论】:

                    【解决方案19】:

                    我知道我参加聚会有点晚了,但我一直在寻找解决方案。我偶然发现了这篇文章。这是我对此的看法,也许它会对你们中的一些人有所帮助。

                    html部分:

                    <button type="button" class="btn btn-lg btn-danger" data-content="test" data-placement="right" data-toggle="popover" title="Popover title" >Hover to toggle popover</button><br>
                    // with custom html stored in a separate element, using "data-target"
                    <button type="button" class="btn btn-lg btn-danger" data-target="#custom-html" data-placement="right" data-toggle="popover" >Hover to toggle popover</button>
                    
                    <div id="custom-html" style="display: none;">
                        <strong>Helloooo!!</strong>
                    </div>
                    

                    js部分:

                    $(function () {
                            let popover = '[data-toggle="popover"]';
                    
                            let popoverId = function(element) {
                                return $(element).popover().data('bs.popover').tip.id;
                            }
                    
                            $(popover).popover({
                                trigger: 'manual',
                                html: true,
                                animation: false
                            })
                            .on('show.bs.popover', function() {
                                // hide all other popovers  
                                $(popover).popover("hide");
                            })
                            .on("mouseenter", function() {
                                // add custom html from element
                                let target = $(this).data('target');
                                $(this).popover().data('bs.popover').config.content = $(target).html();
                    
                                // show the popover
                                $(this).popover("show");
                                
                                $('#' + popoverId(this)).on("mouseleave", () => {
                                   $(this).popover("hide");
                                });
                    
                            }).on("mouseleave", function() {
                                setTimeout(() => {
                                    if (!$("#" + popoverId(this) + ":hover").length) {
                                        $(this).popover("hide");
                                    }
                                }, 100);
                            });
                        })
                    

                    【讨论】:

                      【解决方案20】:

                      这是我的显示动态工具提示的代码,延迟并由 ajax 加载。

                      $(window).on('load', function () {
                          generatePopovers();
                          
                          $.fn.dataTable.tables({ visible: true, api: true }).on('draw.dt', function () {
                              generatePopovers();
                          });
                      });
                      
                      $(document).ajaxStop(function () {
                          generatePopovers();
                      });

                      function generatePopovers() {
                      var popover = $('a[href*="../Something.aspx"]'); //locate the elements to popover
                      
                      popover.each(function (index) {
                          var poplink = $(this);
                          if (poplink.attr("data-toggle") == null) {
                              console.log("RENDER POPOVER: " + poplink.attr('href'));
                              poplink.attr("data-toggle", "popover");
                              poplink.attr("data-html", "true");
                              poplink.attr("data-placement", "top");
                              poplink.attr("data-content", "Loading...");
                              poplink.popover({
                                  animation: false,
                                  html: true,
                                  trigger: 'manual',
                                  container: 'body',
                                  placement: 'top'
                              }).on("mouseenter", function () {
                                  var thispoplink = poplink;
                                  setTimeout(function () {
                                      if (thispoplink.is(":hover")) {
                                          thispoplink.popover("show");
                                          loadDynamicData(thispoplink); //load data by ajax if you want
                                          $('body .popover').on("mouseleave", function () {
                                              thispoplink.popover('hide');
                                          });
                                      }
                                  }, 1000);
                              }).on("mouseleave", function () {
                                  var thispoplink = poplink;
                                  setTimeout(function () {
                                      if (!$("body").find(".popover:hover").length) {
                                          thispoplink.popover("hide");
                                      }
                                  }, 100);
                              });
                          }
                      });

                      function loadDynamicData(popover) {
                          var params = new Object();
                          params.somedata = popover.attr("href").split("somedata=")[1]; //obtain a parameter to send
                          params = JSON.stringify(params);
                          //check if the content is not seted
                          if (popover.attr("data-content") == "Loading...") {
                              $.ajax({
                                  type: "POST",
                                  url: "../Default.aspx/ObtainData",
                                  data: params,
                                  contentType: "application/json; charset=utf-8",
                                  dataType: 'json',
                                  success: function (data) {
                                      console.log(JSON.parse(data.d));
                                      var dato = JSON.parse(data.d);
                                      if (dato != null) {
                                          popover.attr("data-content",dato.something); // here you can set the data returned
                                          if (popover.is(":hover")) {
                                              popover.popover("show"); //use this for reload the view
                                          }
                                      }
                                  },
                      
                                  failure: function (data) {
                                      itShowError("- Error AJAX.<br>");
                                  }
                              });
                          }
                      }

                      【讨论】:

                        猜你喜欢
                        • 2016-08-09
                        • 1970-01-01
                        • 1970-01-01
                        • 1970-01-01
                        • 2015-09-08
                        • 2012-12-11
                        • 1970-01-01
                        • 1970-01-01
                        • 2016-04-19
                        相关资源
                        最近更新 更多