Diff
Modified: trunk/Source/WebCore/ChangeLog (226515 => 226516)
--- trunk/Source/WebCore/ChangeLog 2018-01-08 17:02:33 UTC (rev 226515)
+++ trunk/Source/WebCore/ChangeLog 2018-01-08 17:40:21 UTC (rev 226516)
@@ -1,3 +1,58 @@
+2018-01-08 Zalan Bujtas <[email protected]>
+
+ [RenderTreeBuilder] Move RenderBlock addChild logic to RenderTreeBuilder
+ https://bugs.webkit.org/show_bug.cgi?id=181319
+ <rdar://problem/36313464>
+
+ Reviewed by Antti Koivisto.
+
+ This is about moving the code, no cleanup and/or normalization (unfortunately it also means
+ some temporary changes).
+
+ No change in functionality.
+
+ * Sources.txt:
+ * WebCore.xcodeproj/project.pbxproj:
+ * rendering/RenderBlock.cpp:
+ (WebCore::RenderBlock::addChild):
+ (WebCore::RenderBlock::addChildIgnoringContinuation):
+ (WebCore::RenderBlock::childBecameNonInline):
+ (WebCore::RenderBlock::continuationBefore): Deleted.
+ (WebCore::RenderBlock::addChildToContinuation): Deleted.
+ (WebCore::getInlineRun): Deleted.
+ (WebCore::RenderBlock::makeChildrenNonInline): Deleted.
+ * rendering/RenderBlock.h:
+ * rendering/RenderBox.cpp:
+ (WebCore::markBoxForRelayoutAfterSplit): Deleted.
+ (WebCore::RenderBox::splitAnonymousBoxesAroundChild): Deleted.
+ * rendering/RenderBox.h:
+ * rendering/RenderRubyBase.cpp:
+ (WebCore::RenderRubyBase::moveChildren):
+ (WebCore::RenderRubyBase::moveBlockChildren):
+ * rendering/RenderTable.cpp:
+ (WebCore::RenderTable::addChild):
+ * rendering/RenderTableRow.cpp:
+ (WebCore::RenderTableRow::addChild):
+ * rendering/RenderTableSection.cpp:
+ (WebCore::RenderTableSection::addChild):
+ * rendering/updating/RenderTreeBuilder.cpp:
+ (WebCore::markBoxForRelayoutAfterSplit):
+ (WebCore::getInlineRun):
+ (WebCore::RenderTreeBuilder::RenderTreeBuilder):
+ (WebCore::RenderTreeBuilder::insertChildToRenderBlock):
+ (WebCore::RenderTreeBuilder::insertChildToRenderBlockIgnoringContinuation):
+ (WebCore::RenderTreeBuilder::makeChildrenNonInline):
+ (WebCore::RenderTreeBuilder::splitAnonymousBoxesAroundChild):
+ * rendering/updating/RenderTreeBuilder.h:
+ (WebCore::RenderTreeBuilder::blockBuilder):
+ * rendering/updating/RenderTreeBuilderBlock.cpp: Added.
+ (WebCore::continuationBefore):
+ (WebCore::RenderTreeBuilder::Block::Block):
+ (WebCore::RenderTreeBuilder::Block::insertChild):
+ (WebCore::RenderTreeBuilder::Block::insertChildToContinuation):
+ (WebCore::RenderTreeBuilder::Block::insertChildIgnoringContinuation):
+ * rendering/updating/RenderTreeBuilderBlock.h: Added.
+
2018-01-08 Jeremy Jones <[email protected]>
Standard controls sometimes say video is in pip when it isnt.
Modified: trunk/Source/WebCore/Sources.txt (226515 => 226516)
--- trunk/Source/WebCore/Sources.txt 2018-01-08 17:02:33 UTC (rev 226515)
+++ trunk/Source/WebCore/Sources.txt 2018-01-08 17:40:21 UTC (rev 226516)
@@ -1984,6 +1984,7 @@
rendering/svg/SVGTextQuery.cpp
rendering/updating/RenderTreeBuilder.cpp
+rendering/updating/RenderTreeBuilderBlock.cpp
rendering/updating/RenderTreeBuilderFirstLetter.cpp
rendering/updating/RenderTreeBuilderFormControls.cpp
rendering/updating/RenderTreeBuilderList.cpp
Modified: trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj (226515 => 226516)
--- trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj 2018-01-08 17:02:33 UTC (rev 226515)
+++ trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj 2018-01-08 17:40:21 UTC (rev 226516)
@@ -393,6 +393,7 @@
119340791FE8B92300935F1E /* RenderTreeBuilderTable.h in Headers */ = {isa = PBXBuildFile; fileRef = 119340771FE8B92300935F1E /* RenderTreeBuilderTable.h */; };
1193408A1FEB355D00935F1E /* RenderTreeBuilderRuby.h in Headers */ = {isa = PBXBuildFile; fileRef = 119340881FEB355D00935F1E /* RenderTreeBuilderRuby.h */; };
119340971FED715500935F1E /* RenderTreeBuilderFormControls.h in Headers */ = {isa = PBXBuildFile; fileRef = 119340951FED715500935F1E /* RenderTreeBuilderFormControls.h */; };
+ 119340A31FEE024000935F1E /* RenderTreeBuilderBlock.h in Headers */ = {isa = PBXBuildFile; fileRef = 119340A11FEE024000935F1E /* RenderTreeBuilderBlock.h */; };
11E067EE1E6246E500162D16 /* SimpleLineLayoutCoverage.h in Headers */ = {isa = PBXBuildFile; fileRef = 11E067ED1E6246E500162D16 /* SimpleLineLayoutCoverage.h */; settings = {ATTRIBUTES = (Private, ); }; };
1400D7A817136EA70077CE05 /* ScriptWrappableInlines.h in Headers */ = {isa = PBXBuildFile; fileRef = 1400D7A717136EA70077CE05 /* ScriptWrappableInlines.h */; settings = {ATTRIBUTES = (Private, ); }; };
1403B99709EB13AF00797C7F /* DOMWindow.h in Headers */ = {isa = PBXBuildFile; fileRef = 1403B99509EB13AF00797C7F /* DOMWindow.h */; settings = {ATTRIBUTES = (Private, ); }; };
@@ -5588,6 +5589,8 @@
119340881FEB355D00935F1E /* RenderTreeBuilderRuby.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = RenderTreeBuilderRuby.h; sourceTree = "<group>"; };
119340941FED715500935F1E /* RenderTreeBuilderFormControls.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = RenderTreeBuilderFormControls.cpp; sourceTree = "<group>"; };
119340951FED715500935F1E /* RenderTreeBuilderFormControls.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = RenderTreeBuilderFormControls.h; sourceTree = "<group>"; };
+ 119340A01FEE024000935F1E /* RenderTreeBuilderBlock.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = RenderTreeBuilderBlock.cpp; sourceTree = "<group>"; };
+ 119340A11FEE024000935F1E /* RenderTreeBuilderBlock.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = RenderTreeBuilderBlock.h; sourceTree = "<group>"; };
11E067EB1E62461300162D16 /* SimpleLineLayoutCoverage.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = SimpleLineLayoutCoverage.cpp; sourceTree = "<group>"; };
11E067ED1E6246E500162D16 /* SimpleLineLayoutCoverage.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = SimpleLineLayoutCoverage.h; sourceTree = "<group>"; };
1400D7A717136EA70077CE05 /* ScriptWrappableInlines.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ScriptWrappableInlines.h; sourceTree = "<group>"; };
@@ -24626,6 +24629,8 @@
children = (
E47C39201FE6E0D900BBBC6B /* RenderTreeBuilder.cpp */,
E47C392A1FE6E0DE00BBBC6B /* RenderTreeBuilder.h */,
+ 119340A01FEE024000935F1E /* RenderTreeBuilderBlock.cpp */,
+ 119340A11FEE024000935F1E /* RenderTreeBuilderBlock.h */,
E47C39211FE6E0DA00BBBC6B /* RenderTreeBuilderFirstLetter.cpp */,
E47C39261FE6E0DC00BBBC6B /* RenderTreeBuilderFirstLetter.h */,
119340941FED715500935F1E /* RenderTreeBuilderFormControls.cpp */,
@@ -29053,6 +29058,7 @@
BCEA4887097D93020094C9E4 /* RenderThemeMac.h in Headers */,
93F1998C08245E59001E9ABC /* RenderTreeAsText.h in Headers */,
E47C392D1FE6E0F300BBBC6B /* RenderTreeBuilder.h in Headers */,
+ 119340A31FEE024000935F1E /* RenderTreeBuilderBlock.h in Headers */,
E47C39301FE6E0FD00BBBC6B /* RenderTreeBuilderFirstLetter.h in Headers */,
119340971FED715500935F1E /* RenderTreeBuilderFormControls.h in Headers */,
E47C39321FE6E10500BBBC6B /* RenderTreeBuilderList.h in Headers */,
Modified: trunk/Source/WebCore/rendering/RenderBlock.cpp (226515 => 226516)
--- trunk/Source/WebCore/rendering/RenderBlock.cpp 2018-01-08 17:02:33 UTC (rev 226515)
+++ trunk/Source/WebCore/rendering/RenderBlock.cpp 2018-01-08 17:40:21 UTC (rev 226516)
@@ -446,71 +446,6 @@
setShouldForceRelayoutChildren(oldStyle && diff == StyleDifferenceLayout && needsLayout() && borderOrPaddingLogicalWidthChanged(*oldStyle, style()));
}
-RenderBlock* RenderBlock::continuationBefore(RenderObject* beforeChild)
-{
- if (beforeChild && beforeChild->parent() == this)
- return this;
-
- RenderBlock* nextToLast = this;
- RenderBlock* last = this;
- for (auto* current = downcast<RenderBlock>(continuation()); current; current = downcast<RenderBlock>(current->continuation())) {
- if (beforeChild && beforeChild->parent() == current) {
- if (current->firstChild() == beforeChild)
- return last;
- return current;
- }
-
- nextToLast = last;
- last = current;
- }
-
- if (!beforeChild && !last->firstChild())
- return nextToLast;
- return last;
-}
-
-void RenderBlock::addChildToContinuation(RenderTreeBuilder& builder, RenderPtr<RenderObject> newChild, RenderObject* beforeChild)
-{
- RenderBlock* flow = continuationBefore(beforeChild);
- ASSERT(!beforeChild || is<RenderBlock>(*beforeChild->parent()));
- RenderBoxModelObject* beforeChildParent = nullptr;
- if (beforeChild)
- beforeChildParent = downcast<RenderBoxModelObject>(beforeChild->parent());
- else {
- RenderBoxModelObject* continuation = flow->continuation();
- if (continuation)
- beforeChildParent = continuation;
- else
- beforeChildParent = flow;
- }
-
- if (newChild->isFloatingOrOutOfFlowPositioned()) {
- beforeChildParent->addChildIgnoringContinuation(builder, WTFMove(newChild), beforeChild);
- return;
- }
-
- bool childIsNormal = newChild->isInline() || !newChild->style().columnSpan();
- bool bcpIsNormal = beforeChildParent->isInline() || !beforeChildParent->style().columnSpan();
- bool flowIsNormal = flow->isInline() || !flow->style().columnSpan();
-
- if (flow == beforeChildParent) {
- flow->addChildIgnoringContinuation(builder, WTFMove(newChild), beforeChild);
- return;
- }
-
- // The goal here is to match up if we can, so that we can coalesce and create the
- // minimal # of continuations needed for the inline.
- if (childIsNormal == bcpIsNormal) {
- beforeChildParent->addChildIgnoringContinuation(builder, WTFMove(newChild), beforeChild);
- return;
- }
- if (flowIsNormal == childIsNormal) {
- flow->addChildIgnoringContinuation(builder, WTFMove(newChild), 0); // Just treat like an append.
- return;
- }
- beforeChildParent->addChildIgnoringContinuation(builder, WTFMove(newChild), beforeChild);
-}
-
RenderPtr<RenderBlock> RenderBlock::clone() const
{
RenderPtr<RenderBlock> cloneBlock;
@@ -533,140 +468,14 @@
void RenderBlock::addChild(RenderTreeBuilder& builder, RenderPtr<RenderObject> newChild, RenderObject* beforeChild)
{
- if (continuation() && !isAnonymousBlock())
- addChildToContinuation(builder, WTFMove(newChild), beforeChild);
- else
- addChildIgnoringContinuation(builder, WTFMove(newChild), beforeChild);
+ builder.insertChildToRenderBlock(*this, WTFMove(newChild), beforeChild);
}
void RenderBlock::addChildIgnoringContinuation(RenderTreeBuilder& builder, RenderPtr<RenderObject> newChild, RenderObject* beforeChild)
{
- if (beforeChild && beforeChild->parent() != this) {
- RenderElement* beforeChildContainer = beforeChild->parent();
- while (beforeChildContainer->parent() != this)
- beforeChildContainer = beforeChildContainer->parent();
- ASSERT(beforeChildContainer);
-
- if (beforeChildContainer->isAnonymous()) {
- RELEASE_ASSERT_WITH_SECURITY_IMPLICATION(!beforeChildContainer->isInline());
-
- // If the requested beforeChild is not one of our children, then this is because
- // there is an anonymous container within this object that contains the beforeChild.
- RenderElement* beforeChildAnonymousContainer = beforeChildContainer;
- if (beforeChildAnonymousContainer->isAnonymousBlock()
-#if ENABLE(FULLSCREEN_API)
- // Full screen renderers and full screen placeholders act as anonymous blocks, not tables:
- || beforeChildAnonymousContainer->isRenderFullScreen()
- || beforeChildAnonymousContainer->isRenderFullScreenPlaceholder()
-#endif
- ) {
- // Insert the child into the anonymous block box instead of here.
- if (newChild->isInline() || beforeChild->parent()->firstChild() != beforeChild)
- builder.insertChild(*beforeChild->parent(), WTFMove(newChild), beforeChild);
- else
- builder.insertChild(*this, WTFMove(newChild), beforeChild->parent());
- return;
- }
-
- ASSERT(beforeChildAnonymousContainer->isTable());
-
- if (newChild->isTablePart()) {
- // Insert into the anonymous table.
- builder.insertChild(*beforeChildAnonymousContainer, WTFMove(newChild), beforeChild);
- return;
- }
-
- beforeChild = splitAnonymousBoxesAroundChild(beforeChild);
-
- RELEASE_ASSERT_WITH_SECURITY_IMPLICATION(beforeChild->parent() == this);
- }
- }
-
- bool madeBoxesNonInline = false;
-
- // A block has to either have all of its children inline, or all of its children as blocks.
- // So, if our children are currently inline and a block child has to be inserted, we move all our
- // inline children into anonymous block boxes.
- if (childrenInline() && !newChild->isInline() && !newChild->isFloatingOrOutOfFlowPositioned()) {
- // This is a block with inline content. Wrap the inline content in anonymous blocks.
- makeChildrenNonInline(beforeChild);
- madeBoxesNonInline = true;
-
- if (beforeChild && beforeChild->parent() != this) {
- beforeChild = beforeChild->parent();
- ASSERT(beforeChild->isAnonymousBlock());
- ASSERT(beforeChild->parent() == this);
- }
- } else if (!childrenInline() && (newChild->isFloatingOrOutOfFlowPositioned() || newChild->isInline())) {
- // If we're inserting an inline child but all of our children are blocks, then we have to make sure
- // it is put into an anomyous block box. We try to use an existing anonymous box if possible, otherwise
- // a new one is created and inserted into our list of children in the appropriate position.
- RenderObject* afterChild = beforeChild ? beforeChild->previousSibling() : lastChild();
-
- if (afterChild && afterChild->isAnonymousBlock()) {
- builder.insertChild(downcast<RenderBlock>(*afterChild), WTFMove(newChild));
- return;
- }
-
- if (newChild->isInline()) {
- // No suitable existing anonymous box - create a new one.
- auto newBox = createAnonymousBlock();
- auto& box = *newBox;
- RenderBox::addChild(builder, WTFMove(newBox), beforeChild);
- builder.insertChild(box, WTFMove(newChild));
- return;
- }
- }
-
- invalidateLineLayoutPath();
-
- RenderBox::addChild(builder, WTFMove(newChild), beforeChild);
-
- if (madeBoxesNonInline && is<RenderBlock>(parent()) && isAnonymousBlock())
- downcast<RenderBlock>(*parent()).removeLeftoverAnonymousBlock(this);
- // this object may be dead here
+ builder.insertChildToRenderBlockIgnoringContinuation(*this, WTFMove(newChild), beforeChild);
}
-static void getInlineRun(RenderObject* start, RenderObject* boundary,
- RenderObject*& inlineRunStart,
- RenderObject*& inlineRunEnd)
-{
- // Beginning at |start| we find the largest contiguous run of inlines that
- // we can. We denote the run with start and end points, |inlineRunStart|
- // and |inlineRunEnd|. Note that these two values may be the same if
- // we encounter only one inline.
- //
- // We skip any non-inlines we encounter as long as we haven't found any
- // inlines yet.
- //
- // |boundary| indicates a non-inclusive boundary point. Regardless of whether |boundary|
- // is inline or not, we will not include it in a run with inlines before it. It's as though we encountered
- // a non-inline.
-
- // Start by skipping as many non-inlines as we can.
- RenderObject * curr = start;
- bool sawInline;
- do {
- while (curr && !(curr->isInline() || curr->isFloatingOrOutOfFlowPositioned()))
- curr = curr->nextSibling();
-
- inlineRunStart = inlineRunEnd = curr;
-
- if (!curr)
- return; // No more inline children to be found.
-
- sawInline = curr->isInline();
-
- curr = curr->nextSibling();
- while (curr && (curr->isInline() || curr->isFloatingOrOutOfFlowPositioned()) && (curr != boundary)) {
- inlineRunEnd = curr;
- if (curr->isInline())
- sawInline = true;
- curr = curr->nextSibling();
- }
- } while (!sawInline);
-}
-
void RenderBlock::deleteLines()
{
if (AXObjectCache* cache = document().existingAXObjectCache())
@@ -673,50 +482,6 @@
cache->deferRecomputeIsIgnored(element());
}
-void RenderBlock::makeChildrenNonInline(RenderObject* insertionPoint)
-{
- // makeChildrenNonInline takes a block whose children are *all* inline and it
- // makes sure that inline children are coalesced under anonymous
- // blocks. If |insertionPoint| is defined, then it represents the insertion point for
- // the new block child that is causing us to have to wrap all the inlines. This
- // means that we cannot coalesce inlines before |insertionPoint| with inlines following
- // |insertionPoint|, because the new child is going to be inserted in between the inlines,
- // splitting them.
- ASSERT(isInlineBlockOrInlineTable() || !isInline());
- ASSERT(!insertionPoint || insertionPoint->parent() == this);
-
- setChildrenInline(false);
-
- RenderObject* child = firstChild();
- if (!child)
- return;
-
- deleteLines();
-
- while (child) {
- RenderObject* inlineRunStart;
- RenderObject* inlineRunEnd;
- getInlineRun(child, insertionPoint, inlineRunStart, inlineRunEnd);
-
- if (!inlineRunStart)
- break;
-
- child = inlineRunEnd->nextSibling();
-
- auto newBlock = createAnonymousBlock();
- auto& block = *newBlock;
- insertChildInternal(WTFMove(newBlock), inlineRunStart);
- moveChildrenTo(&block, inlineRunStart, child, RenderBoxModelObject::NormalizeAfterInsertion::No);
- }
-
-#ifndef NDEBUG
- for (RenderObject* c = firstChild(); c; c = c->nextSibling())
- ASSERT(!c->isInline());
-#endif
-
- repaint();
-}
-
void RenderBlock::removeLeftoverAnonymousBlock(RenderBlock* child)
{
ASSERT(child->isAnonymousBlock());
@@ -3212,7 +2977,7 @@
void RenderBlock::childBecameNonInline(RenderElement&)
{
- makeChildrenNonInline();
+ RenderTreeBuilder::current()->makeChildrenNonInline(*this);
if (isAnonymousBlock() && is<RenderBlock>(parent()))
downcast<RenderBlock>(*parent()).removeLeftoverAnonymousBlock(this);
// |this| may be dead here
Modified: trunk/Source/WebCore/rendering/RenderBlock.h (226515 => 226516)
--- trunk/Source/WebCore/rendering/RenderBlock.h 2018-01-08 17:02:33 UTC (rev 226515)
+++ trunk/Source/WebCore/rendering/RenderBlock.h 2018-01-08 17:40:21 UTC (rev 226516)
@@ -395,7 +395,10 @@
void adjustBorderBoxRectForPainting(LayoutRect&) override;
LayoutRect paintRectToClipOutFromBorder(const LayoutRect&) override;
-
+ void addChildIgnoringContinuation(RenderTreeBuilder&, RenderPtr<RenderObject> newChild, RenderObject* beforeChild) override;
+ virtual void removeLeftoverAnonymousBlock(RenderBlock* child);
+ bool isInlineBlockOrInlineTable() const final { return isInline() && isReplaced(); }
+
protected:
virtual void addOverflowFromChildren();
// FIXME-BLOCKFLOW: Remove virtualization when all callers have moved to RenderBlockFlow
@@ -432,17 +435,9 @@
const char* renderName() const override;
- bool isInlineBlockOrInlineTable() const final { return isInline() && isReplaced(); }
-
- void makeChildrenNonInline(RenderObject* insertionPoint = nullptr);
- virtual void removeLeftoverAnonymousBlock(RenderBlock* child);
-
// FIXME-BLOCKFLOW: Remove virtualizaion when all callers have moved to RenderBlockFlow
virtual void moveAllChildrenIncludingFloatsTo(RenderBlock& toBlock, RenderBoxModelObject::NormalizeAfterInsertion normalizeAfterInsertion) { moveAllChildrenTo(&toBlock, normalizeAfterInsertion); }
- void addChildToContinuation(RenderTreeBuilder&, RenderPtr<RenderObject> newChild, RenderObject* beforeChild);
- void addChildIgnoringContinuation(RenderTreeBuilder&, RenderPtr<RenderObject> newChild, RenderObject* beforeChild) override;
-
bool isSelfCollapsingBlock() const override;
virtual bool childrenPreventSelfCollapsing() const;
@@ -502,7 +497,6 @@
virtual VisiblePosition positionForPointWithInlineChildren(const LayoutPoint&, const RenderFragmentContainer*);
RenderPtr<RenderBlock> clone() const;
- RenderBlock* continuationBefore(RenderObject* beforeChild);
RenderFragmentedFlow* updateCachedEnclosingFragmentedFlow(RenderFragmentedFlow*) const;
Modified: trunk/Source/WebCore/rendering/RenderBox.cpp (226515 => 226516)
--- trunk/Source/WebCore/rendering/RenderBox.cpp 2018-01-08 17:02:33 UTC (rev 226515)
+++ trunk/Source/WebCore/rendering/RenderBox.cpp 2018-01-08 17:40:21 UTC (rev 226516)
@@ -4904,57 +4904,6 @@
|| style().logicalMaxWidth().isPercentOrCalculated();
}
-static void markBoxForRelayoutAfterSplit(RenderBox& box)
-{
- // FIXME: The table code should handle that automatically. If not,
- // we should fix it and remove the table part checks.
- if (is<RenderTable>(box)) {
- // Because we may have added some sections with already computed column structures, we need to
- // sync the table structure with them now. This avoids crashes when adding new cells to the table.
- downcast<RenderTable>(box).forceSectionsRecalc();
- } else if (is<RenderTableSection>(box))
- downcast<RenderTableSection>(box).setNeedsCellRecalc();
-
- box.setNeedsLayoutAndPrefWidthsRecalc();
-}
-
-RenderObject* RenderBox::splitAnonymousBoxesAroundChild(RenderObject* beforeChild)
-{
- bool didSplitParentAnonymousBoxes = false;
-
- while (beforeChild->parent() != this) {
- auto& boxToSplit = downcast<RenderBox>(*beforeChild->parent());
- if (boxToSplit.firstChild() != beforeChild && boxToSplit.isAnonymous()) {
- didSplitParentAnonymousBoxes = true;
-
- // We have to split the parent box into two boxes and move children
- // from |beforeChild| to end into the new post box.
- auto newPostBox = boxToSplit.createAnonymousBoxWithSameTypeAs(*this);
- auto& postBox = *newPostBox;
- postBox.setChildrenInline(boxToSplit.childrenInline());
- RenderBox* parentBox = downcast<RenderBox>(boxToSplit.parent());
- // We need to invalidate the |parentBox| before inserting the new node
- // so that the table repainting logic knows the structure is dirty.
- // See for example RenderTableCell:clippedOverflowRectForRepaint.
- markBoxForRelayoutAfterSplit(*parentBox);
- parentBox->insertChildInternal(WTFMove(newPostBox), boxToSplit.nextSibling());
- boxToSplit.moveChildrenTo(&postBox, beforeChild, nullptr, RenderBoxModelObject::NormalizeAfterInsertion::Yes);
-
- markBoxForRelayoutAfterSplit(boxToSplit);
- markBoxForRelayoutAfterSplit(postBox);
-
- beforeChild = &postBox;
- } else
- beforeChild = &boxToSplit;
- }
-
- if (didSplitParentAnonymousBoxes)
- markBoxForRelayoutAfterSplit(*this);
-
- ASSERT(beforeChild->parent() == this);
- return beforeChild;
-}
-
LayoutUnit RenderBox::offsetFromLogicalTopOfFirstPage() const
{
auto* layoutState = view().frameView().layoutContext().layoutState();
Modified: trunk/Source/WebCore/rendering/RenderBox.h (226515 => 226516)
--- trunk/Source/WebCore/rendering/RenderBox.h 2018-01-08 17:02:33 UTC (rev 226515)
+++ trunk/Source/WebCore/rendering/RenderBox.h 2018-01-08 17:40:21 UTC (rev 226516)
@@ -665,8 +665,6 @@
void paintRootBoxFillLayers(const PaintInfo&);
- RenderObject* splitAnonymousBoxesAroundChild(RenderObject* beforeChild);
-
bool skipContainingBlockForPercentHeightCalculation(const RenderBox& containingBlock, bool isPerpendicularWritingMode) const;
private:
Modified: trunk/Source/WebCore/rendering/RenderRubyBase.cpp (226515 => 226516)
--- trunk/Source/WebCore/rendering/RenderRubyBase.cpp 2018-01-08 17:02:33 UTC (rev 226515)
+++ trunk/Source/WebCore/rendering/RenderRubyBase.cpp 2018-01-08 17:40:21 UTC (rev 226516)
@@ -61,7 +61,7 @@
ASSERT_ARG(toBase, toBase);
if (beforeChild && beforeChild->parent() != this)
- beforeChild = splitAnonymousBoxesAroundChild(beforeChild);
+ beforeChild = RenderTreeBuilder::current()->splitAnonymousBoxesAroundChild(*this, beforeChild);
if (childrenInline())
moveInlineChildren(toBase, beforeChild);
@@ -115,7 +115,7 @@
return;
if (toBase->childrenInline())
- toBase->makeChildrenNonInline();
+ RenderTreeBuilder::current()->makeChildrenNonInline(*toBase);
// If an anonymous block would be put next to another such block, then merge those.
RenderObject* firstChildHere = firstChild();
Modified: trunk/Source/WebCore/rendering/RenderTable.cpp (226515 => 226516)
--- trunk/Source/WebCore/rendering/RenderTable.cpp 2018-01-08 17:02:33 UTC (rev 226515)
+++ trunk/Source/WebCore/rendering/RenderTable.cpp 2018-01-08 17:40:21 UTC (rev 226516)
@@ -170,7 +170,7 @@
setNeedsSectionRecalc();
if (beforeChild && beforeChild->parent() != this)
- beforeChild = splitAnonymousBoxesAroundChild(beforeChild);
+ beforeChild = builder.splitAnonymousBoxesAroundChild(*this, beforeChild);
RenderBox::addChild(builder, WTFMove(child), beforeChild);
}
Modified: trunk/Source/WebCore/rendering/RenderTableRow.cpp (226515 => 226516)
--- trunk/Source/WebCore/rendering/RenderTableRow.cpp 2018-01-08 17:02:33 UTC (rev 226515)
+++ trunk/Source/WebCore/rendering/RenderTableRow.cpp 2018-01-08 17:40:21 UTC (rev 226516)
@@ -114,7 +114,7 @@
void RenderTableRow::addChild(RenderTreeBuilder& builder, RenderPtr<RenderObject> child, RenderObject* beforeChild)
{
if (beforeChild && beforeChild->parent() != this)
- beforeChild = splitAnonymousBoxesAroundChild(beforeChild);
+ beforeChild = builder.splitAnonymousBoxesAroundChild(*this, beforeChild);
// Generated content can result in us having a null section so make sure to null check our parent.
if (auto* section = this->section())
Modified: trunk/Source/WebCore/rendering/RenderTableSection.cpp (226515 => 226516)
--- trunk/Source/WebCore/rendering/RenderTableSection.cpp 2018-01-08 17:02:33 UTC (rev 226515)
+++ trunk/Source/WebCore/rendering/RenderTableSection.cpp 2018-01-08 17:40:21 UTC (rev 226516)
@@ -140,7 +140,7 @@
setRowLogicalHeightToRowStyleLogicalHeightIfNotRelative(m_grid[insertionRow]);
if (beforeChild && beforeChild->parent() != this)
- beforeChild = splitAnonymousBoxesAroundChild(beforeChild);
+ beforeChild = builder.splitAnonymousBoxesAroundChild(*this, beforeChild);
ASSERT(!beforeChild || is<RenderTableRow>(*beforeChild));
RenderBox::addChild(builder, WTFMove(child), beforeChild);
Modified: trunk/Source/WebCore/rendering/updating/RenderTreeBuilder.cpp (226515 => 226516)
--- trunk/Source/WebCore/rendering/updating/RenderTreeBuilder.cpp 2018-01-08 17:02:33 UTC (rev 226515)
+++ trunk/Source/WebCore/rendering/updating/RenderTreeBuilder.cpp 2018-01-08 17:40:21 UTC (rev 226516)
@@ -33,6 +33,7 @@
#include "RenderRubyRun.h"
#include "RenderTableRow.h"
#include "RenderText.h"
+#include "RenderTreeBuilderBlock.h"
#include "RenderTreeBuilderFirstLetter.h"
#include "RenderTreeBuilderFormControls.h"
#include "RenderTreeBuilderList.h"
@@ -44,6 +45,59 @@
RenderTreeBuilder* RenderTreeBuilder::s_current;
+static void markBoxForRelayoutAfterSplit(RenderBox& box)
+{
+ // FIXME: The table code should handle that automatically. If not,
+ // we should fix it and remove the table part checks.
+ if (is<RenderTable>(box)) {
+ // Because we may have added some sections with already computed column structures, we need to
+ // sync the table structure with them now. This avoids crashes when adding new cells to the table.
+ downcast<RenderTable>(box).forceSectionsRecalc();
+ } else if (is<RenderTableSection>(box))
+ downcast<RenderTableSection>(box).setNeedsCellRecalc();
+
+ box.setNeedsLayoutAndPrefWidthsRecalc();
+}
+
+static void getInlineRun(RenderObject* start, RenderObject* boundary, RenderObject*& inlineRunStart, RenderObject*& inlineRunEnd)
+{
+ // Beginning at |start| we find the largest contiguous run of inlines that
+ // we can. We denote the run with start and end points, |inlineRunStart|
+ // and |inlineRunEnd|. Note that these two values may be the same if
+ // we encounter only one inline.
+ //
+ // We skip any non-inlines we encounter as long as we haven't found any
+ // inlines yet.
+ //
+ // |boundary| indicates a non-inclusive boundary point. Regardless of whether |boundary|
+ // is inline or not, we will not include it in a run with inlines before it. It's as though we encountered
+ // a non-inline.
+
+ // Start by skipping as many non-inlines as we can.
+ auto* curr = start;
+ bool sawInline;
+ do {
+ while (curr && !(curr->isInline() || curr->isFloatingOrOutOfFlowPositioned()))
+ curr = curr->nextSibling();
+
+ inlineRunStart = inlineRunEnd = curr;
+
+ if (!curr)
+ return; // No more inline children to be found.
+
+ sawInline = curr->isInline();
+
+ curr = curr->nextSibling();
+ while (curr && (curr->isInline() || curr->isFloatingOrOutOfFlowPositioned()) && (curr != boundary)) {
+ inlineRunEnd = curr;
+ if (curr->isInline())
+ sawInline = true;
+ curr = curr->nextSibling();
+ }
+ } while (!sawInline);
+}
+
+
RenderTreeBuilder::RenderTreeBuilder(RenderView& view)
: m_view(view)
, m_firstLetterBuilder(std::make_unique<FirstLetter>(*this))
@@ -52,6 +106,7 @@
, m_tableBuilder(std::make_unique<Table>(*this))
, m_rubyBuilder(std::make_unique<Ruby>(*this))
, m_formControlsBuilder(std::make_unique<FormControls>(*this))
+ , m_blockBuilder(std::make_unique<Block>(*this))
{
RELEASE_ASSERT(!s_current || &m_view != &s_current->m_view);
m_previous = s_current;
@@ -128,6 +183,95 @@
insertChild(position.parent(), WTFMove(child), position.nextSibling());
}
+void RenderTreeBuilder::insertChildToRenderBlock(RenderBlock& parent, RenderPtr<RenderObject> child, RenderObject* beforeChild)
+{
+ blockBuilder().insertChild(parent, WTFMove(child), beforeChild);
+}
+
+void RenderTreeBuilder::insertChildToRenderBlockIgnoringContinuation(RenderBlock& parent, RenderPtr<RenderObject> child, RenderObject* beforeChild)
+{
+ blockBuilder().insertChildIgnoringContinuation(parent, WTFMove(child), beforeChild);
+}
+
+void RenderTreeBuilder::makeChildrenNonInline(RenderBlock& parent, RenderObject* insertionPoint)
+{
+ // makeChildrenNonInline takes a block whose children are *all* inline and it
+ // makes sure that inline children are coalesced under anonymous
+ // blocks. If |insertionPoint| is defined, then it represents the insertion point for
+ // the new block child that is causing us to have to wrap all the inlines. This
+ // means that we cannot coalesce inlines before |insertionPoint| with inlines following
+ // |insertionPoint|, because the new child is going to be inserted in between the inlines,
+ // splitting them.
+ ASSERT(parent.isInlineBlockOrInlineTable() || !parent.isInline());
+ ASSERT(!insertionPoint || insertionPoint->parent() == &parent);
+
+ parent.setChildrenInline(false);
+
+ auto* child = parent.firstChild();
+ if (!child)
+ return;
+
+ parent.deleteLines();
+
+ while (child) {
+ RenderObject* inlineRunStart = nullptr;
+ RenderObject* inlineRunEnd = nullptr;
+ getInlineRun(child, insertionPoint, inlineRunStart, inlineRunEnd);
+
+ if (!inlineRunStart)
+ break;
+
+ child = inlineRunEnd->nextSibling();
+
+ auto newBlock = parent.createAnonymousBlock();
+ auto& block = *newBlock;
+ parent.insertChildInternal(WTFMove(newBlock), inlineRunStart);
+ parent.moveChildrenTo(&block, inlineRunStart, child, RenderBoxModelObject::NormalizeAfterInsertion::No);
+ }
+#ifndef NDEBUG
+ for (RenderObject* c = parent.firstChild(); c; c = c->nextSibling())
+ ASSERT(!c->isInline());
+#endif
+ parent.repaint();
+}
+
+RenderObject* RenderTreeBuilder::splitAnonymousBoxesAroundChild(RenderBox& parent, RenderObject* beforeChild)
+{
+ bool didSplitParentAnonymousBoxes = false;
+
+ while (beforeChild->parent() != &parent) {
+ auto& boxToSplit = downcast<RenderBox>(*beforeChild->parent());
+ if (boxToSplit.firstChild() != beforeChild && boxToSplit.isAnonymous()) {
+ didSplitParentAnonymousBoxes = true;
+
+ // We have to split the parent box into two boxes and move children
+ // from |beforeChild| to end into the new post box.
+ auto newPostBox = boxToSplit.createAnonymousBoxWithSameTypeAs(parent);
+ auto& postBox = *newPostBox;
+ postBox.setChildrenInline(boxToSplit.childrenInline());
+ RenderBox* parentBox = downcast<RenderBox>(boxToSplit.parent());
+ // We need to invalidate the |parentBox| before inserting the new node
+ // so that the table repainting logic knows the structure is dirty.
+ // See for example RenderTableCell:clippedOverflowRectForRepaint.
+ markBoxForRelayoutAfterSplit(*parentBox);
+ parentBox->insertChildInternal(WTFMove(newPostBox), boxToSplit.nextSibling());
+ boxToSplit.moveChildrenTo(&postBox, beforeChild, nullptr, RenderBoxModelObject::NormalizeAfterInsertion::Yes);
+
+ markBoxForRelayoutAfterSplit(boxToSplit);
+ markBoxForRelayoutAfterSplit(postBox);
+
+ beforeChild = &postBox;
+ } else
+ beforeChild = &boxToSplit;
+ }
+
+ if (didSplitParentAnonymousBoxes)
+ markBoxForRelayoutAfterSplit(parent);
+
+ ASSERT(beforeChild->parent() == &parent);
+ return beforeChild;
+}
+
void RenderTreeBuilder::updateAfterDescendants(RenderElement& renderer)
{
if (is<RenderBlock>(renderer))
Modified: trunk/Source/WebCore/rendering/updating/RenderTreeBuilder.h (226515 => 226516)
--- trunk/Source/WebCore/rendering/updating/RenderTreeBuilder.h 2018-01-08 17:02:33 UTC (rev 226515)
+++ trunk/Source/WebCore/rendering/updating/RenderTreeBuilder.h 2018-01-08 17:40:21 UTC (rev 226516)
@@ -46,6 +46,12 @@
// FIXME: Remove.
static RenderTreeBuilder* current() { return s_current; }
+ // These functions are temporary until after all block/inline/continuation code is moved over.
+ void insertChildToRenderBlock(RenderBlock& parent, RenderPtr<RenderObject>, RenderObject* beforeChild = nullptr);
+ void insertChildToRenderBlockIgnoringContinuation(RenderBlock& parent, RenderPtr<RenderObject>, RenderObject* beforeChild = nullptr);
+ void makeChildrenNonInline(RenderBlock& parent, RenderObject* insertionPoint = nullptr);
+ RenderObject* splitAnonymousBoxesAroundChild(RenderBox& parent, RenderObject* beforeChild);
+
private:
class FirstLetter;
class List;
@@ -53,6 +59,7 @@
class Table;
class Ruby;
class FormControls;
+ class Block;
FirstLetter& firstLetterBuilder() { return *m_firstLetterBuilder; }
List& listBuilder() { return *m_listBuilder; }
@@ -60,6 +67,7 @@
Table& tableBuilder() { return *m_tableBuilder; }
Ruby& rubyBuilder() { return *m_rubyBuilder; }
FormControls& formControlsBuilder() { return *m_formControlsBuilder; }
+ Block& blockBuilder() { return *m_blockBuilder; }
RenderView& m_view;
@@ -72,6 +80,7 @@
std::unique_ptr<Table> m_tableBuilder;
std::unique_ptr<Ruby> m_rubyBuilder;
std::unique_ptr<FormControls> m_formControlsBuilder;
+ std::unique_ptr<Block> m_blockBuilder;
};
}
Added: trunk/Source/WebCore/rendering/updating/RenderTreeBuilderBlock.cpp (0 => 226516)
--- trunk/Source/WebCore/rendering/updating/RenderTreeBuilderBlock.cpp (rev 0)
+++ trunk/Source/WebCore/rendering/updating/RenderTreeBuilderBlock.cpp 2018-01-08 17:40:21 UTC (rev 226516)
@@ -0,0 +1,200 @@
+/*
+ * Copyright (C) 2017 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "config.h"
+#include "RenderTreeBuilderBlock.h"
+
+#include "RenderChildIterator.h"
+#include "RenderFullScreen.h"
+
+namespace WebCore {
+
+static RenderBlock* continuationBefore(RenderBlock& parent, RenderObject* beforeChild)
+{
+ if (beforeChild && beforeChild->parent() == &parent)
+ return &parent;
+
+ RenderBlock* nextToLast = &parent;
+ RenderBlock* last = &parent;
+ for (auto* current = downcast<RenderBlock>(parent.continuation()); current; current = downcast<RenderBlock>(current->continuation())) {
+ if (beforeChild && beforeChild->parent() == current) {
+ if (current->firstChild() == beforeChild)
+ return last;
+ return current;
+ }
+
+ nextToLast = last;
+ last = current;
+ }
+
+ if (!beforeChild && !last->firstChild())
+ return nextToLast;
+ return last;
+}
+
+RenderTreeBuilder::Block::Block(RenderTreeBuilder& builder)
+ : m_builder(builder)
+{
+}
+
+void RenderTreeBuilder::Block::insertChild(RenderBlock& parent, RenderPtr<RenderObject> child, RenderObject* beforeChild)
+{
+ if (parent.continuation() && !parent.isAnonymousBlock())
+ insertChildToContinuation(parent, WTFMove(child), beforeChild);
+ else
+ insertChildIgnoringContinuation(parent, WTFMove(child), beforeChild);
+}
+
+void RenderTreeBuilder::Block::insertChildToContinuation(RenderBlock& parent, RenderPtr<RenderObject> child, RenderObject* beforeChild)
+{
+ RenderBlock* flow = continuationBefore(parent, beforeChild);
+ ASSERT(!beforeChild || is<RenderBlock>(*beforeChild->parent()));
+ RenderBoxModelObject* beforeChildParent = nullptr;
+ if (beforeChild)
+ beforeChildParent = downcast<RenderBoxModelObject>(beforeChild->parent());
+ else {
+ RenderBoxModelObject* continuation = flow->continuation();
+ if (continuation)
+ beforeChildParent = continuation;
+ else
+ beforeChildParent = flow;
+ }
+
+ if (child->isFloatingOrOutOfFlowPositioned()) {
+ beforeChildParent->addChildIgnoringContinuation(m_builder, WTFMove(child), beforeChild);
+ return;
+ }
+
+ bool childIsNormal = child->isInline() || !child->style().columnSpan();
+ bool bcpIsNormal = beforeChildParent->isInline() || !beforeChildParent->style().columnSpan();
+ bool flowIsNormal = flow->isInline() || !flow->style().columnSpan();
+
+ if (flow == beforeChildParent) {
+ flow->addChildIgnoringContinuation(m_builder, WTFMove(child), beforeChild);
+ return;
+ }
+
+ // The goal here is to match up if we can, so that we can coalesce and create the
+ // minimal # of continuations needed for the inline.
+ if (childIsNormal == bcpIsNormal) {
+ beforeChildParent->addChildIgnoringContinuation(m_builder, WTFMove(child), beforeChild);
+ return;
+ }
+ if (flowIsNormal == childIsNormal) {
+ flow->addChildIgnoringContinuation(m_builder, WTFMove(child), nullptr); // Just treat like an append.
+ return;
+ }
+ beforeChildParent->addChildIgnoringContinuation(m_builder, WTFMove(child), beforeChild);
+}
+
+void RenderTreeBuilder::Block::insertChildIgnoringContinuation(RenderBlock& parent, RenderPtr<RenderObject> child, RenderObject* beforeChild)
+{
+ if (beforeChild && beforeChild->parent() != &parent) {
+ RenderElement* beforeChildContainer = beforeChild->parent();
+ while (beforeChildContainer->parent() != &parent)
+ beforeChildContainer = beforeChildContainer->parent();
+ ASSERT(beforeChildContainer);
+
+ if (beforeChildContainer->isAnonymous()) {
+ RELEASE_ASSERT_WITH_SECURITY_IMPLICATION(!beforeChildContainer->isInline());
+
+ // If the requested beforeChild is not one of our children, then this is because
+ // there is an anonymous container within this object that contains the beforeChild.
+ RenderElement* beforeChildAnonymousContainer = beforeChildContainer;
+ if (beforeChildAnonymousContainer->isAnonymousBlock()
+#if ENABLE(FULLSCREEN_API)
+ // Full screen renderers and full screen placeholders act as anonymous blocks, not tables:
+ || beforeChildAnonymousContainer->isRenderFullScreen()
+ || beforeChildAnonymousContainer->isRenderFullScreenPlaceholder()
+#endif
+ ) {
+ // Insert the child into the anonymous block box instead of here.
+ if (child->isInline() || beforeChild->parent()->firstChild() != beforeChild)
+ m_builder.insertChild(*beforeChild->parent(), WTFMove(child), beforeChild);
+ else
+ m_builder.insertChild(parent, WTFMove(child), beforeChild->parent());
+ return;
+ }
+
+ ASSERT(beforeChildAnonymousContainer->isTable());
+
+ if (child->isTablePart()) {
+ // Insert into the anonymous table.
+ m_builder.insertChild(*beforeChildAnonymousContainer, WTFMove(child), beforeChild);
+ return;
+ }
+
+ beforeChild = m_builder.splitAnonymousBoxesAroundChild(parent, beforeChild);
+
+ RELEASE_ASSERT_WITH_SECURITY_IMPLICATION(beforeChild->parent() == &parent);
+ }
+ }
+
+ bool madeBoxesNonInline = false;
+
+ // A block has to either have all of its children inline, or all of its children as blocks.
+ // So, if our children are currently inline and a block child has to be inserted, we move all our
+ // inline children into anonymous block boxes.
+ if (parent.childrenInline() && !child->isInline() && !child->isFloatingOrOutOfFlowPositioned()) {
+ // This is a block with inline content. Wrap the inline content in anonymous blocks.
+ m_builder.makeChildrenNonInline(parent, beforeChild);
+ madeBoxesNonInline = true;
+
+ if (beforeChild && beforeChild->parent() != &parent) {
+ beforeChild = beforeChild->parent();
+ ASSERT(beforeChild->isAnonymousBlock());
+ ASSERT(beforeChild->parent() == &parent);
+ }
+ } else if (!parent.childrenInline() && (child->isFloatingOrOutOfFlowPositioned() || child->isInline())) {
+ // If we're inserting an inline child but all of our children are blocks, then we have to make sure
+ // it is put into an anomyous block box. We try to use an existing anonymous box if possible, otherwise
+ // a new one is created and inserted into our list of children in the appropriate position.
+ RenderObject* afterChild = beforeChild ? beforeChild->previousSibling() : parent.lastChild();
+
+ if (afterChild && afterChild->isAnonymousBlock()) {
+ m_builder.insertChild(downcast<RenderBlock>(*afterChild), WTFMove(child));
+ return;
+ }
+
+ if (child->isInline()) {
+ // No suitable existing anonymous box - create a new one.
+ auto newBox = parent.createAnonymousBlock();
+ auto& box = *newBox;
+ parent.RenderBox::addChild(m_builder, WTFMove(newBox), beforeChild);
+ m_builder.insertChild(box, WTFMove(child));
+ return;
+ }
+ }
+
+ parent.invalidateLineLayoutPath();
+
+ parent.RenderBox::addChild(m_builder, WTFMove(child), beforeChild);
+
+ if (madeBoxesNonInline && is<RenderBlock>(parent.parent()) && parent.isAnonymousBlock())
+ downcast<RenderBlock>(*parent.parent()).removeLeftoverAnonymousBlock(&parent);
+ // parent object may be dead here
+}
+
+}
Added: trunk/Source/WebCore/rendering/updating/RenderTreeBuilderBlock.h (0 => 226516)
--- trunk/Source/WebCore/rendering/updating/RenderTreeBuilderBlock.h (rev 0)
+++ trunk/Source/WebCore/rendering/updating/RenderTreeBuilderBlock.h 2018-01-08 17:40:21 UTC (rev 226516)
@@ -0,0 +1,46 @@
+/*
+ * Copyright (C) 2017 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#pragma once
+
+#include "RenderTreeBuilder.h"
+
+namespace WebCore {
+
+class RenderTreeBuilder::Block {
+public:
+ Block(RenderTreeBuilder&);
+
+ void insertChild(RenderBlock& parent, RenderPtr<RenderObject> child, RenderObject* beforeChild);
+ void insertChildIgnoringContinuation(RenderBlock& parent, RenderPtr<RenderObject> child, RenderObject* beforeChild);
+
+private:
+ void insertChildToContinuation(RenderBlock& parent, RenderPtr<RenderObject> child, RenderObject* beforeChild);
+
+ RenderTreeBuilder& m_builder;
+};
+
+}
+