From 37bfd24b937353b1b6c2f0f4a4a20f9b5efaa2f1 Mon Sep 17 00:00:00 2001 From: "joki%netscape.com" Date: Tue, 27 Jul 1999 20:55:03 +0000 Subject: [PATCH] Partial fixes for focus/blur events on windows/frames, fixes for incorrect event.target values --- content/events/public/nsIEventStateManager.h | 1 + content/events/src/nsDOMEvent.cpp | 23 +++- content/events/src/nsEventStateManager.cpp | 108 ++++++++++++++++--- content/events/src/nsEventStateManager.h | 1 + layout/events/public/nsIEventStateManager.h | 1 + layout/events/src/nsDOMEvent.cpp | 23 +++- layout/events/src/nsEventStateManager.cpp | 108 ++++++++++++++++--- layout/events/src/nsEventStateManager.h | 1 + 8 files changed, 228 insertions(+), 38 deletions(-) diff --git a/content/events/public/nsIEventStateManager.h b/content/events/public/nsIEventStateManager.h index cb0887226a9..d5d5eca1555 100644 --- a/content/events/public/nsIEventStateManager.h +++ b/content/events/public/nsIEventStateManager.h @@ -58,6 +58,7 @@ public: NS_IMETHOD ClearFrameRefs(nsIFrame* aFrame) = 0; NS_IMETHOD GetEventTarget(nsIFrame **aFrame) = 0; + NS_IMETHOD GetEventTargetContent(nsIContent** aContent) = 0; NS_IMETHOD GetContentState(nsIContent *aContent, PRInt32& aState) = 0; NS_IMETHOD SetContentState(nsIContent *aContent, PRInt32 aState) = 0; diff --git a/content/events/src/nsDOMEvent.cpp b/content/events/src/nsDOMEvent.cpp index af94547ec74..d0f8bd2b0f8 100644 --- a/content/events/src/nsDOMEvent.cpp +++ b/content/events/src/nsDOMEvent.cpp @@ -27,6 +27,7 @@ #include "nsIWebShell.h" #include "nsIPresShell.h" #include "nsDOMTextRange.h" +#include "nsIDocument.h" static NS_DEFINE_IID(kIDOMNodeIID, NS_IDOMNODE_IID); static NS_DEFINE_IID(kIFrameIID, NS_IFRAME_IID); @@ -146,21 +147,37 @@ NS_METHOD nsDOMEvent::GetTarget(nsIDOMNode** aTarget) } nsIEventStateManager *manager; - nsIFrame *targetFrame; nsIContent *targetContent; if (NS_OK == mPresContext->GetEventStateManager(&manager)) { - manager->GetEventTarget(&targetFrame); + manager->GetEventTargetContent(&targetContent); NS_RELEASE(manager); } - if (NS_OK == targetFrame->GetContent(&targetContent) && nsnull != targetContent) { + if (targetContent) { if (NS_OK == targetContent->QueryInterface(kIDOMNodeIID, (void**)&mTarget)) { *aTarget = mTarget; NS_ADDREF(mTarget); } NS_RELEASE(targetContent); } + else { + //Always want a target. Use document if nothing else. + nsIPresShell* presShell; + nsIDocument* doc; + if (NS_SUCCEEDED(mPresContext->GetShell(&presShell))) { + presShell->GetDocument(&doc); + NS_RELEASE(presShell); + } + + if (doc) { + if (NS_OK == doc->QueryInterface(kIDOMNodeIID, (void**)&mTarget)) { + *aTarget = mTarget; + NS_ADDREF(mTarget); + } + NS_RELEASE(doc); + } + } return NS_OK; } diff --git a/content/events/src/nsEventStateManager.cpp b/content/events/src/nsEventStateManager.cpp index 11d87070223..cc4b592e66e 100644 --- a/content/events/src/nsEventStateManager.cpp +++ b/content/events/src/nsEventStateManager.cpp @@ -122,30 +122,89 @@ nsEventStateManager::PreHandleEvent(nsIPresContext& aPresContext, GenerateDragDropEnterExit(aPresContext, aEvent); break; case NS_GOTFOCUS: -#if 0 - nsIViewManager* viewMgr; - if (NS_SUCCEEDED(aView->GetViewManager(viewMgr)) && viewMgr) { - nsIView* rootView; - viewMgr->GetRootView(rootView); - if (rootView == aView) { - printf("send focus\n"); + { + nsIContent* newFocus; + mCurrentTarget->GetContent(&newFocus); + if (newFocus) { + nsIFocusableContent *focusChange; + if (NS_SUCCEEDED(newFocus->QueryInterface(kIFocusableContentIID, + (void **)&focusChange))) { + NS_RELEASE(focusChange); + NS_RELEASE(newFocus); + break; + } + NS_RELEASE(newFocus); } - else { - printf("don't send focus\n"); + + //fire focus + nsEventStatus status = nsEventStatus_eIgnore; + nsEvent event; + event.eventStructType = NS_EVENT; + event.message = NS_FOCUS_CONTENT; + + if (!mDocument) { + nsCOMPtr presShell; + aPresContext.GetShell(getter_AddRefs(presShell)); + if (presShell) { + presShell->GetDocument(&mDocument); + } + } + + if (mDocument) { + mCurrentTarget = nsnull; + mDocument->HandleDOMEvent(aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); } - NS_RELEASE(viewMgr); } -#endif - //XXX Do we need window related focus change stuff here? break; case NS_LOSTFOCUS: - //XXX Do we need window related focus change stuff here? + { + nsIContent* oldFocus; + mCurrentTarget->GetContent(&oldFocus); + if (oldFocus) { + nsIFocusableContent *focusChange; + if (NS_SUCCEEDED(oldFocus->QueryInterface(kIFocusableContentIID, + (void **)&focusChange))) { + NS_RELEASE(focusChange); + NS_RELEASE(oldFocus); + break; + } + NS_RELEASE(oldFocus); + } + + //fire blur + nsEventStatus status = nsEventStatus_eIgnore; + nsEvent event; + event.eventStructType = NS_EVENT; + event.message = NS_BLUR_CONTENT; + + if (!mDocument) { + nsCOMPtr presShell; + aPresContext.GetShell(getter_AddRefs(presShell)); + if (presShell) { + presShell->GetDocument(&mDocument); + } + } + + if (mDocument) { + mCurrentTarget = nsnull; + mDocument->HandleDOMEvent(aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); + } + } break; case NS_KEY_PRESS: + case NS_KEY_DOWN: + case NS_KEY_UP: { - nsKeyEvent * keyEvent = (nsKeyEvent *)aEvent; - if (keyEvent->isControl) { - keyEvent->charCode += 64; + if (mCurrentFocus) { + mCurrentTargetContent = mCurrentFocus; + NS_ADDREF(mCurrentTargetContent); + } + + if (aEvent->message == NS_KEY_PRESS) { + nsKeyEvent * keyEvent = (nsKeyEvent *)aEvent; + if (keyEvent->isControl) { + keyEvent->charCode += 64; + } } } break; @@ -995,7 +1054,24 @@ nsEventStateManager::GetEventTarget(nsIFrame **aFrame) } *aFrame = mCurrentTarget; + return NS_OK; +} +NS_IMETHODIMP +nsEventStateManager::GetEventTargetContent(nsIContent** aContent) +{ + if (mCurrentTargetContent) { + *aContent = mCurrentTargetContent; + NS_IF_ADDREF(*aContent); + return NS_OK; + } + + if (mCurrentTarget) { + mCurrentTarget->GetContent(aContent); + return NS_OK; + } + + *aContent = nsnull; return NS_OK; } diff --git a/content/events/src/nsEventStateManager.h b/content/events/src/nsEventStateManager.h index b661465ade3..7131a3ba65b 100644 --- a/content/events/src/nsEventStateManager.h +++ b/content/events/src/nsEventStateManager.h @@ -52,6 +52,7 @@ public: NS_IMETHOD ClearFrameRefs(nsIFrame* aFrame); NS_IMETHOD GetEventTarget(nsIFrame **aFrame); + NS_IMETHOD GetEventTargetContent(nsIContent** aContent); NS_IMETHOD GetContentState(nsIContent *aContent, PRInt32& aState); NS_IMETHOD SetContentState(nsIContent *aContent, PRInt32 aState); diff --git a/layout/events/public/nsIEventStateManager.h b/layout/events/public/nsIEventStateManager.h index cb0887226a9..d5d5eca1555 100644 --- a/layout/events/public/nsIEventStateManager.h +++ b/layout/events/public/nsIEventStateManager.h @@ -58,6 +58,7 @@ public: NS_IMETHOD ClearFrameRefs(nsIFrame* aFrame) = 0; NS_IMETHOD GetEventTarget(nsIFrame **aFrame) = 0; + NS_IMETHOD GetEventTargetContent(nsIContent** aContent) = 0; NS_IMETHOD GetContentState(nsIContent *aContent, PRInt32& aState) = 0; NS_IMETHOD SetContentState(nsIContent *aContent, PRInt32 aState) = 0; diff --git a/layout/events/src/nsDOMEvent.cpp b/layout/events/src/nsDOMEvent.cpp index af94547ec74..d0f8bd2b0f8 100644 --- a/layout/events/src/nsDOMEvent.cpp +++ b/layout/events/src/nsDOMEvent.cpp @@ -27,6 +27,7 @@ #include "nsIWebShell.h" #include "nsIPresShell.h" #include "nsDOMTextRange.h" +#include "nsIDocument.h" static NS_DEFINE_IID(kIDOMNodeIID, NS_IDOMNODE_IID); static NS_DEFINE_IID(kIFrameIID, NS_IFRAME_IID); @@ -146,21 +147,37 @@ NS_METHOD nsDOMEvent::GetTarget(nsIDOMNode** aTarget) } nsIEventStateManager *manager; - nsIFrame *targetFrame; nsIContent *targetContent; if (NS_OK == mPresContext->GetEventStateManager(&manager)) { - manager->GetEventTarget(&targetFrame); + manager->GetEventTargetContent(&targetContent); NS_RELEASE(manager); } - if (NS_OK == targetFrame->GetContent(&targetContent) && nsnull != targetContent) { + if (targetContent) { if (NS_OK == targetContent->QueryInterface(kIDOMNodeIID, (void**)&mTarget)) { *aTarget = mTarget; NS_ADDREF(mTarget); } NS_RELEASE(targetContent); } + else { + //Always want a target. Use document if nothing else. + nsIPresShell* presShell; + nsIDocument* doc; + if (NS_SUCCEEDED(mPresContext->GetShell(&presShell))) { + presShell->GetDocument(&doc); + NS_RELEASE(presShell); + } + + if (doc) { + if (NS_OK == doc->QueryInterface(kIDOMNodeIID, (void**)&mTarget)) { + *aTarget = mTarget; + NS_ADDREF(mTarget); + } + NS_RELEASE(doc); + } + } return NS_OK; } diff --git a/layout/events/src/nsEventStateManager.cpp b/layout/events/src/nsEventStateManager.cpp index 11d87070223..cc4b592e66e 100644 --- a/layout/events/src/nsEventStateManager.cpp +++ b/layout/events/src/nsEventStateManager.cpp @@ -122,30 +122,89 @@ nsEventStateManager::PreHandleEvent(nsIPresContext& aPresContext, GenerateDragDropEnterExit(aPresContext, aEvent); break; case NS_GOTFOCUS: -#if 0 - nsIViewManager* viewMgr; - if (NS_SUCCEEDED(aView->GetViewManager(viewMgr)) && viewMgr) { - nsIView* rootView; - viewMgr->GetRootView(rootView); - if (rootView == aView) { - printf("send focus\n"); + { + nsIContent* newFocus; + mCurrentTarget->GetContent(&newFocus); + if (newFocus) { + nsIFocusableContent *focusChange; + if (NS_SUCCEEDED(newFocus->QueryInterface(kIFocusableContentIID, + (void **)&focusChange))) { + NS_RELEASE(focusChange); + NS_RELEASE(newFocus); + break; + } + NS_RELEASE(newFocus); } - else { - printf("don't send focus\n"); + + //fire focus + nsEventStatus status = nsEventStatus_eIgnore; + nsEvent event; + event.eventStructType = NS_EVENT; + event.message = NS_FOCUS_CONTENT; + + if (!mDocument) { + nsCOMPtr presShell; + aPresContext.GetShell(getter_AddRefs(presShell)); + if (presShell) { + presShell->GetDocument(&mDocument); + } + } + + if (mDocument) { + mCurrentTarget = nsnull; + mDocument->HandleDOMEvent(aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); } - NS_RELEASE(viewMgr); } -#endif - //XXX Do we need window related focus change stuff here? break; case NS_LOSTFOCUS: - //XXX Do we need window related focus change stuff here? + { + nsIContent* oldFocus; + mCurrentTarget->GetContent(&oldFocus); + if (oldFocus) { + nsIFocusableContent *focusChange; + if (NS_SUCCEEDED(oldFocus->QueryInterface(kIFocusableContentIID, + (void **)&focusChange))) { + NS_RELEASE(focusChange); + NS_RELEASE(oldFocus); + break; + } + NS_RELEASE(oldFocus); + } + + //fire blur + nsEventStatus status = nsEventStatus_eIgnore; + nsEvent event; + event.eventStructType = NS_EVENT; + event.message = NS_BLUR_CONTENT; + + if (!mDocument) { + nsCOMPtr presShell; + aPresContext.GetShell(getter_AddRefs(presShell)); + if (presShell) { + presShell->GetDocument(&mDocument); + } + } + + if (mDocument) { + mCurrentTarget = nsnull; + mDocument->HandleDOMEvent(aPresContext, &event, nsnull, NS_EVENT_FLAG_INIT, status); + } + } break; case NS_KEY_PRESS: + case NS_KEY_DOWN: + case NS_KEY_UP: { - nsKeyEvent * keyEvent = (nsKeyEvent *)aEvent; - if (keyEvent->isControl) { - keyEvent->charCode += 64; + if (mCurrentFocus) { + mCurrentTargetContent = mCurrentFocus; + NS_ADDREF(mCurrentTargetContent); + } + + if (aEvent->message == NS_KEY_PRESS) { + nsKeyEvent * keyEvent = (nsKeyEvent *)aEvent; + if (keyEvent->isControl) { + keyEvent->charCode += 64; + } } } break; @@ -995,7 +1054,24 @@ nsEventStateManager::GetEventTarget(nsIFrame **aFrame) } *aFrame = mCurrentTarget; + return NS_OK; +} +NS_IMETHODIMP +nsEventStateManager::GetEventTargetContent(nsIContent** aContent) +{ + if (mCurrentTargetContent) { + *aContent = mCurrentTargetContent; + NS_IF_ADDREF(*aContent); + return NS_OK; + } + + if (mCurrentTarget) { + mCurrentTarget->GetContent(aContent); + return NS_OK; + } + + *aContent = nsnull; return NS_OK; } diff --git a/layout/events/src/nsEventStateManager.h b/layout/events/src/nsEventStateManager.h index b661465ade3..7131a3ba65b 100644 --- a/layout/events/src/nsEventStateManager.h +++ b/layout/events/src/nsEventStateManager.h @@ -52,6 +52,7 @@ public: NS_IMETHOD ClearFrameRefs(nsIFrame* aFrame); NS_IMETHOD GetEventTarget(nsIFrame **aFrame); + NS_IMETHOD GetEventTargetContent(nsIContent** aContent); NS_IMETHOD GetContentState(nsIContent *aContent, PRInt32& aState); NS_IMETHOD SetContentState(nsIContent *aContent, PRInt32 aState);