Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

preventDefault() doesn't prevent the action

When I use event.preventDefault() on a link it works, however when I use it on a button doesn't!

DEMO

My code:

<a id="link" href="http://www.google.com">link</a>
<button id="button" onclick="alert('an alert')">button</button>​

$('#link').click(function(event){
  event.preventDefault();
});
$('#button').click(function(event){
  event.preventDefault();
});

​ Link action is cancelled, but when I click on the button, still executes the onClick action.

Any help? what I want to do is to prevent the button onClick action without changing the button html (I know how to do

$('#button').removeAttr('onclick');

like image 916
ilyes kooli Avatar asked May 03 '12 13:05

ilyes kooli


People also ask

What does preventDefault () do?

preventDefault() The preventDefault() method of the Event interface tells the user agent that if the event does not get explicitly handled, its default action should not be taken as it normally would be.

What is the opposite of event preventDefault ()?

There is no opposite method of event. preventDefault() to understand why you first have to look into what event. preventDefault() does when you call it. Underneath the hood, the functionality for preventDefault is essentially calling a return false which halts any further execution.

Is there any significant difference between event preventDefault () vs return false to stop event propagation?

e. preventDefault() will prevent the default event from occuring, e. stopPropagation() will prevent the event from bubbling up and return false will do both. Note that this behaviour differs from normal (non-jQuery) event handlers, in which, notably, return false does not stop the event from bubbling up.


2 Answers

You want event.stopImmediatePropagation(); if there are multiple event handlers on an element and you want to prevent the others to execute. preventDefault() just blocks the default action (such as submitting a form or navigating to another URL) while stopImmediatePropagation() prevents the event from bubbling up the DOM tree and prevents any other event handlers on the same element from being executed.

Here are some useful links explaining the various methods:

  • http://api.jquery.com/event.preventDefault/
  • http://api.jquery.com/event.stopPropagation/
  • http://api.jquery.com/event.stopImmediatePropagation/

However, since it still doesn't work it means that the onclick="" handler executes before the attached event handler. There's nothing you can do since when your code runs the onclick code has already been executed.

The easiest solution is completely removing that handler:

$('#button').removeAttr('onclick');

Even adding an event listener via plain javascript (addEventListener()) with useCapture=true doesn't help - apparently inline events trigger even before the event starts descending the DOM tree.

If you just do not want to remove the handler because you need it, simply convert it to a properly attached event:

var onclickFunc = new Function($('#button').attr('onclick'));
$('#button').click(function(event){
    if(confirm('prevent onclick event?')) {
        event.stopImmediatePropagation();   
    }
}).click(onclickFunc).removeAttr('onclick');
like image 83
ThiefMaster Avatar answered Oct 12 '22 23:10

ThiefMaster


you need stopImmediatePropagation not preventDefault. preventDefault prevents default browser behavior, not method bubbling.

http://api.jquery.com/event.stopImmediatePropagation/

http://api.jquery.com/event.preventDefault/

like image 31
Thomas Jones Avatar answered Oct 12 '22 23:10

Thomas Jones