OLD | NEW |
1 /* | 1 /* |
2 * Copyright (C) 2006, 2007, 2008, 2009, 2010, 2011, 2012 Apple Inc. All rights | 2 * Copyright (C) 2006, 2007, 2008, 2009, 2010, 2011, 2012 Apple Inc. All rights |
3 * reserved. | 3 * reserved. |
4 * | 4 * |
5 * Portions are Copyright (C) 1998 Netscape Communications Corporation. | 5 * Portions are Copyright (C) 1998 Netscape Communications Corporation. |
6 * | 6 * |
7 * Other contributors: | 7 * Other contributors: |
8 * Robert O'Callahan <roc+@cs.cmu.edu> | 8 * Robert O'Callahan <roc+@cs.cmu.edu> |
9 * David Baron <dbaron@fas.harvard.edu> | 9 * David Baron <dbaron@fas.harvard.edu> |
10 * Christian Biesinger <cbiesinger@gmail.com> | 10 * Christian Biesinger <cbiesinger@gmail.com> |
(...skipping 1195 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1206 if (&scrollbar == HorizontalScrollbar()) | 1206 if (&scrollbar == HorizontalScrollbar()) |
1207 return IntSize( | 1207 return IntSize( |
1208 HorizontalScrollbarStart(0), | 1208 HorizontalScrollbarStart(0), |
1209 (Box().Size().Height() - Box().BorderBottom() - scrollbar.Height()) | 1209 (Box().Size().Height() - Box().BorderBottom() - scrollbar.Height()) |
1210 .ToInt()); | 1210 .ToInt()); |
1211 | 1211 |
1212 NOTREACHED(); | 1212 NOTREACHED(); |
1213 return IntSize(); | 1213 return IntSize(); |
1214 } | 1214 } |
1215 | 1215 |
1216 static inline const LayoutObject& ScrollbarStyleSource( | 1216 LayoutObject* PaintLayerScrollableArea::LayoutObjectForScrollbarStyle() const { |
1217 const LayoutObject& layout_object) { | 1217 LayoutObject* layout_object = GetLayoutBox(); |
1218 if (Node* node = layout_object.GetNode()) { | 1218 Node* node = layout_object->GetNode(); |
1219 if (layout_object.IsLayoutView()) { | |
1220 Document& doc = node->GetDocument(); | |
1221 if (Settings* settings = doc.GetSettings()) { | |
1222 if (!settings->GetAllowCustomScrollbarInMainFrame() && | |
1223 layout_object.GetFrame() && layout_object.GetFrame()->IsMainFrame()) | |
1224 return layout_object; | |
1225 } | |
1226 | 1219 |
1227 // Try the <body> element first as a scrollbar source. | 1220 if (!node) |
1228 Element* body = doc.body(); | 1221 return nullptr; |
1229 if (body && body->GetLayoutObject() && | |
1230 body->GetLayoutObject()->Style()->HasPseudoStyle(kPseudoIdScrollbar)) | |
1231 return *body->GetLayoutObject(); | |
1232 | 1222 |
1233 // If the <body> didn't have a custom style, then the root element might. | 1223 if (layout_object->IsLayoutView()) { |
1234 Element* doc_element = doc.documentElement(); | 1224 Document& doc = node->GetDocument(); |
1235 if (doc_element && doc_element->GetLayoutObject() && | 1225 if (Settings* settings = doc.GetSettings()) { |
1236 doc_element->GetLayoutObject()->Style()->HasPseudoStyle( | 1226 if (!settings->GetAllowCustomScrollbarInMainFrame() && |
1237 kPseudoIdScrollbar)) | 1227 layout_object->GetFrame() && layout_object->GetFrame()->IsMainFrame()) |
1238 return *doc_element->GetLayoutObject(); | 1228 return nullptr; |
1239 } | 1229 } |
1240 | 1230 |
1241 if (layout_object.StyleRef().HasPseudoStyle(kPseudoIdScrollbar)) | 1231 // Try the <body> element first as a scrollbar source. |
1242 return layout_object; | 1232 Element* body = doc.body(); |
| 1233 if (body && body->GetLayoutObject() && |
| 1234 body->GetLayoutObject()->HasCustomScrollbarStyle()) |
| 1235 return body->GetLayoutObject(); |
1243 | 1236 |
1244 if (ShadowRoot* shadow_root = node->ContainingShadowRoot()) { | 1237 // If the <body> didn't have a custom style, then the root element might. |
1245 if (shadow_root->GetType() == ShadowRootType::kUserAgent) { | 1238 Element* doc_element = doc.documentElement(); |
1246 if (LayoutObject* host_layout_object = | 1239 if (doc_element && doc_element->GetLayoutObject() && |
1247 shadow_root->host().GetLayoutObject()) | 1240 doc_element->GetLayoutObject()->HasCustomScrollbarStyle()) |
1248 return *host_layout_object; | 1241 return doc_element->GetLayoutObject(); |
1249 } | 1242 } |
| 1243 |
| 1244 if (layout_object->HasCustomScrollbarStyle()) |
| 1245 return layout_object; |
| 1246 |
| 1247 if (ShadowRoot* shadow_root = node->ContainingShadowRoot()) { |
| 1248 if (shadow_root->GetType() == ShadowRootType::kUserAgent) { |
| 1249 LayoutObject* host_layout_object = shadow_root->host().GetLayoutObject(); |
| 1250 if (host_layout_object && host_layout_object->HasCustomScrollbarStyle()) |
| 1251 return host_layout_object; |
1250 } | 1252 } |
1251 } | 1253 } |
1252 | 1254 |
1253 return layout_object; | 1255 return nullptr; |
1254 } | 1256 } |
1255 | 1257 |
1256 bool PaintLayerScrollableArea::NeedsScrollbarReconstruction() const { | 1258 bool PaintLayerScrollableArea::NeedsScrollbarReconstruction() const { |
1257 const LayoutObject& style_source = ScrollbarStyleSource(Box()); | 1259 LayoutObject* style_source = LayoutObjectForScrollbarStyle(); |
1258 bool should_use_custom = | 1260 bool should_use_custom = |
1259 style_source.IsBox() && | 1261 style_source && style_source->HasCustomScrollbarStyle(); |
1260 style_source.StyleRef().HasPseudoStyle(kPseudoIdScrollbar); | |
1261 bool has_any_scrollbar = HasScrollbar(); | 1262 bool has_any_scrollbar = HasScrollbar(); |
1262 bool has_custom = | 1263 bool has_custom = |
1263 (HasHorizontalScrollbar() && | 1264 (HasHorizontalScrollbar() && |
1264 HorizontalScrollbar()->IsCustomScrollbar()) || | 1265 HorizontalScrollbar()->IsCustomScrollbar()) || |
1265 (HasVerticalScrollbar() && VerticalScrollbar()->IsCustomScrollbar()); | 1266 (HasVerticalScrollbar() && VerticalScrollbar()->IsCustomScrollbar()); |
1266 bool did_custom_scrollbar_owner_changed = false; | 1267 bool did_custom_scrollbar_owner_changed = false; |
1267 | 1268 |
1268 if (HasHorizontalScrollbar() && HorizontalScrollbar()->IsCustomScrollbar()) { | 1269 if (HasHorizontalScrollbar() && HorizontalScrollbar()->IsCustomScrollbar()) { |
1269 if (style_source != ToLayoutScrollbar(HorizontalScrollbar())->StyleSource()) | 1270 if (style_source && |
| 1271 *style_source != |
| 1272 ToLayoutScrollbar(HorizontalScrollbar())->StyleSource()) |
1270 did_custom_scrollbar_owner_changed = true; | 1273 did_custom_scrollbar_owner_changed = true; |
1271 } | 1274 } |
1272 | 1275 |
1273 if (HasVerticalScrollbar() && VerticalScrollbar()->IsCustomScrollbar()) { | 1276 if (HasVerticalScrollbar() && VerticalScrollbar()->IsCustomScrollbar()) { |
1274 if (style_source != ToLayoutScrollbar(VerticalScrollbar())->StyleSource()) | 1277 if (style_source && |
| 1278 *style_source != ToLayoutScrollbar(VerticalScrollbar())->StyleSource()) |
1275 did_custom_scrollbar_owner_changed = true; | 1279 did_custom_scrollbar_owner_changed = true; |
1276 } | 1280 } |
1277 | 1281 |
1278 return has_any_scrollbar && | 1282 return has_any_scrollbar && |
1279 ((should_use_custom != has_custom) || | 1283 ((should_use_custom != has_custom) || |
1280 (should_use_custom && did_custom_scrollbar_owner_changed)); | 1284 (should_use_custom && did_custom_scrollbar_owner_changed)); |
1281 } | 1285 } |
1282 | 1286 |
1283 void PaintLayerScrollableArea::ComputeScrollbarExistence( | 1287 void PaintLayerScrollableArea::ComputeScrollbarExistence( |
1284 bool& needs_horizontal_scrollbar, | 1288 bool& needs_horizontal_scrollbar, |
(...skipping 170 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1455 if (Layer()->HasCompositedLayerMapping()) | 1459 if (Layer()->HasCompositedLayerMapping()) |
1456 Layer()->GetCompositedLayerMapping()->PositionOverflowControlsLayers(); | 1460 Layer()->GetCompositedLayerMapping()->PositionOverflowControlsLayers(); |
1457 } | 1461 } |
1458 | 1462 |
1459 void PaintLayerScrollableArea::UpdateScrollCornerStyle() { | 1463 void PaintLayerScrollableArea::UpdateScrollCornerStyle() { |
1460 if (!scroll_corner_ && !HasScrollbar()) | 1464 if (!scroll_corner_ && !HasScrollbar()) |
1461 return; | 1465 return; |
1462 if (!scroll_corner_ && HasOverlayScrollbars()) | 1466 if (!scroll_corner_ && HasOverlayScrollbars()) |
1463 return; | 1467 return; |
1464 | 1468 |
1465 const LayoutObject& style_source = ScrollbarStyleSource(Box()); | 1469 const LayoutObject* style_source = LayoutObjectForScrollbarStyle(); |
| 1470 |
1466 RefPtr<ComputedStyle> corner = | 1471 RefPtr<ComputedStyle> corner = |
1467 Box().HasOverflowClip() | 1472 Box().HasOverflowClip() && style_source |
1468 ? style_source.GetUncachedPseudoStyle( | 1473 ? style_source->GetUncachedPseudoStyle( |
1469 PseudoStyleRequest(kPseudoIdScrollbarCorner), | 1474 PseudoStyleRequest(kPseudoIdScrollbarCorner), |
1470 style_source.Style()) | 1475 style_source->Style()) |
1471 : PassRefPtr<ComputedStyle>(nullptr); | 1476 : PassRefPtr<ComputedStyle>(nullptr); |
1472 if (corner) { | 1477 if (corner) { |
1473 if (!scroll_corner_) { | 1478 if (!scroll_corner_) { |
1474 scroll_corner_ = | 1479 scroll_corner_ = |
1475 LayoutScrollbarPart::CreateAnonymous(&Box().GetDocument(), this); | 1480 LayoutScrollbarPart::CreateAnonymous(&Box().GetDocument(), this); |
1476 scroll_corner_->SetDangerousOneWayParent(&Box()); | 1481 scroll_corner_->SetDangerousOneWayParent(&Box()); |
1477 } | 1482 } |
1478 scroll_corner_->SetStyleWithWritingModeOfParent(std::move(corner)); | 1483 scroll_corner_->SetStyleWithWritingModeOfParent(std::move(corner)); |
1479 } else if (scroll_corner_) { | 1484 } else if (scroll_corner_) { |
1480 scroll_corner_->Destroy(); | 1485 scroll_corner_->Destroy(); |
(...skipping 137 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1618 if (Box().CanResize()) | 1623 if (Box().CanResize()) |
1619 frame_view->AddResizerArea(Box()); | 1624 frame_view->AddResizerArea(Box()); |
1620 else | 1625 else |
1621 frame_view->RemoveResizerArea(Box()); | 1626 frame_view->RemoveResizerArea(Box()); |
1622 } | 1627 } |
1623 | 1628 |
1624 void PaintLayerScrollableArea::UpdateResizerStyle() { | 1629 void PaintLayerScrollableArea::UpdateResizerStyle() { |
1625 if (!resizer_ && !Box().CanResize()) | 1630 if (!resizer_ && !Box().CanResize()) |
1626 return; | 1631 return; |
1627 | 1632 |
1628 const LayoutObject& style_source = ScrollbarStyleSource(Box()); | 1633 const LayoutObject* style_source = LayoutObjectForScrollbarStyle(); |
| 1634 |
1629 RefPtr<ComputedStyle> resizer = | 1635 RefPtr<ComputedStyle> resizer = |
1630 Box().HasOverflowClip() | 1636 Box().HasOverflowClip() && style_source |
1631 ? style_source.GetUncachedPseudoStyle( | 1637 ? style_source->GetUncachedPseudoStyle( |
1632 PseudoStyleRequest(kPseudoIdResizer), style_source.Style()) | 1638 PseudoStyleRequest(kPseudoIdResizer), style_source->Style()) |
1633 : PassRefPtr<ComputedStyle>(nullptr); | 1639 : PassRefPtr<ComputedStyle>(nullptr); |
1634 if (resizer) { | 1640 if (resizer) { |
1635 if (!resizer_) { | 1641 if (!resizer_) { |
1636 resizer_ = | 1642 resizer_ = |
1637 LayoutScrollbarPart::CreateAnonymous(&Box().GetDocument(), this); | 1643 LayoutScrollbarPart::CreateAnonymous(&Box().GetDocument(), this); |
1638 resizer_->SetDangerousOneWayParent(&Box()); | 1644 resizer_->SetDangerousOneWayParent(&Box()); |
1639 } | 1645 } |
1640 resizer_->SetStyleWithWritingModeOfParent(std::move(resizer)); | 1646 resizer_->SetStyleWithWritingModeOfParent(std::move(resizer)); |
1641 } else if (resizer_) { | 1647 } else if (resizer_) { |
1642 resizer_->Destroy(); | 1648 resizer_->Destroy(); |
(...skipping 405 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2048 | 2054 |
2049 void PaintLayerScrollableArea::ScrollbarManager::SetHasHorizontalScrollbar( | 2055 void PaintLayerScrollableArea::ScrollbarManager::SetHasHorizontalScrollbar( |
2050 bool has_scrollbar) { | 2056 bool has_scrollbar) { |
2051 if (has_scrollbar) { | 2057 if (has_scrollbar) { |
2052 // This doesn't hit in any tests, but since the equivalent code in | 2058 // This doesn't hit in any tests, but since the equivalent code in |
2053 // setHasVerticalScrollbar does, presumably this code does as well. | 2059 // setHasVerticalScrollbar does, presumably this code does as well. |
2054 DisableCompositingQueryAsserts disabler; | 2060 DisableCompositingQueryAsserts disabler; |
2055 if (!h_bar_) { | 2061 if (!h_bar_) { |
2056 h_bar_ = CreateScrollbar(kHorizontalScrollbar); | 2062 h_bar_ = CreateScrollbar(kHorizontalScrollbar); |
2057 h_bar_is_attached_ = 1; | 2063 h_bar_is_attached_ = 1; |
2058 if (!h_bar_->IsCustomScrollbar()) | 2064 ScrollableArea()->DidAddScrollbar(*h_bar_, kHorizontalScrollbar); |
2059 ScrollableArea()->DidAddScrollbar(*h_bar_, kHorizontalScrollbar); | |
2060 } else { | 2065 } else { |
2061 h_bar_is_attached_ = 1; | 2066 h_bar_is_attached_ = 1; |
2062 } | 2067 } |
2063 } else { | 2068 } else { |
2064 h_bar_is_attached_ = 0; | 2069 h_bar_is_attached_ = 0; |
2065 if (!DelayScrollOffsetClampScope::ClampingIsDelayed()) | 2070 if (!DelayScrollOffsetClampScope::ClampingIsDelayed()) |
2066 DestroyScrollbar(kHorizontalScrollbar); | 2071 DestroyScrollbar(kHorizontalScrollbar); |
2067 } | 2072 } |
2068 } | 2073 } |
2069 | 2074 |
2070 void PaintLayerScrollableArea::ScrollbarManager::SetHasVerticalScrollbar( | 2075 void PaintLayerScrollableArea::ScrollbarManager::SetHasVerticalScrollbar( |
2071 bool has_scrollbar) { | 2076 bool has_scrollbar) { |
2072 if (has_scrollbar) { | 2077 if (has_scrollbar) { |
2073 DisableCompositingQueryAsserts disabler; | 2078 DisableCompositingQueryAsserts disabler; |
2074 if (!v_bar_) { | 2079 if (!v_bar_) { |
2075 v_bar_ = CreateScrollbar(kVerticalScrollbar); | 2080 v_bar_ = CreateScrollbar(kVerticalScrollbar); |
2076 v_bar_is_attached_ = 1; | 2081 v_bar_is_attached_ = 1; |
2077 if (!v_bar_->IsCustomScrollbar()) | 2082 ScrollableArea()->DidAddScrollbar(*v_bar_, kVerticalScrollbar); |
2078 ScrollableArea()->DidAddScrollbar(*v_bar_, kVerticalScrollbar); | |
2079 } else { | 2083 } else { |
2080 v_bar_is_attached_ = 1; | 2084 v_bar_is_attached_ = 1; |
2081 } | 2085 } |
2082 } else { | 2086 } else { |
2083 v_bar_is_attached_ = 0; | 2087 v_bar_is_attached_ = 0; |
2084 if (!DelayScrollOffsetClampScope::ClampingIsDelayed()) | 2088 if (!DelayScrollOffsetClampScope::ClampingIsDelayed()) |
2085 DestroyScrollbar(kVerticalScrollbar); | 2089 DestroyScrollbar(kVerticalScrollbar); |
2086 } | 2090 } |
2087 } | 2091 } |
2088 | 2092 |
2089 Scrollbar* PaintLayerScrollableArea::ScrollbarManager::CreateScrollbar( | 2093 void PaintLayerScrollableArea::WillRemoveScrollbar( |
| 2094 Scrollbar& scrollbar, |
2090 ScrollbarOrientation orientation) { | 2095 ScrollbarOrientation orientation) { |
2091 DCHECK(orientation == kHorizontalScrollbar ? !h_bar_is_attached_ | 2096 SetScrollbarNeedsPaintInvalidation(orientation); |
2092 : !v_bar_is_attached_); | 2097 if (orientation == kHorizontalScrollbar) |
2093 Scrollbar* scrollbar = nullptr; | 2098 rebuild_horizontal_scrollbar_layer_ = true; |
2094 const LayoutObject& style_source = | 2099 else |
2095 ScrollbarStyleSource(ScrollableArea()->Box()); | 2100 rebuild_vertical_scrollbar_layer_ = true; |
2096 bool has_custom_scrollbar_style = | |
2097 style_source.IsBox() && | |
2098 style_source.StyleRef().HasPseudoStyle(kPseudoIdScrollbar); | |
2099 if (has_custom_scrollbar_style) { | |
2100 DCHECK(style_source.GetNode() && style_source.GetNode()->IsElementNode()); | |
2101 scrollbar = LayoutScrollbar::CreateCustomScrollbar( | |
2102 ScrollableArea(), orientation, ToElement(style_source.GetNode())); | |
2103 } else { | |
2104 ScrollbarControlSize scrollbar_size = kRegularScrollbar; | |
2105 if (style_source.StyleRef().HasAppearance()) { | |
2106 scrollbar_size = LayoutTheme::GetTheme().ScrollbarControlSizeForPart( | |
2107 style_source.StyleRef().Appearance()); | |
2108 } | |
2109 scrollbar = Scrollbar::Create( | |
2110 ScrollableArea(), orientation, scrollbar_size, | |
2111 &ScrollableArea()->Box().GetFrame()->GetPage()->GetChromeClient()); | |
2112 } | |
2113 ScrollableArea()->Box().GetDocument().View()->AddScrollbar(scrollbar); | |
2114 return scrollbar; | |
2115 } | |
2116 | 2101 |
2117 void PaintLayerScrollableArea::ScrollbarManager::DestroyScrollbar( | 2102 PaintInvalidationCapableScrollableArea::WillRemoveScrollbar(scrollbar, |
2118 ScrollbarOrientation orientation) { | 2103 orientation); |
2119 Member<Scrollbar>& scrollbar = | |
2120 orientation == kHorizontalScrollbar ? h_bar_ : v_bar_; | |
2121 DCHECK(orientation == kHorizontalScrollbar ? !h_bar_is_attached_ | |
2122 : !v_bar_is_attached_); | |
2123 if (!scrollbar) | |
2124 return; | |
2125 | |
2126 ScrollableArea()->SetScrollbarNeedsPaintInvalidation(orientation); | |
2127 if (orientation == kHorizontalScrollbar) | |
2128 ScrollableArea()->rebuild_horizontal_scrollbar_layer_ = true; | |
2129 else | |
2130 ScrollableArea()->rebuild_vertical_scrollbar_layer_ = true; | |
2131 | |
2132 if (!scrollbar->IsCustomScrollbar()) | |
2133 ScrollableArea()->WillRemoveScrollbar(*scrollbar, orientation); | |
2134 | |
2135 ScrollableArea()->Box().GetDocument().View()->RemoveScrollbar(scrollbar); | |
2136 scrollbar->DisconnectFromScrollableArea(); | |
2137 scrollbar = nullptr; | |
2138 } | 2104 } |
2139 | 2105 |
2140 uint64_t PaintLayerScrollableArea::Id() const { | 2106 uint64_t PaintLayerScrollableArea::Id() const { |
2141 return DOMNodeIds::IdForNode(Box().GetNode()); | 2107 return DOMNodeIds::IdForNode(Box().GetNode()); |
2142 } | 2108 } |
2143 | 2109 |
2144 int PaintLayerScrollableArea::PreventRelayoutScope::count_ = 0; | 2110 int PaintLayerScrollableArea::PreventRelayoutScope::count_ = 0; |
2145 SubtreeLayoutScope* | 2111 SubtreeLayoutScope* |
2146 PaintLayerScrollableArea::PreventRelayoutScope::layout_scope_ = nullptr; | 2112 PaintLayerScrollableArea::PreventRelayoutScope::layout_scope_ = nullptr; |
2147 bool PaintLayerScrollableArea::PreventRelayoutScope::relayout_needed_ = false; | 2113 bool PaintLayerScrollableArea::PreventRelayoutScope::relayout_needed_ = false; |
(...skipping 95 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2243 | 2209 |
2244 void PaintLayerScrollableArea::DelayScrollOffsetClampScope:: | 2210 void PaintLayerScrollableArea::DelayScrollOffsetClampScope:: |
2245 ClampScrollableAreas() { | 2211 ClampScrollableAreas() { |
2246 for (auto& scrollable_area : *needs_clamp_) | 2212 for (auto& scrollable_area : *needs_clamp_) |
2247 scrollable_area->ClampScrollOffsetAfterOverflowChange(); | 2213 scrollable_area->ClampScrollOffsetAfterOverflowChange(); |
2248 delete needs_clamp_; | 2214 delete needs_clamp_; |
2249 needs_clamp_ = nullptr; | 2215 needs_clamp_ = nullptr; |
2250 } | 2216 } |
2251 | 2217 |
2252 } // namespace blink | 2218 } // namespace blink |
OLD | NEW |