¿Cómo puedo mantener vivos los popovers de Bootstrap mientras estoy flotando?


114

Estoy usando una ventana emergente de Bootstrap para crear una tarjeta flotante que muestre la información del usuario, y la estoy activando al pasar el mouse sobre un botón. Quiero mantener vivo este popover mientras el popover mismo se mantiene suspendido, pero desaparece tan pronto como el usuario deja de pasar el mouse sobre el botón. ¿Cómo puedo hacer esto?

$('#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>


quieres mantener vivo lo que? ¿Pasé el cursor sobre el botón y se mantuvo abierto?
David Chase

leer la última línea de la pregunta
vikas devde

Respuestas:


172

Pruebe con el fragmento de código a continuación:

Pequeña modificación (de la solución proporcionada por vikas) para adaptarse a mi caso de uso.

  1. Abrir popover en el evento hover para el botón popover
  2. Mantenga el popover abierto al pasar el cursor sobre el cuadro de popover
  3. Cierre la ventana emergente en mouseleave para el botón de ventana emergente o el cuadro de ventana emergente.

$(".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>


Esto funciona perfectamente, me di cuenta de que faltaba un ;segundo $(_this).popover("hide"). Pero gracias, ¡fue tan simple y limpio!
chivo expiatorio

3
Esta respuesta es asombrosa. Funciona muy bien en BS3 a partir de mayo de 2015 ^^
degenerado

1
Lo usé en una tabla y agregué container: 'body'a las opciones porque hacía que las celdas se desplazaran. ¡Gran respuesta!
Alexander Derck

El popover se oculta si lo ingresa y luego vuelve al elemento disparador antes de 300ms. Para solucionarlo, verifique si AMBOS el popover y su disparador son: hover antes de ocultarlo en setTimeout. También usaría setTimeout y el mismo enfoque en mouseleave el popover mismo, para arreglar el parpadeo.
rzb

Asegúrese de configurarlo animation:falsepara corregir el parpadeo; consulte el enlace Plunker que tengo arriba. Funciona perfectamente para mí.
OkezieE

84

He venido después de otra solución a esto ... aquí está el código

    $('.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);
    });

6
Es importante agregar, de lo animation: falsecontrario, mover el mouse sobre el enlace repetidamente hará que no funcione correctamente
jasop

5
Tengo una pequeña modificación en tu código @vikas ( gist.github.com/Nitrodist/7913848 ). Vuelve a comprobar la condición después de 50 ms para que no se quede atascado abierto. Es decir, lo vuelve a comprobar continuamente cada 50 ms.
Nitrodist

2
¿Cómo se puede adaptar esto para que funcione en elementos activos recién agregados al documento?
williamsowen

28

Aquí está mi opinión: http://jsfiddle.net/WojtekKruszewski/Zf3m7/22/

A veces, mientras mueve el mouse desde el disparador de popover al contenido de popover real en diagonal , se desplaza sobre los elementos de abajo. Quería manejar tales situaciones: siempre que llegue al contenido de la ventana emergente antes de que se active el tiempo de espera, está a salvo (la ventana emergente no desaparecerá). Requiere delayopción.

Este truco básicamente anula la leavefunción Popover , pero llama al original (que inicia el temporizador para ocultar el popover). Luego, adjunta un oyente único a los mouseenterelementos de contenido de popover.

Si el mouse entra en la ventana emergente, el temporizador se borra. Luego, escucha mouseleaveen popover y, si se activa, llama a la función de licencia original para que pueda iniciar el temporizador de ocultación.

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);
      });
    })
  }
};

5
La búsqueda del contenedor podría mejorarse usando De container = self.$tip;esta manera, el popover incluso se puede encontrar cuando containerse establece la propiedad. Aquí hay un violín: jsfiddle.net/dennis_c/xJc65
dbroeks

3
@pferrel He resuelto este problema en mi bifurcación del violín de @Wojtek_Kruszewski : jsfiddle.net/HugeHugh/pN26d vea la parte que verifica if (!thisTip.is(':visible'))antes de llamar aloriginalShow()
H Dog

1
Si el popover se inicializa con la opción, container: 'body',esta solución no funcionará como se esperaba. La variable containerdebe reemplazarse por self.$tip. Verifique mi respuesta para obtener más detalles: stackoverflow.com/a/28731847/439427
Rubens Mariuzzo

1
Brillante. Esto funciona cuando se usa el parámetro 'selector', a diferencia de las otras respuestas.
jetlej

1
Aquí hay una versión mejorada que corrige un error al salir y volver a ingresar la punta que aún la ocultaba, y también corrige el escenario cuando la punta está unida al cuerpo jsfiddle.net/Zf3m7/1499
Zoltán Tamási

14

Creo que una forma fácil sería esta:

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

De esta forma, el popover se crea dentro del propio elemento de destino. así que cuando mueves el mouse sobre el popover, todavía está sobre el elemento. Bootstrap 3.3.2 funciona bien con esto. La versión anterior puede tener algunos problemas con la animación, por lo que es posible que desee desactivar "animation: false"


