I've got a website in development with new pages loaded via AJAX instead of traditional page loads. Most links on the site will use AJAX to load a new page, however there are some links I need to exclude from this behaviour. For example, local hash links that simply scroll you down to an anchor on the same page. Or, links to PDF files that are hosted locally but should obviously not be loaded via AJAX. I have enough control over the HTML that I can simply add a class to these links that I want to exclude, such as .local-anchor, or .pdf. The code I have effectively excludes these links if you directly load the page the first time, however any time the page is loaded via AJAX my exclusion no longer works. The .local-anchor links and any others that should be excluded are still somehow executing the AJAX functions. Example of the relevant JS code:
$(document).on("click", "a:not('.local-anchor, .pdf')", function(e) {
var href = $(this).attr("href");
// check that it points to this domain
if ( href.indexOf(document.domain) > -1 || href.indexOf(':') === -1 ) {
history.pushState({}, '', href);
loadPage(href);
e.stopPropagation();
e.preventDefault();
}
});
You can see this live page (in development) here: http://dma.nz/practice/
The links:
Our approach to design
The architectural process
Awards + Publications
Contact
Scroll you to anchors further down the same page and should be excluded. Yet if this page is loaded via AJAX (test by navigating to one of the other main nav links on top right and then return to Practice) then these links are triggering AJAX to reload this same page which screws things up.
How do I need to amend this JS to make sure they are ALWAYS excluded?
Related
I'm currently working on a web project with jQuery mobile but navigation just won't work.
When i hit a page from the menu (eg. "customers") the url displays correctly (www.aaa.bb/#customers) and the page is loaded without any problems. When i hit another page the url is also correct and the page loads but when i then try to go back using the browser's back button the page doesn't change even though the url changes correctly..
I have seperate files for my different pages. Could this cause the problem?
If so, why does the url change correctly then?
Thank you!
Edit: Ajax is enabled on my page
If you are using AJAX to navigate throughout your site it is necessary to update the history yourself using history.pushState, since your HTTP (ajax) call will otherwise not be logged and stored in the history.
There are various ways you can manipulate the history, or change how you AJAX calls get fired, here is a solid doc on how to manipulate browser history, follow this up by creating a function that checks onpopstate event that is fired and update your page.
After hours of reading docs and testing different attempts I wrote this solution:
$(window).on("navigate", function(){
var file="/";
if(typeof history.state.pageUrl != 'undefined') {
file += history.state.pageUrl + ".php";
}
else{
file += "index.php";
}
$(":mobile-pagecontainer").pagecontainer( "change", root + file, {"reverse": true} );
});
This solution only works for my specific problem and may not work for others.
Known limitations:
all your jQuery Mobile pages have to be in the root directory of you website
the filenames of your pages have to be equal to their data-url attribute
all your pages have to have the same file extension (.php)
Dialogs will probably cause trouble too. I am also facing a strange issue when navigating to my index.php file.
I will improve my solution over time and post it again.
I have a website that's mostly generated via PHP and uses the jQuery library (v1.11.1). My problem is that I would like to link to anchor tags that are generated dynamically on separate pages.
For example, I have the following link on index.php?page=Home:
And on the page that's loaded when $_GET[page] == "ABC," I have the anchor:
<a name="firstItem"></a>
So far, so good. But when I try to click the link, it redirects to the page without jumping to the anchor. The same behaviour happens if I click Reload. However, if I enter the URL directly into the browser window, it DOES jump to the anchor.
I've found that the problem goes away if I delete the "function detach()" from the jQuery file, but then some other libraries that I've loaded fail to work. Any suggestions?
My project is to have preview of some websites inside my website, I'm using Iframe for now to load the website preview and then the user can interact within the Iframe.
I have to change the Iframe implementation to be within the page For SEO purpose, So what could be the replacement is Jquery .load() function.
$('div#websitePreview').load('Website_URL');
but the problem is when the user interact with the website (click some link) the whole page will redirect to the new link, so is there a way to load the page which been clicked by the user in the same div by ajax call without leaving my website?
UPDATE:
The websites I'm going to preview have subdomains of my original site
There is no way to achieve this, due cross domain security restrictions in modern browsers. You aren't allowed to access other domains content via ajax.
The other point is, that you may have css bugs if you load an entry page in a div on your site, because the loaded css will override your site's css.
Assuming the websites you are 'previewing' are on the same domain as your website, you can amend every a tag within the loaded div to perform an AJAX request with the following code:
var $container = $('#websitePreview')
$container.load('http://www.example.com'); // initial load
// link click within loaded content.
$container.on('click', 'a', function(e) {
e.preventDefault();
$container.load($(this).attr('href'));
});
On the other hand, if the previewed sites are on separate domains, you cannot load HTML from them due to the Same Origin Policy. An iframe or CORS request is your only option in those situations, and if the url is 3rd party, the latter is extremely unlikely to happen.
try
$('div#websitePreview a').live('click', function(event){
event.preventDefault();
var url = $(this).attr('href');
$('div#websitePreview').load(url);
}
I'm working on a web app with JQuery Mobile 1.2 and php. From the profile page, I have a popup asking the user to confirm logout. What I want to do is intercept that button with a click event to process the logout via an ajax request.
I have a custom.js file included in all my project pages. The app loads in the accounts page. I know it is getting loaded and working across the ajax navigation.
When I include this code in custom.js:
$("#perfil").live('pageshow',function(event){
alert('This page was just enhanced by jQuery Mobile!');
});
I get the alert when the profile page is shown. The problem is the click function.
When I include this:
$("#perfil").live('pageshow',function(event){
alert('This page was just enhanced by jQuery Mobile!');
$('#logoutButton').click(function(){
$('#output').html('Logging Out...');
$.get("api/logout",function(data){
if(data.success) {
window.location = "index"
}
else{
$('#output').html('Logout failed. Try again');
}
}, "json");
});
});
The behavior is odd. When I navigate from the main page to the profile page, I get the alert. But the button doesn't respond. However, when I refresh (or initially load the app from the profile page) the button behaves correctly and runs the the javascript logout function.
Here is the code for the html button:
<a id="logoutButton" data-role="button" data-icon="check"
data-inline="true" data-theme="e">Si, finalizar.</a>
Your custom.js on your profile page is not actaully getting loaded (more on that below), and as a result when you are binding the click event your button does not exist in the DOM, you can get around this by using event delegation for example
$(document).on('click', '#logoutButton', function(){
$('#output').html('Logging Out...');
$.get("api/logout",function(data){
if(data.success) {
window.location = "index"
}
else{
$('#output').html('Logout failed. Try again');
}
}, "json");
});
Now the reason why your custom.js isn't getting loaded is because by default when you load a page in jQuery Mobile the default behavior is to load just the data-role="page" div via ajax and attach it to the DOM of the current page. The important part to realize is that only the div page gets loaded, and not any other resources on that page.
If you want a custom script on a seperate page to be loaded you need to include it within the div data-role="page" wrapper. You can also tell JQM to fully load a page without ajax by using the data-ajax="false" attribute on your links (or rel="external" if its a different domain).
As a side point you should consider using .on instead of .live as of jQuery 1.7 .live has been depreciated.
In JQM, it all depends on how your data is initialized and how the pages are structured.
When loading your main page, all scripts are initialized once and cached for "Ajax" like response and feel.
If your main and profile page are in a multi-page format, your click button won't be an issue as the scripts are initialized once.
Or if you are in a single page, rel="external" from main to profile page will work. External links will force JQM to make a new HTTP request; However, you do loose page transition effects.
I believe a better architecture is to create single JQM pages and utilize a log-out button
Log-out as a binding function.
*How to bind your click function:
$('#foo').bind('click', function() {
alert('User clicked on "foo."');
});
Source
I'm developing an application in which I have internal and external links. i noticed that Jquery mobile does not load the spinner when an external link is clicked:
Example
Spinner is shown
Spinner is NOT shown
I have tried :
$('a[href][rel=external]').click(function(){ //doesnt work
$.mobile.showPageLoadingMsg();
}
and:
$('a[href][rel=external]').click(function(){
// shows the spinner but it gets stuck forever
$.mobile.showPageLoadingMsg();
$('#loadingDiv').div("refresh");
}
can someone help me show the spinner when the rel = external links are clicked?
http://jquerymobile.com/test/docs/pages/page-links.html
Links that point to other domains or that have rel="external",
data-ajax="false" or target attributes will not be loaded with Ajax.
Instead, these links will cause a full page refresh with no animated
transition. Both attributes (rel="external" and data-ajax="false")
have the same effect, but a different semantic meaning: rel="external"
should be used when linking to another site or domain, while
data-ajax="false" is useful for simply opting a page within your
domain from being loaded via Ajax. Because of security restrictions,
the framework always opts links to external domains out of the Ajax
behavior.
You wouldn't get a loading spinner as it is just going to do a page redirect. Also for your jsfiddle, google.com will not work as they don't allow iframe access. If you change it to another site like http://jsfiddle.net it will switch the site properly.
If you MUST show the spinner, you can do something like this
http://jsfiddle.net/RqkYM/10/
$('a[href][rel=external]').click(function(e){
e.preventDefault();
e.stopPropagation();
$.mobile.showPageLoadingMsg();
window.location = $(this).attr('href');
});
It will display the spinner then do a redirect
If you want, you could load the external page with $.mobile.changePage() See here for docs
It has a showLoadMsg option that "Decides whether or not to show the loading message when loading external pages."
EDIT:
Here is an example of loading an external page like I described:
http://jsfiddle.net/KYvDv/2/
$.mobile.changePage( "/gQxCN/1/show/", {
showLoadMsg: true
});