LayoutScrollbarPart* LayoutScrollbarPart::createAnonymous(Document* document, LayoutScrollbar* scrollbar, ScrollbarPart part)
{
    LayoutScrollbarPart* layoutObject = new LayoutScrollbarPart(scrollbar, part);
    recordScrollbarPartStats(*document, part);
    layoutObject->setDocumentForAnonymous(document);
    return layoutObject;
}
int LayoutScrollbar::minimumThumbLength() const
{
    LayoutScrollbarPart* partLayoutObject = m_parts.get(ThumbPart);
    if (!partLayoutObject)
        return 0;
    partLayoutObject->layout();
    return orientation() == HorizontalScrollbar ? partLayoutObject->size().width() : partLayoutObject->size().height();
}
void LayoutScrollbar::updateScrollbarPart(ScrollbarPart partType, bool destroy)
{
    if (partType == NoPart)
        return;

    RefPtr<ComputedStyle> partStyle = !destroy ? getScrollbarPseudoStyle(partType,  pseudoForScrollbarPart(partType)) : PassRefPtr<ComputedStyle>(nullptr);

    bool needLayoutObject = !destroy && partStyle && partStyle->display() != NONE;

    if (needLayoutObject && partStyle->display() != BLOCK) {
        // See if we are a button that should not be visible according to OS settings.
        ScrollbarButtonsPlacement buttonsPlacement = theme()->buttonsPlacement();
        switch (partType) {
        case BackButtonStartPart:
            needLayoutObject = (buttonsPlacement == ScrollbarButtonsPlacementSingle || buttonsPlacement == ScrollbarButtonsPlacementDoubleStart
                || buttonsPlacement == ScrollbarButtonsPlacementDoubleBoth);
            break;
        case ForwardButtonStartPart:
            needLayoutObject = (buttonsPlacement == ScrollbarButtonsPlacementDoubleStart || buttonsPlacement == ScrollbarButtonsPlacementDoubleBoth);
            break;
        case BackButtonEndPart:
            needLayoutObject = (buttonsPlacement == ScrollbarButtonsPlacementDoubleEnd || buttonsPlacement == ScrollbarButtonsPlacementDoubleBoth);
            break;
        case ForwardButtonEndPart:
            needLayoutObject = (buttonsPlacement == ScrollbarButtonsPlacementSingle || buttonsPlacement == ScrollbarButtonsPlacementDoubleEnd
                || buttonsPlacement == ScrollbarButtonsPlacementDoubleBoth);
            break;
        default:
            break;
        }
    }

    LayoutScrollbarPart* partLayoutObject = m_parts.get(partType);
    if (!partLayoutObject && needLayoutObject) {
        partLayoutObject = LayoutScrollbarPart::createAnonymous(&owningLayoutObject()->document(), this, partType);
        m_parts.set(partType, partLayoutObject);
    } else if (partLayoutObject && !needLayoutObject) {
        m_parts.remove(partType);
        partLayoutObject->destroy();
        partLayoutObject = 0;
    }

    if (partLayoutObject)
        partLayoutObject->setStyle(partStyle.release());
}
示例#4
0
void LayoutScrollbar::updateScrollbarParts(bool destroy) {
  updateScrollbarPart(ScrollbarBGPart, destroy);
  updateScrollbarPart(BackButtonStartPart, destroy);
  updateScrollbarPart(ForwardButtonStartPart, destroy);
  updateScrollbarPart(BackTrackPart, destroy);
  updateScrollbarPart(ThumbPart, destroy);
  updateScrollbarPart(ForwardTrackPart, destroy);
  updateScrollbarPart(BackButtonEndPart, destroy);
  updateScrollbarPart(ForwardButtonEndPart, destroy);
  updateScrollbarPart(TrackBGPart, destroy);

  if (destroy)
    return;

  // See if the scrollbar's thickness changed.  If so, we need to mark our
  // owning object as needing a layout.
  bool isHorizontal = orientation() == HorizontalScrollbar;
  int oldThickness = isHorizontal ? height() : width();
  int newThickness = 0;
  LayoutScrollbarPart* part = m_parts.get(ScrollbarBGPart);
  if (part) {
    part->layout();
    newThickness =
        (isHorizontal ? part->size().height() : part->size().width()).toInt();
  }

  if (newThickness != oldThickness) {
    setFrameRect(
        IntRect(location(), IntSize(isHorizontal ? width() : newThickness,
                                    isHorizontal ? newThickness : height())));
    if (LayoutBox* box = owningLayoutObjectWithinFrame()) {
      if (box->isLayoutBlock())
        toLayoutBlock(box)->notifyScrollbarThicknessChanged();
      box->setChildNeedsLayout();
      if (m_scrollableArea)
        m_scrollableArea->setScrollCornerNeedsPaintInvalidation();
    }
  }
}
IntRect LayoutScrollbar::trackPieceRectWithMargins(ScrollbarPart partType, const IntRect& oldRect) const
{
    LayoutScrollbarPart* partLayoutObject = m_parts.get(partType);
    if (!partLayoutObject)
        return oldRect;

    partLayoutObject->layout();

    IntRect rect = oldRect;
    if (orientation() == HorizontalScrollbar) {
        rect.setX(rect.x() + partLayoutObject->marginLeft());
        rect.setWidth(rect.width() - partLayoutObject->marginWidth());
    } else {
        rect.setY(rect.y() + partLayoutObject->marginTop());
        rect.setHeight(rect.height() - partLayoutObject->marginHeight());
    }
    return rect;
}
示例#6
0
IntRect LayoutScrollbar::trackRect(int startLength, int endLength) const {
  LayoutScrollbarPart* part = m_parts.get(TrackBGPart);
  if (part)
    part->layout();

  if (orientation() == HorizontalScrollbar) {
    int marginLeft = part ? part->marginLeft().toInt() : 0;
    int marginRight = part ? part->marginRight().toInt() : 0;
    startLength += marginLeft;
    endLength += marginRight;
    int totalLength = startLength + endLength;
    return IntRect(x() + startLength, y(), width() - totalLength, height());
  }

  int marginTop = part ? part->marginTop().toInt() : 0;
  int marginBottom = part ? part->marginBottom().toInt() : 0;
  startLength += marginTop;
  endLength += marginBottom;
  int totalLength = startLength + endLength;

  return IntRect(x(), y() + startLength, width(), height() - totalLength);
}
示例#7
0
IntRect LayoutScrollbar::buttonRect(ScrollbarPart partType) const {
  LayoutScrollbarPart* partLayoutObject = m_parts.get(partType);
  if (!partLayoutObject)
    return IntRect();

  partLayoutObject->layout();

  bool isHorizontal = orientation() == HorizontalScrollbar;
  if (partType == BackButtonStartPart)
    return IntRect(
        location(),
        IntSize(
            isHorizontal ? partLayoutObject->pixelSnappedWidth() : width(),
            isHorizontal ? height() : partLayoutObject->pixelSnappedHeight()));
  if (partType == ForwardButtonEndPart) {
    return IntRect(
        isHorizontal ? x() + width() - partLayoutObject->pixelSnappedWidth()
                     : x(),
        isHorizontal ? y()
                     : y() + height() - partLayoutObject->pixelSnappedHeight(),
        isHorizontal ? partLayoutObject->pixelSnappedWidth() : width(),
        isHorizontal ? height() : partLayoutObject->pixelSnappedHeight());
  }

  if (partType == ForwardButtonStartPart) {
    IntRect previousButton = buttonRect(BackButtonStartPart);
    return IntRect(
        isHorizontal ? x() + previousButton.width() : x(),
        isHorizontal ? y() : y() + previousButton.height(),
        isHorizontal ? partLayoutObject->pixelSnappedWidth() : width(),
        isHorizontal ? height() : partLayoutObject->pixelSnappedHeight());
  }

  IntRect followingButton = buttonRect(ForwardButtonEndPart);
  return IntRect(
      isHorizontal
          ? x() + width() - followingButton.width() -
                partLayoutObject->pixelSnappedWidth()
          : x(),
      isHorizontal ? y()
                   : y() + height() - followingButton.height() -
                         partLayoutObject->pixelSnappedHeight(),
      isHorizontal ? partLayoutObject->pixelSnappedWidth() : width(),
      isHorizontal ? height() : partLayoutObject->pixelSnappedHeight());
}
示例#8
0
void LayoutScrollbar::updateScrollbarPart(ScrollbarPart partType,
                                          bool destroy) {
  if (partType == NoPart)
    return;

  RefPtr<ComputedStyle> partStyle =
      !destroy
          ? getScrollbarPseudoStyle(partType, pseudoForScrollbarPart(partType))
          : PassRefPtr<ComputedStyle>(nullptr);

  bool needLayoutObject =
      !destroy && partStyle && partStyle->display() != EDisplay::None;

  if (needLayoutObject && partStyle->display() != EDisplay::Block) {
    // See if we are a button that should not be visible according to OS
    // settings.
    WebScrollbarButtonsPlacement buttonsPlacement = theme().buttonsPlacement();
    switch (partType) {
      case BackButtonStartPart:
        needLayoutObject =
            (buttonsPlacement == WebScrollbarButtonsPlacementSingle ||
             buttonsPlacement == WebScrollbarButtonsPlacementDoubleStart ||
             buttonsPlacement == WebScrollbarButtonsPlacementDoubleBoth);
        break;
      case ForwardButtonStartPart:
        needLayoutObject =
            (buttonsPlacement == WebScrollbarButtonsPlacementDoubleStart ||
             buttonsPlacement == WebScrollbarButtonsPlacementDoubleBoth);
        break;
      case BackButtonEndPart:
        needLayoutObject =
            (buttonsPlacement == WebScrollbarButtonsPlacementDoubleEnd ||
             buttonsPlacement == WebScrollbarButtonsPlacementDoubleBoth);
        break;
      case ForwardButtonEndPart:
        needLayoutObject =
            (buttonsPlacement == WebScrollbarButtonsPlacementSingle ||
             buttonsPlacement == WebScrollbarButtonsPlacementDoubleEnd ||
             buttonsPlacement == WebScrollbarButtonsPlacementDoubleBoth);
        break;
      default:
        break;
    }
  }

  LayoutScrollbarPart* partLayoutObject = m_parts.get(partType);
  if (!partLayoutObject && needLayoutObject && m_scrollableArea) {
    partLayoutObject = LayoutScrollbarPart::createAnonymous(
        &owningLayoutObject()->document(), m_scrollableArea, this, partType);
    m_parts.set(partType, partLayoutObject);
    setNeedsPaintInvalidation(partType);
  } else if (partLayoutObject && !needLayoutObject) {
    m_parts.remove(partType);
    partLayoutObject->destroy();
    partLayoutObject = nullptr;
    if (!destroy)
      setNeedsPaintInvalidation(partType);
  }

  if (partLayoutObject)
    partLayoutObject->setStyleWithWritingModeOfParent(partStyle.release());
}