зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1484113 - part 1: Create HTMLEditor::GetFirstTableRowElement() for internal use of nsITableEditor::GetFirstRow() r=m_kato
nsITableEditor::GetFirstRow() is an XPCOM method, so, for internal use, we should create non-virtual method, that is GetFirstTableRowElement(). This patch makes it never return NS_SUCCESS_EDITOR_ELEMENT_NOT_FOUND since nobody refers it and it's detectable. If the method returns nullptr without error, it's the case of NS_SUCCESS_EDITOR_ELEMENT_NOT_FOUND. Additionally, this patch changes the return type of GetFirstRow() from Node to Element since it always return an Element node if not null. Differential Revision: https://phabricator.services.mozilla.com/D3780 --HG-- extra : moz-landing-system : lando
This commit is contained in:
Родитель
56de772ab3
Коммит
57ac6bcbf2
|
@ -2561,7 +2561,7 @@ HTMLEditor::Align(const nsAString& aAlignType)
|
||||||
|
|
||||||
Element*
|
Element*
|
||||||
HTMLEditor::GetElementOrParentByTagName(const nsAtom& aTagName,
|
HTMLEditor::GetElementOrParentByTagName(const nsAtom& aTagName,
|
||||||
nsINode* aNode)
|
nsINode* aNode) const
|
||||||
{
|
{
|
||||||
MOZ_ASSERT(&aTagName != nsGkAtoms::_empty);
|
MOZ_ASSERT(&aTagName != nsGkAtoms::_empty);
|
||||||
|
|
||||||
|
@ -2577,7 +2577,7 @@ HTMLEditor::GetElementOrParentByTagName(const nsAtom& aTagName,
|
||||||
|
|
||||||
Element*
|
Element*
|
||||||
HTMLEditor::GetElementOrParentByTagNameAtSelection(Selection& aSelection,
|
HTMLEditor::GetElementOrParentByTagNameAtSelection(Selection& aSelection,
|
||||||
const nsAtom& aTagName)
|
const nsAtom& aTagName) const
|
||||||
{
|
{
|
||||||
MOZ_ASSERT(&aTagName != nsGkAtoms::_empty);
|
MOZ_ASSERT(&aTagName != nsGkAtoms::_empty);
|
||||||
|
|
||||||
|
@ -2605,7 +2605,7 @@ HTMLEditor::GetElementOrParentByTagNameAtSelection(Selection& aSelection,
|
||||||
|
|
||||||
Element*
|
Element*
|
||||||
HTMLEditor::GetElementOrParentByTagNameInternal(const nsAtom& aTagName,
|
HTMLEditor::GetElementOrParentByTagNameInternal(const nsAtom& aTagName,
|
||||||
nsINode& aNode)
|
nsINode& aNode) const
|
||||||
{
|
{
|
||||||
MOZ_ASSERT(&aTagName != nsGkAtoms::_empty);
|
MOZ_ASSERT(&aTagName != nsGkAtoms::_empty);
|
||||||
|
|
||||||
|
|
|
@ -402,7 +402,7 @@ public:
|
||||||
* an Element. Otherwise, nullptr.
|
* an Element. Otherwise, nullptr.
|
||||||
*/
|
*/
|
||||||
Element*
|
Element*
|
||||||
GetElementOrParentByTagName(const nsAtom& aTagName, nsINode* aNode);
|
GetElementOrParentByTagName(const nsAtom& aTagName, nsINode* aNode) const;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get an active editor's editing host in DOM window. If this editor isn't
|
* Get an active editor's editing host in DOM window. If this editor isn't
|
||||||
|
@ -912,7 +912,7 @@ protected: // Shouldn't be used by friend classes
|
||||||
*/
|
*/
|
||||||
Element*
|
Element*
|
||||||
GetElementOrParentByTagNameAtSelection(Selection& aSelection,
|
GetElementOrParentByTagNameAtSelection(Selection& aSelection,
|
||||||
const nsAtom& aTagName);
|
const nsAtom& aTagName) const;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* GetElementOrParentByTagNameInternal() looks for an element node whose
|
* GetElementOrParentByTagNameInternal() looks for an element node whose
|
||||||
|
@ -933,7 +933,7 @@ protected: // Shouldn't be used by friend classes
|
||||||
*/
|
*/
|
||||||
Element*
|
Element*
|
||||||
GetElementOrParentByTagNameInternal(const nsAtom& aTagName,
|
GetElementOrParentByTagNameInternal(const nsAtom& aTagName,
|
||||||
nsINode& aNode);
|
nsINode& aNode) const;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* GetSelectedElement() returns an element node which is in first range of
|
* GetSelectedElement() returns an element node which is in first range of
|
||||||
|
@ -972,6 +972,26 @@ protected: // Shouldn't be used by friend classes
|
||||||
const nsAtom* aTagName,
|
const nsAtom* aTagName,
|
||||||
ErrorResult& aRv);
|
ErrorResult& aRv);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* GetFirstTableRowElement() returns the first <tr> element in the most
|
||||||
|
* nearest ancestor of aTableOrElementInTable or itself.
|
||||||
|
*
|
||||||
|
* @param aTableOrElementInTable <table> element or another element.
|
||||||
|
* If this is a <table> element, returns
|
||||||
|
* first <tr> element in it. Otherwise,
|
||||||
|
* returns first <tr> element in nearest
|
||||||
|
* ancestor <table> element.
|
||||||
|
* @param aRv Returns an error code. When
|
||||||
|
* aTableOrElementInTable is neither
|
||||||
|
* <table> nor in a <table> element,
|
||||||
|
* returns NS_ERROR_FAILURE.
|
||||||
|
* However, if <table> does not have
|
||||||
|
* <tr> element, returns NS_OK.
|
||||||
|
*/
|
||||||
|
Element*
|
||||||
|
GetFirstTableRowElement(Element& aTableOrElementInTable,
|
||||||
|
ErrorResult& aRv) const;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* PasteInternal() pasts text with replacing selected content.
|
* PasteInternal() pasts text with replacing selected content.
|
||||||
* This tries to dispatch ePaste event first. If its defaultPrevent() is
|
* This tries to dispatch ePaste event first. If its defaultPrevent() is
|
||||||
|
|
|
@ -221,52 +221,60 @@ HTMLEditor::InsertTableCell(int32_t aNumber,
|
||||||
}
|
}
|
||||||
|
|
||||||
NS_IMETHODIMP
|
NS_IMETHODIMP
|
||||||
HTMLEditor::GetFirstRow(Element* aTableElement,
|
HTMLEditor::GetFirstRow(Element* aTableOrElementInTable,
|
||||||
nsINode** aRowNode)
|
Element** aFirstRowElement)
|
||||||
{
|
{
|
||||||
if (NS_WARN_IF(!aTableElement) || NS_WARN_IF(!aRowNode)) {
|
if (NS_WARN_IF(!aTableOrElementInTable) || NS_WARN_IF(!aFirstRowElement)) {
|
||||||
return NS_ERROR_INVALID_ARG;
|
return NS_ERROR_INVALID_ARG;
|
||||||
}
|
}
|
||||||
|
ErrorResult error;
|
||||||
|
RefPtr<Element> firstRowElement =
|
||||||
|
GetFirstTableRowElement(*aTableOrElementInTable, error);
|
||||||
|
if (NS_WARN_IF(error.Failed())) {
|
||||||
|
return error.StealNSResult();
|
||||||
|
}
|
||||||
|
firstRowElement.forget(aFirstRowElement);
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
*aRowNode = nullptr;
|
Element*
|
||||||
|
HTMLEditor::GetFirstTableRowElement(Element& aTableOrElementInTable,
|
||||||
|
ErrorResult& aRv) const
|
||||||
|
{
|
||||||
|
MOZ_ASSERT(!aRv.Failed());
|
||||||
|
|
||||||
Element* tableElement =
|
Element* tableElement =
|
||||||
GetElementOrParentByTagNameInternal(*nsGkAtoms::table, *aTableElement);
|
GetElementOrParentByTagNameInternal(*nsGkAtoms::table,
|
||||||
|
aTableOrElementInTable);
|
||||||
|
// If the element is not in <table>, return error.
|
||||||
if (NS_WARN_IF(!tableElement)) {
|
if (NS_WARN_IF(!tableElement)) {
|
||||||
return NS_ERROR_FAILURE;
|
aRv.Throw(NS_ERROR_FAILURE);
|
||||||
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
nsCOMPtr<nsIContent> tableChild = tableElement->GetFirstChild();
|
for (nsIContent* tableChild = tableElement->GetFirstChild();
|
||||||
while (tableChild) {
|
tableChild;
|
||||||
|
tableChild = tableChild->GetNextSibling()) {
|
||||||
if (tableChild->IsHTMLElement(nsGkAtoms::tr)) {
|
if (tableChild->IsHTMLElement(nsGkAtoms::tr)) {
|
||||||
// Found a row directly under <table>
|
// Found a row directly under <table>
|
||||||
tableChild.forget(aRowNode);
|
return tableChild->AsElement();
|
||||||
return NS_OK;
|
|
||||||
}
|
}
|
||||||
// Look for row in one of the row container elements
|
// <table> can have table section elements like <tbody>. <tr> elements
|
||||||
|
// may be children of them.
|
||||||
if (tableChild->IsAnyOfHTMLElements(nsGkAtoms::tbody,
|
if (tableChild->IsAnyOfHTMLElements(nsGkAtoms::tbody,
|
||||||
nsGkAtoms::thead,
|
nsGkAtoms::thead,
|
||||||
nsGkAtoms::tfoot)) {
|
nsGkAtoms::tfoot)) {
|
||||||
nsCOMPtr<nsIContent> rowNode = tableChild->GetFirstChild();
|
for (nsIContent* tableSectionChild = tableChild->GetFirstChild();
|
||||||
|
tableSectionChild;
|
||||||
// We can encounter textnodes here -- must find a row
|
tableSectionChild = tableSectionChild->GetNextSibling()) {
|
||||||
while (rowNode && !HTMLEditUtils::IsTableRow(rowNode)) {
|
if (tableSectionChild->IsHTMLElement(nsGkAtoms::tr)) {
|
||||||
rowNode = rowNode->GetNextSibling();
|
return tableSectionChild->AsElement();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (rowNode) {
|
|
||||||
rowNode.forget(aRowNode);
|
|
||||||
return NS_OK;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// Here if table child was a CAPTION or COLGROUP
|
|
||||||
// or child of a row parent wasn't a row (bad HTML?),
|
|
||||||
// or first child was a textnode
|
|
||||||
// Look in next table child
|
|
||||||
tableChild = tableChild->GetNextSibling();
|
|
||||||
}
|
}
|
||||||
// If here, row was not found
|
// Don't return error when there is no <tr> element in the <table>.
|
||||||
return NS_SUCCESS_EDITOR_ELEMENT_NOT_FOUND;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
NS_IMETHODIMP
|
NS_IMETHODIMP
|
||||||
|
@ -442,9 +450,10 @@ HTMLEditor::InsertTableColumn(int32_t aNumber,
|
||||||
} else {
|
} else {
|
||||||
// Get current row and append new cells after last cell in row
|
// Get current row and append new cells after last cell in row
|
||||||
if (!rowIndex) {
|
if (!rowIndex) {
|
||||||
rv = GetFirstRow(table, getter_AddRefs(rowNode));
|
ErrorResult error;
|
||||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
rowNode = GetFirstTableRowElement(*table, error);
|
||||||
return rv;
|
if (NS_WARN_IF(error.Failed())) {
|
||||||
|
return error.StealNSResult();
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
nsCOMPtr<nsINode> nextRow;
|
nsCOMPtr<nsINode> nextRow;
|
||||||
|
|
|
@ -203,14 +203,25 @@ interface nsITableEditor : nsISupports
|
||||||
out long aActualRowSpan, out long aActualColSpan,
|
out long aActualRowSpan, out long aActualColSpan,
|
||||||
out boolean aIsSelected);
|
out boolean aIsSelected);
|
||||||
|
|
||||||
/** Get the first row element in a table
|
/**
|
||||||
*
|
* getFirstRow() returns first <tr> element in a <table> element.
|
||||||
* @return The row at the requested index
|
*
|
||||||
* Returns null if there are no rows in table
|
* @param aTableOrElementInTable If a <table> element, returns its first
|
||||||
* (in C++ returns: NS_EDITOR_ELEMENT_NOT_FOUND if an element is not found
|
* <tr> element.
|
||||||
* passes NS_SUCCEEDED macro)
|
* If another element, looks for nearest
|
||||||
*/
|
* ancestor <table> element first. Then,
|
||||||
Node getFirstRow(in Element aTableElement);
|
* return its first <tr> element.
|
||||||
|
* @return <tr> element in the <table> element.
|
||||||
|
* If <table> element is not found, this
|
||||||
|
* throws an exception.
|
||||||
|
* If there is a <table> element but it
|
||||||
|
* does not have <tr> elements, returns
|
||||||
|
* null without throwing exception.
|
||||||
|
* Note that this may return anonymous <tr>
|
||||||
|
* element if <table> has one or more cells
|
||||||
|
* but <tr> element is not in the source.
|
||||||
|
*/
|
||||||
|
Element getFirstRow(in Element aTableElement);
|
||||||
|
|
||||||
/** Get the next row element starting the search from aTableElement
|
/** Get the next row element starting the search from aTableElement
|
||||||
*
|
*
|
||||||
|
|
Загрузка…
Ссылка в новой задаче