From d0e7a72d94fc3cc97966d672a3b20ca1207d9400 Mon Sep 17 00:00:00 2001 From: Masayuki Nakano Date: Thu, 12 Sep 2019 07:27:30 +0000 Subject: [PATCH] Bug 1574852 - part 101: Move `HTMLEditRules::DidDeleteSelection()` to `HTMLEditor` r=m_kato Differential Revision: https://phabricator.services.mozilla.com/D45295 --HG-- extra : moz-landing-system : lando --- editor/libeditor/HTMLEditRules.cpp | 93 ++++++++++++++---------------- editor/libeditor/HTMLEditRules.h | 7 --- editor/libeditor/HTMLEditor.h | 10 ++++ editor/libeditor/TextEditRules.cpp | 2 - editor/libeditor/TextEditor.cpp | 20 +++++-- 5 files changed, 69 insertions(+), 63 deletions(-) diff --git a/editor/libeditor/HTMLEditRules.cpp b/editor/libeditor/HTMLEditRules.cpp index ddd21723205f..bc20f1d892a5 100644 --- a/editor/libeditor/HTMLEditRules.cpp +++ b/editor/libeditor/HTMLEditRules.cpp @@ -490,10 +490,13 @@ nsresult HTMLEditor::OnEndHandlingTopLevelEditSubActionInternal() { // Note we only want to do this if the overall operation was deletion, // not if deletion was done along the way for // EditSubAction::eInsertHTMLSource, EditSubAction::eInsertText, etc. - // That's why this is here rather than DidDeleteSelection(). + // That's why this is here rather than DeleteSelectionAsSubAction(). // However, we shouldn't insert
elements if we've already removed // empty block parents because users may want to disappear the line by // the deletion. + // XXX We should make HandleDeleteSelection() store expected container + // for handling this here since we cannot trust current selection is + // collapsed at deleted point. if (GetTopLevelEditSubAction() == EditSubAction::eDeleteSelectedContent && TopLevelEditSubActionDataRef().mDidDeleteNonCollapsedRange && !TopLevelEditSubActionDataRef().mDidDeleteEmptyParentBlocks) { @@ -833,8 +836,6 @@ nsresult HTMLEditRules::DidDoAction(EditSubActionInfo& aInfo, case EditSubAction::eInsertLineBreak: case EditSubAction::eInsertTextComingFromIME: return NS_OK; - case EditSubAction::eDeleteSelectedContent: - return DidDeleteSelection(); case EditSubAction::eInsertElement: case EditSubAction::eInsertQuotedText: return NS_OK; @@ -842,6 +843,7 @@ nsresult HTMLEditRules::DidDoAction(EditSubActionInfo& aInfo, case EditSubAction::eCreateOrChangeList: case EditSubAction::eCreateOrRemoveBlock: case EditSubAction::eDecreaseZIndex: + case EditSubAction::eDeleteSelectedContent: case EditSubAction::eIncreaseZIndex: case EditSubAction::eIndent: case EditSubAction::eInsertHTMLSource: @@ -4058,57 +4060,48 @@ nsresult HTMLEditor::DeleteElementsExceptTableRelatedElements(nsINode& aNode) { return NS_OK; } -nsresult HTMLEditRules::DidDeleteSelection() { - MOZ_ASSERT(IsEditorDataAvailable()); +nsresult HTMLEditor::DeleteMostAncestorMailCiteElementIfEmpty( + nsIContent& aContent) { + MOZ_ASSERT(IsEditActionDataAvailable()); - // find where we are - EditorDOMPoint atStartOfSelection( - EditorBase::GetStartPoint(*SelectionRefPtr())); - if (NS_WARN_IF(!atStartOfSelection.IsSet())) { - return NS_ERROR_FAILURE; + // The element must be `
` or + // ``. + RefPtr mailCiteElement = GetMostAncestorMailCiteElement(aContent); + if (!mailCiteElement) { + return NS_OK; } - - // find any enclosing mailcite - RefPtr citeNode = HTMLEditorRef().GetMostAncestorMailCiteElement( - *atStartOfSelection.GetContainer()); - if (citeNode) { - bool isEmpty = true, seenBR = false; - HTMLEditorRef().IsEmptyNodeImpl(citeNode, &isEmpty, true, true, false, - &seenBR); - if (isEmpty) { - EditorDOMPoint atCiteNode(citeNode); - { - AutoEditorDOMPointChildInvalidator lockOffset(atCiteNode); - nsresult rv = - MOZ_KnownLive(HTMLEditorRef()).DeleteNodeWithTransaction(*citeNode); - if (NS_WARN_IF(!CanHandleEditAction())) { - return NS_ERROR_EDITOR_DESTROYED; - } - if (NS_WARN_IF(NS_FAILED(rv))) { - return rv; - } - } - if (atCiteNode.IsSet() && seenBR) { - RefPtr brElement = - MOZ_KnownLive(HTMLEditorRef()) - .InsertBRElementWithTransaction(atCiteNode); - if (NS_WARN_IF(!CanHandleEditAction())) { - return NS_ERROR_EDITOR_DESTROYED; - } - if (NS_WARN_IF(!brElement)) { - return NS_ERROR_FAILURE; - } - IgnoredErrorResult error; - SelectionRefPtr()->Collapse(EditorRawDOMPoint(brElement), error); - if (NS_WARN_IF(!CanHandleEditAction())) { - return NS_ERROR_EDITOR_DESTROYED; - } - NS_WARNING_ASSERTION( - !error.Failed(), - "Failed to collapse selection at the new
element"); - } + bool isEmpty = true, seenBR = false; + IsEmptyNodeImpl(mailCiteElement, &isEmpty, true, true, false, &seenBR); + EditorDOMPoint atEmptyMailCiteElement(mailCiteElement); + { + AutoEditorDOMPointChildInvalidator lockOffset(atEmptyMailCiteElement); + nsresult rv = DeleteNodeWithTransaction(*mailCiteElement); + if (NS_WARN_IF(Destroyed())) { + return NS_ERROR_EDITOR_DESTROYED; + } + if (NS_WARN_IF(NS_FAILED(rv))) { + return rv; } } + + if (NS_WARN_IF(!atEmptyMailCiteElement.IsSet()) || !seenBR) { + return NS_OK; + } + + RefPtr brElement = + InsertBRElementWithTransaction(atEmptyMailCiteElement); + if (NS_WARN_IF(Destroyed())) { + return NS_ERROR_EDITOR_DESTROYED; + } + if (NS_WARN_IF(!brElement)) { + return NS_ERROR_FAILURE; + } + IgnoredErrorResult ignoredError; + SelectionRefPtr()->Collapse(EditorRawDOMPoint(brElement), ignoredError); + if (NS_WARN_IF(Destroyed())) { + return NS_ERROR_EDITOR_DESTROYED; + } + NS_WARNING_ASSERTION(!ignoredError.Failed(), "Selection::Collapse() failed"); return NS_OK; } diff --git a/editor/libeditor/HTMLEditRules.h b/editor/libeditor/HTMLEditRules.h index 1197d9161b0c..db8042e28bb7 100644 --- a/editor/libeditor/HTMLEditRules.h +++ b/editor/libeditor/HTMLEditRules.h @@ -106,13 +106,6 @@ class HTMLEditRules : public TextEditRules { return mData->HTMLEditorRef(); } - /** - * Called after deleting selected content. - * This method removes unnecessary empty nodes and/or inserts
if - * necessary. - */ - MOZ_CAN_RUN_SCRIPT MOZ_MUST_USE nsresult DidDeleteSelection(); - nsresult AppendInnerFormatNodes(nsTArray>& aArray, nsINode* aNode); nsresult GetFormatString(nsINode* aNode, nsAString& outFormat); diff --git a/editor/libeditor/HTMLEditor.h b/editor/libeditor/HTMLEditor.h index 9fb5103b9167..a993c36566c6 100644 --- a/editor/libeditor/HTMLEditor.h +++ b/editor/libeditor/HTMLEditor.h @@ -2274,6 +2274,16 @@ class HTMLEditor final : public TextEditor, HandleDeleteSelection(nsIEditor::EDirection aDirectionAndAmount, nsIEditor::EStripWrappers aStripWrappers); + /** + * DeleteMostAncestorMailCiteElementIfEmpty() deletes most ancestor + * mail cite element (`
` or + * ``, the former can be created with middle click + * paste with `Control` or `Command` even in the web) of aContent if it + * becomes empty. + */ + MOZ_CAN_RUN_SCRIPT MOZ_MUST_USE nsresult + DeleteMostAncestorMailCiteElementIfEmpty(nsIContent& aContent); + /** * LiftUpListItemElement() moves aListItemElement outside its parent. * If it's in a middle of a list element, the parent list element is split diff --git a/editor/libeditor/TextEditRules.cpp b/editor/libeditor/TextEditRules.cpp index 9f344c83f2c5..0172329c7709 100644 --- a/editor/libeditor/TextEditRules.cpp +++ b/editor/libeditor/TextEditRules.cpp @@ -261,8 +261,6 @@ nsresult TextEditRules::DidDoAction(EditSubActionInfo& aInfo, switch (aInfo.mEditSubAction) { case EditSubAction::eDeleteSelectedContent: - MOZ_ASSERT(!mIsHTMLEditRules); - return NS_OK; case EditSubAction::eInsertElement: case EditSubAction::eUndo: case EditSubAction::eRedo: diff --git a/editor/libeditor/TextEditor.cpp b/editor/libeditor/TextEditor.cpp index 7d05549579f7..5d6c674741b3 100644 --- a/editor/libeditor/TextEditor.cpp +++ b/editor/libeditor/TextEditor.cpp @@ -667,10 +667,22 @@ nsresult TextEditor::DeleteSelectionAsSubAction(EDirection aDirection, if (!handled) { rv = DeleteSelectionWithTransaction(aDirection, aStripWrappers); } - // post-process - rv = rules->DidDoAction(subActionInfo, rv); - if (NS_WARN_IF(NS_FAILED(rv))) { - return rv; + + if (AsHTMLEditor()) { + EditorDOMPoint atNewStartOfSelection( + EditorBase::GetStartPoint(*SelectionRefPtr())); + if (NS_WARN_IF(!atNewStartOfSelection.IsSet())) { + return NS_ERROR_FAILURE; + } + if (atNewStartOfSelection.GetContainerAsContent()) { + nsresult rv = + MOZ_KnownLive(AsHTMLEditor()) + ->DeleteMostAncestorMailCiteElementIfEmpty(MOZ_KnownLive( + *atNewStartOfSelection.GetContainerAsContent())); + if (NS_WARN_IF(NS_FAILED(rv))) { + return rv; + } + } } // XXX This is odd. We just tries to remove empty text node here but we