Bug 1885602 - Part 5: Implement navigating to the SUMO help topic from the menu heade...
[gecko.git] / dom / html / HTMLTableRowElement.cpp
blobaf36dc52650221af675ea67b78f5f92bbe80641d
1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* vim: set ts=8 sts=2 et sw=2 tw=80: */
3 /* This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this
5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
7 #include "mozilla/dom/HTMLTableRowElement.h"
8 #include "mozilla/dom/HTMLTableElement.h"
9 #include "mozilla/MappedDeclarationsBuilder.h"
10 #include "nsAttrValueInlines.h"
11 #include "mozilla/dom/BindingUtils.h"
12 #include "mozilla/dom/HTMLTableRowElementBinding.h"
13 #include "nsContentList.h"
14 #include "nsContentUtils.h"
16 NS_IMPL_NS_NEW_HTML_ELEMENT(TableRow)
18 namespace mozilla::dom {
20 HTMLTableRowElement::~HTMLTableRowElement() = default;
22 JSObject* HTMLTableRowElement::WrapNode(JSContext* aCx,
23 JS::Handle<JSObject*> aGivenProto) {
24 return HTMLTableRowElement_Binding::Wrap(aCx, this, aGivenProto);
27 NS_IMPL_CYCLE_COLLECTION_INHERITED(HTMLTableRowElement, nsGenericHTMLElement,
28 mCells)
30 NS_IMPL_ISUPPORTS_CYCLE_COLLECTION_INHERITED_0(HTMLTableRowElement,
31 nsGenericHTMLElement)
33 NS_IMPL_ELEMENT_CLONE(HTMLTableRowElement)
35 // protected method
36 HTMLTableSectionElement* HTMLTableRowElement::GetSection() const {
37 nsIContent* parent = GetParent();
38 if (parent && parent->IsAnyOfHTMLElements(nsGkAtoms::thead, nsGkAtoms::tbody,
39 nsGkAtoms::tfoot)) {
40 return static_cast<HTMLTableSectionElement*>(parent);
42 return nullptr;
45 // protected method
46 HTMLTableElement* HTMLTableRowElement::GetTable() const {
47 nsIContent* parent = GetParent();
48 if (!parent) {
49 return nullptr;
52 // We may not be in a section
53 HTMLTableElement* table = HTMLTableElement::FromNode(parent);
54 if (table) {
55 return table;
58 return HTMLTableElement::FromNodeOrNull(parent->GetParent());
61 int32_t HTMLTableRowElement::RowIndex() const {
62 HTMLTableElement* table = GetTable();
63 if (!table) {
64 return -1;
67 nsIHTMLCollection* rows = table->Rows();
69 uint32_t numRows = rows->Length();
71 for (uint32_t i = 0; i < numRows; i++) {
72 if (rows->GetElementAt(i) == this) {
73 return i;
77 return -1;
80 int32_t HTMLTableRowElement::SectionRowIndex() const {
81 HTMLTableSectionElement* section = GetSection();
82 if (!section) {
83 return -1;
86 nsCOMPtr<nsIHTMLCollection> coll = section->Rows();
87 uint32_t numRows = coll->Length();
88 for (uint32_t i = 0; i < numRows; i++) {
89 if (coll->GetElementAt(i) == this) {
90 return i;
94 return -1;
97 static bool IsCell(Element* aElement, int32_t aNamespaceID, nsAtom* aAtom,
98 void* aData) {
99 return aElement->IsAnyOfHTMLElements(nsGkAtoms::td, nsGkAtoms::th);
102 nsIHTMLCollection* HTMLTableRowElement::Cells() {
103 if (!mCells) {
104 mCells = new nsContentList(this, IsCell,
105 nullptr, // destroy func
106 nullptr, // closure data
107 false, nullptr, kNameSpaceID_XHTML, false);
110 return mCells;
113 already_AddRefed<nsGenericHTMLElement> HTMLTableRowElement::InsertCell(
114 int32_t aIndex, ErrorResult& aError) {
115 if (aIndex < -1) {
116 aError.Throw(NS_ERROR_DOM_INDEX_SIZE_ERR);
117 return nullptr;
120 // Make sure mCells is initialized.
121 nsIHTMLCollection* cells = Cells();
123 NS_ASSERTION(mCells, "How did that happen?");
125 nsCOMPtr<nsINode> nextSibling;
126 // -1 means append, so should use null nextSibling
127 if (aIndex != -1) {
128 nextSibling = cells->Item(aIndex);
129 // Check whether we're inserting past end of list. We want to avoid doing
130 // this unless we really have to, since this has to walk all our kids. If
131 // we have a nextSibling, we're clearly not past end of list.
132 if (!nextSibling) {
133 uint32_t cellCount = cells->Length();
134 if (aIndex > int32_t(cellCount)) {
135 aError.Throw(NS_ERROR_DOM_INDEX_SIZE_ERR);
136 return nullptr;
141 // create the cell
142 RefPtr<mozilla::dom::NodeInfo> nodeInfo;
143 nsContentUtils::QNameChanged(mNodeInfo, nsGkAtoms::td,
144 getter_AddRefs(nodeInfo));
146 RefPtr<nsGenericHTMLElement> cell =
147 NS_NewHTMLTableCellElement(nodeInfo.forget());
148 if (!cell) {
149 aError.Throw(NS_ERROR_OUT_OF_MEMORY);
150 return nullptr;
153 nsINode::InsertBefore(*cell, nextSibling, aError);
155 return cell.forget();
158 void HTMLTableRowElement::DeleteCell(int32_t aValue, ErrorResult& aError) {
159 if (aValue < -1) {
160 aError.Throw(NS_ERROR_DOM_INDEX_SIZE_ERR);
161 return;
164 nsIHTMLCollection* cells = Cells();
166 uint32_t refIndex;
167 if (aValue == -1) {
168 refIndex = cells->Length();
169 if (refIndex == 0) {
170 return;
173 --refIndex;
174 } else {
175 refIndex = (uint32_t)aValue;
178 nsCOMPtr<nsINode> cell = cells->Item(refIndex);
179 if (!cell) {
180 aError.Throw(NS_ERROR_DOM_INDEX_SIZE_ERR);
181 return;
184 nsINode::RemoveChild(*cell, aError);
187 bool HTMLTableRowElement::ParseAttribute(int32_t aNamespaceID,
188 nsAtom* aAttribute,
189 const nsAString& aValue,
190 nsIPrincipal* aMaybeScriptedPrincipal,
191 nsAttrValue& aResult) {
193 * ignore these attributes, stored simply as strings
195 * ch
198 if (aNamespaceID == kNameSpaceID_None) {
199 if (aAttribute == nsGkAtoms::height) {
200 // Per spec should be ParseNonzeroHTMLDimension, but no browsers do that.
201 // See https://github.com/whatwg/html/issues/4716
202 return aResult.ParseHTMLDimension(aValue);
204 if (aAttribute == nsGkAtoms::align) {
205 return ParseTableCellHAlignValue(aValue, aResult);
207 if (aAttribute == nsGkAtoms::bgcolor) {
208 return aResult.ParseColor(aValue);
210 if (aAttribute == nsGkAtoms::valign) {
211 return ParseTableVAlignValue(aValue, aResult);
215 return nsGenericHTMLElement::ParseBackgroundAttribute(
216 aNamespaceID, aAttribute, aValue, aResult) ||
217 nsGenericHTMLElement::ParseAttribute(aNamespaceID, aAttribute, aValue,
218 aMaybeScriptedPrincipal, aResult);
221 void HTMLTableRowElement::MapAttributesIntoRule(
222 MappedDeclarationsBuilder& aBuilder) {
223 nsGenericHTMLElement::MapHeightAttributeInto(aBuilder);
224 nsGenericHTMLElement::MapDivAlignAttributeInto(aBuilder);
225 nsGenericHTMLElement::MapVAlignAttributeInto(aBuilder);
226 nsGenericHTMLElement::MapBackgroundAttributesInto(aBuilder);
227 nsGenericHTMLElement::MapCommonAttributesInto(aBuilder);
230 NS_IMETHODIMP_(bool)
231 HTMLTableRowElement::IsAttributeMapped(const nsAtom* aAttribute) const {
232 static const MappedAttributeEntry attributes[] = {
233 {nsGkAtoms::align}, {nsGkAtoms::valign}, {nsGkAtoms::height}, {nullptr}};
235 static const MappedAttributeEntry* const map[] = {
236 attributes,
237 sCommonAttributeMap,
238 sBackgroundAttributeMap,
241 return FindAttributeDependence(aAttribute, map);
244 nsMapRuleToAttributesFunc HTMLTableRowElement::GetAttributeMappingFunction()
245 const {
246 return &MapAttributesIntoRule;
249 } // namespace mozilla::dom