提交 9423819d 编写于 作者: O Ojan Vafai

First pass at removing position:fixed.

The root is never scrollable, so position:fixed doesn't
do anything anymore.

Also remove some dead frame-level scrolling code that interacted
with fixed position things.

R=esprehn@chromium.org

Review URL: https://codereview.chromium.org/686633002
上级 6b828261
......@@ -1721,9 +1721,6 @@ template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EPosition e)
case AbsolutePosition:
m_value.valueID = CSSValueAbsolute;
break;
case FixedPosition:
m_value.valueID = CSSValueFixed;
break;
}
}
......@@ -1737,8 +1734,6 @@ template<> inline CSSPrimitiveValue::operator EPosition() const
return RelativePosition;
case CSSValueAbsolute:
return AbsolutePosition;
case CSSValueFixed:
return FixedPosition;
default:
break;
}
......
......@@ -138,7 +138,6 @@ void StyleAdjuster::adjustRenderStyle(RenderStyle* style, RenderStyle* parentSty
|| style->hasFilter()
|| style->hasBlendMode()
|| style->hasIsolation()
|| style->position() == FixedPosition
|| hasWillChangeThatCreatesStackingContext(style)))
style->setZIndex(0);
......
......@@ -771,61 +771,8 @@ void FrameView::scrollContentsIfNeeded()
bool FrameView::scrollContentsFastPath(const IntSize& scrollDelta)
{
if (!contentsInCompositedLayer() || hasSlowRepaintObjects())
return false;
if (!m_viewportConstrainedObjects || m_viewportConstrainedObjects->isEmpty())
return true;
Region regionToUpdate;
ViewportConstrainedObjectSet::const_iterator end = m_viewportConstrainedObjects->end();
for (ViewportConstrainedObjectSet::const_iterator it = m_viewportConstrainedObjects->begin(); it != end; ++it) {
RenderObject* renderer = *it;
ASSERT(renderer->style()->hasViewportConstrainedPosition());
ASSERT(renderer->hasLayer());
RenderLayer* layer = toRenderBoxModelObject(renderer)->layer();
CompositingState state = layer->compositingState();
if (state == PaintsIntoOwnBacking || state == PaintsIntoGroupedBacking)
continue;
// If the fixed layer has a blur/drop-shadow filter applied on at least one of its parents, we cannot
// scroll using the fast path, otherwise the outsets of the filter will be moved around the page.
if (layer->hasAncestorWithFilterOutsets())
return false;
IntRect updateRect = pixelSnappedIntRect(layer->paintInvalidator().paintInvalidationRectIncludingNonCompositingDescendants());
const RenderLayerModelObject* repaintContainer = layer->renderer()->containerForPaintInvalidation();
if (repaintContainer && !repaintContainer->isRenderView()) {
// Invalidate the old and new locations of fixed position elements that are not drawn into the RenderView.
updateRect.moveBy(scrollPosition());
IntRect previousRect = updateRect;
previousRect.move(scrollDelta);
// FIXME: Rather than uniting the rects, we should just issue both invalidations.
updateRect.unite(previousRect);
layer->renderer()->invalidatePaintUsingContainer(repaintContainer, updateRect, InvalidationScroll);
} else {
// Coalesce the paint invalidations that will be issued to the renderView.
updateRect = contentsToRootView(updateRect);
if (!updateRect.isEmpty())
regionToUpdate.unite(updateRect);
}
}
// Invalidate the old and new locations of fixed position elements that are drawn into the RenderView.
Vector<IntRect> subRectsToUpdate = regionToUpdate.rects();
size_t viewportConstrainedObjectsCount = subRectsToUpdate.size();
for (size_t i = 0; i < viewportConstrainedObjectsCount; ++i) {
IntRect updateRect = subRectsToUpdate[i];
IntRect scrolledRect = updateRect;
scrolledRect.move(-scrollDelta);
updateRect.unite(scrolledRect);
// FIXME: We should be able to issue these invalidations separately and before we actually scroll.
renderView()->layer()->paintInvalidator().setBackingNeedsPaintInvalidationInRect(rootViewToContents(updateRect));
}
return true;
// FIXME(sky): Remove
return false;
}
void FrameView::scrollContentsSlowPath(const IntRect& updateRect)
......@@ -897,28 +844,7 @@ void FrameView::updateLayersAndCompositingAfterScrollIfNeeded()
void FrameView::updateFixedElementPaintInvalidationRectsAfterScroll()
{
if (!hasViewportConstrainedObjects())
return;
// Update the paint invalidation rects for fixed elements after scrolling and invalidation to reflect
// the new scroll position.
ViewportConstrainedObjectSet::const_iterator end = m_viewportConstrainedObjects->end();
for (ViewportConstrainedObjectSet::const_iterator it = m_viewportConstrainedObjects->begin(); it != end; ++it) {
RenderObject* renderer = *it;
// m_viewportConstrainedObjects should not contain non-viewport constrained objects.
ASSERT(renderer->style()->hasViewportConstrainedPosition());
// Fixed items should always have layers.
ASSERT(renderer->hasLayer());
RenderLayer* layer = toRenderBoxModelObject(renderer)->layer();
// Don't need to do this for composited fixed items.
if (layer->compositingState() == PaintsIntoOwnBacking)
continue;
layer->paintInvalidator().computePaintInvalidationRectsIncludingNonCompositingDescendants();
}
// FIXME(sky): Remove
}
void FrameView::updateCompositedSelectionBoundsIfNeeded()
......
......@@ -169,20 +169,7 @@ static void clearPositionConstraintExceptForLayer(GraphicsLayer* layer, Graphics
static WebLayerPositionConstraint computePositionConstraint(const RenderLayer* layer)
{
ASSERT(layer->hasCompositedLayerMapping());
do {
if (layer->renderer()->style()->position() == FixedPosition) {
const RenderObject* fixedPositionObject = layer->renderer();
bool fixedToRight = !fixedPositionObject->style()->right().isAuto();
bool fixedToBottom = !fixedPositionObject->style()->bottom().isAuto();
return WebLayerPositionConstraint::fixedPosition(fixedToRight, fixedToBottom);
}
layer = layer->parent();
// Composited layers that inherit a fixed position state will be positioned with respect to the nearest compositedLayerMapping's GraphicsLayer.
// So, once we find a layer that has its own compositedLayerMapping, we can stop searching for a fixed position RenderObject.
} while (layer && !layer->hasCompositedLayerMapping());
// FIXME(sky): Remove
return WebLayerPositionConstraint();
}
......@@ -791,30 +778,7 @@ void ScrollingCoordinator::handleWheelEventPhase(PlatformWheelEventPhase phase)
bool ScrollingCoordinator::hasVisibleSlowRepaintViewportConstrainedObjects(FrameView* frameView) const
{
const FrameView::ViewportConstrainedObjectSet* viewportConstrainedObjects = frameView->viewportConstrainedObjects();
if (!viewportConstrainedObjects)
return false;
for (FrameView::ViewportConstrainedObjectSet::const_iterator it = viewportConstrainedObjects->begin(), end = viewportConstrainedObjects->end(); it != end; ++it) {
RenderObject* renderer = *it;
ASSERT(renderer->isBoxModelObject() && renderer->hasLayer());
ASSERT(renderer->style()->position() == FixedPosition);
RenderLayer* layer = toRenderBoxModelObject(renderer)->layer();
// Whether the RenderLayer scrolls with the viewport is a tree-depenent
// property and our viewportConstrainedObjects collection is maintained
// with only RenderObject-level information.
if (!layer->scrollsWithViewport())
continue;
// We're only smart enough to scroll viewport-constrainted objects
// in the compositor if they have their own backing or they paint
// into a grouped back (which necessarily all have the same viewport
// constraints).
CompositingState compositingState = layer->compositingState();
if (compositingState != PaintsIntoOwnBacking && compositingState != PaintsIntoGroupedBacking)
return true;
}
// FIXME(sky): Remove
return false;
}
......
......@@ -52,7 +52,6 @@ public:
void reset(const LayoutRect& r)
{
m_overflowClipRect = r;
m_fixedClipRect = r;
m_posClipRect = r;
m_fixed = 0;
}
......@@ -60,9 +59,6 @@ public:
const ClipRect& overflowClipRect() const { return m_overflowClipRect; }
void setOverflowClipRect(const ClipRect& r) { m_overflowClipRect = r; }
const ClipRect& fixedClipRect() const { return m_fixedClipRect; }
void setFixedClipRect(const ClipRect&r) { m_fixedClipRect = r; }
const ClipRect& posClipRect() const { return m_posClipRect; }
void setPosClipRect(const ClipRect& r) { m_posClipRect = r; }
......@@ -79,7 +75,6 @@ public:
bool operator==(const ClipRects& other) const
{
return m_overflowClipRect == other.overflowClipRect()
&& m_fixedClipRect == other.fixedClipRect()
&& m_posClipRect == other.posClipRect()
&& fixed() == other.fixed();
}
......@@ -87,7 +82,6 @@ public:
ClipRects& operator=(const ClipRects& other)
{
m_overflowClipRect = other.overflowClipRect();
m_fixedClipRect = other.fixedClipRect();
m_posClipRect = other.posClipRect();
m_fixed = other.fixed();
return *this;
......@@ -96,7 +90,6 @@ public:
private:
ClipRects(const LayoutRect& r)
: m_overflowClipRect(r)
, m_fixedClipRect(r)
, m_posClipRect(r)
, m_refCnt(1)
, m_fixed(0)
......@@ -105,7 +98,6 @@ private:
ClipRects(const ClipRects& other)
: m_overflowClipRect(other.overflowClipRect())
, m_fixedClipRect(other.fixedClipRect())
, m_posClipRect(other.posClipRect())
, m_refCnt(1)
, m_fixed(other.fixed())
......@@ -113,7 +105,6 @@ private:
}
ClipRect m_overflowClipRect;
ClipRect m_fixedClipRect;
ClipRect m_posClipRect;
unsigned m_refCnt : 31;
unsigned m_fixed : 1;
......
......@@ -48,16 +48,9 @@ LayoutState::LayoutState(RenderBox& renderer, const LayoutSize& offset, bool con
, m_renderer(renderer)
{
renderer.view()->pushLayoutState(*this);
bool fixed = renderer.isOutOfFlowPositioned() && renderer.style()->position() == FixedPosition;
if (fixed) {
// FIXME: This doesn't work correctly with transforms.
FloatPoint fixedOffset = renderer.view()->localToAbsolute(FloatPoint(), IsFixed);
m_layoutOffset = LayoutSize(fixedOffset.x(), fixedOffset.y()) + offset;
} else {
m_layoutOffset = m_next->m_layoutOffset + offset;
}
m_layoutOffset = m_next->m_layoutOffset + offset;
if (renderer.isOutOfFlowPositioned() && !fixed) {
if (renderer.isOutOfFlowPositioned()) {
if (RenderObject* container = renderer.container()) {
if (container->style()->hasInFlowPosition() && container->isRenderInline())
m_layoutOffset += toRenderInline(container)->offsetForInFlowPositionedInline(renderer);
......
......@@ -42,7 +42,6 @@ PaintInvalidationState::PaintInvalidationState(const PaintInvalidationState& nex
{
// FIXME: SVG could probably benefit from a stack-based optimization like html does. crbug.com/391054
bool establishesPaintInvalidationContainer = &m_renderer == &m_paintInvalidationContainer;
bool fixed = m_renderer.style()->position() == FixedPosition;
if (establishesPaintInvalidationContainer) {
// When we hit a new paint invalidation container, we don't need to
......@@ -53,15 +52,10 @@ PaintInvalidationState::PaintInvalidationState(const PaintInvalidationState& nex
if (!renderer.supportsPaintInvalidationStateCachedOffsets() || !next.m_cachedOffsetsEnabled) {
m_cachedOffsetsEnabled = false;
} else {
if (fixed) {
FloatPoint fixedOffset = m_renderer.localToContainerPoint(FloatPoint(), &m_paintInvalidationContainer, TraverseDocumentBoundaries);
m_paintOffset = LayoutSize(fixedOffset.x(), fixedOffset.y());
} else {
LayoutSize offset = m_renderer.isBox() ? toRenderBox(renderer).locationOffset() : LayoutSize();
m_paintOffset = next.m_paintOffset + offset;
}
LayoutSize offset = m_renderer.isBox() ? toRenderBox(renderer).locationOffset() : LayoutSize();
m_paintOffset = next.m_paintOffset + offset;
if (m_renderer.isOutOfFlowPositioned() && !fixed) {
if (m_renderer.isOutOfFlowPositioned()) {
if (RenderObject* container = m_renderer.container()) {
if (container->style()->hasInFlowPosition() && container->isRenderInline())
m_paintOffset += toRenderInline(container)->offsetForInFlowPositionedInline(toRenderBox(renderer));
......@@ -72,7 +66,7 @@ PaintInvalidationState::PaintInvalidationState(const PaintInvalidationState& nex
m_paintOffset += renderer.layer()->offsetForInFlowPosition();
}
m_clipped = !fixed && next.m_clipped;
m_clipped = next.m_clipped;
if (m_clipped)
m_clipRect = next.m_clipRect;
}
......
......@@ -1096,10 +1096,7 @@ void RenderBlock::addOverflowFromPositionedObjects()
TrackedRendererListHashSet::iterator end = positionedDescendants->end();
for (TrackedRendererListHashSet::iterator it = positionedDescendants->begin(); it != end; ++it) {
positionedObject = *it;
// Fixed positioned elements don't contribute to layout overflow, since they don't scroll with the content.
if (positionedObject->style()->position() != FixedPosition)
addOverflowFromChild(positionedObject, LayoutSize(positionedObject->x(), positionedObject->y()));
addOverflowFromChild(positionedObject, LayoutSize(positionedObject->x(), positionedObject->y()));
}
}
......@@ -1204,33 +1201,7 @@ bool RenderBlock::simplifiedLayout()
void RenderBlock::markFixedPositionObjectForLayoutIfNeeded(RenderObject* child, SubtreeLayoutScope& layoutScope)
{
if (child->style()->position() != FixedPosition)
return;
bool hasStaticBlockPosition = child->style()->hasStaticBlockPosition(isHorizontalWritingMode());
bool hasStaticInlinePosition = child->style()->hasStaticInlinePosition(isHorizontalWritingMode());
if (!hasStaticBlockPosition && !hasStaticInlinePosition)
return;
RenderObject* o = child->parent();
while (o && !o->isRenderView() && o->style()->position() != AbsolutePosition)
o = o->parent();
if (o->style()->position() != AbsolutePosition)
return;
RenderBox* box = toRenderBox(child);
if (hasStaticInlinePosition) {
LogicalExtentComputedValues computedValues;
box->computeLogicalWidth(computedValues);
LayoutUnit newLeft = computedValues.m_position;
if (newLeft != box->logicalLeft())
layoutScope.setChildNeedsLayout(child);
} else if (hasStaticBlockPosition) {
LayoutUnit oldTop = box->logicalTop();
box->updateLogicalHeight();
if (box->logicalTop() != oldTop)
layoutScope.setChildNeedsLayout(child);
}
// FIXME(sky): Remove
}
LayoutUnit RenderBlock::marginIntrinsicLogicalWidthForChild(RenderBox* child) const
......@@ -3195,7 +3166,7 @@ bool RenderBlock::recalcChildOverflowAfterStyleChange()
if (!box->needsOverflowRecalcAfterStyleChange())
continue;
RenderBlock* block = toRenderBlock(box);
if (!block->recalcOverflowAfterStyleChange() || box->style()->position() == FixedPosition)
if (!block->recalcOverflowAfterStyleChange())
continue;
childrenOverflowChanged = true;
......
......@@ -1556,14 +1556,11 @@ void RenderBox::mapLocalToContainer(const RenderLayerModelObject* paintInvalidat
if (!o)
return;
bool isFixedPos = style()->position() == FixedPosition;
bool hasTransform = hasLayer() && layer()->transform();
// If this box has a transform, it acts as a fixed position container for fixed descendants,
// and may itself also be fixed position. So propagate 'fixed' up only if this box is fixed position.
if (hasTransform && !isFixedPos)
if (hasTransform)
mode &= ~IsFixed;
else if (isFixedPos)
mode |= IsFixed;
if (wasFixed)
*wasFixed = mode & IsFixed;
......@@ -1593,14 +1590,12 @@ void RenderBox::mapLocalToContainer(const RenderLayerModelObject* paintInvalidat
void RenderBox::mapAbsoluteToLocalPoint(MapCoordinatesFlags mode, TransformState& transformState) const
{
bool isFixedPos = style()->position() == FixedPosition;
bool hasTransform = hasLayer() && layer()->transform();
if (hasTransform && !isFixedPos) {
if (hasTransform) {
// If this box has a transform, it acts as a fixed position container for fixed descendants,
// and may itself also be fixed position. So propagate 'fixed' up only if this box is fixed position.
mode &= ~IsFixed;
} else if (isFixedPos)
mode |= IsFixed;
}
RenderBoxModelObject::mapAbsoluteToLocalPoint(mode, transformState);
}
......@@ -1726,7 +1721,7 @@ void RenderBox::mapRectToPaintInvalidationBacking(const RenderLayerModelObject*
// included into the visual overflow for repaint, we wouldn't have this issue.
inflatePaintInvalidationRectForReflectionAndFilter(rect);
if (paintInvalidationState && paintInvalidationState->canMapToContainer(paintInvalidationContainer) && position != FixedPosition) {
if (paintInvalidationState && paintInvalidationState->canMapToContainer(paintInvalidationContainer)) {
if (layer() && layer()->transform())
rect = layer()->transform()->mapRect(pixelSnappedIntRect(rect));
......@@ -2455,15 +2450,6 @@ LayoutUnit RenderBox::containingBlockLogicalWidthForPositioned(const RenderBoxMo
if (checkForPerpendicularWritingMode && containingBlock->isHorizontalWritingMode() != isHorizontalWritingMode())
return containingBlockLogicalHeightForPositioned(containingBlock, false);
// Use viewport as container for top-level fixed-position elements.
if (style()->position() == FixedPosition && containingBlock->isRenderView()) {
const RenderView* view = toRenderView(containingBlock);
if (FrameView* frameView = view->frameView()) {
LayoutRect viewportRect = frameView->visibleContentRect();
return containingBlock->isHorizontalWritingMode() ? viewportRect.width() : viewportRect.height();
}
}
if (containingBlock->isBox())
return toRenderBox(containingBlock)->clientLogicalWidth();
......@@ -2495,15 +2481,6 @@ LayoutUnit RenderBox::containingBlockLogicalHeightForPositioned(const RenderBoxM
if (checkForPerpendicularWritingMode && containingBlock->isHorizontalWritingMode() != isHorizontalWritingMode())
return containingBlockLogicalWidthForPositioned(containingBlock, false);
// Use viewport as container for top-level fixed-position elements.
if (style()->position() == FixedPosition && containingBlock->isRenderView()) {
const RenderView* view = toRenderView(containingBlock);
if (FrameView* frameView = view->frameView()) {
LayoutRect viewportRect = frameView->visibleContentRect();
return containingBlock->isHorizontalWritingMode() ? viewportRect.height() : viewportRect.width();
}
}
if (containingBlock->isBox()) {
const RenderBlock* cb = containingBlock->isRenderBlock() ?
toRenderBlock(containingBlock) : containingBlock->containingBlock();
......
......@@ -2580,7 +2580,6 @@ const RenderObject* RenderBoxModelObject::pushMappingToContainer(const RenderLay
return 0;
bool isInline = isRenderInline();
bool isFixedPos = !isInline && style()->position() == FixedPosition;
bool hasTransform = !isInline && hasLayer() && layer()->transform();
LayoutSize adjustmentForSkippedAncestor;
......@@ -2598,10 +2597,10 @@ const RenderObject* RenderBoxModelObject::pushMappingToContainer(const RenderLay
TransformationMatrix t;
getTransformFromContainer(container, containerOffset, t);
t.translateRight(adjustmentForSkippedAncestor.width().toFloat(), adjustmentForSkippedAncestor.height().toFloat());
geometryMap.push(this, t, preserve3D, offsetDependsOnPoint, isFixedPos, hasTransform);
geometryMap.push(this, t, preserve3D, offsetDependsOnPoint, hasTransform);
} else {
containerOffset += adjustmentForSkippedAncestor;
geometryMap.push(this, containerOffset, preserve3D, offsetDependsOnPoint, isFixedPos, hasTransform);
geometryMap.push(this, containerOffset, preserve3D, offsetDependsOnPoint, hasTransform);
}
return ancestorSkipped ? ancestorToStopAt : container;
......
......@@ -38,7 +38,6 @@ RenderGeometryMap::RenderGeometryMap(MapCoordinatesFlags flags)
: m_insertionPosition(kNotFound)
, m_nonUniformStepsCount(0)
, m_transformedStepsCount(0)
, m_fixedStepsCount(0)
, m_mapCoordinatesFlags(flags)
{
}
......@@ -56,7 +55,6 @@ void RenderGeometryMap::mapToContainer(TransformState& transformState, const Ren
return;
}
bool inFixed = false;
#if ENABLE(ASSERT)
bool foundContainer = !container || (m_mapping.size() && m_mapping[0].m_renderer == container);
#endif
......@@ -72,14 +70,6 @@ void RenderGeometryMap::mapToContainer(TransformState& transformState, const Ren
break;
}
// If this box has a transform, it acts as a fixed position container
// for fixed descendants, which prevents the propagation of 'fixed'
// unless the layer itself is also fixed position.
if (i && currentStep.m_hasTransform && !currentStep.m_isFixedPosition)
inFixed = false;
else if (currentStep.m_isFixedPosition)
inFixed = true;
ASSERT(!i == isTopmostRenderView(currentStep.m_renderer));
if (!i) {
......@@ -93,11 +83,6 @@ void RenderGeometryMap::mapToContainer(TransformState& transformState, const Ren
else
transformState.move(currentStep.m_offset.width(), currentStep.m_offset.height(), accumulate);
}
if (inFixed && !currentStep.m_offsetForFixedPosition.isZero()) {
ASSERT(currentStep.m_renderer->isRenderView());
transformState.move(currentStep.m_offsetForFixedPosition);
}
}
ASSERT(foundContainer);
......@@ -108,7 +93,7 @@ FloatPoint RenderGeometryMap::mapToContainer(const FloatPoint& p, const RenderLa
{
FloatPoint result;
if (!hasFixedPositionStep() && !hasTransformStep() && !hasNonUniformStep() && (!container || (m_mapping.size() && container == m_mapping[0].m_renderer)))
if (!hasTransformStep() && !hasNonUniformStep() && (!container || (m_mapping.size() && container == m_mapping[0].m_renderer)))
result = p + m_accumulatedOffset;
else {
TransformState transformState(TransformState::ApplyTransformDirection, p);
......@@ -153,7 +138,7 @@ FloatQuad RenderGeometryMap::mapToContainer(const FloatRect& rect, const RenderL
{
FloatRect result;
if (!hasFixedPositionStep() && !hasTransformStep() && !hasNonUniformStep() && (!container || (m_mapping.size() && container == m_mapping[0].m_renderer))) {
if (!hasTransformStep() && !hasNonUniformStep() && (!container || (m_mapping.size() && container == m_mapping[0].m_renderer))) {
result = rect;
result.move(m_accumulatedOffset);
} else {
......@@ -195,7 +180,7 @@ static bool canMapBetweenRenderers(const RenderObject* renderer, const RenderObj
{
for (const RenderObject* current = renderer; ; current = current->parent()) {
const RenderStyle* style = current->style();
if (style->position() == FixedPosition || style->isFlippedBlocksWritingMode())
if (style->isFlippedBlocksWritingMode())
return false;
if (current->hasTransform())
......@@ -233,40 +218,36 @@ void RenderGeometryMap::pushMappingsToAncestor(const RenderLayer* layer, const R
TemporaryChange<size_t> positionChange(m_insertionPosition, m_mapping.size());
bool accumulatingTransform = layer->renderer()->style()->preserves3D() || ancestorLayer->renderer()->style()->preserves3D();
push(renderer, toLayoutSize(layerOffset), accumulatingTransform, /*isNonUniform*/ false, /*isFixedPosition*/ false, /*hasTransform*/ false);
push(renderer, toLayoutSize(layerOffset), accumulatingTransform, /*isNonUniform*/ false, /*hasTransform*/ false);
return;
}
const RenderLayerModelObject* ancestorRenderer = ancestorLayer ? ancestorLayer->renderer() : 0;
pushMappingsToAncestor(renderer, ancestorRenderer);
}
void RenderGeometryMap::push(const RenderObject* renderer, const LayoutSize& offsetFromContainer, bool accumulatingTransform, bool isNonUniform, bool isFixedPosition, bool hasTransform, LayoutSize offsetForFixedPosition)
void RenderGeometryMap::push(const RenderObject* renderer, const LayoutSize& offsetFromContainer, bool accumulatingTransform, bool isNonUniform, bool hasTransform)
{
// fprintf(stderr, "RenderGeometryMap::push %p %d,%d isNonUniform=%d\n", renderer, offsetFromContainer.width().toInt(), offsetFromContainer.height().toInt(), isNonUniform);
ASSERT(m_insertionPosition != kNotFound);
ASSERT(!renderer->isRenderView() || !m_insertionPosition || m_mapCoordinatesFlags & TraverseDocumentBoundaries);
ASSERT(offsetForFixedPosition.isZero() || renderer->isRenderView());
m_mapping.insert(m_insertionPosition, RenderGeometryMapStep(renderer, accumulatingTransform, isNonUniform, isFixedPosition, hasTransform));
m_mapping.insert(m_insertionPosition, RenderGeometryMapStep(renderer, accumulatingTransform, isNonUniform, hasTransform));
RenderGeometryMapStep& step = m_mapping[m_insertionPosition];
step.m_offset = offsetFromContainer;
step.m_offsetForFixedPosition = offsetForFixedPosition;
stepInserted(step);
}
void RenderGeometryMap::push(const RenderObject* renderer, const TransformationMatrix& t, bool accumulatingTransform, bool isNonUniform, bool isFixedPosition, bool hasTransform, LayoutSize offsetForFixedPosition)
void RenderGeometryMap::push(const RenderObject* renderer, const TransformationMatrix& t, bool accumulatingTransform, bool isNonUniform, bool hasTransform)
{
ASSERT(m_insertionPosition != kNotFound);
ASSERT(!renderer->isRenderView() || !m_insertionPosition || m_mapCoordinatesFlags & TraverseDocumentBoundaries);
ASSERT(offsetForFixedPosition.isZero() || renderer->isRenderView());
m_mapping.insert(m_insertionPosition, RenderGeometryMapStep(renderer, accumulatingTransform, isNonUniform, isFixedPosition, hasTransform));
m_mapping.insert(m_insertionPosition, RenderGeometryMapStep(renderer, accumulatingTransform, isNonUniform, hasTransform));
RenderGeometryMapStep& step = m_mapping[m_insertionPosition];
step.m_offsetForFixedPosition = offsetForFixedPosition;
if (!t.isIntegerTranslation())
step.m_transform = adoptPtr(new TransformationMatrix(t));
......@@ -301,9 +282,6 @@ void RenderGeometryMap::stepInserted(const RenderGeometryMapStep& step)
if (step.m_transform)
++m_transformedStepsCount;
if (step.m_isFixedPosition)
++m_fixedStepsCount;
}
void RenderGeometryMap::stepRemoved(const RenderGeometryMapStep& step)
......@@ -319,11 +297,6 @@ void RenderGeometryMap::stepRemoved(const RenderGeometryMapStep& step)
ASSERT(m_transformedStepsCount);
--m_transformedStepsCount;
}
if (step.m_isFixedPosition) {
ASSERT(m_fixedStepsCount);
--m_fixedStepsCount;
}
}
#if ENABLE(ASSERT)
......
......@@ -71,8 +71,8 @@ public:
// Push geometry info between this renderer and some ancestor. The ancestor must be its container() or some
// stacking context between the renderer and its container.
void push(const RenderObject*, const LayoutSize&, bool accumulatingTransform = false, bool isNonUniform = false, bool isFixedPosition = false, bool hasTransform = false, LayoutSize offsetForFixedPosition = LayoutSize());
void push(const RenderObject*, const TransformationMatrix&, bool accumulatingTransform = false, bool isNonUniform = false, bool isFixedPosition = false, bool hasTransform = false, LayoutSize offsetForFixedPosition = LayoutSize());
void push(const RenderObject*, const LayoutSize&, bool accumulatingTransform = false, bool isNonUniform = false, bool hasTransform = false);
void push(const RenderObject*, const TransformationMatrix&, bool accumulatingTransform = false, bool isNonUniform = false, bool hasTransform = false);
private:
void mapToContainer(TransformState&, const RenderLayerModelObject* container = 0) const;
......@@ -82,7 +82,6 @@ private:
bool hasNonUniformStep() const { return m_nonUniformStepsCount; }
bool hasTransformStep() const { return m_transformedStepsCount; }
bool hasFixedPositionStep() const { return m_fixedStepsCount; }
#ifndef NDEBUG
void dumpSteps() const;
......@@ -97,7 +96,6 @@ private:
size_t m_insertionPosition;
int m_nonUniformStepsCount;
int m_transformedStepsCount;
int m_fixedStepsCount;
RenderGeometryMapSteps m_mapping;
LayoutSize m_accumulatedOffset;
MapCoordinatesFlags m_mapCoordinatesFlags;
......
......@@ -40,29 +40,24 @@ struct RenderGeometryMapStep {
RenderGeometryMapStep(const RenderGeometryMapStep& o)
: m_renderer(o.m_renderer)
, m_offset(o.m_offset)
, m_offsetForFixedPosition(o.m_offsetForFixedPosition)
, m_accumulatingTransform(o.m_accumulatingTransform)
, m_isNonUniform(o.m_isNonUniform)
, m_isFixedPosition(o.m_isFixedPosition)
, m_hasTransform(o.m_hasTransform)
{
ASSERT(!o.m_transform);
}
RenderGeometryMapStep(const RenderObject* renderer, bool accumulatingTransform, bool isNonUniform, bool isFixedPosition, bool hasTransform)
RenderGeometryMapStep(const RenderObject* renderer, bool accumulatingTransform, bool isNonUniform, bool hasTransform)
: m_renderer(renderer)
, m_accumulatingTransform(accumulatingTransform)
, m_isNonUniform(isNonUniform)
, m_isFixedPosition(isFixedPosition)
, m_hasTransform(hasTransform)
{
}
const RenderObject* m_renderer;
LayoutSize m_offset;
OwnPtr<TransformationMatrix> m_transform; // Includes offset if non-null.
LayoutSize m_offsetForFixedPosition;
bool m_accumulatingTransform;
bool m_isNonUniform; // Mapping depends on the input point, e.g. because of CSS columns.
bool m_isFixedPosition;
bool m_hasTransform;
};
......
......@@ -251,7 +251,8 @@ void RenderLayer::dirtyAncestorChainHasSelfPaintingLayerDescendantStatus()
bool RenderLayer::scrollsWithViewport() const
{
return renderer()->style()->position() == FixedPosition && renderer()->containerForFixedPosition() == renderer()->view();
// FIXME(sky): Remove
return false;
}
bool RenderLayer::scrollsWithRespectTo(const RenderLayer* other) const
......@@ -602,11 +603,6 @@ FloatPoint RenderLayer::perspectiveOrigin() const
return FloatPoint(floatValueForLength(style->perspectiveOriginX(), borderBox.width().toFloat()), floatValueForLength(style->perspectiveOriginY(), borderBox.height().toFloat()));
}
static inline bool isFixedPositionedContainer(RenderLayer* layer)
{
return layer->isRootLayer() || layer->hasTransform();
}
RenderLayer* RenderLayer::enclosingPositionedAncestor() const
{
RenderLayer* curr = parent();
......@@ -1017,57 +1013,8 @@ static inline const RenderLayer* accumulateOffsetTowardsAncestor(const RenderLay
const RenderLayerModelObject* renderer = layer->renderer();
EPosition position = renderer->style()->position();
// FIXME: Positioning of out-of-flow(fixed, absolute) elements collected in a RenderFlowThread
// may need to be revisited in a future patch.
// If the fixed renderer is inside a RenderFlowThread, we should not compute location using localToAbsolute,
// since localToAbsolute maps the coordinates from flow thread to regions coordinates and regions can be
// positioned in a completely different place in the viewport (RenderView).
if (position == FixedPosition && (!ancestorLayer || ancestorLayer == renderer->view()->layer())) {
// If the fixed layer's container is the root, just add in the offset of the view. We can obtain this by calling
// localToAbsolute() on the RenderView.
FloatPoint absPos = renderer->localToAbsolute(FloatPoint(), IsFixed);
location += LayoutSize(absPos.x(), absPos.y());
return ancestorLayer;
}
// For the fixed positioned elements inside a render flow thread, we should also skip the code path below
// Otherwise, for the case of ancestorLayer == rootLayer and fixed positioned element child of a transformed
// element in render flow thread, we will hit the fixed positioned container before hitting the ancestor layer.
if (position == FixedPosition) {
// For a fixed layers, we need to walk up to the root to see if there's a fixed position container
// (e.g. a transformed layer). It's an error to call convertToLayerCoords() across a layer with a transform,
// so we should always find the ancestor at or before we find the fixed position container.
RenderLayer* fixedPositionContainerLayer = 0;
bool foundAncestor = false;
for (RenderLayer* currLayer = layer->parent(); currLayer; currLayer = currLayer->parent()) {
if (currLayer == ancestorLayer)
foundAncestor = true;
if (isFixedPositionedContainer(currLayer)) {
fixedPositionContainerLayer = currLayer;
ASSERT_UNUSED(foundAncestor, foundAncestor);
break;
}
}
ASSERT(fixedPositionContainerLayer); // We should have hit the RenderView's layer at least.
if (fixedPositionContainerLayer != ancestorLayer) {
LayoutPoint fixedContainerCoords;
layer->convertToLayerCoords(fixedPositionContainerLayer, fixedContainerCoords);
LayoutPoint ancestorCoords;
ancestorLayer->convertToLayerCoords(fixedPositionContainerLayer, ancestorCoords);
location += (fixedContainerCoords - ancestorCoords);
} else {
location += toSize(layer->location());
}
return ancestorLayer;
}
RenderLayer* parentLayer;
if (position == AbsolutePosition || position == FixedPosition) {
if (position == AbsolutePosition) {
// Do what enclosingPositionedAncestor() does, but check for ancestorLayer along the way.
parentLayer = layer->parent();
bool foundAncestorFirst = false;
......
......@@ -52,13 +52,7 @@ namespace blink {
static void adjustClipRectsForChildren(const RenderObject& renderer, ClipRects& clipRects)
{
EPosition position = renderer.style()->position();
// A fixed object is essentially the root of its containing block hierarchy, so when
// we encounter such an object, we reset our clip rects to the fixedClipRect.
if (position == FixedPosition) {
clipRects.setPosClipRect(clipRects.fixedClipRect());
clipRects.setOverflowClipRect(clipRects.fixedClipRect());
clipRects.setFixed(true);
} else if (position == RelativePosition) {
if (position == RelativePosition) {
clipRects.setPosClipRect(clipRects.overflowClipRect());
} else if (position == AbsolutePosition) {
clipRects.setOverflowClipRect(clipRects.posClipRect());
......@@ -81,7 +75,6 @@ static void applyClipRects(const ClipRectsContext& context, RenderObject& render
LayoutRect newClip = toRenderBox(renderer).clipRect(offset);
clipRects.setPosClipRect(intersection(newClip, clipRects.posClipRect()));
clipRects.setOverflowClipRect(intersection(newClip, clipRects.overflowClipRect()));
clipRects.setFixedClipRect(intersection(newClip, clipRects.fixedClipRect()));
}
}
......@@ -304,12 +297,8 @@ void RenderLayerClipper::calculateClipRects(const ClipRectsContext& context, Cli
static ClipRect backgroundClipRectForPosition(const ClipRects& parentRects, EPosition position)
{
if (position == FixedPosition)
return parentRects.fixedClipRect();
if (position == AbsolutePosition)
return parentRects.posClipRect();
return parentRects.overflowClipRect();
}
......
......@@ -71,18 +71,7 @@ ScrollableArea* RenderLayerModelObject::scrollableArea() const
void RenderLayerModelObject::willBeDestroyed()
{
if (isPositioned()) {
// Don't use this->view() because the document's renderView has been set to 0 during destruction.
if (LocalFrame* frame = this->frame()) {
if (FrameView* frameView = frame->view()) {
if (style()->hasViewportConstrainedPosition())
frameView->removeViewportConstrainedObject(this);
}
}
}
RenderObject::willBeDestroyed();
destroyLayer();
}
......@@ -137,17 +126,6 @@ void RenderLayerModelObject::styleDidChange(StyleDifference diff, const RenderSt
layer()->setLayerType(type);
layer()->styleChanged(diff, oldStyle);
}
if (FrameView *frameView = view()->frameView()) {
bool newStyleIsViewportConstained = style()->hasViewportConstrainedPosition();
bool oldStyleIsViewportConstrained = oldStyle && oldStyle->hasViewportConstrainedPosition();
if (newStyleIsViewportConstained != oldStyleIsViewportConstrained) {
if (newStyleIsViewportConstained && layer())
frameView->addViewportConstrainedObject(this);
else
frameView->removeViewportConstrainedObject(this);
}
}
}
void RenderLayerModelObject::addLayerHitTestRects(LayerHitTestRects& rects, const RenderLayer* currentLayer, const LayoutPoint& layerOffset, const LayoutRect& containerRect) const
......
......@@ -622,28 +622,10 @@ void RenderObject::invalidateContainerPreferredLogicalWidths()
}
}
RenderBlock* RenderObject::containerForFixedPosition(const RenderLayerModelObject* paintInvalidationContainer, bool* paintInvalidationContainerSkipped) const
{
ASSERT(!paintInvalidationContainerSkipped || !*paintInvalidationContainerSkipped);
ASSERT(!isText());
ASSERT(style()->position() == FixedPosition);
RenderObject* ancestor = parent();
for (; ancestor && !ancestor->canContainFixedPositionObjects(); ancestor = ancestor->parent()) {
if (paintInvalidationContainerSkipped && ancestor == paintInvalidationContainer)
*paintInvalidationContainerSkipped = true;
}
ASSERT(!ancestor || !ancestor->isAnonymousBlock());
return toRenderBlock(ancestor);
}
RenderBlock* RenderObject::containingBlock() const
{
RenderObject* o = parent();
if (!isText() && m_style->position() == FixedPosition) {
return containerForFixedPosition();
} else if (!isText() && m_style->position() == AbsolutePosition) {
if (!isText() && m_style->position() == AbsolutePosition) {
while (o) {
// For relpositioned inlines, we return the nearest non-anonymous enclosing block. We don't try
// to return the inline itself. This allows us to avoid having a positioned objects
......@@ -2300,9 +2282,7 @@ RenderObject* RenderObject::container(const RenderLayerModelObject* paintInvalid
return o;
EPosition pos = m_style->position();
if (pos == FixedPosition) {
return containerForFixedPosition(paintInvalidationContainer, paintInvalidationContainerSkipped);
} else if (pos == AbsolutePosition) {
if (pos == AbsolutePosition) {
// We technically just want our containing block, but
// we may not have one if we're part of an uninstalled
// subtree. We'll climb as high as we can though.
......@@ -2684,9 +2664,6 @@ Element* RenderObject::offsetParent() const
if (isDocumentElement())
return 0;
if (isOutOfFlowPositioned() && style()->position() == FixedPosition)
return 0;
// If A is an area HTML element which has a map HTML element somewhere in the ancestor
// chain return the nearest ancestor map HTML element and stop this algorithm.
// FIXME: Implement!
......
......@@ -523,7 +523,6 @@ public:
// If paintInvalidationContainer and paintInvalidationContainerSkipped are not null, on return *paintInvalidationContainerSkipped
// is true if the renderer returned is an ancestor of paintInvalidationContainer.
RenderObject* container(const RenderLayerModelObject* paintInvalidationContainer = 0, bool* paintInvalidationContainerSkipped = 0) const;
RenderBlock* containerForFixedPosition(const RenderLayerModelObject* paintInvalidationContainer = 0, bool* paintInvalidationContainerSkipped = 0) const;
virtual RenderObject* hoverAncestor() const { return parent(); }
......@@ -552,7 +551,7 @@ public:
void setPositionState(EPosition position)
{
ASSERT((position != AbsolutePosition && position != FixedPosition) || isBox());
ASSERT(position != AbsolutePosition || isBox());
m_bitfields.setPositionedState(position);
}
void clearPositionedState() { m_bitfields.clearPositionedState(); }
......@@ -1141,6 +1140,7 @@ private:
void setPositionedState(int positionState)
{
// FIXME(sky): Simplify now that we don't have FixedPosition.
// This mask maps FixedPosition and AbsolutePosition to IsOutOfFlowPositioned, saving one bit.
m_positionedState = static_cast<PositionedState>(positionState & 0x3);
}
......
......@@ -204,8 +204,6 @@ void RenderView::mapLocalToContainer(const RenderLayerModelObject* paintInvalida
const RenderObject* RenderView::pushMappingToContainer(const RenderLayerModelObject* ancestorToStopAt, RenderGeometryMap& geometryMap) const
{
// FIXME(sky): Can we remove offsetForFixedPosition?
LayoutSize offsetForFixedPosition;
LayoutSize offset;
RenderObject* container = 0;
......@@ -216,9 +214,9 @@ const RenderObject* RenderView::pushMappingToContainer(const RenderLayerModelObj
if ((!ancestorToStopAt || container) && shouldUseTransformFromContainer(container)) {
TransformationMatrix t;
getTransformFromContainer(container, LayoutSize(), t);
geometryMap.push(this, t, false, false, false, true, offsetForFixedPosition);
geometryMap.push(this, t, false, false, true);
} else {
geometryMap.push(this, offset, false, false, false, false, offsetForFixedPosition);
geometryMap.push(this, offset, false, false, false);
}
return container;
......
......@@ -33,18 +33,7 @@ static const RenderLayer* findParentLayerOnClippingContainerChain(const RenderLa
{
RenderObject* current = layer->renderer();
while (current) {
if (current->style()->position() == FixedPosition) {
for (current = current->parent(); current && !current->canContainFixedPositionObjects(); current = current->parent()) {
// CSS clip applies to fixed position elements even for ancestors that are not what the
// fixed element is positioned with respect to.
if (current->hasClip()) {
ASSERT(current->hasLayer());
return static_cast<const RenderLayerModelObject*>(current)->layer();
}
}
} else {
current = current->containingBlock();
}
current = current->containingBlock();
if (current->hasLayer())
return static_cast<const RenderLayerModelObject*>(current)->layer();
......
......@@ -408,9 +408,8 @@ public:
bool hasStaticBlockPosition(bool horizontal) const { return horizontal ? hasAutoTopAndBottom() : hasAutoLeftAndRight(); }
EPosition position() const { return static_cast<EPosition>(noninherited_flags.position); }
bool hasOutOfFlowPosition() const { return position() == AbsolutePosition || position() == FixedPosition; }
bool hasOutOfFlowPosition() const { return position() == AbsolutePosition; }
bool hasInFlowPosition() const { return position() == RelativePosition; }
bool hasViewportConstrainedPosition() const { return position() == FixedPosition; }
EFloat floating() const { return static_cast<EFloat>(noninherited_flags.floating); }
const Length& width() const { return m_box->width(); }
......
......@@ -73,9 +73,6 @@ enum EPosition {
StaticPosition = 0,
RelativePosition = 1,
AbsolutePosition = 2,
// This value is required to pack our bits efficiently in RenderObject.
// FIXME: Is this still true now that we've remove position: sticky.
FixedPosition = 6
};
enum EFloat {
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册