I'm using the jQuery Mobile option allowSamePageTransition
, which enables me to go from
page A > page A > page A ...
I need this to allow browsing through a catalogue of items. My problem is, the items need some form of interaction and I used to attach the interaction binding to document
, because it is set before the elements affected are generated.
However, reloading the same page over and over again will re-bind my event handlers every time I reload.
My first idea was to use .off
when the page is being hidden, but reloading a page #foo
, will trigger pagehide
on the same page being shown, so all bindings set on
$(document).on("pagebeforeshow.foo_events", "#foo", function(e) {
// bind when shown
});
will be unbound again by the previous #foo
being hidden
$(document).on("pagehide", "#foo", function (e) {
$(this).off(".foo_events");
// removes bindings on #foo being hidden AND shown
});
The only solution I have come up with is plastering the document
with classes, which I don't like doing:
priv.setBindings = function (param) {
var doc = $(document);
doc
.filter(function() { return $(this).is(".e_gallery") !== true; })
.on("pagebeforeshow.gallery", param.pageId, function (e) {
doc.addClass(".e_gallery");
// run stuff
});
};
But I'm no fan of attaching classes to the dom.
Question:
Is there a way to prevent multiple event bindings set on $(document)
when going to the same page over and over again WITHOUT toggling classes?
Best solution would be to use pageinit
to bind events. If you take a look at an official documentation you will find out that pageinit
will trigger ONLY once, just like document ready, so there's no way events will be bound again. This is best solution because you don't have processing overhead like when removing events with off method.
Working jsFiddle example: http://jsfiddle.net/Gajotres/AAFH8/
Of course this will fail in case multiple HTML solution is used.
Remove event before you bind it:
$(document).on('pagebeforeshow', '#index', function(){
$(document).off('click', '#test-button').on('click', '#test-button',function(e) {
alert('Button click');
});
});
Working jsFiddle example: http://jsfiddle.net/Gajotres/K8YmG/
Use a jQuery Filter selector, like this:
$('#carousel div:Event(!click)').each(function(){
//If click is not bind to #carousel div do something
});
Because event filter is not a part of official jQuery framework it can be found here: http://www.codenothing.com/archives/2009/event-filter/
This is probably best solution because event is going to be bound ONLY once.
Probably an easiest of them all.
$(document).on('pagebeforeshow', '#index', function(){
$(document).on('click', '#test-button',function(e) {
if(e.handled !== true) // This will prevent event triggering more then once
{
alert('Clicked');
e.handled = true;
}
});
});
Working jsFiddle example: http://jsfiddle.net/Gajotres/Yerv9/
This is a 180 percent different solution then solution 3, in this case event is going to be bound numerous times but it will be allowed to execute only once.
If you want to find more about this problem take a look at this article, working examples are included.