Example #1
0
ShapeOutsideDeltas ShapeOutsideInfo::computeDeltasForContainingBlockLine(
    const LineLayoutBlockFlow& containingBlock,
    const FloatingObject& floatingObject,
    LayoutUnit lineTop,
    LayoutUnit lineHeight) {
  ASSERT(lineHeight >= 0);

  LayoutUnit borderBoxTop = containingBlock.logicalTopForFloat(floatingObject) +
                            containingBlock.marginBeforeForChild(m_layoutBox);
  LayoutUnit borderBoxLineTop = lineTop - borderBoxTop;

  if (isShapeDirty() ||
      !m_shapeOutsideDeltas.isForLine(borderBoxLineTop, lineHeight)) {
    LayoutUnit referenceBoxLineTop = borderBoxLineTop - logicalTopOffset();
    LayoutUnit floatMarginBoxWidth = std::max(
        containingBlock.logicalWidthForFloat(floatingObject), LayoutUnit());

    if (computedShape().lineOverlapsShapeMarginBounds(referenceBoxLineTop,
                                                      lineHeight)) {
      LineSegment segment = computedShape().getExcludedInterval(
          (borderBoxLineTop - logicalTopOffset()),
          std::min(lineHeight, shapeLogicalBottom() - borderBoxLineTop));
      if (segment.isValid) {
        LayoutUnit logicalLeftMargin =
            containingBlock.style()->isLeftToRightDirection()
                ? containingBlock.marginStartForChild(m_layoutBox)
                : containingBlock.marginEndForChild(m_layoutBox);
        LayoutUnit rawLeftMarginBoxDelta(
            segment.logicalLeft + logicalLeftOffset() + logicalLeftMargin);
        LayoutUnit leftMarginBoxDelta = clampTo<LayoutUnit>(
            rawLeftMarginBoxDelta, LayoutUnit(), floatMarginBoxWidth);

        LayoutUnit logicalRightMargin =
            containingBlock.style()->isLeftToRightDirection()
                ? containingBlock.marginEndForChild(m_layoutBox)
                : containingBlock.marginStartForChild(m_layoutBox);
        LayoutUnit rawRightMarginBoxDelta(
            segment.logicalRight + logicalLeftOffset() -
            containingBlock.logicalWidthForChild(m_layoutBox) -
            logicalRightMargin);
        LayoutUnit rightMarginBoxDelta = clampTo<LayoutUnit>(
            rawRightMarginBoxDelta, -floatMarginBoxWidth, LayoutUnit());

        m_shapeOutsideDeltas =
            ShapeOutsideDeltas(leftMarginBoxDelta, rightMarginBoxDelta, true,
                               borderBoxLineTop, lineHeight);
        return m_shapeOutsideDeltas;
      }
    }

    // Lines that do not overlap the shape should act as if the float
    // wasn't there for layout purposes. So we set the deltas to remove the
    // entire width of the float.
    m_shapeOutsideDeltas =
        ShapeOutsideDeltas(floatMarginBoxWidth, -floatMarginBoxWidth, false,
                           borderBoxLineTop, lineHeight);
  }

  return m_shapeOutsideDeltas;
}
LayoutUnit ShapeInsideInfo::computeFirstFitPositionForFloat(const FloatSize& floatSize) const
{
    if (!computedShape() || !floatSize.width() || shapeLogicalBottom() < logicalLineTop())
        return 0;

    LayoutUnit firstFitPosition = 0;
    if (computedShape()->firstIncludedIntervalLogicalTop(m_shapeLineTop, floatSize, firstFitPosition) && (m_shapeLineTop <= firstFitPosition))
        return firstFitPosition;

    return 0;
}
Example #3
0
bool ExclusionShapeInsideInfo::computeSegmentsForLine(LayoutUnit lineTop, LayoutUnit lineHeight)
{
    ASSERT(lineHeight >= 0);
    m_lineTop = lineTop;
    m_lineHeight = lineHeight;
    m_segments.clear();
    m_segmentRanges.clear();

    if (lineOverlapsShapeBounds()) {
        ASSERT(m_shape);
        m_shape->getIncludedIntervals(lineTop, std::min(lineHeight, shapeLogicalBottom() - lineTop), m_segments);
    }
    return m_segments.size();
}
Example #4
0
SegmentList ShapeInfo<RenderType>::computeSegmentsForLine(LayoutUnit lineTop, LayoutUnit lineHeight) const
{
    ASSERT(lineHeight >= 0);
    SegmentList segments;

    getIntervals((lineTop - logicalTopOffset()), std::min(lineHeight, shapeLogicalBottom() - lineTop), segments);

    for (size_t i = 0; i < segments.size(); i++) {
        segments[i].logicalLeft += logicalLeftOffset();
        segments[i].logicalRight += logicalLeftOffset();
    }

    return segments;
}
Example #5
0
bool ExclusionShapeInsideInfo::adjustLogicalLineTop(float minSegmentWidth)
{
    if (!m_shape || m_lineHeight <= 0 || m_lineTop > shapeLogicalBottom())
        return false;

    float floatNewLineTop;
    if (m_shape->firstIncludedIntervalLogicalTop(m_lineTop, FloatSize(minSegmentWidth, m_lineHeight), floatNewLineTop)) {
        LayoutUnit newLineTop = floatLogicalTopToLayoutUnit(floatNewLineTop);
        if (newLineTop > m_lineTop) {
            m_lineTop = newLineTop;
            return true;
        }
    }

    return false;
}
Example #6
0
bool ExclusionShapeInsideInfo::adjustLogicalLineTop(float minSegmentWidth)
{
    const ExclusionShape* shape = computedShape();
    if (!shape || m_lineHeight <= 0 || logicalLineTop() > shapeLogicalBottom())
        return false;

    LayoutUnit newLineTop;
    if (shape->firstIncludedIntervalLogicalTop(m_shapeLineTop, LayoutSize(minSegmentWidth, m_lineHeight), newLineTop)) {
        if (newLineTop > m_shapeLineTop) {
            m_shapeLineTop = newLineTop;
            return true;
        }
    }

    return false;
}
Example #7
0
bool ShapeInfo<RenderType, shapeGetter, intervalGetter>::computeSegmentsForLine(LayoutUnit lineTop, LayoutUnit lineHeight)
{
    ASSERT(lineHeight >= 0);
    m_shapeLineTop = lineTop - logicalTopOffset();
    m_lineHeight = lineHeight;
    m_segments.clear();

    if (lineOverlapsShapeBounds())
        (computedShape()->*intervalGetter)(m_shapeLineTop, std::min(m_lineHeight, shapeLogicalBottom() - lineTop), m_segments);

    LayoutUnit logicalLeftOffset = this->logicalLeftOffset();
    for (size_t i = 0; i < m_segments.size(); i++) {
        m_segments[i].logicalLeft += logicalLeftOffset;
        m_segments[i].logicalRight += logicalLeftOffset;
    }

    return m_segments.size();
}
Example #8
0
void ShapeOutsideInfo::updateDeltasForContainingBlockLine(const RenderBlockFlow& containingBlock, const FloatingObject& floatingObject, LayoutUnit lineTop, LayoutUnit lineHeight)
{
    ASSERT(lineHeight >= 0);

    LayoutUnit borderBoxTop = containingBlock.logicalTopForFloat(&floatingObject) + containingBlock.marginBeforeForChild(m_renderer);
    LayoutUnit borderBoxLineTop = lineTop - borderBoxTop;

    if (isShapeDirty() || m_borderBoxLineTop != borderBoxLineTop || m_lineHeight != lineHeight) {
        m_borderBoxLineTop = borderBoxLineTop;
        m_referenceBoxLineTop = borderBoxLineTop - logicalTopOffset();
        m_lineHeight = lineHeight;

        LayoutUnit floatMarginBoxWidth = containingBlock.logicalWidthForFloat(&floatingObject);

        if (computedShape().lineOverlapsShapeMarginBounds(m_referenceBoxLineTop, m_lineHeight)) {
            LineSegment segment = computedShape().getExcludedInterval((borderBoxLineTop - logicalTopOffset()), std::min(lineHeight, shapeLogicalBottom() - borderBoxLineTop));
            if (segment.isValid) {
                LayoutUnit logicalLeftMargin = containingBlock.style().isLeftToRightDirection() ? containingBlock.marginStartForChild(m_renderer) : containingBlock.marginEndForChild(m_renderer);
                LayoutUnit rawLeftMarginBoxDelta = segment.logicalLeft + logicalLeftOffset() + logicalLeftMargin;
                m_leftMarginBoxDelta = clampTo<LayoutUnit>(rawLeftMarginBoxDelta, LayoutUnit(), floatMarginBoxWidth);

                LayoutUnit logicalRightMargin = containingBlock.style().isLeftToRightDirection() ? containingBlock.marginEndForChild(m_renderer) : containingBlock.marginStartForChild(m_renderer);
                LayoutUnit rawRightMarginBoxDelta = segment.logicalRight + logicalLeftOffset() - containingBlock.logicalWidthForChild(m_renderer) - logicalRightMargin;
                m_rightMarginBoxDelta = clampTo<LayoutUnit>(rawRightMarginBoxDelta, -floatMarginBoxWidth, LayoutUnit());
                m_lineOverlapsShape = true;
                return;
            }
        }

        // Lines that do not overlap the shape should act as if the float
        // wasn't there for layout purposes. So we set the deltas to remove the
        // entire width of the float
        m_leftMarginBoxDelta = floatMarginBoxWidth;
        m_rightMarginBoxDelta = -floatMarginBoxWidth;
        m_lineOverlapsShape = false;
    }
}