jQuery Multiple Event Handlers - How to Cancel?
Asked Answered
A

6

49

I have two functions bound to a click event at two different times (using jQuery). The order in which they are fired is significant. They are firing in the correct order. The problem is, when the first function returns false, the second function is still firing!

How can I properly cancel the event?

Example code:

$(document).click(function() { 
  alert('a');
  return false;
});

$(document).click(function() {
  alert('b');
});

You will still see the "b" alert message when clicking the page. This is unacceptable!

Althing answered 16/3, 2009 at 23:13 Comment(0)
H
88

Use the stopImmediatePropagation function of the jQuery event object.

Keeps the rest of the handlers from being executed. This method also stops the bubbling by calling event.stopPropagation().

$(document).click(function(event) { 
  alert('a');
  event.stopImmediatePropagation();
  return false;
});

$(document).click(function() {
  alert('b');
});
Hanukkah answered 16/3, 2009 at 23:31 Comment(2)
You might want to note that you need to be using jQuery version 1.3 and above for this to work.Althing
what about $(document).on("touchstart click", ".myelement", function(e) {e.stopImmediatePropagtion(); //run function here})...If the touchstart fires first on the tablet device will it cancel the click from firing if I keep my finger held down?Collate
C
2

The first thing I'm asking is: why do you have two functions bound to the same click event? Having access to the code, why don't you just make that one single call?

$(function (){
    var callbackOne = function(e){
        alert("I'm the first callback... Warning, I might return false!");
        return false;
    };

    var callbackTwo = function(e){
        alert("I'm the second callback");
    };

    $(document).click(function (e){
        if(callbackOne(e)){
            callbackTwo(e);
        }
    });
});
Collectanea answered 16/3, 2009 at 23:28 Comment(4)
Organization. There is a ton of Javascript code in this app, and it is split up into SEVERAL files. This way, each page only downloads what is necessary, resulting in rapid load times. I have an HTTP handler that combines, compresses, and caches them, too, so they all get fetched in one request.Althing
Ok. So is there really the need for -1? Just trying to help... Your explanation is enough to let us all know it's not the solution for you.Collectanea
Sorry then! :) Don't know who would want to waste his reputation by down-voting a possible valid answer for other people...Collectanea
+1. I've answered plenty of questions by asking "Why are you doing it this way instead of this other way?" Sometimes the asker isn't aware of or forgot to consider other options.Signory
T
2

Thanks, unbind works for redefining functions.

  $(document).ready(function(){
        $("#buscar_mercaderia").click(function(){ alert('Seleccione Tipo de mercaderia'); 
   });
$(".tipo").live('click',function(){
            if($(this).attr('checked')!=''){
                if($(this).val()=='libro'){
                    $("#buscar_mercaderia").unbind('click');
                    $("#buscar_mercaderia").click(function(){  window.open('buscar_libro.php','Buscar Libros', 'width=800,height=500'); });
                }else if($(this).val()=='otra'){
                    $("#buscar_mercaderia").unbind('click');
                    $("#buscar_mercaderia").click(function(){ window.open('buscar_mercaderia.php','Buscar Mercaderias', 'width=800,height=500');  });
                }
            }
        })
Tricia answered 4/3, 2011 at 18:41 Comment(0)
V
1

Does using unbind help?

$(document).click(function() { 
  alert('a');
  $(this).unbind('click');
  return false;
});
Verecund answered 16/3, 2009 at 23:16 Comment(6)
I still need my second event to fire when the first function does NOT return false. Won't unbinding literally "unbind it"?Althing
you can merge my solution with nickf solution and you'll get your behavior :)Dareece
Problem with unbind is that other bound function will fail to trigger.Collectanea
The whole approach seems like a tacky workaround! I need a simple way to cancel the event, nothing more. In regular Javascript, a return means a return, be it true or false. Doesn't seem the same way in jQuery. There HAS to be a way to simulate the "return" functionality using jQuery.Althing
jquery is javascript :p, it's just a library, not a new languageDareece
@Josh: There's no reason to be rude. Cut that out.Weise
D
0

If what nickf said doesn't work, you could use a small state machine:

var trigger = 0;

$(document).click(function() { 

  alert('a');
  if(you_want_to_return_false) {
    trigger = 1;
    return false;
  }
});

$(document).click(function() {
  if(trigger !== 0) {
  alert('b');
  } 
  trigger = 0;
});

Not the prettiest solution, but it will work.

Dareece answered 16/3, 2009 at 23:19 Comment(2)
well, my idea works it's just that it breaks it at the same time. +1 for this idea though.Verecund
This method breaks exactly the same way as the other one does, except with more code. Correct me if I am wrong.Althing
M
0

An other solution is to debounce or throttle the function.

This way you could ensure despite it firing multiple times, it only executes within a set duration. This would allow your code to work as-is.

Milldam answered 8/9, 2020 at 19:47 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.