diff options
Diffstat (limited to 'layout/style/GroupRule.cpp')
-rw-r--r-- | layout/style/GroupRule.cpp | 147 |
1 files changed, 147 insertions, 0 deletions
diff --git a/layout/style/GroupRule.cpp b/layout/style/GroupRule.cpp new file mode 100644 index 0000000000..ff3cd11f8c --- /dev/null +++ b/layout/style/GroupRule.cpp @@ -0,0 +1,147 @@ +/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ +/* vim: set ts=8 sts=2 et sw=2 tw=80: */ +/* This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ + +/* + * internal interface representing CSS style rules that contain other + * rules, such as @media rules + */ + +#include "mozilla/css/GroupRule.h" + +#include "mozilla/dom/CSSRuleList.h" + +#include "nsPrintfCString.h" + +using namespace mozilla::dom; + +namespace mozilla::css { + +GroupRule::GroupRule(StyleSheet* aSheet, Rule* aParentRule, + uint32_t aLineNumber, uint32_t aColumnNumber) + : Rule(aSheet, aParentRule, aLineNumber, aColumnNumber) {} + +GroupRule::~GroupRule() { + MOZ_ASSERT(!mSheet, "SetStyleSheet should have been called"); + if (mRuleList) { + mRuleList->DropReferences(); + } +} + +NS_IMPL_ADDREF_INHERITED(GroupRule, Rule) +NS_IMPL_RELEASE_INHERITED(GroupRule, Rule) + +NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(GroupRule) +NS_INTERFACE_MAP_END_INHERITING(Rule) + +bool GroupRule::IsCCLeaf() const { + if (!Rule::IsCCLeaf()) { + return false; + } + return !mRuleList; +} + +ServoCSSRuleList* GroupRule::CssRules() { + if (!mRuleList) { + // Lazily create the rule list since most style rules won't have child + // rules. + mRuleList = + new ServoCSSRuleList(GetOrCreateRawRules(), GetStyleSheet(), this); + } + return mRuleList; +} + +NS_IMPL_CYCLE_COLLECTION_CLASS(GroupRule) + +NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(GroupRule, Rule) + if (tmp->mRuleList) { + // If tmp has a style sheet (which can happen if it gets unlinked + // earlier than its owning style sheet), then we need to null out the + // style sheet pointer on descendants now, before we clear mRuleList. + tmp->mRuleList->DropReferences(); + tmp->mRuleList = nullptr; + } +NS_IMPL_CYCLE_COLLECTION_UNLINK_END + +NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INHERITED(GroupRule, Rule) + ImplCycleCollectionTraverse(cb, tmp->mRuleList, "mRuleList"); +NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END + +#ifdef DEBUG +void GroupRule::List(FILE* out, int32_t aIndent) const { + // TODO list something reasonable? +} +#endif + +/* virtual */ +void GroupRule::DropSheetReference() { + if (mRuleList) { + mRuleList->DropSheetReference(); + } + Rule::DropSheetReference(); +} + +uint32_t GroupRule::InsertRule(const nsACString& aRule, uint32_t aIndex, + ErrorResult& aRv) { + if (IsReadOnly()) { + return 0; + } + + StyleSheet* sheet = GetStyleSheet(); + if (NS_WARN_IF(!sheet)) { + aRv.Throw(NS_ERROR_FAILURE); + return 0; + } + + uint32_t count = StyleRuleCount(); + if (aIndex > count) { + aRv.ThrowIndexSizeError(nsPrintfCString( + "Can't insert rule at index %u because rule list length is %u", aIndex, + count)); + return 0; + } + + NS_ASSERTION(count <= INT32_MAX, "Too many style rules!"); + + nsresult rv = sheet->InsertRuleIntoGroup(aRule, this, aIndex); + if (NS_FAILED(rv)) { + aRv.Throw(rv); + return 0; + } + return aIndex; +} + +void GroupRule::DeleteRule(uint32_t aIndex, ErrorResult& aRv) { + if (IsReadOnly()) { + return; + } + + StyleSheet* sheet = GetStyleSheet(); + if (NS_WARN_IF(!sheet)) { + aRv.Throw(NS_ERROR_FAILURE); + return; + } + + uint32_t count = StyleRuleCount(); + if (aIndex >= count) { + aRv.ThrowIndexSizeError(nsPrintfCString( + "Index %u is too large for list of length %u", aIndex, count)); + return; + } + + NS_ASSERTION(count <= INT32_MAX, "Too many style rules!"); + + nsresult rv = sheet->DeleteRuleFromGroup(this, aIndex); + if (NS_FAILED(rv)) { + aRv.Throw(rv); + } +} + +size_t GroupRule::SizeOfExcludingThis(MallocSizeOf aMallocSizeOf) const { + // TODO how to implement? + return 0; +} + +} // namespace mozilla::css |