平凡、常见的用例
我想要一个工具提示,它在鼠标悬停时立即显示正在加载的 GIF,该 GIF 被 AJAX 成功回调产生的 HTML 所取代。 AJAX 工具提示的错误答案几乎与在线问这个确切问题的人一样多。特别是,我一直在模拟我在 this 上的努力。 , this ,尤其是几个答案 here .
对于所有这些解决方案(即使是那些专门声称可以解决该问题的解决方案),我一直遇到的问题是,工具提示偶尔会延迟出现并且无法消失。这也不是库问题,因为我过去在使用 jQuery-UI 工具提示时遇到过同样的问题。
图书馆
- jQuery v2.2.3
- Bootstrap v3.3.6
之前尝试过使用 jQuery 1 并遇到了同样的问题:
- jQuery v1.12.3
我的页面也依赖于 jQuery Datatables v1.10.11 库,但这与工具提示问题是正交的,除了我的特定用例生成更多更快的具有可变延迟的 AJAX 工具提示请求,这增加了可能性观察“粘附”问题。
当前尝试
我目前的解决方案大致基于“towr”的回答 here这非常接近工作。我已经尝试了页面上方的每个 解决方案,但它们要么由于某种原因损坏,要么存在“粘附”工具提示问题。
因此,在 AJAX 请求加载数据以填充表格后,我按类遍历单元格 $( ".tooltip-cell" ).on( "mouseover", set_tooltip )
, 其中set_tooltip
是一个执行以下操作的函数
var $e = $(this);
if( $e.attr( "title" ) === undefined ) { // request data once per cell
// show loading GIF
$e.attr( "title", "<img src='images/wait.gif'/>" );
$e.tooltip(
{
html: true,
trigger: "hover"
}
).tooltip( "show" );
// perform AJAX GET
$.ajax(
{
url: "ajax/tooltip_data.php",
data:
{
lookup_id: $e.attr("lookup_id")
},
success:
function(response) {
// prepare final version of tooltip
$e.attr( "title", response ).tooltip( "fixTitle" );
// if mouse still hovers, display final version
if( $e.is( ":hover" ) ) {
$e.tooltip( "show" );
}
},
dataType: "html"
}
);
}
这里的问题是 AJAX 成功回调中的悬停检测。现在显然是 .is(":hover")
已经弃用了很长一段时间,所以我尝试了各种替代方法,例如 $( ":focus :active" ).filter( $e ).length > 0
,但结果总是要么显示所有工具提示并粘贴,要么显示不工具提示。通过引入 setTimeout( function() {}, 2000 );
很容易重现这一点将代码包装在回调中。然后问题总是出现。事实上,我可以创建 10 个相邻的工具提示,将鼠标移到它们上面,2 秒后,它们将与 AJAX HTML 一起出现并粘住,尽管事实上鼠标没有悬停在它们中的任何一个上。通过打印语句和调试,我可以验证 if( <hover-check> )
中的值反过来,这 10 个元素中的每一个都是正确的,因此悬停检查本身不正确或返回陈旧信息。
症结所在
当与该元素对应的回调已准备好工具提示内容时,如何准确确定鼠标当前是否位于该元素的顶部?
其他想法
我在处理这个问题时遇到了两个复杂的问题,但我认为它们没有关联。
1) 我得到一个错误 .tooltip()
是未定义的,除非我的 jQuery JS 包含在 <head>
中我的 Bootstrap JS 包含在我的 HTML 正文的底部。如果我向上移动 Bootstrap 或向下移动 jQuery(始终将 jQuery 保持在 Bootstrap 之上),我会收到错误消息。
2) 解决方案 here看起来不错,但无论我尝试多么仔细地复制代码,我都会得到 $el.data(...) undefined
$el.data('tooltip').tip().is(':visible')
行的错误在我的代码中。尽管链接的演示页面本身对我来说工作正常。
总希望
我希望这个问题可以成为想要这样做的人的规范资源,因为我昨天实际上花了 16(是的,真的 16)个小时来研究这个,实现我能想到的每一个解决方案的每一个变体在线。
最佳答案
核心理念
对我来说,关键在于提供的解决方案 here ,我已在原始问题中链接。
这个解决方案出现在源代码中的问题是使用 $el.data('tooltip').tip().is(':visible')
这总是导致错误 $el.data(...) undefined
,但是检查工具提示的显示状态而不是鼠标悬停状态的想法似乎很有希望。
仔细检查 Bootstrap v3.3.6 工具提示操作后发现,它将悬停元素上的“aria-describedby”设置为工具提示的元素 ID。有了这些信息,我们可以做 $( "#"+ $el.attr( "aria-describedby") ).is( ":visible")
我不知道这将如何适应 future ,但它最终是“坚持”的。
代码
$( ".ajax-tooltip-required" ).tooltip(
{
html: true,
trigger: "manual"
}
).on(
{
mouseenter:
function() {
var $el = $(this);
if( $el.data( "fetched" ) === undefined ) {
$el.data( "fetched", true );
$el.attr( "data-original-title", "<img src='images/wait.gif'/>" ).tooltip( "show" );
$.ajax(
{
url: "ajax/tooltip_data.php",
data: {
lookup_id: $el.attr("lookup_id")
},
success:
function( response ) {
$el.attr( "data-original-title", response );
if( $( "#" + $el.attr( "aria-describedby" ) ).is( ":visible" ) ) {
$el.tooltip( "show" );
}
},
dataType: "html"
}
);
} else {
$(this).tooltip( "show" );
}
},
mouseleave:
function() {
$(this).tooltip( "hide" );
}
}
);
关于javascript - 使用 AJAX 的 Bootstrap 工具提示(再来一次),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/37166278/