Sé que este hilo es antiguo, pero esta es la mejor y más limpia solución en mi opinión y debería tener una clasificación más alta. La única advertencia es que esto se rompería, si coloca el popover (de una manera extraña) "lejos" del elemento disparador. Pero siempre que la distancia entre los dos sea cero (por ejemplo, se superponen), esto funciona de maravilla y no requiere ningún JS personalizado. ¡Gracias!
JohnGalt

Esa es la mejor, limpia y fácil solución hasta ahora. ¡Debería estar mejor clasificado! Agregué delay: { "hide": 400 }para agregar un poco de retraso antes de esconderme y ¡funciona muy bien! 👍
coorasse

14

Usé el gatillo configurado para hovery le di el contenedor configurado al #elementy finalmente agregué una ubicación del boxto right.

Esta debería ser tu configuración:

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

y #exampleCSS necesita position:relative;comprobar el jsfiddle a continuación:

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

Editado

Este violín tiene ambos enlaces que funcionan sin problemas http://jsfiddle.net/davidchase03/FQE57/4/


hmm eso funciona, ¿puedo usar jquery ajax en la contentopción, para tomar el contenido del lado del servidor ... funcionará o necesito hacer un trabajo adicional para eso?
vikas devde

@vikasdevde sí, puede usarlo ajaxen el contenido, pero necesita configurarlo para que funcione ... marque la respuesta correcta si resolvió su OP... para que otros puedan beneficiarse
David Chase

pero si usamos el enlace en sí mismo como un contenedor, todo el popover se convierte en un enlace ... pruébalo
vikas devde

si pones un enlace dentro de la caja, seguirá apareciendo ... ¿correcto?
David Chase

2
Nada de jsfiddle funciona para mí. Chrome 20 de marzo de 2014.
pferrel

7

Así es como lo hice con bootstrap popover con la ayuda de otros bits en la red. Obtiene dinámicamente el título y el contenido de los diversos productos que se muestran en el sitio. Cada producto o popover obtiene una identificación única. Popover desaparecerá al salir del producto ($ this .pop) o el popover. Se usa el tiempo de espera donde se mostrará el elemento emergente hasta que salga a través del producto en lugar de hacerlo.

$(".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();
    };

Esto también funcionará si el popover no es un elemento secundario del elemento de destino. +1
Taha Paksu

6

Aquí hay una solución que ideé que parece funcionar bien y al mismo tiempo le permite usar la implementación normal de Bootstrap para activar todos los popovers.

Violín original: https://jsfiddle.net/eXpressive/hfear592/

Portado a esta pregunta:

<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');
});

2

Estoy de acuerdo en que la mejor manera es usar la que dieron: David Chase , Cu Ly y otros que la forma más sencilla de hacer esto es usar la container: $(this)propiedad de la siguiente manera:

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

Quiero señalar aquí que el popover en este caso heredará todas las propiedades del elemento actual . Entonces, por ejemplo, si hace esto para un .btnelemento (bootstrap), no podrá seleccionar texto dentro del popover . Solo quería dejar constancia de eso, ya que pasé bastante tiempo golpeándome la cabeza con esto.


1

La respuesta de Vikas funciona perfectamente para mí, aquí también agrego soporte para el retraso (mostrar / ocultar).

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);
    });     

También preste atención, cambié:

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

con:

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

para que haga referencia exactamente a ese popover abierto, y no a ningún otro (ya que ahora, a través del retraso, más de 1 podría estar abierto al mismo tiempo)


El comentario que hice al final en realidad no es correcto al usar container: body, si es así, todavía
tengo

1

La respuesta elegida funciona pero fallará si el popover se inicializa con el bodycomo contenedor.

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

Una solución basada en la respuesta elegida es el siguiente código que debe colocarse antes de usar el popover.

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);
            });
        })
    }
};

El cambio es mínimo usando en self.$tiplugar de atravesar el DOM esperando que el popover sea siempre un hermano del elemento.


0

Lo mismo para la información sobre herramientas:

Para mí, la siguiente solución funciona porque no agrega detectores de eventos en cada 'mouseenter' y es posible volver a colocar el cursor sobre el elemento de información sobre herramientas que mantiene viva la información sobre herramientas.

$ ->

  $('.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

0

Esta solución funcionó bien para mí: (ahora es a prueba de balas) ;-)

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);
    });
}

0
        $(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);
            });
        }); 

0

Descubrí mouseleaveque no se dispara cuando suceden cosas extrañas, como que el foco de la ventana cambia repentinamente, luego el usuario regresa al navegador. En casos como ese, mouseleavenunca se disparará hasta que el cursor pase y abandone el elemento nuevamente.

Esta solución que se me ocurrió se basa en mouseenterel windowobjeto, por lo que desaparece cuando el mouse se mueve a cualquier otro lugar de la página.

Esto fue diseñado para funcionar con múltiples elementos en la página que lo activarán (como en una tabla).

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");
        }
    });
});

0

Será más flexible con 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);
    } 
)

0

Sencillo :)

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

0

Recientemente necesité hacer que esto funcionara con KO y las soluciones anteriores no funcionaron bien cuando hubo un retraso en mostrar y ocultar. Lo siguiente debería solucionar este problema. Basado en cómo funcionan las descripciones emergentes de bootstrap. Espero que esto ayude a alguien.

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);
});

-1

Este es mi código para mostrar información sobre herramientas de dinámica con retraso y cargado por 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>");
            }
        });
    }
}

Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.