如何在加载jQuery之前阻止点击事件的链接?
原因是我有很少的链接通过jQuery ajax函数调用AJAX,如果用户在加载jQuery框架之前单击它们,浏览器无法触发jQuery ajax函数并将跟随链接href =“...”
感谢。
编辑:我可以使用它吗?
<head>
...
<script type="text/javascript">
window.onload = prevCl();
function prevCl() {
var links = document.links[];
links.onclick = check();
}
function check() {
if (typeof jQuery == 'undefined') {
return false;
}
}
</script>
</head>
答案 0 :(得分:9)
四种选择:
选项0
阅读Sean Hogan's answer,他指出这可以通过委托( doh!)完成,并且我将一个示例实现放在一起。
选项1
你可以使链接的href
“#”直到加载jQuery,然后(如果合适的话)将其更改为它应该是什么。您可以存储href
属于data-
属性的内容,例如:
<a href='javascript:;' data-href='realtarget.html'>blah</a>
然后:
jQuery(function($) {
$("a[data-href]").each(function() {
var $this = $(this);
$this.attr("href", $this.attr("data-href"));
});
});
同样,只有当你真的需要将href设为href时才是最后一位。如果您通过JavaScript处理点击,则无需。
如果验证是开发周期的重要部分,请务必注意data-xyz
形式的属性在HTML4及之前是无效的(浏览器实际上并不关心,但如果使用验证,则再次。 ..)。它们从HTML5开始有效。
选项2
使用内联onclick
属性在jQuery加载之前拦截点击,并基本上说“抱歉,一刻”。因此,在您文件的顶部的script
标记中:
function sorryLoading() {
alert("Sorry, the page is still loading, one moment please.");
return false;
}
...然后在链接上:
<a href='realtarget.html' class='sorry' onclick='return sorryLoading();'>blah</a>
...然后删除jQuery load上的onclick
:
jQuery(function($) {
$("a.sorry").removeClass('sorry').attr("onclick", "").click(yourRealClickHandler);
});
(如果他们没有相同的点击处理程序,你可以留下最后一位 - click
来电。)
我使用上面的一个类来区分这些链接和其他可能具有内联onclick
的链接(否则,令人惊讶的是选择器“a [onclick]”实际上适用于Chrome,Opera和Firefox for Linux和Windows上的IE6和IE8。)
选项3
因为听起来你希望页面在jQuery加载之前不起作用,所以这是另一种方法:
head
部分(不在底部,我通常建议放在其中)。body
代码之前,将>> >>的点击处理程序与jQuery.ready
调用(或其中的任何一个)挂钩快捷方式)。原因是:#1将确保在呈现页面之前加载jQuery本身,而#2将尽快连接处理程序 。 Google建议在页面末尾使用标记(而不是ready
函数或类似标记),并说在那时,DOM元素就可以被发现了。
另外,当然,您希望通过执行所有页面加载优化的内容,确保链接不能达到用户期望的时间绝对尽可能简短您可以。点击一个链接而没有它看起来像它确实会导致糟糕的用户体验。
答案 1 :(得分:4)
您可以使用事件委派:相当于jQuery live()和delegate()方法的DOM。
以下可能有效:
<head>
<script>
function linkMatcher(node) { // modify this if not all links are disabled
if (node.href) return true;
else return false;
}
document.onclick = function(e) {
e = e || window.event;
var target = e.target || e.srcElement;
for (var node=target; node!=document; node=node.parentNode) {
if (node.tagName == "A") return !linkMatcher(node);
}
}
</script>
</head>
编辑:这会永久禁用链接。可以通过删除事件处理程序来重新启用它们,例如, document.onclick = null
。
下面的complete, live example适用于Chrome,Opera和Firefox for Linux以及适用于Windows的IE6和IE8。它会阻止点击“等待”类的链接(如果您愿意,可以改为完成所有链接),并记住点击的第一个链接。然后它模拟一个长的加载延迟(五秒),然后在链接上挂钩jQuery处理程序并删除阻止点击的文档级处理程序,然后在单击的链接上触发jQuery处理程序(请注意,这只会触发处理程序,而不是底层的默认行为 - 但是当你想触发你的ajax时,我认为没关系)。 - T.J.克劳德
HTML:
<!DOCTYPE html>
<html>
<head>
<script class="jsbin" src="http://ajax.googleapis.com/ajax/libs/jquery/1.4.2/jquery.min.js"></script>
<meta charset=utf-8 />
<title>Link Click Delay Test Page</title>
<!--[if IE]>
<script src="http://html5shiv.googlecode.com/svn/trunk/html5.js"></script>
<![endif]-->
<style>
article, aside, figure, footer, header, hgroup,
menu, nav, section { display: block; }
body {
font-family: sans-serif;
}
p {
margin: 0px;
}
</style>
<script type='text/javascript'>
// A scoping function to avoid creating global symbols
(function() {
// Figure out what to hook clicks on
var container =
document.body ||
document.documentElement ||
document;
// Hook clicks that reach the bottom level
hookClicks();
function hookClicks() {
if (container.attachEvent) {
container.attachEvent("onclick", handleClick);
}
else if (document.addEventListener) {
container.addEventListener("click", handleClick, false);
}
}
// Set up an unhook function for jQuery to call
window.unhookClicks = unhookClicks;
function unhookClicks() {
if (container.attachEvent) {
container.detachEvent("onclick", handleClick);
}
else if (document.addEventListener) {
container.removeEventListener("click", handleClick, false);
}
}
// Handle clicks
function handleClick(event) {
var target;
// Handle Microsoft vs. W3C event passing style
event = event || window.event;
// Get the target (again handling Microsoft vs. W3C style)
target = event.target || event.srcElement;
// Do we have a target that's an A with the class "wait"?
if (target &&
target.tagName.toUpperCase() === "A" &&
(" " + target.className + " ").indexOf(" wait ") >= 0
) {
// It's a link we want to prevent for the moment
// Remember the element that was clicked if there
// isn't already one (or replace it, depends on the
// UX you want to provide
if (!window.pendingLink) {
window.pendingLink = target;
}
// Prevent it from being processed
if (event.preventDefault) { // If W3C method...
event.preventDefault();
}
// This should work if preventDefault doesn't
return false;
}
}
})();
</script>
</head>
<body>
<p><a href='http://www.google.com' class='wait'>Google</a>
- This one waits
<br><a href='http://news.bbc.co.uk' class='wait'>BBC News</a>
- This one also waits
<br><a href='http://www.cnn.com'>CNN</a>
- This one doesn't wait, it goes immediately
</p>
</body>
</html>
JavaScript(无论你的jQuery ready
处理程序在哪里):
jQuery(function($) {
// Use setTimeout to fake a long delay loading
setTimeout(function() {
// Hook up our proper click handling
// Obviously, replace this with whatever does the ajax
$("a.wait").click(function(event) {
alert("The jQuery handler for " + this.href + " link was triggered.");
});
// If we have clicks disabled, enable them
if (window.unhookClicks) {
window.unhookClicks();
window.unhookClicks = undefined;
}
// Do we have a pending link to follow?
if (window.pendingLink) {
// Yes, grab it and clear it
var $link = $(window.pendingLink);
window.pendingLink = undefined;
// Trigger any jQuery event handlers on it.
// Note that this will NOT follow the link,
// just trigger jQuery event handlers that
// are on the link.
$link.click();
}
// We've loaded!
$("<p>Finally loaded!</p>").appendTo(document.body);
// End of fake delay function
}, 5000);
});
答案 2 :(得分:1)
我还没有尝试过,但理论上,只要jquery未完成,就可以向所有阻止默认操作(打开链接)的元素添加一个没有jquery的事件处理程序?
getElementsByTagNames('a').addEventListener('click',function (event) {
if (typeof jQuery == 'undefined') {
event.preventDeafault();
}
},false)