mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-11-25 22:01:30 +00:00
Prevent double submission of forms (bug 72906). r=darin@netscape.com, r=alexsavulov@netscape.com, sr=alecf@netscape.com, a=asa
This commit is contained in:
parent
a38050b457
commit
aeb4d3fdbb
@ -48,8 +48,10 @@ class nsIPresContext;
|
||||
class nsIContent;
|
||||
class nsIFormControl;
|
||||
class nsIDOMHTMLElement;
|
||||
class nsIDocShell;
|
||||
class nsIRequest;
|
||||
|
||||
#define NS_IFORMSUBMITTER_IID \
|
||||
#define NS_IFORMSUBMISSION_IID \
|
||||
{ 0x7ee38e3a, 0x1dd2, 0x11b2, \
|
||||
{0x89, 0x6f, 0xab, 0x28, 0x03, 0x96, 0x25, 0xa9} }
|
||||
|
||||
@ -61,7 +63,7 @@ class nsIFormSubmission : public nsISupports
|
||||
{
|
||||
public:
|
||||
|
||||
NS_DEFINE_STATIC_IID_ACCESSOR(NS_IFORMSUBMITTER_IID)
|
||||
NS_DEFINE_STATIC_IID_ACCESSOR(NS_IFORMSUBMISSION_IID)
|
||||
|
||||
/**
|
||||
* Find out whether or not this form submission accepts files
|
||||
@ -77,9 +79,13 @@ public:
|
||||
* @param aTarget the target window
|
||||
* @param aSource the element responsible for the submission (for web shell)
|
||||
* @param aPresContext the presentation context
|
||||
* @param aDocShell (out param) the DocShell in which the submission was
|
||||
* loaded
|
||||
* @param aRequest (out param) the Request for the submission
|
||||
*/
|
||||
NS_IMETHOD SubmitTo(nsIURI* aActionURL, const nsAString& aTarget,
|
||||
nsIContent* aSource, nsIPresContext* aPresContext) = 0;
|
||||
nsIContent* aSource, nsIPresContext* aPresContext,
|
||||
nsIDocShell** aDocShell, nsIRequest** aRequest) = 0;
|
||||
|
||||
/**
|
||||
* Submit a name/value pair
|
||||
|
@ -38,6 +38,7 @@ REQUIRES = xpcom \
|
||||
locale \
|
||||
unicharutil \
|
||||
webshell \
|
||||
uriloader \
|
||||
htmlparser \
|
||||
necko \
|
||||
view \
|
||||
|
@ -32,6 +32,7 @@ REQUIRES = xpcom \
|
||||
webshell \
|
||||
htmlparser \
|
||||
necko \
|
||||
uriloader \
|
||||
view \
|
||||
pref \
|
||||
docshell \
|
||||
|
@ -98,7 +98,8 @@ public:
|
||||
// nsIFormSubmission
|
||||
//
|
||||
NS_IMETHOD SubmitTo(nsIURI* aActionURL, const nsAString& aTarget,
|
||||
nsIContent* aSource, nsIPresContext* aPresContext);
|
||||
nsIContent* aSource, nsIPresContext* aPresContext,
|
||||
nsIDocShell** aDocShell, nsIRequest** aRequest);
|
||||
|
||||
|
||||
NS_IMETHOD Init() = 0;
|
||||
@ -719,7 +720,8 @@ GetSubmissionFromForm(nsIForm* aForm,
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsFormSubmission::SubmitTo(nsIURI* aActionURL, const nsAString& aTarget,
|
||||
nsIContent* aSource, nsIPresContext* aPresContext)
|
||||
nsIContent* aSource, nsIPresContext* aPresContext,
|
||||
nsIDocShell** aDocShell, nsIRequest** aRequest)
|
||||
{
|
||||
nsresult rv;
|
||||
|
||||
@ -739,9 +741,11 @@ nsFormSubmission::SubmitTo(nsIURI* aActionURL, const nsAString& aTarget,
|
||||
nsCAutoString actionURLSpec;
|
||||
aActionURL->GetSpec(actionURLSpec);
|
||||
|
||||
handler->OnLinkClick(aSource, eLinkVerb_Replace,
|
||||
NS_ConvertUTF8toUCS2(actionURLSpec).get(),
|
||||
PromiseFlatString(aTarget).get(), postDataStream);
|
||||
handler->OnLinkClickSync(aSource, eLinkVerb_Replace,
|
||||
NS_ConvertUTF8toUCS2(actionURLSpec).get(),
|
||||
PromiseFlatString(aTarget).get(),
|
||||
postDataStream, nsnull,
|
||||
aDocShell, aRequest);
|
||||
}
|
||||
|
||||
return rv;
|
||||
|
@ -75,6 +75,10 @@
|
||||
#include "nsRange.h"
|
||||
#include "nsIScriptSecurityManager.h"
|
||||
#include "nsNetUtil.h"
|
||||
#include "nsIWebProgress.h"
|
||||
#include "nsIDocShell.h"
|
||||
#include "nsIWebProgressListener.h"
|
||||
#include "nsWeakReference.h"
|
||||
|
||||
// radio buttons
|
||||
#include "nsIDOMHTMLInputElement.h"
|
||||
@ -88,15 +92,20 @@ class nsFormControlList;
|
||||
// nsHTMLFormElement
|
||||
|
||||
class nsHTMLFormElement : public nsGenericHTMLContainerElement,
|
||||
public nsSupportsWeakReference,
|
||||
public nsIDOMHTMLFormElement,
|
||||
public nsIDOMNSHTMLFormElement,
|
||||
public nsIWebProgressListener,
|
||||
public nsIForm
|
||||
{
|
||||
public:
|
||||
nsHTMLFormElement() :
|
||||
mGeneratingSubmit(PR_FALSE),
|
||||
mGeneratingReset(PR_FALSE),
|
||||
mDemotingForm(PR_FALSE) { };
|
||||
mDemotingForm(PR_FALSE),
|
||||
mIsSubmitting(PR_FALSE),
|
||||
mSubmittingRequest(nsnull) { }
|
||||
|
||||
|
||||
virtual ~nsHTMLFormElement();
|
||||
|
||||
@ -120,6 +129,9 @@ public:
|
||||
// nsIDOMNSHTMLFormElement
|
||||
NS_DECL_NSIDOMNSHTMLFORMELEMENT
|
||||
|
||||
// nsIWebProgressListener
|
||||
NS_DECL_NSIWEBPROGRESSLISTENER
|
||||
|
||||
// nsIForm
|
||||
NS_IMETHOD AddElement(nsIFormControl* aElement);
|
||||
NS_IMETHOD AddElementToTable(nsIFormControl* aChild,
|
||||
@ -217,6 +229,8 @@ protected:
|
||||
PRPackedBool mGeneratingSubmit;
|
||||
PRPackedBool mGeneratingReset;
|
||||
PRPackedBool mDemotingForm;
|
||||
PRPackedBool mIsSubmitting;
|
||||
nsCOMPtr<nsIRequest> mSubmittingRequest;
|
||||
|
||||
protected:
|
||||
// Detection of first form to notify observers
|
||||
@ -393,9 +407,11 @@ NS_IMPL_RELEASE_INHERITED(nsHTMLFormElement, nsGenericElement)
|
||||
// QueryInterface implementation for nsHTMLFormElement
|
||||
NS_HTML_CONTENT_INTERFACE_MAP_BEGIN(nsHTMLFormElement,
|
||||
nsGenericHTMLContainerElement)
|
||||
NS_INTERFACE_MAP_ENTRY(nsISupportsWeakReference)
|
||||
NS_INTERFACE_MAP_ENTRY(nsIDOMHTMLFormElement)
|
||||
NS_INTERFACE_MAP_ENTRY(nsIDOMNSHTMLFormElement)
|
||||
NS_INTERFACE_MAP_ENTRY(nsIForm)
|
||||
NS_INTERFACE_MAP_ENTRY(nsIWebProgressListener)
|
||||
NS_INTERFACE_MAP_ENTRY_CONTENT_CLASSINFO(HTMLFormElement)
|
||||
NS_HTML_CONTENT_INTERFACE_MAP_END
|
||||
|
||||
@ -652,9 +668,26 @@ nsHTMLFormElement::DoReset()
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
#define NS_ENSURE_SUBMIT_SUCCESS(rv) \
|
||||
if (NS_FAILED(rv)) { \
|
||||
mIsSubmitting = PR_FALSE; \
|
||||
return rv; \
|
||||
}
|
||||
|
||||
nsresult
|
||||
nsHTMLFormElement::DoSubmit(nsIPresContext* aPresContext, nsEvent* aEvent)
|
||||
{
|
||||
NS_ASSERTION(!mIsSubmitting, "Either two people are trying to submit or the "
|
||||
"previous submit was not properly cancelled by the DocShell");
|
||||
if (mIsSubmitting) {
|
||||
// XXX Should this return an error?
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
// Mark us as submitting so that we don't try to submit again
|
||||
mIsSubmitting = PR_TRUE;
|
||||
mSubmittingRequest = nsnull;
|
||||
|
||||
nsIContent *originatingElement = nsnull;
|
||||
|
||||
// Get the originating frame (failure is non-fatal)
|
||||
@ -670,42 +703,54 @@ nsHTMLFormElement::DoSubmit(nsIPresContext* aPresContext, nsEvent* aEvent)
|
||||
nsCOMPtr<nsIFormSubmission> submission;
|
||||
nsresult rv = GetSubmissionFromForm(this, aPresContext,
|
||||
getter_AddRefs(submission));
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
NS_ENSURE_SUBMIT_SUCCESS(rv);
|
||||
|
||||
//
|
||||
// Dump the data into the submission object
|
||||
//
|
||||
rv = WalkFormElements(submission, originatingElement);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
NS_ENSURE_SUBMIT_SUCCESS(rv);
|
||||
|
||||
//
|
||||
// Get the action and target
|
||||
//
|
||||
nsCOMPtr<nsIURI> actionURI;
|
||||
rv = GetActionURL(getter_AddRefs(actionURI));
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
NS_ENSURE_SUBMIT_SUCCESS(rv);
|
||||
|
||||
if (actionURI) {
|
||||
nsAutoString target;
|
||||
rv = GetTarget(target);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
//
|
||||
// Notify observers of submit
|
||||
//
|
||||
PRBool aCancelSubmit = PR_FALSE;
|
||||
rv = NotifySubmitObservers(actionURI, &aCancelSubmit);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
if (!aCancelSubmit) {
|
||||
//
|
||||
// Submit
|
||||
//
|
||||
rv = submission->SubmitTo(actionURI, target, this, aPresContext);
|
||||
}
|
||||
if (!actionURI) {
|
||||
mIsSubmitting = PR_FALSE;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
return rv;
|
||||
nsAutoString target;
|
||||
rv = GetTarget(target);
|
||||
NS_ENSURE_SUBMIT_SUCCESS(rv);
|
||||
|
||||
//
|
||||
// Notify observers of submit
|
||||
//
|
||||
PRBool aCancelSubmit = PR_FALSE;
|
||||
rv = NotifySubmitObservers(actionURI, &aCancelSubmit);
|
||||
NS_ENSURE_SUBMIT_SUCCESS(rv);
|
||||
|
||||
if (aCancelSubmit) {
|
||||
mIsSubmitting = PR_FALSE;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
//
|
||||
// Submit
|
||||
//
|
||||
nsCOMPtr<nsIDocShell> docShell;
|
||||
rv = submission->SubmitTo(actionURI, target, this, aPresContext,
|
||||
getter_AddRefs(docShell),
|
||||
getter_AddRefs(mSubmittingRequest));
|
||||
NS_ENSURE_SUBMIT_SUCCESS(rv);
|
||||
|
||||
nsCOMPtr<nsIWebProgress> webProgress = do_GetInterface(docShell);
|
||||
NS_ASSERTION(webProgress, "nsIDocShell null or not converted to nsIWebProgress!");
|
||||
return webProgress->AddProgressListener(this);
|
||||
}
|
||||
|
||||
|
||||
@ -1104,6 +1149,69 @@ nsHTMLFormElement::GetLength(PRInt32* aLength)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
// nsIWebProgressListener
|
||||
NS_IMETHODIMP
|
||||
nsHTMLFormElement::OnStateChange(nsIWebProgress* aWebProgress,
|
||||
nsIRequest* aRequest,
|
||||
PRInt32 aStateFlags,
|
||||
PRUint32 aStatus)
|
||||
{
|
||||
// If STATE_STOP is never fired for any reason (redirect? Failed state
|
||||
// change?) the form element will leak. It will be kept around by the
|
||||
// nsIWebProgressListener (assuming it keeps a strong pointer). We will
|
||||
// consequently leak the request.
|
||||
if (aRequest == mSubmittingRequest &&
|
||||
aStateFlags & nsIWebProgressListener::STATE_STOP) {
|
||||
mIsSubmitting = PR_FALSE;
|
||||
mSubmittingRequest = nsnull;
|
||||
aWebProgress->RemoveProgressListener(this);
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsHTMLFormElement::OnProgressChange(nsIWebProgress* aWebProgress,
|
||||
nsIRequest* aRequest,
|
||||
PRInt32 aCurSelfProgress,
|
||||
PRInt32 aMaxSelfProgress,
|
||||
PRInt32 aCurTotalProgress,
|
||||
PRInt32 aMaxTotalProgress)
|
||||
{
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsHTMLFormElement::OnLocationChange(nsIWebProgress* aWebProgress,
|
||||
nsIRequest* aRequest,
|
||||
nsIURI* location)
|
||||
{
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsHTMLFormElement::OnStatusChange(nsIWebProgress* aWebProgress,
|
||||
nsIRequest* aRequest,
|
||||
nsresult aStatus,
|
||||
const PRUnichar* aMessage)
|
||||
{
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsHTMLFormElement::OnSecurityChange(nsIWebProgress* aWebProgress,
|
||||
nsIRequest* aRequest,
|
||||
PRInt32 state)
|
||||
{
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsHTMLFormElement::IndexOfControl(nsIFormControl* aControl, PRInt32* aIndex)
|
||||
{
|
||||
|
@ -648,7 +648,9 @@ nsDocShell::LoadURI(nsIURI * aURI,
|
||||
nsnull, // No headers stream
|
||||
loadType,
|
||||
nsnull, // No SHEntry
|
||||
firstParty);
|
||||
firstParty,
|
||||
nsnull, // No nsIDocShell
|
||||
nsnull); // No nsIRequest
|
||||
}
|
||||
|
||||
return rv;
|
||||
@ -2417,8 +2419,10 @@ nsDocShell::Reload(PRUint32 aReloadFlags)
|
||||
nsnull, // No post data
|
||||
nsnull, // No headers data
|
||||
type, // Load type
|
||||
nsnull, // No SHEntry
|
||||
PR_TRUE);
|
||||
nsnull, // No SHEntry
|
||||
PR_TRUE,
|
||||
nsnull, // No nsIDocShell
|
||||
nsnull); // No nsIRequest
|
||||
return rv;
|
||||
}
|
||||
|
||||
@ -4285,9 +4289,19 @@ nsDocShell::InternalLoad(nsIURI * aURI,
|
||||
nsIInputStream * aHeadersData,
|
||||
PRUint32 aLoadType,
|
||||
nsISHEntry * aSHEntry,
|
||||
PRBool firstParty)
|
||||
PRBool firstParty,
|
||||
nsIDocShell** aDocShell,
|
||||
nsIRequest** aRequest)
|
||||
{
|
||||
nsresult rv;
|
||||
nsresult rv = NS_OK;
|
||||
|
||||
// Initialize aDocShell/aRequest
|
||||
if (aDocShell) {
|
||||
*aDocShell = nsnull;
|
||||
}
|
||||
if (aRequest) {
|
||||
*aRequest = nsnull;
|
||||
}
|
||||
|
||||
nsCOMPtr<nsISupports> owner(aOwner);
|
||||
//
|
||||
@ -4334,8 +4348,9 @@ nsDocShell::InternalLoad(nsIURI * aURI,
|
||||
|
||||
extProtService->ExternalProtocolHandlerExists(urlScheme.get(),
|
||||
&haveHandler);
|
||||
if (haveHandler)
|
||||
if (haveHandler) {
|
||||
return extProtService->LoadUrl(aURI);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -4397,7 +4412,9 @@ nsDocShell::InternalLoad(nsIURI * aURI,
|
||||
aHeadersData,
|
||||
aLoadType,
|
||||
aSHEntry,
|
||||
firstParty);
|
||||
firstParty,
|
||||
aDocShell,
|
||||
aRequest);
|
||||
if (rv == NS_ERROR_NO_CONTENT) {
|
||||
if (bIsNewWindow) {
|
||||
//
|
||||
@ -4512,7 +4529,8 @@ nsDocShell::InternalLoad(nsIURI * aURI,
|
||||
// been called.
|
||||
mLSHE = aSHEntry;
|
||||
|
||||
rv = DoURILoad(aURI, aReferrer, owner, aPostData, aHeadersData, firstParty);
|
||||
rv = DoURILoad(aURI, aReferrer, owner, aPostData, aHeadersData, firstParty,
|
||||
aDocShell, aRequest);
|
||||
|
||||
return rv;
|
||||
}
|
||||
@ -4583,12 +4601,15 @@ nsDocShell::GetCurrentDocumentOwner(nsISupports ** aOwner)
|
||||
return rv;
|
||||
}
|
||||
|
||||
nsresult nsDocShell::DoURILoad(nsIURI * aURI,
|
||||
nsIURI * aReferrerURI,
|
||||
nsISupports * aOwner,
|
||||
nsIInputStream * aPostData,
|
||||
nsIInputStream * aHeadersData,
|
||||
PRBool firstParty)
|
||||
nsresult
|
||||
nsDocShell::DoURILoad(nsIURI * aURI,
|
||||
nsIURI * aReferrerURI,
|
||||
nsISupports * aOwner,
|
||||
nsIInputStream * aPostData,
|
||||
nsIInputStream * aHeadersData,
|
||||
PRBool firstParty,
|
||||
nsIDocShell ** aDocShell,
|
||||
nsIRequest ** aRequest)
|
||||
{
|
||||
nsresult rv;
|
||||
nsCOMPtr<nsIURILoader> uriLoader;
|
||||
@ -4716,6 +4737,20 @@ nsresult nsDocShell::DoURILoad(nsIURI * aURI,
|
||||
}
|
||||
|
||||
rv = DoChannelLoad(channel, uriLoader);
|
||||
|
||||
//
|
||||
// If the channel load failed, we failed and nsIWebProgress just ain't
|
||||
// gonna happen.
|
||||
//
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
if (aDocShell) {
|
||||
*aDocShell = this;
|
||||
NS_ADDREF(*aDocShell);
|
||||
}
|
||||
if (aRequest) {
|
||||
CallQueryInterface(channel, aRequest);
|
||||
}
|
||||
}
|
||||
|
||||
return rv;
|
||||
}
|
||||
@ -5497,7 +5532,9 @@ nsDocShell::LoadHistoryEntry(nsISHEntry * aEntry, PRUint32 aLoadType)
|
||||
nsnull, // No headers stream
|
||||
aLoadType, // Load type
|
||||
aEntry, // SHEntry
|
||||
PR_TRUE);
|
||||
PR_TRUE,
|
||||
nsnull, // No nsIDocShell
|
||||
nsnull); // No nsIRequest
|
||||
return rv;
|
||||
}
|
||||
|
||||
|
@ -209,7 +209,9 @@ protected:
|
||||
nsISupports * aOwner,
|
||||
nsIInputStream * aPostData,
|
||||
nsIInputStream * aHeadersData,
|
||||
PRBool firstParty);
|
||||
PRBool firstParty,
|
||||
nsIDocShell ** aDocShell,
|
||||
nsIRequest ** aRequest);
|
||||
NS_IMETHOD AddHeadersToChannel(nsIInputStream * aHeadersData,
|
||||
nsIChannel * aChannel);
|
||||
virtual nsresult DoChannelLoad(nsIChannel * aChannel,
|
||||
|
@ -44,6 +44,7 @@ interface nsIDocumentCharsetInfo;
|
||||
interface nsIWebNavigation;
|
||||
interface nsISimpleEnumerator;
|
||||
interface nsIInputStream;
|
||||
interface nsIRequest;
|
||||
interface nsISHEntry;
|
||||
|
||||
[scriptable, uuid(69E5DE00-7B8B-11d3-AF61-00A024FFC08C)]
|
||||
@ -123,7 +124,9 @@ interface nsIDocShell : nsISupports
|
||||
in nsIInputStream aHeadersStream,
|
||||
in unsigned long aLoadFlags,
|
||||
in nsISHEntry aSHEntry,
|
||||
in boolean firstParty);
|
||||
in boolean firstParty,
|
||||
out nsIDocShell aDocShell,
|
||||
out nsIRequest aRequest);
|
||||
|
||||
/**
|
||||
* Creates a DocShellLoadInfo object that you can manipulate and then pass
|
||||
|
@ -455,17 +455,18 @@ struct OnLinkClickEvent : public PLEvent {
|
||||
~OnLinkClickEvent();
|
||||
|
||||
void HandleEvent() {
|
||||
mHandler->HandleLinkClickEvent(mContent, mVerb, mURLSpec->get(),
|
||||
mTargetSpec->get(), mPostDataStream,
|
||||
mHeadersDataStream);
|
||||
mHandler->OnLinkClickSync(mContent, mVerb, mURLSpec.get(),
|
||||
mTargetSpec.get(), mPostDataStream,
|
||||
mHeadersDataStream,
|
||||
nsnull, nsnull);
|
||||
}
|
||||
|
||||
nsWebShell* mHandler;
|
||||
nsString* mURLSpec;
|
||||
nsString* mTargetSpec;
|
||||
nsIInputStream* mPostDataStream;
|
||||
nsIInputStream* mHeadersDataStream;
|
||||
nsIContent* mContent;
|
||||
nsWebShell* mHandler;
|
||||
nsString mURLSpec;
|
||||
nsString mTargetSpec;
|
||||
nsCOMPtr<nsIInputStream> mPostDataStream;
|
||||
nsCOMPtr<nsIInputStream> mHeadersDataStream;
|
||||
nsCOMPtr<nsIContent> mContent;
|
||||
nsLinkVerb mVerb;
|
||||
};
|
||||
|
||||
@ -489,14 +490,11 @@ OnLinkClickEvent::OnLinkClickEvent(nsWebShell* aHandler,
|
||||
{
|
||||
mHandler = aHandler;
|
||||
NS_ADDREF(aHandler);
|
||||
mURLSpec = new nsString(aURLSpec);
|
||||
mTargetSpec = new nsString(aTargetSpec);
|
||||
mURLSpec.Assign(aURLSpec);
|
||||
mTargetSpec.Assign(aTargetSpec);
|
||||
mPostDataStream = aPostDataStream;
|
||||
NS_IF_ADDREF(mPostDataStream);
|
||||
mHeadersDataStream = aHeadersDataStream;
|
||||
NS_IF_ADDREF(mHeadersDataStream);
|
||||
mContent = aContent;
|
||||
NS_IF_ADDREF(mContent);
|
||||
mVerb = aVerb;
|
||||
|
||||
PL_InitEvent(this, nsnull,
|
||||
@ -512,13 +510,7 @@ OnLinkClickEvent::OnLinkClickEvent(nsWebShell* aHandler,
|
||||
|
||||
OnLinkClickEvent::~OnLinkClickEvent()
|
||||
{
|
||||
NS_IF_RELEASE(mContent);
|
||||
NS_IF_RELEASE(mHandler);
|
||||
NS_IF_RELEASE(mPostDataStream);
|
||||
NS_IF_RELEASE(mHeadersDataStream);
|
||||
if (nsnull != mURLSpec) delete mURLSpec;
|
||||
if (nsnull != mTargetSpec) delete mTargetSpec;
|
||||
|
||||
}
|
||||
|
||||
//----------------------------------------
|
||||
@ -554,17 +546,27 @@ nsWebShell::GetEventQueue(nsIEventQueue **aQueue)
|
||||
return *aQueue ? NS_OK : NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
void
|
||||
nsWebShell::HandleLinkClickEvent(nsIContent *aContent,
|
||||
nsLinkVerb aVerb,
|
||||
const PRUnichar* aURLSpec,
|
||||
const PRUnichar* aTargetSpec,
|
||||
nsIInputStream* aPostDataStream,
|
||||
nsIInputStream* aHeadersDataStream)
|
||||
NS_IMETHODIMP
|
||||
nsWebShell::OnLinkClickSync(nsIContent *aContent,
|
||||
nsLinkVerb aVerb,
|
||||
const PRUnichar* aURLSpec,
|
||||
const PRUnichar* aTargetSpec,
|
||||
nsIInputStream* aPostDataStream,
|
||||
nsIInputStream* aHeadersDataStream,
|
||||
nsIDocShell** aDocShell,
|
||||
nsIRequest** aRequest)
|
||||
{
|
||||
nsresult rv;
|
||||
nsAutoString target(aTargetSpec);
|
||||
|
||||
// Initialize the DocShell / Request
|
||||
if (aDocShell) {
|
||||
*aDocShell = nsnull;
|
||||
}
|
||||
if (aRequest) {
|
||||
*aRequest = nsnull;
|
||||
}
|
||||
|
||||
switch(aVerb) {
|
||||
case eLinkVerb_New:
|
||||
target.Assign(NS_LITERAL_STRING("_blank"));
|
||||
@ -599,19 +601,21 @@ nsWebShell::HandleLinkClickEvent(nsIContent *aContent,
|
||||
listener->OnStartURIOpen(uri, &abort);
|
||||
}
|
||||
}
|
||||
return;
|
||||
return rv;
|
||||
}
|
||||
|
||||
rv = InternalLoad(uri, // New URI
|
||||
mCurrentURI, // Referer URI
|
||||
nsnull, // No onwer
|
||||
PR_TRUE, // Inherit owner from document
|
||||
target.get(), // Window target
|
||||
aPostDataStream, // Post data stream
|
||||
aHeadersDataStream, // Headers stream
|
||||
LOAD_LINK, // Load type
|
||||
nsnull, // No SHEntry
|
||||
PR_TRUE); // first party site
|
||||
return InternalLoad(uri, // New URI
|
||||
mCurrentURI, // Referer URI
|
||||
nsnull, // No onwer
|
||||
PR_TRUE, // Inherit owner from document
|
||||
target.get(), // Window target
|
||||
aPostDataStream, // Post data stream
|
||||
aHeadersDataStream, // Headers stream
|
||||
LOAD_LINK, // Load type
|
||||
nsnull, // No SHEntry
|
||||
PR_TRUE, // first party site
|
||||
aDocShell, // DocShell out-param
|
||||
aRequest); // Request out-param
|
||||
}
|
||||
break;
|
||||
case eLinkVerb_Embed:
|
||||
@ -619,6 +623,7 @@ nsWebShell::HandleLinkClickEvent(nsIContent *aContent,
|
||||
// in NS 4.x
|
||||
default:
|
||||
NS_ABORT_IF_FALSE(0,"unexpected link verb");
|
||||
return NS_ERROR_UNEXPECTED;
|
||||
}
|
||||
}
|
||||
|
||||
@ -997,7 +1002,9 @@ nsresult nsWebShell::EndPageLoad(nsIWebProgress *aProgress,
|
||||
nsnull, // No headers stream
|
||||
LOAD_RELOAD_BYPASS_PROXY_AND_CACHE,// Load type
|
||||
nsnull, // No SHEntry
|
||||
PR_TRUE); // first party site
|
||||
PR_TRUE, // first party site
|
||||
nsnull, // No nsIDocShell
|
||||
nsnull); // No nsIRequest
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -71,6 +71,14 @@ public:
|
||||
const PRUnichar* aTargetSpec,
|
||||
nsIInputStream* aPostDataStream = 0,
|
||||
nsIInputStream* aHeadersDataStream = 0);
|
||||
NS_IMETHOD OnLinkClickSync(nsIContent* aContent,
|
||||
nsLinkVerb aVerb,
|
||||
const PRUnichar* aURLSpec,
|
||||
const PRUnichar* aTargetSpec,
|
||||
nsIInputStream* aPostDataStream = 0,
|
||||
nsIInputStream* aHeadersDataStream = 0,
|
||||
nsIDocShell** aDocShell = 0,
|
||||
nsIRequest** aRequest = 0);
|
||||
NS_IMETHOD OnOverLink(nsIContent* aContent,
|
||||
const PRUnichar* aURLSpec,
|
||||
const PRUnichar* aTargetSpec);
|
||||
@ -81,12 +89,6 @@ public:
|
||||
|
||||
// nsWebShell
|
||||
nsresult GetEventQueue(nsIEventQueue **aQueue);
|
||||
void HandleLinkClickEvent(nsIContent *aContent,
|
||||
nsLinkVerb aVerb,
|
||||
const PRUnichar* aURLSpec,
|
||||
const PRUnichar* aTargetSpec,
|
||||
nsIInputStream* aPostDataStream = 0,
|
||||
nsIInputStream* aHeadersDataStream = 0);
|
||||
|
||||
static nsEventStatus PR_CALLBACK HandleEvent(nsGUIEvent *aEvent);
|
||||
|
||||
|
@ -40,6 +40,8 @@
|
||||
#include "nsISupports.h"
|
||||
|
||||
class nsIInputStream;
|
||||
class nsIDocShell;
|
||||
class nsIRequest;
|
||||
class nsIContent;
|
||||
class nsString;
|
||||
struct nsGUIEvent;
|
||||
@ -73,11 +75,16 @@ public:
|
||||
NS_DEFINE_STATIC_IID_ACCESSOR(NS_ILINKHANDLER_IID)
|
||||
|
||||
/**
|
||||
* Process a click on a link. aContent is the content for the frame
|
||||
* that generated the trigger. aURLSpec is an absolute url spec that
|
||||
* defines the destination for the link. aTargetSpec indicates where
|
||||
* the link is targeted (it may be an empty string). aVerb indicates
|
||||
* the verb to use when the link is triggered.
|
||||
* Process a click on a link.
|
||||
*
|
||||
* @param aContent the content for the frame that generated the trigger
|
||||
* @param aVerb the verb to use when the link is triggered
|
||||
* @param aURLSpec an absolute URL spec that defines the destination for the
|
||||
* link
|
||||
* @param aTargetSpec indicates where the link is targeted (may be an empty
|
||||
* string)
|
||||
* @param aPostDataStream the POST data to send
|
||||
* @param aHeadersDataStream ???
|
||||
*/
|
||||
NS_IMETHOD OnLinkClick(nsIContent* aContent,
|
||||
nsLinkVerb aVerb,
|
||||
@ -87,10 +94,39 @@ public:
|
||||
nsIInputStream* aHeadersDataStream = 0) = 0;
|
||||
|
||||
/**
|
||||
* Process a mouse-over a link. aContent is the
|
||||
* linked content. aURLSpec is an absolute url spec that defines the
|
||||
* destination for the link. aTargetSpec indicates where the link is
|
||||
* targeted (it may be an empty string).
|
||||
* Process a click on a link.
|
||||
*
|
||||
* Works the same as OnLinkClick() except it happens immediately rather than
|
||||
* through an event.
|
||||
*
|
||||
* @param aContent the content for the frame that generated the trigger
|
||||
* @param aVerb the verb to use when the link is triggered
|
||||
* @param aURLSpec an absolute URL spec that defines the destination for the
|
||||
* link
|
||||
* @param aTargetSpec indicates where the link is targeted (may be an empty
|
||||
* string)
|
||||
* @param aPostDataStream the POST data to send
|
||||
* @param aHeadersDataStream ???
|
||||
* @param aDocShell (out-param) the DocShell that the request was opened on
|
||||
* @param aRequest the request that was opened
|
||||
*/
|
||||
NS_IMETHOD OnLinkClickSync(nsIContent* aContent,
|
||||
nsLinkVerb aVerb,
|
||||
const PRUnichar* aURLSpec,
|
||||
const PRUnichar* aTargetSpec,
|
||||
nsIInputStream* aPostDataStream = 0,
|
||||
nsIInputStream* aHeadersDataStream = 0,
|
||||
nsIDocShell** aDocShell = 0,
|
||||
nsIRequest** aRequest = 0) = 0;
|
||||
|
||||
/**
|
||||
* Process a mouse-over a link.
|
||||
*
|
||||
* @param aContent the linked content.
|
||||
* @param aURLSpec an absolute url spec that defines the destination for the
|
||||
* link
|
||||
* @param aTargetSpec indicates where the link is targeted (it may be an empty
|
||||
* string)
|
||||
*/
|
||||
NS_IMETHOD OnOverLink(nsIContent* aContent,
|
||||
const PRUnichar* aURLSpec,
|
||||
|
Loading…
Reference in New Issue
Block a user