| author | Masayuki Nakano <masayuki@d-toybox.com> |
| Tue, 19 Aug 2014 20:54:08 +0900 | |
| changeset 200359 | 99f640f313595fc5ce635439fbeb9571b7f36629 |
| parent 200358 | e8101d5f9defc1c3810c6074d6a3cf292447346d |
| child 200360 | 77bf46f52906ecd6c09a13539642be83471661a1 |
| push id | 27342 |
| push user | ryanvm@gmail.com |
| push date | Tue, 19 Aug 2014 20:23:11 +0000 |
| treeherder | mozilla-central@149d3ce6e020 [default view] [failures only] |
| perfherder | [talos] [build metrics] [platform microbench] (compared to previous push) |
| reviewers | ehsan |
| bugs | 1053048 |
| milestone | 34.0a1 |
| first release with | nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
|
| last release without | nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
|
--- a/content/html/content/src/nsTextEditorState.cpp +++ b/content/html/content/src/nsTextEditorState.cpp @@ -659,16 +659,18 @@ public: /** SetEditor gives an address to the editor that will be accessed * @param aEditor the editor this listener calls for editing operations */ void SetFrame(nsTextControlFrame *aFrame){mFrame = aFrame;} void SettingValue(bool aValue) { mSettingValue = aValue; } void SetValueChanged(bool aSetValueChanged) { mSetValueChanged = aSetValueChanged; } + bool IsInEditAction() const { return mInEditAction; } + NS_DECL_ISUPPORTS NS_DECL_NSISELECTIONLISTENER NS_DECL_NSIDOMEVENTLISTENER NS_DECL_NSIEDITOROBSERVER @@ -703,31 +705,36 @@ protected: * refrain from calling OnValueChanged. */ bool mSettingValue; /** * Whether we are in the process of a SetValue call that doesn't want * |SetValueChanged| to be called. */ bool mSetValueChanged; + /** + * mInEditAction is true while editor handling an edit action. + */ + bool mInEditAction; }; /* * nsTextInputListener implementation */ nsTextInputListener::nsTextInputListener(nsITextControlElement* aTxtCtrlElement) : mFrame(nullptr) , mTxtCtrlElement(aTxtCtrlElement) , mSelectionWasCollapsed(true) , mHadUndoItems(false) , mHadRedoItems(false) , mSettingValue(false) , mSetValueChanged(true) +, mInEditAction(false) { } nsTextInputListener::~nsTextInputListener() { } NS_IMPL_ISUPPORTS(nsTextInputListener, @@ -884,16 +891,18 @@ nsTextInputListener::HandleEvent(nsIDOME return NS_OK; } // BEGIN nsIEditorObserver NS_IMETHODIMP nsTextInputListener::EditAction() { + mInEditAction = false; + nsWeakFrame weakFrame = mFrame; nsITextControlFrame* frameBase = do_QueryFrame(mFrame); nsTextControlFrame* frame = static_cast<nsTextControlFrame*> (frameBase); NS_ASSERTION(frame, "Where is our frame?"); // // Update the undo / redo menus // @@ -929,22 +938,24 @@ nsTextInputListener::EditAction() } return NS_OK; } NS_IMETHODIMP nsTextInputListener::BeforeEditAction() { + mInEditAction = true; return NS_OK; } NS_IMETHODIMP nsTextInputListener::CancelEditAction() { + mInEditAction = false; return NS_OK; } // END nsIEditorObserver nsresult nsTextInputListener::UpdateTextInputCommands(const nsAString& commandsToUpdate, @@ -1513,16 +1524,23 @@ void nsTextEditorState::UnbindFromFrame(nsTextControlFrame* aFrame) { NS_ENSURE_TRUE_VOID(mBoundFrame); // If it was, however, it should be unbounded from the same frame. NS_ASSERTION(!aFrame || aFrame == mBoundFrame, "Unbinding from the wrong frame"); NS_ENSURE_TRUE_VOID(!aFrame || aFrame == mBoundFrame); + // If the editor is modified, we need to notify it here because editor may be + // destroyed before EditAction() is called if selection listener causes + // flushing layout. + if (mTextListener && mTextListener->IsInEditAction()) { + mTextListener->EditAction(); + } + // We need to start storing the value outside of the editor if we're not // going to use it anymore, so retrieve it for now. nsAutoString value; GetValue(value, true); if (mRestoringSelection) { mRestoringSelection->Revoke(); mRestoringSelection = nullptr;