Removed the ajaxClick function and moved its logic into the live click event handler, where it is now refactored and simplified. Thx to Jeffrey Way for ideas that went into this refactor.

Also, clicks that are triggered on anchors will now be able to make a new http request, which improves listview behavior when clicking LIs that resolve to external urls.

Included in commit is a new demo/test page with various link types to make sure they behave as expected.

Fixes #272, Fixes #264
This commit is contained in:
scottjehl 2010-10-23 17:24:06 -04:00
parent 6f5ce29175
commit e736caebfe
2 changed files with 69 additions and 37 deletions

View file

@ -0,0 +1,40 @@
<!DOCTYPE html>
<html>
<head>
<title>jQuery Mobile Docs - Pages</title>
<link rel="stylesheet" href="../../themes/default" />
<script type="text/javascript" src="../../js/all"></script>
</head>
<body>
<div data-role="page">
<div data-role="header">
<h1>Linking pages</h1>
</div><!-- /header -->
<div data-role="content">
<p>jQuery Mobile is designed to work with simple page linking conventions. The following list demonstrates how different types of links will be handled, either remotely or through an Ajax Request.</p>
<ul data-role="listview" data-inset="true" data-theme="c" data-dividertheme="b">
<li data-role="list-divider">Examples of links that work within a single-page (if the page exists)</li>
<li><a href="docs/pages/index.html">[href="docs/pages/index.html"]</a></li>
<li><a href="/docs/toolbars/index.html">[href="/docs/toolbars/index.html"]</a></li>
<li><a href="#somelocalID">[href="#somelocalID"]</a></li>
<li>Note: an full URL to the same-domain will also work</li>
<li data-role="list-divider">Examples of links that trigger a refresh</li>
<li><a href="docs/pages/index.html" rel="external">[rel="external"]</a></li>
<li><a href="docs/pages/index.html" target="_blank">[target="_blank"]</a></li>
<li><a href="mailto:john@doe.com">[href="mailto:john@doe.com"]</a></li>
<li><a href="tel:543-434-3454">[href="tel:543-434-3454"]</a></li>
<li><a href="http://google.com">[href="http://google.com"]</a></li>
<li data-role="list-divider">Links that return false</li>
<li><a href="#">[href="#"]</a></li>
</ul>
</div><!-- /content -->
</div><!-- /page -->
</body>
</html>

View file

@ -104,47 +104,39 @@
$('#ui-base').attr('href', baseUrl);
}
// send a link through hash tracking
jQuery.fn.ajaxClick = function() {
var href = jQuery( this ).attr( "href" );
pageTransition = jQuery( this ).data( "transition" ) || "slide";
forceBack = jQuery( this ).data( "back" ) || undefined;
nextPageRole = jQuery( this ).attr( "data-rel" );
//find new base for url building
var newBaseURL = getBaseURL();
//if href is absolute but local, or a local ID, no base needed
if( /^\//.test(href) || (/https?:\/\//.test(href) && !!(href).match(location.hostname)) || /^#/.test(href) ){
newBaseURL = '';
//click routing - direct to HTTP or Ajax, accordingly
jQuery( "a" ).live( "click", function(event) {
var $this = $(this),
//get href, remove same-domain protocol and host
href = $this.attr( "href" ).replace( location.protocol + "//" + location.host, ""),
//if it still starts with a protocol, it's external, or could be :mailto, etc
external = /^\w+:|#/.test( href ) || $this.is( "[target],[rel=external]" ),
nullLink = href == '#';
if( nullLink ){
//for links created purely for interaction - ignore
return false;
}
// set href to relative path using baseURL and
if( !/https?:\/\//.test(href) ){
href = newBaseURL + href;
else if( external ){
//deliberately redirect, in case click was triggered
location.href = href;
}
//if it's a non-local-anchor and Ajax is not supported, or if it's an external link, go to page without ajax
if ( ( /^[^#]/.test(href) && !jQuery.support.ajax ) || ( /https?:\/\//.test(href) && !!!href.match(location.hostname) ) ) {
location = href
}
else{
if( $(this).is(unHashedSelectors) ){
changePage(href, pageTransition, undefined);
}
else{
changePage(href, pageTransition, undefined, true);
else {
//use ajax
var pageTransition = $this.data( "transition" ) || "slide",
forceBack = $this.data( "back" ) || undefined,
changeHashOnSuccess = !$(this).is(unHashedSelectors);
nextPageRole = $this.attr( "data-rel" );
//if it's a relative href, prefix href with base url
if( href.indexOf('/') !== 0 && href.indexOf('#') !== 0 ){
href = getBaseURL() + href;
}
changePage(href, pageTransition, forceBack, changeHashOnSuccess);
}
return this;
};
// ajaxify all navigable links
jQuery( "a:not([href='#']):not([target]):not([rel='external']):not([href^='mailto:'])" ).live( "click", function(event) {
jQuery( this ).ajaxClick();
return false;
event.preventDefault();
});
// turn on/off page loading message.
@ -199,7 +191,7 @@
from = toIsArray ? to[0] : $.activePage,
to = toIsArray ? to[1] : to,
url = fileUrl = $.type(to) === "string" ? to.replace( /^#/, "" ) : null,
back = (back !== undefined) ? back : (forceBack || ( urlStack.length > 1 && urlStack[ urlStack.length - 2 ].url === url )),
back = (back !== undefined) ? back : ( urlStack.length > 1 && urlStack[ urlStack.length - 2 ].url === url ),
transition = (transition !== undefined) ? transition : ( pageTransition || "slide" );
//unset pageTransition, forceBack