From d24443fb55ddc6a309c08a9a248128fef269d2a3 Mon Sep 17 00:00:00 2001
From: jeresig <jeresig@gmail.com>
Date: Mon, 25 Jan 2010 13:45:07 -0500
Subject: [PATCH] Make sure that it's possible to preventDefault
 natively-triggered (submit, focus, blur, click) events.
 Fixes #5695.

---
 src/event.js       |   52 ++++++++++++++++++++++++++++++++--------------------
 test/unit/event.js |   30 +++++++++++++++++++++++++++++-
 2 files changed, 61 insertions(+), 21 deletions(-)

diff --git a/src/event.js b/src/event.js
index a4b8f6c..9873185 100644
--- a/src/event.js
+++ b/src/event.js
@@ -270,36 +270,48 @@ jQuery.event = {
 			handle.apply( elem, data );
 		}
 
-		var nativeFn, nativeHandler;
+		var parent = elem.parentNode || elem.ownerDocument;
+
+		// Trigger an inline bound script
 		try {
 			if ( !(elem && elem.nodeName && jQuery.noData[elem.nodeName.toLowerCase()]) ) {
-				nativeFn = elem[ type ];
-				nativeHandler = elem[ "on" + type ];
+				if ( elem[ "on" + type ] && elem[ "on" + type ].apply( elem, data ) === false ) {
+					event.result = false;
+				}
 			}
+
 		// prevent IE from throwing an error for some elements with some event types, see #3533
 		} catch (e) {}
 
-		var isClick = jQuery.nodeName(elem, "a") && type === "click";
+		if ( !event.isPropagationStopped() && parent ) {
+			jQuery.event.trigger( event, data, parent, true );
 
-		// Trigger the native events (except for clicks on links)
-		if ( !bubbling && nativeFn && !event.isDefaultPrevented() && !isClick ) {
-			this.triggered = true;
-			try {
-				elem[ type ]();
-			// prevent IE from throwing an error for some hidden elements
-			} catch (e) {}
+		} else if ( !event.isDefaultPrevented() ) {
+			var target = event.target, old,
+				isClick = jQuery.nodeName(target, "a") && type === "click";
 
-		// Handle triggering native .onfoo handlers
-		} else if ( nativeHandler && elem[ "on" + type ].apply( elem, data ) === false ) {
-			event.result = false;
-		}
+			if ( !isClick && !(target && target.nodeName && jQuery.noData[target.nodeName.toLowerCase()]) ) {
+				try {
+					if ( target[ type ] ) {
+						// Make sure that we don't accidentally re-trigger the onFOO events
+						old = target[ "on" + type ];
 
-		this.triggered = false;
+						if ( old ) {
+							target[ "on" + type ] = null;
+						}
+
+						this.triggered = true;
+						target[ type ]();
+					}
+
+				// prevent IE from throwing an error for some elements with some event types, see #3533
+				} catch (e) {}
+
+				if ( old ) {
+					target[ "on" + type ] = old;
+				}
 
-		if ( !event.isPropagationStopped() ) {
-			var parent = elem.parentNode || elem.ownerDocument;
-			if ( parent ) {
-				jQuery.event.trigger( event, data, parent, true );
+				this.triggered = false;
 			}
 		}
 	},
diff --git a/test/unit/event.js b/test/unit/event.js
index 99ed419..df01bae 100644
--- a/test/unit/event.js
+++ b/test/unit/event.js
@@ -394,7 +394,7 @@ test("trigger() bubbling", function() {
 });
 
 test("trigger(type, [data], [fn])", function() {
-	expect(12);
+	expect(14);
 
 	var handler = function(event, a, b, c) {
 		equals( event.type, "click", "check passed data" );
@@ -439,6 +439,34 @@ test("trigger(type, [data], [fn])", function() {
 		pass = false;
 	}
 	ok( pass, "Trigger on a table with a colon in the even type, see #3533" );
+
+	var form = jQuery("<form action=''></form>").appendTo("body");
+
+	// Make sure it can be prevented locally
+	form.submit(function(){
+		ok( true, "Local bind still works." );
+		return false;
+	});
+
+	// Trigger 1
+	form.trigger("submit");
+
+	form.unbind("submit");
+
+	jQuery(document).submit(function(){
+		ok( true, "Make sure bubble works up to document." );
+		return false;
+	});
+
+	// Trigger 1
+	form.trigger("submit");
+
+	jQuery(document).unbind("submit");
+
+	form.remove();
+});
+
+test("jQuery.Event.currentTarget", function(){
 });
 
 test("trigger(eventObject, [data], [fn])", function() {
-- 
1.7.10.4