From 1c2882e5e684f95acdddcf569c5951bad3063b20 Mon Sep 17 00:00:00 2001 From: "joki%netscape.com" Date: Sun, 28 Mar 1999 22:22:54 +0000 Subject: [PATCH] Updating internal implementations to new DOM2 api syntax, capture/bubble functionality, new EventStateManager stuff (focus improvements) --- content/base/src/nsDocument.cpp | 67 +- content/base/src/nsDocument.h | 12 +- content/base/src/nsGenericDOMDataNode.cpp | 63 +- content/base/src/nsGenericDOMDataNode.h | 60 +- content/base/src/nsGenericElement.cpp | 65 +- content/base/src/nsGenericElement.h | 60 +- .../events/public/nsIEventListenerManager.h | 32 +- content/events/public/nsIEventStateManager.h | 17 +- content/events/src/nsDOMEvent.cpp | 6 +- content/events/src/nsDOMEvent.h | 4 - content/events/src/nsEventListenerManager.cpp | 713 +++++++++++++----- content/events/src/nsEventListenerManager.h | 81 +- content/events/src/nsEventStateManager.cpp | 145 ++-- content/events/src/nsEventStateManager.h | 18 +- .../html/content/src/nsHTMLAnchorElement.cpp | 47 +- content/html/style/src/nsCSSStyleSheet.cpp | 11 +- content/html/style/src/nsHTMLStyleSheet.cpp | 6 +- content/xml/content/src/nsXMLElement.cpp | 54 +- layout/base/nsPresShell.cpp | 2 +- layout/base/src/nsDocument.cpp | 67 +- layout/base/src/nsDocument.h | 12 +- layout/base/src/nsGenericDOMDataNode.cpp | 63 +- layout/base/src/nsGenericDOMDataNode.h | 60 +- layout/base/src/nsGenericElement.cpp | 65 +- layout/base/src/nsGenericElement.h | 60 +- .../events/public/nsIEventListenerManager.h | 32 +- layout/events/public/nsIEventStateManager.h | 17 +- layout/events/src/nsDOMEvent.cpp | 6 +- layout/events/src/nsDOMEvent.h | 4 - layout/events/src/nsEventListenerManager.cpp | 713 +++++++++++++----- layout/events/src/nsEventListenerManager.h | 81 +- layout/events/src/nsEventStateManager.cpp | 145 ++-- layout/events/src/nsEventStateManager.h | 18 +- layout/forms/nsHTMLButtonControlFrame.cpp | 4 +- layout/forms/nsImageControlFrame.cpp | 2 +- layout/forms/nsListControlFrame.cpp | 1 + layout/forms/nsListControlFrame.h | 2 +- layout/forms/nsTextControlFrame.cpp | 2 +- layout/html/base/src/nsPresShell.cpp | 2 +- .../html/content/src/nsHTMLAnchorElement.cpp | 47 +- .../html/forms/src/nsButtonControlFrame.cpp | 4 +- .../forms/src/nsHTMLButtonControlFrame.cpp | 4 +- layout/html/forms/src/nsImageControlFrame.cpp | 2 +- layout/html/forms/src/nsListControlFrame.cpp | 1 + layout/html/forms/src/nsListControlFrame.h | 2 +- .../html/forms/src/nsSelectControlFrame.cpp | 2 +- layout/html/forms/src/nsTextControlFrame.cpp | 2 +- layout/html/style/src/nsCSSStyleSheet.cpp | 11 +- layout/html/style/src/nsHTMLStyleSheet.cpp | 6 +- layout/style/nsCSSStyleSheet.cpp | 11 +- layout/style/nsHTMLStyleSheet.cpp | 6 +- layout/xml/content/src/nsXMLElement.cpp | 54 +- 52 files changed, 2087 insertions(+), 884 deletions(-) diff --git a/content/base/src/nsDocument.cpp b/content/base/src/nsDocument.cpp index c335def8e11c..b31e5861b769 100644 --- a/content/base/src/nsDocument.cpp +++ b/content/base/src/nsDocument.cpp @@ -677,6 +677,12 @@ nsresult nsDocument::QueryInterface(REFNSIID aIID, void** aInstancePtr) NS_ADDREF_THIS(); return NS_OK; } + if (aIID.Equals(kIDOMEventTargetIID)) { + nsIDOMEventTarget* tmp = this; + *aInstancePtr = (void*) tmp; + NS_ADDREF_THIS(); + return NS_OK; + } if (aIID.Equals(kIDOMNodeIID)) { nsIDOMNode* tmp = this; *aInstancePtr = (void*) tmp; @@ -1773,32 +1779,30 @@ nsresult nsDocument::HandleDOMEvent(nsIPresContext& aPresContext, nsresult mRet = NS_OK; nsIDOMEvent* mDOMEvent = nsnull; - if (DOM_EVENT_INIT == aFlags) { + if (NS_EVENT_FLAG_INIT == aFlags) { aDOMEvent = &mDOMEvent; } //Capturing stage - /*if (mEventCapturer) { - mEventCapturer->HandleDOMEvent(aPresContext, aEvent, aDOMEvent, aFlags, aEventStatus); - }*/ + if (NS_EVENT_FLAG_BUBBLE != aFlags) { + //XXX Check window capture here + } //Local handling stage if (nsnull != mListenerManager) { - mListenerManager->HandleEvent(aPresContext, aEvent, aDOMEvent, aEventStatus); + mListenerManager->HandleEvent(aPresContext, aEvent, aDOMEvent, aFlags, aEventStatus); } //Bubbling stage - if (DOM_EVENT_CAPTURE != aFlags && nsnull != mScriptContextOwner) { + if (NS_EVENT_FLAG_CAPTURE != aFlags && nsnull != mScriptContextOwner) { nsIScriptGlobalObject* mGlobal; if (NS_OK == mScriptContextOwner->GetScriptGlobalObject(&mGlobal)) { - mGlobal->HandleDOMEvent(aPresContext, aEvent, aDOMEvent, DOM_EVENT_BUBBLE, aEventStatus); + mGlobal->HandleDOMEvent(aPresContext, aEvent, aDOMEvent, NS_EVENT_FLAG_BUBBLE, aEventStatus); NS_RELEASE(mGlobal); } } - /*Need to go to window here*/ - - if (DOM_EVENT_INIT == aFlags) { + if (NS_EVENT_FLAG_INIT == aFlags) { // We're leaving the DOM event loop so if we created a DOM event, release here. if (nsnull != *aDOMEvent) { nsrefcnt rc; @@ -1819,22 +1823,51 @@ nsresult nsDocument::HandleDOMEvent(nsIPresContext& aPresContext, return mRet; } -nsresult nsDocument::AddEventListener(nsIDOMEventListener *aListener, const nsIID& aIID) +nsresult nsDocument::AddEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID) { - nsIEventListenerManager *mManager; + nsIEventListenerManager *manager; - if (NS_OK == GetListenerManager(&mManager)) { - mManager->AddEventListener(aListener, aIID); - NS_RELEASE(mManager); + if (NS_OK == GetListenerManager(&manager)) { + manager->AddEventListenerByIID(aListener, aIID, NS_EVENT_FLAG_BUBBLE); + NS_RELEASE(manager); return NS_OK; } return NS_ERROR_FAILURE; } -nsresult nsDocument::RemoveEventListener(nsIDOMEventListener *aListener, const nsIID& aIID) +nsresult nsDocument::RemoveEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID) { if (nsnull != mListenerManager) { - mListenerManager->RemoveEventListener(aListener, aIID); + mListenerManager->RemoveEventListenerByIID(aListener, aIID, NS_EVENT_FLAG_BUBBLE); + return NS_OK; + } + return NS_ERROR_FAILURE; +} + +nsresult nsDocument::AddEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture) +{ + nsIEventListenerManager *manager; + + if (NS_OK == GetListenerManager(&manager)) { + PRInt32 flags = (aPostProcess ? NS_EVENT_FLAG_POST_PROCESS : NS_EVENT_FLAG_NONE) | + (aUseCapture ? NS_EVENT_FLAG_CAPTURE : NS_EVENT_FLAG_BUBBLE); + + manager->AddEventListenerByType(aListener, aType, flags); + NS_RELEASE(manager); + return NS_OK; + } + return NS_ERROR_FAILURE; +} + +nsresult nsDocument::RemoveEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture) +{ + if (nsnull != mListenerManager) { + PRInt32 flags = (aPostProcess ? NS_EVENT_FLAG_POST_PROCESS : NS_EVENT_FLAG_NONE) | + (aUseCapture ? NS_EVENT_FLAG_CAPTURE : NS_EVENT_FLAG_BUBBLE); + + mListenerManager->RemoveEventListenerByType(aListener, aType, flags); return NS_OK; } return NS_ERROR_FAILURE; diff --git a/content/base/src/nsDocument.h b/content/base/src/nsDocument.h index 186c4c37db3a..9224c4461085 100644 --- a/content/base/src/nsDocument.h +++ b/content/base/src/nsDocument.h @@ -25,6 +25,7 @@ #include "nsIScriptObjectOwner.h" #include "nsIScriptContextOwner.h" #include "nsIDOMEventCapturer.h" +#include "nsIDOMEventTarget.h" #include "nsXIFConverter.h" #include "nsIJSScriptObject.h" #include "nsIContent.h" @@ -311,11 +312,18 @@ public: NS_IMETHOD ReleaseEvent(const nsString& aType); // nsIDOMEventReceiver interface - NS_IMETHOD AddEventListener(nsIDOMEventListener *aListener, const nsIID& aIID); - NS_IMETHOD RemoveEventListener(nsIDOMEventListener *aListener, const nsIID& aIID); + NS_IMETHOD AddEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID); + NS_IMETHOD RemoveEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID); NS_IMETHOD GetListenerManager(nsIEventListenerManager** aInstancePtrResult); NS_IMETHOD GetNewListenerManager(nsIEventListenerManager **aInstancePtrResult); + // nsIDOMEventTarget interface + NS_IMETHOD AddEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture); + NS_IMETHOD RemoveEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture); + + NS_IMETHOD HandleDOMEvent(nsIPresContext& aPresContext, nsEvent* aEvent, nsIDOMEvent** aDOMEvent, diff --git a/content/base/src/nsGenericDOMDataNode.cpp b/content/base/src/nsGenericDOMDataNode.cpp index 64c3de9c3f43..78500e079854 100644 --- a/content/base/src/nsGenericDOMDataNode.cpp +++ b/content/base/src/nsGenericDOMDataNode.cpp @@ -61,6 +61,7 @@ nsGenericDOMDataNode::nsGenericDOMDataNode() mScriptObject = nsnull; mListenerManager = nsnull; mRangeList = nsnull; + mCapturer = nsnull; } nsGenericDOMDataNode::~nsGenericDOMDataNode() @@ -428,13 +429,13 @@ nsGenericDOMDataNode::GetNewListenerManager(nsIEventListenerManager** aResult) } nsresult -nsGenericDOMDataNode::AddEventListener(nsIDOMEventListener* aListener, +nsGenericDOMDataNode::AddEventListenerByIID(nsIDOMEventListener* aListener, const nsIID& aIID) { nsIEventListenerManager *manager; if (NS_OK == GetListenerManager(&manager)) { - manager->AddEventListener(aListener, aIID); + manager->AddEventListenerByIID(aListener, aIID, NS_EVENT_FLAG_BUBBLE); NS_RELEASE(manager); return NS_OK; } @@ -442,11 +443,42 @@ nsGenericDOMDataNode::AddEventListener(nsIDOMEventListener* aListener, } nsresult -nsGenericDOMDataNode::RemoveEventListener(nsIDOMEventListener* aListener, +nsGenericDOMDataNode::RemoveEventListenerByIID(nsIDOMEventListener* aListener, const nsIID& aIID) { if (nsnull != mListenerManager) { - mListenerManager->RemoveEventListener(aListener, aIID); + mListenerManager->RemoveEventListenerByIID(aListener, aIID, NS_EVENT_FLAG_BUBBLE); + return NS_OK; + } + return NS_ERROR_FAILURE; +} + +nsresult +nsGenericDOMDataNode::AddEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture) +{ + nsIEventListenerManager *manager; + + if (NS_OK == GetListenerManager(&manager)) { + PRInt32 flags = (aPostProcess ? NS_EVENT_FLAG_POST_PROCESS : NS_EVENT_FLAG_NONE) | + (aUseCapture ? NS_EVENT_FLAG_CAPTURE : NS_EVENT_FLAG_BUBBLE); + + manager->AddEventListenerByType(aListener, aType, flags); + NS_RELEASE(manager); + return NS_OK; + } + return NS_ERROR_FAILURE; +} + +nsresult +nsGenericDOMDataNode::RemoveEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture) +{ + if (nsnull != mListenerManager) { + PRInt32 flags = (aPostProcess ? NS_EVENT_FLAG_POST_PROCESS : NS_EVENT_FLAG_NONE) | + (aUseCapture ? NS_EVENT_FLAG_CAPTURE : NS_EVENT_FLAG_BUBBLE); + + mListenerManager->RemoveEventListenerByType(aListener, aType, flags); return NS_OK; } return NS_ERROR_FAILURE; @@ -652,26 +684,35 @@ nsGenericDOMDataNode::HandleDOMEvent(nsIPresContext& aPresContext, nsEventStatus& aEventStatus) { nsresult ret = NS_OK; - nsIDOMEvent* domEvent = nsnull; - if (DOM_EVENT_INIT == aFlags) { + + if (NS_EVENT_FLAG_INIT == aFlags) { aDOMEvent = &domEvent; + + //Initiate capturing phase. Special case first call to document + if (nsnull != mDocument) { + mDocument->HandleDOMEvent(aPresContext, aEvent, aDOMEvent, NS_EVENT_FLAG_CAPTURE, aEventStatus); + } } - //Capturing stage + //Capturing stage evaluation + //Always pass capturing up the tree before local evaulation + if (NS_EVENT_FLAG_BUBBLE != aFlags && nsnull != mCapturer) { + mCapturer->HandleDOMEvent(aPresContext, aEvent, aDOMEvent, NS_EVENT_FLAG_CAPTURE, aEventStatus); + } //Local handling stage if (nsnull != mListenerManager) { - mListenerManager->HandleEvent(aPresContext, aEvent, aDOMEvent, aEventStatus); + mListenerManager->HandleEvent(aPresContext, aEvent, aDOMEvent, aFlags, aEventStatus); } //Bubbling stage - if (DOM_EVENT_CAPTURE != aFlags && mParent != nsnull) { + if (NS_EVENT_FLAG_CAPTURE != aFlags && mParent != nsnull) { ret = mParent->HandleDOMEvent(aPresContext, aEvent, aDOMEvent, - DOM_EVENT_BUBBLE, aEventStatus); + NS_EVENT_FLAG_BUBBLE, aEventStatus); } - if (DOM_EVENT_INIT == aFlags) { + if (NS_EVENT_FLAG_INIT == aFlags) { // We're leaving the DOM event loop so if we created a DOM event, // release here. if (nsnull != *aDOMEvent) { diff --git a/content/base/src/nsGenericDOMDataNode.h b/content/base/src/nsGenericDOMDataNode.h index 19cadb259184..635822c723a7 100644 --- a/content/base/src/nsGenericDOMDataNode.h +++ b/content/base/src/nsGenericDOMDataNode.h @@ -30,6 +30,7 @@ extern const nsIID kIDOMCharacterDataIID; extern const nsIID kIDOMNodeIID; extern const nsIID kIDOMEventReceiverIID; +extern const nsIID kIDOMEventTargetIID; extern const nsIID kIScriptObjectOwnerIID; extern const nsIID kISupportsIID; extern const nsIID kIContentIID; @@ -102,12 +103,18 @@ struct nsGenericDOMDataNode { nsresult ReplaceData(PRUint32 aOffset, PRUint32 aCount, const nsString& aArg); // nsIDOMEventReceiver interface - nsresult AddEventListener(nsIDOMEventListener *aListener, const nsIID& aIID); - nsresult RemoveEventListener(nsIDOMEventListener* aListener, + nsresult AddEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID); + nsresult RemoveEventListenerByIID(nsIDOMEventListener* aListener, const nsIID& aIID); nsresult GetListenerManager(nsIEventListenerManager** aInstancePtrResult); nsresult GetNewListenerManager(nsIEventListenerManager** aInstancePtrResult); + // nsIDOMEventTarget interface + nsresult AddEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture); + nsresult RemoveEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture); + // nsIScriptObjectOwner interface nsresult GetScriptObject(nsIScriptContext* aContext, void** aScriptObject); nsresult SetScriptObject(void *aScriptObject); @@ -213,6 +220,7 @@ struct nsGenericDOMDataNode { nsIContent* mParent; void* mScriptObject; nsIEventListenerManager* mListenerManager; + nsIContent* mCapturer; nsTextFragment mText; nsVoidArray *mRangeList; @@ -314,21 +322,33 @@ struct nsGenericDOMDataNode { * generic content object (either nsGenericHTMLLeafElement or * nsGenericHTMLContainerContent) */ -#define NS_IMPL_IDOMEVENTRECEIVER_USING_GENERIC_DOM_DATA(_g) \ - NS_IMETHOD AddEventListener(nsIDOMEventListener *aListener, \ - const nsIID& aIID) { \ - return _g.AddEventListener(aListener, aIID); \ - } \ - NS_IMETHOD RemoveEventListener(nsIDOMEventListener *aListener, \ - const nsIID& aIID) { \ - return _g.RemoveEventListener(aListener, aIID); \ - } \ - NS_IMETHOD GetListenerManager(nsIEventListenerManager** aResult) { \ - return _g.GetListenerManager(aResult); \ - } \ - NS_IMETHOD GetNewListenerManager(nsIEventListenerManager** aResult) { \ - return _g.GetNewListenerManager(aResult); \ - } +#define NS_IMPL_IDOMEVENTRECEIVER_USING_GENERIC_DOM_DATA(_g) \ + NS_IMETHOD AddEventListenerByIID(nsIDOMEventListener *aListener, \ + const nsIID& aIID) { \ + return _g.AddEventListenerByIID(aListener, aIID); \ + } \ + NS_IMETHOD RemoveEventListenerByIID(nsIDOMEventListener *aListener, \ + const nsIID& aIID) { \ + return _g.RemoveEventListenerByIID(aListener, aIID); \ + } \ + NS_IMETHOD GetListenerManager(nsIEventListenerManager** aResult) { \ + return _g.GetListenerManager(aResult); \ + } \ + NS_IMETHOD GetNewListenerManager(nsIEventListenerManager** aResult) { \ + return _g.GetNewListenerManager(aResult); \ + } \ + NS_IMETHOD AddEventListener(const nsString& aType, \ + nsIDOMEventListener* aListener, \ + PRBool aPostProcess, \ + PRBool aUseCapture) { \ + return _g.AddEventListener(aType, aListener, aPostProcess, aUseCapture); \ + } \ + NS_IMETHOD RemoveEventListener(const nsString& aType, \ + nsIDOMEventListener* aListener, \ + PRBool aPostProcess, \ + PRBool aUseCapture) { \ + return _g.RemoveEventListener(aType, aListener, aPostProcess, aUseCapture); \ + } /** * Implement the nsIScriptObjectOwner API by forwarding the methods to a @@ -474,6 +494,12 @@ struct nsGenericDOMDataNode { NS_ADDREF_THIS(); \ return NS_OK; \ } \ + if (_id.Equals(kIDOMEventTargetIID)) { \ + nsIDOMEventTarget* tmp = _this; \ + *_iptr = (void*) tmp; \ + NS_ADDREF_THIS(); \ + return NS_OK; \ + } \ if (_id.Equals(kIScriptObjectOwnerIID)) { \ nsIScriptObjectOwner* tmp = _this; \ *_iptr = (void*) tmp; \ diff --git a/content/base/src/nsGenericElement.cpp b/content/base/src/nsGenericElement.cpp index 5580161c9616..03977c7b3c00 100644 --- a/content/base/src/nsGenericElement.cpp +++ b/content/base/src/nsGenericElement.cpp @@ -63,6 +63,7 @@ NS_DEFINE_IID(kIDOMNodeIID, NS_IDOMNODE_IID); NS_DEFINE_IID(kIDOMElementIID, NS_IDOMELEMENT_IID); NS_DEFINE_IID(kIDOMTextIID, NS_IDOMTEXT_IID); NS_DEFINE_IID(kIDOMEventReceiverIID, NS_IDOMEVENTRECEIVER_IID); +NS_DEFINE_IID(kIDOMEventTargetIID, NS_IDOMEVENTTARGET_IID); NS_DEFINE_IID(kIScriptObjectOwnerIID, NS_ISCRIPTOBJECTOWNER_IID); NS_DEFINE_IID(kIJSScriptObjectIID, NS_IJSSCRIPTOBJECT_IID); NS_DEFINE_IID(kISupportsIID, NS_ISUPPORTS_IID); @@ -206,6 +207,7 @@ nsGenericElement::GetDOMSlots() mDOMSlots->mStyle = nsnull; mDOMSlots->mAttributeMap = nsnull; mDOMSlots->mRangeList = nsnull; + mDOMSlots->mCapturer = nsnull; } return mDOMSlots; @@ -737,24 +739,36 @@ nsGenericElement::HandleDOMEvent(nsIPresContext& aPresContext, nsresult ret = NS_OK; nsIDOMEvent* domEvent = nsnull; - if (DOM_EVENT_INIT == aFlags) { + if (NS_EVENT_FLAG_INIT == aFlags) { aDOMEvent = &domEvent; + + //Initiate capturing phase + //Initiate capturing phase. Special case first call to document + if (nsnull != mDocument) { + mDocument->HandleDOMEvent(aPresContext, aEvent, aDOMEvent, NS_EVENT_FLAG_CAPTURE, aEventStatus); + } } - //Capturing stage + //Capturing stage evaluation + //Always pass capturing up the tree before local evaulation + if (NS_EVENT_FLAG_BUBBLE != aFlags) { + if (nsnull != mDOMSlots && nsnull != mDOMSlots->mCapturer) { + mDOMSlots->mCapturer->HandleDOMEvent(aPresContext, aEvent, aDOMEvent, NS_EVENT_FLAG_CAPTURE, aEventStatus); + } + } //Local handling stage if (nsnull != mListenerManager) { - mListenerManager->HandleEvent(aPresContext, aEvent, aDOMEvent, aEventStatus); + mListenerManager->HandleEvent(aPresContext, aEvent, aDOMEvent, aFlags, aEventStatus); } //Bubbling stage - if ((DOM_EVENT_CAPTURE != aFlags) && (mParent != nsnull) && (mDocument != nsnull)) { + if ((NS_EVENT_FLAG_CAPTURE != aFlags) && (mParent != nsnull) && (mDocument != nsnull)) { ret = mParent->HandleDOMEvent(aPresContext, aEvent, aDOMEvent, - DOM_EVENT_BUBBLE, aEventStatus); + NS_EVENT_FLAG_BUBBLE, aEventStatus); } - if (DOM_EVENT_INIT == aFlags) { + if (NS_EVENT_FLAG_INIT == aFlags) { // We're leaving the DOM event loop so if we created a DOM event, // release here. if (nsnull != *aDOMEvent) { @@ -948,13 +962,13 @@ nsGenericElement::GetNewListenerManager(nsIEventListenerManager** aResult) } nsresult -nsGenericElement::AddEventListener(nsIDOMEventListener* aListener, +nsGenericElement::AddEventListenerByIID(nsIDOMEventListener* aListener, const nsIID& aIID) { nsIEventListenerManager *manager; if (NS_OK == GetListenerManager(&manager)) { - manager->AddEventListener(aListener, aIID); + manager->AddEventListenerByIID(aListener, aIID, NS_EVENT_FLAG_BUBBLE); NS_RELEASE(manager); return NS_OK; } @@ -962,11 +976,42 @@ nsGenericElement::AddEventListener(nsIDOMEventListener* aListener, } nsresult -nsGenericElement::RemoveEventListener(nsIDOMEventListener* aListener, +nsGenericElement::RemoveEventListenerByIID(nsIDOMEventListener* aListener, const nsIID& aIID) { if (nsnull != mListenerManager) { - mListenerManager->RemoveEventListener(aListener, aIID); + mListenerManager->RemoveEventListenerByIID(aListener, aIID, NS_EVENT_FLAG_BUBBLE); + return NS_OK; + } + return NS_ERROR_FAILURE; +} + +nsresult +nsGenericElement::AddEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture) +{ + nsIEventListenerManager *manager; + + if (NS_OK == GetListenerManager(&manager)) { + PRInt32 flags = (aPostProcess ? NS_EVENT_FLAG_POST_PROCESS : NS_EVENT_FLAG_NONE) | + (aUseCapture ? NS_EVENT_FLAG_CAPTURE : NS_EVENT_FLAG_BUBBLE); + + manager->AddEventListenerByType(aListener, aType, flags); + NS_RELEASE(manager); + return NS_OK; + } + return NS_ERROR_FAILURE; +} + +nsresult +nsGenericElement::RemoveEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture) +{ + if (nsnull != mListenerManager) { + PRInt32 flags = (aPostProcess ? NS_EVENT_FLAG_POST_PROCESS : NS_EVENT_FLAG_NONE) | + (aUseCapture ? NS_EVENT_FLAG_CAPTURE : NS_EVENT_FLAG_BUBBLE); + + mListenerManager->RemoveEventListenerByType(aListener, aType, flags); return NS_OK; } return NS_ERROR_FAILURE; diff --git a/content/base/src/nsGenericElement.h b/content/base/src/nsGenericElement.h index 659f0bab8f90..421013cb4291 100644 --- a/content/base/src/nsGenericElement.h +++ b/content/base/src/nsGenericElement.h @@ -33,6 +33,7 @@ extern const nsIID kIDOMNodeIID; extern const nsIID kIDOMElementIID; extern const nsIID kIDOMEventReceiverIID; +extern const nsIID kIDOMEventTargetIID; extern const nsIID kIScriptObjectOwnerIID; extern const nsIID kIJSScriptObjectIID; extern const nsIID kISupportsIID; @@ -79,6 +80,7 @@ typedef struct { nsDOMCSSDeclaration *mStyle; nsDOMAttributeMap* mAttributeMap; nsVoidArray *mRangeList; + nsIContent* mCapturer; } nsDOMSlots; class nsGenericElement : public nsIJSScriptObject { @@ -116,12 +118,18 @@ public: nsresult Normalize(); // nsIDOMEventReceiver interface - nsresult AddEventListener(nsIDOMEventListener *aListener, const nsIID& aIID); - nsresult RemoveEventListener(nsIDOMEventListener* aListener, + nsresult AddEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID); + nsresult RemoveEventListenerByIID(nsIDOMEventListener* aListener, const nsIID& aIID); nsresult GetListenerManager(nsIEventListenerManager** aInstancePtrResult); nsresult GetNewListenerManager(nsIEventListenerManager** aInstancePtrResult); + // nsIDOMEventTarget interface + nsresult AddEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture); + nsresult RemoveEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture); + // nsIScriptObjectOwner interface nsresult GetScriptObject(nsIScriptContext* aContext, void** aScriptObject); nsresult SetScriptObject(void *aScriptObject); @@ -373,21 +381,33 @@ public: * generic content object (either nsGenericHTMLLeafElement or * nsGenericHTMLContainerContent) */ -#define NS_IMPL_IDOMEVENTRECEIVER_USING_GENERIC(_g) \ - NS_IMETHOD AddEventListener(nsIDOMEventListener *aListener, \ - const nsIID& aIID) { \ - return _g.AddEventListener(aListener, aIID); \ - } \ - NS_IMETHOD RemoveEventListener(nsIDOMEventListener *aListener, \ - const nsIID& aIID) { \ - return _g.RemoveEventListener(aListener, aIID); \ - } \ - NS_IMETHOD GetListenerManager(nsIEventListenerManager** aResult) { \ - return _g.GetListenerManager(aResult); \ - } \ - NS_IMETHOD GetNewListenerManager(nsIEventListenerManager** aResult) { \ - return _g.GetNewListenerManager(aResult); \ - } +#define NS_IMPL_IDOMEVENTRECEIVER_USING_GENERIC(_g) \ + NS_IMETHOD AddEventListenerByIID(nsIDOMEventListener *aListener, \ + const nsIID& aIID) { \ + return _g.AddEventListenerByIID(aListener, aIID); \ + } \ + NS_IMETHOD RemoveEventListenerByIID(nsIDOMEventListener *aListener, \ + const nsIID& aIID) { \ + return _g.RemoveEventListenerByIID(aListener, aIID); \ + } \ + NS_IMETHOD GetListenerManager(nsIEventListenerManager** aResult) { \ + return _g.GetListenerManager(aResult); \ + } \ + NS_IMETHOD GetNewListenerManager(nsIEventListenerManager** aResult) { \ + return _g.GetNewListenerManager(aResult); \ + } \ + NS_IMETHOD AddEventListener(const nsString& aType, \ + nsIDOMEventListener* aListener, \ + PRBool aPostProcess, \ + PRBool aUseCapture) { \ + return _g.AddEventListener(aType, aListener, aPostProcess, aUseCapture); \ + } \ + NS_IMETHOD RemoveEventListener(const nsString& aType, \ + nsIDOMEventListener* aListener, \ + PRBool aPostProcess, \ + PRBool aUseCapture) { \ + return _g.RemoveEventListener(aType, aListener, aPostProcess, aUseCapture); \ + } #define NS_IMPL_ICONTENT_USING_GENERIC(_g) \ NS_IMETHOD GetDocument(nsIDocument*& aResult) const { \ @@ -532,6 +552,12 @@ public: NS_ADDREF_THIS(); \ return NS_OK; \ } \ + if (_id.Equals(kIDOMEventTargetIID)) { \ + nsIDOMEventTarget* tmp = _this; \ + *_iptr = (void*) tmp; \ + NS_ADDREF_THIS(); \ + return NS_OK; \ + } \ if (_id.Equals(kIScriptObjectOwnerIID)) { \ nsIScriptObjectOwner* tmp = _this; \ *_iptr = (void*) tmp; \ diff --git a/content/events/public/nsIEventListenerManager.h b/content/events/public/nsIEventListenerManager.h index d47ad17c1473..c367c15cf193 100644 --- a/content/events/public/nsIEventListenerManager.h +++ b/content/events/public/nsIEventListenerManager.h @@ -51,8 +51,29 @@ public: * @param an event listener */ - virtual nsresult AddEventListener(nsIDOMEventListener *aListener, const nsIID& aIID) = 0; + virtual nsresult AddEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID, PRInt32 flags) = 0; + /** + * Removes events listeners of all types. + * @param an event listener + */ + + virtual nsresult RemoveEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID, PRInt32 flags) = 0; + + /** + * Sets events listeners of all types. + * @param an event listener + */ + + virtual nsresult AddEventListenerByType(nsIDOMEventListener *aListener, const nsString& type, PRInt32 flags) = 0; + + /** + * Removes events listeners of all types. + * @param an event listener + */ + + virtual nsresult RemoveEventListenerByType(nsIDOMEventListener *aListener, const nsString& type, PRInt32 flags) = 0; + /** * Creates a script event listener for the given script object with name mName and function * content mFunc. @@ -70,21 +91,16 @@ public: virtual nsresult RegisterScriptEventListener(nsIScriptContext *aContext, nsIScriptObjectOwner *aScriptObjectOwner, REFNSIID aIID) = 0; - /** - * Removes events listeners of all types. - * @param an event listener - */ - - virtual nsresult RemoveEventListener(nsIDOMEventListener *aListener, const nsIID& aIID) = 0; - /** * Causes a check for event listeners and processing by them if they exist. + * Event flags live in nsGUIEvent.h * @param an event listener */ virtual nsresult HandleEvent(nsIPresContext& aPresContext, nsEvent* aEvent, nsIDOMEvent** aDOMEvent, + PRUint32 aFlags, nsEventStatus& aEventStatus) = 0; /** diff --git a/content/events/public/nsIEventStateManager.h b/content/events/public/nsIEventStateManager.h index 9d529c4db754..d3d0ada64587 100644 --- a/content/events/public/nsIEventStateManager.h +++ b/content/events/public/nsIEventStateManager.h @@ -28,12 +28,6 @@ class nsIPresContext; class nsIDOMEvent; class nsIFrame; -enum nsLinkEventState { - eLinkState_Unspecified = 0, - eLinkState_Active = 1, // mouse is down on link - eLinkState_Hover = 2 // mouse is hovering over link -}; - /* * Event listener manager interface. */ @@ -61,11 +55,16 @@ public: NS_IMETHOD GetEventTarget(nsIFrame **aFrame) = 0; - NS_IMETHOD GetLinkState(nsIContent *aLink, nsLinkEventState& aState) = 0; - NS_IMETHOD SetActiveLink(nsIContent *aLink) = 0; - NS_IMETHOD SetHoverLink(nsIContent *aLink) = 0; + NS_IMETHOD GetContentState(nsIContent *aContent, PRInt32& aState) = 0; + NS_IMETHOD SetActiveContent(nsIContent *aActive) = 0; + NS_IMETHOD SetHoverContent(nsIContent *aHover) = 0; NS_IMETHOD SetFocusedContent(nsIContent *aContent) = 0; }; +#define NS_EVENT_STATE_UNSPECIFIED 0000 +#define NS_EVENT_STATE_ACTIVE 0001 // mouse is down on content +#define NS_EVENT_STATE_FOCUS 0002 // content has focus +#define NS_EVENT_STATE_HOVER 0003 // mouse is hovering over content + #endif // nsIEventStateManager_h__ diff --git a/content/events/src/nsDOMEvent.cpp b/content/events/src/nsDOMEvent.cpp index bc834f29a149..18b9bb4cae3c 100644 --- a/content/events/src/nsDOMEvent.cpp +++ b/content/events/src/nsDOMEvent.cpp @@ -261,6 +261,7 @@ NS_METHOD nsDOMEvent::GetCharCode(PRUint32* aCharCode) { switch (mEvent->message) { case NS_KEY_UP: + case NS_KEY_PRESS: case NS_KEY_DOWN: *aCharCode = ((nsKeyEvent*)mEvent)->charCode; #ifdef NS_DEBUG @@ -283,6 +284,7 @@ NS_METHOD nsDOMEvent::GetKeyCode(PRUint32* aKeyCode) { switch (mEvent->message) { case NS_KEY_UP: + case NS_KEY_PRESS: case NS_KEY_DOWN: *aKeyCode = ((nsKeyEvent*)mEvent)->keyCode; break; @@ -441,9 +443,9 @@ const char* nsDOMEvent::GetEventName(PRUint32 aEventType) return mEventNames[eDOMEvents_keydown]; case NS_KEY_PRESS: return mEventNames[eDOMEvents_keypress]; - case NS_GOTFOCUS: + case NS_FOCUS_CONTENT: return mEventNames[eDOMEvents_focus]; - case NS_LOSTFOCUS: + case NS_BLUR_CONTENT: return mEventNames[eDOMEvents_blur]; case NS_PAGE_LOAD: case NS_IMAGE_LOAD: diff --git a/content/events/src/nsDOMEvent.h b/content/events/src/nsDOMEvent.h index 18315ca84eaa..0ebcda3c8d81 100644 --- a/content/events/src/nsDOMEvent.h +++ b/content/events/src/nsDOMEvent.h @@ -33,10 +33,6 @@ class nsIDOMRenderingContext; class nsDOMEvent : public nsIDOMEvent, public nsIDOMNSEvent, public nsIPrivateDOMEvent { -#define DOM_EVENT_INIT 0x0001 -#define DOM_EVENT_BUBBLE 0x0002 -#define DOM_EVENT_CAPTURE 0x0004 - public: // Note: this enum must be kept in sync with mEventNames in nsDOMEvent.cpp enum nsDOMEvents { diff --git a/content/events/src/nsEventListenerManager.cpp b/content/events/src/nsEventListenerManager.cpp index bb8a647855ec..c3d958fbef3d 100644 --- a/content/events/src/nsEventListenerManager.cpp +++ b/content/events/src/nsEventListenerManager.cpp @@ -36,6 +36,7 @@ #include "nsIScriptObjectOwner.h" #include "nsIScriptEventListener.h" #include "nsDOMEventsIIDs.h" +#include "prmem.h" static NS_DEFINE_IID(kIEventListenerManagerIID, NS_IEVENTLISTENERMANAGER_IID); static NS_DEFINE_IID(kIDOMEventListenerIID, NS_IDOMEVENTLISTENER_IID); @@ -125,11 +126,12 @@ void nsEventListenerManager::ReleaseListeners(nsVoidArray* aListeners) { if (nsnull != aListeners) { PRInt32 i, count = aListeners->Count(); - nsIDOMEventListener *mElement; + nsListenerStruct *ls; for (i = 0; i < count; i++) { - mElement = (nsIDOMEventListener *)aListeners->ElementAt(i); - if (mElement != nsnull) { - NS_RELEASE(mElement); + ls = (nsListenerStruct*)aListeners->ElementAt(i); + if (ls != nsnull) { + NS_IF_RELEASE(ls->mListener); + PR_DELETE(ls); } } delete aListeners; @@ -149,24 +151,221 @@ nsresult nsEventListenerManager::GetEventListeners(nsVoidArray **aListeners, con * Sets events listeners of all types. * @param an event listener */ -nsresult nsEventListenerManager::AddEventListener(nsIDOMEventListener *aListener, const nsIID& aIID) +nsresult nsEventListenerManager::AddEventListener(nsIDOMEventListener *aListener, + const nsIID& aIID, + PRInt32 aFlags, + PRInt32 aSubType) { - nsVoidArray** mListeners = GetListenersByIID(aIID); + nsVoidArray** listeners = GetListenersByIID(aIID); - if (nsnull == *mListeners) { - *mListeners = new nsVoidArray(); + if (nsnull == *listeners) { + *listeners = new nsVoidArray(); } - if (nsnull == *mListeners) { + if (nsnull == *listeners) { return NS_ERROR_OUT_OF_MEMORY; } - (*mListeners)->InsertElementAt((void*)aListener, (*mListeners)->Count()); + PRBool found = PR_FALSE; + nsListenerStruct* ls; + nsIScriptEventListener* sel = nsnull; + nsIScriptEventListener* regSel; + + aListener->QueryInterface(kIScriptEventListenerIID, (void**)&sel); + + for (int i=0; i<(*listeners)->Count(); i++) { + ls = (nsListenerStruct*)(*listeners)->ElementAt(i); + if (ls->mListener == aListener) { + ls->mFlags |= aFlags; + ls->mSubType |= aSubType; + found = PR_TRUE; + break; + } + else if (sel) { + if (NS_OK == ls->mListener->QueryInterface(kIScriptEventListenerIID, (void**)®Sel)) { + if (NS_OK == regSel->CheckIfEqual(sel)) { + if (ls->mFlags & aFlags && ls->mSubType & aSubType) { + found = PR_TRUE; + break; + } + } + } + } + } + + if (!found) { + ls = PR_NEW(nsListenerStruct); + if (ls) { + ls->mListener = aListener; + ls->mFlags = aFlags; + ls->mSubType = aSubType; + (*listeners)->InsertElementAt((void*)ls, (*listeners)->Count()); + } + } NS_ADDREF(aListener); return NS_OK; } + +nsresult nsEventListenerManager::RemoveEventListener(nsIDOMEventListener *aListener, + const nsIID& aIID, + PRInt32 aFlags, + PRInt32 aSubType) +{ + nsVoidArray** listeners = GetListenersByIID(aIID); + + if (nsnull == *listeners) { + return NS_OK; + } + + nsListenerStruct* ls; + + for (int i=0; i<(*listeners)->Count(); i++) { + ls = (nsListenerStruct*)(*listeners)->ElementAt(i); + if (ls->mListener == aListener) { + ls->mFlags &= ~aFlags; + ls->mSubType &= ~aSubType; + if (ls->mFlags == NS_EVENT_FLAG_NONE && ls->mSubType == NS_EVENT_BITS_NONE) { + NS_RELEASE(ls->mListener); + (*listeners)->RemoveElement((void*)ls); + PR_DELETE(ls); + } + break; + } + } + + return NS_OK; +} + +nsresult nsEventListenerManager::AddEventListenerByIID(nsIDOMEventListener *aListener, + const nsIID& aIID, PRInt32 aFlags) +{ + AddEventListener(aListener, aIID, aFlags, NS_EVENT_BITS_NONE); + return NS_OK; +} + +nsresult nsEventListenerManager::RemoveEventListenerByIID(nsIDOMEventListener *aListener, + const nsIID& aIID, PRInt32 aFlags) +{ + RemoveEventListener(aListener, aIID, aFlags, NS_EVENT_BITS_NONE); + return NS_OK; +} + +nsresult nsEventListenerManager::GetIdentifiersForType(const nsString& aType, nsIID& aIID, PRInt32* aFlags) +{ + if (aType == "mousedown") { + aIID = kIDOMMouseListenerIID; + *aFlags = NS_EVENT_BITS_MOUSE_MOUSEDOWN; + } + else if (aType == "mouseup") { + aIID = kIDOMMouseListenerIID; + *aFlags = NS_EVENT_BITS_MOUSE_MOUSEUP; + } + else if (aType == "click") { + aIID = kIDOMMouseListenerIID; + *aFlags = NS_EVENT_BITS_MOUSE_CLICK; + } + else if (aType == "dblclick") { + aIID = kIDOMMouseListenerIID; + *aFlags = NS_EVENT_BITS_MOUSE_DBLCLICK; + } + else if (aType == "mouseover") { + aIID = kIDOMMouseListenerIID; + *aFlags = NS_EVENT_BITS_MOUSE_MOUSEOVER; + } + else if (aType == "mouseout") { + aIID = kIDOMMouseListenerIID; + *aFlags = NS_EVENT_BITS_MOUSE_MOUSEOUT; + } + else if (aType == "keydown") { + aIID = kIDOMKeyListenerIID; + *aFlags = NS_EVENT_BITS_KEY_KEYDOWN; + } + else if (aType == "keyup") { + aIID = kIDOMKeyListenerIID; + *aFlags = NS_EVENT_BITS_KEY_KEYUP; + } + else if (aType == "keypress") { + aIID = kIDOMKeyListenerIID; + *aFlags = NS_EVENT_BITS_KEY_KEYPRESS; + } + else if (aType == "mousemove") { + aIID = kIDOMMouseMotionListenerIID; + *aFlags = NS_EVENT_BITS_MOUSEMOTION_MOUSEMOVE; + } + else if (aType == "focus") { + aIID = kIDOMFocusListenerIID; + *aFlags = NS_EVENT_BITS_FOCUS_FOCUS; + } + else if (aType == "blur") { + aIID = kIDOMFocusListenerIID; + *aFlags = NS_EVENT_BITS_FOCUS_BLUR; + } + else if (aType == "submit") { + aIID = kIDOMFormListenerIID; + *aFlags = NS_EVENT_BITS_FORM_SUBMIT; + } + else if (aType == "reset") { + aIID = kIDOMFormListenerIID; + *aFlags = NS_EVENT_BITS_FORM_RESET; + } + else if (aType == "change") { + aIID = kIDOMFormListenerIID; + *aFlags = NS_EVENT_BITS_FORM_CHANGE; + } + else if (aType == "load") { + aIID = kIDOMLoadListenerIID; + *aFlags = NS_EVENT_BITS_LOAD_LOAD; + } + else if (aType == "unload") { + aIID = kIDOMLoadListenerIID; + *aFlags = NS_EVENT_BITS_LOAD_UNLOAD; + } + else if (aType == "abort") { + aIID = kIDOMLoadListenerIID; + *aFlags = NS_EVENT_BITS_LOAD_ABORT; + } + else if (aType == "error") { + aIID = kIDOMLoadListenerIID; + *aFlags = NS_EVENT_BITS_LOAD_ERROR; + } + else if (aType == "paint") { + aIID = kIDOMPaintListenerIID; + *aFlags = NS_EVENT_BITS_PAINT_PAINT; + } + else { + return NS_ERROR_FAILURE; + } + return NS_OK; +} + +nsresult nsEventListenerManager::AddEventListenerByType(nsIDOMEventListener *aListener, + const nsString& aType, PRInt32 aFlags) +{ + PRInt32 subType; + nsIID iid; + + if (NS_OK == GetIdentifiersForType(aType, iid, &subType)) { + AddEventListener(aListener, iid, aFlags, subType); + } + + return NS_OK; +} + +nsresult nsEventListenerManager::RemoveEventListenerByType(nsIDOMEventListener *aListener, + const nsString& aType, PRInt32 aFlags) +{ + PRInt32 subType; + nsIID iid; + + if (NS_OK == GetIdentifiersForType(aType, iid, &subType)) { + RemoveEventListener(aListener, iid, aFlags, subType); + } + + return NS_OK; +} + const char *mEventArgv[] = {"event"}; nsresult nsEventListenerManager::SetJSEventListener(nsIScriptContext *aContext, JSObject *aObject, REFNSIID aIID) @@ -177,20 +376,18 @@ nsresult nsEventListenerManager::SetJSEventListener(nsIScriptContext *aContext, //Run through the listeners for this IID and see if a script listener is registered //If so, we're set. if (nsnull != mListeners) { - nsIScriptEventListener *mScriptListener; - nsIDOMEventListener *mEventListener; + nsListenerStruct *ls; for (int i=0; iCount(); i++) { - mEventListener = (nsIDOMEventListener*)mListeners->ElementAt(i); - if (NS_OK == mEventListener->QueryInterface(kIScriptEventListenerIID, (void**)&mScriptListener)) { - NS_RELEASE(mScriptListener); + ls = (nsListenerStruct*)mListeners->ElementAt(i); + if (ls->mFlags & NS_PRIV_EVENT_FLAG_SCRIPT) { return NS_OK; } } } //If we didn't find a script listener or no listeners existed create and add a new one. nsIDOMEventListener *mScriptListener; - if (NS_OK == NS_NewScriptEventListener(&mScriptListener, aContext, aObject)) { - AddEventListener(mScriptListener, aIID); + if (NS_OK == NS_NewJSEventListener(&mScriptListener, aContext, aObject)) { + AddEventListenerByIID(mScriptListener, aIID, NS_EVENT_FLAG_BUBBLE | NS_PRIV_EVENT_FLAG_SCRIPT); NS_RELEASE(mScriptListener); return NS_OK; } @@ -233,22 +430,6 @@ nsresult nsEventListenerManager::RegisterScriptEventListener(nsIScriptContext *a return NS_ERROR_FAILURE; } -/** -* Removes event listeners of all types. -* @param an event listener -*/ - -nsresult nsEventListenerManager::RemoveEventListener(nsIDOMEventListener *aListener, const nsIID& aIID) -{ - nsVoidArray** mListeners = GetListenersByIID(aIID); - - if (nsnull != *mListeners && PR_TRUE == (*mListeners)->RemoveElement((void*)aListener)) { - NS_RELEASE(aListener); - return NS_OK; - } - return NS_ERROR_FAILURE; -} - /** * Causes a check for event listeners and processing by them if they exist. * @param an event listener @@ -257,9 +438,13 @@ nsresult nsEventListenerManager::RemoveEventListener(nsIDOMEventListener *aListe nsresult nsEventListenerManager::HandleEvent(nsIPresContext& aPresContext, nsEvent* aEvent, nsIDOMEvent** aDOMEvent, + PRUint32 aFlags, nsEventStatus& aEventStatus) { nsresult ret = NS_OK; + if (aFlags & NS_EVENT_FLAG_INIT) { + aFlags |= NS_EVENT_FLAG_BUBBLE; + } switch(aEvent->message) { case NS_MOUSE_LEFT_BUTTON_DOWN: @@ -282,46 +467,94 @@ nsresult nsEventListenerManager::HandleEvent(nsIPresContext& aPresContext, } if (NS_OK == ret) { for (int i=0; iCount(); i++) { - nsIDOMEventListener *mEventListener; + nsListenerStruct *ls; nsIDOMMouseListener *mMouseListener; + nsIScriptEventListener *scriptListener; - mEventListener = (nsIDOMEventListener*)mMouseListeners->ElementAt(i); + ls = (nsListenerStruct*)mMouseListeners->ElementAt(i); - if (NS_OK == mEventListener->QueryInterface(kIDOMMouseListenerIID, (void**)&mMouseListener)) { - switch(aEvent->message) { - case NS_MOUSE_LEFT_BUTTON_DOWN: - case NS_MOUSE_MIDDLE_BUTTON_DOWN: - case NS_MOUSE_RIGHT_BUTTON_DOWN: - ret = mMouseListener->MouseDown(*aDOMEvent); - break; - case NS_MOUSE_LEFT_BUTTON_UP: - case NS_MOUSE_MIDDLE_BUTTON_UP: - case NS_MOUSE_RIGHT_BUTTON_UP: - ret = mMouseListener->MouseUp(*aDOMEvent); - break; - case NS_MOUSE_LEFT_CLICK: - case NS_MOUSE_MIDDLE_CLICK: - case NS_MOUSE_RIGHT_CLICK: - ret = mMouseListener->MouseClick(*aDOMEvent); - break; - case NS_MOUSE_LEFT_DOUBLECLICK: - case NS_MOUSE_MIDDLE_DOUBLECLICK: - case NS_MOUSE_RIGHT_DOUBLECLICK: - ret = mMouseListener->MouseDblClick(*aDOMEvent); - break; - case NS_MOUSE_ENTER: - ret = mMouseListener->MouseOver(*aDOMEvent); - break; - case NS_MOUSE_EXIT: - ret = mMouseListener->MouseOut(*aDOMEvent); - break; - default: - break; + if (ls->mFlags & aFlags) { + if (NS_OK == ls->mListener->QueryInterface(kIDOMMouseListenerIID, (void**)&mMouseListener)) { + switch(aEvent->message) { + case NS_MOUSE_LEFT_BUTTON_DOWN: + case NS_MOUSE_MIDDLE_BUTTON_DOWN: + case NS_MOUSE_RIGHT_BUTTON_DOWN: + ret = mMouseListener->MouseDown(*aDOMEvent); + break; + case NS_MOUSE_LEFT_BUTTON_UP: + case NS_MOUSE_MIDDLE_BUTTON_UP: + case NS_MOUSE_RIGHT_BUTTON_UP: + ret = mMouseListener->MouseUp(*aDOMEvent); + break; + case NS_MOUSE_LEFT_CLICK: + case NS_MOUSE_MIDDLE_CLICK: + case NS_MOUSE_RIGHT_CLICK: + ret = mMouseListener->MouseClick(*aDOMEvent); + break; + case NS_MOUSE_LEFT_DOUBLECLICK: + case NS_MOUSE_MIDDLE_DOUBLECLICK: + case NS_MOUSE_RIGHT_DOUBLECLICK: + ret = mMouseListener->MouseDblClick(*aDOMEvent); + break; + case NS_MOUSE_ENTER: + ret = mMouseListener->MouseOver(*aDOMEvent); + break; + case NS_MOUSE_EXIT: + ret = mMouseListener->MouseOut(*aDOMEvent); + break; + default: + break; + } + NS_RELEASE(mMouseListener); + } + else { + PRBool correctSubType = PR_FALSE; + switch(aEvent->message) { + case NS_MOUSE_LEFT_BUTTON_DOWN: + case NS_MOUSE_MIDDLE_BUTTON_DOWN: + case NS_MOUSE_RIGHT_BUTTON_DOWN: + if (ls->mSubType & NS_EVENT_BITS_MOUSE_MOUSEDOWN) { + correctSubType = PR_TRUE; + } + break; + case NS_MOUSE_LEFT_BUTTON_UP: + case NS_MOUSE_MIDDLE_BUTTON_UP: + case NS_MOUSE_RIGHT_BUTTON_UP: + if (ls->mSubType & NS_EVENT_BITS_MOUSE_MOUSEUP) { + correctSubType = PR_TRUE; + } + break; + case NS_MOUSE_LEFT_CLICK: + case NS_MOUSE_MIDDLE_CLICK: + case NS_MOUSE_RIGHT_CLICK: + if (ls->mSubType & NS_EVENT_BITS_MOUSE_CLICK) { + correctSubType = PR_TRUE; + } + break; + case NS_MOUSE_LEFT_DOUBLECLICK: + case NS_MOUSE_MIDDLE_DOUBLECLICK: + case NS_MOUSE_RIGHT_DOUBLECLICK: + if (ls->mSubType & NS_EVENT_BITS_MOUSE_DBLCLICK) { + correctSubType = PR_TRUE; + } + break; + case NS_MOUSE_ENTER: + if (ls->mSubType & NS_EVENT_BITS_MOUSE_MOUSEOVER) { + correctSubType = PR_TRUE; + } + break; + case NS_MOUSE_EXIT: + if (ls->mSubType & NS_EVENT_BITS_MOUSE_MOUSEOUT) { + correctSubType = PR_TRUE; + } + break; + default: + break; + } + if (correctSubType || ls->mSubType == NS_EVENT_BITS_NONE) { + ret = ls->mListener->HandleEvent(*aDOMEvent); + } } - NS_RELEASE(mMouseListener); - } - else { - ret = mEventListener->ProcessEvent(*aDOMEvent); } aEventStatus = (NS_OK == ret) ? aEventStatus : nsEventStatus_eConsumeNoDefault; } @@ -336,23 +569,37 @@ nsresult nsEventListenerManager::HandleEvent(nsIPresContext& aPresContext, } if (NS_OK == ret) { for (int i=0; iCount(); i++) { - nsIDOMEventListener *mEventListener; + nsListenerStruct *ls; nsIDOMMouseMotionListener *mMouseMotionListener; - mEventListener = (nsIDOMEventListener*)mMouseMotionListeners->ElementAt(i); + ls = (nsListenerStruct*)mMouseMotionListeners->ElementAt(i); - if (NS_OK == mEventListener->QueryInterface(kIDOMMouseMotionListenerIID, (void**)&mMouseMotionListener)) { - switch(aEvent->message) { - case NS_MOUSE_MOVE: - ret = mMouseMotionListener->MouseMove(*aDOMEvent); - break; - default: - break; + if (ls->mFlags & aFlags) { + if (NS_OK == ls->mListener->QueryInterface(kIDOMMouseMotionListenerIID, (void**)&mMouseMotionListener)) { + switch(aEvent->message) { + case NS_MOUSE_MOVE: + ret = mMouseMotionListener->MouseMove(*aDOMEvent); + break; + default: + break; + } + NS_RELEASE(mMouseMotionListener); + } + else { + PRBool correctSubType = PR_FALSE; + switch(aEvent->message) { + case NS_MOUSE_MOVE: + if (ls->mSubType & NS_EVENT_BITS_MOUSEMOTION_MOUSEMOVE) { + correctSubType = PR_TRUE; + } + break; + default: + break; + } + if (correctSubType || ls->mSubType == NS_EVENT_BITS_NONE) { + ret = ls->mListener->HandleEvent(*aDOMEvent); + } } - NS_RELEASE(mMouseMotionListener); - } - else { - ret = mEventListener->ProcessEvent(*aDOMEvent); } aEventStatus = (NS_OK == ret) ? aEventStatus : nsEventStatus_eConsumeNoDefault; } @@ -362,28 +609,36 @@ nsresult nsEventListenerManager::HandleEvent(nsIPresContext& aPresContext, case NS_TEXT_EVENT: #if DEBUG_TAGUE - printf("DOM: got text event\n"); + printf("DOM: got text event\n"); #endif - if (nsnull != mTextListeners) { - if (nsnull == *aDOMEvent) { - ret = NS_NewDOMEvent(aDOMEvent,aPresContext,aEvent); - } - if (NS_OK == ret) { - for (int i=0; iCount(); i++) { - nsIDOMEventListener *mEventListener; - nsIDOMTextListener *mTextListener; + if (nsnull != mTextListeners) { + if (nsnull == *aDOMEvent) { + ret = NS_NewDOMEvent(aDOMEvent,aPresContext,aEvent); + } + if (NS_OK == ret) { + for (int i=0; iCount(); i++) { + nsListenerStruct *ls; + nsIDOMTextListener *mTextListener; - mEventListener = (nsIDOMEventListener*)mTextListeners->ElementAt(i); - - if (NS_OK == mEventListener->QueryInterface(kIDOMTextListenerIID, (void**)&mTextListener)) { - ret = mTextListener->HandleText(*aDOMEvent); - NS_RELEASE(mTextListener); - } - else { - ret = mEventListener->ProcessEvent(*aDOMEvent); - } + ls = (nsListenerStruct*)mTextListeners->ElementAt(i); + + if (ls->mFlags & aFlags) { + if (NS_OK == ls->mListener->QueryInterface(kIDOMTextListenerIID, (void**)&mTextListener)) { + ret = mTextListener->HandleText(*aDOMEvent); + NS_RELEASE(mTextListener); + } + else { + PRBool correctSubType = PR_FALSE; + if (ls->mSubType & NS_EVENT_BITS_TEXT_TEXT) { + correctSubType = PR_TRUE; + } + if (correctSubType || ls->mSubType == NS_EVENT_BITS_NONE) { + ret = ls->mListener->HandleEvent(*aDOMEvent); + } + } + } + aEventStatus = (NS_OK == ret) ? aEventStatus : nsEventStatus_eConsumeNoDefault; } - aEventStatus = (NS_OK == ret) ? aEventStatus : nsEventStatus_eConsumeNoDefault; } } break; @@ -397,29 +652,53 @@ nsresult nsEventListenerManager::HandleEvent(nsIPresContext& aPresContext, } if (NS_OK == ret) { for (int i=0; iCount(); i++) { - nsIDOMEventListener *mEventListener; + nsListenerStruct *ls; nsIDOMKeyListener *mKeyListener; - mEventListener = (nsIDOMEventListener*)mKeyListeners->ElementAt(i); + ls = (nsListenerStruct*)mKeyListeners->ElementAt(i); - if (NS_OK == mEventListener->QueryInterface(kIDOMKeyListenerIID, (void**)&mKeyListener)) { - switch(aEvent->message) { - case NS_KEY_UP: - ret = mKeyListener->KeyUp(*aDOMEvent); - break; - case NS_KEY_DOWN: - ret = mKeyListener->KeyDown(*aDOMEvent); - break; - case NS_KEY_PRESS: - ret = mKeyListener->KeyPress(*aDOMEvent); - break; - default: - break; + if (ls->mFlags & aFlags) { + if (NS_OK == ls->mListener->QueryInterface(kIDOMKeyListenerIID, (void**)&mKeyListener)) { + switch(aEvent->message) { + case NS_KEY_UP: + ret = mKeyListener->KeyUp(*aDOMEvent); + break; + case NS_KEY_DOWN: + ret = mKeyListener->KeyDown(*aDOMEvent); + break; + case NS_KEY_PRESS: + ret = mKeyListener->KeyPress(*aDOMEvent); + break; + default: + break; + } + NS_RELEASE(mKeyListener); + } + else { + PRBool correctSubType = PR_FALSE; + switch(aEvent->message) { + case NS_KEY_UP: + if (ls->mSubType & NS_EVENT_BITS_KEY_KEYUP) { + correctSubType = PR_TRUE; + } + break; + case NS_KEY_DOWN: + if (ls->mSubType & NS_EVENT_BITS_KEY_KEYDOWN) { + correctSubType = PR_TRUE; + } + break; + case NS_KEY_PRESS: + if (ls->mSubType & NS_EVENT_BITS_KEY_KEYPRESS) { + correctSubType = PR_TRUE; + } + break; + default: + break; + } + if (correctSubType || ls->mSubType == NS_EVENT_BITS_NONE) { + ret = ls->mListener->HandleEvent(*aDOMEvent); + } } - NS_RELEASE(mKeyListener); - } - else { - ret = mEventListener->ProcessEvent(*aDOMEvent); } aEventStatus = (NS_OK == ret) ? aEventStatus : nsEventStatus_eConsumeNoDefault; } @@ -427,34 +706,53 @@ nsresult nsEventListenerManager::HandleEvent(nsIPresContext& aPresContext, } break; - case NS_GOTFOCUS: - case NS_LOSTFOCUS: + case NS_FOCUS_CONTENT: + case NS_BLUR_CONTENT: if (nsnull != mFocusListeners) { if (nsnull == *aDOMEvent) { ret = NS_NewDOMEvent(aDOMEvent, aPresContext, aEvent); } if (NS_OK == ret) { for (int i=0; iCount(); i++) { - nsIDOMEventListener *mEventListener; + nsListenerStruct *ls; nsIDOMFocusListener *mFocusListener; - mEventListener = (nsIDOMEventListener*)mFocusListeners->ElementAt(i); + ls = (nsListenerStruct*)mFocusListeners->ElementAt(i); - if (NS_OK == mEventListener->QueryInterface(kIDOMFocusListenerIID, (void**)&mFocusListener)) { - switch(aEvent->message) { - case NS_GOTFOCUS: - ret = mFocusListener->Focus(*aDOMEvent); - break; - case NS_LOSTFOCUS: - ret = mFocusListener->Blur(*aDOMEvent); - break; - default: - break; + if (ls->mFlags & aFlags) { + if (NS_OK == ls->mListener->QueryInterface(kIDOMFocusListenerIID, (void**)&mFocusListener)) { + switch(aEvent->message) { + case NS_FOCUS_CONTENT: + ret = mFocusListener->Focus(*aDOMEvent); + break; + case NS_BLUR_CONTENT: + ret = mFocusListener->Blur(*aDOMEvent); + break; + default: + break; + } + NS_RELEASE(mFocusListener); + } + else { + PRBool correctSubType = PR_FALSE; + switch(aEvent->message) { + case NS_FOCUS_CONTENT: + if (ls->mSubType & NS_EVENT_BITS_FOCUS_FOCUS) { + correctSubType = PR_TRUE; + } + break; + case NS_BLUR_CONTENT: + if (ls->mSubType & NS_EVENT_BITS_FOCUS_BLUR) { + correctSubType = PR_TRUE; + } + break; + default: + break; + } + if (correctSubType || ls->mSubType == NS_EVENT_BITS_NONE) { + ret = ls->mListener->HandleEvent(*aDOMEvent); + } } - NS_RELEASE(mFocusListener); - } - else { - ret = mEventListener->ProcessEvent(*aDOMEvent); } aEventStatus = (NS_OK == ret) ? aEventStatus : nsEventStatus_eConsumeNoDefault; } @@ -471,29 +769,53 @@ nsresult nsEventListenerManager::HandleEvent(nsIPresContext& aPresContext, } if (NS_OK == ret) { for (int i=0; iCount(); i++) { - nsIDOMEventListener *mEventListener; + nsListenerStruct *ls; nsIDOMFormListener *mFormListener; - mEventListener = (nsIDOMEventListener*)mFormListeners->ElementAt(i); + ls = (nsListenerStruct*)mFormListeners->ElementAt(i); - if (NS_OK == mEventListener->QueryInterface(kIDOMFormListenerIID, (void**)&mFormListener)) { - switch(aEvent->message) { - case NS_FORM_SUBMIT: - ret = mFormListener->Submit(*aDOMEvent); - break; - case NS_FORM_RESET: - ret = mFormListener->Reset(*aDOMEvent); - break; - case NS_FORM_CHANGE: - ret = mFormListener->Change(*aDOMEvent); - break; - default: - break; + if (ls->mFlags & aFlags) { + if (NS_OK == ls->mListener->QueryInterface(kIDOMFormListenerIID, (void**)&mFormListener)) { + switch(aEvent->message) { + case NS_FORM_SUBMIT: + ret = mFormListener->Submit(*aDOMEvent); + break; + case NS_FORM_RESET: + ret = mFormListener->Reset(*aDOMEvent); + break; + case NS_FORM_CHANGE: + ret = mFormListener->Change(*aDOMEvent); + break; + default: + break; + } + NS_RELEASE(mFormListener); + } + else { + PRBool correctSubType = PR_FALSE; + switch(aEvent->message) { + case NS_FORM_SUBMIT: + if (ls->mSubType & NS_EVENT_BITS_FORM_SUBMIT) { + correctSubType = PR_TRUE; + } + break; + case NS_FORM_RESET: + if (ls->mSubType & NS_EVENT_BITS_FORM_RESET) { + correctSubType = PR_TRUE; + } + break; + case NS_FORM_CHANGE: + if (ls->mSubType & NS_EVENT_BITS_FORM_CHANGE) { + correctSubType = PR_TRUE; + } + break; + default: + break; + } + if (correctSubType || ls->mSubType == NS_EVENT_BITS_NONE) { + ret = ls->mListener->HandleEvent(*aDOMEvent); + } } - NS_RELEASE(mFormListener); - } - else { - ret = mEventListener->ProcessEvent(*aDOMEvent); } aEventStatus = (NS_OK == ret) ? aEventStatus : nsEventStatus_eConsumeNoDefault; } @@ -509,26 +831,45 @@ nsresult nsEventListenerManager::HandleEvent(nsIPresContext& aPresContext, } if (NS_OK == ret) { for (int i=0; iCount(); i++) { - nsIDOMEventListener *mEventListener; + nsListenerStruct *ls; nsIDOMLoadListener *mLoadListener; - mEventListener = (nsIDOMEventListener*)mLoadListeners->ElementAt(i); + ls = (nsListenerStruct*)mLoadListeners->ElementAt(i); - if (NS_OK == mEventListener->QueryInterface(kIDOMLoadListenerIID, (void**)&mLoadListener)) { - switch(aEvent->message) { - case NS_PAGE_LOAD: - ret = mLoadListener->Load(*aDOMEvent); - break; - case NS_PAGE_UNLOAD: - ret = mLoadListener->Unload(*aDOMEvent); - break; - default: - break; + if (ls->mFlags & aFlags) { + if (NS_OK == ls->mListener->QueryInterface(kIDOMLoadListenerIID, (void**)&mLoadListener)) { + switch(aEvent->message) { + case NS_PAGE_LOAD: + ret = mLoadListener->Load(*aDOMEvent); + break; + case NS_PAGE_UNLOAD: + ret = mLoadListener->Unload(*aDOMEvent); + break; + default: + break; + } + NS_RELEASE(mLoadListener); + } + else { + PRBool correctSubType = PR_FALSE; + switch(aEvent->message) { + case NS_PAGE_LOAD: + if (ls->mSubType & NS_EVENT_BITS_LOAD_LOAD) { + correctSubType = PR_TRUE; + } + break; + case NS_PAGE_UNLOAD: + if (ls->mSubType & NS_EVENT_BITS_LOAD_UNLOAD) { + correctSubType = PR_TRUE; + } + break; + default: + break; + } + if (correctSubType || ls->mSubType == NS_EVENT_BITS_NONE) { + ret = ls->mListener->HandleEvent(*aDOMEvent); + } } - NS_RELEASE(mLoadListener); - } - else { - ret = mEventListener->ProcessEvent(*aDOMEvent); } aEventStatus = (NS_OK == ret) ? aEventStatus : nsEventStatus_eConsumeNoDefault; } @@ -543,18 +884,26 @@ nsresult nsEventListenerManager::HandleEvent(nsIPresContext& aPresContext, } if (NS_OK == ret) { for (int i=0; iCount(); i++) { - nsIDOMEventListener *eventListener; + nsListenerStruct *ls; nsIDOMPaintListener *paintListener; - eventListener = (nsIDOMEventListener*)mPaintListeners->ElementAt(i); + ls = (nsListenerStruct*)mPaintListeners->ElementAt(i); - if (NS_OK == eventListener->QueryInterface(kIDOMPaintListenerIID, - (void**)&paintListener)) { - ret = paintListener->Paint(*aDOMEvent); - NS_RELEASE(paintListener); - } - else { - ret = eventListener->ProcessEvent(*aDOMEvent); + if (ls->mFlags & aFlags) { + if (NS_OK == ls->mListener->QueryInterface(kIDOMPaintListenerIID, + (void**)&paintListener)) { + ret = paintListener->Paint(*aDOMEvent); + NS_RELEASE(paintListener); + } + else { + PRBool correctSubType = PR_FALSE; + if (ls->mSubType & NS_EVENT_BITS_PAINT_PAINT) { + correctSubType = PR_TRUE; + } + if (correctSubType || ls->mSubType == NS_EVENT_BITS_NONE) { + ret = ls->mListener->HandleEvent(*aDOMEvent); + } + } } aEventStatus = (NS_OK == ret) ? aEventStatus diff --git a/content/events/src/nsEventListenerManager.h b/content/events/src/nsEventListenerManager.h index 1c1b3fe4dfbf..c7d7be7422bb 100644 --- a/content/events/src/nsEventListenerManager.h +++ b/content/events/src/nsEventListenerManager.h @@ -23,7 +23,16 @@ #include "jsapi.h" class nsIDOMEvent; - + +typedef struct { + nsIDOMEventListener* mListener; + PRUint8 mFlags; + PRUint8 mSubType; +} nsListenerStruct; + +//Flag must live higher than all event flags in nsGUIEvent.h +#define NS_PRIV_EVENT_FLAG_SCRIPT 0x10 + /* * Event listener manager */ @@ -52,7 +61,11 @@ public: * @param an event listener */ - virtual nsresult AddEventListener(nsIDOMEventListener *aListener, REFNSIID aIID); + virtual nsresult AddEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID, PRInt32 aFlags); + virtual nsresult RemoveEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID, PRInt32 aFlags); + virtual nsresult AddEventListenerByType(nsIDOMEventListener *aListener, const nsString& type, PRInt32 aFlags); + virtual nsresult RemoveEventListenerByType(nsIDOMEventListener *aListener, const nsString& type, PRInt32 aFlags) ; + virtual nsresult AddScriptEventListener(nsIScriptContext* aContext, nsIScriptObjectOwner *aScriptObjectOwner, nsIAtom *aName, @@ -62,14 +75,14 @@ public: nsIScriptObjectOwner *aScriptObjectOwner, const nsIID& aIID); - virtual nsresult RemoveEventListener(nsIDOMEventListener *aListener, REFNSIID aIID); virtual nsresult CaptureEvent(nsIDOMEventListener *aListener); virtual nsresult ReleaseEvent(nsIDOMEventListener *aListener); virtual nsresult HandleEvent(nsIPresContext& aPresContext, nsEvent* aEvent, - nsIDOMEvent** aDOMEvent, + nsIDOMEvent** aDOMEvent, + PRUint32 aFlags, nsEventStatus& aEventStatus); virtual nsresult CreateEvent(nsIPresContext& aPresContext, @@ -78,6 +91,9 @@ public: protected: nsresult SetJSEventListener(nsIScriptContext *aContext, JSObject *aObject, REFNSIID aIID); + nsresult GetIdentifiersForType(const nsString& aType, nsIID& aIID, PRInt32* aSubType); + nsresult AddEventListener(nsIDOMEventListener *aListener, const nsIID& aIID, PRInt32 aFlags, PRInt32 aSubType); + nsresult RemoveEventListener(nsIDOMEventListener *aListener, const nsIID& aIID, PRInt32 aFlags, PRInt32 aSubType); nsVoidArray* mEventListeners; nsVoidArray* mMouseListeners; @@ -92,4 +108,61 @@ protected: }; + +//Set of defines for distinguishing event hanlders within listener groupings +//XXX Current usage allows no more than 7 types per listener grouping + +#define NS_EVENT_BITS_NONE 0x00 + +//nsIDOMMouseListener +#define NS_EVENT_BITS_MOUSE_NONE 0x00 +#define NS_EVENT_BITS_MOUSE_MOUSEDOWN 0x01 +#define NS_EVENT_BITS_MOUSE_MOUSEUP 0x02 +#define NS_EVENT_BITS_MOUSE_CLICK 0x04 +#define NS_EVENT_BITS_MOUSE_DBLCLICK 0x08 +#define NS_EVENT_BITS_MOUSE_MOUSEOVER 0x10 +#define NS_EVENT_BITS_MOUSE_MOUSEOUT 0x20 + +//nsIDOMMouseMotionListener +#define NS_EVENT_BITS_MOUSEMOTION_NONE 0x00 +#define NS_EVENT_BITS_MOUSEMOTION_MOUSEMOVE 0x01 +#define NS_EVENT_BITS_MOUSEMOTION_DRAGMOVE 0x02 + +//nsIDOMKeyListener +#define NS_EVENT_BITS_KEY_NONE 0x00 +#define NS_EVENT_BITS_KEY_KEYDOWN 0x01 +#define NS_EVENT_BITS_KEY_KEYUP 0x02 +#define NS_EVENT_BITS_KEY_KEYPRESS 0x04 + +//nsIDOMTextListener +#define NS_EVENT_BITS_TEXT_NONE 0x00 +#define NS_EVENT_BITS_TEXT_TEXT 0x01 + +//nsIDOMFocusListener +#define NS_EVENT_BITS_FOCUS_NONE 0x00 +#define NS_EVENT_BITS_FOCUS_FOCUS 0x01 +#define NS_EVENT_BITS_FOCUS_BLUR 0x02 + +//nsIDOMFormListener +#define NS_EVENT_BITS_FORM_NONE 0x00 +#define NS_EVENT_BITS_FORM_SUBMIT 0x01 +#define NS_EVENT_BITS_FORM_RESET 0x02 +#define NS_EVENT_BITS_FORM_CHANGE 0x04 + +//nsIDOMLoadListener +#define NS_EVENT_BITS_LOAD_NONE 0x00 +#define NS_EVENT_BITS_LOAD_LOAD 0x01 +#define NS_EVENT_BITS_LOAD_UNLOAD 0x02 +#define NS_EVENT_BITS_LOAD_ABORT 0x04 +#define NS_EVENT_BITS_LOAD_ERROR 0x08 + +//nsIDOMDragListener +#define NS_EVENT_BITS_DRAG_NONE 0x00 +#define NS_EVENT_BITS_DRAG_START 0x01 +#define NS_EVENT_BITS_DRAG_DROP 0x02 + +//nsIDOMPaintListener +#define NS_EVENT_BITS_PAINT_NONE 0x00 +#define NS_EVENT_BITS_PAINT_PAINT 0x01 + #endif // nsEventListenerManager_h__ diff --git a/content/events/src/nsEventStateManager.cpp b/content/events/src/nsEventStateManager.cpp index 2e6717d83f9d..3a60886cc363 100644 --- a/content/events/src/nsEventStateManager.cpp +++ b/content/events/src/nsEventStateManager.cpp @@ -53,12 +53,12 @@ static NS_DEFINE_IID(kIFocusableContentIID, NS_IFOCUSABLECONTENT_IID); nsEventStateManager::nsEventStateManager() { mLastMouseOverFrame = nsnull; mCurrentTarget = nsnull; - mLastLeftMouseDownFrame = nsnull; - mLastMiddleMouseDownFrame = nsnull; - mLastRightMouseDownFrame = nsnull; + mLastLeftMouseDownContent = nsnull; + mLastMiddleMouseDownContent = nsnull; + mLastRightMouseDownContent = nsnull; - mActiveLink = nsnull; - mHoverLink = nsnull; + mActiveContent = nsnull; + mHoverContent = nsnull; mCurrentFocus = nsnull; mDocument = nsnull; mPresContext = nsnull; @@ -67,10 +67,13 @@ nsEventStateManager::nsEventStateManager() { } nsEventStateManager::~nsEventStateManager() { - NS_IF_RELEASE(mActiveLink); - NS_IF_RELEASE(mHoverLink); + NS_IF_RELEASE(mActiveContent); + NS_IF_RELEASE(mHoverContent); NS_IF_RELEASE(mCurrentFocus); NS_IF_RELEASE(mDocument); + NS_IF_RELEASE(mLastLeftMouseDownContent); + NS_IF_RELEASE(mLastMiddleMouseDownContent); + NS_IF_RELEASE(mLastRightMouseDownContent); } NS_IMPL_ADDREF(nsEventStateManager) @@ -98,7 +101,7 @@ nsEventStateManager::PreHandleEvent(nsIPresContext& aPresContext, GenerateMouseEnterExit(aPresContext, aEvent); break; case NS_MOUSE_EXIT: - //GenerateMouseEnterExit(aPresContext, aEvent, aTargetFrame); + GenerateMouseEnterExit(aPresContext, aEvent); break; case NS_GOTFOCUS: //XXX Do we need window related focus change stuff here? @@ -126,6 +129,8 @@ nsEventStateManager::PostHandleEvent(nsIPresContext& aPresContext, case NS_MOUSE_MIDDLE_BUTTON_DOWN: case NS_MOUSE_RIGHT_BUTTON_DOWN: { + ret = CheckForAndDispatchClick(aPresContext, (nsMouseEvent*)aEvent, aStatus); + nsIContent* newFocus; mCurrentTarget->GetContent(&newFocus); if (newFocus) { @@ -137,12 +142,12 @@ nsEventStateManager::PostHandleEvent(nsIPresContext& aPresContext, NS_RELEASE(newFocus); } } - //Break left out on purpose + break; case NS_MOUSE_LEFT_BUTTON_UP: case NS_MOUSE_MIDDLE_BUTTON_UP: case NS_MOUSE_RIGHT_BUTTON_UP: - mCurrentTarget = aTargetFrame; ret = CheckForAndDispatchClick(aPresContext, (nsMouseEvent*)aEvent, aStatus); + SetActiveContent(nsnull); break; case NS_KEY_DOWN: ret = DispatchKeyPressEvent(aPresContext, (nsKeyEvent*)aEvent, aStatus); @@ -182,15 +187,6 @@ nsEventStateManager::ClearFrameRefs(nsIFrame* aFrame) if (aFrame == mCurrentTarget) { mCurrentTarget = nsnull; } - if (aFrame == mLastLeftMouseDownFrame) { - mLastLeftMouseDownFrame = nsnull; - } - if (aFrame == mLastMiddleMouseDownFrame) { - mLastMiddleMouseDownFrame = nsnull; - } - if (aFrame == mLastRightMouseDownFrame) { - mLastRightMouseDownFrame = nsnull; - } return NS_OK; } @@ -274,7 +270,7 @@ nsEventStateManager::GenerateMouseEnterExit(nsIPresContext& aPresContext, nsGUIE if (lastContent != targetContent) { //XXX This event should still go somewhere!! if (nsnull != lastContent) { - lastContent->HandleDOMEvent(aPresContext, &event, nsnull, DOM_EVENT_INIT, status); + lastContent->HandleDOMEvent(aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); } } @@ -296,7 +292,7 @@ nsEventStateManager::GenerateMouseEnterExit(nsIPresContext& aPresContext, nsGUIE if (lastContent != targetContent) { //XXX This event should still go somewhere!! if (nsnull != targetContent) { - targetContent->HandleDOMEvent(aPresContext, &event, nsnull, DOM_EVENT_INIT, status); + targetContent->HandleDOMEvent(aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); } } @@ -329,7 +325,7 @@ nsEventStateManager::GenerateMouseEnterExit(nsIPresContext& aPresContext, nsGUIE mLastMouseOverFrame->GetContent(&lastContent); if (nsnull != lastContent) { - lastContent->HandleDOMEvent(aPresContext, &event, nsnull, DOM_EVENT_INIT, status); + lastContent->HandleDOMEvent(aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); NS_RELEASE(lastContent); } @@ -352,35 +348,44 @@ nsEventStateManager::CheckForAndDispatchClick(nsIPresContext& aPresContext, { nsresult ret = NS_OK; nsMouseEvent event; + nsIContent* mouseContent; PRBool fireClick = PR_FALSE; + mCurrentTarget->GetContent(&mouseContent); + switch (aEvent->message) { case NS_MOUSE_LEFT_BUTTON_DOWN: - mLastLeftMouseDownFrame = mCurrentTarget; + mLastLeftMouseDownContent = mouseContent; + NS_IF_ADDREF(mLastLeftMouseDownContent); break; case NS_MOUSE_LEFT_BUTTON_UP: - if (mLastLeftMouseDownFrame == mCurrentTarget) { + if (mLastLeftMouseDownContent == mouseContent) { fireClick = PR_TRUE; event.message = NS_MOUSE_LEFT_CLICK; } + NS_IF_RELEASE(mLastLeftMouseDownContent); break; case NS_MOUSE_MIDDLE_BUTTON_DOWN: - mLastMiddleMouseDownFrame = mCurrentTarget; + mLastMiddleMouseDownContent = mouseContent; + NS_IF_ADDREF(mLastMiddleMouseDownContent); break; case NS_MOUSE_MIDDLE_BUTTON_UP: - if (mLastMiddleMouseDownFrame == mCurrentTarget) { + if (mLastMiddleMouseDownContent == mouseContent) { fireClick = PR_TRUE; event.message = NS_MOUSE_MIDDLE_CLICK; } + NS_IF_RELEASE(mLastMiddleMouseDownContent); break; case NS_MOUSE_RIGHT_BUTTON_DOWN: - mLastRightMouseDownFrame = mCurrentTarget; + mLastRightMouseDownContent = mouseContent; + NS_IF_ADDREF(mLastRightMouseDownContent); break; case NS_MOUSE_RIGHT_BUTTON_UP: - if (mLastRightMouseDownFrame == mCurrentTarget) { + if (mLastRightMouseDownContent == mouseContent) { fireClick = PR_TRUE; event.message = NS_MOUSE_RIGHT_CLICK; } + NS_IF_RELEASE(mLastRightMouseDownContent); break; } @@ -389,17 +394,9 @@ nsEventStateManager::CheckForAndDispatchClick(nsIPresContext& aPresContext, event.eventStructType = NS_MOUSE_EVENT; event.widget = nsnull; - nsIContent *content; - mCurrentTarget->GetContent(&content); - - if (nsnull != content) { - ret = content->HandleDOMEvent(aPresContext, &event, nsnull, DOM_EVENT_INIT, aStatus); - NS_RELEASE(content); - } - - //Now dispatch to the frame - if (nsnull != mCurrentTarget) { - mCurrentTarget->HandleEvent(aPresContext, &event, aStatus); + if (nsnull != mouseContent) { + ret = mouseContent->HandleDOMEvent(aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, aStatus); + NS_RELEASE(mouseContent); } } return ret; @@ -423,7 +420,7 @@ nsEventStateManager::DispatchKeyPressEvent(nsIPresContext& aPresContext, mCurrentTarget->GetContent(&content); if (nsnull != content) { - ret = content->HandleDOMEvent(aPresContext, &event, nsnull, DOM_EVENT_INIT, aStatus); + ret = content->HandleDOMEvent(aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, aStatus); NS_RELEASE(content); } @@ -679,39 +676,45 @@ nsEventStateManager::GetEventTarget(nsIFrame **aFrame) } NS_IMETHODIMP -nsEventStateManager::GetLinkState(nsIContent *aLink, nsLinkEventState& aState) +nsEventStateManager::GetContentState(nsIContent *aContent, PRInt32& aState) { - if (aLink == mActiveLink) { - aState = eLinkState_Active; + aState = NS_EVENT_STATE_UNSPECIFIED; + + if (aContent == mActiveContent) { + aState |= NS_EVENT_STATE_ACTIVE; } - else if (aLink == mHoverLink) { - aState = eLinkState_Hover; + if (aContent == mHoverContent) { + aState |= NS_EVENT_STATE_HOVER; } - else { - aState = eLinkState_Unspecified; + if (aContent == mCurrentFocus) { + aState |= NS_EVENT_STATE_FOCUS; } return NS_OK; } NS_IMETHODIMP -nsEventStateManager::SetActiveLink(nsIContent *aLink) +nsEventStateManager::SetActiveContent(nsIContent *aActive) { nsIDocument *mDocument; - if (nsnull != mActiveLink) { - if (NS_OK == mActiveLink->GetDocument(mDocument)) { - mDocument->ContentStateChanged(mActiveLink); + if (nsnull != mActiveContent) { + //transferring ref to lastActive from mActiveContent + nsIContent *lastActive = mActiveContent; + + if (NS_OK == mActiveContent->GetDocument(mDocument)) { + mActiveContent = nsnull; + mDocument->ContentStateChanged(lastActive); NS_RELEASE(mDocument); } + NS_RELEASE(lastActive); } - NS_IF_RELEASE(mActiveLink); - mActiveLink = aLink; + mActiveContent = aActive; + NS_IF_ADDREF(mActiveContent); - NS_IF_ADDREF(mActiveLink); - if (nsnull != mActiveLink) { - if (NS_OK == mActiveLink->GetDocument(mDocument)) { - mDocument->ContentStateChanged(mActiveLink); + if (nsnull != mActiveContent) { + if (NS_OK == mActiveContent->GetDocument(mDocument)) { + mDocument->ContentStateChanged(mActiveContent); NS_RELEASE(mDocument); } } @@ -720,24 +723,28 @@ nsEventStateManager::SetActiveLink(nsIContent *aLink) } NS_IMETHODIMP -nsEventStateManager::SetHoverLink(nsIContent *aLink) +nsEventStateManager::SetHoverContent(nsIContent *aHover) { nsIDocument *mDocument; - if (nsnull != mHoverLink) { - if (NS_OK == mHoverLink->GetDocument(mDocument)) { - mDocument->ContentStateChanged(mHoverLink); + if (nsnull != mHoverContent) { + //transferring ref to lastHover from mActiveContent + nsIContent *lastHover = mHoverContent; + + if (NS_OK == mHoverContent->GetDocument(mDocument)) { + mHoverContent = nsnull; + mDocument->ContentStateChanged(lastHover); NS_RELEASE(mDocument); } + NS_RELEASE(lastHover); } - NS_IF_RELEASE(mHoverLink); - mHoverLink = aLink; + mHoverContent = aHover; - NS_IF_ADDREF(mHoverLink); - if (nsnull != mHoverLink) { - if (NS_OK == mHoverLink->GetDocument(mDocument)) { - mDocument->ContentStateChanged(mHoverLink); + NS_IF_ADDREF(mHoverContent); + if (nsnull != mHoverContent) { + if (NS_OK == mHoverContent->GetDocument(mDocument)) { + mDocument->ContentStateChanged(mHoverContent); NS_RELEASE(mDocument); } } @@ -762,7 +769,7 @@ nsEventStateManager::SetFocusedContent(nsIContent *aContent) event.message = NS_BLUR_CONTENT; if (nsnull != mPresContext) { - mCurrentFocus->HandleDOMEvent(*mPresContext, &event, nsnull, DOM_EVENT_INIT, status); + mCurrentFocus->HandleDOMEvent(*mPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); } NS_RELEASE(mCurrentFocus); } @@ -774,7 +781,7 @@ nsEventStateManager::SetFocusedContent(nsIContent *aContent) event.message = NS_FOCUS_CONTENT; if (nsnull != mPresContext) { - aContent->HandleDOMEvent(*mPresContext, &event, nsnull, DOM_EVENT_INIT, status); + aContent->HandleDOMEvent(*mPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); } nsAutoString tabIndex; diff --git a/content/events/src/nsEventStateManager.h b/content/events/src/nsEventStateManager.h index ad9034577f5b..4b43bd89e055 100644 --- a/content/events/src/nsEventStateManager.h +++ b/content/events/src/nsEventStateManager.h @@ -50,10 +50,9 @@ public: NS_IMETHOD GetEventTarget(nsIFrame **aFrame); - NS_IMETHOD GetLinkState(nsIContent *aLink, nsLinkEventState& aState); - NS_IMETHOD SetActiveLink(nsIContent *aLink); - NS_IMETHOD SetHoverLink(nsIContent *aLink); - + NS_IMETHOD GetContentState(nsIContent *aContent, PRInt32& aState); + NS_IMETHOD SetActiveContent(nsIContent *aActive); + NS_IMETHOD SetHoverContent(nsIContent *aHover); NS_IMETHOD SetFocusedContent(nsIContent *aContent); protected: @@ -69,12 +68,13 @@ protected: //Any frames here must be checked for validity in ClearFrameRefs nsIFrame* mCurrentTarget; nsIFrame* mLastMouseOverFrame; - nsIFrame* mLastLeftMouseDownFrame; - nsIFrame* mLastMiddleMouseDownFrame; - nsIFrame* mLastRightMouseDownFrame; - nsIContent* mActiveLink; - nsIContent* mHoverLink; + nsIContent* mLastLeftMouseDownContent; + nsIContent* mLastMiddleMouseDownContent; + nsIContent* mLastRightMouseDownContent; + + nsIContent* mActiveContent; + nsIContent* mHoverContent; nsIContent* mCurrentFocus; PRInt32 mCurrentTabIndex; diff --git a/content/html/content/src/nsHTMLAnchorElement.cpp b/content/html/content/src/nsHTMLAnchorElement.cpp index 2f17017a115f..a021d43ccd30 100644 --- a/content/html/content/src/nsHTMLAnchorElement.cpp +++ b/content/html/content/src/nsHTMLAnchorElement.cpp @@ -283,39 +283,30 @@ nsHTMLAnchorElement::HandleDOMEvent(nsIPresContext& aPresContext, if (NS_CONTENT_ATTR_HAS_VALUE == result) { switch (aEvent->message) { case NS_MOUSE_LEFT_BUTTON_DOWN: - { - nsIEventStateManager *stateManager; - if (NS_OK == aPresContext.GetEventStateManager(&stateManager)) { - stateManager->SetActiveLink(this); - NS_RELEASE(stateManager); + { + nsIEventStateManager *stateManager; + if (NS_OK == aPresContext.GetEventStateManager(&stateManager)) { + stateManager->SetActiveContent(this); + NS_RELEASE(stateManager); + } + aEventStatus = nsEventStatus_eConsumeNoDefault; } - aEventStatus = nsEventStatus_eConsumeNoDefault; - } - break; + break; case NS_MOUSE_LEFT_CLICK: { - nsIEventStateManager *stateManager; - nsLinkEventState linkState; - if (NS_OK == aPresContext.GetEventStateManager(&stateManager)) { - stateManager->GetLinkState(this, linkState); - NS_RELEASE(stateManager); - } - - if (eLinkState_Active == linkState) { - if (nsEventStatus_eConsumeNoDefault != aEventStatus) { - nsAutoString target; - nsIURL* baseURL = nsnull; - GetBaseURL(baseURL); - GetAttribute(kNameSpaceID_HTML, nsHTMLAtoms::target, target); - if (target.Length() == 0) { - GetBaseTarget(target); - } - mInner.TriggerLink(aPresContext, eLinkVerb_Replace, - baseURL, href, target, PR_TRUE); - NS_IF_RELEASE(baseURL); - aEventStatus = nsEventStatus_eConsumeNoDefault; + if (nsEventStatus_eConsumeNoDefault != aEventStatus) { + nsAutoString target; + nsIURL* baseURL = nsnull; + GetBaseURL(baseURL); + GetAttribute(kNameSpaceID_HTML, nsHTMLAtoms::target, target); + if (target.Length() == 0) { + GetBaseTarget(target); } + mInner.TriggerLink(aPresContext, eLinkVerb_Replace, + baseURL, href, target, PR_TRUE); + NS_IF_RELEASE(baseURL); + aEventStatus = nsEventStatus_eConsumeNoDefault; } } break; diff --git a/content/html/style/src/nsCSSStyleSheet.cpp b/content/html/style/src/nsCSSStyleSheet.cpp index 7cf425146d0a..6e30e4cbde95 100644 --- a/content/html/style/src/nsCSSStyleSheet.cpp +++ b/content/html/style/src/nsCSSStyleSheet.cpp @@ -1050,7 +1050,7 @@ static PRBool SelectorMatches(nsIPresContext* aPresContext, // first-child, lang, active, focus, hover, link, outOfDate, visited // XXX disabled, enabled, selected, selection nsAtomList* pseudoClass = aSelector->mPseudoClassList; - nsLinkEventState eventState = eLinkState_Unspecified; + PRInt32 eventState = NS_EVENT_STATE_UNSPECIFIED; nsLinkState linkState = nsLinkState(-1); // not a link nsILinkHandler* linkHandler = nsnull; nsIEventStateManager* eventStateManager = nsnull; @@ -1092,18 +1092,17 @@ static PRBool SelectorMatches(nsIPresContext* aPresContext, if (! eventStateManager) { aPresContext->GetEventStateManager(&eventStateManager); if (eventStateManager) { - eventStateManager->GetLinkState(aContent, eventState); + eventStateManager->GetContentState(aContent, eventState); } } if (nsCSSAtoms::activePseudo == pseudoClass->mAtom) { - result = PRBool(0 != (eventState & eLinkState_Active)); + result = PRBool(0 != (eventState & NS_EVENT_STATE_ACTIVE)); } else if (nsCSSAtoms::focusPseudo == pseudoClass->mAtom) { -// result = PRBool(0 != (eventState & eLinkState_Focus)); - result = PR_FALSE; + result = PRBool(0 != (eventState & NS_EVENT_STATE_FOCUS)); } else if (nsCSSAtoms::hoverPseudo == pseudoClass->mAtom) { - result = PRBool(0 != (eventState & eLinkState_Hover)); + result = PRBool(0 != (eventState & NS_EVENT_STATE_HOVER)); } } else if (IsLinkPseudo(pseudoClass->mAtom)) { diff --git a/content/html/style/src/nsHTMLStyleSheet.cpp b/content/html/style/src/nsHTMLStyleSheet.cpp index 76df8a0a16d5..4e0c42ec5a1c 100644 --- a/content/html/style/src/nsHTMLStyleSheet.cpp +++ b/content/html/style/src/nsHTMLStyleSheet.cpp @@ -468,9 +468,9 @@ PRInt32 HTMLStyleSheetImpl::RulesMatching(nsIPresContext* aPresContext, if ((NS_OK == aPresContext->GetEventStateManager(&eventStateManager)) && (nsnull != eventStateManager)) { - nsLinkEventState state; - if (NS_OK == eventStateManager->GetLinkState(aContent, state)) { - if (0 != (state & eLinkState_Active)) { + PRInt32 state; + if (NS_OK == eventStateManager->GetContentState(aContent, state)) { + if (0 != (state & NS_EVENT_STATE_ACTIVE)) { aResults->AppendElement(mActiveRule); matchCount++; } diff --git a/content/xml/content/src/nsXMLElement.cpp b/content/xml/content/src/nsXMLElement.cpp index dfcb6f4466f5..1dfd072503fd 100644 --- a/content/xml/content/src/nsXMLElement.cpp +++ b/content/xml/content/src/nsXMLElement.cpp @@ -136,45 +136,36 @@ nsXMLElement::HandleDOMEvent(nsIPresContext& aPresContext, { nsIEventStateManager *stateManager; if (NS_OK == aPresContext.GetEventStateManager(&stateManager)) { - stateManager->SetActiveLink(this); + stateManager->SetActiveContent(this); NS_RELEASE(stateManager); } aEventStatus = nsEventStatus_eConsumeNoDefault; } break; - case NS_MOUSE_LEFT_BUTTON_UP: + case NS_MOUSE_LEFT_CLICK: { - nsIEventStateManager *stateManager; - nsLinkEventState linkState; - if (NS_OK == aPresContext.GetEventStateManager(&stateManager)) { - stateManager->GetLinkState(this, linkState); - NS_RELEASE(stateManager); - } - - if (eLinkState_Active == linkState) { - if (nsEventStatus_eConsumeNoDefault != aEventStatus) { - nsAutoString show, href, target; - nsIURL* baseURL = nsnull; - nsLinkVerb verb = eLinkVerb_Replace; - target.Truncate(); - GetAttribute(kNameSpaceID_None, kHrefAtom, href); - GetAttribute(kNameSpaceID_None, kShowAtom, show); - // XXX Should probably do this using atoms - if (show.Equals("new")) { - verb = eLinkVerb_New; - } - else if (show.Equals("embed")) { - verb = eLinkVerb_Embed; - } - - if (nsnull != mInner.mDocument) { - baseURL = mInner.mDocument->GetDocumentURL(); - } - mInner.TriggerLink(aPresContext, verb, baseURL, href, target, PR_TRUE); - NS_IF_RELEASE(baseURL); - aEventStatus = nsEventStatus_eConsumeNoDefault; + if (nsEventStatus_eConsumeNoDefault != aEventStatus) { + nsAutoString show, href, target; + nsIURL* baseURL = nsnull; + nsLinkVerb verb = eLinkVerb_Replace; + target.Truncate(); + GetAttribute(kNameSpaceID_None, kHrefAtom, href); + GetAttribute(kNameSpaceID_None, kShowAtom, show); + // XXX Should probably do this using atoms + if (show.Equals("new")) { + verb = eLinkVerb_New; + } + else if (show.Equals("embed")) { + verb = eLinkVerb_Embed; + } + + if (nsnull != mInner.mDocument) { + baseURL = mInner.mDocument->GetDocumentURL(); } + mInner.TriggerLink(aPresContext, verb, baseURL, href, target, PR_TRUE); + NS_IF_RELEASE(baseURL); + aEventStatus = nsEventStatus_eConsumeNoDefault; } } break; @@ -184,7 +175,6 @@ nsXMLElement::HandleDOMEvent(nsIPresContext& aPresContext, break; case NS_MOUSE_ENTER: - //mouse enter doesn't work yet. Use move until then. { nsAutoString href, target; nsIURL* baseURL = nsnull; diff --git a/layout/base/nsPresShell.cpp b/layout/base/nsPresShell.cpp index 68a2635d777b..8c04de58abfa 100644 --- a/layout/base/nsPresShell.cpp +++ b/layout/base/nsPresShell.cpp @@ -1964,7 +1964,7 @@ PresShell::HandleEvent(nsIView *aView, nsIContent* targetContent; if (NS_OK == mCurrentEventFrame->GetContent(&targetContent) && nsnull != targetContent) { rv = targetContent->HandleDOMEvent(*mPresContext, (nsEvent*)aEvent, nsnull, - DOM_EVENT_INIT, aEventStatus); + NS_EVENT_FLAG_INIT, aEventStatus); NS_RELEASE(targetContent); } diff --git a/layout/base/src/nsDocument.cpp b/layout/base/src/nsDocument.cpp index c335def8e11c..b31e5861b769 100644 --- a/layout/base/src/nsDocument.cpp +++ b/layout/base/src/nsDocument.cpp @@ -677,6 +677,12 @@ nsresult nsDocument::QueryInterface(REFNSIID aIID, void** aInstancePtr) NS_ADDREF_THIS(); return NS_OK; } + if (aIID.Equals(kIDOMEventTargetIID)) { + nsIDOMEventTarget* tmp = this; + *aInstancePtr = (void*) tmp; + NS_ADDREF_THIS(); + return NS_OK; + } if (aIID.Equals(kIDOMNodeIID)) { nsIDOMNode* tmp = this; *aInstancePtr = (void*) tmp; @@ -1773,32 +1779,30 @@ nsresult nsDocument::HandleDOMEvent(nsIPresContext& aPresContext, nsresult mRet = NS_OK; nsIDOMEvent* mDOMEvent = nsnull; - if (DOM_EVENT_INIT == aFlags) { + if (NS_EVENT_FLAG_INIT == aFlags) { aDOMEvent = &mDOMEvent; } //Capturing stage - /*if (mEventCapturer) { - mEventCapturer->HandleDOMEvent(aPresContext, aEvent, aDOMEvent, aFlags, aEventStatus); - }*/ + if (NS_EVENT_FLAG_BUBBLE != aFlags) { + //XXX Check window capture here + } //Local handling stage if (nsnull != mListenerManager) { - mListenerManager->HandleEvent(aPresContext, aEvent, aDOMEvent, aEventStatus); + mListenerManager->HandleEvent(aPresContext, aEvent, aDOMEvent, aFlags, aEventStatus); } //Bubbling stage - if (DOM_EVENT_CAPTURE != aFlags && nsnull != mScriptContextOwner) { + if (NS_EVENT_FLAG_CAPTURE != aFlags && nsnull != mScriptContextOwner) { nsIScriptGlobalObject* mGlobal; if (NS_OK == mScriptContextOwner->GetScriptGlobalObject(&mGlobal)) { - mGlobal->HandleDOMEvent(aPresContext, aEvent, aDOMEvent, DOM_EVENT_BUBBLE, aEventStatus); + mGlobal->HandleDOMEvent(aPresContext, aEvent, aDOMEvent, NS_EVENT_FLAG_BUBBLE, aEventStatus); NS_RELEASE(mGlobal); } } - /*Need to go to window here*/ - - if (DOM_EVENT_INIT == aFlags) { + if (NS_EVENT_FLAG_INIT == aFlags) { // We're leaving the DOM event loop so if we created a DOM event, release here. if (nsnull != *aDOMEvent) { nsrefcnt rc; @@ -1819,22 +1823,51 @@ nsresult nsDocument::HandleDOMEvent(nsIPresContext& aPresContext, return mRet; } -nsresult nsDocument::AddEventListener(nsIDOMEventListener *aListener, const nsIID& aIID) +nsresult nsDocument::AddEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID) { - nsIEventListenerManager *mManager; + nsIEventListenerManager *manager; - if (NS_OK == GetListenerManager(&mManager)) { - mManager->AddEventListener(aListener, aIID); - NS_RELEASE(mManager); + if (NS_OK == GetListenerManager(&manager)) { + manager->AddEventListenerByIID(aListener, aIID, NS_EVENT_FLAG_BUBBLE); + NS_RELEASE(manager); return NS_OK; } return NS_ERROR_FAILURE; } -nsresult nsDocument::RemoveEventListener(nsIDOMEventListener *aListener, const nsIID& aIID) +nsresult nsDocument::RemoveEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID) { if (nsnull != mListenerManager) { - mListenerManager->RemoveEventListener(aListener, aIID); + mListenerManager->RemoveEventListenerByIID(aListener, aIID, NS_EVENT_FLAG_BUBBLE); + return NS_OK; + } + return NS_ERROR_FAILURE; +} + +nsresult nsDocument::AddEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture) +{ + nsIEventListenerManager *manager; + + if (NS_OK == GetListenerManager(&manager)) { + PRInt32 flags = (aPostProcess ? NS_EVENT_FLAG_POST_PROCESS : NS_EVENT_FLAG_NONE) | + (aUseCapture ? NS_EVENT_FLAG_CAPTURE : NS_EVENT_FLAG_BUBBLE); + + manager->AddEventListenerByType(aListener, aType, flags); + NS_RELEASE(manager); + return NS_OK; + } + return NS_ERROR_FAILURE; +} + +nsresult nsDocument::RemoveEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture) +{ + if (nsnull != mListenerManager) { + PRInt32 flags = (aPostProcess ? NS_EVENT_FLAG_POST_PROCESS : NS_EVENT_FLAG_NONE) | + (aUseCapture ? NS_EVENT_FLAG_CAPTURE : NS_EVENT_FLAG_BUBBLE); + + mListenerManager->RemoveEventListenerByType(aListener, aType, flags); return NS_OK; } return NS_ERROR_FAILURE; diff --git a/layout/base/src/nsDocument.h b/layout/base/src/nsDocument.h index 186c4c37db3a..9224c4461085 100644 --- a/layout/base/src/nsDocument.h +++ b/layout/base/src/nsDocument.h @@ -25,6 +25,7 @@ #include "nsIScriptObjectOwner.h" #include "nsIScriptContextOwner.h" #include "nsIDOMEventCapturer.h" +#include "nsIDOMEventTarget.h" #include "nsXIFConverter.h" #include "nsIJSScriptObject.h" #include "nsIContent.h" @@ -311,11 +312,18 @@ public: NS_IMETHOD ReleaseEvent(const nsString& aType); // nsIDOMEventReceiver interface - NS_IMETHOD AddEventListener(nsIDOMEventListener *aListener, const nsIID& aIID); - NS_IMETHOD RemoveEventListener(nsIDOMEventListener *aListener, const nsIID& aIID); + NS_IMETHOD AddEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID); + NS_IMETHOD RemoveEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID); NS_IMETHOD GetListenerManager(nsIEventListenerManager** aInstancePtrResult); NS_IMETHOD GetNewListenerManager(nsIEventListenerManager **aInstancePtrResult); + // nsIDOMEventTarget interface + NS_IMETHOD AddEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture); + NS_IMETHOD RemoveEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture); + + NS_IMETHOD HandleDOMEvent(nsIPresContext& aPresContext, nsEvent* aEvent, nsIDOMEvent** aDOMEvent, diff --git a/layout/base/src/nsGenericDOMDataNode.cpp b/layout/base/src/nsGenericDOMDataNode.cpp index 64c3de9c3f43..78500e079854 100644 --- a/layout/base/src/nsGenericDOMDataNode.cpp +++ b/layout/base/src/nsGenericDOMDataNode.cpp @@ -61,6 +61,7 @@ nsGenericDOMDataNode::nsGenericDOMDataNode() mScriptObject = nsnull; mListenerManager = nsnull; mRangeList = nsnull; + mCapturer = nsnull; } nsGenericDOMDataNode::~nsGenericDOMDataNode() @@ -428,13 +429,13 @@ nsGenericDOMDataNode::GetNewListenerManager(nsIEventListenerManager** aResult) } nsresult -nsGenericDOMDataNode::AddEventListener(nsIDOMEventListener* aListener, +nsGenericDOMDataNode::AddEventListenerByIID(nsIDOMEventListener* aListener, const nsIID& aIID) { nsIEventListenerManager *manager; if (NS_OK == GetListenerManager(&manager)) { - manager->AddEventListener(aListener, aIID); + manager->AddEventListenerByIID(aListener, aIID, NS_EVENT_FLAG_BUBBLE); NS_RELEASE(manager); return NS_OK; } @@ -442,11 +443,42 @@ nsGenericDOMDataNode::AddEventListener(nsIDOMEventListener* aListener, } nsresult -nsGenericDOMDataNode::RemoveEventListener(nsIDOMEventListener* aListener, +nsGenericDOMDataNode::RemoveEventListenerByIID(nsIDOMEventListener* aListener, const nsIID& aIID) { if (nsnull != mListenerManager) { - mListenerManager->RemoveEventListener(aListener, aIID); + mListenerManager->RemoveEventListenerByIID(aListener, aIID, NS_EVENT_FLAG_BUBBLE); + return NS_OK; + } + return NS_ERROR_FAILURE; +} + +nsresult +nsGenericDOMDataNode::AddEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture) +{ + nsIEventListenerManager *manager; + + if (NS_OK == GetListenerManager(&manager)) { + PRInt32 flags = (aPostProcess ? NS_EVENT_FLAG_POST_PROCESS : NS_EVENT_FLAG_NONE) | + (aUseCapture ? NS_EVENT_FLAG_CAPTURE : NS_EVENT_FLAG_BUBBLE); + + manager->AddEventListenerByType(aListener, aType, flags); + NS_RELEASE(manager); + return NS_OK; + } + return NS_ERROR_FAILURE; +} + +nsresult +nsGenericDOMDataNode::RemoveEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture) +{ + if (nsnull != mListenerManager) { + PRInt32 flags = (aPostProcess ? NS_EVENT_FLAG_POST_PROCESS : NS_EVENT_FLAG_NONE) | + (aUseCapture ? NS_EVENT_FLAG_CAPTURE : NS_EVENT_FLAG_BUBBLE); + + mListenerManager->RemoveEventListenerByType(aListener, aType, flags); return NS_OK; } return NS_ERROR_FAILURE; @@ -652,26 +684,35 @@ nsGenericDOMDataNode::HandleDOMEvent(nsIPresContext& aPresContext, nsEventStatus& aEventStatus) { nsresult ret = NS_OK; - nsIDOMEvent* domEvent = nsnull; - if (DOM_EVENT_INIT == aFlags) { + + if (NS_EVENT_FLAG_INIT == aFlags) { aDOMEvent = &domEvent; + + //Initiate capturing phase. Special case first call to document + if (nsnull != mDocument) { + mDocument->HandleDOMEvent(aPresContext, aEvent, aDOMEvent, NS_EVENT_FLAG_CAPTURE, aEventStatus); + } } - //Capturing stage + //Capturing stage evaluation + //Always pass capturing up the tree before local evaulation + if (NS_EVENT_FLAG_BUBBLE != aFlags && nsnull != mCapturer) { + mCapturer->HandleDOMEvent(aPresContext, aEvent, aDOMEvent, NS_EVENT_FLAG_CAPTURE, aEventStatus); + } //Local handling stage if (nsnull != mListenerManager) { - mListenerManager->HandleEvent(aPresContext, aEvent, aDOMEvent, aEventStatus); + mListenerManager->HandleEvent(aPresContext, aEvent, aDOMEvent, aFlags, aEventStatus); } //Bubbling stage - if (DOM_EVENT_CAPTURE != aFlags && mParent != nsnull) { + if (NS_EVENT_FLAG_CAPTURE != aFlags && mParent != nsnull) { ret = mParent->HandleDOMEvent(aPresContext, aEvent, aDOMEvent, - DOM_EVENT_BUBBLE, aEventStatus); + NS_EVENT_FLAG_BUBBLE, aEventStatus); } - if (DOM_EVENT_INIT == aFlags) { + if (NS_EVENT_FLAG_INIT == aFlags) { // We're leaving the DOM event loop so if we created a DOM event, // release here. if (nsnull != *aDOMEvent) { diff --git a/layout/base/src/nsGenericDOMDataNode.h b/layout/base/src/nsGenericDOMDataNode.h index 19cadb259184..635822c723a7 100644 --- a/layout/base/src/nsGenericDOMDataNode.h +++ b/layout/base/src/nsGenericDOMDataNode.h @@ -30,6 +30,7 @@ extern const nsIID kIDOMCharacterDataIID; extern const nsIID kIDOMNodeIID; extern const nsIID kIDOMEventReceiverIID; +extern const nsIID kIDOMEventTargetIID; extern const nsIID kIScriptObjectOwnerIID; extern const nsIID kISupportsIID; extern const nsIID kIContentIID; @@ -102,12 +103,18 @@ struct nsGenericDOMDataNode { nsresult ReplaceData(PRUint32 aOffset, PRUint32 aCount, const nsString& aArg); // nsIDOMEventReceiver interface - nsresult AddEventListener(nsIDOMEventListener *aListener, const nsIID& aIID); - nsresult RemoveEventListener(nsIDOMEventListener* aListener, + nsresult AddEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID); + nsresult RemoveEventListenerByIID(nsIDOMEventListener* aListener, const nsIID& aIID); nsresult GetListenerManager(nsIEventListenerManager** aInstancePtrResult); nsresult GetNewListenerManager(nsIEventListenerManager** aInstancePtrResult); + // nsIDOMEventTarget interface + nsresult AddEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture); + nsresult RemoveEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture); + // nsIScriptObjectOwner interface nsresult GetScriptObject(nsIScriptContext* aContext, void** aScriptObject); nsresult SetScriptObject(void *aScriptObject); @@ -213,6 +220,7 @@ struct nsGenericDOMDataNode { nsIContent* mParent; void* mScriptObject; nsIEventListenerManager* mListenerManager; + nsIContent* mCapturer; nsTextFragment mText; nsVoidArray *mRangeList; @@ -314,21 +322,33 @@ struct nsGenericDOMDataNode { * generic content object (either nsGenericHTMLLeafElement or * nsGenericHTMLContainerContent) */ -#define NS_IMPL_IDOMEVENTRECEIVER_USING_GENERIC_DOM_DATA(_g) \ - NS_IMETHOD AddEventListener(nsIDOMEventListener *aListener, \ - const nsIID& aIID) { \ - return _g.AddEventListener(aListener, aIID); \ - } \ - NS_IMETHOD RemoveEventListener(nsIDOMEventListener *aListener, \ - const nsIID& aIID) { \ - return _g.RemoveEventListener(aListener, aIID); \ - } \ - NS_IMETHOD GetListenerManager(nsIEventListenerManager** aResult) { \ - return _g.GetListenerManager(aResult); \ - } \ - NS_IMETHOD GetNewListenerManager(nsIEventListenerManager** aResult) { \ - return _g.GetNewListenerManager(aResult); \ - } +#define NS_IMPL_IDOMEVENTRECEIVER_USING_GENERIC_DOM_DATA(_g) \ + NS_IMETHOD AddEventListenerByIID(nsIDOMEventListener *aListener, \ + const nsIID& aIID) { \ + return _g.AddEventListenerByIID(aListener, aIID); \ + } \ + NS_IMETHOD RemoveEventListenerByIID(nsIDOMEventListener *aListener, \ + const nsIID& aIID) { \ + return _g.RemoveEventListenerByIID(aListener, aIID); \ + } \ + NS_IMETHOD GetListenerManager(nsIEventListenerManager** aResult) { \ + return _g.GetListenerManager(aResult); \ + } \ + NS_IMETHOD GetNewListenerManager(nsIEventListenerManager** aResult) { \ + return _g.GetNewListenerManager(aResult); \ + } \ + NS_IMETHOD AddEventListener(const nsString& aType, \ + nsIDOMEventListener* aListener, \ + PRBool aPostProcess, \ + PRBool aUseCapture) { \ + return _g.AddEventListener(aType, aListener, aPostProcess, aUseCapture); \ + } \ + NS_IMETHOD RemoveEventListener(const nsString& aType, \ + nsIDOMEventListener* aListener, \ + PRBool aPostProcess, \ + PRBool aUseCapture) { \ + return _g.RemoveEventListener(aType, aListener, aPostProcess, aUseCapture); \ + } /** * Implement the nsIScriptObjectOwner API by forwarding the methods to a @@ -474,6 +494,12 @@ struct nsGenericDOMDataNode { NS_ADDREF_THIS(); \ return NS_OK; \ } \ + if (_id.Equals(kIDOMEventTargetIID)) { \ + nsIDOMEventTarget* tmp = _this; \ + *_iptr = (void*) tmp; \ + NS_ADDREF_THIS(); \ + return NS_OK; \ + } \ if (_id.Equals(kIScriptObjectOwnerIID)) { \ nsIScriptObjectOwner* tmp = _this; \ *_iptr = (void*) tmp; \ diff --git a/layout/base/src/nsGenericElement.cpp b/layout/base/src/nsGenericElement.cpp index 5580161c9616..03977c7b3c00 100644 --- a/layout/base/src/nsGenericElement.cpp +++ b/layout/base/src/nsGenericElement.cpp @@ -63,6 +63,7 @@ NS_DEFINE_IID(kIDOMNodeIID, NS_IDOMNODE_IID); NS_DEFINE_IID(kIDOMElementIID, NS_IDOMELEMENT_IID); NS_DEFINE_IID(kIDOMTextIID, NS_IDOMTEXT_IID); NS_DEFINE_IID(kIDOMEventReceiverIID, NS_IDOMEVENTRECEIVER_IID); +NS_DEFINE_IID(kIDOMEventTargetIID, NS_IDOMEVENTTARGET_IID); NS_DEFINE_IID(kIScriptObjectOwnerIID, NS_ISCRIPTOBJECTOWNER_IID); NS_DEFINE_IID(kIJSScriptObjectIID, NS_IJSSCRIPTOBJECT_IID); NS_DEFINE_IID(kISupportsIID, NS_ISUPPORTS_IID); @@ -206,6 +207,7 @@ nsGenericElement::GetDOMSlots() mDOMSlots->mStyle = nsnull; mDOMSlots->mAttributeMap = nsnull; mDOMSlots->mRangeList = nsnull; + mDOMSlots->mCapturer = nsnull; } return mDOMSlots; @@ -737,24 +739,36 @@ nsGenericElement::HandleDOMEvent(nsIPresContext& aPresContext, nsresult ret = NS_OK; nsIDOMEvent* domEvent = nsnull; - if (DOM_EVENT_INIT == aFlags) { + if (NS_EVENT_FLAG_INIT == aFlags) { aDOMEvent = &domEvent; + + //Initiate capturing phase + //Initiate capturing phase. Special case first call to document + if (nsnull != mDocument) { + mDocument->HandleDOMEvent(aPresContext, aEvent, aDOMEvent, NS_EVENT_FLAG_CAPTURE, aEventStatus); + } } - //Capturing stage + //Capturing stage evaluation + //Always pass capturing up the tree before local evaulation + if (NS_EVENT_FLAG_BUBBLE != aFlags) { + if (nsnull != mDOMSlots && nsnull != mDOMSlots->mCapturer) { + mDOMSlots->mCapturer->HandleDOMEvent(aPresContext, aEvent, aDOMEvent, NS_EVENT_FLAG_CAPTURE, aEventStatus); + } + } //Local handling stage if (nsnull != mListenerManager) { - mListenerManager->HandleEvent(aPresContext, aEvent, aDOMEvent, aEventStatus); + mListenerManager->HandleEvent(aPresContext, aEvent, aDOMEvent, aFlags, aEventStatus); } //Bubbling stage - if ((DOM_EVENT_CAPTURE != aFlags) && (mParent != nsnull) && (mDocument != nsnull)) { + if ((NS_EVENT_FLAG_CAPTURE != aFlags) && (mParent != nsnull) && (mDocument != nsnull)) { ret = mParent->HandleDOMEvent(aPresContext, aEvent, aDOMEvent, - DOM_EVENT_BUBBLE, aEventStatus); + NS_EVENT_FLAG_BUBBLE, aEventStatus); } - if (DOM_EVENT_INIT == aFlags) { + if (NS_EVENT_FLAG_INIT == aFlags) { // We're leaving the DOM event loop so if we created a DOM event, // release here. if (nsnull != *aDOMEvent) { @@ -948,13 +962,13 @@ nsGenericElement::GetNewListenerManager(nsIEventListenerManager** aResult) } nsresult -nsGenericElement::AddEventListener(nsIDOMEventListener* aListener, +nsGenericElement::AddEventListenerByIID(nsIDOMEventListener* aListener, const nsIID& aIID) { nsIEventListenerManager *manager; if (NS_OK == GetListenerManager(&manager)) { - manager->AddEventListener(aListener, aIID); + manager->AddEventListenerByIID(aListener, aIID, NS_EVENT_FLAG_BUBBLE); NS_RELEASE(manager); return NS_OK; } @@ -962,11 +976,42 @@ nsGenericElement::AddEventListener(nsIDOMEventListener* aListener, } nsresult -nsGenericElement::RemoveEventListener(nsIDOMEventListener* aListener, +nsGenericElement::RemoveEventListenerByIID(nsIDOMEventListener* aListener, const nsIID& aIID) { if (nsnull != mListenerManager) { - mListenerManager->RemoveEventListener(aListener, aIID); + mListenerManager->RemoveEventListenerByIID(aListener, aIID, NS_EVENT_FLAG_BUBBLE); + return NS_OK; + } + return NS_ERROR_FAILURE; +} + +nsresult +nsGenericElement::AddEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture) +{ + nsIEventListenerManager *manager; + + if (NS_OK == GetListenerManager(&manager)) { + PRInt32 flags = (aPostProcess ? NS_EVENT_FLAG_POST_PROCESS : NS_EVENT_FLAG_NONE) | + (aUseCapture ? NS_EVENT_FLAG_CAPTURE : NS_EVENT_FLAG_BUBBLE); + + manager->AddEventListenerByType(aListener, aType, flags); + NS_RELEASE(manager); + return NS_OK; + } + return NS_ERROR_FAILURE; +} + +nsresult +nsGenericElement::RemoveEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture) +{ + if (nsnull != mListenerManager) { + PRInt32 flags = (aPostProcess ? NS_EVENT_FLAG_POST_PROCESS : NS_EVENT_FLAG_NONE) | + (aUseCapture ? NS_EVENT_FLAG_CAPTURE : NS_EVENT_FLAG_BUBBLE); + + mListenerManager->RemoveEventListenerByType(aListener, aType, flags); return NS_OK; } return NS_ERROR_FAILURE; diff --git a/layout/base/src/nsGenericElement.h b/layout/base/src/nsGenericElement.h index 659f0bab8f90..421013cb4291 100644 --- a/layout/base/src/nsGenericElement.h +++ b/layout/base/src/nsGenericElement.h @@ -33,6 +33,7 @@ extern const nsIID kIDOMNodeIID; extern const nsIID kIDOMElementIID; extern const nsIID kIDOMEventReceiverIID; +extern const nsIID kIDOMEventTargetIID; extern const nsIID kIScriptObjectOwnerIID; extern const nsIID kIJSScriptObjectIID; extern const nsIID kISupportsIID; @@ -79,6 +80,7 @@ typedef struct { nsDOMCSSDeclaration *mStyle; nsDOMAttributeMap* mAttributeMap; nsVoidArray *mRangeList; + nsIContent* mCapturer; } nsDOMSlots; class nsGenericElement : public nsIJSScriptObject { @@ -116,12 +118,18 @@ public: nsresult Normalize(); // nsIDOMEventReceiver interface - nsresult AddEventListener(nsIDOMEventListener *aListener, const nsIID& aIID); - nsresult RemoveEventListener(nsIDOMEventListener* aListener, + nsresult AddEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID); + nsresult RemoveEventListenerByIID(nsIDOMEventListener* aListener, const nsIID& aIID); nsresult GetListenerManager(nsIEventListenerManager** aInstancePtrResult); nsresult GetNewListenerManager(nsIEventListenerManager** aInstancePtrResult); + // nsIDOMEventTarget interface + nsresult AddEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture); + nsresult RemoveEventListener(const nsString& aType, nsIDOMEventListener* aListener, + PRBool aPostProcess, PRBool aUseCapture); + // nsIScriptObjectOwner interface nsresult GetScriptObject(nsIScriptContext* aContext, void** aScriptObject); nsresult SetScriptObject(void *aScriptObject); @@ -373,21 +381,33 @@ public: * generic content object (either nsGenericHTMLLeafElement or * nsGenericHTMLContainerContent) */ -#define NS_IMPL_IDOMEVENTRECEIVER_USING_GENERIC(_g) \ - NS_IMETHOD AddEventListener(nsIDOMEventListener *aListener, \ - const nsIID& aIID) { \ - return _g.AddEventListener(aListener, aIID); \ - } \ - NS_IMETHOD RemoveEventListener(nsIDOMEventListener *aListener, \ - const nsIID& aIID) { \ - return _g.RemoveEventListener(aListener, aIID); \ - } \ - NS_IMETHOD GetListenerManager(nsIEventListenerManager** aResult) { \ - return _g.GetListenerManager(aResult); \ - } \ - NS_IMETHOD GetNewListenerManager(nsIEventListenerManager** aResult) { \ - return _g.GetNewListenerManager(aResult); \ - } +#define NS_IMPL_IDOMEVENTRECEIVER_USING_GENERIC(_g) \ + NS_IMETHOD AddEventListenerByIID(nsIDOMEventListener *aListener, \ + const nsIID& aIID) { \ + return _g.AddEventListenerByIID(aListener, aIID); \ + } \ + NS_IMETHOD RemoveEventListenerByIID(nsIDOMEventListener *aListener, \ + const nsIID& aIID) { \ + return _g.RemoveEventListenerByIID(aListener, aIID); \ + } \ + NS_IMETHOD GetListenerManager(nsIEventListenerManager** aResult) { \ + return _g.GetListenerManager(aResult); \ + } \ + NS_IMETHOD GetNewListenerManager(nsIEventListenerManager** aResult) { \ + return _g.GetNewListenerManager(aResult); \ + } \ + NS_IMETHOD AddEventListener(const nsString& aType, \ + nsIDOMEventListener* aListener, \ + PRBool aPostProcess, \ + PRBool aUseCapture) { \ + return _g.AddEventListener(aType, aListener, aPostProcess, aUseCapture); \ + } \ + NS_IMETHOD RemoveEventListener(const nsString& aType, \ + nsIDOMEventListener* aListener, \ + PRBool aPostProcess, \ + PRBool aUseCapture) { \ + return _g.RemoveEventListener(aType, aListener, aPostProcess, aUseCapture); \ + } #define NS_IMPL_ICONTENT_USING_GENERIC(_g) \ NS_IMETHOD GetDocument(nsIDocument*& aResult) const { \ @@ -532,6 +552,12 @@ public: NS_ADDREF_THIS(); \ return NS_OK; \ } \ + if (_id.Equals(kIDOMEventTargetIID)) { \ + nsIDOMEventTarget* tmp = _this; \ + *_iptr = (void*) tmp; \ + NS_ADDREF_THIS(); \ + return NS_OK; \ + } \ if (_id.Equals(kIScriptObjectOwnerIID)) { \ nsIScriptObjectOwner* tmp = _this; \ *_iptr = (void*) tmp; \ diff --git a/layout/events/public/nsIEventListenerManager.h b/layout/events/public/nsIEventListenerManager.h index d47ad17c1473..c367c15cf193 100644 --- a/layout/events/public/nsIEventListenerManager.h +++ b/layout/events/public/nsIEventListenerManager.h @@ -51,8 +51,29 @@ public: * @param an event listener */ - virtual nsresult AddEventListener(nsIDOMEventListener *aListener, const nsIID& aIID) = 0; + virtual nsresult AddEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID, PRInt32 flags) = 0; + /** + * Removes events listeners of all types. + * @param an event listener + */ + + virtual nsresult RemoveEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID, PRInt32 flags) = 0; + + /** + * Sets events listeners of all types. + * @param an event listener + */ + + virtual nsresult AddEventListenerByType(nsIDOMEventListener *aListener, const nsString& type, PRInt32 flags) = 0; + + /** + * Removes events listeners of all types. + * @param an event listener + */ + + virtual nsresult RemoveEventListenerByType(nsIDOMEventListener *aListener, const nsString& type, PRInt32 flags) = 0; + /** * Creates a script event listener for the given script object with name mName and function * content mFunc. @@ -70,21 +91,16 @@ public: virtual nsresult RegisterScriptEventListener(nsIScriptContext *aContext, nsIScriptObjectOwner *aScriptObjectOwner, REFNSIID aIID) = 0; - /** - * Removes events listeners of all types. - * @param an event listener - */ - - virtual nsresult RemoveEventListener(nsIDOMEventListener *aListener, const nsIID& aIID) = 0; - /** * Causes a check for event listeners and processing by them if they exist. + * Event flags live in nsGUIEvent.h * @param an event listener */ virtual nsresult HandleEvent(nsIPresContext& aPresContext, nsEvent* aEvent, nsIDOMEvent** aDOMEvent, + PRUint32 aFlags, nsEventStatus& aEventStatus) = 0; /** diff --git a/layout/events/public/nsIEventStateManager.h b/layout/events/public/nsIEventStateManager.h index 9d529c4db754..d3d0ada64587 100644 --- a/layout/events/public/nsIEventStateManager.h +++ b/layout/events/public/nsIEventStateManager.h @@ -28,12 +28,6 @@ class nsIPresContext; class nsIDOMEvent; class nsIFrame; -enum nsLinkEventState { - eLinkState_Unspecified = 0, - eLinkState_Active = 1, // mouse is down on link - eLinkState_Hover = 2 // mouse is hovering over link -}; - /* * Event listener manager interface. */ @@ -61,11 +55,16 @@ public: NS_IMETHOD GetEventTarget(nsIFrame **aFrame) = 0; - NS_IMETHOD GetLinkState(nsIContent *aLink, nsLinkEventState& aState) = 0; - NS_IMETHOD SetActiveLink(nsIContent *aLink) = 0; - NS_IMETHOD SetHoverLink(nsIContent *aLink) = 0; + NS_IMETHOD GetContentState(nsIContent *aContent, PRInt32& aState) = 0; + NS_IMETHOD SetActiveContent(nsIContent *aActive) = 0; + NS_IMETHOD SetHoverContent(nsIContent *aHover) = 0; NS_IMETHOD SetFocusedContent(nsIContent *aContent) = 0; }; +#define NS_EVENT_STATE_UNSPECIFIED 0000 +#define NS_EVENT_STATE_ACTIVE 0001 // mouse is down on content +#define NS_EVENT_STATE_FOCUS 0002 // content has focus +#define NS_EVENT_STATE_HOVER 0003 // mouse is hovering over content + #endif // nsIEventStateManager_h__ diff --git a/layout/events/src/nsDOMEvent.cpp b/layout/events/src/nsDOMEvent.cpp index bc834f29a149..18b9bb4cae3c 100644 --- a/layout/events/src/nsDOMEvent.cpp +++ b/layout/events/src/nsDOMEvent.cpp @@ -261,6 +261,7 @@ NS_METHOD nsDOMEvent::GetCharCode(PRUint32* aCharCode) { switch (mEvent->message) { case NS_KEY_UP: + case NS_KEY_PRESS: case NS_KEY_DOWN: *aCharCode = ((nsKeyEvent*)mEvent)->charCode; #ifdef NS_DEBUG @@ -283,6 +284,7 @@ NS_METHOD nsDOMEvent::GetKeyCode(PRUint32* aKeyCode) { switch (mEvent->message) { case NS_KEY_UP: + case NS_KEY_PRESS: case NS_KEY_DOWN: *aKeyCode = ((nsKeyEvent*)mEvent)->keyCode; break; @@ -441,9 +443,9 @@ const char* nsDOMEvent::GetEventName(PRUint32 aEventType) return mEventNames[eDOMEvents_keydown]; case NS_KEY_PRESS: return mEventNames[eDOMEvents_keypress]; - case NS_GOTFOCUS: + case NS_FOCUS_CONTENT: return mEventNames[eDOMEvents_focus]; - case NS_LOSTFOCUS: + case NS_BLUR_CONTENT: return mEventNames[eDOMEvents_blur]; case NS_PAGE_LOAD: case NS_IMAGE_LOAD: diff --git a/layout/events/src/nsDOMEvent.h b/layout/events/src/nsDOMEvent.h index 18315ca84eaa..0ebcda3c8d81 100644 --- a/layout/events/src/nsDOMEvent.h +++ b/layout/events/src/nsDOMEvent.h @@ -33,10 +33,6 @@ class nsIDOMRenderingContext; class nsDOMEvent : public nsIDOMEvent, public nsIDOMNSEvent, public nsIPrivateDOMEvent { -#define DOM_EVENT_INIT 0x0001 -#define DOM_EVENT_BUBBLE 0x0002 -#define DOM_EVENT_CAPTURE 0x0004 - public: // Note: this enum must be kept in sync with mEventNames in nsDOMEvent.cpp enum nsDOMEvents { diff --git a/layout/events/src/nsEventListenerManager.cpp b/layout/events/src/nsEventListenerManager.cpp index bb8a647855ec..c3d958fbef3d 100644 --- a/layout/events/src/nsEventListenerManager.cpp +++ b/layout/events/src/nsEventListenerManager.cpp @@ -36,6 +36,7 @@ #include "nsIScriptObjectOwner.h" #include "nsIScriptEventListener.h" #include "nsDOMEventsIIDs.h" +#include "prmem.h" static NS_DEFINE_IID(kIEventListenerManagerIID, NS_IEVENTLISTENERMANAGER_IID); static NS_DEFINE_IID(kIDOMEventListenerIID, NS_IDOMEVENTLISTENER_IID); @@ -125,11 +126,12 @@ void nsEventListenerManager::ReleaseListeners(nsVoidArray* aListeners) { if (nsnull != aListeners) { PRInt32 i, count = aListeners->Count(); - nsIDOMEventListener *mElement; + nsListenerStruct *ls; for (i = 0; i < count; i++) { - mElement = (nsIDOMEventListener *)aListeners->ElementAt(i); - if (mElement != nsnull) { - NS_RELEASE(mElement); + ls = (nsListenerStruct*)aListeners->ElementAt(i); + if (ls != nsnull) { + NS_IF_RELEASE(ls->mListener); + PR_DELETE(ls); } } delete aListeners; @@ -149,24 +151,221 @@ nsresult nsEventListenerManager::GetEventListeners(nsVoidArray **aListeners, con * Sets events listeners of all types. * @param an event listener */ -nsresult nsEventListenerManager::AddEventListener(nsIDOMEventListener *aListener, const nsIID& aIID) +nsresult nsEventListenerManager::AddEventListener(nsIDOMEventListener *aListener, + const nsIID& aIID, + PRInt32 aFlags, + PRInt32 aSubType) { - nsVoidArray** mListeners = GetListenersByIID(aIID); + nsVoidArray** listeners = GetListenersByIID(aIID); - if (nsnull == *mListeners) { - *mListeners = new nsVoidArray(); + if (nsnull == *listeners) { + *listeners = new nsVoidArray(); } - if (nsnull == *mListeners) { + if (nsnull == *listeners) { return NS_ERROR_OUT_OF_MEMORY; } - (*mListeners)->InsertElementAt((void*)aListener, (*mListeners)->Count()); + PRBool found = PR_FALSE; + nsListenerStruct* ls; + nsIScriptEventListener* sel = nsnull; + nsIScriptEventListener* regSel; + + aListener->QueryInterface(kIScriptEventListenerIID, (void**)&sel); + + for (int i=0; i<(*listeners)->Count(); i++) { + ls = (nsListenerStruct*)(*listeners)->ElementAt(i); + if (ls->mListener == aListener) { + ls->mFlags |= aFlags; + ls->mSubType |= aSubType; + found = PR_TRUE; + break; + } + else if (sel) { + if (NS_OK == ls->mListener->QueryInterface(kIScriptEventListenerIID, (void**)®Sel)) { + if (NS_OK == regSel->CheckIfEqual(sel)) { + if (ls->mFlags & aFlags && ls->mSubType & aSubType) { + found = PR_TRUE; + break; + } + } + } + } + } + + if (!found) { + ls = PR_NEW(nsListenerStruct); + if (ls) { + ls->mListener = aListener; + ls->mFlags = aFlags; + ls->mSubType = aSubType; + (*listeners)->InsertElementAt((void*)ls, (*listeners)->Count()); + } + } NS_ADDREF(aListener); return NS_OK; } + +nsresult nsEventListenerManager::RemoveEventListener(nsIDOMEventListener *aListener, + const nsIID& aIID, + PRInt32 aFlags, + PRInt32 aSubType) +{ + nsVoidArray** listeners = GetListenersByIID(aIID); + + if (nsnull == *listeners) { + return NS_OK; + } + + nsListenerStruct* ls; + + for (int i=0; i<(*listeners)->Count(); i++) { + ls = (nsListenerStruct*)(*listeners)->ElementAt(i); + if (ls->mListener == aListener) { + ls->mFlags &= ~aFlags; + ls->mSubType &= ~aSubType; + if (ls->mFlags == NS_EVENT_FLAG_NONE && ls->mSubType == NS_EVENT_BITS_NONE) { + NS_RELEASE(ls->mListener); + (*listeners)->RemoveElement((void*)ls); + PR_DELETE(ls); + } + break; + } + } + + return NS_OK; +} + +nsresult nsEventListenerManager::AddEventListenerByIID(nsIDOMEventListener *aListener, + const nsIID& aIID, PRInt32 aFlags) +{ + AddEventListener(aListener, aIID, aFlags, NS_EVENT_BITS_NONE); + return NS_OK; +} + +nsresult nsEventListenerManager::RemoveEventListenerByIID(nsIDOMEventListener *aListener, + const nsIID& aIID, PRInt32 aFlags) +{ + RemoveEventListener(aListener, aIID, aFlags, NS_EVENT_BITS_NONE); + return NS_OK; +} + +nsresult nsEventListenerManager::GetIdentifiersForType(const nsString& aType, nsIID& aIID, PRInt32* aFlags) +{ + if (aType == "mousedown") { + aIID = kIDOMMouseListenerIID; + *aFlags = NS_EVENT_BITS_MOUSE_MOUSEDOWN; + } + else if (aType == "mouseup") { + aIID = kIDOMMouseListenerIID; + *aFlags = NS_EVENT_BITS_MOUSE_MOUSEUP; + } + else if (aType == "click") { + aIID = kIDOMMouseListenerIID; + *aFlags = NS_EVENT_BITS_MOUSE_CLICK; + } + else if (aType == "dblclick") { + aIID = kIDOMMouseListenerIID; + *aFlags = NS_EVENT_BITS_MOUSE_DBLCLICK; + } + else if (aType == "mouseover") { + aIID = kIDOMMouseListenerIID; + *aFlags = NS_EVENT_BITS_MOUSE_MOUSEOVER; + } + else if (aType == "mouseout") { + aIID = kIDOMMouseListenerIID; + *aFlags = NS_EVENT_BITS_MOUSE_MOUSEOUT; + } + else if (aType == "keydown") { + aIID = kIDOMKeyListenerIID; + *aFlags = NS_EVENT_BITS_KEY_KEYDOWN; + } + else if (aType == "keyup") { + aIID = kIDOMKeyListenerIID; + *aFlags = NS_EVENT_BITS_KEY_KEYUP; + } + else if (aType == "keypress") { + aIID = kIDOMKeyListenerIID; + *aFlags = NS_EVENT_BITS_KEY_KEYPRESS; + } + else if (aType == "mousemove") { + aIID = kIDOMMouseMotionListenerIID; + *aFlags = NS_EVENT_BITS_MOUSEMOTION_MOUSEMOVE; + } + else if (aType == "focus") { + aIID = kIDOMFocusListenerIID; + *aFlags = NS_EVENT_BITS_FOCUS_FOCUS; + } + else if (aType == "blur") { + aIID = kIDOMFocusListenerIID; + *aFlags = NS_EVENT_BITS_FOCUS_BLUR; + } + else if (aType == "submit") { + aIID = kIDOMFormListenerIID; + *aFlags = NS_EVENT_BITS_FORM_SUBMIT; + } + else if (aType == "reset") { + aIID = kIDOMFormListenerIID; + *aFlags = NS_EVENT_BITS_FORM_RESET; + } + else if (aType == "change") { + aIID = kIDOMFormListenerIID; + *aFlags = NS_EVENT_BITS_FORM_CHANGE; + } + else if (aType == "load") { + aIID = kIDOMLoadListenerIID; + *aFlags = NS_EVENT_BITS_LOAD_LOAD; + } + else if (aType == "unload") { + aIID = kIDOMLoadListenerIID; + *aFlags = NS_EVENT_BITS_LOAD_UNLOAD; + } + else if (aType == "abort") { + aIID = kIDOMLoadListenerIID; + *aFlags = NS_EVENT_BITS_LOAD_ABORT; + } + else if (aType == "error") { + aIID = kIDOMLoadListenerIID; + *aFlags = NS_EVENT_BITS_LOAD_ERROR; + } + else if (aType == "paint") { + aIID = kIDOMPaintListenerIID; + *aFlags = NS_EVENT_BITS_PAINT_PAINT; + } + else { + return NS_ERROR_FAILURE; + } + return NS_OK; +} + +nsresult nsEventListenerManager::AddEventListenerByType(nsIDOMEventListener *aListener, + const nsString& aType, PRInt32 aFlags) +{ + PRInt32 subType; + nsIID iid; + + if (NS_OK == GetIdentifiersForType(aType, iid, &subType)) { + AddEventListener(aListener, iid, aFlags, subType); + } + + return NS_OK; +} + +nsresult nsEventListenerManager::RemoveEventListenerByType(nsIDOMEventListener *aListener, + const nsString& aType, PRInt32 aFlags) +{ + PRInt32 subType; + nsIID iid; + + if (NS_OK == GetIdentifiersForType(aType, iid, &subType)) { + RemoveEventListener(aListener, iid, aFlags, subType); + } + + return NS_OK; +} + const char *mEventArgv[] = {"event"}; nsresult nsEventListenerManager::SetJSEventListener(nsIScriptContext *aContext, JSObject *aObject, REFNSIID aIID) @@ -177,20 +376,18 @@ nsresult nsEventListenerManager::SetJSEventListener(nsIScriptContext *aContext, //Run through the listeners for this IID and see if a script listener is registered //If so, we're set. if (nsnull != mListeners) { - nsIScriptEventListener *mScriptListener; - nsIDOMEventListener *mEventListener; + nsListenerStruct *ls; for (int i=0; iCount(); i++) { - mEventListener = (nsIDOMEventListener*)mListeners->ElementAt(i); - if (NS_OK == mEventListener->QueryInterface(kIScriptEventListenerIID, (void**)&mScriptListener)) { - NS_RELEASE(mScriptListener); + ls = (nsListenerStruct*)mListeners->ElementAt(i); + if (ls->mFlags & NS_PRIV_EVENT_FLAG_SCRIPT) { return NS_OK; } } } //If we didn't find a script listener or no listeners existed create and add a new one. nsIDOMEventListener *mScriptListener; - if (NS_OK == NS_NewScriptEventListener(&mScriptListener, aContext, aObject)) { - AddEventListener(mScriptListener, aIID); + if (NS_OK == NS_NewJSEventListener(&mScriptListener, aContext, aObject)) { + AddEventListenerByIID(mScriptListener, aIID, NS_EVENT_FLAG_BUBBLE | NS_PRIV_EVENT_FLAG_SCRIPT); NS_RELEASE(mScriptListener); return NS_OK; } @@ -233,22 +430,6 @@ nsresult nsEventListenerManager::RegisterScriptEventListener(nsIScriptContext *a return NS_ERROR_FAILURE; } -/** -* Removes event listeners of all types. -* @param an event listener -*/ - -nsresult nsEventListenerManager::RemoveEventListener(nsIDOMEventListener *aListener, const nsIID& aIID) -{ - nsVoidArray** mListeners = GetListenersByIID(aIID); - - if (nsnull != *mListeners && PR_TRUE == (*mListeners)->RemoveElement((void*)aListener)) { - NS_RELEASE(aListener); - return NS_OK; - } - return NS_ERROR_FAILURE; -} - /** * Causes a check for event listeners and processing by them if they exist. * @param an event listener @@ -257,9 +438,13 @@ nsresult nsEventListenerManager::RemoveEventListener(nsIDOMEventListener *aListe nsresult nsEventListenerManager::HandleEvent(nsIPresContext& aPresContext, nsEvent* aEvent, nsIDOMEvent** aDOMEvent, + PRUint32 aFlags, nsEventStatus& aEventStatus) { nsresult ret = NS_OK; + if (aFlags & NS_EVENT_FLAG_INIT) { + aFlags |= NS_EVENT_FLAG_BUBBLE; + } switch(aEvent->message) { case NS_MOUSE_LEFT_BUTTON_DOWN: @@ -282,46 +467,94 @@ nsresult nsEventListenerManager::HandleEvent(nsIPresContext& aPresContext, } if (NS_OK == ret) { for (int i=0; iCount(); i++) { - nsIDOMEventListener *mEventListener; + nsListenerStruct *ls; nsIDOMMouseListener *mMouseListener; + nsIScriptEventListener *scriptListener; - mEventListener = (nsIDOMEventListener*)mMouseListeners->ElementAt(i); + ls = (nsListenerStruct*)mMouseListeners->ElementAt(i); - if (NS_OK == mEventListener->QueryInterface(kIDOMMouseListenerIID, (void**)&mMouseListener)) { - switch(aEvent->message) { - case NS_MOUSE_LEFT_BUTTON_DOWN: - case NS_MOUSE_MIDDLE_BUTTON_DOWN: - case NS_MOUSE_RIGHT_BUTTON_DOWN: - ret = mMouseListener->MouseDown(*aDOMEvent); - break; - case NS_MOUSE_LEFT_BUTTON_UP: - case NS_MOUSE_MIDDLE_BUTTON_UP: - case NS_MOUSE_RIGHT_BUTTON_UP: - ret = mMouseListener->MouseUp(*aDOMEvent); - break; - case NS_MOUSE_LEFT_CLICK: - case NS_MOUSE_MIDDLE_CLICK: - case NS_MOUSE_RIGHT_CLICK: - ret = mMouseListener->MouseClick(*aDOMEvent); - break; - case NS_MOUSE_LEFT_DOUBLECLICK: - case NS_MOUSE_MIDDLE_DOUBLECLICK: - case NS_MOUSE_RIGHT_DOUBLECLICK: - ret = mMouseListener->MouseDblClick(*aDOMEvent); - break; - case NS_MOUSE_ENTER: - ret = mMouseListener->MouseOver(*aDOMEvent); - break; - case NS_MOUSE_EXIT: - ret = mMouseListener->MouseOut(*aDOMEvent); - break; - default: - break; + if (ls->mFlags & aFlags) { + if (NS_OK == ls->mListener->QueryInterface(kIDOMMouseListenerIID, (void**)&mMouseListener)) { + switch(aEvent->message) { + case NS_MOUSE_LEFT_BUTTON_DOWN: + case NS_MOUSE_MIDDLE_BUTTON_DOWN: + case NS_MOUSE_RIGHT_BUTTON_DOWN: + ret = mMouseListener->MouseDown(*aDOMEvent); + break; + case NS_MOUSE_LEFT_BUTTON_UP: + case NS_MOUSE_MIDDLE_BUTTON_UP: + case NS_MOUSE_RIGHT_BUTTON_UP: + ret = mMouseListener->MouseUp(*aDOMEvent); + break; + case NS_MOUSE_LEFT_CLICK: + case NS_MOUSE_MIDDLE_CLICK: + case NS_MOUSE_RIGHT_CLICK: + ret = mMouseListener->MouseClick(*aDOMEvent); + break; + case NS_MOUSE_LEFT_DOUBLECLICK: + case NS_MOUSE_MIDDLE_DOUBLECLICK: + case NS_MOUSE_RIGHT_DOUBLECLICK: + ret = mMouseListener->MouseDblClick(*aDOMEvent); + break; + case NS_MOUSE_ENTER: + ret = mMouseListener->MouseOver(*aDOMEvent); + break; + case NS_MOUSE_EXIT: + ret = mMouseListener->MouseOut(*aDOMEvent); + break; + default: + break; + } + NS_RELEASE(mMouseListener); + } + else { + PRBool correctSubType = PR_FALSE; + switch(aEvent->message) { + case NS_MOUSE_LEFT_BUTTON_DOWN: + case NS_MOUSE_MIDDLE_BUTTON_DOWN: + case NS_MOUSE_RIGHT_BUTTON_DOWN: + if (ls->mSubType & NS_EVENT_BITS_MOUSE_MOUSEDOWN) { + correctSubType = PR_TRUE; + } + break; + case NS_MOUSE_LEFT_BUTTON_UP: + case NS_MOUSE_MIDDLE_BUTTON_UP: + case NS_MOUSE_RIGHT_BUTTON_UP: + if (ls->mSubType & NS_EVENT_BITS_MOUSE_MOUSEUP) { + correctSubType = PR_TRUE; + } + break; + case NS_MOUSE_LEFT_CLICK: + case NS_MOUSE_MIDDLE_CLICK: + case NS_MOUSE_RIGHT_CLICK: + if (ls->mSubType & NS_EVENT_BITS_MOUSE_CLICK) { + correctSubType = PR_TRUE; + } + break; + case NS_MOUSE_LEFT_DOUBLECLICK: + case NS_MOUSE_MIDDLE_DOUBLECLICK: + case NS_MOUSE_RIGHT_DOUBLECLICK: + if (ls->mSubType & NS_EVENT_BITS_MOUSE_DBLCLICK) { + correctSubType = PR_TRUE; + } + break; + case NS_MOUSE_ENTER: + if (ls->mSubType & NS_EVENT_BITS_MOUSE_MOUSEOVER) { + correctSubType = PR_TRUE; + } + break; + case NS_MOUSE_EXIT: + if (ls->mSubType & NS_EVENT_BITS_MOUSE_MOUSEOUT) { + correctSubType = PR_TRUE; + } + break; + default: + break; + } + if (correctSubType || ls->mSubType == NS_EVENT_BITS_NONE) { + ret = ls->mListener->HandleEvent(*aDOMEvent); + } } - NS_RELEASE(mMouseListener); - } - else { - ret = mEventListener->ProcessEvent(*aDOMEvent); } aEventStatus = (NS_OK == ret) ? aEventStatus : nsEventStatus_eConsumeNoDefault; } @@ -336,23 +569,37 @@ nsresult nsEventListenerManager::HandleEvent(nsIPresContext& aPresContext, } if (NS_OK == ret) { for (int i=0; iCount(); i++) { - nsIDOMEventListener *mEventListener; + nsListenerStruct *ls; nsIDOMMouseMotionListener *mMouseMotionListener; - mEventListener = (nsIDOMEventListener*)mMouseMotionListeners->ElementAt(i); + ls = (nsListenerStruct*)mMouseMotionListeners->ElementAt(i); - if (NS_OK == mEventListener->QueryInterface(kIDOMMouseMotionListenerIID, (void**)&mMouseMotionListener)) { - switch(aEvent->message) { - case NS_MOUSE_MOVE: - ret = mMouseMotionListener->MouseMove(*aDOMEvent); - break; - default: - break; + if (ls->mFlags & aFlags) { + if (NS_OK == ls->mListener->QueryInterface(kIDOMMouseMotionListenerIID, (void**)&mMouseMotionListener)) { + switch(aEvent->message) { + case NS_MOUSE_MOVE: + ret = mMouseMotionListener->MouseMove(*aDOMEvent); + break; + default: + break; + } + NS_RELEASE(mMouseMotionListener); + } + else { + PRBool correctSubType = PR_FALSE; + switch(aEvent->message) { + case NS_MOUSE_MOVE: + if (ls->mSubType & NS_EVENT_BITS_MOUSEMOTION_MOUSEMOVE) { + correctSubType = PR_TRUE; + } + break; + default: + break; + } + if (correctSubType || ls->mSubType == NS_EVENT_BITS_NONE) { + ret = ls->mListener->HandleEvent(*aDOMEvent); + } } - NS_RELEASE(mMouseMotionListener); - } - else { - ret = mEventListener->ProcessEvent(*aDOMEvent); } aEventStatus = (NS_OK == ret) ? aEventStatus : nsEventStatus_eConsumeNoDefault; } @@ -362,28 +609,36 @@ nsresult nsEventListenerManager::HandleEvent(nsIPresContext& aPresContext, case NS_TEXT_EVENT: #if DEBUG_TAGUE - printf("DOM: got text event\n"); + printf("DOM: got text event\n"); #endif - if (nsnull != mTextListeners) { - if (nsnull == *aDOMEvent) { - ret = NS_NewDOMEvent(aDOMEvent,aPresContext,aEvent); - } - if (NS_OK == ret) { - for (int i=0; iCount(); i++) { - nsIDOMEventListener *mEventListener; - nsIDOMTextListener *mTextListener; + if (nsnull != mTextListeners) { + if (nsnull == *aDOMEvent) { + ret = NS_NewDOMEvent(aDOMEvent,aPresContext,aEvent); + } + if (NS_OK == ret) { + for (int i=0; iCount(); i++) { + nsListenerStruct *ls; + nsIDOMTextListener *mTextListener; - mEventListener = (nsIDOMEventListener*)mTextListeners->ElementAt(i); - - if (NS_OK == mEventListener->QueryInterface(kIDOMTextListenerIID, (void**)&mTextListener)) { - ret = mTextListener->HandleText(*aDOMEvent); - NS_RELEASE(mTextListener); - } - else { - ret = mEventListener->ProcessEvent(*aDOMEvent); - } + ls = (nsListenerStruct*)mTextListeners->ElementAt(i); + + if (ls->mFlags & aFlags) { + if (NS_OK == ls->mListener->QueryInterface(kIDOMTextListenerIID, (void**)&mTextListener)) { + ret = mTextListener->HandleText(*aDOMEvent); + NS_RELEASE(mTextListener); + } + else { + PRBool correctSubType = PR_FALSE; + if (ls->mSubType & NS_EVENT_BITS_TEXT_TEXT) { + correctSubType = PR_TRUE; + } + if (correctSubType || ls->mSubType == NS_EVENT_BITS_NONE) { + ret = ls->mListener->HandleEvent(*aDOMEvent); + } + } + } + aEventStatus = (NS_OK == ret) ? aEventStatus : nsEventStatus_eConsumeNoDefault; } - aEventStatus = (NS_OK == ret) ? aEventStatus : nsEventStatus_eConsumeNoDefault; } } break; @@ -397,29 +652,53 @@ nsresult nsEventListenerManager::HandleEvent(nsIPresContext& aPresContext, } if (NS_OK == ret) { for (int i=0; iCount(); i++) { - nsIDOMEventListener *mEventListener; + nsListenerStruct *ls; nsIDOMKeyListener *mKeyListener; - mEventListener = (nsIDOMEventListener*)mKeyListeners->ElementAt(i); + ls = (nsListenerStruct*)mKeyListeners->ElementAt(i); - if (NS_OK == mEventListener->QueryInterface(kIDOMKeyListenerIID, (void**)&mKeyListener)) { - switch(aEvent->message) { - case NS_KEY_UP: - ret = mKeyListener->KeyUp(*aDOMEvent); - break; - case NS_KEY_DOWN: - ret = mKeyListener->KeyDown(*aDOMEvent); - break; - case NS_KEY_PRESS: - ret = mKeyListener->KeyPress(*aDOMEvent); - break; - default: - break; + if (ls->mFlags & aFlags) { + if (NS_OK == ls->mListener->QueryInterface(kIDOMKeyListenerIID, (void**)&mKeyListener)) { + switch(aEvent->message) { + case NS_KEY_UP: + ret = mKeyListener->KeyUp(*aDOMEvent); + break; + case NS_KEY_DOWN: + ret = mKeyListener->KeyDown(*aDOMEvent); + break; + case NS_KEY_PRESS: + ret = mKeyListener->KeyPress(*aDOMEvent); + break; + default: + break; + } + NS_RELEASE(mKeyListener); + } + else { + PRBool correctSubType = PR_FALSE; + switch(aEvent->message) { + case NS_KEY_UP: + if (ls->mSubType & NS_EVENT_BITS_KEY_KEYUP) { + correctSubType = PR_TRUE; + } + break; + case NS_KEY_DOWN: + if (ls->mSubType & NS_EVENT_BITS_KEY_KEYDOWN) { + correctSubType = PR_TRUE; + } + break; + case NS_KEY_PRESS: + if (ls->mSubType & NS_EVENT_BITS_KEY_KEYPRESS) { + correctSubType = PR_TRUE; + } + break; + default: + break; + } + if (correctSubType || ls->mSubType == NS_EVENT_BITS_NONE) { + ret = ls->mListener->HandleEvent(*aDOMEvent); + } } - NS_RELEASE(mKeyListener); - } - else { - ret = mEventListener->ProcessEvent(*aDOMEvent); } aEventStatus = (NS_OK == ret) ? aEventStatus : nsEventStatus_eConsumeNoDefault; } @@ -427,34 +706,53 @@ nsresult nsEventListenerManager::HandleEvent(nsIPresContext& aPresContext, } break; - case NS_GOTFOCUS: - case NS_LOSTFOCUS: + case NS_FOCUS_CONTENT: + case NS_BLUR_CONTENT: if (nsnull != mFocusListeners) { if (nsnull == *aDOMEvent) { ret = NS_NewDOMEvent(aDOMEvent, aPresContext, aEvent); } if (NS_OK == ret) { for (int i=0; iCount(); i++) { - nsIDOMEventListener *mEventListener; + nsListenerStruct *ls; nsIDOMFocusListener *mFocusListener; - mEventListener = (nsIDOMEventListener*)mFocusListeners->ElementAt(i); + ls = (nsListenerStruct*)mFocusListeners->ElementAt(i); - if (NS_OK == mEventListener->QueryInterface(kIDOMFocusListenerIID, (void**)&mFocusListener)) { - switch(aEvent->message) { - case NS_GOTFOCUS: - ret = mFocusListener->Focus(*aDOMEvent); - break; - case NS_LOSTFOCUS: - ret = mFocusListener->Blur(*aDOMEvent); - break; - default: - break; + if (ls->mFlags & aFlags) { + if (NS_OK == ls->mListener->QueryInterface(kIDOMFocusListenerIID, (void**)&mFocusListener)) { + switch(aEvent->message) { + case NS_FOCUS_CONTENT: + ret = mFocusListener->Focus(*aDOMEvent); + break; + case NS_BLUR_CONTENT: + ret = mFocusListener->Blur(*aDOMEvent); + break; + default: + break; + } + NS_RELEASE(mFocusListener); + } + else { + PRBool correctSubType = PR_FALSE; + switch(aEvent->message) { + case NS_FOCUS_CONTENT: + if (ls->mSubType & NS_EVENT_BITS_FOCUS_FOCUS) { + correctSubType = PR_TRUE; + } + break; + case NS_BLUR_CONTENT: + if (ls->mSubType & NS_EVENT_BITS_FOCUS_BLUR) { + correctSubType = PR_TRUE; + } + break; + default: + break; + } + if (correctSubType || ls->mSubType == NS_EVENT_BITS_NONE) { + ret = ls->mListener->HandleEvent(*aDOMEvent); + } } - NS_RELEASE(mFocusListener); - } - else { - ret = mEventListener->ProcessEvent(*aDOMEvent); } aEventStatus = (NS_OK == ret) ? aEventStatus : nsEventStatus_eConsumeNoDefault; } @@ -471,29 +769,53 @@ nsresult nsEventListenerManager::HandleEvent(nsIPresContext& aPresContext, } if (NS_OK == ret) { for (int i=0; iCount(); i++) { - nsIDOMEventListener *mEventListener; + nsListenerStruct *ls; nsIDOMFormListener *mFormListener; - mEventListener = (nsIDOMEventListener*)mFormListeners->ElementAt(i); + ls = (nsListenerStruct*)mFormListeners->ElementAt(i); - if (NS_OK == mEventListener->QueryInterface(kIDOMFormListenerIID, (void**)&mFormListener)) { - switch(aEvent->message) { - case NS_FORM_SUBMIT: - ret = mFormListener->Submit(*aDOMEvent); - break; - case NS_FORM_RESET: - ret = mFormListener->Reset(*aDOMEvent); - break; - case NS_FORM_CHANGE: - ret = mFormListener->Change(*aDOMEvent); - break; - default: - break; + if (ls->mFlags & aFlags) { + if (NS_OK == ls->mListener->QueryInterface(kIDOMFormListenerIID, (void**)&mFormListener)) { + switch(aEvent->message) { + case NS_FORM_SUBMIT: + ret = mFormListener->Submit(*aDOMEvent); + break; + case NS_FORM_RESET: + ret = mFormListener->Reset(*aDOMEvent); + break; + case NS_FORM_CHANGE: + ret = mFormListener->Change(*aDOMEvent); + break; + default: + break; + } + NS_RELEASE(mFormListener); + } + else { + PRBool correctSubType = PR_FALSE; + switch(aEvent->message) { + case NS_FORM_SUBMIT: + if (ls->mSubType & NS_EVENT_BITS_FORM_SUBMIT) { + correctSubType = PR_TRUE; + } + break; + case NS_FORM_RESET: + if (ls->mSubType & NS_EVENT_BITS_FORM_RESET) { + correctSubType = PR_TRUE; + } + break; + case NS_FORM_CHANGE: + if (ls->mSubType & NS_EVENT_BITS_FORM_CHANGE) { + correctSubType = PR_TRUE; + } + break; + default: + break; + } + if (correctSubType || ls->mSubType == NS_EVENT_BITS_NONE) { + ret = ls->mListener->HandleEvent(*aDOMEvent); + } } - NS_RELEASE(mFormListener); - } - else { - ret = mEventListener->ProcessEvent(*aDOMEvent); } aEventStatus = (NS_OK == ret) ? aEventStatus : nsEventStatus_eConsumeNoDefault; } @@ -509,26 +831,45 @@ nsresult nsEventListenerManager::HandleEvent(nsIPresContext& aPresContext, } if (NS_OK == ret) { for (int i=0; iCount(); i++) { - nsIDOMEventListener *mEventListener; + nsListenerStruct *ls; nsIDOMLoadListener *mLoadListener; - mEventListener = (nsIDOMEventListener*)mLoadListeners->ElementAt(i); + ls = (nsListenerStruct*)mLoadListeners->ElementAt(i); - if (NS_OK == mEventListener->QueryInterface(kIDOMLoadListenerIID, (void**)&mLoadListener)) { - switch(aEvent->message) { - case NS_PAGE_LOAD: - ret = mLoadListener->Load(*aDOMEvent); - break; - case NS_PAGE_UNLOAD: - ret = mLoadListener->Unload(*aDOMEvent); - break; - default: - break; + if (ls->mFlags & aFlags) { + if (NS_OK == ls->mListener->QueryInterface(kIDOMLoadListenerIID, (void**)&mLoadListener)) { + switch(aEvent->message) { + case NS_PAGE_LOAD: + ret = mLoadListener->Load(*aDOMEvent); + break; + case NS_PAGE_UNLOAD: + ret = mLoadListener->Unload(*aDOMEvent); + break; + default: + break; + } + NS_RELEASE(mLoadListener); + } + else { + PRBool correctSubType = PR_FALSE; + switch(aEvent->message) { + case NS_PAGE_LOAD: + if (ls->mSubType & NS_EVENT_BITS_LOAD_LOAD) { + correctSubType = PR_TRUE; + } + break; + case NS_PAGE_UNLOAD: + if (ls->mSubType & NS_EVENT_BITS_LOAD_UNLOAD) { + correctSubType = PR_TRUE; + } + break; + default: + break; + } + if (correctSubType || ls->mSubType == NS_EVENT_BITS_NONE) { + ret = ls->mListener->HandleEvent(*aDOMEvent); + } } - NS_RELEASE(mLoadListener); - } - else { - ret = mEventListener->ProcessEvent(*aDOMEvent); } aEventStatus = (NS_OK == ret) ? aEventStatus : nsEventStatus_eConsumeNoDefault; } @@ -543,18 +884,26 @@ nsresult nsEventListenerManager::HandleEvent(nsIPresContext& aPresContext, } if (NS_OK == ret) { for (int i=0; iCount(); i++) { - nsIDOMEventListener *eventListener; + nsListenerStruct *ls; nsIDOMPaintListener *paintListener; - eventListener = (nsIDOMEventListener*)mPaintListeners->ElementAt(i); + ls = (nsListenerStruct*)mPaintListeners->ElementAt(i); - if (NS_OK == eventListener->QueryInterface(kIDOMPaintListenerIID, - (void**)&paintListener)) { - ret = paintListener->Paint(*aDOMEvent); - NS_RELEASE(paintListener); - } - else { - ret = eventListener->ProcessEvent(*aDOMEvent); + if (ls->mFlags & aFlags) { + if (NS_OK == ls->mListener->QueryInterface(kIDOMPaintListenerIID, + (void**)&paintListener)) { + ret = paintListener->Paint(*aDOMEvent); + NS_RELEASE(paintListener); + } + else { + PRBool correctSubType = PR_FALSE; + if (ls->mSubType & NS_EVENT_BITS_PAINT_PAINT) { + correctSubType = PR_TRUE; + } + if (correctSubType || ls->mSubType == NS_EVENT_BITS_NONE) { + ret = ls->mListener->HandleEvent(*aDOMEvent); + } + } } aEventStatus = (NS_OK == ret) ? aEventStatus diff --git a/layout/events/src/nsEventListenerManager.h b/layout/events/src/nsEventListenerManager.h index 1c1b3fe4dfbf..c7d7be7422bb 100644 --- a/layout/events/src/nsEventListenerManager.h +++ b/layout/events/src/nsEventListenerManager.h @@ -23,7 +23,16 @@ #include "jsapi.h" class nsIDOMEvent; - + +typedef struct { + nsIDOMEventListener* mListener; + PRUint8 mFlags; + PRUint8 mSubType; +} nsListenerStruct; + +//Flag must live higher than all event flags in nsGUIEvent.h +#define NS_PRIV_EVENT_FLAG_SCRIPT 0x10 + /* * Event listener manager */ @@ -52,7 +61,11 @@ public: * @param an event listener */ - virtual nsresult AddEventListener(nsIDOMEventListener *aListener, REFNSIID aIID); + virtual nsresult AddEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID, PRInt32 aFlags); + virtual nsresult RemoveEventListenerByIID(nsIDOMEventListener *aListener, const nsIID& aIID, PRInt32 aFlags); + virtual nsresult AddEventListenerByType(nsIDOMEventListener *aListener, const nsString& type, PRInt32 aFlags); + virtual nsresult RemoveEventListenerByType(nsIDOMEventListener *aListener, const nsString& type, PRInt32 aFlags) ; + virtual nsresult AddScriptEventListener(nsIScriptContext* aContext, nsIScriptObjectOwner *aScriptObjectOwner, nsIAtom *aName, @@ -62,14 +75,14 @@ public: nsIScriptObjectOwner *aScriptObjectOwner, const nsIID& aIID); - virtual nsresult RemoveEventListener(nsIDOMEventListener *aListener, REFNSIID aIID); virtual nsresult CaptureEvent(nsIDOMEventListener *aListener); virtual nsresult ReleaseEvent(nsIDOMEventListener *aListener); virtual nsresult HandleEvent(nsIPresContext& aPresContext, nsEvent* aEvent, - nsIDOMEvent** aDOMEvent, + nsIDOMEvent** aDOMEvent, + PRUint32 aFlags, nsEventStatus& aEventStatus); virtual nsresult CreateEvent(nsIPresContext& aPresContext, @@ -78,6 +91,9 @@ public: protected: nsresult SetJSEventListener(nsIScriptContext *aContext, JSObject *aObject, REFNSIID aIID); + nsresult GetIdentifiersForType(const nsString& aType, nsIID& aIID, PRInt32* aSubType); + nsresult AddEventListener(nsIDOMEventListener *aListener, const nsIID& aIID, PRInt32 aFlags, PRInt32 aSubType); + nsresult RemoveEventListener(nsIDOMEventListener *aListener, const nsIID& aIID, PRInt32 aFlags, PRInt32 aSubType); nsVoidArray* mEventListeners; nsVoidArray* mMouseListeners; @@ -92,4 +108,61 @@ protected: }; + +//Set of defines for distinguishing event hanlders within listener groupings +//XXX Current usage allows no more than 7 types per listener grouping + +#define NS_EVENT_BITS_NONE 0x00 + +//nsIDOMMouseListener +#define NS_EVENT_BITS_MOUSE_NONE 0x00 +#define NS_EVENT_BITS_MOUSE_MOUSEDOWN 0x01 +#define NS_EVENT_BITS_MOUSE_MOUSEUP 0x02 +#define NS_EVENT_BITS_MOUSE_CLICK 0x04 +#define NS_EVENT_BITS_MOUSE_DBLCLICK 0x08 +#define NS_EVENT_BITS_MOUSE_MOUSEOVER 0x10 +#define NS_EVENT_BITS_MOUSE_MOUSEOUT 0x20 + +//nsIDOMMouseMotionListener +#define NS_EVENT_BITS_MOUSEMOTION_NONE 0x00 +#define NS_EVENT_BITS_MOUSEMOTION_MOUSEMOVE 0x01 +#define NS_EVENT_BITS_MOUSEMOTION_DRAGMOVE 0x02 + +//nsIDOMKeyListener +#define NS_EVENT_BITS_KEY_NONE 0x00 +#define NS_EVENT_BITS_KEY_KEYDOWN 0x01 +#define NS_EVENT_BITS_KEY_KEYUP 0x02 +#define NS_EVENT_BITS_KEY_KEYPRESS 0x04 + +//nsIDOMTextListener +#define NS_EVENT_BITS_TEXT_NONE 0x00 +#define NS_EVENT_BITS_TEXT_TEXT 0x01 + +//nsIDOMFocusListener +#define NS_EVENT_BITS_FOCUS_NONE 0x00 +#define NS_EVENT_BITS_FOCUS_FOCUS 0x01 +#define NS_EVENT_BITS_FOCUS_BLUR 0x02 + +//nsIDOMFormListener +#define NS_EVENT_BITS_FORM_NONE 0x00 +#define NS_EVENT_BITS_FORM_SUBMIT 0x01 +#define NS_EVENT_BITS_FORM_RESET 0x02 +#define NS_EVENT_BITS_FORM_CHANGE 0x04 + +//nsIDOMLoadListener +#define NS_EVENT_BITS_LOAD_NONE 0x00 +#define NS_EVENT_BITS_LOAD_LOAD 0x01 +#define NS_EVENT_BITS_LOAD_UNLOAD 0x02 +#define NS_EVENT_BITS_LOAD_ABORT 0x04 +#define NS_EVENT_BITS_LOAD_ERROR 0x08 + +//nsIDOMDragListener +#define NS_EVENT_BITS_DRAG_NONE 0x00 +#define NS_EVENT_BITS_DRAG_START 0x01 +#define NS_EVENT_BITS_DRAG_DROP 0x02 + +//nsIDOMPaintListener +#define NS_EVENT_BITS_PAINT_NONE 0x00 +#define NS_EVENT_BITS_PAINT_PAINT 0x01 + #endif // nsEventListenerManager_h__ diff --git a/layout/events/src/nsEventStateManager.cpp b/layout/events/src/nsEventStateManager.cpp index 2e6717d83f9d..3a60886cc363 100644 --- a/layout/events/src/nsEventStateManager.cpp +++ b/layout/events/src/nsEventStateManager.cpp @@ -53,12 +53,12 @@ static NS_DEFINE_IID(kIFocusableContentIID, NS_IFOCUSABLECONTENT_IID); nsEventStateManager::nsEventStateManager() { mLastMouseOverFrame = nsnull; mCurrentTarget = nsnull; - mLastLeftMouseDownFrame = nsnull; - mLastMiddleMouseDownFrame = nsnull; - mLastRightMouseDownFrame = nsnull; + mLastLeftMouseDownContent = nsnull; + mLastMiddleMouseDownContent = nsnull; + mLastRightMouseDownContent = nsnull; - mActiveLink = nsnull; - mHoverLink = nsnull; + mActiveContent = nsnull; + mHoverContent = nsnull; mCurrentFocus = nsnull; mDocument = nsnull; mPresContext = nsnull; @@ -67,10 +67,13 @@ nsEventStateManager::nsEventStateManager() { } nsEventStateManager::~nsEventStateManager() { - NS_IF_RELEASE(mActiveLink); - NS_IF_RELEASE(mHoverLink); + NS_IF_RELEASE(mActiveContent); + NS_IF_RELEASE(mHoverContent); NS_IF_RELEASE(mCurrentFocus); NS_IF_RELEASE(mDocument); + NS_IF_RELEASE(mLastLeftMouseDownContent); + NS_IF_RELEASE(mLastMiddleMouseDownContent); + NS_IF_RELEASE(mLastRightMouseDownContent); } NS_IMPL_ADDREF(nsEventStateManager) @@ -98,7 +101,7 @@ nsEventStateManager::PreHandleEvent(nsIPresContext& aPresContext, GenerateMouseEnterExit(aPresContext, aEvent); break; case NS_MOUSE_EXIT: - //GenerateMouseEnterExit(aPresContext, aEvent, aTargetFrame); + GenerateMouseEnterExit(aPresContext, aEvent); break; case NS_GOTFOCUS: //XXX Do we need window related focus change stuff here? @@ -126,6 +129,8 @@ nsEventStateManager::PostHandleEvent(nsIPresContext& aPresContext, case NS_MOUSE_MIDDLE_BUTTON_DOWN: case NS_MOUSE_RIGHT_BUTTON_DOWN: { + ret = CheckForAndDispatchClick(aPresContext, (nsMouseEvent*)aEvent, aStatus); + nsIContent* newFocus; mCurrentTarget->GetContent(&newFocus); if (newFocus) { @@ -137,12 +142,12 @@ nsEventStateManager::PostHandleEvent(nsIPresContext& aPresContext, NS_RELEASE(newFocus); } } - //Break left out on purpose + break; case NS_MOUSE_LEFT_BUTTON_UP: case NS_MOUSE_MIDDLE_BUTTON_UP: case NS_MOUSE_RIGHT_BUTTON_UP: - mCurrentTarget = aTargetFrame; ret = CheckForAndDispatchClick(aPresContext, (nsMouseEvent*)aEvent, aStatus); + SetActiveContent(nsnull); break; case NS_KEY_DOWN: ret = DispatchKeyPressEvent(aPresContext, (nsKeyEvent*)aEvent, aStatus); @@ -182,15 +187,6 @@ nsEventStateManager::ClearFrameRefs(nsIFrame* aFrame) if (aFrame == mCurrentTarget) { mCurrentTarget = nsnull; } - if (aFrame == mLastLeftMouseDownFrame) { - mLastLeftMouseDownFrame = nsnull; - } - if (aFrame == mLastMiddleMouseDownFrame) { - mLastMiddleMouseDownFrame = nsnull; - } - if (aFrame == mLastRightMouseDownFrame) { - mLastRightMouseDownFrame = nsnull; - } return NS_OK; } @@ -274,7 +270,7 @@ nsEventStateManager::GenerateMouseEnterExit(nsIPresContext& aPresContext, nsGUIE if (lastContent != targetContent) { //XXX This event should still go somewhere!! if (nsnull != lastContent) { - lastContent->HandleDOMEvent(aPresContext, &event, nsnull, DOM_EVENT_INIT, status); + lastContent->HandleDOMEvent(aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); } } @@ -296,7 +292,7 @@ nsEventStateManager::GenerateMouseEnterExit(nsIPresContext& aPresContext, nsGUIE if (lastContent != targetContent) { //XXX This event should still go somewhere!! if (nsnull != targetContent) { - targetContent->HandleDOMEvent(aPresContext, &event, nsnull, DOM_EVENT_INIT, status); + targetContent->HandleDOMEvent(aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); } } @@ -329,7 +325,7 @@ nsEventStateManager::GenerateMouseEnterExit(nsIPresContext& aPresContext, nsGUIE mLastMouseOverFrame->GetContent(&lastContent); if (nsnull != lastContent) { - lastContent->HandleDOMEvent(aPresContext, &event, nsnull, DOM_EVENT_INIT, status); + lastContent->HandleDOMEvent(aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); NS_RELEASE(lastContent); } @@ -352,35 +348,44 @@ nsEventStateManager::CheckForAndDispatchClick(nsIPresContext& aPresContext, { nsresult ret = NS_OK; nsMouseEvent event; + nsIContent* mouseContent; PRBool fireClick = PR_FALSE; + mCurrentTarget->GetContent(&mouseContent); + switch (aEvent->message) { case NS_MOUSE_LEFT_BUTTON_DOWN: - mLastLeftMouseDownFrame = mCurrentTarget; + mLastLeftMouseDownContent = mouseContent; + NS_IF_ADDREF(mLastLeftMouseDownContent); break; case NS_MOUSE_LEFT_BUTTON_UP: - if (mLastLeftMouseDownFrame == mCurrentTarget) { + if (mLastLeftMouseDownContent == mouseContent) { fireClick = PR_TRUE; event.message = NS_MOUSE_LEFT_CLICK; } + NS_IF_RELEASE(mLastLeftMouseDownContent); break; case NS_MOUSE_MIDDLE_BUTTON_DOWN: - mLastMiddleMouseDownFrame = mCurrentTarget; + mLastMiddleMouseDownContent = mouseContent; + NS_IF_ADDREF(mLastMiddleMouseDownContent); break; case NS_MOUSE_MIDDLE_BUTTON_UP: - if (mLastMiddleMouseDownFrame == mCurrentTarget) { + if (mLastMiddleMouseDownContent == mouseContent) { fireClick = PR_TRUE; event.message = NS_MOUSE_MIDDLE_CLICK; } + NS_IF_RELEASE(mLastMiddleMouseDownContent); break; case NS_MOUSE_RIGHT_BUTTON_DOWN: - mLastRightMouseDownFrame = mCurrentTarget; + mLastRightMouseDownContent = mouseContent; + NS_IF_ADDREF(mLastRightMouseDownContent); break; case NS_MOUSE_RIGHT_BUTTON_UP: - if (mLastRightMouseDownFrame == mCurrentTarget) { + if (mLastRightMouseDownContent == mouseContent) { fireClick = PR_TRUE; event.message = NS_MOUSE_RIGHT_CLICK; } + NS_IF_RELEASE(mLastRightMouseDownContent); break; } @@ -389,17 +394,9 @@ nsEventStateManager::CheckForAndDispatchClick(nsIPresContext& aPresContext, event.eventStructType = NS_MOUSE_EVENT; event.widget = nsnull; - nsIContent *content; - mCurrentTarget->GetContent(&content); - - if (nsnull != content) { - ret = content->HandleDOMEvent(aPresContext, &event, nsnull, DOM_EVENT_INIT, aStatus); - NS_RELEASE(content); - } - - //Now dispatch to the frame - if (nsnull != mCurrentTarget) { - mCurrentTarget->HandleEvent(aPresContext, &event, aStatus); + if (nsnull != mouseContent) { + ret = mouseContent->HandleDOMEvent(aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, aStatus); + NS_RELEASE(mouseContent); } } return ret; @@ -423,7 +420,7 @@ nsEventStateManager::DispatchKeyPressEvent(nsIPresContext& aPresContext, mCurrentTarget->GetContent(&content); if (nsnull != content) { - ret = content->HandleDOMEvent(aPresContext, &event, nsnull, DOM_EVENT_INIT, aStatus); + ret = content->HandleDOMEvent(aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, aStatus); NS_RELEASE(content); } @@ -679,39 +676,45 @@ nsEventStateManager::GetEventTarget(nsIFrame **aFrame) } NS_IMETHODIMP -nsEventStateManager::GetLinkState(nsIContent *aLink, nsLinkEventState& aState) +nsEventStateManager::GetContentState(nsIContent *aContent, PRInt32& aState) { - if (aLink == mActiveLink) { - aState = eLinkState_Active; + aState = NS_EVENT_STATE_UNSPECIFIED; + + if (aContent == mActiveContent) { + aState |= NS_EVENT_STATE_ACTIVE; } - else if (aLink == mHoverLink) { - aState = eLinkState_Hover; + if (aContent == mHoverContent) { + aState |= NS_EVENT_STATE_HOVER; } - else { - aState = eLinkState_Unspecified; + if (aContent == mCurrentFocus) { + aState |= NS_EVENT_STATE_FOCUS; } return NS_OK; } NS_IMETHODIMP -nsEventStateManager::SetActiveLink(nsIContent *aLink) +nsEventStateManager::SetActiveContent(nsIContent *aActive) { nsIDocument *mDocument; - if (nsnull != mActiveLink) { - if (NS_OK == mActiveLink->GetDocument(mDocument)) { - mDocument->ContentStateChanged(mActiveLink); + if (nsnull != mActiveContent) { + //transferring ref to lastActive from mActiveContent + nsIContent *lastActive = mActiveContent; + + if (NS_OK == mActiveContent->GetDocument(mDocument)) { + mActiveContent = nsnull; + mDocument->ContentStateChanged(lastActive); NS_RELEASE(mDocument); } + NS_RELEASE(lastActive); } - NS_IF_RELEASE(mActiveLink); - mActiveLink = aLink; + mActiveContent = aActive; + NS_IF_ADDREF(mActiveContent); - NS_IF_ADDREF(mActiveLink); - if (nsnull != mActiveLink) { - if (NS_OK == mActiveLink->GetDocument(mDocument)) { - mDocument->ContentStateChanged(mActiveLink); + if (nsnull != mActiveContent) { + if (NS_OK == mActiveContent->GetDocument(mDocument)) { + mDocument->ContentStateChanged(mActiveContent); NS_RELEASE(mDocument); } } @@ -720,24 +723,28 @@ nsEventStateManager::SetActiveLink(nsIContent *aLink) } NS_IMETHODIMP -nsEventStateManager::SetHoverLink(nsIContent *aLink) +nsEventStateManager::SetHoverContent(nsIContent *aHover) { nsIDocument *mDocument; - if (nsnull != mHoverLink) { - if (NS_OK == mHoverLink->GetDocument(mDocument)) { - mDocument->ContentStateChanged(mHoverLink); + if (nsnull != mHoverContent) { + //transferring ref to lastHover from mActiveContent + nsIContent *lastHover = mHoverContent; + + if (NS_OK == mHoverContent->GetDocument(mDocument)) { + mHoverContent = nsnull; + mDocument->ContentStateChanged(lastHover); NS_RELEASE(mDocument); } + NS_RELEASE(lastHover); } - NS_IF_RELEASE(mHoverLink); - mHoverLink = aLink; + mHoverContent = aHover; - NS_IF_ADDREF(mHoverLink); - if (nsnull != mHoverLink) { - if (NS_OK == mHoverLink->GetDocument(mDocument)) { - mDocument->ContentStateChanged(mHoverLink); + NS_IF_ADDREF(mHoverContent); + if (nsnull != mHoverContent) { + if (NS_OK == mHoverContent->GetDocument(mDocument)) { + mDocument->ContentStateChanged(mHoverContent); NS_RELEASE(mDocument); } } @@ -762,7 +769,7 @@ nsEventStateManager::SetFocusedContent(nsIContent *aContent) event.message = NS_BLUR_CONTENT; if (nsnull != mPresContext) { - mCurrentFocus->HandleDOMEvent(*mPresContext, &event, nsnull, DOM_EVENT_INIT, status); + mCurrentFocus->HandleDOMEvent(*mPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); } NS_RELEASE(mCurrentFocus); } @@ -774,7 +781,7 @@ nsEventStateManager::SetFocusedContent(nsIContent *aContent) event.message = NS_FOCUS_CONTENT; if (nsnull != mPresContext) { - aContent->HandleDOMEvent(*mPresContext, &event, nsnull, DOM_EVENT_INIT, status); + aContent->HandleDOMEvent(*mPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); } nsAutoString tabIndex; diff --git a/layout/events/src/nsEventStateManager.h b/layout/events/src/nsEventStateManager.h index ad9034577f5b..4b43bd89e055 100644 --- a/layout/events/src/nsEventStateManager.h +++ b/layout/events/src/nsEventStateManager.h @@ -50,10 +50,9 @@ public: NS_IMETHOD GetEventTarget(nsIFrame **aFrame); - NS_IMETHOD GetLinkState(nsIContent *aLink, nsLinkEventState& aState); - NS_IMETHOD SetActiveLink(nsIContent *aLink); - NS_IMETHOD SetHoverLink(nsIContent *aLink); - + NS_IMETHOD GetContentState(nsIContent *aContent, PRInt32& aState); + NS_IMETHOD SetActiveContent(nsIContent *aActive); + NS_IMETHOD SetHoverContent(nsIContent *aHover); NS_IMETHOD SetFocusedContent(nsIContent *aContent); protected: @@ -69,12 +68,13 @@ protected: //Any frames here must be checked for validity in ClearFrameRefs nsIFrame* mCurrentTarget; nsIFrame* mLastMouseOverFrame; - nsIFrame* mLastLeftMouseDownFrame; - nsIFrame* mLastMiddleMouseDownFrame; - nsIFrame* mLastRightMouseDownFrame; - nsIContent* mActiveLink; - nsIContent* mHoverLink; + nsIContent* mLastLeftMouseDownContent; + nsIContent* mLastMiddleMouseDownContent; + nsIContent* mLastRightMouseDownContent; + + nsIContent* mActiveContent; + nsIContent* mHoverContent; nsIContent* mCurrentFocus; PRInt32 mCurrentTabIndex; diff --git a/layout/forms/nsHTMLButtonControlFrame.cpp b/layout/forms/nsHTMLButtonControlFrame.cpp index aa0cfe7f1382..117dd56ddbaf 100644 --- a/layout/forms/nsHTMLButtonControlFrame.cpp +++ b/layout/forms/nsHTMLButtonControlFrame.cpp @@ -337,7 +337,7 @@ nsHTMLButtonControlFrame::MouseClicked(nsIPresContext* aPresContext) nsEvent mEvent; mEvent.eventStructType = NS_EVENT; mEvent.message = NS_FORM_RESET; - mContent->HandleDOMEvent(*aPresContext, &mEvent, nsnull, DOM_EVENT_INIT, mStatus); + mContent->HandleDOMEvent(*aPresContext, &mEvent, nsnull, NS_EVENT_FLAG_INIT, mStatus); mFormFrame->OnReset(); } else if (NS_FORM_BUTTON_SUBMIT == type) { @@ -346,7 +346,7 @@ nsHTMLButtonControlFrame::MouseClicked(nsIPresContext* aPresContext) nsEvent mEvent; mEvent.eventStructType = NS_EVENT; mEvent.message = NS_FORM_SUBMIT; - mContent->HandleDOMEvent(*aPresContext, &mEvent, nsnull, DOM_EVENT_INIT, mStatus); + mContent->HandleDOMEvent(*aPresContext, &mEvent, nsnull, NS_EVENT_FLAG_INIT, mStatus); mFormFrame->OnSubmit(aPresContext, this); } diff --git a/layout/forms/nsImageControlFrame.cpp b/layout/forms/nsImageControlFrame.cpp index 58528e685c6d..6c15ab0219a3 100644 --- a/layout/forms/nsImageControlFrame.cpp +++ b/layout/forms/nsImageControlFrame.cpp @@ -360,7 +360,7 @@ nsImageControlFrame::MouseClicked(nsIPresContext* aPresContext) event.eventStructType = NS_EVENT; event.message = NS_FORM_SUBMIT; if (nsnull != formContent) { - formContent->HandleDOMEvent(*aPresContext, &event, nsnull, DOM_EVENT_INIT, status); + formContent->HandleDOMEvent(*aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); NS_RELEASE(formContent); } if (nsEventStatus_eConsumeNoDefault != status) { diff --git a/layout/forms/nsListControlFrame.cpp b/layout/forms/nsListControlFrame.cpp index 195ee9aa23da..44ecf91994bc 100644 --- a/layout/forms/nsListControlFrame.cpp +++ b/layout/forms/nsListControlFrame.cpp @@ -1437,3 +1437,4 @@ nsresult nsListControlFrame::RequiresWidget(PRBool& aRequiresWidget) } + diff --git a/layout/forms/nsListControlFrame.h b/layout/forms/nsListControlFrame.h index 803fc8f3f543..28c849ffb390 100644 --- a/layout/forms/nsListControlFrame.h +++ b/layout/forms/nsListControlFrame.h @@ -89,7 +89,7 @@ public: /*virtual nsresult Focus(nsIDOMEvent* aEvent); virtual nsresult Blur(nsIDOMEvent* aEvent); - virtual nsresult ProcessEvent(nsIDOMEvent* aEvent); + virtual nsresult HandleEvent(nsIDOMEvent* aEvent); NS_IMETHOD AddEventListener(nsIDOMNode * aNode); NS_IMETHOD RemoveEventListener(nsIDOMNode * aNode); diff --git a/layout/forms/nsTextControlFrame.cpp b/layout/forms/nsTextControlFrame.cpp index 1c3b90045d6e..12f1cbba372a 100644 --- a/layout/forms/nsTextControlFrame.cpp +++ b/layout/forms/nsTextControlFrame.cpp @@ -218,7 +218,7 @@ nsTextControlFrame::EnterPressed(nsIPresContext& aPresContext) event.eventStructType = NS_EVENT; event.message = NS_FORM_SUBMIT; - formContent->HandleDOMEvent(aPresContext, &event, nsnull, DOM_EVENT_INIT, status); + formContent->HandleDOMEvent(aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); NS_RELEASE(formContent); } diff --git a/layout/html/base/src/nsPresShell.cpp b/layout/html/base/src/nsPresShell.cpp index 68a2635d777b..8c04de58abfa 100644 --- a/layout/html/base/src/nsPresShell.cpp +++ b/layout/html/base/src/nsPresShell.cpp @@ -1964,7 +1964,7 @@ PresShell::HandleEvent(nsIView *aView, nsIContent* targetContent; if (NS_OK == mCurrentEventFrame->GetContent(&targetContent) && nsnull != targetContent) { rv = targetContent->HandleDOMEvent(*mPresContext, (nsEvent*)aEvent, nsnull, - DOM_EVENT_INIT, aEventStatus); + NS_EVENT_FLAG_INIT, aEventStatus); NS_RELEASE(targetContent); } diff --git a/layout/html/content/src/nsHTMLAnchorElement.cpp b/layout/html/content/src/nsHTMLAnchorElement.cpp index 2f17017a115f..a021d43ccd30 100644 --- a/layout/html/content/src/nsHTMLAnchorElement.cpp +++ b/layout/html/content/src/nsHTMLAnchorElement.cpp @@ -283,39 +283,30 @@ nsHTMLAnchorElement::HandleDOMEvent(nsIPresContext& aPresContext, if (NS_CONTENT_ATTR_HAS_VALUE == result) { switch (aEvent->message) { case NS_MOUSE_LEFT_BUTTON_DOWN: - { - nsIEventStateManager *stateManager; - if (NS_OK == aPresContext.GetEventStateManager(&stateManager)) { - stateManager->SetActiveLink(this); - NS_RELEASE(stateManager); + { + nsIEventStateManager *stateManager; + if (NS_OK == aPresContext.GetEventStateManager(&stateManager)) { + stateManager->SetActiveContent(this); + NS_RELEASE(stateManager); + } + aEventStatus = nsEventStatus_eConsumeNoDefault; } - aEventStatus = nsEventStatus_eConsumeNoDefault; - } - break; + break; case NS_MOUSE_LEFT_CLICK: { - nsIEventStateManager *stateManager; - nsLinkEventState linkState; - if (NS_OK == aPresContext.GetEventStateManager(&stateManager)) { - stateManager->GetLinkState(this, linkState); - NS_RELEASE(stateManager); - } - - if (eLinkState_Active == linkState) { - if (nsEventStatus_eConsumeNoDefault != aEventStatus) { - nsAutoString target; - nsIURL* baseURL = nsnull; - GetBaseURL(baseURL); - GetAttribute(kNameSpaceID_HTML, nsHTMLAtoms::target, target); - if (target.Length() == 0) { - GetBaseTarget(target); - } - mInner.TriggerLink(aPresContext, eLinkVerb_Replace, - baseURL, href, target, PR_TRUE); - NS_IF_RELEASE(baseURL); - aEventStatus = nsEventStatus_eConsumeNoDefault; + if (nsEventStatus_eConsumeNoDefault != aEventStatus) { + nsAutoString target; + nsIURL* baseURL = nsnull; + GetBaseURL(baseURL); + GetAttribute(kNameSpaceID_HTML, nsHTMLAtoms::target, target); + if (target.Length() == 0) { + GetBaseTarget(target); } + mInner.TriggerLink(aPresContext, eLinkVerb_Replace, + baseURL, href, target, PR_TRUE); + NS_IF_RELEASE(baseURL); + aEventStatus = nsEventStatus_eConsumeNoDefault; } } break; diff --git a/layout/html/forms/src/nsButtonControlFrame.cpp b/layout/html/forms/src/nsButtonControlFrame.cpp index 285746cf02f3..cd2b67500621 100644 --- a/layout/html/forms/src/nsButtonControlFrame.cpp +++ b/layout/html/forms/src/nsButtonControlFrame.cpp @@ -322,7 +322,7 @@ nsButtonControlFrame::MouseClicked(nsIPresContext* aPresContext) case NS_FORM_INPUT_RESET: event.message = NS_FORM_RESET; if (nsnull != formContent) { - formContent->HandleDOMEvent(*aPresContext, &event, nsnull, DOM_EVENT_INIT, status); + formContent->HandleDOMEvent(*aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); } if (nsEventStatus_eConsumeNoDefault != status) { mFormFrame->OnReset(); @@ -331,7 +331,7 @@ nsButtonControlFrame::MouseClicked(nsIPresContext* aPresContext) case NS_FORM_INPUT_SUBMIT: event.message = NS_FORM_SUBMIT; if (nsnull != formContent) { - formContent->HandleDOMEvent(*aPresContext, &event, nsnull, DOM_EVENT_INIT, status); + formContent->HandleDOMEvent(*aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); } if (nsEventStatus_eConsumeNoDefault != status) { mFormFrame->OnSubmit(aPresContext, this); diff --git a/layout/html/forms/src/nsHTMLButtonControlFrame.cpp b/layout/html/forms/src/nsHTMLButtonControlFrame.cpp index aa0cfe7f1382..117dd56ddbaf 100644 --- a/layout/html/forms/src/nsHTMLButtonControlFrame.cpp +++ b/layout/html/forms/src/nsHTMLButtonControlFrame.cpp @@ -337,7 +337,7 @@ nsHTMLButtonControlFrame::MouseClicked(nsIPresContext* aPresContext) nsEvent mEvent; mEvent.eventStructType = NS_EVENT; mEvent.message = NS_FORM_RESET; - mContent->HandleDOMEvent(*aPresContext, &mEvent, nsnull, DOM_EVENT_INIT, mStatus); + mContent->HandleDOMEvent(*aPresContext, &mEvent, nsnull, NS_EVENT_FLAG_INIT, mStatus); mFormFrame->OnReset(); } else if (NS_FORM_BUTTON_SUBMIT == type) { @@ -346,7 +346,7 @@ nsHTMLButtonControlFrame::MouseClicked(nsIPresContext* aPresContext) nsEvent mEvent; mEvent.eventStructType = NS_EVENT; mEvent.message = NS_FORM_SUBMIT; - mContent->HandleDOMEvent(*aPresContext, &mEvent, nsnull, DOM_EVENT_INIT, mStatus); + mContent->HandleDOMEvent(*aPresContext, &mEvent, nsnull, NS_EVENT_FLAG_INIT, mStatus); mFormFrame->OnSubmit(aPresContext, this); } diff --git a/layout/html/forms/src/nsImageControlFrame.cpp b/layout/html/forms/src/nsImageControlFrame.cpp index 58528e685c6d..6c15ab0219a3 100644 --- a/layout/html/forms/src/nsImageControlFrame.cpp +++ b/layout/html/forms/src/nsImageControlFrame.cpp @@ -360,7 +360,7 @@ nsImageControlFrame::MouseClicked(nsIPresContext* aPresContext) event.eventStructType = NS_EVENT; event.message = NS_FORM_SUBMIT; if (nsnull != formContent) { - formContent->HandleDOMEvent(*aPresContext, &event, nsnull, DOM_EVENT_INIT, status); + formContent->HandleDOMEvent(*aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); NS_RELEASE(formContent); } if (nsEventStatus_eConsumeNoDefault != status) { diff --git a/layout/html/forms/src/nsListControlFrame.cpp b/layout/html/forms/src/nsListControlFrame.cpp index 195ee9aa23da..44ecf91994bc 100644 --- a/layout/html/forms/src/nsListControlFrame.cpp +++ b/layout/html/forms/src/nsListControlFrame.cpp @@ -1437,3 +1437,4 @@ nsresult nsListControlFrame::RequiresWidget(PRBool& aRequiresWidget) } + diff --git a/layout/html/forms/src/nsListControlFrame.h b/layout/html/forms/src/nsListControlFrame.h index 803fc8f3f543..28c849ffb390 100644 --- a/layout/html/forms/src/nsListControlFrame.h +++ b/layout/html/forms/src/nsListControlFrame.h @@ -89,7 +89,7 @@ public: /*virtual nsresult Focus(nsIDOMEvent* aEvent); virtual nsresult Blur(nsIDOMEvent* aEvent); - virtual nsresult ProcessEvent(nsIDOMEvent* aEvent); + virtual nsresult HandleEvent(nsIDOMEvent* aEvent); NS_IMETHOD AddEventListener(nsIDOMNode * aNode); NS_IMETHOD RemoveEventListener(nsIDOMNode * aNode); diff --git a/layout/html/forms/src/nsSelectControlFrame.cpp b/layout/html/forms/src/nsSelectControlFrame.cpp index 466b31ce6c3d..5c0528215100 100644 --- a/layout/html/forms/src/nsSelectControlFrame.cpp +++ b/layout/html/forms/src/nsSelectControlFrame.cpp @@ -1080,7 +1080,7 @@ nsSelectControlFrame::MouseClicked(nsIPresContext* aPresContext) event.message = NS_FORM_CHANGE; if (nsnull != mContent) { - mContent->HandleDOMEvent(*aPresContext, &event, nsnull, DOM_EVENT_INIT, status); + mContent->HandleDOMEvent(*aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); } } } diff --git a/layout/html/forms/src/nsTextControlFrame.cpp b/layout/html/forms/src/nsTextControlFrame.cpp index 1c3b90045d6e..12f1cbba372a 100644 --- a/layout/html/forms/src/nsTextControlFrame.cpp +++ b/layout/html/forms/src/nsTextControlFrame.cpp @@ -218,7 +218,7 @@ nsTextControlFrame::EnterPressed(nsIPresContext& aPresContext) event.eventStructType = NS_EVENT; event.message = NS_FORM_SUBMIT; - formContent->HandleDOMEvent(aPresContext, &event, nsnull, DOM_EVENT_INIT, status); + formContent->HandleDOMEvent(aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); NS_RELEASE(formContent); } diff --git a/layout/html/style/src/nsCSSStyleSheet.cpp b/layout/html/style/src/nsCSSStyleSheet.cpp index 7cf425146d0a..6e30e4cbde95 100644 --- a/layout/html/style/src/nsCSSStyleSheet.cpp +++ b/layout/html/style/src/nsCSSStyleSheet.cpp @@ -1050,7 +1050,7 @@ static PRBool SelectorMatches(nsIPresContext* aPresContext, // first-child, lang, active, focus, hover, link, outOfDate, visited // XXX disabled, enabled, selected, selection nsAtomList* pseudoClass = aSelector->mPseudoClassList; - nsLinkEventState eventState = eLinkState_Unspecified; + PRInt32 eventState = NS_EVENT_STATE_UNSPECIFIED; nsLinkState linkState = nsLinkState(-1); // not a link nsILinkHandler* linkHandler = nsnull; nsIEventStateManager* eventStateManager = nsnull; @@ -1092,18 +1092,17 @@ static PRBool SelectorMatches(nsIPresContext* aPresContext, if (! eventStateManager) { aPresContext->GetEventStateManager(&eventStateManager); if (eventStateManager) { - eventStateManager->GetLinkState(aContent, eventState); + eventStateManager->GetContentState(aContent, eventState); } } if (nsCSSAtoms::activePseudo == pseudoClass->mAtom) { - result = PRBool(0 != (eventState & eLinkState_Active)); + result = PRBool(0 != (eventState & NS_EVENT_STATE_ACTIVE)); } else if (nsCSSAtoms::focusPseudo == pseudoClass->mAtom) { -// result = PRBool(0 != (eventState & eLinkState_Focus)); - result = PR_FALSE; + result = PRBool(0 != (eventState & NS_EVENT_STATE_FOCUS)); } else if (nsCSSAtoms::hoverPseudo == pseudoClass->mAtom) { - result = PRBool(0 != (eventState & eLinkState_Hover)); + result = PRBool(0 != (eventState & NS_EVENT_STATE_HOVER)); } } else if (IsLinkPseudo(pseudoClass->mAtom)) { diff --git a/layout/html/style/src/nsHTMLStyleSheet.cpp b/layout/html/style/src/nsHTMLStyleSheet.cpp index 76df8a0a16d5..4e0c42ec5a1c 100644 --- a/layout/html/style/src/nsHTMLStyleSheet.cpp +++ b/layout/html/style/src/nsHTMLStyleSheet.cpp @@ -468,9 +468,9 @@ PRInt32 HTMLStyleSheetImpl::RulesMatching(nsIPresContext* aPresContext, if ((NS_OK == aPresContext->GetEventStateManager(&eventStateManager)) && (nsnull != eventStateManager)) { - nsLinkEventState state; - if (NS_OK == eventStateManager->GetLinkState(aContent, state)) { - if (0 != (state & eLinkState_Active)) { + PRInt32 state; + if (NS_OK == eventStateManager->GetContentState(aContent, state)) { + if (0 != (state & NS_EVENT_STATE_ACTIVE)) { aResults->AppendElement(mActiveRule); matchCount++; } diff --git a/layout/style/nsCSSStyleSheet.cpp b/layout/style/nsCSSStyleSheet.cpp index 7cf425146d0a..6e30e4cbde95 100644 --- a/layout/style/nsCSSStyleSheet.cpp +++ b/layout/style/nsCSSStyleSheet.cpp @@ -1050,7 +1050,7 @@ static PRBool SelectorMatches(nsIPresContext* aPresContext, // first-child, lang, active, focus, hover, link, outOfDate, visited // XXX disabled, enabled, selected, selection nsAtomList* pseudoClass = aSelector->mPseudoClassList; - nsLinkEventState eventState = eLinkState_Unspecified; + PRInt32 eventState = NS_EVENT_STATE_UNSPECIFIED; nsLinkState linkState = nsLinkState(-1); // not a link nsILinkHandler* linkHandler = nsnull; nsIEventStateManager* eventStateManager = nsnull; @@ -1092,18 +1092,17 @@ static PRBool SelectorMatches(nsIPresContext* aPresContext, if (! eventStateManager) { aPresContext->GetEventStateManager(&eventStateManager); if (eventStateManager) { - eventStateManager->GetLinkState(aContent, eventState); + eventStateManager->GetContentState(aContent, eventState); } } if (nsCSSAtoms::activePseudo == pseudoClass->mAtom) { - result = PRBool(0 != (eventState & eLinkState_Active)); + result = PRBool(0 != (eventState & NS_EVENT_STATE_ACTIVE)); } else if (nsCSSAtoms::focusPseudo == pseudoClass->mAtom) { -// result = PRBool(0 != (eventState & eLinkState_Focus)); - result = PR_FALSE; + result = PRBool(0 != (eventState & NS_EVENT_STATE_FOCUS)); } else if (nsCSSAtoms::hoverPseudo == pseudoClass->mAtom) { - result = PRBool(0 != (eventState & eLinkState_Hover)); + result = PRBool(0 != (eventState & NS_EVENT_STATE_HOVER)); } } else if (IsLinkPseudo(pseudoClass->mAtom)) { diff --git a/layout/style/nsHTMLStyleSheet.cpp b/layout/style/nsHTMLStyleSheet.cpp index 76df8a0a16d5..4e0c42ec5a1c 100644 --- a/layout/style/nsHTMLStyleSheet.cpp +++ b/layout/style/nsHTMLStyleSheet.cpp @@ -468,9 +468,9 @@ PRInt32 HTMLStyleSheetImpl::RulesMatching(nsIPresContext* aPresContext, if ((NS_OK == aPresContext->GetEventStateManager(&eventStateManager)) && (nsnull != eventStateManager)) { - nsLinkEventState state; - if (NS_OK == eventStateManager->GetLinkState(aContent, state)) { - if (0 != (state & eLinkState_Active)) { + PRInt32 state; + if (NS_OK == eventStateManager->GetContentState(aContent, state)) { + if (0 != (state & NS_EVENT_STATE_ACTIVE)) { aResults->AppendElement(mActiveRule); matchCount++; } diff --git a/layout/xml/content/src/nsXMLElement.cpp b/layout/xml/content/src/nsXMLElement.cpp index dfcb6f4466f5..1dfd072503fd 100644 --- a/layout/xml/content/src/nsXMLElement.cpp +++ b/layout/xml/content/src/nsXMLElement.cpp @@ -136,45 +136,36 @@ nsXMLElement::HandleDOMEvent(nsIPresContext& aPresContext, { nsIEventStateManager *stateManager; if (NS_OK == aPresContext.GetEventStateManager(&stateManager)) { - stateManager->SetActiveLink(this); + stateManager->SetActiveContent(this); NS_RELEASE(stateManager); } aEventStatus = nsEventStatus_eConsumeNoDefault; } break; - case NS_MOUSE_LEFT_BUTTON_UP: + case NS_MOUSE_LEFT_CLICK: { - nsIEventStateManager *stateManager; - nsLinkEventState linkState; - if (NS_OK == aPresContext.GetEventStateManager(&stateManager)) { - stateManager->GetLinkState(this, linkState); - NS_RELEASE(stateManager); - } - - if (eLinkState_Active == linkState) { - if (nsEventStatus_eConsumeNoDefault != aEventStatus) { - nsAutoString show, href, target; - nsIURL* baseURL = nsnull; - nsLinkVerb verb = eLinkVerb_Replace; - target.Truncate(); - GetAttribute(kNameSpaceID_None, kHrefAtom, href); - GetAttribute(kNameSpaceID_None, kShowAtom, show); - // XXX Should probably do this using atoms - if (show.Equals("new")) { - verb = eLinkVerb_New; - } - else if (show.Equals("embed")) { - verb = eLinkVerb_Embed; - } - - if (nsnull != mInner.mDocument) { - baseURL = mInner.mDocument->GetDocumentURL(); - } - mInner.TriggerLink(aPresContext, verb, baseURL, href, target, PR_TRUE); - NS_IF_RELEASE(baseURL); - aEventStatus = nsEventStatus_eConsumeNoDefault; + if (nsEventStatus_eConsumeNoDefault != aEventStatus) { + nsAutoString show, href, target; + nsIURL* baseURL = nsnull; + nsLinkVerb verb = eLinkVerb_Replace; + target.Truncate(); + GetAttribute(kNameSpaceID_None, kHrefAtom, href); + GetAttribute(kNameSpaceID_None, kShowAtom, show); + // XXX Should probably do this using atoms + if (show.Equals("new")) { + verb = eLinkVerb_New; + } + else if (show.Equals("embed")) { + verb = eLinkVerb_Embed; + } + + if (nsnull != mInner.mDocument) { + baseURL = mInner.mDocument->GetDocumentURL(); } + mInner.TriggerLink(aPresContext, verb, baseURL, href, target, PR_TRUE); + NS_IF_RELEASE(baseURL); + aEventStatus = nsEventStatus_eConsumeNoDefault; } } break; @@ -184,7 +175,6 @@ nsXMLElement::HandleDOMEvent(nsIPresContext& aPresContext, break; case NS_MOUSE_ENTER: - //mouse enter doesn't work yet. Use move until then. { nsAutoString href, target; nsIURL* baseURL = nsnull;