diff --git a/dom/base/ContentIterator.cpp b/dom/base/ContentIterator.cpp index 48ca0fb24e95..dbcb4627e260 100644 --- a/dom/base/ContentIterator.cpp +++ b/dom/base/ContentIterator.cpp @@ -134,8 +134,7 @@ void ImplCycleCollectionUnlink(ContentIteratorBase& aField) { ImplCycleCollectionUnlink(aField.mClosestCommonInclusiveAncestor); } -ContentIteratorBase::ContentIteratorBase(Order aOrder) - : mIsDone(false), mOrder(aOrder) {} +ContentIteratorBase::ContentIteratorBase(Order aOrder) : mOrder(aOrder) {} ContentIteratorBase::~ContentIteratorBase() = default; @@ -148,8 +147,6 @@ nsresult ContentIteratorBase::Init(nsINode* aRoot) { return NS_ERROR_NULL_POINTER; } - mIsDone = false; - if (mOrder == Order::Pre) { mFirst = aRoot; mLast = ContentIteratorBase::GetDeepLastChild(aRoot); @@ -166,8 +163,6 @@ nsresult ContentIteratorBase::Init(nsINode* aRoot) { } nsresult ContentIteratorBase::Init(nsRange* aRange) { - mIsDone = false; - if (NS_WARN_IF(!aRange)) { return NS_ERROR_INVALID_ARG; } @@ -183,8 +178,6 @@ nsresult ContentIteratorBase::Init(nsINode* aStartContainer, uint32_t aStartOffset, nsINode* aEndContainer, uint32_t aEndOffset) { - mIsDone = false; - if (NS_WARN_IF(!RangeUtils::IsValidPoints(aStartContainer, aStartOffset, aEndContainer, aEndOffset))) { return NS_ERROR_INVALID_ARG; @@ -196,8 +189,6 @@ nsresult ContentIteratorBase::Init(nsINode* aStartContainer, nsresult ContentIteratorBase::Init(const RawRangeBoundary& aStart, const RawRangeBoundary& aEnd) { - mIsDone = false; - if (NS_WARN_IF(!RangeUtils::IsValidPoints(aStart, aEnd))) { return NS_ERROR_INVALID_ARG; } @@ -293,12 +284,10 @@ nsresult ContentIteratorBase::Initializer::Run() { // If either first or last is null, they both have to be null! if (!mIterator.mFirst || !mIterator.mLast) { - mIterator.mFirst = nullptr; - mIterator.mLast = nullptr; + mIterator.SetEmpty(); } mIterator.mCurNode = mIterator.mFirst; - mIterator.mIsDone = !mIterator.mCurNode; return NS_OK; } @@ -460,7 +449,6 @@ void ContentIteratorBase::SetEmpty() { mFirst = nullptr; mLast = nullptr; mClosestCommonInclusiveAncestor = nullptr; - mIsDone = true; } // static @@ -585,12 +573,11 @@ nsINode* ContentIteratorBase::NextNode(nsINode* aNode) { nsINode* parent = node->GetParentNode(); if (NS_WARN_IF(!parent)) { MOZ_ASSERT(parent, "The node is the root node but not the last node"); - mIsDone = true; + mCurNode = nullptr; return node; } - nsIContent* sibling = node->GetNextSibling(); - if (sibling) { + if (nsIContent* sibling = node->GetNextSibling()) { // next node is sibling's "deep left" child return ContentIteratorBase::GetDeepFirstChild(sibling); } @@ -606,7 +593,7 @@ nsINode* ContentIteratorBase::PrevNode(nsINode* aNode) { nsINode* parent = node->GetParentNode(); if (NS_WARN_IF(!parent)) { MOZ_ASSERT(parent, "The node is the root node but not the first node"); - mIsDone = true; + mCurNode = nullptr; return aNode; } @@ -632,35 +619,36 @@ nsINode* ContentIteratorBase::PrevNode(nsINode* aNode) { ******************************************************/ void ContentIteratorBase::First() { - if (mFirst) { - mozilla::DebugOnly rv = PositionAt(mFirst); - NS_ASSERTION(NS_SUCCEEDED(rv), "Failed to position iterator!"); + if (!mFirst) { + MOZ_ASSERT(IsDone()); + mCurNode = nullptr; + return; } - mIsDone = mFirst == nullptr; + mozilla::DebugOnly rv = PositionAt(mFirst); + NS_ASSERTION(NS_SUCCEEDED(rv), "Failed to position iterator!"); } void ContentIteratorBase::Last() { // Note that mLast can be nullptr if SetEmpty() is called in Init() // since at that time, Init() returns NS_OK. if (!mLast) { - MOZ_ASSERT(mIsDone); + MOZ_ASSERT(IsDone()); + mCurNode = nullptr; return; } mozilla::DebugOnly rv = PositionAt(mLast); NS_ASSERTION(NS_SUCCEEDED(rv), "Failed to position iterator!"); - - mIsDone = mLast == nullptr; } void ContentIteratorBase::Next() { - if (mIsDone || NS_WARN_IF(!mCurNode)) { + if (IsDone()) { return; } if (mCurNode == mLast) { - mIsDone = true; + mCurNode = nullptr; return; } @@ -668,20 +656,18 @@ void ContentIteratorBase::Next() { } void ContentIteratorBase::Prev() { - if (NS_WARN_IF(mIsDone) || NS_WARN_IF(!mCurNode)) { + if (IsDone()) { return; } if (mCurNode == mFirst) { - mIsDone = true; + mCurNode = nullptr; return; } mCurNode = PrevNode(mCurNode); } -bool ContentIteratorBase::IsDone() { return mIsDone; } - // Keeping arrays of indexes for the stack of nodes makes PositionAt // interesting... nsresult ContentIteratorBase::PositionAt(nsINode* aCurNode) { @@ -691,7 +677,6 @@ nsresult ContentIteratorBase::PositionAt(nsINode* aCurNode) { // take an early out if this doesn't actually change the position if (mCurNode == aCurNode) { - mIsDone = false; return NS_OK; } mCurNode = aCurNode; @@ -735,24 +720,13 @@ nsresult ContentIteratorBase::PositionAt(nsINode* aCurNode) { (NS_WARN_IF(!first.IsSet()) || NS_WARN_IF(!last.IsSet()) || NS_WARN_IF(!NodeIsInTraversalRange(mCurNode, mOrder == Order::Pre, first, last)))) { - mIsDone = true; + mCurNode = nullptr; return NS_ERROR_FAILURE; } - mIsDone = false; return NS_OK; } -nsINode* ContentIteratorBase::GetCurrentNode() { - if (mIsDone) { - return nullptr; - } - - NS_ASSERTION(mCurNode, "Null current node in an iterator that's not done!"); - - return mCurNode; -} - /****************************************************** * ContentSubtreeIterator init routines ******************************************************/ @@ -764,8 +738,6 @@ nsresult ContentSubtreeIterator::Init(nsINode* aRoot) { nsresult ContentSubtreeIterator::Init(nsRange* aRange) { MOZ_ASSERT(aRange); - mIsDone = false; - if (NS_WARN_IF(!aRange->IsPositioned())) { return NS_ERROR_INVALID_ARG; } @@ -785,8 +757,6 @@ nsresult ContentSubtreeIterator::Init(nsINode* aStartContainer, nsresult ContentSubtreeIterator::Init(const RawRangeBoundary& aStartBoundary, const RawRangeBoundary& aEndBoundary) { - mIsDone = false; - RefPtr range = nsRange::Create(aStartBoundary, aEndBoundary, IgnoreErrors()); if (NS_WARN_IF(!range) || NS_WARN_IF(!range->IsPositioned())) { @@ -972,26 +942,18 @@ nsIContent* ContentSubtreeIterator::DetermineLastContent() const { ****************************************************************/ // we can't call PositionAt in a subtree iterator... -void ContentSubtreeIterator::First() { - mIsDone = mFirst == nullptr; - - mCurNode = mFirst; -} +void ContentSubtreeIterator::First() { mCurNode = mFirst; } // we can't call PositionAt in a subtree iterator... -void ContentSubtreeIterator::Last() { - mIsDone = mLast == nullptr; - - mCurNode = mLast; -} +void ContentSubtreeIterator::Last() { mCurNode = mLast; } void ContentSubtreeIterator::Next() { - if (mIsDone || !mCurNode) { + if (IsDone()) { return; } if (mCurNode == mLast) { - mIsDone = true; + mCurNode = nullptr; return; } @@ -1013,22 +975,17 @@ void ContentSubtreeIterator::Next() { } mCurNode = nextNode; - - // This shouldn't be needed, but since our selection code can put us - // in a situation where mLast is in generated content, we need this - // to stop the iterator when we've walked past past the last node! - mIsDone = mCurNode == nullptr; } void ContentSubtreeIterator::Prev() { // Prev should be optimized to use the mStartNodes, just as Next // uses mInclusiveAncestorsOfEndContainer. - if (mIsDone || !mCurNode) { + if (IsDone()) { return; } if (mCurNode == mFirst) { - mIsDone = true; + mCurNode = nullptr; return; } @@ -1041,16 +998,10 @@ void ContentSubtreeIterator::Prev() { prevNode = ContentIteratorBase::GetDeepLastChild(prevNode); mCurNode = GetTopAncestorInRange(prevNode); - - // This shouldn't be needed, but since our selection code can put us - // in a situation where mFirst is in generated content, we need this - // to stop the iterator when we've walked past past the first node! - mIsDone = mCurNode == nullptr; } nsresult ContentSubtreeIterator::PositionAt(nsINode* aCurNode) { NS_ERROR("Not implemented!"); - return NS_ERROR_NOT_IMPLEMENTED; } diff --git a/dom/base/ContentIterator.h b/dom/base/ContentIterator.h index adba24d6339c..012443c8dd36 100644 --- a/dom/base/ContentIterator.h +++ b/dom/base/ContentIterator.h @@ -51,9 +51,9 @@ class ContentIteratorBase { virtual void Next(); virtual void Prev(); - virtual nsINode* GetCurrentNode(); + nsINode* GetCurrentNode() const { return mCurNode; } - virtual bool IsDone(); + bool IsDone() const { return !mCurNode; } virtual nsresult PositionAt(nsINode* aCurNode); @@ -102,8 +102,6 @@ class ContentIteratorBase { // See . nsCOMPtr mClosestCommonInclusiveAncestor; - bool mIsDone; - const Order mOrder; friend void ImplCycleCollectionTraverse(nsCycleCollectionTraversalCallback&, @@ -185,14 +183,14 @@ class ContentSubtreeIterator final : public ContentIteratorBase { virtual nsresult Init(const RawRangeBoundary& aStartBoundary, const RawRangeBoundary& aEndBoundary) override; - virtual void Next() override; - virtual void Prev() override; + void Next() override; + void Prev() override; // Must override these because we don't do PositionAt - virtual void First() override; + void First() override; // Must override these because we don't do PositionAt - virtual void Last() override; + void Last() override; - virtual nsresult PositionAt(nsINode* aCurNode) override; + nsresult PositionAt(nsINode* aCurNode) override; friend void ImplCycleCollectionTraverse(nsCycleCollectionTraversalCallback&, ContentSubtreeIterator&, const char*, diff --git a/testing/web-platform/tests/selection/drag-disabled-textarea-shadow-dom.html b/testing/web-platform/tests/selection/drag-disabled-textarea-shadow-dom.html new file mode 100644 index 000000000000..9270cfc5c6be --- /dev/null +++ b/testing/web-platform/tests/selection/drag-disabled-textarea-shadow-dom.html @@ -0,0 +1,39 @@ + + + + + + + + + + +