diff options
Diffstat (limited to 'Source/WebCore/rendering/LogicalSelectionOffsetCaches.h')
-rw-r--r-- | Source/WebCore/rendering/LogicalSelectionOffsetCaches.h | 100 |
1 files changed, 22 insertions, 78 deletions
diff --git a/Source/WebCore/rendering/LogicalSelectionOffsetCaches.h b/Source/WebCore/rendering/LogicalSelectionOffsetCaches.h index 118111bbe..ecd63fd19 100644 --- a/Source/WebCore/rendering/LogicalSelectionOffsetCaches.h +++ b/Source/WebCore/rendering/LogicalSelectionOffsetCaches.h @@ -18,96 +18,40 @@ * */ -#ifndef LogicalSelectionOffsetCaches_h -#define LogicalSelectionOffsetCaches_h +#pragma once #include "RenderBlock.h" namespace WebCore { -static inline bool isContainingBlockCandidateForAbsolutelyPositionedObject(RenderElement& object) -{ - return object.style().position() != StaticPosition - || (object.hasTransform() && object.isRenderBlock()) -#if ENABLE(SVG) - || object.isSVGForeignObject() -#endif - || object.isRenderView(); -} - -static inline bool isNonRenderBlockInline(RenderElement& object) -{ - return (object.isInline() && !object.isReplaced()) || !object.isRenderBlock(); -} - -static inline RenderBlock* containingBlockForFixedPosition(RenderElement* parent) -{ - RenderElement* object = parent; - while (object && !object->canContainFixedPositionObjects()) - object = object->parent(); - ASSERT(!object || !object->isAnonymousBlock()); - return toRenderBlock(object); -} - -static inline RenderBlock* containingBlockForAbsolutePosition(RenderElement* parent) -{ - RenderElement* object = parent; - while (object && !isContainingBlockCandidateForAbsolutelyPositionedObject(*object)) - object = object->parent(); - - // For a relatively positioned inline, return its nearest non-anonymous containing block, - // not the inline itself, to avoid having a positioned objects list in all RenderInlines - // and use RenderBlock* as RenderElement::containingBlock's return type. - // Use RenderBlock::container() to obtain the inline. - if (object && !object->isRenderBlock()) - object = object->containingBlock(); - - while (object && object->isAnonymousBlock()) - object = object->containingBlock(); - - return toRenderBlock(object); -} - -static inline RenderBlock* containingBlockForObjectInFlow(RenderElement* parent) -{ - RenderElement* object = parent; - while (object && isNonRenderBlockInline(*object)) - object = object->parent(); - return toRenderBlock(object); -} - class LogicalSelectionOffsetCaches { public: class ContainingBlockInfo { public: ContainingBlockInfo() - : m_block(0) - , m_cache(0) - , m_hasFloatsOrFlowThreads(false) + : m_hasFloatsOrFlowThreads(false) , m_cachedLogicalLeftSelectionOffset(false) , m_cachedLogicalRightSelectionOffset(false) { } - void setBlock(RenderBlock* block, const LogicalSelectionOffsetCaches* cache) + void setBlock(RenderBlock* block, const LogicalSelectionOffsetCaches* cache, bool parentCacheHasFloatsOrFlowThreads = false) { m_block = block; - m_hasFloatsOrFlowThreads = m_hasFloatsOrFlowThreads || m_block->containsFloats() || m_block->flowThreadContainingBlock(); + bool blockHasFloatsOrFlowThreads = m_block ? (m_block->containsFloats() || m_block->flowThreadContainingBlock()) : false; + m_hasFloatsOrFlowThreads = parentCacheHasFloatsOrFlowThreads || m_hasFloatsOrFlowThreads || blockHasFloatsOrFlowThreads; m_cache = cache; m_cachedLogicalLeftSelectionOffset = false; m_cachedLogicalRightSelectionOffset = false; } - RenderBlock* block() const { return m_block; } - const LogicalSelectionOffsetCaches* cache() const { return m_cache; } - LayoutUnit logicalLeftSelectionOffset(RenderBlock& rootBlock, LayoutUnit position) const { ASSERT(m_cache); if (m_hasFloatsOrFlowThreads || !m_cachedLogicalLeftSelectionOffset) { m_cachedLogicalLeftSelectionOffset = true; - m_logicalLeftSelectionOffset = m_block->logicalLeftSelectionOffset(rootBlock, position, *m_cache); + m_logicalLeftSelectionOffset = m_block ? m_block->logicalLeftSelectionOffset(rootBlock, position, *m_cache) : LayoutUnit::fromPixel(0); } else - ASSERT(m_logicalLeftSelectionOffset == m_block->logicalLeftSelectionOffset(rootBlock, position, *m_cache)); + ASSERT(m_logicalLeftSelectionOffset == (m_block ? m_block->logicalLeftSelectionOffset(rootBlock, position, *m_cache) : LayoutUnit::fromPixel(0))); return m_logicalLeftSelectionOffset; } @@ -116,15 +60,19 @@ public: ASSERT(m_cache); if (m_hasFloatsOrFlowThreads || !m_cachedLogicalRightSelectionOffset) { m_cachedLogicalRightSelectionOffset = true; - m_logicalRightSelectionOffset = m_block->logicalRightSelectionOffset(rootBlock, position, *m_cache); + m_logicalRightSelectionOffset = m_block ? m_block->logicalRightSelectionOffset(rootBlock, position, *m_cache) : LayoutUnit::fromPixel(0); } else - ASSERT(m_logicalRightSelectionOffset == m_block->logicalRightSelectionOffset(rootBlock, position, *m_cache)); + ASSERT(m_logicalRightSelectionOffset == (m_block ? m_block->logicalRightSelectionOffset(rootBlock, position, *m_cache) : LayoutUnit::fromPixel(0))); return m_logicalRightSelectionOffset; } + RenderBlock* block() const { return m_block; } + const LogicalSelectionOffsetCaches* cache() const { return m_cache; } + bool hasFloatsOrFlowThreads() const { return m_hasFloatsOrFlowThreads; } + private: - RenderBlock* m_block; - const LogicalSelectionOffsetCaches* m_cache; + RenderBlock* m_block { nullptr }; + const LogicalSelectionOffsetCaches* m_cache { nullptr }; bool m_hasFloatsOrFlowThreads : 1; mutable bool m_cachedLogicalLeftSelectionOffset : 1; mutable bool m_cachedLogicalRightSelectionOffset : 1; @@ -140,12 +88,10 @@ public: // such that we can remove this assertion. ASSERT(rootBlock.isSelectionRoot()); #endif - auto parent = rootBlock.parent(); - // LogicalSelectionOffsetCaches should not be used on an orphaned tree. - m_containingBlockForFixedPosition.setBlock(containingBlockForFixedPosition(parent), 0); - m_containingBlockForAbsolutePosition.setBlock(containingBlockForAbsolutePosition(parent), 0); - m_containingBlockForInflowPosition.setBlock(containingBlockForObjectInFlow(parent), 0); + m_containingBlockForFixedPosition.setBlock(rootBlock.containingBlockForFixedPosition(), nullptr); + m_containingBlockForAbsolutePosition.setBlock(rootBlock.containingBlockForAbsolutePosition(), nullptr); + m_containingBlockForInflowPosition.setBlock(rootBlock.containingBlockForObjectInFlow(), nullptr); } LogicalSelectionOffsetCaches(RenderBlock& block, const LogicalSelectionOffsetCaches& cache) @@ -153,12 +99,12 @@ public: , m_containingBlockForAbsolutePosition(cache.m_containingBlockForAbsolutePosition) { if (block.canContainFixedPositionObjects()) - m_containingBlockForFixedPosition.setBlock(&block, &cache); + m_containingBlockForFixedPosition.setBlock(&block, &cache, cache.m_containingBlockForFixedPosition.hasFloatsOrFlowThreads()); - if (isContainingBlockCandidateForAbsolutelyPositionedObject(block) && !block.isRenderInline() && !block.isAnonymousBlock()) - m_containingBlockForFixedPosition.setBlock(&block, &cache); + if (block.canContainAbsolutelyPositionedObjects() && !block.isRenderInline() && !block.isAnonymousBlock()) + m_containingBlockForAbsolutePosition.setBlock(&block, &cache, cache.m_containingBlockForAbsolutePosition.hasFloatsOrFlowThreads()); - m_containingBlockForInflowPosition.setBlock(&block, &cache); + m_containingBlockForInflowPosition.setBlock(&block, &cache, cache.m_containingBlockForInflowPosition.hasFloatsOrFlowThreads()); } const ContainingBlockInfo& containingBlockInfo(RenderBlock& block) const @@ -183,5 +129,3 @@ private: }; } // namespace WebCore - -#endif // LogicalSelectionOffsetCaches_h |