From 7d82e6658486e49bbbe823faeef83a4ab05641da Mon Sep 17 00:00:00 2001 From: Andrea Marchesini Date: Sat, 7 Dec 2013 12:09:14 +0000 Subject: [PATCH] Bug 946479 - nsIFilePickers/nnsIColorPicker cannot run in parallel for a single HTMLInputElement, r=bz --- content/html/content/src/HTMLInputElement.cpp | 37 ++++++++++++++++++- content/html/content/src/HTMLInputElement.h | 4 ++ 2 files changed, 39 insertions(+), 2 deletions(-) diff --git a/content/html/content/src/HTMLInputElement.cpp b/content/html/content/src/HTMLInputElement.cpp index 806363da52ff..a44d0cc45a08 100644 --- a/content/html/content/src/HTMLInputElement.cpp +++ b/content/html/content/src/HTMLInputElement.cpp @@ -614,6 +614,8 @@ private: NS_IMETHODIMP HTMLInputElement::nsFilePickerShownCallback::Done(int16_t aResult) { + mInput->PickerClosed(); + if (aResult == nsIFilePicker::returnCancel) { return NS_OK; } @@ -796,6 +798,8 @@ nsColorPickerShownCallback::Done(const nsAString& aColor) */ nsresult rv = NS_OK; + mInput->PickerClosed(); + if (!aColor.IsEmpty()) { UpdateInternal(aColor, false); } @@ -839,6 +843,11 @@ HTMLInputElement::IsPopupBlocked() const nsresult HTMLInputElement::InitColorPicker() { + if (mPickerRunning) { + NS_WARNING("Just one nsIColorPicker is allowed"); + return NS_ERROR_FAILURE; + } + nsCOMPtr doc = OwnerDoc(); nsCOMPtr win = doc->GetWindow(); @@ -869,12 +878,22 @@ HTMLInputElement::InitColorPicker() nsCOMPtr callback = new nsColorPickerShownCallback(this, colorPicker); - return colorPicker->Open(callback); + rv = colorPicker->Open(callback); + if (NS_SUCCEEDED(rv)) { + mPickerRunning = true; + } + + return rv; } nsresult HTMLInputElement::InitFilePicker(FilePickerType aType) { + if (mPickerRunning) { + NS_WARNING("Just one nsIFilePicker is allowed"); + return NS_ERROR_FAILURE; + } + // Get parent nsPIDOMWindow object. nsCOMPtr doc = OwnerDoc(); @@ -955,10 +974,16 @@ HTMLInputElement::InitFilePicker(FilePickerType aType) } } - return filePicker->Open(callback); + rv = filePicker->Open(callback); + if (NS_SUCCEEDED(rv)) { + mPickerRunning = true; + } + + return rv; } HTMLInputElement::gUploadLastDir->FetchDirectoryAndDisplayPicker(doc, filePicker, callback); + mPickerRunning = true; return NS_OK; } @@ -1094,6 +1119,8 @@ HTMLInputElement::HTMLInputElement(already_AddRefed aNodeInfo, , mIsDraggingRange(false) , mProgressTimerIsActive(false) , mNumberControlSpinnerIsSpinning(false) + , mNumberControlSpinnerSpinsUp(false) + , mPickerRunning(false) { // We are in a type=text so we now we currenty need a nsTextEditorState. mInputData.mState = new nsTextEditorState(this); @@ -7178,6 +7205,12 @@ HTMLInputElement::UpdateHasRange() } } +void +HTMLInputElement::PickerClosed() +{ + mPickerRunning = false; +} + JSObject* HTMLInputElement::WrapNode(JSContext* aCx, JS::Handle aScope) { diff --git a/content/html/content/src/HTMLInputElement.h b/content/html/content/src/HTMLInputElement.h index a6fd14a866cb..3b2392ff8528 100644 --- a/content/html/content/src/HTMLInputElement.h +++ b/content/html/content/src/HTMLInputElement.h @@ -203,6 +203,9 @@ public: void SetFiles(const nsTArray >& aFiles, bool aSetValueChanged); void SetFiles(nsIDOMFileList* aFiles, bool aSetValueChanged); + // Called when a nsIFilePicker or a nsIColorPicker terminate. + void PickerClosed(); + void SetCheckedChangedInternal(bool aCheckedChanged); bool GetCheckedChanged() const { return mCheckedChanged; @@ -1267,6 +1270,7 @@ protected: bool mProgressTimerIsActive : 1; bool mNumberControlSpinnerIsSpinning : 1; bool mNumberControlSpinnerSpinsUp : 1; + bool mPickerRunning : 1; private: static void MapAttributesIntoRule(const nsMappedAttributes* aAttributes,