NS_IMETHODIMP InsertNodeTransaction::DoTransaction() { if (NS_WARN_IF(!mEditorBase) || NS_WARN_IF(!mContentToInsert) || NS_WARN_IF(!mPointToInsert.IsSet())) { return NS_ERROR_NOT_INITIALIZED; } if (!mPointToInsert.IsSetAndValid()) { // It seems that DOM tree has been changed after first DoTransaction() // and current RedoTranaction() call. if (mPointToInsert.GetChild()) { EditorDOMPoint newPointToInsert(mPointToInsert.GetChild()); if (!newPointToInsert.IsSet()) { // The insertion point has been removed from the DOM tree. // In this case, we should append the node to the container instead. newPointToInsert.SetToEndOf(mPointToInsert.GetContainer()); if (NS_WARN_IF(!newPointToInsert.IsSet())) { return NS_ERROR_FAILURE; } } mPointToInsert = newPointToInsert; } else { mPointToInsert.SetToEndOf(mPointToInsert.GetContainer()); if (NS_WARN_IF(!mPointToInsert.IsSet())) { return NS_ERROR_FAILURE; } } } mEditorBase->MarkNodeDirty(GetAsDOMNode(mContentToInsert)); ErrorResult error; mPointToInsert.GetContainer()->InsertBefore(*mContentToInsert, mPointToInsert.GetChild(), error); error.WouldReportJSException(); if (NS_WARN_IF(error.Failed())) { return error.StealNSResult(); } // Only set selection to insertion point if editor gives permission if (mEditorBase->GetShouldTxnSetSelection()) { RefPtr<Selection> selection = mEditorBase->GetSelection(); if (NS_WARN_IF(!selection)) { return NS_ERROR_FAILURE; } // Place the selection just after the inserted element EditorRawDOMPoint afterInsertedNode(mContentToInsert); DebugOnly<bool> advanced = afterInsertedNode.AdvanceOffset(); NS_WARNING_ASSERTION(advanced, "Failed to advance offset after the inserted node"); selection->Collapse(afterInsertedNode, error); if (NS_WARN_IF(error.Failed())) { error.SuppressException(); } } return NS_OK; }
NS_IMETHODIMP HTMLEditor::GetResizedObject(nsIDOMElement** aResizedObject) { nsCOMPtr<nsIDOMElement> ret = static_cast<nsIDOMElement*>(GetAsDOMNode(mResizedObject)); ret.forget(aResizedObject); return NS_OK; }
NS_IMETHODIMP HTMLEditor::DoInlineTableEditingAction(nsIDOMElement* aElement) { NS_ENSURE_ARG_POINTER(aElement); bool anonElement = false; if (aElement && NS_SUCCEEDED(aElement->HasAttribute(NS_LITERAL_STRING("_moz_anonclass"), &anonElement)) && anonElement) { nsAutoString anonclass; nsresult rv = aElement->GetAttribute(NS_LITERAL_STRING("_moz_anonclass"), anonclass); NS_ENSURE_SUCCESS(rv, rv); if (!StringBeginsWith(anonclass, NS_LITERAL_STRING("mozTable"))) return NS_OK; nsCOMPtr<nsIDOMNode> tableNode = GetEnclosingTable(mInlineEditedCell); nsCOMPtr<nsIDOMElement> tableElement = do_QueryInterface(tableNode); int32_t rowCount, colCount; rv = GetTableSize(tableElement, &rowCount, &colCount); NS_ENSURE_SUCCESS(rv, rv); bool hideUI = false; bool hideResizersWithInlineTableUI = (GetAsDOMNode(mResizedObject) == tableElement); if (anonclass.EqualsLiteral("mozTableAddColumnBefore")) InsertTableColumn(1, false); else if (anonclass.EqualsLiteral("mozTableAddColumnAfter")) InsertTableColumn(1, true); else if (anonclass.EqualsLiteral("mozTableAddRowBefore")) InsertTableRow(1, false); else if (anonclass.EqualsLiteral("mozTableAddRowAfter")) InsertTableRow(1, true); else if (anonclass.EqualsLiteral("mozTableRemoveColumn")) { DeleteTableColumn(1); #ifndef DISABLE_TABLE_DELETION hideUI = (colCount == 1); #endif } else if (anonclass.EqualsLiteral("mozTableRemoveRow")) { DeleteTableRow(1); #ifndef DISABLE_TABLE_DELETION hideUI = (rowCount == 1); #endif } else return NS_OK; if (hideUI) { HideInlineTableEditingUI(); if (hideResizersWithInlineTableUI) HideResizers(); } } return NS_OK; }
NS_IMETHODIMP TextEditRules::AfterEdit(EditAction action, nsIEditor::EDirection aDirection) { if (mLockRulesSniffing) { return NS_OK; } AutoLockRulesSniffing lockIt(this); NS_PRECONDITION(mActionNesting>0, "bad action nesting!"); if (!--mActionNesting) { NS_ENSURE_STATE(mTextEditor); RefPtr<Selection> selection = mTextEditor->GetSelection(); NS_ENSURE_STATE(selection); NS_ENSURE_STATE(mTextEditor); nsresult rv = mTextEditor->HandleInlineSpellCheck(action, selection, GetAsDOMNode(mCachedSelectionNode), mCachedSelectionOffset, nullptr, 0, nullptr, 0); NS_ENSURE_SUCCESS(rv, rv); // no longer uses mCachedSelectionNode, so release it. mCachedSelectionNode = nullptr; // if only trailing <br> remaining remove it rv = RemoveRedundantTrailingBR(); if (NS_FAILED(rv)) { return rv; } // detect empty doc rv = CreateBogusNodeIfNeeded(selection); NS_ENSURE_SUCCESS(rv, rv); // ensure trailing br node rv = CreateTrailingBRIfNeeded(); NS_ENSURE_SUCCESS(rv, rv); // collapse the selection to the trailing BR if it's at the end of our text node CollapseSelectionToTrailingBRIfNeeded(selection); } return NS_OK; }